%!PS % PostScript Array to Image Conversion % ==================================== % by Don Lancaster %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % Copyright c 2007 by Don Lancaster & Synergetics, Box 809, Thatcher, AZ, 85552 % (928) 428-4073 Email: don@tinaja.com Website: http://www.tinaja.com % Consulting services available http://www.tinaja.com/info01.html % All commercial rights and all electronic media rights ~fully~ reserved. % Linking usually welcome. Reposting expressly forbidden. Version 1.5 % ========= % IMPORTANT NOTE: Don Lancaster's file gonzo.ps is required for the demos in % this program. The actual utilities can stand alone. % After obvious location mods, uncomment ONE of the following two lines: (C:/Users/don/Desktop/gonzo/gonzo.psl) run % use internal gonzo % (A:\\gonzo.ps) run % use external gonzo % NOTE THAT ALL PS FILENAME STRINGS !!!DEMAND!!! DOUBLE REVERSE SLASHES. % Also note that Acrobat 8.1 or higher defaults to prevent most PS disk access. % The workaround is to prerun Distiller from the Windows command line using "acrodist -F". % Any .PSL file can then be dragged and dropped into any Distiller on or under the desktop. % GONZO20A Guru Gonzo PostScript power tools (Interim release) % Includes gonzo justification and layout utilities. % Copyright c 1990, 1996, 2001 by Don Lancaster and Synergetics, Box 809, % Thatcher Arizona, 5552 (928) 428-4073 don@tinaja.com support % via http://www.tinaja.com All commercial rights and all electronic % media rights **FULLY** reserved. Reposting is expressly forbidden. % ===================================== % The PostScript string operator has a number of advantages over a normal % array in that it stores info more compactly, can be read and written to as a % file, has more operators available to it, and still behaves as an array % with such operators as get, put, or {} forall. % A data structure of an array-of-strings can be a potent means of storing % and manipulating x-y data that ultimately comes from or becomes a PS image % or a conventional .BMP data file. % A group of utilities that simplify and ease the use of PostScript % array-of-strings is presented here. % A complete tutorial appears as http://www.tinaja.com/glib/bmp2psa.pdf % Its sourcecode is available as http://www.tinaja.com/glib/bmp2psa.psl % demos below require your own new bitmaps and relocation renaming! %%%%%%%%%% (A) MERGE STRING UTILITY %%%%%%%%%%%%%%%%%%%%%% % Excerpted from the Gonzo Utilities at http://www.tinaja.com/glib/gonzotut.pdf % Useful in combining filenames and as a general tool. /mergestr {2 copy length exch length add string dup dup 4 3 roll 4 index length exch putinterval 3 1 roll exch 0 exch putinterval} def (Hello ) (there.) mergestr == % returns (Hello there.)if uncommented %%%%%%%%%% (B) STRING TO ARRAY CONVERTER %%%%%%%%%%%%%%%%%%%%%% /string2array {mark exch { } forall ] } store (Hello!) string2array % should return [72 101 108 108 111 33]. == % comment to remove %%%%%%%%%% (C) ARRAY TO STRING CONVERTER %%%%%%%%%%%%%%%%%%%%%% /array2string {dup length string dup /NullEncode filter 3 -1 roll {1 index exch write} forall pop } def [72 105 32 116 104 101 114 101] array2string == % returns(Hi there). %%%%%%%%%%%% (D) STRING READ FROM AS A FILE %%%%%%%%%%%%%%%%%%%%%%% /str1 (This is a test) store /file1 str1 0 (%EOF) /SubFileDecode filter store 6 { file1 read pop == } repeat % should return 84 104 105 115 32 105. %%%%%%%%%%%% (E) STRING WRITTEN TO AS A FILE %%%%%%%%%%%%%%%%%%%%%%% /str2 (zzzzzzzzzzzzzzzzzzz) store /file2 str2 /NullEncode filter store file2 65 write file2 66 write file2 67 write % should return (ABCzzzzzzzzzzzzzzzz). str2 == % if uncommented %%%%%%%%%% (F) CREATE DEMO ARRAY-OF-STRINGS FILES %%%%%%%%%%%%% % these workfiles can be useful for developing and testing the utilities that follow % data shown creates a 6 pixel wide by 3 pixel high image with a rainbow on the bottom % row, gray elsewhere except for an upper right red pixel. /redAOS [ [250 250 0 0 0 250 ] array2string [100 100 100 100 100 100 ] array2string [100 100 100 100 100 250 ] array2string ] store /greenAOS [ [ 0 250 250 250 0 0 ] array2string [100 100 100 100 100 100 ] array2string [100 100 100 100 100 0 ] array2string ] store /blueAOS [ [ 0 0 0 250 250 250 ] array2string [100 100 100 100 100 100 ] array2string [100 100 100 100 100 0 ] array2string ] store %%%%%%%%%%%% (G) CONVERT ARRAYS-OF-STRINGS TO A POSTSCRIPT IMAGE %%%%%%%%%%% % three AOS string gathering procs needed by image... /getredAOSrow {redAOS AOSrowcount get} store /getgreenAOSrow {greenAOS AOSrowcount get} store /getblueAOSrow {blueAOS AOSrowcount get /AOSrowcount AOSrowcount 1 add store } store % increment row counter for all gets % the AOS to image converter maps the AOS into a unit square. Scaling to final size and shape % must be done by CTM mods... /convertAOStoPSimage { /AOSrowcount 0 store << /ImageType 1 /Width redAOS 0 get length /Height redAOS length /ImageMatrix [redAOS 0 get length 0 0 redAOS length 0 0 ] /MultipleDataSources true /DataSource [ {getredAOSrow} {getgreenAOSrow} {getblueAOSrow}] /BitsPerComponent 8 /Decode [ 0 1 0 1 0 1 ] /Interpolate false /AOSrowcount 0 store % custom proc added here >> dup begin image end } bind store % uncomment for demo 0 0 0 setrgbcolor 50 50 10 setgrid % requires Gonzo 20 20 showgrid % requires Gonzo convertAOStoPSimage showpage %%%%%%%%%%%% (H) CONVERT ARRAY-OF-STRINGS TO A .BMP BITMAP %%%%%%%%%%% % requires arrayfilepathprefix path and outputbitmap filenames defined. % Also valid data in redAOS, greenAOS, and blueAOS. /convertAOS2BMPimage { /bmpoutfile arrayfilepathprefix % make bmp write file outputbitmapfilename mergestr (w+) file store %(w+) aids debug /xpixels redAOS 0 get length store % calc bmp data /ypixels redAOS length store /padcount xpixels 4 mod % calc bmp padding [0 3 2 1] exch get store /totalbmpsize xpixels padcount % calc file length add ypixels mul 54 add store bmpoutfile 66 write % BEGIN HEADER bmpoutfile 77 write % with ASCII "BM". totalbmpsize 256 3 exp cvi idiv % calc length byte /byte4 exch store totalbmpsize 256 3 exp cvi mod /res3 exch store res3 65536 idiv /byte3 exch store res3 65536 mod /res2 exch store res2 256 idiv /byte2 exch store res2 256 mod /byte1 exch store bmpoutfile byte1 write % write length as modulo 256 bmpoutfile byte2 write bmpoutfile byte3 write bmpoutfile byte4 write 4 {bmpoutfile 0 write} repeat % four reserved nulls bmpoutfile 54 write % start of data offset bmpoutfile 0 write bmpoutfile 0 write bmpoutfile 0 write bmpoutfile 40 write % write data header size bmpoutfile 0 write bmpoutfile 0 write bmpoutfile 0 write bmpoutfile xpixels 256 mod write % write x size lsbs bmpoutfile xpixels 256 idiv write bmpoutfile 0 write % assume < 65K bmpoutfile 0 write bmpoutfile ypixels 256 mod write % write y size lsbs bmpoutfile ypixels 256 idiv write bmpoutfile 0 write % assume < 65K bmpoutfile 0 write bmpoutfile 1 write % number of bit planes bmpoutfile 0 write bmpoutfile 24 write % write color mode bmpoutfile 0 write 4 {bmpoutfile 0 write} repeat % compression mode 4 {bmpoutfile 0 write} repeat % pixel data size 4 {bmpoutfile 0 write} repeat % width resolution 4 {bmpoutfile 0 write} repeat % height resolution 4 {bmpoutfile 0 write} repeat % colors used 4 {bmpoutfile 0 write} repeat % important colors 0 1 ypixels 1 sub {/currow exch store % start data write /curred redAOS currow get store % grab RGB row data /curgreen greenAOS currow get store /curblue blueAOS currow get store 0 1 xpixels 1 sub {/curpos exch store % BGR pixel write bmpoutfile curblue curpos get write bmpoutfile curgreen curpos get write bmpoutfile curred curpos get write } for % finish row padcount {bmpoutfile 0 write } repeat % add row padding } for % finish image bmpoutfile closefile % close file % this is an extremely small bitmap!!! view at 1600%. } bind store % and exit % uncomment for demo /arrayfilepathprefix (C:/Users/don/Desktop/web/new_psutils818/psutils/test/aosutil1/) store /outputbitmapfilename (bmpout1.bmp) store convertAOS2BMPimage %%%%%%%%%%%% (I) CONVERT A .BMP BITMAP TO A PS ARRAY-OF-STRINGS %%%%%%%%%%% % requires a predefined arrayfilepathprefix and inputtbitmapfilename /inputbitmap2AOS { % START ANALYSIS /bmpinfile arrayfilepathprefix % create .BMP read file inputtbitmapfilename mergestr (r) file store bmpinfile read % check for ok format pop 66 eq % "B" as first character? bmpinfile read pop 77 eq and % "M" as second char? bmpinfile 26 setfileposition % one color plane? bmpinfile read pop 1 eq and not {NOT_A_BITMAP_FILE!} if % report bitmap error bmpinfile 28 setfileposition % report color message bmpinfile read pop 24 eq not {NOT_24_BIT_COLOR!} if bmpinfile 10 setfileposition % find the offset bmpinfile read pop bmpinfile read pop 256 mul add /offset exch store bmpinfile 18 setfileposition % find the xpixels bmpinfile read pop bmpinfile read pop 256 mul add /xpixels exch store bmpinfile 22 setfileposition % find the ypixels bmpinfile read pop bmpinfile read pop 256 mul add /ypixels exch store /padcount xpixels 4 mod % calculate padding [0 3 2 1] exch get store /redAOS ypixels array store % empty AOS arrays /greenAOS ypixels array store /blueAOS ypixels array store 0 1 ypixels 1 sub {/rowcount exch store % GRAB DATA by rows bmpinfile offset % go to row start rowcount xpixels 3 mul % X3 for triads padcount add mul % plus padding add setfileposition % set row start /redAOSrow xpixels string store % create rows /greenAOSrow xpixels string store /blueAOSrow xpixels string store 0 1 xpixels 1 sub {/posn exch store % for each pixel triad blueAOSrow posn bmpinfile read pop put % blue greenAOSrow posn bmpinfile read pop put % green redAOSrow posn bmpinfile read pop put % red } for % till row done redAOS rowcount redAOSrow put % place strings greenAOS rowcount greenAOSrow put blueAOS rowcount blueAOSrow put } for % for each row } bind store % completing proc % uncomment for round trip demo BMP ----- PS AOS ----> BMP % requires preplaced .BMP file data source or name change /arrayfilepathprefix (C:/Users/don/Desktop/web/new_psutils818/psutils/test/aosutil1/) store /inputtbitmapfilename (smalla.bmp) store /outputtbitmapfilename (smallz.bmp) store inputbitmap2AOS convertAOS2BMPimage gsave 0 0 0 setrgbcolor 50 50 translate 372 354 scale convertAOStoPSimage grestore showpage % EOF