home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Frozen Fish 1: Amiga
/
FrozenFish-Apr94.iso
/
bbs
/
oct93
/
graphics
/
readdctv.lha
/
ReadDCTV
/
ReadDCTV.c
< prev
next >
Wrap
C/C++ Source or Header
|
1993-06-27
|
7KB
|
288 lines
/* ReadDCTV by Garrick Meeker */
#include <dos/dos.h>
#include <exec/memory.h>
#include <iffp/ilbmapp.h>
#include <iffp/packer.h>
#include <libraries/dctv.h>
#include <libraries/iffparse.h>
#include <math.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <clib/dctv_protos.h>
#include <clib/exec_protos.h>
#include <clib/graphics_protos.h>
#include <clib/iffparse_protos.h>
#include <pragmas/dctv_pragmas.h>
#include <pragmas/exec_pragmas.h>
#include <pragmas/graphics_pragmas.h>
#include <pragmas/iffparse_pragmas.h>
char *vers = "\0$VER: ReadDCTV 1.0";
char *Copyright = "ReadDCTV v1.0 by Garrick Meeker";
char *usage = "Usage: ReadDCTV dctvfile iff24file";
char *write_err = "Error writing file";
LONG Convert(void);
struct IFFHandle *OpenOutfile(void);
BOOL WriteRGB(struct IFFHandle *iff24, struct DCTVCvtHandle *cvt);
BOOL WriteChunkyLine(struct IFFHandle *iff,UBYTE *chunks,int width);
void ConvertPlane(UBYTE planemask, UBYTE *line, int width);
void CloseOutfile(struct IFFHandle *iff24);
void bye(UBYTE *s, int e);
void cleanup(void);
struct Library *DCTVBase = NULL;
struct Library *GfxBase = NULL;
struct Library *IFFParseBase = NULL;
struct ILBMInfo ilbm = {0};
LONG error=NULL;
UBYTE *infile=NULL;
UBYTE *outfile=NULL;
UWORD *plane=NULL;
BYTE *compressed=NULL;
LONG ilbmprops[] = {
ID_ILBM, ID_BMHD,
ID_ILBM, ID_CMAP,
ID_ILBM, ID_CAMG,
TAG_DONE
};
LONG ilbmstops[] = {
ID_ILBM, ID_BODY,
TAG_DONE
};
void main(int argc, char **argv)
{
if((argc<3)||(argv[argc-1][0]=='?'))
{
printf("%s\n%s\n",Copyright,usage);
bye("",RETURN_OK);
}
infile = argv[1];
outfile = argv[2];
if(!(GfxBase = OpenLibrary("graphics.library", 0)))
bye("Unable to open graphics.library.\n",RETURN_WARN);
if(!(IFFParseBase = OpenLibrary("iffparse.library",0)))
bye("Unable to open iffparse.library.\n",RETURN_WARN);
if(!(DCTVBase = OpenLibrary("dctv.library",3)))
bye("Unable to open dctv.library v3.\n",RETURN_WARN);
/* Load image */
ilbm.ParseInfo.propchks = ilbmprops;
ilbm.ParseInfo.stopchks = ilbmstops;
if(!(ilbm.ParseInfo.iff = AllocIFF()))
bye(IFFerr(IFFERR_NOMEM),RETURN_FAIL);
if (error = loadbrush(&ilbm,infile))
{
printf("Unable to load ilbm \"%s\", ifferr=%s\n",infile,IFFerr(error));
bye("",RETURN_WARN);
}
error=Convert();
unloadbrush(&ilbm);
bye("",error);
}
/* Convert to 24 bit */
LONG Convert()
{
struct IFFHandle *iff24 = NULL;
struct DCTVCvtHandle *cvt = NULL;
if(!(TestDCTVSignature(ilbm.brbitmap))) {
puts("This is not a DCTV picture.");
return RETURN_WARN;
}
if (!(cvt = AllocDCTVCvtTags( ilbm.brbitmap,
DCTVCVTA_Type, (ULONG)DCTVCVTT_DCTVtoRGB,
DCTVCVTA_Width, (ULONG)((ilbm.brbitmap->BytesPerRow)<<3),
DCTVCVTA_Height, (ULONG)ilbm.brbitmap->Rows,
DCTVCVTA_Flags, (ULONG)((ilbm.camg & LACE) ? DCTVCVTF_Lace : 0),
DCTVCVTA_ColorTable, ilbm.colortable,
DCTVCVTA_ErrorCode, &error,
TAG_END))) {
printf("DCTV conversion failed %lu\n",error);
error=RETURN_WARN;
goto abortconvert;
}
if (!(plane=(AllocMem(ilbm.brbitmap->BytesPerRow,MEMF_ANY)))) {
puts("Out of memory.");
error=RETURN_WARN;
goto abortconvert;
}
if (!(compressed=(AllocMem(MaxPackedSize(ilbm.brbitmap->BytesPerRow),MEMF_ANY)))) {
puts("Out of memory.");
error=RETURN_WARN;
goto abortconvert;
}
if (!(iff24=OpenOutfile())) {
puts("Unable to open output file.");
error=RETURN_FAIL;
goto abortconvert;
}
while (cvt->DstLineNum < cvt->Height) {
/* Break on Ctrl-C */
if (SetSignal(0,SIGBREAKF_CTRL_C) & SIGBREAKF_CTRL_C) return RETURN_WARN;
CvtDCTVLine(cvt);
if(cvt->DstLineNum>0)
if(!(WriteRGB(iff24,cvt))) {
printf("%s\n",write_err);
error=RETURN_FAIL;
goto abortconvert;
}
}
if(PopChunk(iff24)) { /* Close BODY chunk */
printf("%s\n",write_err);
error=RETURN_FAIL;
goto abortconvert;
}
if(PopChunk(iff24)) { /* Close FORM */
printf("%s\n",write_err);
error=RETURN_FAIL;
goto abortconvert;
}
error = RETURN_OK;
abortconvert:
if(compressed) FreeMem(compressed,MaxPackedSize(ilbm.brbitmap->BytesPerRow));
if(plane) FreeMem(plane,ilbm.brbitmap->BytesPerRow);
if(cvt) FreeDCTVCvt(cvt);
CloseOutfile(iff24);
return error;
}
/* Open 24-bit IFF */
struct IFFHandle *OpenOutfile()
{
struct IFFHandle *iff=NULL;
BitMapHeader bmhd;
if (!(iff = AllocIFF())) return NULL;
if (!(iff->iff_Stream=Open(outfile,MODE_NEWFILE)))
goto abortopen;
InitIFFasDOS(iff);
if (OpenIFF(iff,IFFF_WRITE)) goto abortopen;
/* Write header */
if (PushChunk(iff,ID_ILBM,ID_FORM,IFFSIZE_UNKNOWN))
goto abortopen;
/* Write BMHD */
if (PushChunk(iff,ID_ILBM,ID_BMHD,sizeof(BitMapHeader)))
goto abortopen;
/* Set BMHD values */
CopyMem(&ilbm.Bmhd,&bmhd,sizeof(bmhd));
bmhd.nPlanes=24;
bmhd.masking=mskNone;
bmhd.compression=cmpByteRun1;
bmhd.reserved1=0;
if (WriteChunkBytes(iff,&bmhd,sizeof(bmhd)) != sizeof(bmhd))
goto abortopen;
if (PopChunk(iff))
goto abortopen;
/* Write BODY header */
if (PushChunk(iff,ID_ILBM,ID_BODY,IFFSIZE_UNKNOWN))
goto abortopen;
return iff;
abortopen:
CloseOutfile(iff);
return NULL;
}
void CloseOutfile(struct IFFHandle *iff)
{
if(iff) {
CloseIFF(iff);
if (iff->iff_Stream)
Close(iff->iff_Stream);
FreeIFF(iff);
}
}
BOOL WriteRGB(struct IFFHandle *iff, struct DCTVCvtHandle *cvt)
{
if (!(WriteChunkyLine(iff,cvt->Red,cvt->Width)!=cvt->Width))
return FALSE;
if (!(WriteChunkyLine(iff,cvt->Green,cvt->Width)!=cvt->Width))
return FALSE;
if (!(WriteChunkyLine(iff,cvt->Blue,cvt->Width)!=cvt->Width))
return FALSE;
return TRUE;
}
/* Write one line of a primary color */
BOOL WriteChunkyLine(struct IFFHandle *iff,UBYTE *chunks,int width)
{
UBYTE i;
LONG length;
/* Pointers are incremented by packrow() so we use a copy */
BYTE *temp_plane;
BYTE *temp_comp;
/* Ends when i overflows */
for (i=1; i!=0; i+=i) {
temp_plane=(BYTE *)plane;
temp_comp=compressed;
ConvertPlane(i, chunks, width);
length=packrow(&temp_plane,&temp_comp,(LONG)ilbm.brbitmap->BytesPerRow);
if (WriteChunkBytes(iff,compressed,length)!=length)
return FALSE;
}
return TRUE;
}
void ConvertPlane(UBYTE planemask, UBYTE *line, int width)
{
int i,j,end;
UWORD currbit;
for (i=0,j=0; i<width; j++) {
for (plane[j]=0,currbit=0x8000,end=min(width,i+16); i<end; i++,currbit=currbit>>1) {
if (line[i]&planemask)
plane[j] |= currbit;
}
}
}
void bye(UBYTE *s, int e)
{
if(s&&(*s)) printf("%s\n",s);
cleanup();
exit(e);
}
void cleanup()
{
if(ilbm.ParseInfo.iff) FreeIFF(ilbm.ParseInfo.iff);
if(IFFParseBase) CloseLibrary(IFFParseBase);
if(GfxBase) CloseLibrary(GfxBase);
if(DCTVBase) CloseLibrary(DCTVBase);
}