diff options
Diffstat (limited to 'src/lib')
| -rw-r--r-- | src/lib/openjp2/j2k.c | 88 | ||||
| -rw-r--r-- | src/lib/openjp2/openjpeg.h | 7 | ||||
| -rw-r--r-- | src/lib/openjp2/tcd.c | 46 |
3 files changed, 107 insertions, 34 deletions
diff --git a/src/lib/openjp2/j2k.c b/src/lib/openjp2/j2k.c index 8e4b3966..641932a9 100644 --- a/src/lib/openjp2/j2k.c +++ b/src/lib/openjp2/j2k.c @@ -6832,25 +6832,84 @@ OPJ_BOOL opj_j2k_setup_encoder(opj_j2k_t *p_j2k, parameters->tcp_rates[0] = 0; } + if (parameters->cp_disto_alloc) { + /* Emit warnings if tcp_rates are not decreasing */ + for (i = 1; i < (OPJ_UINT32) parameters->tcp_numlayers; i++) { + OPJ_FLOAT32 rate_i_corr = parameters->tcp_rates[i]; + OPJ_FLOAT32 rate_i_m_1_corr = parameters->tcp_rates[i - 1]; + if (rate_i_corr <= 1.0) { + rate_i_corr = 1.0; + } + if (rate_i_m_1_corr <= 1.0) { + rate_i_m_1_corr = 1.0; + } + if (rate_i_corr >= rate_i_m_1_corr) { + if (rate_i_corr != parameters->tcp_rates[i] && + rate_i_m_1_corr != parameters->tcp_rates[i - 1]) { + opj_event_msg(p_manager, EVT_WARNING, + "tcp_rates[%d]=%f (corrected as %f) should be strictly lesser " + "than tcp_rates[%d]=%f (corrected as %f)\n", + i, parameters->tcp_rates[i], rate_i_corr, + i - 1, parameters->tcp_rates[i - 1], rate_i_m_1_corr); + } else if (rate_i_corr != parameters->tcp_rates[i]) { + opj_event_msg(p_manager, EVT_WARNING, + "tcp_rates[%d]=%f (corrected as %f) should be strictly lesser " + "than tcp_rates[%d]=%f\n", + i, parameters->tcp_rates[i], rate_i_corr, + i - 1, parameters->tcp_rates[i - 1]); + } else if (rate_i_m_1_corr != parameters->tcp_rates[i - 1]) { + opj_event_msg(p_manager, EVT_WARNING, + "tcp_rates[%d]=%f should be strictly lesser " + "than tcp_rates[%d]=%f (corrected as %f)\n", + i, parameters->tcp_rates[i], + i - 1, parameters->tcp_rates[i - 1], rate_i_m_1_corr); + } else { + opj_event_msg(p_manager, EVT_WARNING, + "tcp_rates[%d]=%f should be strictly lesser " + "than tcp_rates[%d]=%f\n", + i, parameters->tcp_rates[i], + i - 1, parameters->tcp_rates[i - 1]); + } + } + } + } else if (parameters->cp_fixed_quality) { + /* Emit warnings if tcp_distoratio are not increasing */ + for (i = 1; i < (OPJ_UINT32) parameters->tcp_numlayers; i++) { + if (parameters->tcp_distoratio[i] < parameters->tcp_distoratio[i - 1] && + !(i == (OPJ_UINT32)parameters->tcp_numlayers - 1 && + parameters->tcp_distoratio[i] == 0)) { + opj_event_msg(p_manager, EVT_WARNING, + "tcp_distoratio[%d]=%f should be strictly greater " + "than tcp_distoratio[%d]=%f\n", + i, parameters->tcp_distoratio[i], i - 1, + parameters->tcp_distoratio[i - 1]); + } + } + } + /* see if max_codestream_size does limit input rate */ if (parameters->max_cs_size <= 0) { if (parameters->tcp_rates[parameters->tcp_numlayers - 1] > 0) { OPJ_FLOAT32 temp_size; - temp_size = (OPJ_FLOAT32)(image->numcomps * image->comps[0].w * - image->comps[0].h * image->comps[0].prec) / - (parameters->tcp_rates[parameters->tcp_numlayers - 1] * 8 * - (OPJ_FLOAT32)image->comps[0].dx * (OPJ_FLOAT32)image->comps[0].dy); - parameters->max_cs_size = (int) floor(temp_size); + temp_size = (OPJ_FLOAT32)(((double)image->numcomps * image->comps[0].w * + image->comps[0].h * image->comps[0].prec) / + ((double)parameters->tcp_rates[parameters->tcp_numlayers - 1] * 8 * + image->comps[0].dx * image->comps[0].dy)); + if (temp_size > INT_MAX) { + parameters->max_cs_size = INT_MAX; + } else { + parameters->max_cs_size = (int) floor(temp_size); + } } else { parameters->max_cs_size = 0; } } else { OPJ_FLOAT32 temp_rate; OPJ_BOOL cap = OPJ_FALSE; - temp_rate = (OPJ_FLOAT32)(image->numcomps * image->comps[0].w * - image->comps[0].h * image->comps[0].prec) / - (OPJ_FLOAT32)(((OPJ_UINT32)parameters->max_cs_size) * 8 * image->comps[0].dx * - image->comps[0].dy); + temp_rate = (OPJ_FLOAT32)(((double)image->numcomps * image->comps[0].w * + image->comps[0].h * image->comps[0].prec) / + (((double)parameters->max_cs_size) * 8 * image->comps[0].dx * + image->comps[0].dy)); for (i = 0; i < (OPJ_UINT32) parameters->tcp_numlayers; i++) { if (parameters->tcp_rates[i] < temp_rate) { parameters->tcp_rates[i] = temp_rate; @@ -7084,6 +7143,10 @@ OPJ_BOOL opj_j2k_setup_encoder(opj_j2k_t *p_j2k, tcp->rates[j] = parameters->tcp_rates[j]; } } + if (!cp->m_specific_param.m_enc.m_fixed_quality && + tcp->rates[j] <= 1.0) { + tcp->rates[j] = 0.0; /* force lossless */ + } } tcp->csty = (OPJ_UINT32)parameters->csty; @@ -9591,9 +9654,10 @@ static OPJ_BOOL opj_j2k_read_SPCod_SPCoc(opj_j2k_t *p_j2k, /* If user wants to remove more resolutions than the codestream contains, return error */ if (l_cp->m_specific_param.m_dec.m_reduce >= l_tccp->numresolutions) { opj_event_msg(p_manager, EVT_ERROR, - "Error decoding component %d.\nThe number of resolutions to remove is higher than the number " - "of resolutions of this component\nModify the cp_reduce parameter.\n\n", - compno); + "Error decoding component %d.\nThe number of resolutions " + "to remove (%d) is greater or equal than the number " + "of resolutions of this component (%d)\nModify the cp_reduce parameter.\n\n", + compno, l_cp->m_specific_param.m_dec.m_reduce, l_tccp->numresolutions); p_j2k->m_specific_param.m_decoder.m_state |= 0x8000;/* FIXME J2K_DEC_STATE_ERR;*/ return OPJ_FALSE; diff --git a/src/lib/openjp2/openjpeg.h b/src/lib/openjp2/openjpeg.h index 7020d37d..79e0bb4f 100644 --- a/src/lib/openjp2/openjpeg.h +++ b/src/lib/openjp2/openjpeg.h @@ -381,9 +381,12 @@ typedef struct opj_cparameters { OPJ_UINT32 numpocs; /** number of layers */ int tcp_numlayers; - /** rates of layers - might be subsequently limited by the max_cs_size field */ + /** rates of layers - might be subsequently limited by the max_cs_size field. + * Should be decreasing. 1 can be + * used as last value to indicate the last layer is lossless. */ float tcp_rates[100]; - /** different psnr for successive layers */ + /** different psnr for successive layers. Should be increasing. 0 can be + * used as last value to indicate the last layer is lossless. */ float tcp_distoratio[100]; /** number of resolutions */ int numresolution; diff --git a/src/lib/openjp2/tcd.c b/src/lib/openjp2/tcd.c index c652f8ba..d577f024 100644 --- a/src/lib/openjp2/tcd.c +++ b/src/lib/openjp2/tcd.c @@ -273,28 +273,33 @@ void opj_tcd_makelayer(opj_tcd_t *tcd, n = cblk->numpassesinlayers; - for (passno = cblk->numpassesinlayers; passno < cblk->totalpasses; passno++) { - OPJ_UINT32 dr; - OPJ_FLOAT64 dd; - opj_tcd_pass_t *pass = &cblk->passes[passno]; - - if (n == 0) { - dr = pass->rate; - dd = pass->distortiondec; - } else { - dr = pass->rate - cblk->passes[n - 1].rate; - dd = pass->distortiondec - cblk->passes[n - 1].distortiondec; - } + if (thresh < 0) { + /* Special value to indicate to use all passes */ + n = cblk->totalpasses; + } else { + for (passno = cblk->numpassesinlayers; passno < cblk->totalpasses; passno++) { + OPJ_UINT32 dr; + OPJ_FLOAT64 dd; + opj_tcd_pass_t *pass = &cblk->passes[passno]; + + if (n == 0) { + dr = pass->rate; + dd = pass->distortiondec; + } else { + dr = pass->rate - cblk->passes[n - 1].rate; + dd = pass->distortiondec - cblk->passes[n - 1].distortiondec; + } - if (!dr) { - if (dd != 0) { + if (!dr) { + if (dd != 0) { + n = passno + 1; + } + continue; + } + if (thresh - (dd / dr) < + DBL_EPSILON) { /* do not rely on float equality, check with DBL_EPSILON margin */ n = passno + 1; } - continue; - } - if (thresh - (dd / dr) < - DBL_EPSILON) { /* do not rely on float equality, check with DBL_EPSILON margin */ - n = passno + 1; } } @@ -617,7 +622,8 @@ OPJ_BOOL opj_tcd_rateallocate(opj_tcd_t *tcd, opj_t2_destroy(t2); } else { - goodthresh = min; + /* Special value to indicate to use all passes */ + goodthresh = -1; } if (cstr_info) { /* Threshold for Marcela Index */ |
