DIRECTORY IODefs: FROM "iodefs", StreamDefs: FROM "streamdefs", StringDefs: FROM "stringdefs", SystemDefs: FROM "systemdefs", PressDefs: FROM "pressdefs"; B7Page: PROGRAM IMPORTS IODefs, StreamDefs, StringDefs, SystemDefs, PressDefs = BEGIN Font:TYPE = POINTER TO FontBody; FontBody:TYPE = RECORD[family:STRING, size:CARDINAL _ 0, face:CARDINAL _ 0, rotation:CARDINAL _ 0, widths:Widths _ NIL]; Widths:TYPE = POINTER TO WidthBody; WidthBody:TYPE = RECORD[micaX:ARRAY [0..256) OF INTEGER, bBox:ARRAY [0..4) OF INTEGER]; JustificationMode: TYPE = {leftJustified, rightJustified, centered, bottomJustified, topJustified}; labelFont, entryFont, titleFont, commentFont, quoteFont: Font _ NIL; wStream:StreamDefs.StreamHandle; --Fonts.Widths stream outFile:POINTER TO PressDefs.PressFileDescriptor; outFileName:STRING = "B7Page.Press"; str:STRING _ [15]; row,column:CARDINAL; char:CHARACTER; leftEdge:CARDINAL_4000; rightEdge:CARDINAL_19000; bottomEdge:CARDINAL_6000; topEdge:CARDINAL_24800; gridWidth:CARDINAL_20; labelMargin:CARDINAL_200; titleMargin:CARDINAL_700; title:STRING = "Bravo 7"; comment1:STRING = "Here is the story on Bravo 7: each column designates one key stroke. The codes ^I=#011, ^L=#014,"; comment2:STRING = "^M=#015, and ^Z=#032 have formatting functions that preclude their use as printing characters,"; comment3:STRING = "while DEL=#177 can't be typed; ^J=#012 only spaces correctly in Hardcopy mode."; numCols:CARDINAL=8; numRows:CARDINAL=16; colWidth:CARDINAL=(rightEdge-leftEdge)/numCols; rowHeight:CARDINAL=(topEdge-bottomEdge)/numRows; FindWidths: PROCEDURE[f:Font]= BEGIN success:BOOLEAN; IF f=NIL THEN ERROR AttemptToFindWidthsOfNIL; f.widths _ SystemDefs.AllocateHeapNode[SIZE[WidthBody]]; success _ PressDefs.LookupFontName[wStream, f.family, f.face, f.size, f.rotation, @f.widths.micaX, NIL, @f.widths.bBox]; IF ~success THEN ERROR FontNotInWidthDictionary; END; FontNotInWidthDictionary: SIGNAL = CODE; AttemptToFindWidthsOfNIL: SIGNAL = CODE; PutString: PROCEDURE[s:STRING,f:Font,x,y:CARDINAL,m:JustificationMode]= BEGIN length:CARDINAL _ 0; height, i:CARDINAL; IF f.widths=NIL THEN ERROR FontHasNoWidthData; FOR i IN [0..s.length) DO length _ length+f.widths.micaX[s[i]-0C]; ENDLOOP; height _ f.widths.bBox[3]*8/10; SELECT m FROM leftJustified => BEGIN y _ y-height/2 END; rightJustified => BEGIN y _ y-height/2; x _ x-length END; centered => BEGIN y _ y-height/2; x _ x-length/2 END; topJustified => BEGIN y _ y-height; x _ x-length/2 END; bottomJustified => BEGIN x _ x-length/2 END; ENDCASE; PressDefs.SetFont[outFile, f.family, f.size, f.face, f.rotation]; PressDefs.PutText[outFile, s, x, y]; END; FontHasNoWidthData:SIGNAL = CODE; InitFont: PROCEDURE[fam:STRING, size:CARDINAL, face,rot:CARDINAL _ 0] RETURNS [Font] = BEGIN f:Font; f _ SystemDefs.AllocateHeapNode[SIZE[FontBody]]; f^ _ FontBody[fam,size,face,rot,NIL]; RETURN [f]; END; PutChar: PROCEDURE[char:CHARACTER, font:Font,x,y:CARDINAL] = INLINE BEGIN string:STRING _ [1]; string.length _ 1; string[0] _ char; PutString[string,font,x,y,centered]; END; PutStringChar: PROCEDURE[string1:STRING,font1:Font,char:CHARACTER, font2:Font,x,y:CARDINAL] = INLINE BEGIN string2:STRING _ [1]; string2.length _ 1; string2[0] _ char; PutStringString[string1,font1,string2,font2,x,y]; END; PutStringString: PROCEDURE[string1:STRING,font1:Font,string2:STRING, font2:Font,x,y:CARDINAL] = INLINE BEGIN PutString[string1,font1,x,y+50,bottomJustified]; PutString[string2,font2,x,y,topJustified]; END; PutCharS: PROCEDURE[char:CHARACTER, font:Font,x,y:CARDINAL] = BEGIN PutStringString["ctrl",font,"s",font,x+300,y]; PutChar[char,font,x-400,y]; END; IODefs.WriteLine["Starting:"]; wStream _ StreamDefs.NewWordStream["Fonts.Widths", StreamDefs.Read]; outFile _ SystemDefs.AllocateHeapNode[SIZE[PressDefs.PressFileDescriptor]]; PressDefs.InitPressFileDescriptor[outFile,outFileName]; labelFont _ InitFont["TimesRoman",10]; entryFont _ InitFont["TimesRoman",10]; titleFont _ InitFont["TimesRoman",18,2]; commentFont _ InitFont["TimesRoman",10]; quoteFont _ InitFont["Gacha",12]; FindWidths[labelFont]; FindWidths[entryFont]; FindWidths[titleFont]; FindWidths[commentFont]; FindWidths[quoteFont]; --Put down the rules of the grid; FOR row IN [0..numRows] DO PressDefs.PutRectangle[outFile,leftEdge,bottomEdge+row*rowHeight, numCols*colWidth+gridWidth,gridWidth] ENDLOOP; FOR column IN [0..numCols] DO PressDefs.PutRectangle[outFile,leftEdge+column*colWidth,bottomEdge, gridWidth,numRows*rowHeight+gridWidth] ENDLOOP; --Put numeric labels on the grid, in labelFont; FOR column IN [0..numCols) DO str[0]_('0)+column; str.length _ 1; PutString[str, labelFont, leftEdge+colWidth/2+column*colWidth, bottomEdge+labelMargin+numRows*rowHeight,bottomJustified]; ENDLOOP; FOR row IN [0..numRows) DO str.length_0; StringDefs.AppendChar[str,'#]; SELECT row*numCols FROM IN [0B..7B] => StringDefs.AppendString[str,"00"]; IN [10B..77B] => StringDefs.AppendString[str,"0"]; ENDCASE; StringDefs.AppendNumber[str,row*numCols,8]; PutString[str, labelFont, leftEdge-labelMargin, bottomEdge+(numRows-row)*rowHeight-(rowHeight/2), rightJustified]; ENDLOOP; --put title at the bottom of the page PutString[title, titleFont, leftEdge+(numCols*colWidth/2), bottomEdge-titleMargin, topJustified]; --and add comments below it PutString[comment1,commentFont,leftEdge-1000,bottomEdge*6/10,leftJustified]; PutString[comment2,commentFont,leftEdge-1000,bottomEdge/2,leftJustified]; PutString[comment3,commentFont,leftEdge-1000,bottomEdge*4/10,leftJustified]; --start putting in keys FOR char IN [0C..177C] DO BEGIN l:CARDINAL; x,y,row,column:CARDINAL; l_char-0C; row_l/numCols; column _ l MOD numCols; x _ leftEdge+column*colWidth+colWidth/2; y _ bottomEdge+(numRows-row)*rowHeight-rowHeight/2; SELECT char FROM =0C => PutCharS[char+100B,commentFont,x,y]; IN [1C..10C] => PutCharS[char+140B,commentFont,x,y]; =11C => NULL; IN [12C..13C]=> PutCharS[char+140B,commentFont,x,y]; IN [14C..15C] => NULL; IN [16C..31C]=> PutCharS[char+140B,commentFont,x,y]; =32C => NULL; IN [33C..37C]=> PutCharS[char+100B,commentFont,x,y]; =40C => PutString["space",commentFont,x,y,centered]; =41C => PutChar[char,entryFont,x,y]; =42C => PutChar[char,quoteFont,x,y]; IN [43C..46C] => PutChar[char,entryFont,x,y]; =47C => PutChar[char,quoteFont,x,y]; IN [50C..54C] => PutChar[char,entryFont,x,y]; =55C => PutChar[30C,entryFont,x,y]; IN [56C..100C] => PutChar[char,entryFont,x,y]; IN [101C..132C] => PutStringChar["shift",commentFont,char+40B,entryFont, x,y]; IN [133C..137C] => PutChar[char,entryFont,x,y]; =140C => PutStringChar["shift",commentFont,30C,entryFont, x,y]; IN [141C..176C] => PutChar[char,entryFont,x,y]; =177C => NULL; ENDCASE; END ENDLOOP; PressDefs.WritePage[outFile]; PressDefs.ClosePressFile[outFile]; IODefs.WriteLine[""]; IODefs.WriteLine["Done."] END. (635)\f1 166f0b6f1B82b4B29b8B115b6B30b9B81b18B1031b13B29f0 17f1 374b12B738b10B212b7B180b13B226b15B203b8B