├── Makefile ├── README ├── acApp.cpp ├── acApp.h ├── acBitmapFont.cpp ├── acBitmapFont.h ├── acFont.h ├── acFreeTypeFont.cpp ├── acFreeTypeFont.h ├── acGeo.cpp ├── acGeo.h ├── acMatrix4f.cpp ├── acMatrix4f.h ├── acSerial.cpp ├── acSerial.h ├── acThread.cpp ├── acThread.h ├── acVec3f.cpp ├── acVec3f.h ├── acVec4f.cpp ├── acVec4f.h ├── acVectorFont.cpp ├── acVectorFont.h ├── acu.h ├── geometry.c ├── jpeg.cpp ├── main.c ├── misc.cpp ├── text.cpp ├── video.c └── windows ├── acu.mcp ├── glut.h ├── glut32.dll ├── glut32.lib └── jpeg ├── cderror.h ├── cdjpeg.c ├── cdjpeg.h ├── cjpeg.c ├── ckconfig.c ├── djpeg.c ├── example.c ├── jcapimin.c ├── jcapistd.c ├── jccoefct.c ├── jccolor.c ├── jcdctmgr.c ├── jchuff.c ├── jchuff.h ├── jcinit.c ├── jcmainct.c ├── jcmarker.c ├── jcmaster.c ├── jcomapi.c ├── jconfig.h ├── jcparam.c ├── jcphuff.c ├── jcprepct.c ├── jcsample.c ├── jctrans.c ├── jdapimin.c ├── jdapistd.c ├── jdatadst.c ├── jdatasrc.c ├── jdcoefct.c ├── jdcolor.c ├── jdct.h ├── jddctmgr.c ├── jdhuff.c ├── jdhuff.h ├── jdinput.c ├── jdmainct.c ├── jdmarker.c ├── jdmaster.c ├── jdmerge.c ├── jdphuff.c ├── jdpostct.c ├── jdsample.c ├── jdtrans.c ├── jerror.c ├── jerror.h ├── jfdctflt.c ├── jfdctfst.c ├── jfdctint.c ├── jidctflt.c ├── jidctfst.c ├── jidctint.c ├── jidctred.c ├── jinclude.h ├── jmemansi.c ├── jmemdos.c ├── jmemmac.c ├── jmemmgr.c ├── jmemname.c ├── jmemnobs.c ├── jmemsys.h ├── jmorecfg.h ├── jpegint.h ├── jpeglib.h ├── jpegtran.c ├── jquant1.c ├── jquant2.c ├── jutils.c ├── jversion.h ├── rdbmp.c ├── rdcolmap.c ├── rdgif.c ├── rdjpgcom.c ├── rdppm.c ├── rdrle.c ├── rdswitch.c ├── rdtarga.c ├── transupp.c ├── transupp.h ├── wrbmp.c ├── wrgif.c ├── wrjpgcom.c ├── wrppm.c ├── wrrle.c └── wrtarga.c /Makefile: -------------------------------------------------------------------------------- 1 | #!gmake 2 | #include $(ROOT)/usr/include/make/commondefs 3 | 4 | #MYINC_DIR = /u/$(USER)/include 5 | ACINC_DIR = /acg/include 6 | 7 | #MYLIB_DIR = /u/$(USER)/lib 8 | ACLIB_DIR = /acg/lib 9 | 10 | default: lib 11 | 12 | #jarold extralibs = -lsocket -lpthread 13 | extralibs = 14 | 15 | # these are the linux (?) options 16 | #CC=CC 17 | #OPTIONS=-g -DACU_LINUX -DAC_GLWRAP -LANG:ansi-for-init-scope=ON 18 | 19 | # these are the options for cygwin make with gcc 20 | #CC=gcc 21 | #OPTIONS=-g -DNO_JPEG 22 | 23 | #this is macosx 24 | CC=cc 25 | OPTIONS = -g -DACU_MAC -F/System/Library/Frameworks/GLUT 26 | 27 | .c.o: 28 | $(CC) $(OPTIONS) $(extralibs) -c $< 29 | 30 | %.o : %.cpp 31 | $(CC) $(OPTIONS) $(extralibs) -c $< 32 | 33 | OBJS=\ 34 | acApp.o acGeo.o acVec3f.o acVec4f.o acMatrix4f.o \ 35 | geometry.o main.o misc.o text.o video.o \ 36 | acBitmapFont.o acVectorFont.o 37 | # NOT USED IN CYGWIN -- jpeg.o 38 | # RETIRED -- acFreeTypeFont.o ai.o acx.o 39 | 40 | lib: $(OBJS) 41 | rm -f libacu.a libacu.so 42 | /usr/bin/ar ru libacu.a $? 43 | # on mac you must run randlib, video.c un-inited constants mean -c 44 | ranlib -c libacu.a 45 | 46 | clean: 47 | rm -f *.o libacu.a libacu.so *~ 48 | 49 | install: lib 50 | rm -f $(ACLIB_DIR)/libacu.a $(ACLIB_DIR)/libacu.so 51 | cp libacu.a libacu.so $(ACLIB_DIR)/. 52 | chmod 555 $(ACLIB_DIR)/libacu.a $(ACLIB_DIR)/libacu.so 53 | cp *.h $(ACINC_DIR)/. 54 | 55 | mine: lib 56 | rm -f $(MYLIB_DIR)/libacu.a $(MYLIB_DIR)/libacu.so 57 | cp libacu.a libacu.so $(MYLIB_DIR)/. 58 | chmod 555 $(MYLIB_DIR)/libacu.a $(MYLIB_DIR)/libacu.so 59 | cp *.h $(MYINC_DIR)/. 60 | 61 | again: clean lib 62 | 63 | -------------------------------------------------------------------------------- /README: -------------------------------------------------------------------------------- 1 | about acu, sometimes a twice-weekly newsletter for the acu community 2 | 3 | [ todo ] 4 | acApp::mouseDrag -> pass in mouse button, save lastmousex,y 5 | add acuStringWidth, or acuDrawString(char *, x, y, align) 6 | or acuDrawParagraph(char * x, y, align, leading, etc) 7 | 8 | [ october 31 2000 ] 9 | - removed acx and ai, both of which were unsupported 10 | - removed acMatrix4f, it wasn't particularly well designed 11 | - removed acThread, it hasn't been used 12 | - removed Makefile.cygnus, because i think it's way outta date 13 | 14 | [ whenever ] 15 | - acuLine functions have been modified and renamed slightly. 16 | - acx and ai stuff was added. these are not supported. 17 | - acMatrix4f has been added for 'thrill seekers', its api 18 | may change and/or some of its functions may be removed 19 | 20 | [ august 10 1999 ] 21 | stuff from tom 22 | - acApp and acWindow are one, and all of the apps are broken 23 | in between. 24 | stuff from ben 25 | - fixed bugs in polygon drawing code, thanks to casey, who 26 | tried using it for the first time since acu's inception 27 | - windows version now supports jpeg. yay. 28 | 29 | [ july 2 1999 ] 30 | stuff from ben 31 | - acuScreenGrab (and subsequently acApp::screenGrab) can now write 32 | (hold your breath) ppm, raw, and (drum roll) tiff files. death to 33 | scrsave! die die die! documentation for using these fancy features 34 | can be found in the acu online documentation (acu.h) or from the 35 | forthcoming o'reilly book, now in draft form from our very own 36 | casey reas. 37 | - fixed a number of bugs with the previously undocumented and unheard 38 | of acuReadRawFile, acuWriteRawFile, acuRecomponentArray and others. 39 | they're now briefly mentioned in the docs, read up, they could 40 | save you time and money. 41 | - cleaned up acuTexRectf, which was having 'issues'. 42 | - additional fistfuls of minor bug fixes, many found by bug magnets 43 | jocelyn lin and bill keays. 44 | stuff from tom 45 | - theApp in acApp is now a static class member 46 | - moved callback function defs to .h instead of .cpp 47 | 48 | [ may 2 1999 ] 49 | stuff from ben and tom 50 | - more documentation and examples in acu.h 51 | - video proxy now works with a string of jpeg files 52 | - unified the sgi and windows codewarrior versions 53 | - lots of windows porting stuff ironed out 54 | - attempt to add jpeg to windows failed, will try again in a few weeks 55 | - objective c stuff (acoApp) no longer in the main acu distribution 56 | - added codewarrior project file 57 | - lots of little cleanup things 58 | 59 | [ mar 26 1999 ] 60 | stuff from ben 61 | - ABS(x) had a bug. oops. 62 | - added acuSetInteger(ACU_TIME_STEP, step) so that people 63 | can slow down the time returned by acuCurrentTimeMillis. 64 | - merged in the changes for the windows version of acu. 65 | these changes should make the mac version simpler as well. 66 | 67 | [ mar 18 1999 ] 68 | stuff from ben 69 | - acu.h and acApp.h are finally documented. 70 | - added acuColorHsb - fight the RGB tyranny! 71 | - did some fixes/changes to the font stuff to get that 72 | behaving a little bit better (or failing more gracefully) 73 | - misc bug fixes 74 | 75 | [ feb 22 1999 ] 76 | MESS AND CLEAN UP by Ben 77 | - acApp function names all begin with lowercase. 78 | - made acuGet/acuSet methods for ACU_SCREEN_FOV. 79 | - removed acuSetMazoFov, acuMalloc, acuFree, acuRound 80 | because they were silly. 81 | - removed random comments and dead code. 82 | - removed twod.c, since it only contained the line functions, 83 | and put it into 84 | 85 | [ feb 21 1999 ] 86 | FIX by Tom 87 | - Switched CANNOT_BIND_TEXTURES on for Golan 88 | - Reorgainized /mas/acg/projects for stable acu development future 89 | 90 | 91 | [ feb 20 1999 ] 92 | ADDITION by Tom 93 | - Added acoApp to libacu.a, which is the objective-C version of acApp 94 | * This adds libobjc to the things to link against, thought this should 95 | only matter to people using acoApp. See Makefile for more documentation. 96 | 97 | 98 | [ feb 19 1999 ] 99 | ADDITIONS/FIXES by Tom 100 | 101 | - C/C++ cleanup. Made acu.h a straight C file, including extern C wrapper 102 | - changed straight C files to file.c, C++ files now file.C 103 | - moved acApp core into acu as that makes more sense 104 | 105 | 106 | [ jan 29 1999 ] 107 | 108 | ADDITIONS/FIXES IN THIS VERSION 109 | - drawing fonts now take x, y positions. this is 110 | (hopefully) faster than calling glTranslatef for 111 | each individual character. 112 | - acVec3f has been modified and closer to its 113 | final resting place. be warned, however, to use 114 | acVec3f at your own risk. 115 | 116 | 117 | [ jan 25 1999 ] 118 | 119 | ADDITIONS/FIXES IN THIS VERSION 120 | - font support is now included 121 | - reading & writing of jpeg files 122 | - acuScreenGrab (mmmm... tasty...) 123 | 124 | DEMOS/EXAMPLES/HOWTO 125 | included, though in sort of a mess, are a few of my 126 | projects, rewritten for acu. among these are the following: 127 | hsvspace6 - live demo of the hsv color cone (uses video input) 128 | spinner2 - unfinished port of my java spinner applet (loads a jpeg file) 129 | disgrand2 - gradient-sorting of colors in video input (uses 2d) 130 | 131 | OTHER NOTES 132 | - you need to include -ljpeg in your Makefile, to include the 133 | jpeg library. look for a line that reads '-lGL -lXm -lglut' etc. 134 | - you might not want to use acVec3f unless you really need it and 135 | are willing to rewrite code when its api changes over the next week 136 | -------------------------------------------------------------------------------- /acApp.cpp: -------------------------------------------------------------------------------- 1 | #include "acApp.h" 2 | 3 | //acApp *acApp::theApp = NULL; 4 | int aaGrabCount; 5 | int aaLastMouseButton; 6 | boolean aaValidWindowSize; 7 | acApp* apps[10]; 8 | 9 | int aahaveShrunk=FALSE, aafullScreen=TRUE, aafullWidth, aafullHeight; 10 | int aaWinH, aaWinW, aaWinX, aaWinY; 11 | 12 | /* for mouseCallback Y switcheroo and reshaping */ 13 | extern "C" GLint acuWindowHeight; 14 | extern "C" GLint acuWindowWidth; 15 | 16 | // keep these here, otherwise will cause conflicts! (don't put in .h) 17 | #include 18 | #include 19 | 20 | 21 | /* This is some glue that connects the app to the window system */ 22 | 23 | /* 24 | #ifdef ACU_WIN32 25 | #include "ansi_prefix.win32.h" 26 | #include 27 | #include 28 | #define ExternalApp extern "C" __declspec(dllexport) acApp 29 | #define ExternalType extern "C" __declspec(dllexport) char 30 | #else 31 | #define ExternalApp extern "C" acApp 32 | #define ExternalType extern "C" char 33 | #endif 34 | */ 35 | 36 | acApp::acApp() 37 | { 38 | aaGrabCount = -1; 39 | aaValidWindowSize = FALSE; 40 | X = Y = 0; 41 | W = H = 100; 42 | } 43 | 44 | void acApp::selfStart() 45 | { 46 | GLint screenSize[2]; 47 | 48 | // the following 3 lines were removed from acuOpen 49 | glutCreateWindow("acu"); 50 | glutFullScreen(); 51 | acuGlobalGLSettings(); 52 | 53 | //theApp = this; 54 | apps[glutGetWindow()] = this; 55 | 56 | glutDisplayFunc(display_cb); 57 | glutMouseFunc(mouse_cb); 58 | glutMotionFunc(motion_cb); 59 | glutPassiveMotionFunc(passive_motion_cb); 60 | glutIdleFunc(idle_cb); 61 | glutKeyboardFunc(keyboard_cb); 62 | glutSpecialFunc(special_key_cb); 63 | glutReshapeFunc(reshape_cb); 64 | 65 | acuGetIntegerv(ACU_WINDOW_SIZE, screenSize); 66 | resize(0, 0, screenSize[0], screenSize[1]); 67 | setFocus(true); 68 | glutMainLoop(); 69 | } 70 | 71 | void acApp::subStart() { 72 | //theApp = this; 73 | apps[glutGetWindow()] = this; 74 | 75 | glutDisplayFunc(display_cb); 76 | glutMouseFunc(mouse_cb); 77 | glutMotionFunc(motion_cb); 78 | glutPassiveMotionFunc(passive_motion_cb); 79 | glutIdleFunc(idle_cb); 80 | glutKeyboardFunc(keyboard_cb); 81 | glutSpecialFunc(special_key_cb); 82 | glutReshapeFunc(reshape_cb); 83 | } 84 | 85 | void acApp::setFocus(bool state) { } 86 | 87 | void acApp::setParent(void *parent) { } 88 | 89 | void acApp::resize(float posX, float posY, float width, float height) { 90 | X = posX; 91 | Y = posY; 92 | W = width; 93 | H = height; 94 | } 95 | 96 | bool acApp::pointInside(float x, float y) { 97 | return (x >= 0 && y >= 0 && x < W && y < H); 98 | } 99 | 100 | void acApp::screenGrab() { 101 | char ext[6]; 102 | switch (acuGetInteger(ACU_SCREEN_GRAB_FORMAT)) { 103 | case ACU_FILE_FORMAT_JPEG: sprintf(ext, "jpg"); break; 104 | case ACU_FILE_FORMAT_RAW: sprintf(ext, "raw"); break; 105 | case ACU_FILE_FORMAT_PPM: sprintf(ext, "ppm"); break; 106 | case ACU_FILE_FORMAT_TIFF: sprintf(ext, "tif"); break; 107 | case ACU_FILE_FORMAT_SCRSAVE: sprintf(ext, "rgb"); break; 108 | } 109 | 110 | char grabTemp[24]; 111 | if (aaGrabCount == -1) { 112 | // set aaGrabCount by checking to see how many files exist 113 | aaGrabCount = 0; 114 | int fd = -1; 115 | do { 116 | if (fd != -1) { 117 | close(fd); 118 | aaGrabCount++; 119 | } 120 | sprintf(grabTemp, "screen-%04d.%s", aaGrabCount, ext); 121 | } while ((fd = open(grabTemp, O_RDONLY)) != -1); 122 | } 123 | sprintf(grabTemp, "screen-%04d.%s", aaGrabCount, ext); 124 | acuScreenGrab(grabTemp); 125 | aaGrabCount++; 126 | } 127 | 128 | //int acApp::getModifiers() { return lastModifiers; } 129 | void acApp::mouseMove(float x, float y) { } 130 | void acApp::mouseDown(float x, float y, int button) { } 131 | 132 | void acApp::mouseDrag(float x, float y) { } 133 | void acApp::mouseDrag(float x, float y, int button) { } 134 | void acApp::mouseUp(float x, float y, int button) { } 135 | 136 | /* this quitAtOne idle callback rewiring quit thing 137 | * is a workaround for bad driver/cards that don't like 138 | * to quit in fullscreen mode 139 | */ 140 | int quitAtOne = 0; 141 | 142 | void winddown_cb(void) { 143 | if(quitAtOne <= 1) acuClose(); 144 | else --quitAtOne; 145 | } 146 | 147 | void acApp::keyDown(char c) { 148 | GLint small[] = {100, 100}; 149 | // Default behavior, close program on escape 150 | if (c == 27) { // escape 151 | // it doesn't exit in fullscreen mode, but shrinks first 152 | acuSetIntegerv(ACU_WINDOW_SIZE, small); 153 | glutIdleFunc(winddown_cb); 154 | quitAtOne = 5; 155 | } 156 | } 157 | 158 | void acApp::specialKeyDown( int key) { 159 | /* default behavior of SKD: toggle between fullscreen on F1 160 | * if you override and want to keep, just call acApp::specialKeyDown(key) 161 | * on F1 (or even acApp::specialKeyDown(GLUT_KEY_F1) on a different key) 162 | */ 163 | GLint size[2]; 164 | if(key == GLUT_KEY_F1) { 165 | if(aafullScreen) { 166 | if(aahaveShrunk == FALSE) { 167 | aahaveShrunk = TRUE; 168 | aafullWidth = acuWindowWidth; 169 | aafullHeight = acuWindowHeight; 170 | aaWinW = acuWindowWidth - 70; 171 | aaWinH = acuWindowHeight - 90; 172 | aaWinX = 35; 173 | aaWinY = 55; 174 | } 175 | aafullScreen = FALSE; 176 | aafullWidth = (int)W; 177 | aafullHeight = (int)H; 178 | size[0] = aaWinW; size[1] = aaWinH; 179 | acuSetIntegerv(ACU_WINDOW_SIZE, size); 180 | glutPositionWindow(aaWinX, aaWinY); 181 | } 182 | else { 183 | aafullScreen = TRUE; 184 | aaWinX = glutGet(GLUT_WINDOW_X); 185 | aaWinY = glutGet(GLUT_WINDOW_Y); 186 | aaWinW = (int)W; 187 | aaWinH = (int)H; 188 | glutFullScreen(); 189 | } 190 | } 191 | } 192 | 193 | void acApp::draw() { } 194 | void acApp::idle() { } 195 | 196 | void display_cb(void) { 197 | if (!aaValidWindowSize) 198 | aaValidWindowSize = (acuGetInteger(ACU_WINDOW_WIDTH) != 0); 199 | if (aaValidWindowSize) { 200 | /* BENJAMIN FRY -- FIX ME!!! */ 201 | acuOpenMazoFrame(); 202 | //acApp::theApp->draw(); 203 | apps[glutGetWindow()]->draw(); 204 | acuCloseMazoFrame(); 205 | } 206 | } 207 | 208 | void mouse_cb(int button, int state, int x, int y) { 209 | //lastModifiers = glutGetModifiers(); 210 | if (state == GLUT_DOWN) { 211 | apps[glutGetWindow()]->mouseDown(x, ((acuWindowHeight-1)-y), button); 212 | } else if (state == GLUT_UP) { 213 | apps[glutGetWindow()]->mouseUp(x, ((acuWindowHeight-1)-y), button); 214 | } 215 | aaLastMouseButton = button; 216 | } 217 | 218 | void motion_cb(int x, int y) { 219 | //lastModifiers = glutGetModifiers(); 220 | apps[glutGetWindow()]->mouseDrag(x, ((acuWindowHeight-1)-y)); 221 | apps[glutGetWindow()]->mouseDrag(x, ((acuWindowHeight-1)-y), aaLastMouseButton); 222 | } 223 | 224 | void passive_motion_cb(int x, int y) { 225 | //lastModifiers = glutGetModifiers(); 226 | apps[glutGetWindow()]->mouseMove(x, ((acuWindowHeight-1)-y)); 227 | } 228 | 229 | void idle_cb(void) { 230 | apps[glutGetWindow()]->idle(); 231 | glutPostRedisplay(); 232 | } 233 | 234 | void keyboard_cb(unsigned char key, int x, int y) { 235 | //lastModifiers = glutGetModifiers(); 236 | apps[glutGetWindow()]->keyDown(key); 237 | } 238 | 239 | void special_key_cb(int key, int x, int y) { 240 | //lastModifiers = glutGetModifiers(); 241 | apps[glutGetWindow()]->specialKeyDown(key); 242 | } 243 | 244 | void reshape_cb(int width, int height) { 245 | acuWindowWidth = width; 246 | acuWindowHeight = height; 247 | apps[glutGetWindow()]->resize(0, 0, width, height); 248 | } 249 | 250 | 251 | -------------------------------------------------------------------------------- /acApp.h: -------------------------------------------------------------------------------- 1 | #ifndef _AC_APP_H_ 2 | #define _AC_APP_H_ 3 | 4 | #include "acu.h" 5 | #include "acGeo.h" 6 | 7 | 8 | class acApp : public acGeo { 9 | public: 10 | /* Your application can just have a simple 'main' in 11 | * a separate main.cpp file that looks something like this: 12 | * void main() { 13 | * acuOpen(); 14 | * acApp *myApp = makeApp(); 15 | * myApp->selfStart(); 16 | * } 17 | * selfStart() is the 'bootstrap' function to get the 18 | * app up and running. Don't override it unless you know 19 | * what you're doing. 20 | */ 21 | acApp(); 22 | virtual void selfStart(); 23 | virtual void subStart(); 24 | 25 | /* Called to let you know your program is (or isn't) getting attention. */ 26 | virtual void setFocus(bool state); 27 | 28 | virtual void setParent(void *parent); 29 | 30 | /* The X, Y, W, H variables are the position and size of the window */ 31 | float X, Y, W, H; 32 | 33 | /* Called when you are resized. 34 | Default implementation is to update X, Y, W, H 35 | If you override resize(), call acApp::resize() or do 36 | this yourself */ 37 | virtual void resize(float posX, float posY, float width, float height); 38 | 39 | /* Someone is asking you if (x,y) is your responsibility */ 40 | virtual bool pointInside(float x, float y); 41 | 42 | /* (Generally) called once every frame, just before draw(). 43 | * This is automatically called repeatedly as your 44 | * application 'idles'. Move things around here. 45 | * 46 | * This is inherited from acGeo. 47 | */ 48 | virtual void idle(); 49 | 50 | /* Override this to do your actual drawing to the screen 51 | * A good acApp should draw the same thing if draw is called 52 | * twice in succession since idle(), not draw(), changes the model 53 | * 54 | * This is inherited from acGeo. 55 | */ 56 | virtual void draw(); 57 | 58 | /* Writes the current GL buffer (your application's window) 59 | * to a JPEG file called 'screen-XXXX.jpg' with XXX being 60 | * automatically numbered. In addition, it won't write over 61 | * existing screen-XXXX files, because it looks for the highest 62 | * numbered screen in the current directory. 63 | * 64 | * See acu.h for more information about writing to 65 | * different file formats. 66 | * 67 | * If you're the type of person who wants to make a movie 68 | * of your acu application, you could use the following code 69 | * to resize your window so that subsequent screen grabs 70 | * would be 640x480. Put this towards the end of your 71 | * prepare() function. 72 | * 73 | * int screenSize[2]; 74 | * screenSize[0] = 640; 75 | * screenSize[1] = 480; 76 | * acuSetIntegerv(ACU_WINDOW_SIZE, screenSize); 77 | */ 78 | void screenGrab(); 79 | 80 | /* Override these functions to get mouse events. 81 | * for mouseDown and mouseUp, button is one of: 82 | * GLUT_LEFT_BUTTON, GLUT_MIDDLE_BUTTON, or GLUT_RIGHT_BUTTON 83 | * Modifiers are one of: 84 | * GLUT_ACTIVE_SHIFT, GLUT_ACTIVE_CTRL, GLUT_ACTIVE_ALT 85 | */ 86 | //int getModifiers(); 87 | virtual void mouseMove(float x, float y); 88 | virtual void mouseDown(float x, float y, int button); 89 | virtual void mouseDrag(float x, float y); /* deprecated */ 90 | virtual void mouseDrag(float x, float y, int button); 91 | virtual void mouseUp(float x, float y, int button); 92 | 93 | /* Override to get keys from the keyboard. */ 94 | virtual void keyDown(char c); 95 | 96 | /* Any sort of non-standard key, possibilities are: 97 | * GLUT_KEY_F1, GLUT_KEY_F2, GLUT_KEY_F3, GLUT_KEY_F4, 98 | * GLUT_KEY_F5, GLUT_KEY_F6, GLUT_KEY_F7, GLUT_KEY_F8, 99 | * GLUT_KEY_F9, GLUT_KEY_F10, GLUT_KEY_F11, GLUT_KEY_F12, 100 | * GLUT_KEY_LEFT, GLUT_KEY_UP, GLUT_KEY_RIGHT, GLUT_KEY_DOWN 101 | * GLUT_KEY_PAGE_UP, GLUT_KEY_PAGE_DOWN, 102 | * GLUT_KEY_HOME, GLUT_KEY_END, GLUT_KEY_INSERT 103 | */ 104 | virtual void specialKeyDown(int key); 105 | 106 | //static acApp *theApp; 107 | }; 108 | 109 | // made "extern" by max, who had nothing better to do. 3/24/01 110 | extern acApp* apps[10]; 111 | // ---- definition in acApp.cpp 112 | 113 | void display_cb(void); 114 | void mouse_cb(int button, int state, int x, int y); 115 | void motion_cb(int x, int y); 116 | void passive_motion_cb(int x, int y); 117 | void idle_cb(void); 118 | void keyboard_cb(unsigned char key, int x, int y); 119 | void special_key_cb(int key, int x, int y); 120 | void reshape_cb(int x, int y); 121 | 122 | /* This is some glue that connects the app to the window system */ 123 | #ifdef ACU_WIN32 124 | #ifndef __CYGWIN__ 125 | /* cygwin doesn't know what this file is */ 126 | #include "ansi_prefix.win32.h" 127 | #endif 128 | #define ExportApp extern "C" __declspec(dllexport) acApp 129 | #define ExportType extern "C" __declspec(dllexport) char 130 | #else 131 | #define ExportApp extern "C" acApp 132 | #define ExportType extern "C" char 133 | #endif 134 | 135 | /* this is the function declaration - put the function in your App */ 136 | ExportApp *makeApp(void); 137 | 138 | #endif 139 | -------------------------------------------------------------------------------- /acBitmapFont.cpp: -------------------------------------------------------------------------------- 1 | #include "acBitmapFont.h" 2 | 3 | 4 | // this is for encoding from windows ansi to mac ordering for 5 | // the 8 bits chars outside ascii range (chars with values > 127) 6 | int win2mac[256] = { 7 | 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 8 | 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 9 | 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 10 | 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 11 | 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 12 | 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101, 13 | 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 14 | 115, 116, 117, 118, 119, 120, 121, 122, 123, 124, 125, 126, 127, 15 | -1, -1, 226, 196, 227, 201, 160, 224, 246, 228, -1, 220, 206, -1, 16 | -1, -1, -1, 212, 213, 210, 211, 165, 208, 209, 247, 170, -1, 221, 17 | 207, -1, -1, 217, -1, 193, 162, 163, 219, 180, -1, 164, 172, 169, 18 | 187, 199, 194, -1, 168, 248, 161, 177, -1, -1, 171, 181, 166, 225, 19 | 252, -1, 188, 200, -1, -1, -1, 192, 203, 231, 229, 204, 128, 129, 20 | 174, 130, 233, 131, 230, 232, 237, 234, 235, 236, -1, 132, 241, 21 | 238, 239, 205, 133, -1, 175, 244, 242, 243, 134, -1, -1, 167, 136, 22 | 135, 137, 139, 138, 140, 190, 141, 143, 142, 144, 145, 147, 146, 23 | 148, 149, -1, 150, 152, 151, 153, 155, 154, 214, 191, 157, 156, 158, 24 | 159, -1, -1 25 | }; 26 | 27 | 28 | acBitmapFont::acBitmapFont(const char *filename) { 29 | int i; 30 | valid = FALSE; 31 | FILE *fp = fopen(filename, "rb"); 32 | if (fp == NULL) { 33 | sprintf(acuDebugStr, "Could not open font file %s", filename); 34 | acuDebugString(ACU_DEBUG_PROBLEM); 35 | return; 36 | } 37 | 38 | // read the base font information 39 | numChars = acuReadInt(fp); 40 | //printf("num chars for font is %d\n", numChars); 41 | numBits = acuReadInt(fp); 42 | mboxX = acuReadInt(fp); 43 | mboxY = acuReadInt(fp); 44 | baseHt = acuReadInt(fp); 45 | acuReadInt(fp); // ignore 4 for struct; 46 | 47 | // allocate enough space for the character info 48 | value = new int[numChars]; 49 | height = new int[numChars]; 50 | width = new int[numChars]; 51 | setWidth = new int[numChars]; 52 | topExtent = new int[numChars]; 53 | leftExtent = new int[numChars]; 54 | 55 | // read the information about the individual characters 56 | for (i = 0; i < numChars; i++) { 57 | value[i] = acuReadInt(fp); 58 | height[i] = acuReadInt(fp); 59 | width[i] = acuReadInt(fp); 60 | setWidth[i] = acuReadInt(fp); 61 | topExtent[i] = acuReadInt(fp); 62 | leftExtent[i] = acuReadInt(fp); 63 | acuReadInt(fp); // pointer, ignored 64 | } 65 | 66 | // read in the bitmap data 67 | //images = new unsigned char[numChars][64*64*4]; 68 | images = new unsigned char*[numChars]; 69 | for (i = 0; i < numChars; i++) { 70 | images[i] = new unsigned char[64*64*4]; 71 | int bitmapSize = height[i] * width[i]; 72 | //printf("bitmap size is %d\n", bitmapSize); 73 | unsigned char *temp = new unsigned char[bitmapSize]; 74 | fread(temp, bitmapSize, 1, fp); 75 | 76 | // convert the bitmap to an alpha channel 77 | int w = width[i]; 78 | int h = height[i]; 79 | for (int x = 0; x < w; x++) { 80 | for (int y = 0; y < h; y++) { 81 | int offset = (y*64 + x) * 4; 82 | images[i][offset + 0] = 255; 83 | images[i][offset + 1] = 255; 84 | images[i][offset + 2] = 255; 85 | images[i][offset + 3] = temp[(h-y-1)*w + x]; 86 | //printf((images[i][offset+3] > 128) ? "*" : "."); 87 | } 88 | //printf("\n"); 89 | } 90 | } 91 | 92 | // build textures for each of the characters 93 | texNames = new GLuint[numChars]; 94 | glPixelStorei(GL_UNPACK_ALIGNMENT, 1); 95 | //printf("numChars is %d\n", numChars); 96 | glGenTextures(numChars, texNames); 97 | //for (int m = 0; m < numChars; m++) { 98 | //printf("%d ", texNames[m]); 99 | //} 100 | 101 | for (i = 0; i < numChars; i++) { 102 | glBindTexture(GL_TEXTURE_2D, texNames[i]); 103 | glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 64, 64, 0, 104 | GL_RGBA, GL_UNSIGNED_BYTE, images[i]); 105 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP); 106 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP); 107 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 108 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 109 | glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); 110 | } 111 | valid = TRUE; 112 | } 113 | 114 | int acBitmapFont::getFormat() { 115 | return ACU_BITMAP_FONT; 116 | } 117 | 118 | float acBitmapFont::getDescent() { 119 | return (float)(height['p'-33] - topExtent['p'-33]) / 64.0f; 120 | } 121 | 122 | float acBitmapFont::getHeight() { 123 | return (float)mboxY / 64.0f; 124 | } 125 | 126 | float acBitmapFont::charWidth(unsigned char c) { 127 | // width of the horizontal space char takes up 128 | //if (c != ' ') { 129 | if (charExists(c)) { 130 | return (float)setWidth[win2mac[c]-33] / 64.0f; 131 | 132 | } else { 133 | //return charWidth('i')*1.2f; 134 | return charWidth('n'); // support monospace better 135 | } 136 | } 137 | 138 | float acBitmapFont::charHeight(unsigned char c) { 139 | return charExists(c) ? (float)height[win2mac[c]-33]/64.0f : 0; 140 | } 141 | 142 | float acBitmapFont::charBitmapWidth(unsigned char c) { 143 | // width of the bitmap itself 144 | return charExists(c) ? (float)width[win2mac[c]-33] / 64.0f : 0; 145 | } 146 | 147 | float acBitmapFont::charBitmapHeight(unsigned char c) { 148 | // same as charHeight 149 | return charExists(c) ? (float)height[win2mac[c]-33] / 64.0f : 0; 150 | } 151 | 152 | float acBitmapFont::charTop(unsigned char c) { 153 | return charExists(c) ? 154 | (-charHeight(c) + (float)(topExtent[win2mac[c]-33]) / 64.0f) : 0; 155 | } 156 | 157 | float acBitmapFont::charTopExtent(unsigned char c) { 158 | return charExists(c) ? 159 | (float)topExtent[win2mac[c]-33] / 64.0f : 0; 160 | } 161 | 162 | float acBitmapFont::charLeftExtent(unsigned char c) { 163 | return charExists(c) ? 164 | (float)leftExtent[win2mac[c]-33] / 64.0f : 0; 165 | } 166 | 167 | boolean acBitmapFont::charExists(unsigned char c) { 168 | //return (c-33 < numChars); 169 | if (win2mac[c] == -1) return false; // out of encoding 170 | return ((c > 32) && (c-33 < numChars)); 171 | //return ((c > 32) && (c < numChars)); 172 | } 173 | 174 | unsigned char* acBitmapFont::getCharData(unsigned char c, float *x, float *y, float *w, float *h) { 175 | if (!charExists(c)) return NULL; 176 | *x = charLeftExtent(c); 177 | *y = charTop(c); 178 | *w = charBitmapWidth(c); 179 | *h = charHeight(c); 180 | /* 181 | params[0] = charLeftExtent(c); // x 182 | params[1] = charTop(c); // y 183 | params[2] = charBitmapWidth(c); // width 184 | params[3] = charHeight(c); // height 185 | //params[4] = bwidth; // maxu 186 | //params[5] = height; // maxv 187 | */ 188 | return images[c-33]; 189 | } 190 | 191 | void acBitmapFont::drawChar(unsigned char c, float x, float y) { 192 | // x,y is insertion point, lower-left, on baseline 193 | //if (c < 33) return; 194 | //if (c > numChars + 32) return; 195 | if (!charExists(c)) return; 196 | 197 | /* 198 | if (!charExists(c)) { 199 | int m = win2mac[c-128]; 200 | if (m == -1) m = 'X'; 201 | printf("%d does not exist %c '%c'\n", c, c, m); 202 | return; 203 | } 204 | 205 | //if (c+33 > 127) { 206 | if (c > 127) { 207 | //printf("got something outside: %d\n", c+33); 208 | c = win2mac[c]; 209 | if (c == -1) return; // char not in encoding 210 | printf("found %c\n", (unsigned char)c); 211 | } 212 | //glEnable(GL_TEXTURE_2D); 213 | */ 214 | 215 | float height = charHeight(c); 216 | //float width = charWidth(c); 217 | float bwidth = charBitmapWidth(c); 218 | float top = charTop(c); 219 | float lextent = charLeftExtent(c); 220 | 221 | #ifndef CANNOT_BIND_TEXTURES 222 | 223 | if (glIsTexture(texNames[win2mac[c]-33])) { 224 | acuNamedTexRectf(x+lextent, y+top, 225 | x+lextent+bwidth, y+height+top, 226 | texNames[win2mac[c]-33], bwidth, height); 227 | } else { 228 | sprintf(acuDebugStr, "Could not bind: %c %d\n", c, c); 229 | acuDebugString(ACU_DEBUG_MUMBLE); 230 | acuTexRectf(x+lextent, y+top, x+lextent+bwidth, y+height+top, 231 | images[c-33], GL_RGBA, 4, 64, 64, bwidth, height); 232 | } 233 | 234 | #else 235 | 236 | acuTexRectf(x+lextent, y+top, x+lextent+bwidth, y+height+top, 237 | images[win2mac[c]-33], GL_RGBA, 4, 64, 64, bwidth, height); 238 | #endif 239 | 240 | #if 0 241 | // to draw the baseline 242 | glBegin(GL_LINES); 243 | glVertex3f(x, y, 0); 244 | glVertex3f(x+width*0.95f, y, 0); 245 | glEnd(); 246 | #endif 247 | } 248 | 249 | 250 | -------------------------------------------------------------------------------- /acBitmapFont.h: -------------------------------------------------------------------------------- 1 | #ifndef _AC_BITMAP_FONT_H_ 2 | #define _AC_BITMAP_FONT_H_ 3 | 4 | #include "acu.h" 5 | #include "acFont.h" 6 | 7 | 8 | class acBitmapFont : public acFont { 9 | public: 10 | acBitmapFont() { } // for subclasses.. grr. 11 | acBitmapFont(const char *filename); 12 | 13 | float getDescent(); 14 | float getHeight(); 15 | float charWidth(unsigned char c); 16 | float charHeight(unsigned char c); 17 | boolean charExists(unsigned char c); 18 | void drawChar(unsigned char c, float x, float y); 19 | int getFormat(); 20 | unsigned char* getCharData(unsigned char c, float *x, float *y, 21 | float *w, float *h); 22 | //protected: 23 | int numChars; 24 | int numBits; 25 | int mboxX; 26 | int mboxY; 27 | int baseHt; 28 | 29 | // per character 30 | int *value; 31 | int *height; 32 | int *width; 33 | int *setWidth; 34 | int *topExtent; 35 | int *leftExtent; 36 | 37 | unsigned char **images; 38 | GLuint *texNames; 39 | 40 | float charBitmapWidth(unsigned char c); 41 | float charBitmapHeight(unsigned char c); 42 | float charTop(unsigned char c); 43 | float charTopExtent(unsigned char c); 44 | float charLeftExtent(unsigned char c); 45 | }; 46 | 47 | #endif 48 | 49 | -------------------------------------------------------------------------------- /acFont.h: -------------------------------------------------------------------------------- 1 | #ifndef _AC_FONT_H_ 2 | #define _AC_FONT_H_ 3 | 4 | #include "acu.h" 5 | 6 | 7 | class acFont { 8 | public: 9 | virtual float getAscent() { return charHeight('H'); } 10 | virtual float getDescent() { return 0; } 11 | virtual float getXHeight() { return charHeight('x'); } 12 | virtual float getHeight() { return 0; } 13 | virtual float getEmWidth() { return charWidth('M'); } 14 | virtual float getDefaultLeading() { return getHeight() * 1.2; } 15 | virtual float charWidth(unsigned char c) { return 0; } 16 | virtual float charHeight(unsigned char c) { return 0; } 17 | virtual boolean charExists(unsigned char c) { return FALSE; } 18 | virtual void drawChar(unsigned char c, float x, float y) { } 19 | virtual float kernWidth(unsigned char a, unsigned char b) { return 0; } 20 | virtual int getFormat() { return ACU_ERROR; } 21 | virtual boolean isValid() { return valid; } 22 | 23 | virtual float stringWidth(unsigned char *s) { 24 | float wide = 0; 25 | float pwide = 0; 26 | unsigned char previous = 0; 27 | while (*s != 0) { 28 | if (*s == '\n') { 29 | if (wide > pwide) pwide = wide; 30 | wide = 0; 31 | previous = 0; 32 | } else { 33 | wide += charWidth(*s); 34 | if (previous != 0) 35 | wide += kernWidth(previous, *s); 36 | previous = *s; 37 | } 38 | s++; 39 | } 40 | return (pwide > wide) ? pwide : wide; 41 | } 42 | 43 | virtual void drawString(unsigned char *c, float x, float y) { 44 | glPushMatrix(); 45 | float startX = x; 46 | int index = 0; 47 | unsigned char previous = 0; 48 | while (c[index] != 0) { 49 | if (c[index] == '\n') { 50 | x = startX; 51 | y -= getDefaultLeading(); 52 | //printf("adding leading\n"); 53 | previous = 0; 54 | } else { 55 | drawChar(c[index], x, y); 56 | x += charWidth(c[index]); 57 | if (previous != 0) 58 | x += kernWidth(previous, c[index]); 59 | previous = c[index]; 60 | } 61 | index++; 62 | } 63 | glPopMatrix(); 64 | } 65 | 66 | 67 | protected: 68 | boolean valid; 69 | }; 70 | 71 | 72 | #endif 73 | -------------------------------------------------------------------------------- /acFreeTypeFont.cpp: -------------------------------------------------------------------------------- 1 | #include "acFreeTypeFont.h" 2 | 3 | 4 | acFreeTypeFont::acFreeTypeFont(const char *name) { 5 | valid = FALSE; 6 | 7 | char filename[256]; 8 | strcpy(filename, name); 9 | char *p = strchr(filename, ' '); 10 | *p++ = 0; 11 | fontSize = atoi(p); 12 | 13 | face = new FTFace(); 14 | if (!face->open(filename)) { 15 | sprintf(acuDebugStr, "unable to open font %s", filename); 16 | acuDebugString(ACU_DEBUG_PROBLEM); 17 | return; 18 | } 19 | 20 | font = new GLTTPixmapFont(face); 21 | if (!font->create(fontSize)) { 22 | sprintf(acuDebugStr, "could not set up %s in size %d", font, fontSize); 23 | acuDebugString(ACU_DEBUG_PROBLEM); 24 | return; 25 | } 26 | valid = TRUE; 27 | //printf("initialized font\n"); 28 | } 29 | 30 | acFreeTypeFont::acFreeTypeFont(const char *filename) { 31 | int i; 32 | valid = FALSE; 33 | FILE *fp = fopen(filename, "rb"); 34 | if (fp == NULL) { 35 | sprintf(acuDebugStr, "Could not open font file %s", filename); 36 | acuDebugString(ACU_DEBUG_PROBLEM); 37 | return; 38 | } 39 | 40 | // read the base font information 41 | numChars = acuReadInt(fp); 42 | numBits = acuReadInt(fp); 43 | mboxX = acuReadInt(fp); 44 | mboxY = acuReadInt(fp); 45 | baseHt = acuReadInt(fp); 46 | acuReadInt(fp); // ignore 4 for struct; 47 | 48 | // allocate enough space for the character info 49 | value = new int[numChars]; 50 | height = new int[numChars]; 51 | width = new int[numChars]; 52 | setWidth = new int[numChars]; 53 | topExtent = new int[numChars]; 54 | leftExtent = new int[numChars]; 55 | 56 | // read the information about the individual characters 57 | for (i = 0; i < numChars; i++) { 58 | value[i] = acuReadInt(fp); 59 | height[i] = acuReadInt(fp); 60 | width[i] = acuReadInt(fp); 61 | setWidth[i] = acuReadInt(fp); 62 | topExtent[i] = acuReadInt(fp); 63 | leftExtent[i] = acuReadInt(fp); 64 | acuReadInt(fp); // pointer, ignored 65 | } 66 | 67 | // read in the FreeType data 68 | //images = new unsigned char[numChars][64*64*4]; 69 | images = new unsigned char*[numChars]; 70 | for (i = 0; i < numChars; i++) { 71 | images[i] = new unsigned char[64*64*4]; 72 | int FreeTypeSize = height[i] * width[i]; 73 | //printf("FreeType size is %d\n", FreeTypeSize); 74 | unsigned char *temp = new unsigned char[FreeTypeSize]; 75 | fread(temp, FreeTypeSize, 1, fp); 76 | 77 | // convert the FreeType to an alpha channel 78 | int w = width[i]; 79 | int h = height[i]; 80 | for (int x = 0; x < w; x++) { 81 | for (int y = 0; y < h; y++) { 82 | int offset = (y*64 + x) * 4; 83 | images[i][offset + 0] = 255; 84 | images[i][offset + 1] = 255; 85 | images[i][offset + 2] = 255; 86 | images[i][offset + 3] = temp[(h-y-1)*w + x]; 87 | //printf((images[i][offset+3] > 128) ? "*" : "."); 88 | } 89 | //printf("\n"); 90 | } 91 | } 92 | 93 | // build textures for each of the characters 94 | texNames = new GLuint[numChars]; 95 | glPixelStorei(GL_UNPACK_ALIGNMENT, 1); 96 | //printf("numChars is %d\n", numChars); 97 | glGenTextures(numChars, texNames); 98 | //for (int m = 0; m < numChars; m++) { 99 | //printf("%d ", texNames[m]); 100 | //} 101 | 102 | for (i = 0; i < numChars; i++) { 103 | glBindTexture(GL_TEXTURE_2D, texNames[i]); 104 | glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 64, 64, 0, 105 | GL_RGBA, GL_UNSIGNED_BYTE, images[i]); 106 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP); 107 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP); 108 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 109 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 110 | glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); 111 | } 112 | valid = TRUE; 113 | } 114 | 115 | float acFreeTypeFont::getDescent() { 116 | return (float)(height['p'-33] - topExtent['p'-33]) / 64.0f; 117 | } 118 | 119 | float acFreeTypeFont::getHeight() { 120 | return (float)mboxY / 64.0f; 121 | } 122 | 123 | float acFreeTypeFont::charWidth(char c) { 124 | // width of the horizontal space char takes up 125 | if (c != ' ') { 126 | return (float)setWidth[c-33] / 64.0f; 127 | } else { 128 | //return charWidth('i')*1.2f; 129 | return charWidth('n'); // support monospace better 130 | } 131 | } 132 | 133 | float acFreeTypeFont::charHeight(char c) { 134 | return (float)height[c-33] / 64.0f; 135 | } 136 | 137 | float acFreeTypeFont::charFreeTypeWidth(char c) { 138 | // width of the FreeType itself 139 | return (float)width[c-33] / 64.0f; 140 | } 141 | 142 | float acFreeTypeFont::charFreeTypeHeight(char c) { 143 | // same as charHeight 144 | return (float)height[c-33] / 64.0f; 145 | } 146 | 147 | float acFreeTypeFont::charTop(char c) { 148 | return -charHeight(c) + (float)(topExtent[c-33]) / 64.0f; 149 | } 150 | 151 | float acFreeTypeFont::charTopExtent(char c) { 152 | return (float)topExtent[c-33] / 64.0f; 153 | } 154 | 155 | float acFreeTypeFont::charLeftExtent(char c) { 156 | return (float)leftExtent[c-33] / 64.0f; 157 | } 158 | 159 | boolean acFreeTypeFont::charExists(char c) { 160 | //return (c-33 < numChars); 161 | return ((c > 32) && (c-33 < numChars)); 162 | 163 | } 164 | 165 | unsigned char* acFreeTypeFont::getCharData(char c, float *x, float *y, float *w, float *h) { 166 | if (!charExists(c)) return NULL; 167 | *x = charLeftExtent(c); 168 | *y = charTop(c); 169 | *w = charFreeTypeWidth(c); 170 | *h = charHeight(c); 171 | /* 172 | params[0] = charLeftExtent(c); // x 173 | params[1] = charTop(c); // y 174 | params[2] = charFreeTypeWidth(c); // width 175 | params[3] = charHeight(c); // height 176 | //params[4] = bwidth; // maxu 177 | //params[5] = height; // maxv 178 | */ 179 | return images[c-33]; 180 | } 181 | 182 | void acFreeTypeFont::drawChar(char c, float x, float y) { 183 | // x,y is insertion point, lower-left, on baseline 184 | //if (c < 33) return; 185 | //if (c > numChars + 32) return; 186 | if (!charExists(c)) return; 187 | 188 | //glEnable(GL_TEXTURE_2D); 189 | 190 | float height = charHeight(c); 191 | //float width = charWidth(c); 192 | float bwidth = charFreeTypeWidth(c); 193 | float top = charTop(c); 194 | float lextent = charLeftExtent(c); 195 | 196 | #ifndef CANNOT_BIND_TEXTURES 197 | 198 | if (glIsTexture(texNames[c-33])) { 199 | acuNamedTexRectf(x+lextent, y+top, 200 | x+lextent+bwidth, y+height+top, 201 | texNames[c-33], bwidth, height); 202 | } else { 203 | sprintf(acuDebugStr, "Could not bind: %c %d\n", c, c); 204 | acuDebugString(ACU_DEBUG_MUMBLE); 205 | acuTexRectf(x+lextent, y+top, x+lextent+bwidth, y+height+top, 206 | images[c-33], GL_RGBA, 4, 64, 64, bwidth, height); 207 | } 208 | 209 | #else 210 | 211 | acuTexRectf(x+lextent, y+top, x+lextent+bwidth, y+height+top, 212 | images[c-33], GL_RGBA, 4, 64, 64, bwidth, height); 213 | #endif 214 | 215 | #if 0 216 | // to draw the baseline 217 | glBegin(GL_LINES); 218 | glVertex3f(x, y, 0); 219 | glVertex3f(x+width*0.95f, y, 0); 220 | glEnd(); 221 | #endif 222 | } 223 | 224 | 225 | -------------------------------------------------------------------------------- /acFreeTypeFont.h: -------------------------------------------------------------------------------- 1 | #ifndef _AC_BITMAP_FONT_H_ 2 | #define _AC_BITMAP_FONT_H_ 3 | 4 | #include "acu.h" 5 | #include "acFont.h" 6 | 7 | 8 | class acFreeTypeFont : public acFont { 9 | public: 10 | acFreeTypeFont(const char *filename); 11 | 12 | float getDescent(); 13 | float getHeight(); 14 | float charWidth(char c); 15 | float charHeight(char c); 16 | boolean charExists(char c); 17 | void drawChar(char c, float x, float y); 18 | 19 | unsigned char* getCharData(char c, float *x, float *y, 20 | float *w, float *h); 21 | protected: 22 | int numChars; 23 | int numBits; 24 | int mboxX; 25 | int mboxY; 26 | int baseHt; 27 | 28 | // per character 29 | int *value; 30 | int *height; 31 | int *width; 32 | int *setWidth; 33 | int *topExtent; 34 | int *leftExtent; 35 | 36 | unsigned char **images; 37 | GLuint *texNames; 38 | 39 | //float charFreeTypeWidth(char c); 40 | //float charFreeTypeHeight(char c); 41 | //float charTop(char c); 42 | //float charTopExtent(char c); 43 | //float charLeftExtent(char c); 44 | }; 45 | 46 | #endif 47 | 48 | -------------------------------------------------------------------------------- /acGeo.cpp: -------------------------------------------------------------------------------- 1 | #include "acGeo.h" 2 | 3 | /* acGeo ---------------------------------------------*/ 4 | 5 | void acGeo::draw() { /* no default visuals */} 6 | 7 | void acGeo::idle() { /* no default behavior */} 8 | 9 | void acGeo::message(const char *string) { /* no default */ } 10 | 11 | -------------------------------------------------------------------------------- /acGeo.h: -------------------------------------------------------------------------------- 1 | #ifndef _AC_GEO_ 2 | #define _AC_GEO_ 3 | 4 | #include "acu.h" 5 | 6 | class acGeo { 7 | public: 8 | virtual void idle(); 9 | virtual void draw(); 10 | virtual void message(const char *string); 11 | }; 12 | 13 | /* This is some glue that connects the app to the window system */ 14 | #ifdef ACU_WIN32 15 | /* cygwin doesn't know what this file is */ 16 | #ifndef __CYGWIN__ 17 | #include "ansi_prefix.win32.h" 18 | #endif 19 | #define ExportGeo extern "C" __declspec(dllexport) acGeo 20 | #define ExportType extern "C" __declspec(dllexport) char 21 | #else 22 | #define ExportGeo extern "C" acGeo 23 | #define ExportType extern "C" char 24 | #endif 25 | // this is the decaration, but the function in your geo 26 | ExportGeo *makeGeo(void); 27 | 28 | #endif 29 | -------------------------------------------------------------------------------- /acMatrix4f.h: -------------------------------------------------------------------------------- 1 | #ifndef _ACMATRIX4F_ 2 | #define _ACMATRIX4F_ 3 | 4 | #include "acu.h" 5 | #include "acVec3f.h" 6 | #include 7 | 8 | 9 | class acMatrix4f { 10 | public: 11 | float m[4][4]; 12 | 13 | acMatrix4f(); 14 | acMatrix4f(float source[4][4]); 15 | void set(float *source); 16 | void set(acMatrix4f *source); 17 | void set(float source[4][4]); 18 | 19 | void get(float *target); 20 | 21 | void setZero(); 22 | void setIdentity(); 23 | 24 | void copy(float to[4][4]); 25 | 26 | void transform3(acVec3f *v1, acVec3f *v2); 27 | void transform3(acVec3f *vector); 28 | void transform3(float *v1, float *v2); 29 | void transform4(float *v1, float *v2); 30 | 31 | static void multiply(float mat1[4][4], float mat2[4][4], 32 | float outmat[4][4]); 33 | 34 | void multiply(float mat[4][4], float outmat[4][4]); 35 | void multiplyBy(acMatrix4f *matrix); 36 | void multiplyBy(float mat[4][4]); 37 | 38 | void rotgen(float x, float y, float z, float angle); 39 | void rotate(char axis, float angle); 40 | void scale(float sx, float sy, float sz); 41 | void translate(float tx, float ty, float tz); 42 | 43 | boolean eigenCheck(float *value); 44 | float invert(acMatrix4f *target); 45 | 46 | void transformSpace(float x, float y, acVec3f *trans); 47 | void getEyePoint(acVec3f *eye); 48 | void getDirection(float x, float y, acVec3f *dw); 49 | void print(); 50 | }; 51 | 52 | #endif 53 | -------------------------------------------------------------------------------- /acSerial.cpp: -------------------------------------------------------------------------------- 1 | #include "acSerial.h" 2 | 3 | 4 | acSerial::acSerial(char *serialPort, int rate) { 5 | //fprintf(stderr, "CONNECTING VIA PORT %s \n", serialPort); 6 | comm = CreateFile(serialPort, 7 | GENERIC_READ | GENERIC_WRITE, 8 | 0, // comm devices must be opened w/exclusive-access 9 | NULL, // no security attrs 10 | OPEN_EXISTING, // comm devices must use OPEN_EXISTING 11 | 0, // not overlapped I/O 12 | NULL); // hTemplate must be NULL for comm devices 13 | 14 | if (comm == INVALID_HANDLE_VALUE) { 15 | DWORD dwError = GetLastError(); 16 | fprintf(stderr, "acSerial: Error code %ld while opening %s.\n", 17 | dwError, serialPort); 18 | if (dwError == ERROR_FILE_NOT_FOUND) { 19 | fprintf(stderr, "ERROR_FILE_NOT_FOUND\n"); 20 | } else if (dwError == ERROR_NOT_SUPPORTED) { 21 | fprintf(stderr, "ERROR_NOT_SUPPORTED\n"); 22 | } 23 | return; 24 | } 25 | 26 | // Omit the call to SetupComm to use the default queue sizes. 27 | // Get the current configuration. 28 | DCB dcb; 29 | BOOL fSuccess = GetCommState(comm, &dcb); 30 | if (!fSuccess) { 31 | /* Handle the error. */ 32 | printf("acSerial: Error getting the comm state"); 33 | comm = INVALID_HANDLE_VALUE; 34 | return; 35 | } 36 | 37 | // Fill in the DCB: baud=19200, 8 data bits, no parity, 1 stop bit. 38 | dcb.BaudRate = rate; 39 | dcb.ByteSize = 8; 40 | dcb.Parity = NOPARITY; 41 | dcb.StopBits = ONESTOPBIT; 42 | fSuccess = SetCommState(comm, &dcb); 43 | 44 | if (!fSuccess) { 45 | fprintf(stderr, "acSerial: Error setting the comm state"); 46 | comm = INVALID_HANDLE_VALUE; 47 | return; 48 | } 49 | 50 | COMMTIMEOUTS cto; 51 | cto.ReadIntervalTimeout = 10; 52 | cto.ReadTotalTimeoutMultiplier = 1; 53 | cto.ReadTotalTimeoutConstant = 200; 54 | cto.WriteTotalTimeoutMultiplier = 10; 55 | cto.WriteTotalTimeoutConstant = 100; 56 | if (!SetCommTimeouts(comm, &cto)) { 57 | fprintf(stderr, "acSerial: Unable to set proper timeouts"); 58 | } 59 | } 60 | 61 | 62 | acSerial::~acSerial() { 63 | if (comm != INVALID_HANDLE_VALUE) { 64 | CloseHandle(comm); 65 | } 66 | } 67 | 68 | 69 | int acSerial::write(unsigned char *buffer, int count) { 70 | DWORD bytes = count; 71 | bool result = WriteFile(comm, buffer, bytes, &bytes, NULL); 72 | if (result == 0) { 73 | // FLAG ERROR HERE... what should we do?? 74 | COMSTAT comstat; 75 | DWORD errorflags; 76 | ClearCommError(comm , &errorflags, &comstat); 77 | fprintf(stderr, "max loves win32, and what the fsck does " 78 | "one do with comm errors?\n"); 79 | } 80 | return bytes; 81 | } 82 | 83 | 84 | int acSerial::read(unsigned char *buffer, int count) { 85 | //bool stat; 86 | 87 | if (comm == INVALID_HANDLE_VALUE) return -1; 88 | 89 | COMSTAT comstat; 90 | LPDWORD errorflags = 0; 91 | ClearCommError(comm, errorflags, &comstat); 92 | // quick hack to allow for hacking... 93 | // don't know if this is really necessary... 94 | 95 | while (comstat.cbInQue < count) { 96 | //fprintf(stderr, "acSerial: only %d bytes available (not %d)\n", 97 | // comstat.cbInQue, count); 98 | Sleep(2); // used to be 1 99 | ClearCommError(comm, errorflags, &comstat); 100 | } 101 | DWORD length; 102 | if (ReadFile(comm, buffer, count, &length, NULL) == 0) { 103 | fprintf(stderr, "acSerial: Readfile failed\n"); 104 | return -1; 105 | } 106 | return length; 107 | 108 | /* 109 | int retryCount = 10; 110 | while ((comstat.cbInQue < bytestoread) && retryCount) { 111 | fprintf(stderr, "acSerial:: only %d bytes available (not %d)\n", 112 | comstat.cbInQue, count); 113 | Sleep(1); 114 | ClearCommError(comm, errorflags, &comstat); 115 | retryCount--; 116 | } 117 | if (comstat.cbInQue < bytestoread) { 118 | byte garbage[1024]; 119 | inlength = MIN(comstat.cbInQue, 1024); 120 | if (ReadFile(tagCOM, garbage, inlength, &inlength, NULL) == 0) { 121 | fprintf(stderr, "readResponse(): Readfile failed: "); 122 | acSocket::printSystemError("miniSerial::readResponse()"); 123 | } 124 | return -1; 125 | } else { 126 | inlength = bytestoread; 127 | if (ReadFile(tagCOM, databuffer, inlength, &inlength, NULL) == 0) { 128 | fprintf(stderr, "readResponse(): Readfile failed: "); 129 | acSocket::printSystemError("miniSerial::readResponse()"); 130 | return -1; 131 | } 132 | return inlength; 133 | } 134 | */ 135 | } 136 | -------------------------------------------------------------------------------- /acSerial.h: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | 5 | // added by fry, 26 september 2001 6 | 7 | // this is a simplified version of the code max wrote for 8 | // the moma project, with api fixed to look something like 9 | // a regular streams-type object. 10 | // example code at the end of this document. 11 | 12 | 13 | class acSerial { 14 | public: 15 | HANDLE comm; 16 | 17 | acSerial(char *portname, int rate); 18 | ~acSerial(); 19 | 20 | int read(unsigned char *buffer, int count); 21 | int write(unsigned char *buffer, int count); 22 | }; 23 | 24 | 25 | /* 26 | // sample implementation example 27 | // not guaranteed to work, but there haven't been any 28 | // confirmed bugs found here yet. just bitchin and moanin. 29 | 30 | class HappySerial : public acThread { 31 | public: 32 | unsigned char buffer[128]; 33 | acSerial *happy; 34 | boolean ready; 35 | 36 | HappySerial() { 37 | ready = false; 38 | happy = new acSerial("COM2", 9600); 39 | } 40 | 41 | ~HappySerial() { 42 | delete happy; 43 | } 44 | 45 | void run() { 46 | while (true) { 47 | while (ready) { } // wait until the app reads 48 | //printf("reading...\n"); 49 | int count = happy->read(buffer, 4); 50 | //printf("got data..\n"); 51 | ready = true; 52 | acThread::sleep(50); 53 | } 54 | } 55 | }; 56 | 57 | 58 | 59 | inside draw() ... 60 | 61 | if (happy.ready) { 62 | tilt += 63 | ((TWO_PI * ((float)happy.buffer[0] / 255.0)) - tilt) / 20.0; 64 | 65 | rotationSpeed += 66 | ((4.0 * ((float)happy.buffer[1] / 255.0)) - rotationSpeed) / 10.0; 67 | 68 | thickSteps = (STEPS * happy.buffer[2]) / 255; 69 | 70 | //printf("got new data %d %d %d %d\n", 71 | // happy.buffer[0], happy.buffer[1], 72 | // happy.buffer[2], happy.buffer[3]); 73 | happy.ready = false; 74 | } else { 75 | //printf("no new data\n"); 76 | } 77 | 78 | */ 79 | -------------------------------------------------------------------------------- /acThread.cpp: -------------------------------------------------------------------------------- 1 | #include "acThread.h" 2 | 3 | 4 | long WINAPI acThreadProcess(long parameter); 5 | long WINAPI acThreadProcess(long parameter) { 6 | //printf("attempting to start %x\n", parameter); 7 | acThread *theThread = (acThread*)parameter; 8 | theThread->run(); 9 | return 1L; 10 | } 11 | 12 | 13 | acThread::acThread() { 14 | } 15 | 16 | 17 | acThread::~acThread() { 18 | stop(); 19 | } 20 | 21 | 22 | void acThread::start() { 23 | threadID = 0; 24 | threadHandle = CreateThread(NULL, // no specific security settings 25 | 0, // use a regular stack size 26 | (LPTHREAD_START_ROUTINE) acThreadProcess, 27 | this, // pass self as arg to thread function 28 | //NULL, // null arg to thread function 29 | (unsigned long) 0, // CREATE_SUSPENDED is false 30 | &threadID); // unique integer ID for thread 31 | if (!threadHandle) { 32 | //acuDebug(ACU_DEBUG_EMERGENCY, "could not create thread"); 33 | fprintf(stderr, "could not create thread\n"); 34 | // this will terminate the application 35 | } 36 | SetThreadPriority(threadHandle, THREAD_PRIORITY_NORMAL); 37 | } 38 | 39 | 40 | void acThread::run() { } 41 | 42 | 43 | void acThread::stop() { } 44 | 45 | 46 | void acThread::sleep(int millis) { 47 | Sleep(millis); 48 | } 49 | -------------------------------------------------------------------------------- /acThread.h: -------------------------------------------------------------------------------- 1 | #ifndef AC_THREAD_H 2 | #define AC_THREAD_H 3 | 4 | // this includes acu constants 5 | //#include "acApp.h" 6 | 7 | #include 8 | //#ifdef ACU_WIN32 9 | // this includes HANDLE, etc. for windows 10 | #include 11 | //#endif 12 | 13 | 14 | /* 15 | notes about using acThread: 16 | 17 | you cannot start a thread until idle(), 18 | it cannot be started inside your acApp's class constructor 19 | do something like this: 20 | void idle() { 21 | if (!started) { 22 | myThread->start(); 23 | started = TRUE; 24 | } 25 | } 26 | 27 | stop() currently does nothing 28 | the destructor ~acThread() just calls stop (which does nothing) 29 | */ 30 | 31 | class acThread { 32 | public: 33 | acThread(); 34 | ~acThread(); 35 | 36 | void start(); 37 | void stop(); 38 | 39 | virtual void run(); 40 | 41 | static void sleep(int millis); // hot mama java style 42 | 43 | private: 44 | unsigned long threadID; 45 | HANDLE threadHandle; 46 | }; 47 | 48 | 49 | #endif 50 | -------------------------------------------------------------------------------- /acVec3f.cpp: -------------------------------------------------------------------------------- 1 | #include "acVec3f.h" 2 | 3 | 4 | acVec3f::acVec3f(float newX, float newY, float newZ) { 5 | x = newX; 6 | y = newY; 7 | z = newZ; 8 | } 9 | 10 | acVec3f::acVec3f(void) { 11 | x = y = z = 0.0; 12 | } 13 | 14 | void acVec3f::set(float newX, float newY, float newZ) { 15 | x = newX; 16 | y = newY; 17 | z = newZ; 18 | } 19 | 20 | void acVec3f::set(acVec3f B) { 21 | x = B.x; 22 | y = B.y; 23 | z = B.z; 24 | } 25 | 26 | void acVec3f::get(float v[]) { 27 | v[0] = x; 28 | v[1] = y; 29 | v[2] = z; 30 | } 31 | 32 | void acVec3f::operator=(acVec3f B) { 33 | set( B.x, B.y, B.z ); 34 | return; 35 | } 36 | 37 | int acVec3f::operator==(acVec3f B) { 38 | return (x==B.x && y==B.y && z==B.z); 39 | } 40 | 41 | void acVec3f::operator+=(acVec3f B) { 42 | set( x+B.x, y+B.y, z+B.z ); 43 | } 44 | 45 | void acVec3f::operator-=(acVec3f B) { 46 | set( x-B.x, y-B.y, z-B.z ); 47 | } 48 | 49 | void acVec3f::operator*=(float F) { 50 | set( x*F, y*F, z*F ); 51 | } 52 | 53 | void acVec3f::operator/=(float F) { 54 | set( x/F, y/F, z/F ); 55 | } 56 | 57 | float acVec3f::dot(acVec3f &B) { 58 | float D; 59 | D = x*B.x + y*B.y + z*B.z; 60 | return D; 61 | } 62 | 63 | acVec3f acVec3f::cross(acVec3f &B) { 64 | acVec3f C; 65 | C.set(y*B.z - z*B.y, z*B.x - x*B.z, x*B.y - y*B.x); 66 | return C; 67 | } 68 | 69 | void acVec3f::componentMult(acVec3f &B) { 70 | set( x*B.x, y*B.y, z*B.z ); 71 | } 72 | 73 | acVec3f acVec3f::normalize(acVec3f &A) { 74 | float N; 75 | acVec3f C; 76 | N = A.x*A.x + A.y*A.y + A.z*A.z; 77 | N = sqrt(N); 78 | C.set(A.x/N, A.y/N, A.z/N); 79 | return C; 80 | } 81 | 82 | void acVec3f::normalize() { 83 | float N; 84 | N = x*x + y*y + z*z; 85 | N = sqrt(N); 86 | if (N != 0) { 87 | x /= N; y /= N; z /= N; 88 | } 89 | } 90 | 91 | float acVec3f::length() { 92 | return sqrt(x*x + y*y + z*z); 93 | } 94 | 95 | void acVec3f::scale(float amount) { 96 | x *= amount; 97 | y *= amount; 98 | z *= amount; 99 | } 100 | 101 | void acVec3f::add(acVec3f *what) { 102 | x += what->x; 103 | y += what->y; 104 | z += what->z; 105 | } 106 | 107 | float acVec3f::lengthSquared() { 108 | return x*x + y*y + z*z; 109 | } 110 | 111 | 112 | /* operators */ 113 | 114 | acVec3f operator+(acVec3f A, acVec3f B) { 115 | acVec3f C; 116 | C.set(A.x+B.x, A.y+B.y, A.z+B.z); 117 | return C; 118 | } 119 | 120 | acVec3f operator-(acVec3f A, acVec3f B) { 121 | acVec3f C; 122 | C.set(A.x-B.x, A.y-B.y, A.z-B.z); 123 | return C; 124 | } 125 | 126 | acVec3f operator*(acVec3f A, float M) { 127 | acVec3f C; 128 | C.set(A.x*M, A.y*M, A.z*M); 129 | return C; 130 | } 131 | 132 | acVec3f operator/(acVec3f A, float M) { 133 | acVec3f C; 134 | C.set(A.x/M, A.y/M, A.z/M); 135 | return C; 136 | } 137 | -------------------------------------------------------------------------------- /acVec3f.h: -------------------------------------------------------------------------------- 1 | #ifndef _AC_VEC3F_ 2 | #define _AC_VEC3F_ 3 | 4 | #include 5 | 6 | 7 | class acVec3f 8 | { 9 | public: 10 | float x,y,z; 11 | 12 | acVec3f(float newX, float newY, float newZ); 13 | acVec3f(void); 14 | 15 | void set(float newX, float newY, float newZ); 16 | void set(acVec3f B); 17 | void get(float v[]); 18 | 19 | int operator==(acVec3f B); 20 | void operator=(acVec3f B); 21 | void operator+=(acVec3f B); 22 | void operator-=(acVec3f B); 23 | void operator*=(float F); 24 | void operator/=(float F); 25 | 26 | static acVec3f normalize(acVec3f &A); 27 | void normalize(); 28 | float length(); 29 | float lengthSquared(); 30 | float dot(acVec3f &B); 31 | acVec3f cross(acVec3f &B); 32 | void componentMult(acVec3f &B); 33 | 34 | void scale(float amount); 35 | void add(acVec3f *what); 36 | }; 37 | 38 | 39 | acVec3f operator+(acVec3f A, acVec3f B); // add 40 | acVec3f operator-(acVec3f A, acVec3f B); // subtract 41 | acVec3f operator*(acVec3f A, float Scalar); // multiply by scalar 42 | acVec3f operator/(acVec3f A, float Scalar); // divide by scalar 43 | 44 | #endif 45 | -------------------------------------------------------------------------------- /acVec4f.cpp: -------------------------------------------------------------------------------- 1 | #include "acVec4f.h" 2 | 3 | 4 | acVec4f::acVec4f(float newX, float newY, float newZ, float newW) { 5 | x = newX; 6 | y = newY; 7 | z = newZ; 8 | w = newW; 9 | } 10 | 11 | acVec4f::acVec4f(void) { 12 | x = y = z = w = 0.0; 13 | } 14 | 15 | void acVec4f::set(float newX, float newY, float newZ, float newW) { 16 | x = newX; 17 | y = newY; 18 | z = newZ; 19 | w = newW; 20 | } 21 | 22 | void acVec4f::set(acVec4f B) { 23 | x = B.x; 24 | y = B.y; 25 | z = B.z; 26 | w = B.w; 27 | } 28 | 29 | void acVec4f::get(float v[]) { 30 | v[0] = x; 31 | v[1] = y; 32 | v[2] = z; 33 | v[2] = w; 34 | } 35 | 36 | void acVec4f::operator=(acVec4f B) { 37 | x = B.x; 38 | y = B.y; 39 | z = B.z; 40 | w = B.w; 41 | return; 42 | } 43 | 44 | int acVec4f::operator==(acVec4f B) { 45 | return (x==B.x && y==B.y && z==B.z && w==B.w); 46 | } 47 | 48 | void acVec4f::operator+=(acVec4f B) { 49 | set( x+B.x, y+B.y, z+B.z, w+B.w ); 50 | } 51 | 52 | void acVec4f::operator-=(acVec4f B) { 53 | set( x-B.x, y-B.y, z-B.z, w-B.w ); 54 | } 55 | 56 | void acVec4f::operator*=(float F) { 57 | set( x*F, y*F, z*F, w*F ); 58 | } 59 | 60 | void acVec4f::operator/=(float F) { 61 | set( x/F, y/F, z/F, w/F ); 62 | } 63 | 64 | float acVec4f::dot(acVec4f &B) { 65 | float D; 66 | D = x*B.x + y*B.y + z*B.z + w*B.w; 67 | return D; 68 | } 69 | 70 | /*acVec4f acVec4f::cross(acVec4f &B) { 71 | acVec4f C; 72 | C.set(y*B.z - z*B.y, z*B.x - x*B.z, x*B.y - y*B.x); 73 | return C; 74 | }*/ 75 | 76 | void acVec4f::componentMult(acVec4f &B) { 77 | set( x*B.x, y*B.y, z*B.z, w*B.w ); 78 | } 79 | 80 | acVec4f acVec4f::normalize(acVec4f &A) { 81 | float N; 82 | acVec4f C; 83 | N = A.x*A.x + A.y*A.y + A.z*A.z + A.w*A.w; 84 | N = sqrt(N); 85 | C.set(A.x/N, A.y/N, A.z/N, A.w/N); 86 | return C; 87 | } 88 | 89 | void acVec4f::normalize() { 90 | float N; 91 | N = x*x + y*y + z*z + w*w; 92 | N = sqrt(N); 93 | if (N != 0) { 94 | x /= N; y /= N; z /= N; w /= N; 95 | } 96 | } 97 | 98 | float acVec4f::length() { 99 | return sqrt(x*x + y*y + z*z + w*w); 100 | } 101 | 102 | void acVec4f::scale(float amount) { 103 | x *= amount; 104 | y *= amount; 105 | z *= amount; 106 | w *= amount; 107 | } 108 | 109 | void acVec4f::add(acVec4f *what) { 110 | x += what->x; 111 | y += what->y; 112 | z += what->z; 113 | w += what->w; 114 | } 115 | 116 | float acVec4f::lengthSquared() { 117 | return x*x + y*y + z*z + w*w; 118 | } 119 | 120 | 121 | /* operators */ 122 | 123 | acVec4f operator+(acVec4f A, acVec4f B) { 124 | acVec4f C; 125 | C.set(A.x+B.x, A.y+B.y, A.z+B.z, A.w+B.w); 126 | return C; 127 | } 128 | 129 | acVec4f operator-(acVec4f A, acVec4f B) { 130 | acVec4f C; 131 | C.set(A.x-B.x, A.y-B.y, A.z-B.z, A.w-B.w); 132 | return C; 133 | } 134 | 135 | acVec4f operator*(acVec4f A, float M) { 136 | acVec4f C; 137 | C.set(A.x*M, A.y*M, A.z*M, A.w*M); 138 | return C; 139 | } 140 | 141 | acVec4f operator/(acVec4f A, float M) { 142 | acVec4f C; 143 | C.set(A.x/M, A.y/M, A.z/M, A.w/M); 144 | return C; 145 | } 146 | -------------------------------------------------------------------------------- /acVec4f.h: -------------------------------------------------------------------------------- 1 | #ifndef _AC_VEC4F_ 2 | #define _AC_VEC4F_ 3 | 4 | #include 5 | 6 | 7 | class acVec4f 8 | { 9 | public: 10 | float x,y,z,w; 11 | 12 | acVec4f(float newX, float newY, float newZ, float newW); 13 | acVec4f(void); 14 | 15 | void set(float newX, float newY, float newZ, float newW); 16 | void set(acVec4f B); 17 | void get(float v[]); 18 | 19 | int operator==(acVec4f B); 20 | void operator=(acVec4f B); 21 | void operator+=(acVec4f B); 22 | void operator-=(acVec4f B); 23 | void operator*=(float F); 24 | void operator/=(float F); 25 | 26 | static acVec4f normalize(acVec4f &A); 27 | void normalize(); 28 | float length(); 29 | float lengthSquared(); 30 | float dot(acVec4f &B); 31 | /*acVec4f cross(acVec4f &B);*/ 32 | void componentMult(acVec4f &B); 33 | 34 | void scale(float amount); 35 | void add(acVec4f *what); 36 | }; 37 | 38 | 39 | acVec4f operator+(acVec4f A, acVec4f B); // add 40 | acVec4f operator-(acVec4f A, acVec4f B); // subtract 41 | acVec4f operator*(acVec4f A, float Scalar); // multiply by scalar 42 | acVec4f operator/(acVec4f A, float Scalar); // divide by scalar 43 | 44 | #endif 45 | -------------------------------------------------------------------------------- /acVectorFont.cpp: -------------------------------------------------------------------------------- 1 | #include "acVectorFont.h" 2 | 3 | 4 | acVectorFont::acVectorFont(const char* filename) { 5 | valid = FALSE; 6 | int i; 7 | 8 | for (i = 0; i < 256; i++) { 9 | numPoints[i] = 0; 10 | width[i] = 0; 11 | height[i] = 0; 12 | } 13 | 14 | FILE *fp = fopen(filename, "r"); 15 | if (fp == NULL) { 16 | sprintf(acuDebugStr, "Could not open font file %s", filename); 17 | acuDebugString(ACU_DEBUG_PROBLEM); 18 | return; 19 | } 20 | 21 | // read the font 22 | char str[64]; 23 | float nX, nY; 24 | unsigned char currentLetter = 0; 25 | int currentPoint = 0; 26 | float bigWidth = 0; 27 | float bigHeight = 0; 28 | leading = 0; 29 | 30 | // fgets reads until newline or eof 31 | while (fgets(str, 64, fp)) { 32 | switch (str[0]) { 33 | case 'C': // what character 34 | if (currentLetter != 0) { 35 | numPoints[currentLetter] = currentPoint; 36 | height[currentLetter] = bigHeight; 37 | if (width[currentLetter] == 0) { 38 | // support the old-school format, not for long 39 | width[currentLetter] = bigWidth * 1.5; 40 | } 41 | currentPoint = 0; 42 | } 43 | currentLetter = str[2]; 44 | width[currentLetter] = 0; 45 | height[currentLetter] = 0; 46 | bigWidth = 0; 47 | bigHeight = 0; 48 | currentPoint = 0; 49 | break; 50 | 51 | case 'L': // lineto 52 | sscanf(str, "L %f %f\n", &nX, &nY); 53 | kind[currentLetter][currentPoint] = LINETO; 54 | x[currentLetter][currentPoint] = nX; 55 | y[currentLetter][currentPoint] = nY; 56 | if (nX > bigWidth) bigWidth = nX; 57 | if (nY > bigHeight) bigHeight = nY; 58 | currentPoint++; 59 | break; 60 | 61 | case 'M': // moveto 62 | sscanf(str, "M %f %f\n", &nX, &nY); 63 | kind[currentLetter][currentPoint] = MOVETO; 64 | x[currentLetter][currentPoint] = nX; 65 | y[currentLetter][currentPoint] = nY; 66 | if (nX > bigWidth) bigWidth = nX; 67 | if (nY > bigHeight) bigHeight = nY; 68 | currentPoint++; 69 | break; 70 | 71 | case 'W': // width 72 | sscanf(str, "W %f\n", &width[currentLetter]); 73 | break; 74 | 75 | case 'D': // leading 76 | sscanf(str, "D %f\n", &leading); 77 | break; 78 | 79 | case 0: // blank line 80 | case '#': // comment 81 | break; 82 | 83 | default: 84 | // got something not understood 85 | sprintf(acuDebugStr, "strange line in %s: \"%s\"", filename, str); 86 | acuDebugString(ACU_DEBUG_PROBLEM); 87 | break; 88 | } 89 | } 90 | // cleanup for the last char read from the file 91 | if (currentLetter != 0) { 92 | numPoints[currentLetter] = currentPoint; 93 | height[currentLetter] = bigHeight; 94 | if (width[currentLetter] == 0) { 95 | // support the old-school format, not for long 96 | width[currentLetter] = bigWidth * 1.5; 97 | } 98 | } 99 | fclose(fp); 100 | 101 | descent = 0; 102 | maxHeight = 0; 103 | for (i = 0; i < 256; i++) { 104 | for (int p = 0; p < numPoints[i]; p++) { 105 | if (y[i][p] < descent) descent = y[i][p]; 106 | if (y[i][p] > maxHeight) maxHeight = y[i][p]; 107 | } 108 | } 109 | if (leading == 0) { 110 | // default leading, if not defined in font 111 | leading = getHeight() * 1.2; 112 | } 113 | valid = TRUE; 114 | } 115 | 116 | int acVectorFont::getFormat() { 117 | return ACU_VECTOR_FONT; 118 | } 119 | 120 | void acVectorFont::drawChar(unsigned char c, float tx, float ty) { 121 | glBegin(GL_LINE_STRIP); 122 | for (int i = 0; i < numPoints[c]; i++) { 123 | if (kind[c][i] == MOVETO) { 124 | glEnd(); 125 | glBegin(GL_LINE_STRIP); 126 | } 127 | //acuDebug(ACU_DEBUG_PROBLEM, "vecfont not finished yet!\n"); 128 | glVertex2f(tx + x[c][i], ty + y[c][i]); 129 | } 130 | glEnd(); 131 | } 132 | 133 | float acVectorFont::getDescent() { 134 | return descent; 135 | } 136 | 137 | float acVectorFont::getHeight() { 138 | return maxHeight + descent; 139 | } 140 | 141 | float acVectorFont::charWidth(unsigned char c) { 142 | if (c != ' ') { 143 | return width[c]; 144 | } else { 145 | return charWidth('n'); 146 | } 147 | } 148 | 149 | float acVectorFont::charHeight(unsigned char c) { 150 | return height[c]; 151 | } 152 | 153 | boolean acVectorFont::charExists(unsigned char c) { 154 | return (numPoints[c] != 0); 155 | } 156 | 157 | 158 | float acVectorFont::getDefaultLeading() { 159 | return leading; 160 | } 161 | -------------------------------------------------------------------------------- /acVectorFont.h: -------------------------------------------------------------------------------- 1 | #ifndef _AC_VECTOR_FONT_H_ 2 | #define _AC_VECTOR_FONT_H_ 3 | 4 | #include "acu.h" 5 | #include "acFont.h" 6 | 7 | 8 | // this may cause name conflicts down the road 9 | #define MOVETO 1 10 | #define LINETO 2 11 | 12 | 13 | class acVectorFont : public acFont { 14 | public: 15 | acVectorFont(const char* filename); 16 | 17 | float getDescent(); 18 | float getHeight(); 19 | float charWidth(unsigned char c); 20 | float charHeight(unsigned char c); 21 | boolean charExists(unsigned char c); 22 | //float kernWidth(char a, char b); 23 | void drawChar(unsigned char c, float x, float y); 24 | float getDefaultLeading(); 25 | int getFormat(); 26 | 27 | protected: 28 | float x[256][50]; 29 | float y[256][50]; 30 | int kind[256][50]; 31 | int numPoints[256]; 32 | float width[256]; 33 | float height[256]; 34 | 35 | float leading; 36 | float descent; 37 | float maxHeight; 38 | }; 39 | 40 | #endif 41 | 42 | 43 | 44 | 45 | 46 | -------------------------------------------------------------------------------- /geometry.c: -------------------------------------------------------------------------------- 1 | #include "acu.h" 2 | 3 | 4 | GLUtriangulatorObj *acuTesselator; 5 | 6 | 7 | /** 8 | * Make sure that texWidth and texHeight are a power 9 | * of two. If not, things won't work. This function does 10 | * no error checking so as not to waste any time. 11 | * 12 | * components is 3 for RGB and 4 for RGBA 13 | * format is GL_RGB or GL_RGBA or whatever 14 | */ 15 | void acuTexRectf(GLfloat x1, GLfloat y1, GLfloat x2, GLfloat y2, 16 | unsigned char *texImage, GLenum format, GLint components, 17 | GLsizei texWidth, GLsizei texHeight, 18 | GLfloat maxU, GLfloat maxV) { 19 | glEnable(GL_TEXTURE_2D); 20 | 21 | glTexImage2D(GL_TEXTURE_2D, 0, components, texWidth, texHeight, 22 | 0, format, GL_UNSIGNED_BYTE, texImage); 23 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP); 24 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP); 25 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); 26 | glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); 27 | glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); 28 | 29 | glNormal3f(0, 0, 1); 30 | 31 | glBegin(GL_QUADS); 32 | 33 | glTexCoord2f(0.0, 0.0); 34 | glVertex3f(x1, y1, 0.0); 35 | 36 | glTexCoord2f(0.0, maxV); 37 | glVertex3f(x1, y2, 0.0); 38 | 39 | glTexCoord2f(maxU, maxV); 40 | glVertex3f(x2, y2, 0.0); 41 | 42 | glTexCoord2f(maxU, 0.0); 43 | glVertex3f(x2, y1, 0.0); 44 | 45 | glEnd(); 46 | 47 | glDisable(GL_TEXTURE_2D); 48 | } 49 | 50 | 51 | /** 52 | * Same as above, but works with a texture that has 53 | * been bound to a name, using glBindTexture. See the 54 | * GL docs on glBindTexture if that don't make sense. 55 | */ 56 | void acuNamedTexRectf(GLfloat x1, GLfloat y1, GLfloat x2, GLfloat y2, 57 | GLint name, GLfloat maxU, GLfloat maxV) { 58 | glEnable(GL_TEXTURE_2D); 59 | 60 | glBindTexture(GL_TEXTURE_2D, name); 61 | 62 | glNormal3f(0, 0, 1); 63 | 64 | glBegin(GL_QUADS); 65 | 66 | glTexCoord2f(0.0, 0.0); 67 | glVertex3f(x1, y1, 0.0); 68 | 69 | glTexCoord2f(0.0, maxV); 70 | glVertex3f(x1, y2, 0.0); 71 | 72 | glTexCoord2f(maxU, maxV); 73 | glVertex3f(x2, y2, 0.0); 74 | 75 | glTexCoord2f(maxU, 0.0); 76 | glVertex3f(x2, y1, 0.0); 77 | 78 | glEnd(); 79 | 80 | glDisable(GL_TEXTURE_2D); 81 | } 82 | 83 | 84 | /** 85 | * Draw a tesselated polygon, concave or convex. 86 | * The array passed in takes the format: 87 | * { x1, y1, z1, x2, y2, z2, ... , xN-1, yN-1, zN-1 } 88 | */ 89 | void acuPolygon(GLint count, GLfloat *vertices) { 90 | GLdouble *p, *pts; 91 | int i; 92 | 93 | if (acuTesselator == NULL) { 94 | acuPolygonOpen(); 95 | // if it fails, then the program dies (ha ha ha, sorry) 96 | } 97 | 98 | gluBeginPolygon(acuTesselator); 99 | 100 | //GLdouble *pts = new GLdouble[count*3]; 101 | pts = (GLdouble*) malloc(sizeof(GLdouble) * count*3); 102 | for (i = 0; i < count*3; i++) { 103 | pts[i] = (double)vertices[i]; 104 | } 105 | 106 | for (i = 0; i < count; i++) { 107 | //GLdouble *p = &pts[i*3]; 108 | p = &pts[i*3]; 109 | gluTessVertex(acuTesselator, p, p); 110 | } 111 | gluEndPolygon(acuTesselator); 112 | //delete pts; 113 | free(pts); 114 | } 115 | 116 | 117 | static void polygonBegin(GLenum type) { 118 | glBegin(type); 119 | } 120 | 121 | static void polygonVertex(void* data) { 122 | GLdouble* pts = (GLdouble*) data; 123 | glVertex3dv(pts); 124 | } 125 | 126 | static void polygonEdgeFlag(GLboolean flag) { 127 | glEdgeFlag(flag); 128 | } 129 | 130 | static void polygonEnd(void) { 131 | glEnd(); 132 | } 133 | 134 | static void polygonError(GLenum code) { 135 | const GLubyte* error = gluErrorString(code); 136 | // should pass error as a char* using sprintf, but too lazy 137 | acuDebug(ACU_DEBUG_PROBLEM, "Error while tesselating."); 138 | } 139 | 140 | /** 141 | * Called only once, creates the tesselator object that 142 | * will be used for triangulating all them triangles. 143 | */ 144 | void acuPolygonOpen() { 145 | //GLUtriangulatorObj *tesselator; 146 | if (acuTesselator != NULL) { 147 | acuDebug(ACU_DEBUG_PROBLEM, 148 | "No need to call acuPolygonOpen more than once."); 149 | } 150 | 151 | acuTesselator = gluNewTess(); 152 | if (acuTesselator == NULL) { 153 | acuDebug(ACU_DEBUG_EMERGENCY, 154 | "Could not create tesselator object."); 155 | } 156 | 157 | acuDebug(ACU_DEBUG_EMERGENCY, 158 | "Tesselator is broken under Codewarrior 6 for windows"); 159 | /* 160 | gluTessCallback(acuTesselator, (GLenum)GLU_BEGIN, 161 | (void (*)())polygonBegin); 162 | 163 | gluTessCallback(acuTesselator, (GLenum)GLU_END, 164 | (void (*)())polygonEnd); 165 | 166 | gluTessCallback(acuTesselator, (GLenum)GLU_EDGE_FLAG, 167 | (void (*)())polygonEdgeFlag); 168 | 169 | gluTessCallback(acuTesselator, (GLenum)GLU_ERROR, 170 | (void (*)())polygonError); 171 | 172 | gluTessCallback(acuTesselator, (GLenum)GLU_VERTEX, 173 | (void (*)())polygonVertex); 174 | */ 175 | } 176 | 177 | /** 178 | * Deallocates the tesselator at the end of a program 179 | */ 180 | void acuPolygonClose() { 181 | gluDeleteTess(acuTesselator); 182 | } 183 | 184 | 185 | void acuLine2f(GLfloat x1, GLfloat y1, GLfloat x2, GLfloat y2) { 186 | glBegin(GL_LINES); 187 | glVertex3f(x1, y1, 0); 188 | glVertex3f(x2, y2, 0); 189 | glEnd(); 190 | } 191 | 192 | 193 | void acuLine2fv(int count, GLfloat *x, GLfloat *y) { 194 | int i; 195 | glBegin(GL_LINE_STRIP); 196 | for (i = 0; i < count; i++) { 197 | glVertex3f(x[i], y[i], 0); 198 | } 199 | glEnd(); 200 | } 201 | 202 | 203 | void acuLine3f(float x1, float y1, float z1, float x2, float y2, float z2) { 204 | //printf("frgsdfg\n"); 205 | glBegin(GL_LINES); 206 | //glNormal3f(0, 0, 1); 207 | glNormal3f(x1, y1, z1); 208 | glVertex3f(x1, y1, z1); 209 | glNormal3f(x2, y2, z2); 210 | glVertex3f(x2, y2, z2); 211 | glEnd(); 212 | } 213 | 214 | 215 | void acuLine3fv(int count, GLfloat *x, GLfloat *y, GLfloat *z) { 216 | int i; 217 | glBegin(GL_LINE_STRIP); 218 | for (i = 0; i < count; i++) { 219 | glVertex3f(x[i], y[i], z[i]); 220 | } 221 | glEnd(); 222 | } 223 | -------------------------------------------------------------------------------- /text.cpp: -------------------------------------------------------------------------------- 1 | #include "acu.h" 2 | #include "acFont.h" 3 | #include "acBitmapFont.h" 4 | //#include "acFreeTypeFont.h" 5 | #include "acVectorFont.h" 6 | 7 | #define ACU_FONT_LIST_MAX 50 8 | 9 | boolean acuTextInited = FALSE; 10 | boolean acuFontNormalize = TRUE; 11 | 12 | acFont* acutFontList[ACU_FONT_LIST_MAX]; 13 | char acutFontNames[ACU_FONT_LIST_MAX][128]; 14 | int acutCurrentFont; 15 | 16 | 17 | void acuTextInit() { 18 | //printf("text init called\n"); 19 | //acutFontList = new acFont*[ACU_FONT_LIST_MAX]; 20 | for (int i = 0; i < ACU_FONT_LIST_MAX; i++) { 21 | acutFontList[i] = NULL; 22 | acutFontNames[i][0] = 0; // empty string 23 | } 24 | acutCurrentFont = ACU_ERROR; 25 | acuTextInited = TRUE; 26 | } 27 | 28 | 29 | void acuUnloadFont(int which) { 30 | if (acutCurrentFont == which) { 31 | acuDebug(ACU_DEBUG_PROBLEM, "you cannot unload the current font"); 32 | return; 33 | } 34 | acutFontList[which] = NULL; 35 | acutFontNames[which][0] = 0; 36 | } 37 | 38 | 39 | int acuFindFont(char *filename) { 40 | for (int i = 0; i < ACU_FONT_LIST_MAX; i++) { 41 | if (strcmp(acutFontNames[i], filename) == 0) 42 | return i; 43 | } 44 | return ACU_ERROR; 45 | } 46 | 47 | 48 | // returns ACU_ERROR, -1 if problems 49 | int acuLoadFont(char *filename) { 50 | if (!acuTextInited) acuTextInit(); 51 | 52 | int which = acuFindFont(filename); 53 | if (which != ACU_ERROR) return which; 54 | 55 | // construct it depending on what type of font it is 56 | acFont *newbie = NULL; 57 | if (strstr(filename, ".jvf") || strstr(filename, ".JVF")) { 58 | newbie = new acVectorFont(filename); 59 | } else if (strstr(filename, ".ttf") || strstr(filename, ".TTF")) { 60 | //newbie = new acFreeTypeFont(filename); 61 | } else { 62 | newbie = new acBitmapFont(filename); 63 | } 64 | 65 | if ((newbie == NULL) || (!newbie->isValid())) { 66 | return ACU_ERROR; 67 | } 68 | 69 | for (int i = 0; i < ACU_FONT_LIST_MAX; i++) { 70 | if (acutFontList[i] == NULL) { 71 | acutFontList[i] = newbie; 72 | //printf("setting font %d, %d to %s\n", newbie, i, filename); 73 | strcpy(acutFontNames[i], filename); 74 | return i; 75 | } 76 | } 77 | delete newbie; 78 | sprintf(acuDebugStr, "Too many fonts, cannot open %s", filename); 79 | acuDebugString(ACU_DEBUG_PROBLEM); 80 | return ACU_ERROR; 81 | } 82 | 83 | 84 | void acuSetFont(int index) { 85 | if (acutFontList[index] != NULL) { 86 | acutCurrentFont = index; 87 | } else { 88 | sprintf(acuDebugStr, "Index %d is not a valid font.", index); 89 | acuDebugString(ACU_DEBUG_PROBLEM); 90 | } 91 | } 92 | 93 | 94 | void* acuGetFont(int index) { 95 | return acutFontList[index]; 96 | } 97 | 98 | 99 | void acuDrawChar(char c, GLfloat x, GLfloat y) { 100 | acuDrawChar2((unsigned char)c, x, y); 101 | } 102 | 103 | void acuDrawChar2(unsigned char c, GLfloat x, GLfloat y) { 104 | if (acutCurrentFont == ACU_ERROR) return; 105 | acutFontList[acutCurrentFont]->drawChar(c, x, y); 106 | } 107 | 108 | 109 | void acuDrawString(char *c, GLfloat x, GLfloat y) { 110 | acuDrawString2((unsigned char*) c, x, y); 111 | } 112 | 113 | void acuDrawString2(unsigned char *c, GLfloat x, GLfloat y) { 114 | if (acutCurrentFont == ACU_ERROR) return; 115 | acutFontList[acutCurrentFont]->drawString(c, x, y); 116 | } 117 | 118 | 119 | float acuGetCharMetric(acuEnum pname, unsigned char c) { 120 | if (acutCurrentFont == ACU_ERROR) { 121 | acuDebug(ACU_DEBUG_PROBLEM, 122 | "Can't get char metrics when no font is set"); 123 | return 0; 124 | } 125 | switch (pname) { 126 | case ACU_CHAR_WIDTH: 127 | return acutFontList[acutCurrentFont]->charWidth(c); 128 | default: 129 | break; 130 | } 131 | return 0; 132 | } 133 | 134 | 135 | void acuGetCharMetrics(acuEnum pname, unsigned char *c, GLfloat *metrics) { 136 | if (acutCurrentFont == ACU_ERROR) return; 137 | 138 | switch (pname) { 139 | case ACU_STRING_WIDTH: 140 | metrics[0] = acutFontList[acutCurrentFont]->stringWidth(c); 141 | break; 142 | 143 | default: 144 | sprintf(acuDebugStr, 145 | "acuGetCharMetrics: %d is not a valid param.", pname); 146 | acuDebugString(ACU_DEBUG_PROBLEM); 147 | break; 148 | } 149 | } 150 | -------------------------------------------------------------------------------- /windows/acu.mcp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dribnet/acu/d9381f1ee52e3c6d169818e4c1785a3667b1080c/windows/acu.mcp -------------------------------------------------------------------------------- /windows/glut32.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dribnet/acu/d9381f1ee52e3c6d169818e4c1785a3667b1080c/windows/glut32.dll -------------------------------------------------------------------------------- /windows/glut32.lib: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/dribnet/acu/d9381f1ee52e3c6d169818e4c1785a3667b1080c/windows/glut32.lib -------------------------------------------------------------------------------- /windows/jpeg/cderror.h: -------------------------------------------------------------------------------- 1 | /* 2 | * cderror.h 3 | * 4 | * Copyright (C) 1994-1997, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file defines the error and message codes for the cjpeg/djpeg 9 | * applications. These strings are not needed as part of the JPEG library 10 | * proper. 11 | * Edit this file to add new codes, or to translate the message strings to 12 | * some other language. 13 | */ 14 | 15 | /* 16 | * To define the enum list of message codes, include this file without 17 | * defining macro JMESSAGE. To create a message string table, include it 18 | * again with a suitable JMESSAGE definition (see jerror.c for an example). 19 | */ 20 | #ifndef JMESSAGE 21 | #ifndef CDERROR_H 22 | #define CDERROR_H 23 | /* First time through, define the enum list */ 24 | #define JMAKE_ENUM_LIST 25 | #else 26 | /* Repeated inclusions of this file are no-ops unless JMESSAGE is defined */ 27 | #define JMESSAGE(code,string) 28 | #endif /* CDERROR_H */ 29 | #endif /* JMESSAGE */ 30 | 31 | #ifdef JMAKE_ENUM_LIST 32 | 33 | typedef enum { 34 | 35 | #define JMESSAGE(code,string) code , 36 | 37 | #endif /* JMAKE_ENUM_LIST */ 38 | 39 | JMESSAGE(JMSG_FIRSTADDONCODE=1000, NULL) /* Must be first entry! */ 40 | 41 | #ifdef BMP_SUPPORTED 42 | JMESSAGE(JERR_BMP_BADCMAP, "Unsupported BMP colormap format") 43 | JMESSAGE(JERR_BMP_BADDEPTH, "Only 8- and 24-bit BMP files are supported") 44 | JMESSAGE(JERR_BMP_BADHEADER, "Invalid BMP file: bad header length") 45 | JMESSAGE(JERR_BMP_BADPLANES, "Invalid BMP file: biPlanes not equal to 1") 46 | JMESSAGE(JERR_BMP_COLORSPACE, "BMP output must be grayscale or RGB") 47 | JMESSAGE(JERR_BMP_COMPRESSED, "Sorry, compressed BMPs not yet supported") 48 | JMESSAGE(JERR_BMP_NOT, "Not a BMP file - does not start with BM") 49 | JMESSAGE(JTRC_BMP, "%ux%u 24-bit BMP image") 50 | JMESSAGE(JTRC_BMP_MAPPED, "%ux%u 8-bit colormapped BMP image") 51 | JMESSAGE(JTRC_BMP_OS2, "%ux%u 24-bit OS2 BMP image") 52 | JMESSAGE(JTRC_BMP_OS2_MAPPED, "%ux%u 8-bit colormapped OS2 BMP image") 53 | #endif /* BMP_SUPPORTED */ 54 | 55 | #ifdef GIF_SUPPORTED 56 | JMESSAGE(JERR_GIF_BUG, "GIF output got confused") 57 | JMESSAGE(JERR_GIF_CODESIZE, "Bogus GIF codesize %d") 58 | JMESSAGE(JERR_GIF_COLORSPACE, "GIF output must be grayscale or RGB") 59 | JMESSAGE(JERR_GIF_IMAGENOTFOUND, "Too few images in GIF file") 60 | JMESSAGE(JERR_GIF_NOT, "Not a GIF file") 61 | JMESSAGE(JTRC_GIF, "%ux%ux%d GIF image") 62 | JMESSAGE(JTRC_GIF_BADVERSION, 63 | "Warning: unexpected GIF version number '%c%c%c'") 64 | JMESSAGE(JTRC_GIF_EXTENSION, "Ignoring GIF extension block of type 0x%02x") 65 | JMESSAGE(JTRC_GIF_NONSQUARE, "Caution: nonsquare pixels in input") 66 | JMESSAGE(JWRN_GIF_BADDATA, "Corrupt data in GIF file") 67 | JMESSAGE(JWRN_GIF_CHAR, "Bogus char 0x%02x in GIF file, ignoring") 68 | JMESSAGE(JWRN_GIF_ENDCODE, "Premature end of GIF image") 69 | JMESSAGE(JWRN_GIF_NOMOREDATA, "Ran out of GIF bits") 70 | #endif /* GIF_SUPPORTED */ 71 | 72 | #ifdef PPM_SUPPORTED 73 | JMESSAGE(JERR_PPM_COLORSPACE, "PPM output must be grayscale or RGB") 74 | JMESSAGE(JERR_PPM_NONNUMERIC, "Nonnumeric data in PPM file") 75 | JMESSAGE(JERR_PPM_NOT, "Not a PPM/PGM file") 76 | JMESSAGE(JTRC_PGM, "%ux%u PGM image") 77 | JMESSAGE(JTRC_PGM_TEXT, "%ux%u text PGM image") 78 | JMESSAGE(JTRC_PPM, "%ux%u PPM image") 79 | JMESSAGE(JTRC_PPM_TEXT, "%ux%u text PPM image") 80 | #endif /* PPM_SUPPORTED */ 81 | 82 | #ifdef RLE_SUPPORTED 83 | JMESSAGE(JERR_RLE_BADERROR, "Bogus error code from RLE library") 84 | JMESSAGE(JERR_RLE_COLORSPACE, "RLE output must be grayscale or RGB") 85 | JMESSAGE(JERR_RLE_DIMENSIONS, "Image dimensions (%ux%u) too large for RLE") 86 | JMESSAGE(JERR_RLE_EMPTY, "Empty RLE file") 87 | JMESSAGE(JERR_RLE_EOF, "Premature EOF in RLE header") 88 | JMESSAGE(JERR_RLE_MEM, "Insufficient memory for RLE header") 89 | JMESSAGE(JERR_RLE_NOT, "Not an RLE file") 90 | JMESSAGE(JERR_RLE_TOOMANYCHANNELS, "Cannot handle %d output channels for RLE") 91 | JMESSAGE(JERR_RLE_UNSUPPORTED, "Cannot handle this RLE setup") 92 | JMESSAGE(JTRC_RLE, "%ux%u full-color RLE file") 93 | JMESSAGE(JTRC_RLE_FULLMAP, "%ux%u full-color RLE file with map of length %d") 94 | JMESSAGE(JTRC_RLE_GRAY, "%ux%u grayscale RLE file") 95 | JMESSAGE(JTRC_RLE_MAPGRAY, "%ux%u grayscale RLE file with map of length %d") 96 | JMESSAGE(JTRC_RLE_MAPPED, "%ux%u colormapped RLE file with map of length %d") 97 | #endif /* RLE_SUPPORTED */ 98 | 99 | #ifdef TARGA_SUPPORTED 100 | JMESSAGE(JERR_TGA_BADCMAP, "Unsupported Targa colormap format") 101 | JMESSAGE(JERR_TGA_BADPARMS, "Invalid or unsupported Targa file") 102 | JMESSAGE(JERR_TGA_COLORSPACE, "Targa output must be grayscale or RGB") 103 | JMESSAGE(JTRC_TGA, "%ux%u RGB Targa image") 104 | JMESSAGE(JTRC_TGA_GRAY, "%ux%u grayscale Targa image") 105 | JMESSAGE(JTRC_TGA_MAPPED, "%ux%u colormapped Targa image") 106 | #else 107 | JMESSAGE(JERR_TGA_NOTCOMP, "Targa support was not compiled") 108 | #endif /* TARGA_SUPPORTED */ 109 | 110 | JMESSAGE(JERR_BAD_CMAP_FILE, 111 | "Color map file is invalid or of unsupported format") 112 | JMESSAGE(JERR_TOO_MANY_COLORS, 113 | "Output file format cannot handle %d colormap entries") 114 | JMESSAGE(JERR_UNGETC_FAILED, "ungetc failed") 115 | #ifdef TARGA_SUPPORTED 116 | JMESSAGE(JERR_UNKNOWN_FORMAT, 117 | "Unrecognized input file format --- perhaps you need -targa") 118 | #else 119 | JMESSAGE(JERR_UNKNOWN_FORMAT, "Unrecognized input file format") 120 | #endif 121 | JMESSAGE(JERR_UNSUPPORTED_FORMAT, "Unsupported output file format") 122 | 123 | #ifdef JMAKE_ENUM_LIST 124 | 125 | JMSG_LASTADDONCODE 126 | } ADDON_MESSAGE_CODE; 127 | 128 | #undef JMAKE_ENUM_LIST 129 | #endif /* JMAKE_ENUM_LIST */ 130 | 131 | /* Zap JMESSAGE macro so that future re-inclusions do nothing by default */ 132 | #undef JMESSAGE 133 | -------------------------------------------------------------------------------- /windows/jpeg/cdjpeg.c: -------------------------------------------------------------------------------- 1 | /* 2 | * cdjpeg.c 3 | * 4 | * Copyright (C) 1991-1997, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains common support routines used by the IJG application 9 | * programs (cjpeg, djpeg, jpegtran). 10 | */ 11 | 12 | #include "cdjpeg.h" /* Common decls for cjpeg/djpeg applications */ 13 | #include /* to declare isupper(), tolower() */ 14 | #ifdef NEED_SIGNAL_CATCHER 15 | #include /* to declare signal() */ 16 | #endif 17 | #ifdef USE_SETMODE 18 | #include /* to declare setmode()'s parameter macros */ 19 | /* If you have setmode() but not , just delete this line: */ 20 | #include /* to declare setmode() */ 21 | #endif 22 | 23 | 24 | /* 25 | * Signal catcher to ensure that temporary files are removed before aborting. 26 | * NB: for Amiga Manx C this is actually a global routine named _abort(); 27 | * we put "#define signal_catcher _abort" in jconfig.h. Talk about bogus... 28 | */ 29 | 30 | #ifdef NEED_SIGNAL_CATCHER 31 | 32 | static j_common_ptr sig_cinfo; 33 | 34 | void /* must be global for Manx C */ 35 | signal_catcher (int signum) 36 | { 37 | if (sig_cinfo != NULL) { 38 | if (sig_cinfo->err != NULL) /* turn off trace output */ 39 | sig_cinfo->err->trace_level = 0; 40 | jpeg_destroy(sig_cinfo); /* clean up memory allocation & temp files */ 41 | } 42 | exit(EXIT_FAILURE); 43 | } 44 | 45 | 46 | GLOBAL(void) 47 | enable_signal_catcher (j_common_ptr cinfo) 48 | { 49 | sig_cinfo = cinfo; 50 | #ifdef SIGINT /* not all systems have SIGINT */ 51 | signal(SIGINT, signal_catcher); 52 | #endif 53 | #ifdef SIGTERM /* not all systems have SIGTERM */ 54 | signal(SIGTERM, signal_catcher); 55 | #endif 56 | } 57 | 58 | #endif 59 | 60 | 61 | /* 62 | * Optional progress monitor: display a percent-done figure on stderr. 63 | */ 64 | 65 | #ifdef PROGRESS_REPORT 66 | 67 | METHODDEF(void) 68 | progress_monitor (j_common_ptr cinfo) 69 | { 70 | cd_progress_ptr prog = (cd_progress_ptr) cinfo->progress; 71 | int total_passes = prog->pub.total_passes + prog->total_extra_passes; 72 | int percent_done = (int) (prog->pub.pass_counter*100L/prog->pub.pass_limit); 73 | 74 | if (percent_done != prog->percent_done) { 75 | prog->percent_done = percent_done; 76 | if (total_passes > 1) { 77 | fprintf(stderr, "\rPass %d/%d: %3d%% ", 78 | prog->pub.completed_passes + prog->completed_extra_passes + 1, 79 | total_passes, percent_done); 80 | } else { 81 | fprintf(stderr, "\r %3d%% ", percent_done); 82 | } 83 | fflush(stderr); 84 | } 85 | } 86 | 87 | 88 | GLOBAL(void) 89 | start_progress_monitor (j_common_ptr cinfo, cd_progress_ptr progress) 90 | { 91 | /* Enable progress display, unless trace output is on */ 92 | if (cinfo->err->trace_level == 0) { 93 | progress->pub.progress_monitor = progress_monitor; 94 | progress->completed_extra_passes = 0; 95 | progress->total_extra_passes = 0; 96 | progress->percent_done = -1; 97 | cinfo->progress = &progress->pub; 98 | } 99 | } 100 | 101 | 102 | GLOBAL(void) 103 | end_progress_monitor (j_common_ptr cinfo) 104 | { 105 | /* Clear away progress display */ 106 | if (cinfo->err->trace_level == 0) { 107 | fprintf(stderr, "\r \r"); 108 | fflush(stderr); 109 | } 110 | } 111 | 112 | #endif 113 | 114 | 115 | /* 116 | * Case-insensitive matching of possibly-abbreviated keyword switches. 117 | * keyword is the constant keyword (must be lower case already), 118 | * minchars is length of minimum legal abbreviation. 119 | */ 120 | 121 | GLOBAL(boolean) 122 | keymatch (char * arg, const char * keyword, int minchars) 123 | { 124 | register int ca, ck; 125 | register int nmatched = 0; 126 | 127 | while ((ca = *arg++) != '\0') { 128 | if ((ck = *keyword++) == '\0') 129 | return FALSE; /* arg longer than keyword, no good */ 130 | if (isupper(ca)) /* force arg to lcase (assume ck is already) */ 131 | ca = tolower(ca); 132 | if (ca != ck) 133 | return FALSE; /* no good */ 134 | nmatched++; /* count matched characters */ 135 | } 136 | /* reached end of argument; fail if it's too short for unique abbrev */ 137 | if (nmatched < minchars) 138 | return FALSE; 139 | return TRUE; /* A-OK */ 140 | } 141 | 142 | 143 | /* 144 | * Routines to establish binary I/O mode for stdin and stdout. 145 | * Non-Unix systems often require some hacking to get out of text mode. 146 | */ 147 | 148 | GLOBAL(FILE *) 149 | read_stdin (void) 150 | { 151 | FILE * input_file = stdin; 152 | 153 | #ifdef USE_SETMODE /* need to hack file mode? */ 154 | setmode(fileno(stdin), O_BINARY); 155 | #endif 156 | #ifdef USE_FDOPEN /* need to re-open in binary mode? */ 157 | if ((input_file = fdopen(fileno(stdin), READ_BINARY)) == NULL) { 158 | fprintf(stderr, "Cannot reopen stdin\n"); 159 | exit(EXIT_FAILURE); 160 | } 161 | #endif 162 | return input_file; 163 | } 164 | 165 | 166 | GLOBAL(FILE *) 167 | write_stdout (void) 168 | { 169 | FILE * output_file = stdout; 170 | 171 | #ifdef USE_SETMODE /* need to hack file mode? */ 172 | setmode(fileno(stdout), O_BINARY); 173 | #endif 174 | #ifdef USE_FDOPEN /* need to re-open in binary mode? */ 175 | if ((output_file = fdopen(fileno(stdout), WRITE_BINARY)) == NULL) { 176 | fprintf(stderr, "Cannot reopen stdout\n"); 177 | exit(EXIT_FAILURE); 178 | } 179 | #endif 180 | return output_file; 181 | } 182 | -------------------------------------------------------------------------------- /windows/jpeg/cdjpeg.h: -------------------------------------------------------------------------------- 1 | /* 2 | * cdjpeg.h 3 | * 4 | * Copyright (C) 1994-1997, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains common declarations for the sample applications 9 | * cjpeg and djpeg. It is NOT used by the core JPEG library. 10 | */ 11 | 12 | #define JPEG_CJPEG_DJPEG /* define proper options in jconfig.h */ 13 | #define JPEG_INTERNAL_OPTIONS /* cjpeg.c,djpeg.c need to see xxx_SUPPORTED */ 14 | #include "jinclude.h" 15 | #include "jpeglib.h" 16 | #include "jerror.h" /* get library error codes too */ 17 | #include "cderror.h" /* get application-specific error codes */ 18 | 19 | 20 | /* 21 | * Object interface for cjpeg's source file decoding modules 22 | */ 23 | 24 | typedef struct cjpeg_source_struct * cjpeg_source_ptr; 25 | 26 | struct cjpeg_source_struct { 27 | JMETHOD(void, start_input, (j_compress_ptr cinfo, 28 | cjpeg_source_ptr sinfo)); 29 | JMETHOD(JDIMENSION, get_pixel_rows, (j_compress_ptr cinfo, 30 | cjpeg_source_ptr sinfo)); 31 | JMETHOD(void, finish_input, (j_compress_ptr cinfo, 32 | cjpeg_source_ptr sinfo)); 33 | 34 | FILE *input_file; 35 | 36 | JSAMPARRAY buffer; 37 | JDIMENSION buffer_height; 38 | }; 39 | 40 | 41 | /* 42 | * Object interface for djpeg's output file encoding modules 43 | */ 44 | 45 | typedef struct djpeg_dest_struct * djpeg_dest_ptr; 46 | 47 | struct djpeg_dest_struct { 48 | /* start_output is called after jpeg_start_decompress finishes. 49 | * The color map will be ready at this time, if one is needed. 50 | */ 51 | JMETHOD(void, start_output, (j_decompress_ptr cinfo, 52 | djpeg_dest_ptr dinfo)); 53 | /* Emit the specified number of pixel rows from the buffer. */ 54 | JMETHOD(void, put_pixel_rows, (j_decompress_ptr cinfo, 55 | djpeg_dest_ptr dinfo, 56 | JDIMENSION rows_supplied)); 57 | /* Finish up at the end of the image. */ 58 | JMETHOD(void, finish_output, (j_decompress_ptr cinfo, 59 | djpeg_dest_ptr dinfo)); 60 | 61 | /* Target file spec; filled in by djpeg.c after object is created. */ 62 | FILE * output_file; 63 | 64 | /* Output pixel-row buffer. Created by module init or start_output. 65 | * Width is cinfo->output_width * cinfo->output_components; 66 | * height is buffer_height. 67 | */ 68 | JSAMPARRAY buffer; 69 | JDIMENSION buffer_height; 70 | }; 71 | 72 | 73 | /* 74 | * cjpeg/djpeg may need to perform extra passes to convert to or from 75 | * the source/destination file format. The JPEG library does not know 76 | * about these passes, but we'd like them to be counted by the progress 77 | * monitor. We use an expanded progress monitor object to hold the 78 | * additional pass count. 79 | */ 80 | 81 | struct cdjpeg_progress_mgr { 82 | struct jpeg_progress_mgr pub; /* fields known to JPEG library */ 83 | int completed_extra_passes; /* extra passes completed */ 84 | int total_extra_passes; /* total extra */ 85 | /* last printed percentage stored here to avoid multiple printouts */ 86 | int percent_done; 87 | }; 88 | 89 | typedef struct cdjpeg_progress_mgr * cd_progress_ptr; 90 | 91 | 92 | /* Short forms of external names for systems with brain-damaged linkers. */ 93 | 94 | #ifdef NEED_SHORT_EXTERNAL_NAMES 95 | #define jinit_read_bmp jIRdBMP 96 | #define jinit_write_bmp jIWrBMP 97 | #define jinit_read_gif jIRdGIF 98 | #define jinit_write_gif jIWrGIF 99 | #define jinit_read_ppm jIRdPPM 100 | #define jinit_write_ppm jIWrPPM 101 | #define jinit_read_rle jIRdRLE 102 | #define jinit_write_rle jIWrRLE 103 | #define jinit_read_targa jIRdTarga 104 | #define jinit_write_targa jIWrTarga 105 | #define read_quant_tables RdQTables 106 | #define read_scan_script RdScnScript 107 | #define set_quant_slots SetQSlots 108 | #define set_sample_factors SetSFacts 109 | #define read_color_map RdCMap 110 | #define enable_signal_catcher EnSigCatcher 111 | #define start_progress_monitor StProgMon 112 | #define end_progress_monitor EnProgMon 113 | #define read_stdin RdStdin 114 | #define write_stdout WrStdout 115 | #endif /* NEED_SHORT_EXTERNAL_NAMES */ 116 | 117 | /* Module selection routines for I/O modules. */ 118 | 119 | EXTERN(cjpeg_source_ptr) jinit_read_bmp JPP((j_compress_ptr cinfo)); 120 | EXTERN(djpeg_dest_ptr) jinit_write_bmp JPP((j_decompress_ptr cinfo, 121 | boolean is_os2)); 122 | EXTERN(cjpeg_source_ptr) jinit_read_gif JPP((j_compress_ptr cinfo)); 123 | EXTERN(djpeg_dest_ptr) jinit_write_gif JPP((j_decompress_ptr cinfo)); 124 | EXTERN(cjpeg_source_ptr) jinit_read_ppm JPP((j_compress_ptr cinfo)); 125 | EXTERN(djpeg_dest_ptr) jinit_write_ppm JPP((j_decompress_ptr cinfo)); 126 | EXTERN(cjpeg_source_ptr) jinit_read_rle JPP((j_compress_ptr cinfo)); 127 | EXTERN(djpeg_dest_ptr) jinit_write_rle JPP((j_decompress_ptr cinfo)); 128 | EXTERN(cjpeg_source_ptr) jinit_read_targa JPP((j_compress_ptr cinfo)); 129 | EXTERN(djpeg_dest_ptr) jinit_write_targa JPP((j_decompress_ptr cinfo)); 130 | 131 | /* cjpeg support routines (in rdswitch.c) */ 132 | 133 | EXTERN(boolean) read_quant_tables JPP((j_compress_ptr cinfo, char * filename, 134 | int scale_factor, boolean force_baseline)); 135 | EXTERN(boolean) read_scan_script JPP((j_compress_ptr cinfo, char * filename)); 136 | EXTERN(boolean) set_quant_slots JPP((j_compress_ptr cinfo, char *arg)); 137 | EXTERN(boolean) set_sample_factors JPP((j_compress_ptr cinfo, char *arg)); 138 | 139 | /* djpeg support routines (in rdcolmap.c) */ 140 | 141 | EXTERN(void) read_color_map JPP((j_decompress_ptr cinfo, FILE * infile)); 142 | 143 | /* common support routines (in cdjpeg.c) */ 144 | 145 | EXTERN(void) enable_signal_catcher JPP((j_common_ptr cinfo)); 146 | EXTERN(void) start_progress_monitor JPP((j_common_ptr cinfo, 147 | cd_progress_ptr progress)); 148 | EXTERN(void) end_progress_monitor JPP((j_common_ptr cinfo)); 149 | EXTERN(boolean) keymatch JPP((char * arg, const char * keyword, int minchars)); 150 | EXTERN(FILE *) read_stdin JPP((void)); 151 | EXTERN(FILE *) write_stdout JPP((void)); 152 | 153 | /* miscellaneous useful macros */ 154 | 155 | #ifdef DONT_USE_B_MODE /* define mode parameters for fopen() */ 156 | #define READ_BINARY "r" 157 | #define WRITE_BINARY "w" 158 | #else 159 | #ifdef VMS /* VMS is very nonstandard */ 160 | #define READ_BINARY "rb", "ctx=stm" 161 | #define WRITE_BINARY "wb", "ctx=stm" 162 | #else /* standard ANSI-compliant case */ 163 | #define READ_BINARY "rb" 164 | #define WRITE_BINARY "wb" 165 | #endif 166 | #endif 167 | 168 | #ifndef EXIT_FAILURE /* define exit() codes if not provided */ 169 | #define EXIT_FAILURE 1 170 | #endif 171 | #ifndef EXIT_SUCCESS 172 | #ifdef VMS 173 | #define EXIT_SUCCESS 1 /* VMS is very nonstandard */ 174 | #else 175 | #define EXIT_SUCCESS 0 176 | #endif 177 | #endif 178 | #ifndef EXIT_WARNING 179 | #ifdef VMS 180 | #define EXIT_WARNING 1 /* VMS is very nonstandard */ 181 | #else 182 | #define EXIT_WARNING 2 183 | #endif 184 | #endif 185 | -------------------------------------------------------------------------------- /windows/jpeg/jcapistd.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jcapistd.c 3 | * 4 | * Copyright (C) 1994-1996, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains application interface code for the compression half 9 | * of the JPEG library. These are the "standard" API routines that are 10 | * used in the normal full-compression case. They are not used by a 11 | * transcoding-only application. Note that if an application links in 12 | * jpeg_start_compress, it will end up linking in the entire compressor. 13 | * We thus must separate this file from jcapimin.c to avoid linking the 14 | * whole compression library into a transcoder. 15 | */ 16 | 17 | #define JPEG_INTERNALS 18 | #include "jinclude.h" 19 | #include "jpeglib.h" 20 | 21 | 22 | /* 23 | * Compression initialization. 24 | * Before calling this, all parameters and a data destination must be set up. 25 | * 26 | * We require a write_all_tables parameter as a failsafe check when writing 27 | * multiple datastreams from the same compression object. Since prior runs 28 | * will have left all the tables marked sent_table=TRUE, a subsequent run 29 | * would emit an abbreviated stream (no tables) by default. This may be what 30 | * is wanted, but for safety's sake it should not be the default behavior: 31 | * programmers should have to make a deliberate choice to emit abbreviated 32 | * images. Therefore the documentation and examples should encourage people 33 | * to pass write_all_tables=TRUE; then it will take active thought to do the 34 | * wrong thing. 35 | */ 36 | 37 | GLOBAL(void) 38 | jpeg_start_compress (j_compress_ptr cinfo, boolean write_all_tables) 39 | { 40 | if (cinfo->global_state != CSTATE_START) 41 | ERREXIT1(cinfo, JERR_BAD_STATE, cinfo->global_state); 42 | 43 | if (write_all_tables) 44 | jpeg_suppress_tables(cinfo, FALSE); /* mark all tables to be written */ 45 | 46 | /* (Re)initialize error mgr and destination modules */ 47 | (*cinfo->err->reset_error_mgr) ((j_common_ptr) cinfo); 48 | (*cinfo->dest->init_destination) (cinfo); 49 | /* Perform master selection of active modules */ 50 | jinit_compress_master(cinfo); 51 | /* Set up for the first pass */ 52 | (*cinfo->master->prepare_for_pass) (cinfo); 53 | /* Ready for application to drive first pass through jpeg_write_scanlines 54 | * or jpeg_write_raw_data. 55 | */ 56 | cinfo->next_scanline = 0; 57 | cinfo->global_state = (cinfo->raw_data_in ? CSTATE_RAW_OK : CSTATE_SCANNING); 58 | } 59 | 60 | 61 | /* 62 | * Write some scanlines of data to the JPEG compressor. 63 | * 64 | * The return value will be the number of lines actually written. 65 | * This should be less than the supplied num_lines only in case that 66 | * the data destination module has requested suspension of the compressor, 67 | * or if more than image_height scanlines are passed in. 68 | * 69 | * Note: we warn about excess calls to jpeg_write_scanlines() since 70 | * this likely signals an application programmer error. However, 71 | * excess scanlines passed in the last valid call are *silently* ignored, 72 | * so that the application need not adjust num_lines for end-of-image 73 | * when using a multiple-scanline buffer. 74 | */ 75 | 76 | GLOBAL(JDIMENSION) 77 | jpeg_write_scanlines (j_compress_ptr cinfo, JSAMPARRAY scanlines, 78 | JDIMENSION num_lines) 79 | { 80 | JDIMENSION row_ctr, rows_left; 81 | 82 | if (cinfo->global_state != CSTATE_SCANNING) 83 | ERREXIT1(cinfo, JERR_BAD_STATE, cinfo->global_state); 84 | if (cinfo->next_scanline >= cinfo->image_height) 85 | WARNMS(cinfo, JWRN_TOO_MUCH_DATA); 86 | 87 | /* Call progress monitor hook if present */ 88 | if (cinfo->progress != NULL) { 89 | cinfo->progress->pass_counter = (long) cinfo->next_scanline; 90 | cinfo->progress->pass_limit = (long) cinfo->image_height; 91 | (*cinfo->progress->progress_monitor) ((j_common_ptr) cinfo); 92 | } 93 | 94 | /* Give master control module another chance if this is first call to 95 | * jpeg_write_scanlines. This lets output of the frame/scan headers be 96 | * delayed so that application can write COM, etc, markers between 97 | * jpeg_start_compress and jpeg_write_scanlines. 98 | */ 99 | if (cinfo->master->call_pass_startup) 100 | (*cinfo->master->pass_startup) (cinfo); 101 | 102 | /* Ignore any extra scanlines at bottom of image. */ 103 | rows_left = cinfo->image_height - cinfo->next_scanline; 104 | if (num_lines > rows_left) 105 | num_lines = rows_left; 106 | 107 | row_ctr = 0; 108 | (*cinfo->main->process_data) (cinfo, scanlines, &row_ctr, num_lines); 109 | cinfo->next_scanline += row_ctr; 110 | return row_ctr; 111 | } 112 | 113 | 114 | /* 115 | * Alternate entry point to write raw data. 116 | * Processes exactly one iMCU row per call, unless suspended. 117 | */ 118 | 119 | GLOBAL(JDIMENSION) 120 | jpeg_write_raw_data (j_compress_ptr cinfo, JSAMPIMAGE data, 121 | JDIMENSION num_lines) 122 | { 123 | JDIMENSION lines_per_iMCU_row; 124 | 125 | if (cinfo->global_state != CSTATE_RAW_OK) 126 | ERREXIT1(cinfo, JERR_BAD_STATE, cinfo->global_state); 127 | if (cinfo->next_scanline >= cinfo->image_height) { 128 | WARNMS(cinfo, JWRN_TOO_MUCH_DATA); 129 | return 0; 130 | } 131 | 132 | /* Call progress monitor hook if present */ 133 | if (cinfo->progress != NULL) { 134 | cinfo->progress->pass_counter = (long) cinfo->next_scanline; 135 | cinfo->progress->pass_limit = (long) cinfo->image_height; 136 | (*cinfo->progress->progress_monitor) ((j_common_ptr) cinfo); 137 | } 138 | 139 | /* Give master control module another chance if this is first call to 140 | * jpeg_write_raw_data. This lets output of the frame/scan headers be 141 | * delayed so that application can write COM, etc, markers between 142 | * jpeg_start_compress and jpeg_write_raw_data. 143 | */ 144 | if (cinfo->master->call_pass_startup) 145 | (*cinfo->master->pass_startup) (cinfo); 146 | 147 | /* Verify that at least one iMCU row has been passed. */ 148 | lines_per_iMCU_row = cinfo->max_v_samp_factor * DCTSIZE; 149 | if (num_lines < lines_per_iMCU_row) 150 | ERREXIT(cinfo, JERR_BUFFER_SIZE); 151 | 152 | /* Directly compress the row. */ 153 | if (! (*cinfo->coef->compress_data) (cinfo, data)) { 154 | /* If compressor did not consume the whole row, suspend processing. */ 155 | return 0; 156 | } 157 | 158 | /* OK, we processed one iMCU row. */ 159 | cinfo->next_scanline += lines_per_iMCU_row; 160 | return lines_per_iMCU_row; 161 | } 162 | -------------------------------------------------------------------------------- /windows/jpeg/jchuff.h: -------------------------------------------------------------------------------- 1 | /* 2 | * jchuff.h 3 | * 4 | * Copyright (C) 1991-1997, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains declarations for Huffman entropy encoding routines 9 | * that are shared between the sequential encoder (jchuff.c) and the 10 | * progressive encoder (jcphuff.c). No other modules need to see these. 11 | */ 12 | 13 | /* The legal range of a DCT coefficient is 14 | * -1024 .. +1023 for 8-bit data; 15 | * -16384 .. +16383 for 12-bit data. 16 | * Hence the magnitude should always fit in 10 or 14 bits respectively. 17 | */ 18 | 19 | #if BITS_IN_JSAMPLE == 8 20 | #define MAX_COEF_BITS 10 21 | #else 22 | #define MAX_COEF_BITS 14 23 | #endif 24 | 25 | /* Derived data constructed for each Huffman table */ 26 | 27 | typedef struct { 28 | unsigned int ehufco[256]; /* code for each symbol */ 29 | char ehufsi[256]; /* length of code for each symbol */ 30 | /* If no code has been allocated for a symbol S, ehufsi[S] contains 0 */ 31 | } c_derived_tbl; 32 | 33 | /* Short forms of external names for systems with brain-damaged linkers. */ 34 | 35 | #ifdef NEED_SHORT_EXTERNAL_NAMES 36 | #define jpeg_make_c_derived_tbl jMkCDerived 37 | #define jpeg_gen_optimal_table jGenOptTbl 38 | #endif /* NEED_SHORT_EXTERNAL_NAMES */ 39 | 40 | /* Expand a Huffman table definition into the derived format */ 41 | EXTERN(void) jpeg_make_c_derived_tbl 42 | JPP((j_compress_ptr cinfo, boolean isDC, int tblno, 43 | c_derived_tbl ** pdtbl)); 44 | 45 | /* Generate an optimal table definition given the specified counts */ 46 | EXTERN(void) jpeg_gen_optimal_table 47 | JPP((j_compress_ptr cinfo, JHUFF_TBL * htbl, long freq[])); 48 | -------------------------------------------------------------------------------- /windows/jpeg/jcinit.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jcinit.c 3 | * 4 | * Copyright (C) 1991-1997, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains initialization logic for the JPEG compressor. 9 | * This routine is in charge of selecting the modules to be executed and 10 | * making an initialization call to each one. 11 | * 12 | * Logically, this code belongs in jcmaster.c. It's split out because 13 | * linking this routine implies linking the entire compression library. 14 | * For a transcoding-only application, we want to be able to use jcmaster.c 15 | * without linking in the whole library. 16 | */ 17 | 18 | #define JPEG_INTERNALS 19 | #include "jinclude.h" 20 | #include "jpeglib.h" 21 | 22 | 23 | /* 24 | * Master selection of compression modules. 25 | * This is done once at the start of processing an image. We determine 26 | * which modules will be used and give them appropriate initialization calls. 27 | */ 28 | 29 | GLOBAL(void) 30 | jinit_compress_master (j_compress_ptr cinfo) 31 | { 32 | /* Initialize master control (includes parameter checking/processing) */ 33 | jinit_c_master_control(cinfo, FALSE /* full compression */); 34 | 35 | /* Preprocessing */ 36 | if (! cinfo->raw_data_in) { 37 | jinit_color_converter(cinfo); 38 | jinit_downsampler(cinfo); 39 | jinit_c_prep_controller(cinfo, FALSE /* never need full buffer here */); 40 | } 41 | /* Forward DCT */ 42 | jinit_forward_dct(cinfo); 43 | /* Entropy encoding: either Huffman or arithmetic coding. */ 44 | if (cinfo->arith_code) { 45 | ERREXIT(cinfo, JERR_ARITH_NOTIMPL); 46 | } else { 47 | if (cinfo->progressive_mode) { 48 | #ifdef C_PROGRESSIVE_SUPPORTED 49 | jinit_phuff_encoder(cinfo); 50 | #else 51 | ERREXIT(cinfo, JERR_NOT_COMPILED); 52 | #endif 53 | } else 54 | jinit_huff_encoder(cinfo); 55 | } 56 | 57 | /* Need a full-image coefficient buffer in any multi-pass mode. */ 58 | jinit_c_coef_controller(cinfo, 59 | (boolean) (cinfo->num_scans > 1 || cinfo->optimize_coding)); 60 | jinit_c_main_controller(cinfo, FALSE /* never need full buffer here */); 61 | 62 | jinit_marker_writer(cinfo); 63 | 64 | /* We can now tell the memory manager to allocate virtual arrays. */ 65 | (*cinfo->mem->realize_virt_arrays) ((j_common_ptr) cinfo); 66 | 67 | /* Write the datastream header (SOI) immediately. 68 | * Frame and scan headers are postponed till later. 69 | * This lets application insert special markers after the SOI. 70 | */ 71 | (*cinfo->marker->write_file_header) (cinfo); 72 | } 73 | -------------------------------------------------------------------------------- /windows/jpeg/jcomapi.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jcomapi.c 3 | * 4 | * Copyright (C) 1994-1997, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains application interface routines that are used for both 9 | * compression and decompression. 10 | */ 11 | 12 | #define JPEG_INTERNALS 13 | #include "jinclude.h" 14 | #include "jpeglib.h" 15 | 16 | 17 | /* 18 | * Abort processing of a JPEG compression or decompression operation, 19 | * but don't destroy the object itself. 20 | * 21 | * For this, we merely clean up all the nonpermanent memory pools. 22 | * Note that temp files (virtual arrays) are not allowed to belong to 23 | * the permanent pool, so we will be able to close all temp files here. 24 | * Closing a data source or destination, if necessary, is the application's 25 | * responsibility. 26 | */ 27 | 28 | GLOBAL(void) 29 | jpeg_abort (j_common_ptr cinfo) 30 | { 31 | int pool; 32 | 33 | /* Do nothing if called on a not-initialized or destroyed JPEG object. */ 34 | if (cinfo->mem == NULL) 35 | return; 36 | 37 | /* Releasing pools in reverse order might help avoid fragmentation 38 | * with some (brain-damaged) malloc libraries. 39 | */ 40 | for (pool = JPOOL_NUMPOOLS-1; pool > JPOOL_PERMANENT; pool--) { 41 | (*cinfo->mem->free_pool) (cinfo, pool); 42 | } 43 | 44 | /* Reset overall state for possible reuse of object */ 45 | if (cinfo->is_decompressor) { 46 | cinfo->global_state = DSTATE_START; 47 | /* Try to keep application from accessing now-deleted marker list. 48 | * A bit kludgy to do it here, but this is the most central place. 49 | */ 50 | ((j_decompress_ptr) cinfo)->marker_list = NULL; 51 | } else { 52 | cinfo->global_state = CSTATE_START; 53 | } 54 | } 55 | 56 | 57 | /* 58 | * Destruction of a JPEG object. 59 | * 60 | * Everything gets deallocated except the master jpeg_compress_struct itself 61 | * and the error manager struct. Both of these are supplied by the application 62 | * and must be freed, if necessary, by the application. (Often they are on 63 | * the stack and so don't need to be freed anyway.) 64 | * Closing a data source or destination, if necessary, is the application's 65 | * responsibility. 66 | */ 67 | 68 | GLOBAL(void) 69 | jpeg_destroy (j_common_ptr cinfo) 70 | { 71 | /* We need only tell the memory manager to release everything. */ 72 | /* NB: mem pointer is NULL if memory mgr failed to initialize. */ 73 | if (cinfo->mem != NULL) 74 | (*cinfo->mem->self_destruct) (cinfo); 75 | cinfo->mem = NULL; /* be safe if jpeg_destroy is called twice */ 76 | cinfo->global_state = 0; /* mark it destroyed */ 77 | } 78 | 79 | 80 | /* 81 | * Convenience routines for allocating quantization and Huffman tables. 82 | * (Would jutils.c be a more reasonable place to put these?) 83 | */ 84 | 85 | GLOBAL(JQUANT_TBL *) 86 | jpeg_alloc_quant_table (j_common_ptr cinfo) 87 | { 88 | JQUANT_TBL *tbl; 89 | 90 | tbl = (JQUANT_TBL *) 91 | (*cinfo->mem->alloc_small) (cinfo, JPOOL_PERMANENT, SIZEOF(JQUANT_TBL)); 92 | tbl->sent_table = FALSE; /* make sure this is false in any new table */ 93 | return tbl; 94 | } 95 | 96 | 97 | GLOBAL(JHUFF_TBL *) 98 | jpeg_alloc_huff_table (j_common_ptr cinfo) 99 | { 100 | JHUFF_TBL *tbl; 101 | 102 | tbl = (JHUFF_TBL *) 103 | (*cinfo->mem->alloc_small) (cinfo, JPOOL_PERMANENT, SIZEOF(JHUFF_TBL)); 104 | tbl->sent_table = FALSE; /* make sure this is false in any new table */ 105 | return tbl; 106 | } 107 | -------------------------------------------------------------------------------- /windows/jpeg/jconfig.h: -------------------------------------------------------------------------------- 1 | /* jconfig.vc --- jconfig.h for Microsoft Visual C++ on Windows 95 or NT. */ 2 | /* see jconfig.doc for explanations */ 3 | 4 | #define HAVE_PROTOTYPES 5 | #define HAVE_UNSIGNED_CHAR 6 | #define HAVE_UNSIGNED_SHORT 7 | /* #define void char */ 8 | /* #define const */ 9 | #undef CHAR_IS_UNSIGNED 10 | #define HAVE_STDDEF_H 11 | #define HAVE_STDLIB_H 12 | #undef NEED_BSD_STRINGS 13 | #undef NEED_SYS_TYPES_H 14 | #undef NEED_FAR_POINTERS /* we presume a 32-bit flat memory model */ 15 | #undef NEED_SHORT_EXTERNAL_NAMES 16 | #undef INCOMPLETE_TYPES_BROKEN 17 | 18 | /* changes by fry, boolean is defined in acu.h, but don't want to include 19 | it otherwise it requires a rebuild of all 50 files whenever acu.h is touched */ 20 | 21 | /* Define "boolean" as unsigned char, not int, per Windows custom */ 22 | //#ifndef __RPCNDR_H__ /* don't conflict if rpcndr.h already read */ 23 | //typedef unsigned char boolean; 24 | //#endif 25 | //#include "acu.h" 26 | #ifndef boolean 27 | //typedef int boolean; 28 | typedef unsigned char boolean; 29 | #endif 30 | #define HAVE_BOOLEAN /* prevent jmorecfg.h from redefining it */ 31 | 32 | 33 | #ifdef JPEG_INTERNALS 34 | 35 | #undef RIGHT_SHIFT_IS_UNSIGNED 36 | 37 | #endif /* JPEG_INTERNALS */ 38 | 39 | #ifdef JPEG_CJPEG_DJPEG 40 | 41 | #define BMP_SUPPORTED /* BMP image file format */ 42 | #define GIF_SUPPORTED /* GIF image file format */ 43 | #define PPM_SUPPORTED /* PBMPLUS PPM/PGM image file format */ 44 | #undef RLE_SUPPORTED /* Utah RLE image file format */ 45 | #define TARGA_SUPPORTED /* Targa image file format */ 46 | 47 | #define TWO_FILE_COMMANDLINE /* optional */ 48 | #define USE_SETMODE /* Microsoft has setmode() */ 49 | #undef NEED_SIGNAL_CATCHER 50 | #undef DONT_USE_B_MODE 51 | #undef PROGRESS_REPORT /* optional */ 52 | 53 | #endif /* JPEG_CJPEG_DJPEG */ 54 | -------------------------------------------------------------------------------- /windows/jpeg/jdatadst.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jdatadst.c 3 | * 4 | * Copyright (C) 1994-1996, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains compression data destination routines for the case of 9 | * emitting JPEG data to a file (or any stdio stream). While these routines 10 | * are sufficient for most applications, some will want to use a different 11 | * destination manager. 12 | * IMPORTANT: we assume that fwrite() will correctly transcribe an array of 13 | * JOCTETs into 8-bit-wide elements on external storage. If char is wider 14 | * than 8 bits on your machine, you may need to do some tweaking. 15 | */ 16 | 17 | /* this is not a core library module, so it doesn't define JPEG_INTERNALS */ 18 | #include "jinclude.h" 19 | #include "jpeglib.h" 20 | #include "jerror.h" 21 | 22 | 23 | /* Expanded data destination object for stdio output */ 24 | 25 | typedef struct { 26 | struct jpeg_destination_mgr pub; /* public fields */ 27 | 28 | FILE * outfile; /* target stream */ 29 | JOCTET * buffer; /* start of buffer */ 30 | } my_destination_mgr; 31 | 32 | typedef my_destination_mgr * my_dest_ptr; 33 | 34 | #define OUTPUT_BUF_SIZE 4096 /* choose an efficiently fwrite'able size */ 35 | 36 | 37 | /* 38 | * Initialize destination --- called by jpeg_start_compress 39 | * before any data is actually written. 40 | */ 41 | 42 | METHODDEF(void) 43 | init_destination (j_compress_ptr cinfo) 44 | { 45 | my_dest_ptr dest = (my_dest_ptr) cinfo->dest; 46 | 47 | /* Allocate the output buffer --- it will be released when done with image */ 48 | dest->buffer = (JOCTET *) 49 | (*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_IMAGE, 50 | OUTPUT_BUF_SIZE * SIZEOF(JOCTET)); 51 | 52 | dest->pub.next_output_byte = dest->buffer; 53 | dest->pub.free_in_buffer = OUTPUT_BUF_SIZE; 54 | } 55 | 56 | 57 | /* 58 | * Empty the output buffer --- called whenever buffer fills up. 59 | * 60 | * In typical applications, this should write the entire output buffer 61 | * (ignoring the current state of next_output_byte & free_in_buffer), 62 | * reset the pointer & count to the start of the buffer, and return TRUE 63 | * indicating that the buffer has been dumped. 64 | * 65 | * In applications that need to be able to suspend compression due to output 66 | * overrun, a FALSE return indicates that the buffer cannot be emptied now. 67 | * In this situation, the compressor will return to its caller (possibly with 68 | * an indication that it has not accepted all the supplied scanlines). The 69 | * application should resume compression after it has made more room in the 70 | * output buffer. Note that there are substantial restrictions on the use of 71 | * suspension --- see the documentation. 72 | * 73 | * When suspending, the compressor will back up to a convenient restart point 74 | * (typically the start of the current MCU). next_output_byte & free_in_buffer 75 | * indicate where the restart point will be if the current call returns FALSE. 76 | * Data beyond this point will be regenerated after resumption, so do not 77 | * write it out when emptying the buffer externally. 78 | */ 79 | 80 | METHODDEF(boolean) 81 | empty_output_buffer (j_compress_ptr cinfo) 82 | { 83 | my_dest_ptr dest = (my_dest_ptr) cinfo->dest; 84 | 85 | if (JFWRITE(dest->outfile, dest->buffer, OUTPUT_BUF_SIZE) != 86 | (size_t) OUTPUT_BUF_SIZE) 87 | ERREXIT(cinfo, JERR_FILE_WRITE); 88 | 89 | dest->pub.next_output_byte = dest->buffer; 90 | dest->pub.free_in_buffer = OUTPUT_BUF_SIZE; 91 | 92 | return TRUE; 93 | } 94 | 95 | 96 | /* 97 | * Terminate destination --- called by jpeg_finish_compress 98 | * after all data has been written. Usually needs to flush buffer. 99 | * 100 | * NB: *not* called by jpeg_abort or jpeg_destroy; surrounding 101 | * application must deal with any cleanup that should happen even 102 | * for error exit. 103 | */ 104 | 105 | METHODDEF(void) 106 | term_destination (j_compress_ptr cinfo) 107 | { 108 | my_dest_ptr dest = (my_dest_ptr) cinfo->dest; 109 | size_t datacount = OUTPUT_BUF_SIZE - dest->pub.free_in_buffer; 110 | 111 | /* Write any data remaining in the buffer */ 112 | if (datacount > 0) { 113 | if (JFWRITE(dest->outfile, dest->buffer, datacount) != datacount) 114 | ERREXIT(cinfo, JERR_FILE_WRITE); 115 | } 116 | fflush(dest->outfile); 117 | /* Make sure we wrote the output file OK */ 118 | if (ferror(dest->outfile)) 119 | ERREXIT(cinfo, JERR_FILE_WRITE); 120 | } 121 | 122 | 123 | /* 124 | * Prepare for output to a stdio stream. 125 | * The caller must have already opened the stream, and is responsible 126 | * for closing it after finishing compression. 127 | */ 128 | 129 | GLOBAL(void) 130 | jpeg_stdio_dest (j_compress_ptr cinfo, FILE * outfile) 131 | { 132 | my_dest_ptr dest; 133 | 134 | /* The destination object is made permanent so that multiple JPEG images 135 | * can be written to the same file without re-executing jpeg_stdio_dest. 136 | * This makes it dangerous to use this manager and a different destination 137 | * manager serially with the same JPEG object, because their private object 138 | * sizes may be different. Caveat programmer. 139 | */ 140 | if (cinfo->dest == NULL) { /* first time for this JPEG object? */ 141 | cinfo->dest = (struct jpeg_destination_mgr *) 142 | (*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_PERMANENT, 143 | SIZEOF(my_destination_mgr)); 144 | } 145 | 146 | dest = (my_dest_ptr) cinfo->dest; 147 | dest->pub.init_destination = init_destination; 148 | dest->pub.empty_output_buffer = empty_output_buffer; 149 | dest->pub.term_destination = term_destination; 150 | dest->outfile = outfile; 151 | } 152 | -------------------------------------------------------------------------------- /windows/jpeg/jdatasrc.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jdatasrc.c 3 | * 4 | * Copyright (C) 1994-1996, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains decompression data source routines for the case of 9 | * reading JPEG data from a file (or any stdio stream). While these routines 10 | * are sufficient for most applications, some will want to use a different 11 | * source manager. 12 | * IMPORTANT: we assume that fread() will correctly transcribe an array of 13 | * JOCTETs from 8-bit-wide elements on external storage. If char is wider 14 | * than 8 bits on your machine, you may need to do some tweaking. 15 | */ 16 | 17 | /* this is not a core library module, so it doesn't define JPEG_INTERNALS */ 18 | #include "jinclude.h" 19 | #include "jpeglib.h" 20 | #include "jerror.h" 21 | 22 | 23 | /* Expanded data source object for stdio input */ 24 | 25 | typedef struct { 26 | struct jpeg_source_mgr pub; /* public fields */ 27 | 28 | FILE * infile; /* source stream */ 29 | JOCTET * buffer; /* start of buffer */ 30 | boolean start_of_file; /* have we gotten any data yet? */ 31 | } my_source_mgr; 32 | 33 | typedef my_source_mgr * my_src_ptr; 34 | 35 | #define INPUT_BUF_SIZE 4096 /* choose an efficiently fread'able size */ 36 | 37 | 38 | /* 39 | * Initialize source --- called by jpeg_read_header 40 | * before any data is actually read. 41 | */ 42 | 43 | METHODDEF(void) 44 | init_source (j_decompress_ptr cinfo) 45 | { 46 | my_src_ptr src = (my_src_ptr) cinfo->src; 47 | 48 | /* We reset the empty-input-file flag for each image, 49 | * but we don't clear the input buffer. 50 | * This is correct behavior for reading a series of images from one source. 51 | */ 52 | src->start_of_file = TRUE; 53 | } 54 | 55 | 56 | /* 57 | * Fill the input buffer --- called whenever buffer is emptied. 58 | * 59 | * In typical applications, this should read fresh data into the buffer 60 | * (ignoring the current state of next_input_byte & bytes_in_buffer), 61 | * reset the pointer & count to the start of the buffer, and return TRUE 62 | * indicating that the buffer has been reloaded. It is not necessary to 63 | * fill the buffer entirely, only to obtain at least one more byte. 64 | * 65 | * There is no such thing as an EOF return. If the end of the file has been 66 | * reached, the routine has a choice of ERREXIT() or inserting fake data into 67 | * the buffer. In most cases, generating a warning message and inserting a 68 | * fake EOI marker is the best course of action --- this will allow the 69 | * decompressor to output however much of the image is there. However, 70 | * the resulting error message is misleading if the real problem is an empty 71 | * input file, so we handle that case specially. 72 | * 73 | * In applications that need to be able to suspend compression due to input 74 | * not being available yet, a FALSE return indicates that no more data can be 75 | * obtained right now, but more may be forthcoming later. In this situation, 76 | * the decompressor will return to its caller (with an indication of the 77 | * number of scanlines it has read, if any). The application should resume 78 | * decompression after it has loaded more data into the input buffer. Note 79 | * that there are substantial restrictions on the use of suspension --- see 80 | * the documentation. 81 | * 82 | * When suspending, the decompressor will back up to a convenient restart point 83 | * (typically the start of the current MCU). next_input_byte & bytes_in_buffer 84 | * indicate where the restart point will be if the current call returns FALSE. 85 | * Data beyond this point must be rescanned after resumption, so move it to 86 | * the front of the buffer rather than discarding it. 87 | */ 88 | 89 | METHODDEF(boolean) 90 | fill_input_buffer (j_decompress_ptr cinfo) 91 | { 92 | my_src_ptr src = (my_src_ptr) cinfo->src; 93 | size_t nbytes; 94 | 95 | nbytes = JFREAD(src->infile, src->buffer, INPUT_BUF_SIZE); 96 | 97 | if (nbytes <= 0) { 98 | if (src->start_of_file) /* Treat empty input file as fatal error */ 99 | ERREXIT(cinfo, JERR_INPUT_EMPTY); 100 | WARNMS(cinfo, JWRN_JPEG_EOF); 101 | /* Insert a fake EOI marker */ 102 | src->buffer[0] = (JOCTET) 0xFF; 103 | src->buffer[1] = (JOCTET) JPEG_EOI; 104 | nbytes = 2; 105 | } 106 | 107 | src->pub.next_input_byte = src->buffer; 108 | src->pub.bytes_in_buffer = nbytes; 109 | src->start_of_file = FALSE; 110 | 111 | return TRUE; 112 | } 113 | 114 | 115 | /* 116 | * Skip data --- used to skip over a potentially large amount of 117 | * uninteresting data (such as an APPn marker). 118 | * 119 | * Writers of suspendable-input applications must note that skip_input_data 120 | * is not granted the right to give a suspension return. If the skip extends 121 | * beyond the data currently in the buffer, the buffer can be marked empty so 122 | * that the next read will cause a fill_input_buffer call that can suspend. 123 | * Arranging for additional bytes to be discarded before reloading the input 124 | * buffer is the application writer's problem. 125 | */ 126 | 127 | METHODDEF(void) 128 | skip_input_data (j_decompress_ptr cinfo, long num_bytes) 129 | { 130 | my_src_ptr src = (my_src_ptr) cinfo->src; 131 | 132 | /* Just a dumb implementation for now. Could use fseek() except 133 | * it doesn't work on pipes. Not clear that being smart is worth 134 | * any trouble anyway --- large skips are infrequent. 135 | */ 136 | if (num_bytes > 0) { 137 | while (num_bytes > (long) src->pub.bytes_in_buffer) { 138 | num_bytes -= (long) src->pub.bytes_in_buffer; 139 | (void) fill_input_buffer(cinfo); 140 | /* note we assume that fill_input_buffer will never return FALSE, 141 | * so suspension need not be handled. 142 | */ 143 | } 144 | src->pub.next_input_byte += (size_t) num_bytes; 145 | src->pub.bytes_in_buffer -= (size_t) num_bytes; 146 | } 147 | } 148 | 149 | 150 | /* 151 | * An additional method that can be provided by data source modules is the 152 | * resync_to_restart method for error recovery in the presence of RST markers. 153 | * For the moment, this source module just uses the default resync method 154 | * provided by the JPEG library. That method assumes that no backtracking 155 | * is possible. 156 | */ 157 | 158 | 159 | /* 160 | * Terminate source --- called by jpeg_finish_decompress 161 | * after all data has been read. Often a no-op. 162 | * 163 | * NB: *not* called by jpeg_abort or jpeg_destroy; surrounding 164 | * application must deal with any cleanup that should happen even 165 | * for error exit. 166 | */ 167 | 168 | METHODDEF(void) 169 | term_source (j_decompress_ptr cinfo) 170 | { 171 | /* no work necessary here */ 172 | } 173 | 174 | 175 | /* 176 | * Prepare for input from a stdio stream. 177 | * The caller must have already opened the stream, and is responsible 178 | * for closing it after finishing decompression. 179 | */ 180 | 181 | GLOBAL(void) 182 | jpeg_stdio_src (j_decompress_ptr cinfo, FILE * infile) 183 | { 184 | my_src_ptr src; 185 | 186 | /* The source object and input buffer are made permanent so that a series 187 | * of JPEG images can be read from the same file by calling jpeg_stdio_src 188 | * only before the first one. (If we discarded the buffer at the end of 189 | * one image, we'd likely lose the start of the next one.) 190 | * This makes it unsafe to use this manager and a different source 191 | * manager serially with the same JPEG object. Caveat programmer. 192 | */ 193 | if (cinfo->src == NULL) { /* first time for this JPEG object? */ 194 | cinfo->src = (struct jpeg_source_mgr *) 195 | (*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_PERMANENT, 196 | SIZEOF(my_source_mgr)); 197 | src = (my_src_ptr) cinfo->src; 198 | src->buffer = (JOCTET *) 199 | (*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_PERMANENT, 200 | INPUT_BUF_SIZE * SIZEOF(JOCTET)); 201 | } 202 | 203 | src = (my_src_ptr) cinfo->src; 204 | src->pub.init_source = init_source; 205 | src->pub.fill_input_buffer = fill_input_buffer; 206 | src->pub.skip_input_data = skip_input_data; 207 | src->pub.resync_to_restart = jpeg_resync_to_restart; /* use default method */ 208 | src->pub.term_source = term_source; 209 | src->infile = infile; 210 | src->pub.bytes_in_buffer = 0; /* forces fill_input_buffer on first read */ 211 | src->pub.next_input_byte = NULL; /* until buffer loaded */ 212 | } 213 | -------------------------------------------------------------------------------- /windows/jpeg/jdct.h: -------------------------------------------------------------------------------- 1 | /* 2 | * jdct.h 3 | * 4 | * Copyright (C) 1994-1996, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This include file contains common declarations for the forward and 9 | * inverse DCT modules. These declarations are private to the DCT managers 10 | * (jcdctmgr.c, jddctmgr.c) and the individual DCT algorithms. 11 | * The individual DCT algorithms are kept in separate files to ease 12 | * machine-dependent tuning (e.g., assembly coding). 13 | */ 14 | 15 | 16 | /* 17 | * A forward DCT routine is given a pointer to a work area of type DCTELEM[]; 18 | * the DCT is to be performed in-place in that buffer. Type DCTELEM is int 19 | * for 8-bit samples, INT32 for 12-bit samples. (NOTE: Floating-point DCT 20 | * implementations use an array of type FAST_FLOAT, instead.) 21 | * The DCT inputs are expected to be signed (range +-CENTERJSAMPLE). 22 | * The DCT outputs are returned scaled up by a factor of 8; they therefore 23 | * have a range of +-8K for 8-bit data, +-128K for 12-bit data. This 24 | * convention improves accuracy in integer implementations and saves some 25 | * work in floating-point ones. 26 | * Quantization of the output coefficients is done by jcdctmgr.c. 27 | */ 28 | 29 | #if BITS_IN_JSAMPLE == 8 30 | typedef int DCTELEM; /* 16 or 32 bits is fine */ 31 | #else 32 | typedef INT32 DCTELEM; /* must have 32 bits */ 33 | #endif 34 | 35 | typedef JMETHOD(void, forward_DCT_method_ptr, (DCTELEM * data)); 36 | typedef JMETHOD(void, float_DCT_method_ptr, (FAST_FLOAT * data)); 37 | 38 | 39 | /* 40 | * An inverse DCT routine is given a pointer to the input JBLOCK and a pointer 41 | * to an output sample array. The routine must dequantize the input data as 42 | * well as perform the IDCT; for dequantization, it uses the multiplier table 43 | * pointed to by compptr->dct_table. The output data is to be placed into the 44 | * sample array starting at a specified column. (Any row offset needed will 45 | * be applied to the array pointer before it is passed to the IDCT code.) 46 | * Note that the number of samples emitted by the IDCT routine is 47 | * DCT_scaled_size * DCT_scaled_size. 48 | */ 49 | 50 | /* typedef inverse_DCT_method_ptr is declared in jpegint.h */ 51 | 52 | /* 53 | * Each IDCT routine has its own ideas about the best dct_table element type. 54 | */ 55 | 56 | typedef MULTIPLIER ISLOW_MULT_TYPE; /* short or int, whichever is faster */ 57 | #if BITS_IN_JSAMPLE == 8 58 | typedef MULTIPLIER IFAST_MULT_TYPE; /* 16 bits is OK, use short if faster */ 59 | #define IFAST_SCALE_BITS 2 /* fractional bits in scale factors */ 60 | #else 61 | typedef INT32 IFAST_MULT_TYPE; /* need 32 bits for scaled quantizers */ 62 | #define IFAST_SCALE_BITS 13 /* fractional bits in scale factors */ 63 | #endif 64 | typedef FAST_FLOAT FLOAT_MULT_TYPE; /* preferred floating type */ 65 | 66 | 67 | /* 68 | * Each IDCT routine is responsible for range-limiting its results and 69 | * converting them to unsigned form (0..MAXJSAMPLE). The raw outputs could 70 | * be quite far out of range if the input data is corrupt, so a bulletproof 71 | * range-limiting step is required. We use a mask-and-table-lookup method 72 | * to do the combined operations quickly. See the comments with 73 | * prepare_range_limit_table (in jdmaster.c) for more info. 74 | */ 75 | 76 | #define IDCT_range_limit(cinfo) ((cinfo)->sample_range_limit + CENTERJSAMPLE) 77 | 78 | #define RANGE_MASK (MAXJSAMPLE * 4 + 3) /* 2 bits wider than legal samples */ 79 | 80 | 81 | /* Short forms of external names for systems with brain-damaged linkers. */ 82 | 83 | #ifdef NEED_SHORT_EXTERNAL_NAMES 84 | #define jpeg_fdct_islow jFDislow 85 | #define jpeg_fdct_ifast jFDifast 86 | #define jpeg_fdct_float jFDfloat 87 | #define jpeg_idct_islow jRDislow 88 | #define jpeg_idct_ifast jRDifast 89 | #define jpeg_idct_float jRDfloat 90 | #define jpeg_idct_4x4 jRD4x4 91 | #define jpeg_idct_2x2 jRD2x2 92 | #define jpeg_idct_1x1 jRD1x1 93 | #endif /* NEED_SHORT_EXTERNAL_NAMES */ 94 | 95 | /* Extern declarations for the forward and inverse DCT routines. */ 96 | 97 | EXTERN(void) jpeg_fdct_islow JPP((DCTELEM * data)); 98 | EXTERN(void) jpeg_fdct_ifast JPP((DCTELEM * data)); 99 | EXTERN(void) jpeg_fdct_float JPP((FAST_FLOAT * data)); 100 | 101 | EXTERN(void) jpeg_idct_islow 102 | JPP((j_decompress_ptr cinfo, jpeg_component_info * compptr, 103 | JCOEFPTR coef_block, JSAMPARRAY output_buf, JDIMENSION output_col)); 104 | EXTERN(void) jpeg_idct_ifast 105 | JPP((j_decompress_ptr cinfo, jpeg_component_info * compptr, 106 | JCOEFPTR coef_block, JSAMPARRAY output_buf, JDIMENSION output_col)); 107 | EXTERN(void) jpeg_idct_float 108 | JPP((j_decompress_ptr cinfo, jpeg_component_info * compptr, 109 | JCOEFPTR coef_block, JSAMPARRAY output_buf, JDIMENSION output_col)); 110 | EXTERN(void) jpeg_idct_4x4 111 | JPP((j_decompress_ptr cinfo, jpeg_component_info * compptr, 112 | JCOEFPTR coef_block, JSAMPARRAY output_buf, JDIMENSION output_col)); 113 | EXTERN(void) jpeg_idct_2x2 114 | JPP((j_decompress_ptr cinfo, jpeg_component_info * compptr, 115 | JCOEFPTR coef_block, JSAMPARRAY output_buf, JDIMENSION output_col)); 116 | EXTERN(void) jpeg_idct_1x1 117 | JPP((j_decompress_ptr cinfo, jpeg_component_info * compptr, 118 | JCOEFPTR coef_block, JSAMPARRAY output_buf, JDIMENSION output_col)); 119 | 120 | 121 | /* 122 | * Macros for handling fixed-point arithmetic; these are used by many 123 | * but not all of the DCT/IDCT modules. 124 | * 125 | * All values are expected to be of type INT32. 126 | * Fractional constants are scaled left by CONST_BITS bits. 127 | * CONST_BITS is defined within each module using these macros, 128 | * and may differ from one module to the next. 129 | */ 130 | 131 | #define ONE ((INT32) 1) 132 | #define CONST_SCALE (ONE << CONST_BITS) 133 | 134 | /* Convert a positive real constant to an integer scaled by CONST_SCALE. 135 | * Caution: some C compilers fail to reduce "FIX(constant)" at compile time, 136 | * thus causing a lot of useless floating-point operations at run time. 137 | */ 138 | 139 | #define FIX(x) ((INT32) ((x) * CONST_SCALE + 0.5)) 140 | 141 | /* Descale and correctly round an INT32 value that's scaled by N bits. 142 | * We assume RIGHT_SHIFT rounds towards minus infinity, so adding 143 | * the fudge factor is correct for either sign of X. 144 | */ 145 | 146 | #define DESCALE(x,n) RIGHT_SHIFT((x) + (ONE << ((n)-1)), n) 147 | 148 | /* Multiply an INT32 variable by an INT32 constant to yield an INT32 result. 149 | * This macro is used only when the two inputs will actually be no more than 150 | * 16 bits wide, so that a 16x16->32 bit multiply can be used instead of a 151 | * full 32x32 multiply. This provides a useful speedup on many machines. 152 | * Unfortunately there is no way to specify a 16x16->32 multiply portably 153 | * in C, but some C compilers will do the right thing if you provide the 154 | * correct combination of casts. 155 | */ 156 | 157 | #ifdef SHORTxSHORT_32 /* may work if 'int' is 32 bits */ 158 | #define MULTIPLY16C16(var,const) (((INT16) (var)) * ((INT16) (const))) 159 | #endif 160 | #ifdef SHORTxLCONST_32 /* known to work with Microsoft C 6.0 */ 161 | #define MULTIPLY16C16(var,const) (((INT16) (var)) * ((INT32) (const))) 162 | #endif 163 | 164 | #ifndef MULTIPLY16C16 /* default definition */ 165 | #define MULTIPLY16C16(var,const) ((var) * (const)) 166 | #endif 167 | 168 | /* Same except both inputs are variables. */ 169 | 170 | #ifdef SHORTxSHORT_32 /* may work if 'int' is 32 bits */ 171 | #define MULTIPLY16V16(var1,var2) (((INT16) (var1)) * ((INT16) (var2))) 172 | #endif 173 | 174 | #ifndef MULTIPLY16V16 /* default definition */ 175 | #define MULTIPLY16V16(var1,var2) ((var1) * (var2)) 176 | #endif 177 | -------------------------------------------------------------------------------- /windows/jpeg/jdhuff.h: -------------------------------------------------------------------------------- 1 | /* 2 | * jdhuff.h 3 | * 4 | * Copyright (C) 1991-1997, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains declarations for Huffman entropy decoding routines 9 | * that are shared between the sequential decoder (jdhuff.c) and the 10 | * progressive decoder (jdphuff.c). No other modules need to see these. 11 | */ 12 | 13 | /* Short forms of external names for systems with brain-damaged linkers. */ 14 | 15 | #ifdef NEED_SHORT_EXTERNAL_NAMES 16 | #define jpeg_make_d_derived_tbl jMkDDerived 17 | #define jpeg_fill_bit_buffer jFilBitBuf 18 | #define jpeg_huff_decode jHufDecode 19 | #endif /* NEED_SHORT_EXTERNAL_NAMES */ 20 | 21 | 22 | /* Derived data constructed for each Huffman table */ 23 | 24 | #define HUFF_LOOKAHEAD 8 /* # of bits of lookahead */ 25 | 26 | typedef struct { 27 | /* Basic tables: (element [0] of each array is unused) */ 28 | INT32 maxcode[18]; /* largest code of length k (-1 if none) */ 29 | /* (maxcode[17] is a sentinel to ensure jpeg_huff_decode terminates) */ 30 | INT32 valoffset[17]; /* huffval[] offset for codes of length k */ 31 | /* valoffset[k] = huffval[] index of 1st symbol of code length k, less 32 | * the smallest code of length k; so given a code of length k, the 33 | * corresponding symbol is huffval[code + valoffset[k]] 34 | */ 35 | 36 | /* Link to public Huffman table (needed only in jpeg_huff_decode) */ 37 | JHUFF_TBL *pub; 38 | 39 | /* Lookahead tables: indexed by the next HUFF_LOOKAHEAD bits of 40 | * the input data stream. If the next Huffman code is no more 41 | * than HUFF_LOOKAHEAD bits long, we can obtain its length and 42 | * the corresponding symbol directly from these tables. 43 | */ 44 | int look_nbits[1< 32 bits on your machine, and shifting/masking longs is 76 | * reasonably fast, making bit_buf_type be long and setting BIT_BUF_SIZE 77 | * appropriately should be a win. Unfortunately we can't define the size 78 | * with something like #define BIT_BUF_SIZE (sizeof(bit_buf_type)*8) 79 | * because not all machines measure sizeof in 8-bit bytes. 80 | */ 81 | 82 | typedef struct { /* Bitreading state saved across MCUs */ 83 | bit_buf_type get_buffer; /* current bit-extraction buffer */ 84 | int bits_left; /* # of unused bits in it */ 85 | } bitread_perm_state; 86 | 87 | typedef struct { /* Bitreading working state within an MCU */ 88 | /* Current data source location */ 89 | /* We need a copy, rather than munging the original, in case of suspension */ 90 | const JOCTET * next_input_byte; /* => next byte to read from source */ 91 | size_t bytes_in_buffer; /* # of bytes remaining in source buffer */ 92 | /* Bit input buffer --- note these values are kept in register variables, 93 | * not in this struct, inside the inner loops. 94 | */ 95 | bit_buf_type get_buffer; /* current bit-extraction buffer */ 96 | int bits_left; /* # of unused bits in it */ 97 | /* Pointer needed by jpeg_fill_bit_buffer. */ 98 | j_decompress_ptr cinfo; /* back link to decompress master record */ 99 | } bitread_working_state; 100 | 101 | /* Macros to declare and load/save bitread local variables. */ 102 | #define BITREAD_STATE_VARS \ 103 | register bit_buf_type get_buffer; \ 104 | register int bits_left; \ 105 | bitread_working_state br_state 106 | 107 | #define BITREAD_LOAD_STATE(cinfop,permstate) \ 108 | br_state.cinfo = cinfop; \ 109 | br_state.next_input_byte = cinfop->src->next_input_byte; \ 110 | br_state.bytes_in_buffer = cinfop->src->bytes_in_buffer; \ 111 | get_buffer = permstate.get_buffer; \ 112 | bits_left = permstate.bits_left; 113 | 114 | #define BITREAD_SAVE_STATE(cinfop,permstate) \ 115 | cinfop->src->next_input_byte = br_state.next_input_byte; \ 116 | cinfop->src->bytes_in_buffer = br_state.bytes_in_buffer; \ 117 | permstate.get_buffer = get_buffer; \ 118 | permstate.bits_left = bits_left 119 | 120 | /* 121 | * These macros provide the in-line portion of bit fetching. 122 | * Use CHECK_BIT_BUFFER to ensure there are N bits in get_buffer 123 | * before using GET_BITS, PEEK_BITS, or DROP_BITS. 124 | * The variables get_buffer and bits_left are assumed to be locals, 125 | * but the state struct might not be (jpeg_huff_decode needs this). 126 | * CHECK_BIT_BUFFER(state,n,action); 127 | * Ensure there are N bits in get_buffer; if suspend, take action. 128 | * val = GET_BITS(n); 129 | * Fetch next N bits. 130 | * val = PEEK_BITS(n); 131 | * Fetch next N bits without removing them from the buffer. 132 | * DROP_BITS(n); 133 | * Discard next N bits. 134 | * The value N should be a simple variable, not an expression, because it 135 | * is evaluated multiple times. 136 | */ 137 | 138 | #define CHECK_BIT_BUFFER(state,nbits,action) \ 139 | { if (bits_left < (nbits)) { \ 140 | if (! jpeg_fill_bit_buffer(&(state),get_buffer,bits_left,nbits)) \ 141 | { action; } \ 142 | get_buffer = (state).get_buffer; bits_left = (state).bits_left; } } 143 | 144 | #define GET_BITS(nbits) \ 145 | (((int) (get_buffer >> (bits_left -= (nbits)))) & ((1<<(nbits))-1)) 146 | 147 | #define PEEK_BITS(nbits) \ 148 | (((int) (get_buffer >> (bits_left - (nbits)))) & ((1<<(nbits))-1)) 149 | 150 | #define DROP_BITS(nbits) \ 151 | (bits_left -= (nbits)) 152 | 153 | /* Load up the bit buffer to a depth of at least nbits */ 154 | EXTERN(boolean) jpeg_fill_bit_buffer 155 | JPP((bitread_working_state * state, register bit_buf_type get_buffer, 156 | register int bits_left, int nbits)); 157 | 158 | 159 | /* 160 | * Code for extracting next Huffman-coded symbol from input bit stream. 161 | * Again, this is time-critical and we make the main paths be macros. 162 | * 163 | * We use a lookahead table to process codes of up to HUFF_LOOKAHEAD bits 164 | * without looping. Usually, more than 95% of the Huffman codes will be 8 165 | * or fewer bits long. The few overlength codes are handled with a loop, 166 | * which need not be inline code. 167 | * 168 | * Notes about the HUFF_DECODE macro: 169 | * 1. Near the end of the data segment, we may fail to get enough bits 170 | * for a lookahead. In that case, we do it the hard way. 171 | * 2. If the lookahead table contains no entry, the next code must be 172 | * more than HUFF_LOOKAHEAD bits long. 173 | * 3. jpeg_huff_decode returns -1 if forced to suspend. 174 | */ 175 | 176 | #define HUFF_DECODE(result,state,htbl,failaction,slowlabel) \ 177 | { register int nb, look; \ 178 | if (bits_left < HUFF_LOOKAHEAD) { \ 179 | if (! jpeg_fill_bit_buffer(&state,get_buffer,bits_left, 0)) {failaction;} \ 180 | get_buffer = state.get_buffer; bits_left = state.bits_left; \ 181 | if (bits_left < HUFF_LOOKAHEAD) { \ 182 | nb = 1; goto slowlabel; \ 183 | } \ 184 | } \ 185 | look = PEEK_BITS(HUFF_LOOKAHEAD); \ 186 | if ((nb = htbl->look_nbits[look]) != 0) { \ 187 | DROP_BITS(nb); \ 188 | result = htbl->look_sym[look]; \ 189 | } else { \ 190 | nb = HUFF_LOOKAHEAD+1; \ 191 | slowlabel: \ 192 | if ((result=jpeg_huff_decode(&state,get_buffer,bits_left,htbl,nb)) < 0) \ 193 | { failaction; } \ 194 | get_buffer = state.get_buffer; bits_left = state.bits_left; \ 195 | } \ 196 | } 197 | 198 | /* Out-of-line case for Huffman code fetching */ 199 | EXTERN(int) jpeg_huff_decode 200 | JPP((bitread_working_state * state, register bit_buf_type get_buffer, 201 | register int bits_left, d_derived_tbl * htbl, int min_bits)); 202 | -------------------------------------------------------------------------------- /windows/jpeg/jdtrans.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jdtrans.c 3 | * 4 | * Copyright (C) 1995-1997, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains library routines for transcoding decompression, 9 | * that is, reading raw DCT coefficient arrays from an input JPEG file. 10 | * The routines in jdapimin.c will also be needed by a transcoder. 11 | */ 12 | 13 | #define JPEG_INTERNALS 14 | #include "jinclude.h" 15 | #include "jpeglib.h" 16 | 17 | 18 | /* Forward declarations */ 19 | LOCAL(void) transdecode_master_selection JPP((j_decompress_ptr cinfo)); 20 | 21 | 22 | /* 23 | * Read the coefficient arrays from a JPEG file. 24 | * jpeg_read_header must be completed before calling this. 25 | * 26 | * The entire image is read into a set of virtual coefficient-block arrays, 27 | * one per component. The return value is a pointer to the array of 28 | * virtual-array descriptors. These can be manipulated directly via the 29 | * JPEG memory manager, or handed off to jpeg_write_coefficients(). 30 | * To release the memory occupied by the virtual arrays, call 31 | * jpeg_finish_decompress() when done with the data. 32 | * 33 | * An alternative usage is to simply obtain access to the coefficient arrays 34 | * during a buffered-image-mode decompression operation. This is allowed 35 | * after any jpeg_finish_output() call. The arrays can be accessed until 36 | * jpeg_finish_decompress() is called. (Note that any call to the library 37 | * may reposition the arrays, so don't rely on access_virt_barray() results 38 | * to stay valid across library calls.) 39 | * 40 | * Returns NULL if suspended. This case need be checked only if 41 | * a suspending data source is used. 42 | */ 43 | 44 | GLOBAL(jvirt_barray_ptr *) 45 | jpeg_read_coefficients (j_decompress_ptr cinfo) 46 | { 47 | if (cinfo->global_state == DSTATE_READY) { 48 | /* First call: initialize active modules */ 49 | transdecode_master_selection(cinfo); 50 | cinfo->global_state = DSTATE_RDCOEFS; 51 | } 52 | if (cinfo->global_state == DSTATE_RDCOEFS) { 53 | /* Absorb whole file into the coef buffer */ 54 | for (;;) { 55 | int retcode; 56 | /* Call progress monitor hook if present */ 57 | if (cinfo->progress != NULL) 58 | (*cinfo->progress->progress_monitor) ((j_common_ptr) cinfo); 59 | /* Absorb some more input */ 60 | retcode = (*cinfo->inputctl->consume_input) (cinfo); 61 | if (retcode == JPEG_SUSPENDED) 62 | return NULL; 63 | if (retcode == JPEG_REACHED_EOI) 64 | break; 65 | /* Advance progress counter if appropriate */ 66 | if (cinfo->progress != NULL && 67 | (retcode == JPEG_ROW_COMPLETED || retcode == JPEG_REACHED_SOS)) { 68 | if (++cinfo->progress->pass_counter >= cinfo->progress->pass_limit) { 69 | /* startup underestimated number of scans; ratchet up one scan */ 70 | cinfo->progress->pass_limit += (long) cinfo->total_iMCU_rows; 71 | } 72 | } 73 | } 74 | /* Set state so that jpeg_finish_decompress does the right thing */ 75 | cinfo->global_state = DSTATE_STOPPING; 76 | } 77 | /* At this point we should be in state DSTATE_STOPPING if being used 78 | * standalone, or in state DSTATE_BUFIMAGE if being invoked to get access 79 | * to the coefficients during a full buffered-image-mode decompression. 80 | */ 81 | if ((cinfo->global_state == DSTATE_STOPPING || 82 | cinfo->global_state == DSTATE_BUFIMAGE) && cinfo->buffered_image) { 83 | return cinfo->coef->coef_arrays; 84 | } 85 | /* Oops, improper usage */ 86 | ERREXIT1(cinfo, JERR_BAD_STATE, cinfo->global_state); 87 | return NULL; /* keep compiler happy */ 88 | } 89 | 90 | 91 | /* 92 | * Master selection of decompression modules for transcoding. 93 | * This substitutes for jdmaster.c's initialization of the full decompressor. 94 | */ 95 | 96 | LOCAL(void) 97 | transdecode_master_selection (j_decompress_ptr cinfo) 98 | { 99 | /* This is effectively a buffered-image operation. */ 100 | cinfo->buffered_image = TRUE; 101 | 102 | /* Entropy decoding: either Huffman or arithmetic coding. */ 103 | if (cinfo->arith_code) { 104 | ERREXIT(cinfo, JERR_ARITH_NOTIMPL); 105 | } else { 106 | if (cinfo->progressive_mode) { 107 | #ifdef D_PROGRESSIVE_SUPPORTED 108 | jinit_phuff_decoder(cinfo); 109 | #else 110 | ERREXIT(cinfo, JERR_NOT_COMPILED); 111 | #endif 112 | } else 113 | jinit_huff_decoder(cinfo); 114 | } 115 | 116 | /* Always get a full-image coefficient buffer. */ 117 | jinit_d_coef_controller(cinfo, TRUE); 118 | 119 | /* We can now tell the memory manager to allocate virtual arrays. */ 120 | (*cinfo->mem->realize_virt_arrays) ((j_common_ptr) cinfo); 121 | 122 | /* Initialize input side of decompressor to consume first scan. */ 123 | (*cinfo->inputctl->start_input_pass) (cinfo); 124 | 125 | /* Initialize progress monitoring. */ 126 | if (cinfo->progress != NULL) { 127 | int nscans; 128 | /* Estimate number of scans to set pass_limit. */ 129 | if (cinfo->progressive_mode) { 130 | /* Arbitrarily estimate 2 interleaved DC scans + 3 AC scans/component. */ 131 | nscans = 2 + 3 * cinfo->num_components; 132 | } else if (cinfo->inputctl->has_multiple_scans) { 133 | /* For a nonprogressive multiscan file, estimate 1 scan per component. */ 134 | nscans = cinfo->num_components; 135 | } else { 136 | nscans = 1; 137 | } 138 | cinfo->progress->pass_counter = 0L; 139 | cinfo->progress->pass_limit = (long) cinfo->total_iMCU_rows * nscans; 140 | cinfo->progress->completed_passes = 0; 141 | cinfo->progress->total_passes = 1; 142 | } 143 | } 144 | -------------------------------------------------------------------------------- /windows/jpeg/jerror.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jerror.c 3 | * 4 | * Copyright (C) 1991-1998, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains simple error-reporting and trace-message routines. 9 | * These are suitable for Unix-like systems and others where writing to 10 | * stderr is the right thing to do. Many applications will want to replace 11 | * some or all of these routines. 12 | * 13 | * If you define USE_WINDOWS_MESSAGEBOX in jconfig.h or in the makefile, 14 | * you get a Windows-specific hack to display error messages in a dialog box. 15 | * It ain't much, but it beats dropping error messages into the bit bucket, 16 | * which is what happens to output to stderr under most Windows C compilers. 17 | * 18 | * These routines are used by both the compression and decompression code. 19 | */ 20 | 21 | /* this is not a core library module, so it doesn't define JPEG_INTERNALS */ 22 | #include "jinclude.h" 23 | #include "jpeglib.h" 24 | #include "jversion.h" 25 | #include "jerror.h" 26 | 27 | #ifdef USE_WINDOWS_MESSAGEBOX 28 | #include 29 | #endif 30 | 31 | #ifndef EXIT_FAILURE /* define exit() codes if not provided */ 32 | #define EXIT_FAILURE 1 33 | #endif 34 | 35 | 36 | /* 37 | * Create the message string table. 38 | * We do this from the master message list in jerror.h by re-reading 39 | * jerror.h with a suitable definition for macro JMESSAGE. 40 | * The message table is made an external symbol just in case any applications 41 | * want to refer to it directly. 42 | */ 43 | 44 | #ifdef NEED_SHORT_EXTERNAL_NAMES 45 | #define jpeg_std_message_table jMsgTable 46 | #endif 47 | 48 | #define JMESSAGE(code,string) string , 49 | 50 | const char * const jpeg_std_message_table[] = { 51 | #include "jerror.h" 52 | NULL 53 | }; 54 | 55 | 56 | /* 57 | * Error exit handler: must not return to caller. 58 | * 59 | * Applications may override this if they want to get control back after 60 | * an error. Typically one would longjmp somewhere instead of exiting. 61 | * The setjmp buffer can be made a private field within an expanded error 62 | * handler object. Note that the info needed to generate an error message 63 | * is stored in the error object, so you can generate the message now or 64 | * later, at your convenience. 65 | * You should make sure that the JPEG object is cleaned up (with jpeg_abort 66 | * or jpeg_destroy) at some point. 67 | */ 68 | 69 | METHODDEF(void) 70 | error_exit (j_common_ptr cinfo) 71 | { 72 | /* Always display the message */ 73 | (*cinfo->err->output_message) (cinfo); 74 | 75 | /* Let the memory manager delete any temp files before we die */ 76 | jpeg_destroy(cinfo); 77 | 78 | exit(EXIT_FAILURE); 79 | } 80 | 81 | 82 | /* 83 | * Actual output of an error or trace message. 84 | * Applications may override this method to send JPEG messages somewhere 85 | * other than stderr. 86 | * 87 | * On Windows, printing to stderr is generally completely useless, 88 | * so we provide optional code to produce an error-dialog popup. 89 | * Most Windows applications will still prefer to override this routine, 90 | * but if they don't, it'll do something at least marginally useful. 91 | * 92 | * NOTE: to use the library in an environment that doesn't support the 93 | * C stdio library, you may have to delete the call to fprintf() entirely, 94 | * not just not use this routine. 95 | */ 96 | 97 | METHODDEF(void) 98 | output_message (j_common_ptr cinfo) 99 | { 100 | char buffer[JMSG_LENGTH_MAX]; 101 | 102 | /* Create the message */ 103 | (*cinfo->err->format_message) (cinfo, buffer); 104 | 105 | #ifdef USE_WINDOWS_MESSAGEBOX 106 | /* Display it in a message dialog box */ 107 | MessageBox(GetActiveWindow(), buffer, "JPEG Library Error", 108 | MB_OK | MB_ICONERROR); 109 | #else 110 | /* Send it to stderr, adding a newline */ 111 | fprintf(stderr, "%s\n", buffer); 112 | #endif 113 | } 114 | 115 | 116 | /* 117 | * Decide whether to emit a trace or warning message. 118 | * msg_level is one of: 119 | * -1: recoverable corrupt-data warning, may want to abort. 120 | * 0: important advisory messages (always display to user). 121 | * 1: first level of tracing detail. 122 | * 2,3,...: successively more detailed tracing messages. 123 | * An application might override this method if it wanted to abort on warnings 124 | * or change the policy about which messages to display. 125 | */ 126 | 127 | METHODDEF(void) 128 | emit_message (j_common_ptr cinfo, int msg_level) 129 | { 130 | struct jpeg_error_mgr * err = cinfo->err; 131 | 132 | if (msg_level < 0) { 133 | /* It's a warning message. Since corrupt files may generate many warnings, 134 | * the policy implemented here is to show only the first warning, 135 | * unless trace_level >= 3. 136 | */ 137 | if (err->num_warnings == 0 || err->trace_level >= 3) 138 | (*err->output_message) (cinfo); 139 | /* Always count warnings in num_warnings. */ 140 | err->num_warnings++; 141 | } else { 142 | /* It's a trace message. Show it if trace_level >= msg_level. */ 143 | if (err->trace_level >= msg_level) 144 | (*err->output_message) (cinfo); 145 | } 146 | } 147 | 148 | 149 | /* 150 | * Format a message string for the most recent JPEG error or message. 151 | * The message is stored into buffer, which should be at least JMSG_LENGTH_MAX 152 | * characters. Note that no '\n' character is added to the string. 153 | * Few applications should need to override this method. 154 | */ 155 | 156 | METHODDEF(void) 157 | format_message (j_common_ptr cinfo, char * buffer) 158 | { 159 | struct jpeg_error_mgr * err = cinfo->err; 160 | int msg_code = err->msg_code; 161 | const char * msgtext = NULL; 162 | const char * msgptr; 163 | char ch; 164 | boolean isstring; 165 | 166 | /* Look up message string in proper table */ 167 | if (msg_code > 0 && msg_code <= err->last_jpeg_message) { 168 | msgtext = err->jpeg_message_table[msg_code]; 169 | } else if (err->addon_message_table != NULL && 170 | msg_code >= err->first_addon_message && 171 | msg_code <= err->last_addon_message) { 172 | msgtext = err->addon_message_table[msg_code - err->first_addon_message]; 173 | } 174 | 175 | /* Defend against bogus message number */ 176 | if (msgtext == NULL) { 177 | err->msg_parm.i[0] = msg_code; 178 | msgtext = err->jpeg_message_table[0]; 179 | } 180 | 181 | /* Check for string parameter, as indicated by %s in the message text */ 182 | isstring = FALSE; 183 | msgptr = msgtext; 184 | while ((ch = *msgptr++) != '\0') { 185 | if (ch == '%') { 186 | if (*msgptr == 's') isstring = TRUE; 187 | break; 188 | } 189 | } 190 | 191 | /* Format the message into the passed buffer */ 192 | if (isstring) 193 | sprintf(buffer, msgtext, err->msg_parm.s); 194 | else 195 | sprintf(buffer, msgtext, 196 | err->msg_parm.i[0], err->msg_parm.i[1], 197 | err->msg_parm.i[2], err->msg_parm.i[3], 198 | err->msg_parm.i[4], err->msg_parm.i[5], 199 | err->msg_parm.i[6], err->msg_parm.i[7]); 200 | } 201 | 202 | 203 | /* 204 | * Reset error state variables at start of a new image. 205 | * This is called during compression startup to reset trace/error 206 | * processing to default state, without losing any application-specific 207 | * method pointers. An application might possibly want to override 208 | * this method if it has additional error processing state. 209 | */ 210 | 211 | METHODDEF(void) 212 | reset_error_mgr (j_common_ptr cinfo) 213 | { 214 | cinfo->err->num_warnings = 0; 215 | /* trace_level is not reset since it is an application-supplied parameter */ 216 | cinfo->err->msg_code = 0; /* may be useful as a flag for "no error" */ 217 | } 218 | 219 | 220 | /* 221 | * Fill in the standard error-handling methods in a jpeg_error_mgr object. 222 | * Typical call is: 223 | * struct jpeg_compress_struct cinfo; 224 | * struct jpeg_error_mgr err; 225 | * 226 | * cinfo.err = jpeg_std_error(&err); 227 | * after which the application may override some of the methods. 228 | */ 229 | 230 | GLOBAL(struct jpeg_error_mgr *) 231 | jpeg_std_error (struct jpeg_error_mgr * err) 232 | { 233 | err->error_exit = error_exit; 234 | err->emit_message = emit_message; 235 | err->output_message = output_message; 236 | err->format_message = format_message; 237 | err->reset_error_mgr = reset_error_mgr; 238 | 239 | err->trace_level = 0; /* default = no tracing */ 240 | err->num_warnings = 0; /* no warnings emitted yet */ 241 | err->msg_code = 0; /* may be useful as a flag for "no error" */ 242 | 243 | /* Initialize message table pointers */ 244 | err->jpeg_message_table = jpeg_std_message_table; 245 | err->last_jpeg_message = (int) JMSG_LASTMSGCODE - 1; 246 | 247 | err->addon_message_table = NULL; 248 | err->first_addon_message = 0; /* for safety */ 249 | err->last_addon_message = 0; 250 | 251 | return err; 252 | } 253 | -------------------------------------------------------------------------------- /windows/jpeg/jfdctflt.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jfdctflt.c 3 | * 4 | * Copyright (C) 1994-1996, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains a floating-point implementation of the 9 | * forward DCT (Discrete Cosine Transform). 10 | * 11 | * This implementation should be more accurate than either of the integer 12 | * DCT implementations. However, it may not give the same results on all 13 | * machines because of differences in roundoff behavior. Speed will depend 14 | * on the hardware's floating point capacity. 15 | * 16 | * A 2-D DCT can be done by 1-D DCT on each row followed by 1-D DCT 17 | * on each column. Direct algorithms are also available, but they are 18 | * much more complex and seem not to be any faster when reduced to code. 19 | * 20 | * This implementation is based on Arai, Agui, and Nakajima's algorithm for 21 | * scaled DCT. Their original paper (Trans. IEICE E-71(11):1095) is in 22 | * Japanese, but the algorithm is described in the Pennebaker & Mitchell 23 | * JPEG textbook (see REFERENCES section in file README). The following code 24 | * is based directly on figure 4-8 in P&M. 25 | * While an 8-point DCT cannot be done in less than 11 multiplies, it is 26 | * possible to arrange the computation so that many of the multiplies are 27 | * simple scalings of the final outputs. These multiplies can then be 28 | * folded into the multiplications or divisions by the JPEG quantization 29 | * table entries. The AA&N method leaves only 5 multiplies and 29 adds 30 | * to be done in the DCT itself. 31 | * The primary disadvantage of this method is that with a fixed-point 32 | * implementation, accuracy is lost due to imprecise representation of the 33 | * scaled quantization values. However, that problem does not arise if 34 | * we use floating point arithmetic. 35 | */ 36 | 37 | #define JPEG_INTERNALS 38 | #include "jinclude.h" 39 | #include "jpeglib.h" 40 | #include "jdct.h" /* Private declarations for DCT subsystem */ 41 | 42 | #ifdef DCT_FLOAT_SUPPORTED 43 | 44 | 45 | /* 46 | * This module is specialized to the case DCTSIZE = 8. 47 | */ 48 | 49 | #if DCTSIZE != 8 50 | Sorry, this code only copes with 8x8 DCTs. /* deliberate syntax err */ 51 | #endif 52 | 53 | 54 | /* 55 | * Perform the forward DCT on one block of samples. 56 | */ 57 | 58 | GLOBAL(void) 59 | jpeg_fdct_float (FAST_FLOAT * data) 60 | { 61 | FAST_FLOAT tmp0, tmp1, tmp2, tmp3, tmp4, tmp5, tmp6, tmp7; 62 | FAST_FLOAT tmp10, tmp11, tmp12, tmp13; 63 | FAST_FLOAT z1, z2, z3, z4, z5, z11, z13; 64 | FAST_FLOAT *dataptr; 65 | int ctr; 66 | 67 | /* Pass 1: process rows. */ 68 | 69 | dataptr = data; 70 | for (ctr = DCTSIZE-1; ctr >= 0; ctr--) { 71 | tmp0 = dataptr[0] + dataptr[7]; 72 | tmp7 = dataptr[0] - dataptr[7]; 73 | tmp1 = dataptr[1] + dataptr[6]; 74 | tmp6 = dataptr[1] - dataptr[6]; 75 | tmp2 = dataptr[2] + dataptr[5]; 76 | tmp5 = dataptr[2] - dataptr[5]; 77 | tmp3 = dataptr[3] + dataptr[4]; 78 | tmp4 = dataptr[3] - dataptr[4]; 79 | 80 | /* Even part */ 81 | 82 | tmp10 = tmp0 + tmp3; /* phase 2 */ 83 | tmp13 = tmp0 - tmp3; 84 | tmp11 = tmp1 + tmp2; 85 | tmp12 = tmp1 - tmp2; 86 | 87 | dataptr[0] = tmp10 + tmp11; /* phase 3 */ 88 | dataptr[4] = tmp10 - tmp11; 89 | 90 | z1 = (tmp12 + tmp13) * ((FAST_FLOAT) 0.707106781); /* c4 */ 91 | dataptr[2] = tmp13 + z1; /* phase 5 */ 92 | dataptr[6] = tmp13 - z1; 93 | 94 | /* Odd part */ 95 | 96 | tmp10 = tmp4 + tmp5; /* phase 2 */ 97 | tmp11 = tmp5 + tmp6; 98 | tmp12 = tmp6 + tmp7; 99 | 100 | /* The rotator is modified from fig 4-8 to avoid extra negations. */ 101 | z5 = (tmp10 - tmp12) * ((FAST_FLOAT) 0.382683433); /* c6 */ 102 | z2 = ((FAST_FLOAT) 0.541196100) * tmp10 + z5; /* c2-c6 */ 103 | z4 = ((FAST_FLOAT) 1.306562965) * tmp12 + z5; /* c2+c6 */ 104 | z3 = tmp11 * ((FAST_FLOAT) 0.707106781); /* c4 */ 105 | 106 | z11 = tmp7 + z3; /* phase 5 */ 107 | z13 = tmp7 - z3; 108 | 109 | dataptr[5] = z13 + z2; /* phase 6 */ 110 | dataptr[3] = z13 - z2; 111 | dataptr[1] = z11 + z4; 112 | dataptr[7] = z11 - z4; 113 | 114 | dataptr += DCTSIZE; /* advance pointer to next row */ 115 | } 116 | 117 | /* Pass 2: process columns. */ 118 | 119 | dataptr = data; 120 | for (ctr = DCTSIZE-1; ctr >= 0; ctr--) { 121 | tmp0 = dataptr[DCTSIZE*0] + dataptr[DCTSIZE*7]; 122 | tmp7 = dataptr[DCTSIZE*0] - dataptr[DCTSIZE*7]; 123 | tmp1 = dataptr[DCTSIZE*1] + dataptr[DCTSIZE*6]; 124 | tmp6 = dataptr[DCTSIZE*1] - dataptr[DCTSIZE*6]; 125 | tmp2 = dataptr[DCTSIZE*2] + dataptr[DCTSIZE*5]; 126 | tmp5 = dataptr[DCTSIZE*2] - dataptr[DCTSIZE*5]; 127 | tmp3 = dataptr[DCTSIZE*3] + dataptr[DCTSIZE*4]; 128 | tmp4 = dataptr[DCTSIZE*3] - dataptr[DCTSIZE*4]; 129 | 130 | /* Even part */ 131 | 132 | tmp10 = tmp0 + tmp3; /* phase 2 */ 133 | tmp13 = tmp0 - tmp3; 134 | tmp11 = tmp1 + tmp2; 135 | tmp12 = tmp1 - tmp2; 136 | 137 | dataptr[DCTSIZE*0] = tmp10 + tmp11; /* phase 3 */ 138 | dataptr[DCTSIZE*4] = tmp10 - tmp11; 139 | 140 | z1 = (tmp12 + tmp13) * ((FAST_FLOAT) 0.707106781); /* c4 */ 141 | dataptr[DCTSIZE*2] = tmp13 + z1; /* phase 5 */ 142 | dataptr[DCTSIZE*6] = tmp13 - z1; 143 | 144 | /* Odd part */ 145 | 146 | tmp10 = tmp4 + tmp5; /* phase 2 */ 147 | tmp11 = tmp5 + tmp6; 148 | tmp12 = tmp6 + tmp7; 149 | 150 | /* The rotator is modified from fig 4-8 to avoid extra negations. */ 151 | z5 = (tmp10 - tmp12) * ((FAST_FLOAT) 0.382683433); /* c6 */ 152 | z2 = ((FAST_FLOAT) 0.541196100) * tmp10 + z5; /* c2-c6 */ 153 | z4 = ((FAST_FLOAT) 1.306562965) * tmp12 + z5; /* c2+c6 */ 154 | z3 = tmp11 * ((FAST_FLOAT) 0.707106781); /* c4 */ 155 | 156 | z11 = tmp7 + z3; /* phase 5 */ 157 | z13 = tmp7 - z3; 158 | 159 | dataptr[DCTSIZE*5] = z13 + z2; /* phase 6 */ 160 | dataptr[DCTSIZE*3] = z13 - z2; 161 | dataptr[DCTSIZE*1] = z11 + z4; 162 | dataptr[DCTSIZE*7] = z11 - z4; 163 | 164 | dataptr++; /* advance pointer to next column */ 165 | } 166 | } 167 | 168 | #endif /* DCT_FLOAT_SUPPORTED */ 169 | -------------------------------------------------------------------------------- /windows/jpeg/jfdctfst.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jfdctfst.c 3 | * 4 | * Copyright (C) 1994-1996, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains a fast, not so accurate integer implementation of the 9 | * forward DCT (Discrete Cosine Transform). 10 | * 11 | * A 2-D DCT can be done by 1-D DCT on each row followed by 1-D DCT 12 | * on each column. Direct algorithms are also available, but they are 13 | * much more complex and seem not to be any faster when reduced to code. 14 | * 15 | * This implementation is based on Arai, Agui, and Nakajima's algorithm for 16 | * scaled DCT. Their original paper (Trans. IEICE E-71(11):1095) is in 17 | * Japanese, but the algorithm is described in the Pennebaker & Mitchell 18 | * JPEG textbook (see REFERENCES section in file README). The following code 19 | * is based directly on figure 4-8 in P&M. 20 | * While an 8-point DCT cannot be done in less than 11 multiplies, it is 21 | * possible to arrange the computation so that many of the multiplies are 22 | * simple scalings of the final outputs. These multiplies can then be 23 | * folded into the multiplications or divisions by the JPEG quantization 24 | * table entries. The AA&N method leaves only 5 multiplies and 29 adds 25 | * to be done in the DCT itself. 26 | * The primary disadvantage of this method is that with fixed-point math, 27 | * accuracy is lost due to imprecise representation of the scaled 28 | * quantization values. The smaller the quantization table entry, the less 29 | * precise the scaled value, so this implementation does worse with high- 30 | * quality-setting files than with low-quality ones. 31 | */ 32 | 33 | #define JPEG_INTERNALS 34 | #include "jinclude.h" 35 | #include "jpeglib.h" 36 | #include "jdct.h" /* Private declarations for DCT subsystem */ 37 | 38 | #ifdef DCT_IFAST_SUPPORTED 39 | 40 | 41 | /* 42 | * This module is specialized to the case DCTSIZE = 8. 43 | */ 44 | 45 | #if DCTSIZE != 8 46 | Sorry, this code only copes with 8x8 DCTs. /* deliberate syntax err */ 47 | #endif 48 | 49 | 50 | /* Scaling decisions are generally the same as in the LL&M algorithm; 51 | * see jfdctint.c for more details. However, we choose to descale 52 | * (right shift) multiplication products as soon as they are formed, 53 | * rather than carrying additional fractional bits into subsequent additions. 54 | * This compromises accuracy slightly, but it lets us save a few shifts. 55 | * More importantly, 16-bit arithmetic is then adequate (for 8-bit samples) 56 | * everywhere except in the multiplications proper; this saves a good deal 57 | * of work on 16-bit-int machines. 58 | * 59 | * Again to save a few shifts, the intermediate results between pass 1 and 60 | * pass 2 are not upscaled, but are represented only to integral precision. 61 | * 62 | * A final compromise is to represent the multiplicative constants to only 63 | * 8 fractional bits, rather than 13. This saves some shifting work on some 64 | * machines, and may also reduce the cost of multiplication (since there 65 | * are fewer one-bits in the constants). 66 | */ 67 | 68 | #define CONST_BITS 8 69 | 70 | 71 | /* Some C compilers fail to reduce "FIX(constant)" at compile time, thus 72 | * causing a lot of useless floating-point operations at run time. 73 | * To get around this we use the following pre-calculated constants. 74 | * If you change CONST_BITS you may want to add appropriate values. 75 | * (With a reasonable C compiler, you can just rely on the FIX() macro...) 76 | */ 77 | 78 | #if CONST_BITS == 8 79 | #define FIX_0_382683433 ((INT32) 98) /* FIX(0.382683433) */ 80 | #define FIX_0_541196100 ((INT32) 139) /* FIX(0.541196100) */ 81 | #define FIX_0_707106781 ((INT32) 181) /* FIX(0.707106781) */ 82 | #define FIX_1_306562965 ((INT32) 334) /* FIX(1.306562965) */ 83 | #else 84 | #define FIX_0_382683433 FIX(0.382683433) 85 | #define FIX_0_541196100 FIX(0.541196100) 86 | #define FIX_0_707106781 FIX(0.707106781) 87 | #define FIX_1_306562965 FIX(1.306562965) 88 | #endif 89 | 90 | 91 | /* We can gain a little more speed, with a further compromise in accuracy, 92 | * by omitting the addition in a descaling shift. This yields an incorrectly 93 | * rounded result half the time... 94 | */ 95 | 96 | #ifndef USE_ACCURATE_ROUNDING 97 | #undef DESCALE 98 | #define DESCALE(x,n) RIGHT_SHIFT(x, n) 99 | #endif 100 | 101 | 102 | /* Multiply a DCTELEM variable by an INT32 constant, and immediately 103 | * descale to yield a DCTELEM result. 104 | */ 105 | 106 | #define MULTIPLY(var,const) ((DCTELEM) DESCALE((var) * (const), CONST_BITS)) 107 | 108 | 109 | /* 110 | * Perform the forward DCT on one block of samples. 111 | */ 112 | 113 | GLOBAL(void) 114 | jpeg_fdct_ifast (DCTELEM * data) 115 | { 116 | DCTELEM tmp0, tmp1, tmp2, tmp3, tmp4, tmp5, tmp6, tmp7; 117 | DCTELEM tmp10, tmp11, tmp12, tmp13; 118 | DCTELEM z1, z2, z3, z4, z5, z11, z13; 119 | DCTELEM *dataptr; 120 | int ctr; 121 | SHIFT_TEMPS 122 | 123 | /* Pass 1: process rows. */ 124 | 125 | dataptr = data; 126 | for (ctr = DCTSIZE-1; ctr >= 0; ctr--) { 127 | tmp0 = dataptr[0] + dataptr[7]; 128 | tmp7 = dataptr[0] - dataptr[7]; 129 | tmp1 = dataptr[1] + dataptr[6]; 130 | tmp6 = dataptr[1] - dataptr[6]; 131 | tmp2 = dataptr[2] + dataptr[5]; 132 | tmp5 = dataptr[2] - dataptr[5]; 133 | tmp3 = dataptr[3] + dataptr[4]; 134 | tmp4 = dataptr[3] - dataptr[4]; 135 | 136 | /* Even part */ 137 | 138 | tmp10 = tmp0 + tmp3; /* phase 2 */ 139 | tmp13 = tmp0 - tmp3; 140 | tmp11 = tmp1 + tmp2; 141 | tmp12 = tmp1 - tmp2; 142 | 143 | dataptr[0] = tmp10 + tmp11; /* phase 3 */ 144 | dataptr[4] = tmp10 - tmp11; 145 | 146 | z1 = MULTIPLY(tmp12 + tmp13, FIX_0_707106781); /* c4 */ 147 | dataptr[2] = tmp13 + z1; /* phase 5 */ 148 | dataptr[6] = tmp13 - z1; 149 | 150 | /* Odd part */ 151 | 152 | tmp10 = tmp4 + tmp5; /* phase 2 */ 153 | tmp11 = tmp5 + tmp6; 154 | tmp12 = tmp6 + tmp7; 155 | 156 | /* The rotator is modified from fig 4-8 to avoid extra negations. */ 157 | z5 = MULTIPLY(tmp10 - tmp12, FIX_0_382683433); /* c6 */ 158 | z2 = MULTIPLY(tmp10, FIX_0_541196100) + z5; /* c2-c6 */ 159 | z4 = MULTIPLY(tmp12, FIX_1_306562965) + z5; /* c2+c6 */ 160 | z3 = MULTIPLY(tmp11, FIX_0_707106781); /* c4 */ 161 | 162 | z11 = tmp7 + z3; /* phase 5 */ 163 | z13 = tmp7 - z3; 164 | 165 | dataptr[5] = z13 + z2; /* phase 6 */ 166 | dataptr[3] = z13 - z2; 167 | dataptr[1] = z11 + z4; 168 | dataptr[7] = z11 - z4; 169 | 170 | dataptr += DCTSIZE; /* advance pointer to next row */ 171 | } 172 | 173 | /* Pass 2: process columns. */ 174 | 175 | dataptr = data; 176 | for (ctr = DCTSIZE-1; ctr >= 0; ctr--) { 177 | tmp0 = dataptr[DCTSIZE*0] + dataptr[DCTSIZE*7]; 178 | tmp7 = dataptr[DCTSIZE*0] - dataptr[DCTSIZE*7]; 179 | tmp1 = dataptr[DCTSIZE*1] + dataptr[DCTSIZE*6]; 180 | tmp6 = dataptr[DCTSIZE*1] - dataptr[DCTSIZE*6]; 181 | tmp2 = dataptr[DCTSIZE*2] + dataptr[DCTSIZE*5]; 182 | tmp5 = dataptr[DCTSIZE*2] - dataptr[DCTSIZE*5]; 183 | tmp3 = dataptr[DCTSIZE*3] + dataptr[DCTSIZE*4]; 184 | tmp4 = dataptr[DCTSIZE*3] - dataptr[DCTSIZE*4]; 185 | 186 | /* Even part */ 187 | 188 | tmp10 = tmp0 + tmp3; /* phase 2 */ 189 | tmp13 = tmp0 - tmp3; 190 | tmp11 = tmp1 + tmp2; 191 | tmp12 = tmp1 - tmp2; 192 | 193 | dataptr[DCTSIZE*0] = tmp10 + tmp11; /* phase 3 */ 194 | dataptr[DCTSIZE*4] = tmp10 - tmp11; 195 | 196 | z1 = MULTIPLY(tmp12 + tmp13, FIX_0_707106781); /* c4 */ 197 | dataptr[DCTSIZE*2] = tmp13 + z1; /* phase 5 */ 198 | dataptr[DCTSIZE*6] = tmp13 - z1; 199 | 200 | /* Odd part */ 201 | 202 | tmp10 = tmp4 + tmp5; /* phase 2 */ 203 | tmp11 = tmp5 + tmp6; 204 | tmp12 = tmp6 + tmp7; 205 | 206 | /* The rotator is modified from fig 4-8 to avoid extra negations. */ 207 | z5 = MULTIPLY(tmp10 - tmp12, FIX_0_382683433); /* c6 */ 208 | z2 = MULTIPLY(tmp10, FIX_0_541196100) + z5; /* c2-c6 */ 209 | z4 = MULTIPLY(tmp12, FIX_1_306562965) + z5; /* c2+c6 */ 210 | z3 = MULTIPLY(tmp11, FIX_0_707106781); /* c4 */ 211 | 212 | z11 = tmp7 + z3; /* phase 5 */ 213 | z13 = tmp7 - z3; 214 | 215 | dataptr[DCTSIZE*5] = z13 + z2; /* phase 6 */ 216 | dataptr[DCTSIZE*3] = z13 - z2; 217 | dataptr[DCTSIZE*1] = z11 + z4; 218 | dataptr[DCTSIZE*7] = z11 - z4; 219 | 220 | dataptr++; /* advance pointer to next column */ 221 | } 222 | } 223 | 224 | #endif /* DCT_IFAST_SUPPORTED */ 225 | -------------------------------------------------------------------------------- /windows/jpeg/jinclude.h: -------------------------------------------------------------------------------- 1 | /* 2 | * jinclude.h 3 | * 4 | * Copyright (C) 1991-1994, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file exists to provide a single place to fix any problems with 9 | * including the wrong system include files. (Common problems are taken 10 | * care of by the standard jconfig symbols, but on really weird systems 11 | * you may have to edit this file.) 12 | * 13 | * NOTE: this file is NOT intended to be included by applications using the 14 | * JPEG library. Most applications need only include jpeglib.h. 15 | */ 16 | 17 | 18 | /* Include auto-config file to find out which system include files we need. */ 19 | 20 | #include "jconfig.h" /* auto configuration options */ 21 | #define JCONFIG_INCLUDED /* so that jpeglib.h doesn't do it again */ 22 | 23 | /* 24 | * We need the NULL macro and size_t typedef. 25 | * On an ANSI-conforming system it is sufficient to include . 26 | * Otherwise, we get them from or ; we may have to 27 | * pull in as well. 28 | * Note that the core JPEG library does not require ; 29 | * only the default error handler and data source/destination modules do. 30 | * But we must pull it in because of the references to FILE in jpeglib.h. 31 | * You can remove those references if you want to compile without . 32 | */ 33 | 34 | #ifdef HAVE_STDDEF_H 35 | #include 36 | #endif 37 | 38 | #ifdef HAVE_STDLIB_H 39 | #include 40 | #endif 41 | 42 | #ifdef NEED_SYS_TYPES_H 43 | #include 44 | #endif 45 | 46 | #include 47 | 48 | /* 49 | * We need memory copying and zeroing functions, plus strncpy(). 50 | * ANSI and System V implementations declare these in . 51 | * BSD doesn't have the mem() functions, but it does have bcopy()/bzero(). 52 | * Some systems may declare memset and memcpy in . 53 | * 54 | * NOTE: we assume the size parameters to these functions are of type size_t. 55 | * Change the casts in these macros if not! 56 | */ 57 | 58 | #ifdef NEED_BSD_STRINGS 59 | 60 | #include 61 | #define MEMZERO(target,size) bzero((void *)(target), (size_t)(size)) 62 | #define MEMCOPY(dest,src,size) bcopy((const void *)(src), (void *)(dest), (size_t)(size)) 63 | 64 | #else /* not BSD, assume ANSI/SysV string lib */ 65 | 66 | #include 67 | #define MEMZERO(target,size) memset((void *)(target), 0, (size_t)(size)) 68 | #define MEMCOPY(dest,src,size) memcpy((void *)(dest), (const void *)(src), (size_t)(size)) 69 | 70 | #endif 71 | 72 | /* 73 | * In ANSI C, and indeed any rational implementation, size_t is also the 74 | * type returned by sizeof(). However, it seems there are some irrational 75 | * implementations out there, in which sizeof() returns an int even though 76 | * size_t is defined as long or unsigned long. To ensure consistent results 77 | * we always use this SIZEOF() macro in place of using sizeof() directly. 78 | */ 79 | 80 | #define SIZEOF(object) ((size_t) sizeof(object)) 81 | 82 | /* 83 | * The modules that use fread() and fwrite() always invoke them through 84 | * these macros. On some systems you may need to twiddle the argument casts. 85 | * CAUTION: argument order is different from underlying functions! 86 | */ 87 | 88 | #define JFREAD(file,buf,sizeofbuf) \ 89 | ((size_t) fread((void *) (buf), (size_t) 1, (size_t) (sizeofbuf), (file))) 90 | #define JFWRITE(file,buf,sizeofbuf) \ 91 | ((size_t) fwrite((const void *) (buf), (size_t) 1, (size_t) (sizeofbuf), (file))) 92 | -------------------------------------------------------------------------------- /windows/jpeg/jmemansi.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jmemansi.c 3 | * 4 | * Copyright (C) 1992-1996, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file provides a simple generic implementation of the system- 9 | * dependent portion of the JPEG memory manager. This implementation 10 | * assumes that you have the ANSI-standard library routine tmpfile(). 11 | * Also, the problem of determining the amount of memory available 12 | * is shoved onto the user. 13 | */ 14 | 15 | #define JPEG_INTERNALS 16 | #include "jinclude.h" 17 | #include "jpeglib.h" 18 | #include "jmemsys.h" /* import the system-dependent declarations */ 19 | 20 | #ifndef HAVE_STDLIB_H /* should declare malloc(),free() */ 21 | extern void * malloc JPP((size_t size)); 22 | extern void free JPP((void *ptr)); 23 | #endif 24 | 25 | #ifndef SEEK_SET /* pre-ANSI systems may not define this; */ 26 | #define SEEK_SET 0 /* if not, assume 0 is correct */ 27 | #endif 28 | 29 | 30 | /* 31 | * Memory allocation and freeing are controlled by the regular library 32 | * routines malloc() and free(). 33 | */ 34 | 35 | GLOBAL(void *) 36 | jpeg_get_small (j_common_ptr cinfo, size_t sizeofobject) 37 | { 38 | return (void *) malloc(sizeofobject); 39 | } 40 | 41 | GLOBAL(void) 42 | jpeg_free_small (j_common_ptr cinfo, void * object, size_t sizeofobject) 43 | { 44 | free(object); 45 | } 46 | 47 | 48 | /* 49 | * "Large" objects are treated the same as "small" ones. 50 | * NB: although we include FAR keywords in the routine declarations, 51 | * this file won't actually work in 80x86 small/medium model; at least, 52 | * you probably won't be able to process useful-size images in only 64KB. 53 | */ 54 | 55 | GLOBAL(void FAR *) 56 | jpeg_get_large (j_common_ptr cinfo, size_t sizeofobject) 57 | { 58 | return (void FAR *) malloc(sizeofobject); 59 | } 60 | 61 | GLOBAL(void) 62 | jpeg_free_large (j_common_ptr cinfo, void FAR * object, size_t sizeofobject) 63 | { 64 | free(object); 65 | } 66 | 67 | 68 | /* 69 | * This routine computes the total memory space available for allocation. 70 | * It's impossible to do this in a portable way; our current solution is 71 | * to make the user tell us (with a default value set at compile time). 72 | * If you can actually get the available space, it's a good idea to subtract 73 | * a slop factor of 5% or so. 74 | */ 75 | 76 | #ifndef DEFAULT_MAX_MEM /* so can override from makefile */ 77 | #define DEFAULT_MAX_MEM 1000000L /* default: one megabyte */ 78 | #endif 79 | 80 | GLOBAL(long) 81 | jpeg_mem_available (j_common_ptr cinfo, long min_bytes_needed, 82 | long max_bytes_needed, long already_allocated) 83 | { 84 | return cinfo->mem->max_memory_to_use - already_allocated; 85 | } 86 | 87 | 88 | /* 89 | * Backing store (temporary file) management. 90 | * Backing store objects are only used when the value returned by 91 | * jpeg_mem_available is less than the total space needed. You can dispense 92 | * with these routines if you have plenty of virtual memory; see jmemnobs.c. 93 | */ 94 | 95 | 96 | METHODDEF(void) 97 | read_backing_store (j_common_ptr cinfo, backing_store_ptr info, 98 | void FAR * buffer_address, 99 | long file_offset, long byte_count) 100 | { 101 | if (fseek(info->temp_file, file_offset, SEEK_SET)) 102 | ERREXIT(cinfo, JERR_TFILE_SEEK); 103 | if (JFREAD(info->temp_file, buffer_address, byte_count) 104 | != (size_t) byte_count) 105 | ERREXIT(cinfo, JERR_TFILE_READ); 106 | } 107 | 108 | 109 | METHODDEF(void) 110 | write_backing_store (j_common_ptr cinfo, backing_store_ptr info, 111 | void FAR * buffer_address, 112 | long file_offset, long byte_count) 113 | { 114 | if (fseek(info->temp_file, file_offset, SEEK_SET)) 115 | ERREXIT(cinfo, JERR_TFILE_SEEK); 116 | if (JFWRITE(info->temp_file, buffer_address, byte_count) 117 | != (size_t) byte_count) 118 | ERREXIT(cinfo, JERR_TFILE_WRITE); 119 | } 120 | 121 | 122 | METHODDEF(void) 123 | close_backing_store (j_common_ptr cinfo, backing_store_ptr info) 124 | { 125 | fclose(info->temp_file); 126 | /* Since this implementation uses tmpfile() to create the file, 127 | * no explicit file deletion is needed. 128 | */ 129 | } 130 | 131 | 132 | /* 133 | * Initial opening of a backing-store object. 134 | * 135 | * This version uses tmpfile(), which constructs a suitable file name 136 | * behind the scenes. We don't have to use info->temp_name[] at all; 137 | * indeed, we can't even find out the actual name of the temp file. 138 | */ 139 | 140 | GLOBAL(void) 141 | jpeg_open_backing_store (j_common_ptr cinfo, backing_store_ptr info, 142 | long total_bytes_needed) 143 | { 144 | if ((info->temp_file = tmpfile()) == NULL) 145 | ERREXITS(cinfo, JERR_TFILE_CREATE, ""); 146 | info->read_backing_store = read_backing_store; 147 | info->write_backing_store = write_backing_store; 148 | info->close_backing_store = close_backing_store; 149 | } 150 | 151 | 152 | /* 153 | * These routines take care of any system-dependent initialization and 154 | * cleanup required. 155 | */ 156 | 157 | GLOBAL(long) 158 | jpeg_mem_init (j_common_ptr cinfo) 159 | { 160 | return DEFAULT_MAX_MEM; /* default for max_memory_to_use */ 161 | } 162 | 163 | GLOBAL(void) 164 | jpeg_mem_term (j_common_ptr cinfo) 165 | { 166 | /* no work */ 167 | } 168 | -------------------------------------------------------------------------------- /windows/jpeg/jmemnobs.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jmemnobs.c 3 | * 4 | * Copyright (C) 1992-1996, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file provides a really simple implementation of the system- 9 | * dependent portion of the JPEG memory manager. This implementation 10 | * assumes that no backing-store files are needed: all required space 11 | * can be obtained from malloc(). 12 | * This is very portable in the sense that it'll compile on almost anything, 13 | * but you'd better have lots of main memory (or virtual memory) if you want 14 | * to process big images. 15 | * Note that the max_memory_to_use option is ignored by this implementation. 16 | */ 17 | 18 | #define JPEG_INTERNALS 19 | #include "jinclude.h" 20 | #include "jpeglib.h" 21 | #include "jmemsys.h" /* import the system-dependent declarations */ 22 | 23 | #ifndef HAVE_STDLIB_H /* should declare malloc(),free() */ 24 | extern void * malloc JPP((size_t size)); 25 | extern void free JPP((void *ptr)); 26 | #endif 27 | 28 | 29 | /* 30 | * Memory allocation and freeing are controlled by the regular library 31 | * routines malloc() and free(). 32 | */ 33 | 34 | GLOBAL(void *) 35 | jpeg_get_small (j_common_ptr cinfo, size_t sizeofobject) 36 | { 37 | return (void *) malloc(sizeofobject); 38 | } 39 | 40 | GLOBAL(void) 41 | jpeg_free_small (j_common_ptr cinfo, void * object, size_t sizeofobject) 42 | { 43 | free(object); 44 | } 45 | 46 | 47 | /* 48 | * "Large" objects are treated the same as "small" ones. 49 | * NB: although we include FAR keywords in the routine declarations, 50 | * this file won't actually work in 80x86 small/medium model; at least, 51 | * you probably won't be able to process useful-size images in only 64KB. 52 | */ 53 | 54 | GLOBAL(void FAR *) 55 | jpeg_get_large (j_common_ptr cinfo, size_t sizeofobject) 56 | { 57 | return (void FAR *) malloc(sizeofobject); 58 | } 59 | 60 | GLOBAL(void) 61 | jpeg_free_large (j_common_ptr cinfo, void FAR * object, size_t sizeofobject) 62 | { 63 | free(object); 64 | } 65 | 66 | 67 | /* 68 | * This routine computes the total memory space available for allocation. 69 | * Here we always say, "we got all you want bud!" 70 | */ 71 | 72 | GLOBAL(long) 73 | jpeg_mem_available (j_common_ptr cinfo, long min_bytes_needed, 74 | long max_bytes_needed, long already_allocated) 75 | { 76 | return max_bytes_needed; 77 | } 78 | 79 | 80 | /* 81 | * Backing store (temporary file) management. 82 | * Since jpeg_mem_available always promised the moon, 83 | * this should never be called and we can just error out. 84 | */ 85 | 86 | GLOBAL(void) 87 | jpeg_open_backing_store (j_common_ptr cinfo, backing_store_ptr info, 88 | long total_bytes_needed) 89 | { 90 | ERREXIT(cinfo, JERR_NO_BACKING_STORE); 91 | } 92 | 93 | 94 | /* 95 | * These routines take care of any system-dependent initialization and 96 | * cleanup required. Here, there isn't any. 97 | */ 98 | 99 | GLOBAL(long) 100 | jpeg_mem_init (j_common_ptr cinfo) 101 | { 102 | return 0; /* just set max_memory_to_use to 0 */ 103 | } 104 | 105 | GLOBAL(void) 106 | jpeg_mem_term (j_common_ptr cinfo) 107 | { 108 | /* no work */ 109 | } 110 | -------------------------------------------------------------------------------- /windows/jpeg/jmemsys.h: -------------------------------------------------------------------------------- 1 | /* 2 | * jmemsys.h 3 | * 4 | * Copyright (C) 1992-1997, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This include file defines the interface between the system-independent 9 | * and system-dependent portions of the JPEG memory manager. No other 10 | * modules need include it. (The system-independent portion is jmemmgr.c; 11 | * there are several different versions of the system-dependent portion.) 12 | * 13 | * This file works as-is for the system-dependent memory managers supplied 14 | * in the IJG distribution. You may need to modify it if you write a 15 | * custom memory manager. If system-dependent changes are needed in 16 | * this file, the best method is to #ifdef them based on a configuration 17 | * symbol supplied in jconfig.h, as we have done with USE_MSDOS_MEMMGR 18 | * and USE_MAC_MEMMGR. 19 | */ 20 | 21 | 22 | /* Short forms of external names for systems with brain-damaged linkers. */ 23 | 24 | #ifdef NEED_SHORT_EXTERNAL_NAMES 25 | #define jpeg_get_small jGetSmall 26 | #define jpeg_free_small jFreeSmall 27 | #define jpeg_get_large jGetLarge 28 | #define jpeg_free_large jFreeLarge 29 | #define jpeg_mem_available jMemAvail 30 | #define jpeg_open_backing_store jOpenBackStore 31 | #define jpeg_mem_init jMemInit 32 | #define jpeg_mem_term jMemTerm 33 | #endif /* NEED_SHORT_EXTERNAL_NAMES */ 34 | 35 | 36 | /* 37 | * These two functions are used to allocate and release small chunks of 38 | * memory. (Typically the total amount requested through jpeg_get_small is 39 | * no more than 20K or so; this will be requested in chunks of a few K each.) 40 | * Behavior should be the same as for the standard library functions malloc 41 | * and free; in particular, jpeg_get_small must return NULL on failure. 42 | * On most systems, these ARE malloc and free. jpeg_free_small is passed the 43 | * size of the object being freed, just in case it's needed. 44 | * On an 80x86 machine using small-data memory model, these manage near heap. 45 | */ 46 | 47 | EXTERN(void *) jpeg_get_small JPP((j_common_ptr cinfo, size_t sizeofobject)); 48 | EXTERN(void) jpeg_free_small JPP((j_common_ptr cinfo, void * object, 49 | size_t sizeofobject)); 50 | 51 | /* 52 | * These two functions are used to allocate and release large chunks of 53 | * memory (up to the total free space designated by jpeg_mem_available). 54 | * The interface is the same as above, except that on an 80x86 machine, 55 | * far pointers are used. On most other machines these are identical to 56 | * the jpeg_get/free_small routines; but we keep them separate anyway, 57 | * in case a different allocation strategy is desirable for large chunks. 58 | */ 59 | 60 | EXTERN(void FAR *) jpeg_get_large JPP((j_common_ptr cinfo, 61 | size_t sizeofobject)); 62 | EXTERN(void) jpeg_free_large JPP((j_common_ptr cinfo, void FAR * object, 63 | size_t sizeofobject)); 64 | 65 | /* 66 | * The macro MAX_ALLOC_CHUNK designates the maximum number of bytes that may 67 | * be requested in a single call to jpeg_get_large (and jpeg_get_small for that 68 | * matter, but that case should never come into play). This macro is needed 69 | * to model the 64Kb-segment-size limit of far addressing on 80x86 machines. 70 | * On those machines, we expect that jconfig.h will provide a proper value. 71 | * On machines with 32-bit flat address spaces, any large constant may be used. 72 | * 73 | * NB: jmemmgr.c expects that MAX_ALLOC_CHUNK will be representable as type 74 | * size_t and will be a multiple of sizeof(align_type). 75 | */ 76 | 77 | #ifndef MAX_ALLOC_CHUNK /* may be overridden in jconfig.h */ 78 | #define MAX_ALLOC_CHUNK 1000000000L 79 | #endif 80 | 81 | /* 82 | * This routine computes the total space still available for allocation by 83 | * jpeg_get_large. If more space than this is needed, backing store will be 84 | * used. NOTE: any memory already allocated must not be counted. 85 | * 86 | * There is a minimum space requirement, corresponding to the minimum 87 | * feasible buffer sizes; jmemmgr.c will request that much space even if 88 | * jpeg_mem_available returns zero. The maximum space needed, enough to hold 89 | * all working storage in memory, is also passed in case it is useful. 90 | * Finally, the total space already allocated is passed. If no better 91 | * method is available, cinfo->mem->max_memory_to_use - already_allocated 92 | * is often a suitable calculation. 93 | * 94 | * It is OK for jpeg_mem_available to underestimate the space available 95 | * (that'll just lead to more backing-store access than is really necessary). 96 | * However, an overestimate will lead to failure. Hence it's wise to subtract 97 | * a slop factor from the true available space. 5% should be enough. 98 | * 99 | * On machines with lots of virtual memory, any large constant may be returned. 100 | * Conversely, zero may be returned to always use the minimum amount of memory. 101 | */ 102 | 103 | EXTERN(long) jpeg_mem_available JPP((j_common_ptr cinfo, 104 | long min_bytes_needed, 105 | long max_bytes_needed, 106 | long already_allocated)); 107 | 108 | 109 | /* 110 | * This structure holds whatever state is needed to access a single 111 | * backing-store object. The read/write/close method pointers are called 112 | * by jmemmgr.c to manipulate the backing-store object; all other fields 113 | * are private to the system-dependent backing store routines. 114 | */ 115 | 116 | #define TEMP_NAME_LENGTH 64 /* max length of a temporary file's name */ 117 | 118 | 119 | #ifdef USE_MSDOS_MEMMGR /* DOS-specific junk */ 120 | 121 | typedef unsigned short XMSH; /* type of extended-memory handles */ 122 | typedef unsigned short EMSH; /* type of expanded-memory handles */ 123 | 124 | typedef union { 125 | short file_handle; /* DOS file handle if it's a temp file */ 126 | XMSH xms_handle; /* handle if it's a chunk of XMS */ 127 | EMSH ems_handle; /* handle if it's a chunk of EMS */ 128 | } handle_union; 129 | 130 | #endif /* USE_MSDOS_MEMMGR */ 131 | 132 | #ifdef USE_MAC_MEMMGR /* Mac-specific junk */ 133 | #include 134 | #endif /* USE_MAC_MEMMGR */ 135 | 136 | 137 | typedef struct backing_store_struct * backing_store_ptr; 138 | 139 | typedef struct backing_store_struct { 140 | /* Methods for reading/writing/closing this backing-store object */ 141 | JMETHOD(void, read_backing_store, (j_common_ptr cinfo, 142 | backing_store_ptr info, 143 | void FAR * buffer_address, 144 | long file_offset, long byte_count)); 145 | JMETHOD(void, write_backing_store, (j_common_ptr cinfo, 146 | backing_store_ptr info, 147 | void FAR * buffer_address, 148 | long file_offset, long byte_count)); 149 | JMETHOD(void, close_backing_store, (j_common_ptr cinfo, 150 | backing_store_ptr info)); 151 | 152 | /* Private fields for system-dependent backing-store management */ 153 | #ifdef USE_MSDOS_MEMMGR 154 | /* For the MS-DOS manager (jmemdos.c), we need: */ 155 | handle_union handle; /* reference to backing-store storage object */ 156 | char temp_name[TEMP_NAME_LENGTH]; /* name if it's a file */ 157 | #else 158 | #ifdef USE_MAC_MEMMGR 159 | /* For the Mac manager (jmemmac.c), we need: */ 160 | short temp_file; /* file reference number to temp file */ 161 | FSSpec tempSpec; /* the FSSpec for the temp file */ 162 | char temp_name[TEMP_NAME_LENGTH]; /* name if it's a file */ 163 | #else 164 | /* For a typical implementation with temp files, we need: */ 165 | FILE * temp_file; /* stdio reference to temp file */ 166 | char temp_name[TEMP_NAME_LENGTH]; /* name of temp file */ 167 | #endif 168 | #endif 169 | } backing_store_info; 170 | 171 | 172 | /* 173 | * Initial opening of a backing-store object. This must fill in the 174 | * read/write/close pointers in the object. The read/write routines 175 | * may take an error exit if the specified maximum file size is exceeded. 176 | * (If jpeg_mem_available always returns a large value, this routine can 177 | * just take an error exit.) 178 | */ 179 | 180 | EXTERN(void) jpeg_open_backing_store JPP((j_common_ptr cinfo, 181 | backing_store_ptr info, 182 | long total_bytes_needed)); 183 | 184 | 185 | /* 186 | * These routines take care of any system-dependent initialization and 187 | * cleanup required. jpeg_mem_init will be called before anything is 188 | * allocated (and, therefore, nothing in cinfo is of use except the error 189 | * manager pointer). It should return a suitable default value for 190 | * max_memory_to_use; this may subsequently be overridden by the surrounding 191 | * application. (Note that max_memory_to_use is only important if 192 | * jpeg_mem_available chooses to consult it ... no one else will.) 193 | * jpeg_mem_term may assume that all requested memory has been freed and that 194 | * all opened backing-store objects have been closed. 195 | */ 196 | 197 | EXTERN(long) jpeg_mem_init JPP((j_common_ptr cinfo)); 198 | EXTERN(void) jpeg_mem_term JPP((j_common_ptr cinfo)); 199 | -------------------------------------------------------------------------------- /windows/jpeg/jutils.c: -------------------------------------------------------------------------------- 1 | /* 2 | * jutils.c 3 | * 4 | * Copyright (C) 1991-1996, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains tables and miscellaneous utility routines needed 9 | * for both compression and decompression. 10 | * Note we prefix all global names with "j" to minimize conflicts with 11 | * a surrounding application. 12 | */ 13 | 14 | #define JPEG_INTERNALS 15 | #include "jinclude.h" 16 | #include "jpeglib.h" 17 | 18 | 19 | /* 20 | * jpeg_zigzag_order[i] is the zigzag-order position of the i'th element 21 | * of a DCT block read in natural order (left to right, top to bottom). 22 | */ 23 | 24 | #if 0 /* This table is not actually needed in v6a */ 25 | 26 | const int jpeg_zigzag_order[DCTSIZE2] = { 27 | 0, 1, 5, 6, 14, 15, 27, 28, 28 | 2, 4, 7, 13, 16, 26, 29, 42, 29 | 3, 8, 12, 17, 25, 30, 41, 43, 30 | 9, 11, 18, 24, 31, 40, 44, 53, 31 | 10, 19, 23, 32, 39, 45, 52, 54, 32 | 20, 22, 33, 38, 46, 51, 55, 60, 33 | 21, 34, 37, 47, 50, 56, 59, 61, 34 | 35, 36, 48, 49, 57, 58, 62, 63 35 | }; 36 | 37 | #endif 38 | 39 | /* 40 | * jpeg_natural_order[i] is the natural-order position of the i'th element 41 | * of zigzag order. 42 | * 43 | * When reading corrupted data, the Huffman decoders could attempt 44 | * to reference an entry beyond the end of this array (if the decoded 45 | * zero run length reaches past the end of the block). To prevent 46 | * wild stores without adding an inner-loop test, we put some extra 47 | * "63"s after the real entries. This will cause the extra coefficient 48 | * to be stored in location 63 of the block, not somewhere random. 49 | * The worst case would be a run-length of 15, which means we need 16 50 | * fake entries. 51 | */ 52 | 53 | const int jpeg_natural_order[DCTSIZE2+16] = { 54 | 0, 1, 8, 16, 9, 2, 3, 10, 55 | 17, 24, 32, 25, 18, 11, 4, 5, 56 | 12, 19, 26, 33, 40, 48, 41, 34, 57 | 27, 20, 13, 6, 7, 14, 21, 28, 58 | 35, 42, 49, 56, 57, 50, 43, 36, 59 | 29, 22, 15, 23, 30, 37, 44, 51, 60 | 58, 59, 52, 45, 38, 31, 39, 46, 61 | 53, 60, 61, 54, 47, 55, 62, 63, 62 | 63, 63, 63, 63, 63, 63, 63, 63, /* extra entries for safety in decoder */ 63 | 63, 63, 63, 63, 63, 63, 63, 63 64 | }; 65 | 66 | 67 | /* 68 | * Arithmetic utilities 69 | */ 70 | 71 | GLOBAL(long) 72 | jdiv_round_up (long a, long b) 73 | /* Compute a/b rounded up to next integer, ie, ceil(a/b) */ 74 | /* Assumes a >= 0, b > 0 */ 75 | { 76 | return (a + b - 1L) / b; 77 | } 78 | 79 | 80 | GLOBAL(long) 81 | jround_up (long a, long b) 82 | /* Compute a rounded up to next multiple of b, ie, ceil(a/b)*b */ 83 | /* Assumes a >= 0, b > 0 */ 84 | { 85 | a += b - 1L; 86 | return a - (a % b); 87 | } 88 | 89 | 90 | /* On normal machines we can apply MEMCOPY() and MEMZERO() to sample arrays 91 | * and coefficient-block arrays. This won't work on 80x86 because the arrays 92 | * are FAR and we're assuming a small-pointer memory model. However, some 93 | * DOS compilers provide far-pointer versions of memcpy() and memset() even 94 | * in the small-model libraries. These will be used if USE_FMEM is defined. 95 | * Otherwise, the routines below do it the hard way. (The performance cost 96 | * is not all that great, because these routines aren't very heavily used.) 97 | */ 98 | 99 | #ifndef NEED_FAR_POINTERS /* normal case, same as regular macros */ 100 | #define FMEMCOPY(dest,src,size) MEMCOPY(dest,src,size) 101 | #define FMEMZERO(target,size) MEMZERO(target,size) 102 | #else /* 80x86 case, define if we can */ 103 | #ifdef USE_FMEM 104 | #define FMEMCOPY(dest,src,size) _fmemcpy((void FAR *)(dest), (const void FAR *)(src), (size_t)(size)) 105 | #define FMEMZERO(target,size) _fmemset((void FAR *)(target), 0, (size_t)(size)) 106 | #endif 107 | #endif 108 | 109 | 110 | GLOBAL(void) 111 | jcopy_sample_rows (JSAMPARRAY input_array, int source_row, 112 | JSAMPARRAY output_array, int dest_row, 113 | int num_rows, JDIMENSION num_cols) 114 | /* Copy some rows of samples from one place to another. 115 | * num_rows rows are copied from input_array[source_row++] 116 | * to output_array[dest_row++]; these areas may overlap for duplication. 117 | * The source and destination arrays must be at least as wide as num_cols. 118 | */ 119 | { 120 | register JSAMPROW inptr, outptr; 121 | #ifdef FMEMCOPY 122 | register size_t count = (size_t) (num_cols * SIZEOF(JSAMPLE)); 123 | #else 124 | register JDIMENSION count; 125 | #endif 126 | register int row; 127 | 128 | input_array += source_row; 129 | output_array += dest_row; 130 | 131 | for (row = num_rows; row > 0; row--) { 132 | inptr = *input_array++; 133 | outptr = *output_array++; 134 | #ifdef FMEMCOPY 135 | FMEMCOPY(outptr, inptr, count); 136 | #else 137 | for (count = num_cols; count > 0; count--) 138 | *outptr++ = *inptr++; /* needn't bother with GETJSAMPLE() here */ 139 | #endif 140 | } 141 | } 142 | 143 | 144 | GLOBAL(void) 145 | jcopy_block_row (JBLOCKROW input_row, JBLOCKROW output_row, 146 | JDIMENSION num_blocks) 147 | /* Copy a row of coefficient blocks from one place to another. */ 148 | { 149 | #ifdef FMEMCOPY 150 | FMEMCOPY(output_row, input_row, num_blocks * (DCTSIZE2 * SIZEOF(JCOEF))); 151 | #else 152 | register JCOEFPTR inptr, outptr; 153 | register long count; 154 | 155 | inptr = (JCOEFPTR) input_row; 156 | outptr = (JCOEFPTR) output_row; 157 | for (count = (long) num_blocks * DCTSIZE2; count > 0; count--) { 158 | *outptr++ = *inptr++; 159 | } 160 | #endif 161 | } 162 | 163 | 164 | GLOBAL(void) 165 | jzero_far (void FAR * target, size_t bytestozero) 166 | /* Zero out a chunk of FAR memory. */ 167 | /* This might be sample-array data, block-array data, or alloc_large data. */ 168 | { 169 | #ifdef FMEMZERO 170 | FMEMZERO(target, bytestozero); 171 | #else 172 | register char FAR * ptr = (char FAR *) target; 173 | register size_t count; 174 | 175 | for (count = bytestozero; count > 0; count--) { 176 | *ptr++ = 0; 177 | } 178 | #endif 179 | } 180 | -------------------------------------------------------------------------------- /windows/jpeg/jversion.h: -------------------------------------------------------------------------------- 1 | /* 2 | * jversion.h 3 | * 4 | * Copyright (C) 1991-1998, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains software version identification. 9 | */ 10 | 11 | 12 | #define JVERSION "6b 27-Mar-1998" 13 | 14 | #define JCOPYRIGHT "Copyright (C) 1998, Thomas G. Lane" 15 | -------------------------------------------------------------------------------- /windows/jpeg/rdcolmap.c: -------------------------------------------------------------------------------- 1 | /* 2 | * rdcolmap.c 3 | * 4 | * Copyright (C) 1994-1996, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file implements djpeg's "-map file" switch. It reads a source image 9 | * and constructs a colormap to be supplied to the JPEG decompressor. 10 | * 11 | * Currently, these file formats are supported for the map file: 12 | * GIF: the contents of the GIF's global colormap are used. 13 | * PPM (either text or raw flavor): the entire file is read and 14 | * each unique pixel value is entered in the map. 15 | * Note that reading a large PPM file will be horrendously slow. 16 | * Typically, a PPM-format map file should contain just one pixel 17 | * of each desired color. Such a file can be extracted from an 18 | * ordinary image PPM file with ppmtomap(1). 19 | * 20 | * Rescaling a PPM that has a maxval unequal to MAXJSAMPLE is not 21 | * currently implemented. 22 | */ 23 | 24 | #include "cdjpeg.h" /* Common decls for cjpeg/djpeg applications */ 25 | 26 | #ifdef QUANT_2PASS_SUPPORTED /* otherwise can't quantize to supplied map */ 27 | 28 | /* Portions of this code are based on the PBMPLUS library, which is: 29 | ** 30 | ** Copyright (C) 1988 by Jef Poskanzer. 31 | ** 32 | ** Permission to use, copy, modify, and distribute this software and its 33 | ** documentation for any purpose and without fee is hereby granted, provided 34 | ** that the above copyright notice appear in all copies and that both that 35 | ** copyright notice and this permission notice appear in supporting 36 | ** documentation. This software is provided "as is" without express or 37 | ** implied warranty. 38 | */ 39 | 40 | 41 | /* 42 | * Add a (potentially) new color to the color map. 43 | */ 44 | 45 | LOCAL(void) 46 | add_map_entry (j_decompress_ptr cinfo, int R, int G, int B) 47 | { 48 | JSAMPROW colormap0 = cinfo->colormap[0]; 49 | JSAMPROW colormap1 = cinfo->colormap[1]; 50 | JSAMPROW colormap2 = cinfo->colormap[2]; 51 | int ncolors = cinfo->actual_number_of_colors; 52 | int index; 53 | 54 | /* Check for duplicate color. */ 55 | for (index = 0; index < ncolors; index++) { 56 | if (GETJSAMPLE(colormap0[index]) == R && 57 | GETJSAMPLE(colormap1[index]) == G && 58 | GETJSAMPLE(colormap2[index]) == B) 59 | return; /* color is already in map */ 60 | } 61 | 62 | /* Check for map overflow. */ 63 | if (ncolors >= (MAXJSAMPLE+1)) 64 | ERREXIT1(cinfo, JERR_QUANT_MANY_COLORS, (MAXJSAMPLE+1)); 65 | 66 | /* OK, add color to map. */ 67 | colormap0[ncolors] = (JSAMPLE) R; 68 | colormap1[ncolors] = (JSAMPLE) G; 69 | colormap2[ncolors] = (JSAMPLE) B; 70 | cinfo->actual_number_of_colors++; 71 | } 72 | 73 | 74 | /* 75 | * Extract color map from a GIF file. 76 | */ 77 | 78 | LOCAL(void) 79 | read_gif_map (j_decompress_ptr cinfo, FILE * infile) 80 | { 81 | int header[13]; 82 | int i, colormaplen; 83 | int R, G, B; 84 | 85 | /* Initial 'G' has already been read by read_color_map */ 86 | /* Read the rest of the GIF header and logical screen descriptor */ 87 | for (i = 1; i < 13; i++) { 88 | if ((header[i] = getc(infile)) == EOF) 89 | ERREXIT(cinfo, JERR_BAD_CMAP_FILE); 90 | } 91 | 92 | /* Verify GIF Header */ 93 | if (header[1] != 'I' || header[2] != 'F') 94 | ERREXIT(cinfo, JERR_BAD_CMAP_FILE); 95 | 96 | /* There must be a global color map. */ 97 | if ((header[10] & 0x80) == 0) 98 | ERREXIT(cinfo, JERR_BAD_CMAP_FILE); 99 | 100 | /* OK, fetch it. */ 101 | colormaplen = 2 << (header[10] & 0x07); 102 | 103 | for (i = 0; i < colormaplen; i++) { 104 | R = getc(infile); 105 | G = getc(infile); 106 | B = getc(infile); 107 | if (R == EOF || G == EOF || B == EOF) 108 | ERREXIT(cinfo, JERR_BAD_CMAP_FILE); 109 | add_map_entry(cinfo, 110 | R << (BITS_IN_JSAMPLE-8), 111 | G << (BITS_IN_JSAMPLE-8), 112 | B << (BITS_IN_JSAMPLE-8)); 113 | } 114 | } 115 | 116 | 117 | /* Support routines for reading PPM */ 118 | 119 | 120 | LOCAL(int) 121 | pbm_getc (FILE * infile) 122 | /* Read next char, skipping over any comments */ 123 | /* A comment/newline sequence is returned as a newline */ 124 | { 125 | register int ch; 126 | 127 | ch = getc(infile); 128 | if (ch == '#') { 129 | do { 130 | ch = getc(infile); 131 | } while (ch != '\n' && ch != EOF); 132 | } 133 | return ch; 134 | } 135 | 136 | 137 | LOCAL(unsigned int) 138 | read_pbm_integer (j_decompress_ptr cinfo, FILE * infile) 139 | /* Read an unsigned decimal integer from the PPM file */ 140 | /* Swallows one trailing character after the integer */ 141 | /* Note that on a 16-bit-int machine, only values up to 64k can be read. */ 142 | /* This should not be a problem in practice. */ 143 | { 144 | register int ch; 145 | register unsigned int val; 146 | 147 | /* Skip any leading whitespace */ 148 | do { 149 | ch = pbm_getc(infile); 150 | if (ch == EOF) 151 | ERREXIT(cinfo, JERR_BAD_CMAP_FILE); 152 | } while (ch == ' ' || ch == '\t' || ch == '\n' || ch == '\r'); 153 | 154 | if (ch < '0' || ch > '9') 155 | ERREXIT(cinfo, JERR_BAD_CMAP_FILE); 156 | 157 | val = ch - '0'; 158 | while ((ch = pbm_getc(infile)) >= '0' && ch <= '9') { 159 | val *= 10; 160 | val += ch - '0'; 161 | } 162 | return val; 163 | } 164 | 165 | 166 | /* 167 | * Extract color map from a PPM file. 168 | */ 169 | 170 | LOCAL(void) 171 | read_ppm_map (j_decompress_ptr cinfo, FILE * infile) 172 | { 173 | int c; 174 | unsigned int w, h, maxval, row, col; 175 | int R, G, B; 176 | 177 | /* Initial 'P' has already been read by read_color_map */ 178 | c = getc(infile); /* save format discriminator for a sec */ 179 | 180 | /* while we fetch the remaining header info */ 181 | w = read_pbm_integer(cinfo, infile); 182 | h = read_pbm_integer(cinfo, infile); 183 | maxval = read_pbm_integer(cinfo, infile); 184 | 185 | if (w <= 0 || h <= 0 || maxval <= 0) /* error check */ 186 | ERREXIT(cinfo, JERR_BAD_CMAP_FILE); 187 | 188 | /* For now, we don't support rescaling from an unusual maxval. */ 189 | if (maxval != (unsigned int) MAXJSAMPLE) 190 | ERREXIT(cinfo, JERR_BAD_CMAP_FILE); 191 | 192 | switch (c) { 193 | case '3': /* it's a text-format PPM file */ 194 | for (row = 0; row < h; row++) { 195 | for (col = 0; col < w; col++) { 196 | R = read_pbm_integer(cinfo, infile); 197 | G = read_pbm_integer(cinfo, infile); 198 | B = read_pbm_integer(cinfo, infile); 199 | add_map_entry(cinfo, R, G, B); 200 | } 201 | } 202 | break; 203 | 204 | case '6': /* it's a raw-format PPM file */ 205 | for (row = 0; row < h; row++) { 206 | for (col = 0; col < w; col++) { 207 | R = getc(infile); 208 | G = getc(infile); 209 | B = getc(infile); 210 | if (R == EOF || G == EOF || B == EOF) 211 | ERREXIT(cinfo, JERR_BAD_CMAP_FILE); 212 | add_map_entry(cinfo, R, G, B); 213 | } 214 | } 215 | break; 216 | 217 | default: 218 | ERREXIT(cinfo, JERR_BAD_CMAP_FILE); 219 | break; 220 | } 221 | } 222 | 223 | 224 | /* 225 | * Main entry point from djpeg.c. 226 | * Input: opened input file (from file name argument on command line). 227 | * Output: colormap and actual_number_of_colors fields are set in cinfo. 228 | */ 229 | 230 | GLOBAL(void) 231 | read_color_map (j_decompress_ptr cinfo, FILE * infile) 232 | { 233 | /* Allocate space for a color map of maximum supported size. */ 234 | cinfo->colormap = (*cinfo->mem->alloc_sarray) 235 | ((j_common_ptr) cinfo, JPOOL_IMAGE, 236 | (JDIMENSION) (MAXJSAMPLE+1), (JDIMENSION) 3); 237 | cinfo->actual_number_of_colors = 0; /* initialize map to empty */ 238 | 239 | /* Read first byte to determine file format */ 240 | switch (getc(infile)) { 241 | case 'G': 242 | read_gif_map(cinfo, infile); 243 | break; 244 | case 'P': 245 | read_ppm_map(cinfo, infile); 246 | break; 247 | default: 248 | ERREXIT(cinfo, JERR_BAD_CMAP_FILE); 249 | break; 250 | } 251 | } 252 | 253 | #endif /* QUANT_2PASS_SUPPORTED */ 254 | -------------------------------------------------------------------------------- /windows/jpeg/rdgif.c: -------------------------------------------------------------------------------- 1 | /* 2 | * rdgif.c 3 | * 4 | * Copyright (C) 1991-1997, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains routines to read input images in GIF format. 9 | * 10 | ***************************************************************************** 11 | * NOTE: to avoid entanglements with Unisys' patent on LZW compression, * 12 | * the ability to read GIF files has been removed from the IJG distribution. * 13 | * Sorry about that. * 14 | ***************************************************************************** 15 | * 16 | * We are required to state that 17 | * "The Graphics Interchange Format(c) is the Copyright property of 18 | * CompuServe Incorporated. GIF(sm) is a Service Mark property of 19 | * CompuServe Incorporated." 20 | */ 21 | 22 | #include "cdjpeg.h" /* Common decls for cjpeg/djpeg applications */ 23 | 24 | #ifdef GIF_SUPPORTED 25 | 26 | /* 27 | * The module selection routine for GIF format input. 28 | */ 29 | 30 | GLOBAL(cjpeg_source_ptr) 31 | jinit_read_gif (j_compress_ptr cinfo) 32 | { 33 | fprintf(stderr, "GIF input is unsupported for legal reasons. Sorry.\n"); 34 | exit(EXIT_FAILURE); 35 | return NULL; /* keep compiler happy */ 36 | } 37 | 38 | #endif /* GIF_SUPPORTED */ 39 | -------------------------------------------------------------------------------- /windows/jpeg/transupp.h: -------------------------------------------------------------------------------- 1 | /* 2 | * transupp.h 3 | * 4 | * Copyright (C) 1997, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains declarations for image transformation routines and 9 | * other utility code used by the jpegtran sample application. These are 10 | * NOT part of the core JPEG library. But we keep these routines separate 11 | * from jpegtran.c to ease the task of maintaining jpegtran-like programs 12 | * that have other user interfaces. 13 | * 14 | * NOTE: all the routines declared here have very specific requirements 15 | * about when they are to be executed during the reading and writing of the 16 | * source and destination files. See the comments in transupp.c, or see 17 | * jpegtran.c for an example of correct usage. 18 | */ 19 | 20 | /* If you happen not to want the image transform support, disable it here */ 21 | #ifndef TRANSFORMS_SUPPORTED 22 | #define TRANSFORMS_SUPPORTED 1 /* 0 disables transform code */ 23 | #endif 24 | 25 | /* Short forms of external names for systems with brain-damaged linkers. */ 26 | 27 | #ifdef NEED_SHORT_EXTERNAL_NAMES 28 | #define jtransform_request_workspace jTrRequest 29 | #define jtransform_adjust_parameters jTrAdjust 30 | #define jtransform_execute_transformation jTrExec 31 | #define jcopy_markers_setup jCMrkSetup 32 | #define jcopy_markers_execute jCMrkExec 33 | #endif /* NEED_SHORT_EXTERNAL_NAMES */ 34 | 35 | 36 | /* 37 | * Codes for supported types of image transformations. 38 | */ 39 | 40 | typedef enum { 41 | JXFORM_NONE, /* no transformation */ 42 | JXFORM_FLIP_H, /* horizontal flip */ 43 | JXFORM_FLIP_V, /* vertical flip */ 44 | JXFORM_TRANSPOSE, /* transpose across UL-to-LR axis */ 45 | JXFORM_TRANSVERSE, /* transpose across UR-to-LL axis */ 46 | JXFORM_ROT_90, /* 90-degree clockwise rotation */ 47 | JXFORM_ROT_180, /* 180-degree rotation */ 48 | JXFORM_ROT_270 /* 270-degree clockwise (or 90 ccw) */ 49 | } JXFORM_CODE; 50 | 51 | /* 52 | * Although rotating and flipping data expressed as DCT coefficients is not 53 | * hard, there is an asymmetry in the JPEG format specification for images 54 | * whose dimensions aren't multiples of the iMCU size. The right and bottom 55 | * image edges are padded out to the next iMCU boundary with junk data; but 56 | * no padding is possible at the top and left edges. If we were to flip 57 | * the whole image including the pad data, then pad garbage would become 58 | * visible at the top and/or left, and real pixels would disappear into the 59 | * pad margins --- perhaps permanently, since encoders & decoders may not 60 | * bother to preserve DCT blocks that appear to be completely outside the 61 | * nominal image area. So, we have to exclude any partial iMCUs from the 62 | * basic transformation. 63 | * 64 | * Transpose is the only transformation that can handle partial iMCUs at the 65 | * right and bottom edges completely cleanly. flip_h can flip partial iMCUs 66 | * at the bottom, but leaves any partial iMCUs at the right edge untouched. 67 | * Similarly flip_v leaves any partial iMCUs at the bottom edge untouched. 68 | * The other transforms are defined as combinations of these basic transforms 69 | * and process edge blocks in a way that preserves the equivalence. 70 | * 71 | * The "trim" option causes untransformable partial iMCUs to be dropped; 72 | * this is not strictly lossless, but it usually gives the best-looking 73 | * result for odd-size images. Note that when this option is active, 74 | * the expected mathematical equivalences between the transforms may not hold. 75 | * (For example, -rot 270 -trim trims only the bottom edge, but -rot 90 -trim 76 | * followed by -rot 180 -trim trims both edges.) 77 | * 78 | * We also offer a "force to grayscale" option, which simply discards the 79 | * chrominance channels of a YCbCr image. This is lossless in the sense that 80 | * the luminance channel is preserved exactly. It's not the same kind of 81 | * thing as the rotate/flip transformations, but it's convenient to handle it 82 | * as part of this package, mainly because the transformation routines have to 83 | * be aware of the option to know how many components to work on. 84 | */ 85 | 86 | typedef struct { 87 | /* Options: set by caller */ 88 | JXFORM_CODE transform; /* image transform operator */ 89 | boolean trim; /* if TRUE, trim partial MCUs as needed */ 90 | boolean force_grayscale; /* if TRUE, convert color image to grayscale */ 91 | 92 | /* Internal workspace: caller should not touch these */ 93 | int num_components; /* # of components in workspace */ 94 | jvirt_barray_ptr * workspace_coef_arrays; /* workspace for transformations */ 95 | } jpeg_transform_info; 96 | 97 | 98 | #if TRANSFORMS_SUPPORTED 99 | 100 | /* Request any required workspace */ 101 | EXTERN(void) jtransform_request_workspace 102 | JPP((j_decompress_ptr srcinfo, jpeg_transform_info *info)); 103 | /* Adjust output image parameters */ 104 | EXTERN(jvirt_barray_ptr *) jtransform_adjust_parameters 105 | JPP((j_decompress_ptr srcinfo, j_compress_ptr dstinfo, 106 | jvirt_barray_ptr *src_coef_arrays, 107 | jpeg_transform_info *info)); 108 | /* Execute the actual transformation, if any */ 109 | EXTERN(void) jtransform_execute_transformation 110 | JPP((j_decompress_ptr srcinfo, j_compress_ptr dstinfo, 111 | jvirt_barray_ptr *src_coef_arrays, 112 | jpeg_transform_info *info)); 113 | 114 | #endif /* TRANSFORMS_SUPPORTED */ 115 | 116 | 117 | /* 118 | * Support for copying optional markers from source to destination file. 119 | */ 120 | 121 | typedef enum { 122 | JCOPYOPT_NONE, /* copy no optional markers */ 123 | JCOPYOPT_COMMENTS, /* copy only comment (COM) markers */ 124 | JCOPYOPT_ALL /* copy all optional markers */ 125 | } JCOPY_OPTION; 126 | 127 | #define JCOPYOPT_DEFAULT JCOPYOPT_COMMENTS /* recommended default */ 128 | 129 | /* Setup decompression object to save desired markers in memory */ 130 | EXTERN(void) jcopy_markers_setup 131 | JPP((j_decompress_ptr srcinfo, JCOPY_OPTION option)); 132 | /* Copy markers saved in the given source object to the destination object */ 133 | EXTERN(void) jcopy_markers_execute 134 | JPP((j_decompress_ptr srcinfo, j_compress_ptr dstinfo, 135 | JCOPY_OPTION option)); 136 | -------------------------------------------------------------------------------- /windows/jpeg/wrtarga.c: -------------------------------------------------------------------------------- 1 | /* 2 | * wrtarga.c 3 | * 4 | * Copyright (C) 1991-1996, Thomas G. Lane. 5 | * This file is part of the Independent JPEG Group's software. 6 | * For conditions of distribution and use, see the accompanying README file. 7 | * 8 | * This file contains routines to write output images in Targa format. 9 | * 10 | * These routines may need modification for non-Unix environments or 11 | * specialized applications. As they stand, they assume output to 12 | * an ordinary stdio stream. 13 | * 14 | * Based on code contributed by Lee Daniel Crocker. 15 | */ 16 | 17 | #include "cdjpeg.h" /* Common decls for cjpeg/djpeg applications */ 18 | 19 | #ifdef TARGA_SUPPORTED 20 | 21 | 22 | /* 23 | * To support 12-bit JPEG data, we'd have to scale output down to 8 bits. 24 | * This is not yet implemented. 25 | */ 26 | 27 | #if BITS_IN_JSAMPLE != 8 28 | Sorry, this code only copes with 8-bit JSAMPLEs. /* deliberate syntax err */ 29 | #endif 30 | 31 | /* 32 | * The output buffer needs to be writable by fwrite(). On PCs, we must 33 | * allocate the buffer in near data space, because we are assuming small-data 34 | * memory model, wherein fwrite() can't reach far memory. If you need to 35 | * process very wide images on a PC, you might have to compile in large-memory 36 | * model, or else replace fwrite() with a putc() loop --- which will be much 37 | * slower. 38 | */ 39 | 40 | 41 | /* Private version of data destination object */ 42 | 43 | typedef struct { 44 | struct djpeg_dest_struct pub; /* public fields */ 45 | 46 | char *iobuffer; /* physical I/O buffer */ 47 | JDIMENSION buffer_width; /* width of one row */ 48 | } tga_dest_struct; 49 | 50 | typedef tga_dest_struct * tga_dest_ptr; 51 | 52 | 53 | LOCAL(void) 54 | write_header (j_decompress_ptr cinfo, djpeg_dest_ptr dinfo, int num_colors) 55 | /* Create and write a Targa header */ 56 | { 57 | char targaheader[18]; 58 | 59 | /* Set unused fields of header to 0 */ 60 | MEMZERO(targaheader, SIZEOF(targaheader)); 61 | 62 | if (num_colors > 0) { 63 | targaheader[1] = 1; /* color map type 1 */ 64 | targaheader[5] = (char) (num_colors & 0xFF); 65 | targaheader[6] = (char) (num_colors >> 8); 66 | targaheader[7] = 24; /* 24 bits per cmap entry */ 67 | } 68 | 69 | targaheader[12] = (char) (cinfo->output_width & 0xFF); 70 | targaheader[13] = (char) (cinfo->output_width >> 8); 71 | targaheader[14] = (char) (cinfo->output_height & 0xFF); 72 | targaheader[15] = (char) (cinfo->output_height >> 8); 73 | targaheader[17] = 0x20; /* Top-down, non-interlaced */ 74 | 75 | if (cinfo->out_color_space == JCS_GRAYSCALE) { 76 | targaheader[2] = 3; /* image type = uncompressed gray-scale */ 77 | targaheader[16] = 8; /* bits per pixel */ 78 | } else { /* must be RGB */ 79 | if (num_colors > 0) { 80 | targaheader[2] = 1; /* image type = colormapped RGB */ 81 | targaheader[16] = 8; 82 | } else { 83 | targaheader[2] = 2; /* image type = uncompressed RGB */ 84 | targaheader[16] = 24; 85 | } 86 | } 87 | 88 | if (JFWRITE(dinfo->output_file, targaheader, 18) != (size_t) 18) 89 | ERREXIT(cinfo, JERR_FILE_WRITE); 90 | } 91 | 92 | 93 | /* 94 | * Write some pixel data. 95 | * In this module rows_supplied will always be 1. 96 | */ 97 | 98 | METHODDEF(void) 99 | put_pixel_rows (j_decompress_ptr cinfo, djpeg_dest_ptr dinfo, 100 | JDIMENSION rows_supplied) 101 | /* used for unquantized full-color output */ 102 | { 103 | tga_dest_ptr dest = (tga_dest_ptr) dinfo; 104 | register JSAMPROW inptr; 105 | register char * outptr; 106 | register JDIMENSION col; 107 | 108 | inptr = dest->pub.buffer[0]; 109 | outptr = dest->iobuffer; 110 | for (col = cinfo->output_width; col > 0; col--) { 111 | outptr[0] = (char) GETJSAMPLE(inptr[2]); /* RGB to BGR order */ 112 | outptr[1] = (char) GETJSAMPLE(inptr[1]); 113 | outptr[2] = (char) GETJSAMPLE(inptr[0]); 114 | inptr += 3, outptr += 3; 115 | } 116 | (void) JFWRITE(dest->pub.output_file, dest->iobuffer, dest->buffer_width); 117 | } 118 | 119 | METHODDEF(void) 120 | put_gray_rows (j_decompress_ptr cinfo, djpeg_dest_ptr dinfo, 121 | JDIMENSION rows_supplied) 122 | /* used for grayscale OR quantized color output */ 123 | { 124 | tga_dest_ptr dest = (tga_dest_ptr) dinfo; 125 | register JSAMPROW inptr; 126 | register char * outptr; 127 | register JDIMENSION col; 128 | 129 | inptr = dest->pub.buffer[0]; 130 | outptr = dest->iobuffer; 131 | for (col = cinfo->output_width; col > 0; col--) { 132 | *outptr++ = (char) GETJSAMPLE(*inptr++); 133 | } 134 | (void) JFWRITE(dest->pub.output_file, dest->iobuffer, dest->buffer_width); 135 | } 136 | 137 | 138 | /* 139 | * Write some demapped pixel data when color quantization is in effect. 140 | * For Targa, this is only applied to grayscale data. 141 | */ 142 | 143 | METHODDEF(void) 144 | put_demapped_gray (j_decompress_ptr cinfo, djpeg_dest_ptr dinfo, 145 | JDIMENSION rows_supplied) 146 | { 147 | tga_dest_ptr dest = (tga_dest_ptr) dinfo; 148 | register JSAMPROW inptr; 149 | register char * outptr; 150 | register JSAMPROW color_map0 = cinfo->colormap[0]; 151 | register JDIMENSION col; 152 | 153 | inptr = dest->pub.buffer[0]; 154 | outptr = dest->iobuffer; 155 | for (col = cinfo->output_width; col > 0; col--) { 156 | *outptr++ = (char) GETJSAMPLE(color_map0[GETJSAMPLE(*inptr++)]); 157 | } 158 | (void) JFWRITE(dest->pub.output_file, dest->iobuffer, dest->buffer_width); 159 | } 160 | 161 | 162 | /* 163 | * Startup: write the file header. 164 | */ 165 | 166 | METHODDEF(void) 167 | start_output_tga (j_decompress_ptr cinfo, djpeg_dest_ptr dinfo) 168 | { 169 | tga_dest_ptr dest = (tga_dest_ptr) dinfo; 170 | int num_colors, i; 171 | FILE *outfile; 172 | 173 | if (cinfo->out_color_space == JCS_GRAYSCALE) { 174 | /* Targa doesn't have a mapped grayscale format, so we will */ 175 | /* demap quantized gray output. Never emit a colormap. */ 176 | write_header(cinfo, dinfo, 0); 177 | if (cinfo->quantize_colors) 178 | dest->pub.put_pixel_rows = put_demapped_gray; 179 | else 180 | dest->pub.put_pixel_rows = put_gray_rows; 181 | } else if (cinfo->out_color_space == JCS_RGB) { 182 | if (cinfo->quantize_colors) { 183 | /* We only support 8-bit colormap indexes, so only 256 colors */ 184 | num_colors = cinfo->actual_number_of_colors; 185 | if (num_colors > 256) 186 | ERREXIT1(cinfo, JERR_TOO_MANY_COLORS, num_colors); 187 | write_header(cinfo, dinfo, num_colors); 188 | /* Write the colormap. Note Targa uses BGR byte order */ 189 | outfile = dest->pub.output_file; 190 | for (i = 0; i < num_colors; i++) { 191 | putc(GETJSAMPLE(cinfo->colormap[2][i]), outfile); 192 | putc(GETJSAMPLE(cinfo->colormap[1][i]), outfile); 193 | putc(GETJSAMPLE(cinfo->colormap[0][i]), outfile); 194 | } 195 | dest->pub.put_pixel_rows = put_gray_rows; 196 | } else { 197 | write_header(cinfo, dinfo, 0); 198 | dest->pub.put_pixel_rows = put_pixel_rows; 199 | } 200 | } else { 201 | ERREXIT(cinfo, JERR_TGA_COLORSPACE); 202 | } 203 | } 204 | 205 | 206 | /* 207 | * Finish up at the end of the file. 208 | */ 209 | 210 | METHODDEF(void) 211 | finish_output_tga (j_decompress_ptr cinfo, djpeg_dest_ptr dinfo) 212 | { 213 | /* Make sure we wrote the output file OK */ 214 | fflush(dinfo->output_file); 215 | if (ferror(dinfo->output_file)) 216 | ERREXIT(cinfo, JERR_FILE_WRITE); 217 | } 218 | 219 | 220 | /* 221 | * The module selection routine for Targa format output. 222 | */ 223 | 224 | GLOBAL(djpeg_dest_ptr) 225 | jinit_write_targa (j_decompress_ptr cinfo) 226 | { 227 | tga_dest_ptr dest; 228 | 229 | /* Create module interface object, fill in method pointers */ 230 | dest = (tga_dest_ptr) 231 | (*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_IMAGE, 232 | SIZEOF(tga_dest_struct)); 233 | dest->pub.start_output = start_output_tga; 234 | dest->pub.finish_output = finish_output_tga; 235 | 236 | /* Calculate output image dimensions so we can allocate space */ 237 | jpeg_calc_output_dimensions(cinfo); 238 | 239 | /* Create I/O buffer. Note we make this near on a PC. */ 240 | dest->buffer_width = cinfo->output_width * cinfo->output_components; 241 | dest->iobuffer = (char *) 242 | (*cinfo->mem->alloc_small) ((j_common_ptr) cinfo, JPOOL_IMAGE, 243 | (size_t) (dest->buffer_width * SIZEOF(char))); 244 | 245 | /* Create decompressor output buffer. */ 246 | dest->pub.buffer = (*cinfo->mem->alloc_sarray) 247 | ((j_common_ptr) cinfo, JPOOL_IMAGE, dest->buffer_width, (JDIMENSION) 1); 248 | dest->pub.buffer_height = 1; 249 | 250 | return (djpeg_dest_ptr) dest; 251 | } 252 | 253 | #endif /* TARGA_SUPPORTED */ 254 | --------------------------------------------------------------------------------