|
Packit |
78deda |
/* ----------------------------------------------------------------------
|
|
Packit |
78deda |
*
|
|
Packit |
78deda |
* Convert a PAM image to an AVS X image
|
|
Packit |
78deda |
*
|
|
Packit |
78deda |
* By Scott Pakin <scott+pbm@pakin.org>
|
|
Packit |
78deda |
*
|
|
Packit |
78deda |
* ----------------------------------------------------------------------
|
|
Packit |
78deda |
*
|
|
Packit |
78deda |
* Copyright (C) 2010 Scott Pakin <scott+pbm@pakin.org>
|
|
Packit |
78deda |
*
|
|
Packit |
78deda |
* This program is free software: you can redistribute it and/or modify
|
|
Packit |
78deda |
* it under the terms of the GNU General Public License as published by
|
|
Packit |
78deda |
* the Free Software Foundation, either version 3 of the License, or (at
|
|
Packit |
78deda |
* your option) any later version.
|
|
Packit |
78deda |
*
|
|
Packit |
78deda |
* This program is distributed in the hope that it will be useful, but
|
|
Packit |
78deda |
* WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
Packit |
78deda |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
Packit |
78deda |
* General Public License for more details.
|
|
Packit |
78deda |
*
|
|
Packit |
78deda |
* You should have received a copy of the GNU General Public License
|
|
Packit |
78deda |
* along with this program. If not, see http://www.gnu.org/licenses/.
|
|
Packit |
78deda |
*
|
|
Packit |
78deda |
* ----------------------------------------------------------------------
|
|
Packit |
78deda |
*/
|
|
Packit |
78deda |
|
|
Packit |
78deda |
#include <stdio.h>
|
|
Packit |
78deda |
#include "pm.h"
|
|
Packit |
78deda |
#include "pam.h"
|
|
Packit |
78deda |
|
|
Packit |
78deda |
|
|
Packit |
78deda |
|
|
Packit |
78deda |
static char
|
|
Packit |
78deda |
sample2char(sample const s,
|
|
Packit |
78deda |
sample const maxval) {
|
|
Packit |
78deda |
/* Scale down a sample to a single byte. */
|
|
Packit |
78deda |
|
|
Packit |
78deda |
return maxval==255 ? s : s * 255 / maxval;
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
|
|
Packit |
78deda |
|
|
Packit |
78deda |
#define THIS_SAMPLE_CHAR(PLANE) \
|
|
Packit |
78deda |
sample2char(tuplerow[col][PLANE], pamP->maxval)
|
|
Packit |
78deda |
|
|
Packit |
78deda |
static void
|
|
Packit |
78deda |
produceAvs(struct pam * const pamP,
|
|
Packit |
78deda |
FILE * const avsFileP) {
|
|
Packit |
78deda |
|
|
Packit |
78deda |
tuple * tuplerow;
|
|
Packit |
78deda |
|
|
Packit |
78deda |
/* Write the AVS header (image width and height as 4-byte
|
|
Packit |
78deda |
big-endian integers).
|
|
Packit |
78deda |
*/
|
|
Packit |
78deda |
pm_writebiglong(avsFileP, pamP->width);
|
|
Packit |
78deda |
pm_writebiglong(avsFileP, pamP->height);
|
|
Packit |
78deda |
|
|
Packit |
78deda |
/* Write the AVS data (alpha, red, green, blue -- one byte apiece. */
|
|
Packit |
78deda |
tuplerow = pnm_allocpamrow(pamP);
|
|
Packit |
78deda |
switch (pamP->depth) {
|
|
Packit |
78deda |
case 1: {
|
|
Packit |
78deda |
/* Black-and-white or grayscale, no alpha */
|
|
Packit |
78deda |
unsigned int row;
|
|
Packit |
78deda |
for (row = 0; row < pamP->height; ++row) {
|
|
Packit |
78deda |
unsigned int col;
|
|
Packit |
78deda |
pnm_readpamrow(pamP, tuplerow);
|
|
Packit |
78deda |
for (col = 0; col < pamP->width; ++col) {
|
|
Packit |
78deda |
pm_writechar(avsFileP, (char)255);
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(0));
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(0));
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(0));
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
} break;
|
|
Packit |
78deda |
|
|
Packit |
78deda |
case 2: {
|
|
Packit |
78deda |
/* Black-and-white or grayscale plus alpha */
|
|
Packit |
78deda |
unsigned int row;
|
|
Packit |
78deda |
for (row = 0; row < pamP->height; ++row) {
|
|
Packit |
78deda |
unsigned int col;
|
|
Packit |
78deda |
pnm_readpamrow(pamP, tuplerow);
|
|
Packit |
78deda |
for (col = 0; col < pamP->width; ++col) {
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(1));
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(0));
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(0));
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(0));
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
} break;
|
|
Packit |
78deda |
|
|
Packit |
78deda |
case 3: {
|
|
Packit |
78deda |
/* RGB, no alpha */
|
|
Packit |
78deda |
unsigned int row;
|
|
Packit |
78deda |
for (row = 0; row < pamP->height; ++row) {
|
|
Packit |
78deda |
unsigned int col;
|
|
Packit |
78deda |
pnm_readpamrow(pamP, tuplerow);
|
|
Packit |
78deda |
for (col = 0; col < pamP->width; ++col) {
|
|
Packit |
78deda |
pm_writechar(avsFileP, (char)255);
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(0));
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(1));
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(2));
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
} break;
|
|
Packit |
78deda |
|
|
Packit |
78deda |
case 4: {
|
|
Packit |
78deda |
/* RGB plus alpha */
|
|
Packit |
78deda |
unsigned int row;
|
|
Packit |
78deda |
for (row = 0; row < pamP->height; ++row) {
|
|
Packit |
78deda |
unsigned int col;
|
|
Packit |
78deda |
pnm_readpamrow( pamP, tuplerow );
|
|
Packit |
78deda |
for (col = 0; col < pamP->width; ++col) {
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(3));
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(0));
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(1));
|
|
Packit |
78deda |
pm_writechar(avsFileP, THIS_SAMPLE_CHAR(2));
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
} break;
|
|
Packit |
78deda |
|
|
Packit |
78deda |
default:
|
|
Packit |
78deda |
pm_error("Unrecognized PAM depth %u. We understand only "
|
|
Packit |
78deda |
"1, 2, 3, and 4", pamP->depth);
|
|
Packit |
78deda |
break;
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
pnm_freepamrow(tuplerow);
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
|
|
Packit |
78deda |
|
|
Packit |
78deda |
|
|
Packit |
78deda |
int
|
|
Packit |
78deda |
main(int argc, const char *argv[]) {
|
|
Packit |
78deda |
struct pam inPam;
|
|
Packit |
78deda |
const char * inputFilename;
|
|
Packit |
78deda |
FILE * inFileP;
|
|
Packit |
78deda |
|
|
Packit |
78deda |
pm_proginit(&argc, argv);
|
|
Packit |
78deda |
|
|
Packit |
78deda |
inputFilename = (argc > 1) ? argv[1] : "-";
|
|
Packit |
78deda |
|
|
Packit |
78deda |
inFileP = pm_openr(inputFilename);
|
|
Packit |
78deda |
|
|
Packit |
78deda |
pnm_readpaminit(inFileP, &inPam, PAM_STRUCT_SIZE(tuple_type));
|
|
Packit |
78deda |
|
|
Packit |
78deda |
produceAvs(&inPam, stdout);
|
|
Packit |
78deda |
|
|
Packit |
78deda |
pm_closer(inFileP);
|
|
Packit |
78deda |
|
|
Packit |
78deda |
return 0;
|
|
Packit |
78deda |
}
|
|
Packit |
78deda |
|