]> granicus.if.org Git - openjpeg/commitdiff
[trunk] add ability in opj_compress to input subsampled images through
authorAntonin Descampe <antonin@gmail.com>
Wed, 26 Mar 2014 14:26:49 +0000 (14:26 +0000)
committerAntonin Descampe <antonin@gmail.com>
Wed, 26 Mar 2014 14:26:49 +0000 (14:26 +0000)
'-F' (aka raw option). Let the user input raw images with 444, 422, 420
(etc) subsampling. To be used in conjunction with '-mct 0' option to
compress subsampled YCC images.

src/bin/jp2/convert.c
src/bin/jp2/convert.h
src/bin/jp2/opj_compress.c

index d3e9773c912d530e407f1554fa5aeca3ef578382..0033b523a163fc71392068d738db7d8efc9916b9 100644 (file)
@@ -2953,9 +2953,11 @@ static opj_image_t* rawtoimage_common(const char *filename, opj_cparameters_t *p
     {
         fprintf(stderr,"\nError: invalid raw image parameters\n");
         fprintf(stderr,"Please use the Format option -F:\n");
-        fprintf(stderr,"-F rawWidth,rawHeight,rawComp,rawBitDepth,s/u (Signed/Unsigned)\n");
-        fprintf(stderr,"Example: -i lena.raw -o lena.j2k -F 512,512,3,8,u\n");
-        fprintf(stderr,"Aborting\n");
+        fprintf(stderr,"-F <width>,<height>,<ncomp>,<bitdepth>,{s,u}@<dx1>x<dy1>:...:<dxn>x<dyn>\n");
+        fprintf(stderr,"If subsampling is omitted, 1x1 is assumed for all components\n");
+        fprintf(stderr,"Example: -i image.raw -o image.j2k -F 512,512,3,8,u@1x1:2x2:2x2\n");
+        fprintf(stderr,"         for raw 512x512 image with 4:2:0 subsampling\n");
+        fprintf(stderr,"Aborting.\n");
         return NULL;
     }
 
@@ -2966,7 +2968,17 @@ static opj_image_t* rawtoimage_common(const char *filename, opj_cparameters_t *p
         return NULL;
     }
     numcomps = raw_cp->rawComp;
-    color_space = OPJ_CLRSPC_SRGB;
+
+    /* FIXME ADE at this point, tcp_mct has not been properly set in calling function */
+    if (numcomps == 0) {
+        color_space = OPJ_CLRSPC_GRAY;
+    } else if ((numcomps >= 3) && (parameters->tcp_mct == 0)) {
+        color_space = OPJ_CLRSPC_SYCC;
+    } else if ((numcomps >= 3) && (parameters->tcp_mct != 2)) {
+        color_space = OPJ_CLRSPC_SRGB;
+    } else {
+        color_space = OPJ_CLRSPC_UNKNOWN;
+    }
     w = raw_cp->rawWidth;
     h = raw_cp->rawHeight;
     cmptparm = (opj_image_cmptparm_t*) malloc((size_t)numcomps * sizeof(opj_image_cmptparm_t));
@@ -2977,8 +2989,8 @@ static opj_image_t* rawtoimage_common(const char *filename, opj_cparameters_t *p
         cmptparm[i].prec = (OPJ_UINT32)raw_cp->rawBitDepth;
         cmptparm[i].bpp = (OPJ_UINT32)raw_cp->rawBitDepth;
         cmptparm[i].sgnd = (OPJ_UINT32)raw_cp->rawSigned;
-        cmptparm[i].dx = (OPJ_UINT32)subsampling_dx;
-        cmptparm[i].dy = (OPJ_UINT32)subsampling_dy;
+        cmptparm[i].dx = (OPJ_UINT32)subsampling_dx * raw_cp->rawComps[i].dx;
+        cmptparm[i].dy = (OPJ_UINT32)subsampling_dy * raw_cp->rawComps[i].dy;
         cmptparm[i].w = (OPJ_UINT32)w;
         cmptparm[i].h = (OPJ_UINT32)h;
     }
@@ -2999,7 +3011,8 @@ static opj_image_t* rawtoimage_common(const char *filename, opj_cparameters_t *p
     {
         unsigned char value = 0;
         for(compno = 0; compno < numcomps; compno++) {
-            for (i = 0; i < w * h; i++) {
+            int nloop = (w*h)/(raw_cp->rawComps[compno].dx*raw_cp->rawComps[compno].dx);
+            for (i = 0; i < nloop; i++) {
                 if (!fread(&value, 1, 1, f)) {
                     fprintf(stderr,"Error reading raw file. End of file probably reached.\n");
                     return NULL;
@@ -3012,7 +3025,8 @@ static opj_image_t* rawtoimage_common(const char *filename, opj_cparameters_t *p
     {
         unsigned short value;
         for(compno = 0; compno < numcomps; compno++) {
-            for (i = 0; i < w * h; i++) {
+            int nloop = (w*h)/(raw_cp->rawComps[compno].dx*raw_cp->rawComps[compno].dx);
+            for (i = 0; i < nloop; i++) {
                 unsigned char temp1;
                 unsigned char temp2;
                 if (!fread(&temp1, 1, 1, f)) {
index 11bc31eefce5df20d722e396ef5e70b5179bccc6..360d92936930922cf953e695fa010abc3f966dd6 100644 (file)
 #ifndef __J2K_CONVERT_H
 #define __J2K_CONVERT_H
 
+/**@name RAW component encoding parameters */
+/*@{*/
+typedef struct raw_comp_cparameters {
+    /** subsampling in X direction */
+    int dx;
+    /** subsampling in Y direction */
+    int dy;
+    /*@}*/
+} raw_comp_cparameters_t;
+
 /**@name RAW image encoding parameters */
 /*@{*/
 typedef struct raw_cparameters {
@@ -38,12 +48,14 @@ typedef struct raw_cparameters {
        int rawWidth;
        /** height of the raw image */
        int rawHeight;
-       /** components of the raw image */
+    /** number of components of the raw image */
        int rawComp;
-       /** bit depth of the raw image */
-       int rawBitDepth;
-       /** signed/unsigned raw image */
-       OPJ_BOOL rawSigned;
+    /** bit depth of the raw image */
+    int rawBitDepth;
+    /** signed/unsigned raw image */
+    OPJ_BOOL rawSigned;
+    /** raw components parameters */
+    raw_comp_cparameters_t *rawComps;
        /*@}*/
 } raw_cparameters_t;
 
index f3a20d0db24f6e505089cc9ad30de0445a4633e9..8bd8b4d362d4e590825094c8737a3b828952a0e6 100644 (file)
@@ -209,7 +209,7 @@ static void encode_help_display(void) {
     fprintf(stdout,"               -F rawWidth,rawHeight,rawComp,rawBitDepth,s/u (Signed/Unsigned)\n");
     fprintf(stdout,"               Example: -i lena.raw -o lena.j2k -F 512,512,3,8,u\n");
     fprintf(stdout,"\n");
-    fprintf(stdout,"-mct {0,1,2} : explicitely specifies if an Multiple Component Transform has to be used.\n");
+    fprintf(stdout,"-mct {0,1,2} : explicitely specifies if a Multiple Component Transform has to be used.\n");
     fprintf(stdout,"               0: no MCT ; 1: RGB->YCC conversion ; 2: custom MCT.\n");
     fprintf(stdout,"               If custom MCT, \"-m\" option has to be used (see hereunder).\n");
     fprintf(stdout,"               By default, RGB->YCC conversion is used if there are 3 components or more,\n");
@@ -569,33 +569,84 @@ static int parse_cmdline_encoder(int argc, char **argv, opj_cparameters_t *param
 
         case 'F':                      /* Raw image format parameters */
         {
+            OPJ_BOOL wrong = OPJ_FALSE;
+            char *substr1;
+            char *substr2;
+            char *sep;
             char signo;
-            char *s = opj_optarg;
-            if (sscanf(s, "%d,%d,%d,%d,%c", &raw_cp->rawWidth, &raw_cp->rawHeight, &raw_cp->rawComp, &raw_cp->rawBitDepth, &signo) == 5) {
+            int width,height,bitdepth,ncomp;
+            int len;
+            OPJ_BOOL raw_signed;
+            substr2 = strchr(opj_optarg,'@');
+            if (substr2 == NULL) {
+                len = (int) strlen(opj_optarg);
+            } else {
+                len = substr2 - opj_optarg;
+                substr2++; /* skip '@' character */
+            }
+            substr1 = (char*) malloc((len+1)*sizeof(char));
+            memcpy(substr1,opj_optarg,len);
+            substr1[len] = '\0';
+            if (sscanf(substr1, "%d,%d,%d,%d,%[su]", &width, &height, &ncomp, &bitdepth, &signo) == 5) {
                 if (signo == 's') {
-                    raw_cp->rawSigned = OPJ_TRUE;
-                    fprintf(stdout,"\nRaw file parameters: %d,%d,%d,%d Signed\n", raw_cp->rawWidth, raw_cp->rawHeight, raw_cp->rawComp, raw_cp->rawBitDepth);
-                }
-                else if (signo == 'u') {
-                    raw_cp->rawSigned = OPJ_FALSE;
-                    fprintf(stdout,"\nRaw file parameters: %d,%d,%d,%d Unsigned\n", raw_cp->rawWidth, raw_cp->rawHeight, raw_cp->rawComp, raw_cp->rawBitDepth);
+                    raw_signed = OPJ_TRUE;
+                } else if (signo == 'u') {
+                    raw_signed = OPJ_FALSE;
+                } else {
+                    wrong = OPJ_TRUE;
                 }
-                else {
-                    fprintf(stderr,"\nError: invalid raw image parameters: Unknown sign of raw file\n");
-                    fprintf(stderr,"Please use the Format option -F:\n");
-                    fprintf(stderr,"-F rawWidth,rawHeight,rawComp,rawBitDepth,s/u (Signed/Unsigned)\n");
-                    fprintf(stderr,"Example: -i lena.raw -o lena.j2k -F 512,512,3,8,u\n");
-                    fprintf(stderr,"Aborting\n");
+            } else {
+                wrong = OPJ_TRUE;
+            }
+            if (!wrong) {
+                int i;
+                int lastdx = 1;
+                int lastdy = 1;
+                raw_cp->rawWidth = width;
+                raw_cp->rawHeight = height;
+                raw_cp->rawComp = ncomp;
+                raw_cp->rawBitDepth = bitdepth;
+                raw_cp->rawSigned  = raw_signed;
+                raw_cp->rawComps = (raw_comp_cparameters_t*) malloc(ncomp*sizeof(raw_comp_cparameters_t));
+                for (i = 0; i < ncomp && !wrong; i++) {
+                    if (substr2 == NULL) {
+                        raw_cp->rawComps[i].dx = lastdx;
+                        raw_cp->rawComps[i].dy = lastdy;
+                    } else {
+                        int dx,dy;
+                        sep = strchr(substr2,':');
+                        if (sep == NULL) {
+                            if (sscanf(substr2, "%dx%d", &dx, &dy) == 2) {
+                                lastdx = dx;
+                                lastdy = dy;
+                                raw_cp->rawComps[i].dx = dx;
+                                raw_cp->rawComps[i].dy = dy;
+                                substr2 = NULL;
+                            } else {
+                                wrong = OPJ_TRUE;
+                            }
+                        } else {
+                            if (sscanf(substr2, "%dx%d:%s", &dx, &dy, substr2) == 3) {
+                                raw_cp->rawComps[i].dx = dx;
+                                raw_cp->rawComps[i].dy = dy;
+                            } else {
+                                wrong = OPJ_TRUE;
+                            }
+                        }
+                    }
                 }
             }
-            else {
+            if (wrong) {
                 fprintf(stderr,"\nError: invalid raw image parameters\n");
                 fprintf(stderr,"Please use the Format option -F:\n");
-                fprintf(stderr,"-F rawWidth,rawHeight,rawComp,rawBitDepth,s/u (Signed/Unsigned)\n");
-                fprintf(stderr,"Example: -i lena.raw -o lena.j2k -F 512,512,3,8,u\n");
-                fprintf(stderr,"Aborting\n");
+                fprintf(stderr,"-F <width>,<height>,<ncomp>,<bitdepth>,{s,u}@<dx1>x<dy1>:...:<dxn>x<dyn>\n");
+                fprintf(stderr,"If subsampling is omitted, 1x1 is assumed for all components\n");
+                fprintf(stderr,"Example: -i image.raw -o image.j2k -F 512,512,3,8,u@1x1:2x2:2x2\n");
+                fprintf(stderr,"         for raw 512x512 image with 4:2:0 subsampling\n");
+                fprintf(stderr,"Aborting.\n");
                 return 1;
             }
+            if (substr1 != NULL) free(substr1);
         }
             break;
 
@@ -1749,6 +1800,7 @@ int main(int argc, char **argv) {
     /* free user parameters structure */
     if(parameters.cp_comment)   free(parameters.cp_comment);
     if(parameters.cp_matrice)   free(parameters.cp_matrice);
+    if(raw_cp.rawComps) free(raw_cp.rawComps);
 
     return 0;
 }