Exemplo n.º 1
0
void
pnm_addtuplefreqoccurrence(struct pam *   const pamP,
                           tuple          const value,
                           tuplehash      const tuplefreqhash,
                           int *          const firstOccurrenceP) {

    unsigned int const hashvalue = pnm_hashtuple(pamP, value);
            
    struct tupleint_list_item * p;

    for (p = tuplefreqhash[hashvalue]; 
         p && !pnm_tupleequal(pamP, p->tupleint.tuple, value);
         p = p->next);

    if (p) {
        /* It's in the hash; just tally one more occurence */
        ++p->tupleint.value;
        *firstOccurrenceP = FALSE;
    } else {
        struct tupleint_list_item * p;

        /* It's not in the hash yet, so add it */
        *firstOccurrenceP = TRUE;

        p = allocTupleIntListItem(pamP);
        if (p == NULL)
            pm_error("out of memory computing hash table");

        pnm_assigntuple(pamP, p->tupleint.tuple, value);
        p->tupleint.value = 1;
        p->next = tuplefreqhash[hashvalue];
        tuplefreqhash[hashvalue] = p;
    }
}
Exemplo n.º 2
0
static void
initPi(unsigned char **   const pi,
       const struct pam * const pamP,
       tuple              const backgroundColor) {
/*----------------------------------------------------------------------------
  Set the initial info about every pixel in pi[][].

  Read through the image in the file described by *inpamP and set each
  pixel which is not of background color, and therefore obviously
  foreground, to type PT_FG.  Set every other pixel to PT_UNKNOWN.
-----------------------------------------------------------------------------*/
    tuple * tuplerow;
    unsigned int row;

    tuplerow  = pnm_allocpamrow(pamP);

    for (row = 0; row < pamP->height; ++row) {
        unsigned int col;

        pnm_readpamrow(pamP, tuplerow);

        for (col = 0; col < pamP->width; ++col) {
            pi[row][col] =
                pnm_tupleequal(pamP, tuplerow[col], backgroundColor) ?
                PT_UNKNOWN : PT_FG;
        }
    }
    pnm_freepamrow(tuplerow);
}
Exemplo n.º 3
0
static void
selectBackground(struct pam * const pamP,
                 tuple        const ul,
                 tuple        const ur,
                 tuple        const lr,
                 tuple        const ll,
                 tuple *      const bgColorP) {

    tuple bg;  /* Reference to one of ul, ur, ll, lr */

    if (pnm_tupleequal(pamP, ul, ur) &&
        (pnm_tupleequal(pamP, ul, ll) ||
         pnm_tupleequal(pamP, ul, lr)))
        bg = ul;
    else if (pnm_tupleequal(pamP, ll, lr) &&
             pnm_tupleequal(pamP, lr, ul))
        bg = ll;
    else {
        /* No 3 corners are same color; look for 2 corners */
        if (pnm_tupleequal(pamP, ul, ur))  /* top edge */
            bg = ul;
        else if (pnm_tupleequal(pamP, ul, ll)) /* left edge */
            bg = ul;
        else if (pnm_tupleequal(pamP, ur, lr)) /* right edge */
            bg = ur;
        else if (pnm_tupleequal(pamP, ll, lr)) /* bottom edge */
            bg = ll;
        else {
            /* No two corners are same color; just use upper left corner */
            bg = ul;
        }
    }
    
    *bgColorP = pnm_allocpamtuple(pamP);
    pnm_assigntuple(pamP, *bgColorP, bg);
}
Exemplo n.º 4
0
static void
writeDjvurleRow(FILE *       const ofP,
                struct pam * const pamP,
                tuple *      const tupleRow,
                tuplehash    const colorhash,
                tuple        const transcolor) {

    unsigned int col;
    unsigned int runlength;
    tuple prevpixel;        /* Previous pixel seen */

    prevpixel = tupleRow[0];
    runlength = 0;
    
    for (col = 0; col < pamP->width; ++col) {
        tuple const newpixel = tupleRow[col];      /* Current pixel color */
        
        if (pnm_tupleequal(pamP, newpixel, prevpixel))
            /* This is a continuation of the current run */
            ++runlength;
          else {
              /* The run is over.  Write it out and start a run of the next
                 color.
              */
              writeRleRun(ofP, pamP, prevpixel, runlength, 
                          colorhash, transcolor);
              runlength = 1;
              prevpixel = newpixel;
          }
        if (runlength >= (1<<20)-1) {
            /* Can't make the run any longer.  Write it out and start a
               new run.
            */
            writeRleRun(ofP, pamP, prevpixel, runlength, 
                        colorhash, transcolor);
            runlength = 1;
        }
    }
    /* Write the last run we started */
    writeRleRun(ofP, pamP, prevpixel, runlength, colorhash, transcolor);
}
Exemplo n.º 5
0
void
pnm_lookuptuple(struct pam *    const pamP, 
                const tuplehash       tuplehash, 
                const tuple           searchval, 
                int *           const foundP, 
                int *           const retvalP) {
    
    unsigned int const hashvalue = pnm_hashtuple(pamP, searchval);
    struct tupleint_list_item * p;
    struct tupleint_list_item * found;

    found = NULL;  /* None found yet */
    for (p = tuplehash[hashvalue]; p && !found; p = p->next)
        if (pnm_tupleequal(pamP, p->tupleint.tuple, searchval)) {
            found = p;
        }

    if (found) {
        *foundP = TRUE;
        *retvalP = found->tupleint.value;
    } else
        *foundP = FALSE;
}
Exemplo n.º 6
0
static void
computeRunlengths(struct pam * const pamP, 
                   tuple *      const tuplerow, 
                   int *        const runlength) {

    int col, start;

    /* Initialize all run lengths to 0.  (This is just an error check.) */
    for (col = 0; col < pamP->width; ++col)
        runlength[col] = 0;
    
    /* Find runs of identical pixels. */
    for ( col = 0; col < pamP->width; ) {
        start = col;
        do {
            ++col;
        } while ( col < pamP->width &&
                  col - start < 128 &&
                  pnm_tupleequal(pamP, tuplerow[col], tuplerow[start]));
        runlength[start] = col - start;
    }
    
    /* Now look for runs of length-1 runs, and turn them into negative runs. */
    for (col = 0; col < pamP->width; ) {
        if (runlength[col] == 1) {
            start = col;
            while (col < pamP->width &&
                   col - start < 128 &&
                   runlength[col] == 1 ) {
                runlength[col] = 0;
                ++col;
            }
            runlength[start] = - ( col - start );
        } else
            col += runlength[col];
    }
}
Exemplo n.º 7
0
static void
addColorOccurrenceToHash(tuple          const color, 
                         tuplehash      const tuplefreqhash,
                         struct pam *   const pamP,
                         unsigned int   const maxsize,
                         unsigned int * const sizeP,
                         bool *         const fullP) {
               
    unsigned int const hashvalue = pnm_hashtuple(pamP, color);
            
    struct tupleint_list_item *p;

    for (p = tuplefreqhash[hashvalue]; 
         p && !pnm_tupleequal(pamP, p->tupleint.tuple, color);
         p = p->next);

    if (p) {
        /* It's in the hash; just tally one more occurence */
        ++p->tupleint.value;
        *fullP = FALSE;
    } else {
        /* It's not in the hash yet, so add it (if allowed) */
        ++(*sizeP);
        if (maxsize > 0 && *sizeP > maxsize) 
            *fullP = TRUE;
        else {
            *fullP = FALSE;
            p = allocTupleIntListItem(pamP);
            if (p == NULL)
                pm_error("out of memory computing hash table");
            pnm_assigntuple(pamP, p->tupleint.tuple, color);
            p->tupleint.value = 1;
            p->next = tuplefreqhash[hashvalue];
            tuplefreqhash[hashvalue] = p;
        }
    }
}