Blame editor/specialty/pamoil.c

Packit 78deda
/* pgmoil.c - read a portable pixmap and turn into an oil painting
Packit 78deda
**
Packit 78deda
** Copyright (C) 1990 by Wilson Bent (whb@hoh-2.att.com)
Packit 78deda
** Shamelessly butchered into a color version by Chris Sheppard
Packit 78deda
** 2001
Packit 78deda
**
Packit 78deda
** Permission to use, copy, modify, and distribute this software and its
Packit 78deda
** documentation for any purpose and without fee is hereby granted, provided
Packit 78deda
** that the above copyright notice appear in all copies and that both that
Packit 78deda
** copyright notice and this permission notice appear in supporting
Packit 78deda
** documentation.  This software is provided "as is" without express or
Packit 78deda
** implied warranty.
Packit 78deda
*/
Packit 78deda
Packit 78deda
#include <stdio.h>
Packit 78deda
#include <stdlib.h>
Packit 78deda
#include <unistd.h>
Packit 78deda
#include "pam.h"
Packit 78deda
#include "mallocvar.h"
Packit 78deda
Packit 78deda
static void 
Packit 78deda
convertRow(struct pam const inpam, tuple ** const tuples,
Packit 78deda
           tuple * const tuplerow, int const row, int const smearFactor,
Packit 78deda
           int * const hist) {
Packit 78deda
Packit 78deda
    int sample;
Packit 78deda
    for (sample = 0; sample < inpam.depth; sample++) {
Packit 78deda
        int col;
Packit 78deda
        for (col = 0; col < inpam.width; ++col)  {
Packit 78deda
            int i;
Packit 78deda
            int drow;
Packit 78deda
            int modalval;
Packit 78deda
                /* The sample value that occurs most often in the neighborhood
Packit 78deda
                   of the pixel being examined
Packit 78deda
                */
Packit 78deda
Packit 78deda
            /* Compute hist[] - frequencies, in the neighborhood, of each 
Packit 78deda
               sample value
Packit 78deda
            */
Packit 78deda
            for (i = 0; i <= inpam.maxval; ++i) hist[i] = 0;
Packit 78deda
Packit 78deda
            for (drow = row - smearFactor; drow <= row + smearFactor; ++drow) {
Packit 78deda
                if (drow >= 0 && drow < inpam.height) {
Packit 78deda
                    int dcol;
Packit 78deda
                    for (dcol = col - smearFactor; 
Packit 78deda
                         dcol <= col + smearFactor; 
Packit 78deda
                         ++dcol) {
Packit 78deda
                        if ( dcol >= 0 && dcol < inpam.width )
Packit 78deda
                            ++hist[tuples[drow][dcol][sample]];
Packit 78deda
                    }
Packit 78deda
                }
Packit 78deda
            }
Packit 78deda
            {
Packit 78deda
                /* Compute modalval */
Packit 78deda
                int sampleval;
Packit 78deda
                int maxfreq;
Packit 78deda
Packit 78deda
                maxfreq = 0;
Packit 78deda
                modalval = 0;
Packit 78deda
Packit 78deda
                for (sampleval = 0; sampleval <= inpam.maxval; ++sampleval) {
Packit 78deda
                    if (hist[sampleval] > maxfreq) {
Packit 78deda
                        maxfreq = hist[sampleval];
Packit 78deda
                        modalval = sampleval;
Packit 78deda
                    }
Packit 78deda
                }
Packit 78deda
            }
Packit 78deda
            tuplerow[col][sample] = modalval;
Packit 78deda
        }
Packit 78deda
    }
Packit 78deda
}
Packit 78deda
Packit 78deda
Packit 78deda
Packit 78deda
int
Packit 78deda
main(int argc, char *argv[] ) {
Packit 78deda
    struct pam inpam, outpam;
Packit 78deda
    FILE* ifp;
Packit 78deda
    tuple ** tuples;
Packit 78deda
    tuple * tuplerow;
Packit 78deda
    int * hist;
Packit 78deda
        /* A buffer for the convertRow subroutine to use */
Packit 78deda
    int argn;
Packit 78deda
    int row;
Packit 78deda
    int smearFactor;
Packit 78deda
    const char* const usage = "[-n <n>] [ppmfile]";
Packit 78deda
Packit 78deda
    ppm_init( &argc, argv );
Packit 78deda
Packit 78deda
    argn = 1;
Packit 78deda
    smearFactor = 3;       /* DEFAULT VALUE */
Packit 78deda
Packit 78deda
    /* Check for options. */
Packit 78deda
    if ( argn < argc && argv[argn][0] == '-' ) {
Packit 78deda
        if ( argv[argn][1] == 'n' ) {
Packit 78deda
            ++argn;
Packit 78deda
            if ( argn == argc || sscanf(argv[argn], "%d", &smearFactor) != 1 )
Packit 78deda
                pm_usage( usage );
Packit 78deda
        } else
Packit 78deda
            pm_usage( usage );
Packit 78deda
        ++argn;
Packit 78deda
    }
Packit 78deda
    if ( argn < argc ) {
Packit 78deda
        ifp = pm_openr( argv[argn] );
Packit 78deda
        ++argn;
Packit 78deda
    } else
Packit 78deda
        ifp = stdin;
Packit 78deda
Packit 78deda
    if ( argn != argc )
Packit 78deda
        pm_usage( usage );
Packit 78deda
Packit 78deda
    tuples = pnm_readpam(ifp, &inpam, PAM_STRUCT_SIZE(tuple_type));
Packit 78deda
    pm_close(ifp);
Packit 78deda
Packit 38c941
    overflow_add(inpam.maxval, 1);
Packit 78deda
    MALLOCARRAY(hist, inpam.maxval + 1);
Packit 78deda
    if (hist == NULL)
Packit 78deda
        pm_error("Unable to allocate memory for histogram.");
Packit 78deda
Packit 78deda
    outpam = inpam; outpam.file = stdout;
Packit 78deda
Packit 78deda
    pnm_writepaminit(&outpam);
Packit 78deda
Packit 78deda
    tuplerow = pnm_allocpamrow(&inpam);
Packit 78deda
Packit 78deda
    for (row = 0; row < inpam.height; ++row) {
Packit 78deda
        convertRow(inpam, tuples, tuplerow, row, smearFactor, hist);
Packit 78deda
        pnm_writepamrow(&outpam, tuplerow);
Packit 78deda
    }
Packit 78deda
Packit 78deda
    pnm_freepamrow(tuplerow);
Packit 78deda
    free(hist);
Packit 78deda
    pnm_freepamarray(tuples, &inpam);
Packit 78deda
Packit 78deda
    pm_close(stdout);
Packit 78deda
    exit(0);
Packit 78deda
}
Packit 78deda