DIRECTORY Ascii, NodeStyle, NodeStyleExtra, NodeStyleObject, TextLooks, NameSymbolTable, Real, SafeStorage, TJaMOps, TJaMBasic; NodeStyleTabsImpl: CEDAR PROGRAM IMPORTS Ascii, TJaMOps, NodeStyle, NodeStyleExtra, NodeStyleObject, Real EXPORTS NodeStyle, NodeStyleExtra = BEGIN OPEN R:Real, NodeStyle, NodeStyleExtra, NodeStyleObject; RulesTabCount: PUBLIC PROC [stop: RulesTabStop] RETURNS [count: INTEGER] = { RETURN [stop.array.length/2] }; RulesTabInfo: PUBLIC PROC [stop: RulesTabStop, num: INTEGER] RETURNS [weight, vshift: REAL] = TRUSTED { ObjectToReal: PROC [ob: TJaMBasic.Object] RETURNS [Real] = TRUSTED { WITH ob:ob SELECT FROM integer => RETURN[ob.ivalue]; real => RETURN[ob.rvalue]; ENDCASE => ERROR }; weight _ ObjectToReal[TJaMOps.AGet[stop.array, num*2]]; vshift _ ObjectToReal[TJaMOps.AGet[stop.array, num*2+1]] }; RulesTabInfoI: PUBLIC PROC [stop: RulesTabStop, num: INTEGER] RETURNS [weight, vshift: INTEGER] = TRUSTED { ObjectToInteger: PROC [ob: TJaMBasic.Object] RETURNS [INTEGER] = TRUSTED { WITH ob:ob SELECT FROM integer => RETURN[ob.ivalue]; real => RETURN[R.RoundI[ob.rvalue]]; ENDCASE => ERROR }; weight _ ObjectToInteger[TJaMOps.AGet[stop.array, num*2]]; vshift _ ObjectToInteger[TJaMOps.AGet[stop.array, num*2+1]] }; GetTabRealCode: PROC [ref: Ref, stop: TabStop, which: TabRealParam, value: Real] RETURNS [code: RealCode] = { code _ EnterReal[value ! realTableOverflow => { code _ overflow; ref.dataList _ NEW[DataEntry _ [ ref.dataList, tab[stop, which, value, IntegerValue[value]]]]; CONTINUE }] }; GetTabOverflow: PUBLIC PROC [ref: Ref, stop: TabStop, which: TabRealParam] RETURNS [value: Real] = { FOR x: DataList _ ref.dataList, x.next UNTIL x=NIL DO xx: REF DataEntry.tab = NARROW[x]; IF xx.tabStop=stop AND xx.which=which THEN RETURN [xx.value]; ENDLOOP; ERROR -- failed to find it on the data list -- }; GetTabIntOverflow: PUBLIC PROC [ref: Ref, stop: TabStop, which: TabRealParam] RETURNS [value: INTEGER] = { FOR x: DataList _ ref.dataList, x.next UNTIL x=NIL DO xx: REF DataEntry.tab = NARROW[x]; IF xx.tabStop=stop AND xx.which=which THEN RETURN [xx.valueI]; ENDLOOP; ERROR -- failed to find it on the data list -- }; RelativeTabStopsOp: PUBLIC PROC [frame: Frame] = { ref: Ref _ StyleForFrame[frame]; name: Name; ok: BOOL; [name, ok] _ TryToPopName[frame]; IF ~ok THEN { -- restore name to stack and return default PushText[frame,"illegal value for tabStops: should be fixed or relative"L]; StyleError[frame,1] }; SELECT name FROM fixed => ref.fixedTabs _ TRUE; relative => ref.fixedTabs _ FALSE; ENDCASE => { -- restore name to stack and return default PushName[frame, name]; PushText[frame,"illegal value for tabStops: should be fixed or relative"L]; StyleError[frame,2] }}; DefaultTabStopsOp: PUBLIC PROC [frame: Frame] = { ref: Ref _ StyleForFrame[frame]; tabStop: TabStop _ TabSpec[ref, frame]; tabStop.loc _ GetTabRealCode[ref, tabStop, loc, PopReal[frame]]; ref.defaultTabStops _ tabStop }; TabStopOp: PUBLIC PROC [frame: Frame] = { ref: Ref _ StyleForFrame[frame]; tabStop: TabStop _ TabSpec[ref, frame]; loc: Real; tabStop.loc _ GetTabRealCode[ref, tabStop, loc, PopReal[frame]]; loc _ GetTabLoc[tabStop, ref]; ref.numTabStops _ ref.numTabStops+1; IF ref.tabStops = NIL OR GetTabLoc[ref.tabStops.first, ref] <= loc THEN ref.tabStops _ CONS[tabStop, ref.tabStops] ELSE { -- copy list up to first with smaller loc old: LIST OF TabStop _ ref.tabStops; new: LIST OF TabStop _ CONS[old.first, NIL]; ref.tabStops _ new; FOR lst: LIST OF TabStop _ old.rest, lst.rest DO IF lst=NIL OR GetTabLoc[lst.first, ref] <= loc THEN { -- insert here new.rest _ CONS[tabStop, lst]; EXIT }; new.rest _ CONS[lst.first, NIL]; new _ new.rest; ENDLOOP }}; TabSpec: PROC [ref: Ref, frame: Frame] RETURNS [tabStop: TabStop] = { -- parse tab specs looks: TextLooks.Looks _ TabLooksSpec[frame]; breakIfPast: BOOL _ TabPastSpec[frame]; tabStop _ TabPattern[ref, frame]; tabStop.looks _ looks; tabStop.breakIfPast _ breakIfPast; TabAlign[tabStop, frame] }; TabLooksSpec: PROC [frame: Frame] RETURNS [lks: TextLooks.Looks] = TRUSTED { name: Name; ok: BOOL; SetLookBit: PROC [look: CHAR] RETURNS [quit: BOOL] = TRUSTED { look _ Ascii.Lower[look]; IF look IN ['a..'z] THEN lks[look] _ TRUE; RETURN [FALSE] }; lks _ TextLooks.noLooks; [name, ok] _ TryToPopName[frame]; IF ~ok THEN RETURN; IF name # looks THEN { PushName[frame, name]; RETURN }; TJaMOps.StringForAll[TJaMOps.PopString[frame.opstk], SetLookBit]; }; TabPastSpec: PROC [frame: Frame] RETURNS [break: BOOL] = { name: Name; ok: BOOL; [name, ok] _ TryToPopName[frame]; IF ~ok THEN RETURN; SELECT name FROM breakIfPast => break _ TRUE; spaceIfPast => break _ FALSE; ENDCASE => { -- restore name to stack and return default PushName[frame, name]; break _ FALSE }}; TabPattern: PROC [ref: Ref, frame: Frame] RETURNS [tabStop: TabStop] = { name: Name; ok: BOOL; [name, ok] _ TryToPopName[frame]; IF ~ok THEN { tabStop _ NEW[blank TabStopRec]; RETURN }; SELECT name FROM blank => tabStop _ NEW[blank TabStopRec]; leaders => { leaderChar: BOOL _ FALSE; string: string TJaMBasic.Object; value: Real; SetLeaderChar: PROC [c: CHAR] RETURNS [quit: BOOL] = { IF leaderChar THEN { PushText[frame,"Cannot specify more than one character for tab leaders"L]; StyleError[frame,1] }; leaderChar _ TRUE; ldrStop.char _ c }; ldrStop: LeaderTabStop _ NEW[leaders TabStopRec]; tabStop _ ldrStop; [name, ok] _ TryToPopName[frame]; IF ~ok THEN ldrStop.congruent _ TRUE ELSE SELECT name FROM centered => ldrStop.congruent _ FALSE; congruent => ldrStop.congruent _ TRUE; ENDCASE => { PushName[frame,name]; PushText[frame,"is not legal as value for tab leaders: congruent or centered"L]; StyleError[frame,2] }; [value, ok] _ TryToPopReal[frame]; ldrStop.spacing _ GetTabRealCode[ref, tabStop, spacing, IF ok THEN value ELSE 0.0]; [string, ok] _ TryToPopString[frame]; IF ok THEN TRUSTED {TJaMOps.StringForAll[string, SetLeaderChar]} ELSE { PushText[frame,"Must specify character for leaders"L]; StyleError[frame,1] }}; rule => { ruleStop: RuleTabStop _ NEW[rule TabStopRec]; tabStop _ ruleStop; ruleStop.vshift _ GetTabRealCode[ref, tabStop, vshift, PopReal[frame]]; ruleStop.weight _ GetTabRealCode[ref, tabStop, weight, PopReal[frame]] }; rules => { rulesStop: RulesTabStop _ NEW[rules TabStopRec]; tabStop _ rulesStop; TRUSTED {rulesStop.array _ TJaMOps.PopArray[frame.opstk] }}; ENDCASE => { PushName[frame, name]; tabStop _ NEW[blank TabStopRec] }}; MissingChar: PROC [frame: Frame] = { PushText[frame,"Cannot specify more than one character for tab alignment"L]; StyleError[frame,1] }; TabAlign: PROC [tabStop: TabStop, frame: Frame] = { name: Name; ok: BOOL; [name, ok] _ TryToPopName[frame]; IF ~ok THEN { tabStop.alignment _ FlushLeft; RETURN }; SELECT name FROM flushLeft => tabStop.alignment _ FlushLeft; flushRight => tabStop.alignment _ FlushRight; centered => tabStop.alignment _ Centered; aligned => { alignmentChar: BOOL _ FALSE; string: string TJaMBasic.Object; SetAlignmentChar: PROC [c: CHAR] RETURNS [quit: BOOL] = { IF alignmentChar THEN { PushText[frame,"Cannot specify more than one character for tab alignment"L]; StyleError[frame,1] }; alignmentChar _ TRUE; tabStop.alignmentChar _ c }; tabStop.alignment _ Character; [string, ok] _ TryToPopString[frame]; IF ok THEN TRUSTED {TJaMOps.StringForAll[string, SetAlignmentChar]} ELSE { PushText[frame,"Must specify character for tab alignment"L]; StyleError[frame,1] }}; ENDCASE => { PushName[frame, name]; tabStop.alignment _ FlushLeft }}; END... NodeStyleTabsImpl.mesa Copyright c 1985 by Xerox Corporation. All rights reserved. Written by Bill Paxton, December 1981 Bill Paxton, December 1, 1982 7:38 am Maxwell, January 6, 1983 10:15 am Paul Rovner, August 10, 1983 4:42 pm Plass, March 1, 1985 4:35:56 pm PST Doug Wyatt, March 3, 1985 4:14:42 pm PST Russ Atkinson (RRA) March 7, 1985 3:38:22 am PST Implements TJaM commands for tab specifications Rules tabs procs For num in [0..RulesTabCount), returns the weight and vshift values for that rule. Real table overflow for tab reals Miscellaneous commands Parsing tab specs Insert in list of tab stops. kept sorted by decreasing location, i.e., from right to left on page this may result in a slight decrease in efficiency for the formatters, but it substantially reduces allocations during the creation of the list since styles tend to define tab stops in increasing order, so can add to start of list and list additions must be non-destructive of the previous list restore name to stack and return default Κ ˜codešœ™Kšœ Οmœ1™K˜K˜K™™š Οn œžœžœžœ žœ˜LKšžœ˜K˜—š  œžœžœžœ˜˜>—K˜—™!K™š œžœ<˜PKšžœ˜šœ/˜/Kšœ˜šœžœ˜ Kšœ=˜=—Kšžœ˜—K˜—š œžœžœ/˜JKšžœ˜šžœ$žœžœž˜5Kšœžœžœ˜"Kšžœžœžœžœ ˜=Kšžœ˜—KšžœΟc(œ˜1K˜—š œžœžœ/˜MKšžœ žœ˜šžœ$žœžœž˜5Kšœžœžœ˜"Kšžœžœžœžœ ˜>Kšžœ˜—Kšžœ‘(œ˜1K˜——™K™š œžœžœ˜2K˜ Kšœ ˜ Kšœžœ˜ K˜!šžœžœ‘+˜9K˜KKšœ˜—šžœž˜Kšœžœ˜Kšœžœ˜"šžœ‘+˜8Kšœ˜K˜KKšœ˜——K˜—š œžœžœ˜1K˜ Kšœ'˜'K˜@Kšœ ˜ —K™—™K™š  œžœžœ˜)K˜ Kšœ'˜'K˜ K˜@šœb™bKšœ¦™¦—K˜Kšœ$˜$šžœžœžœ+ž˜GKšœžœ˜*—šžœ‘)˜0Kšœžœžœ˜$Kš œžœžœ žœ žœ˜,Kšœ˜šžœžœžœž˜0š žœžœžœ"žœ‘˜DKšœ žœžœ˜&—Kšœ žœ žœ˜ K˜Kšžœ˜ ——K˜—š œžœžœ‘˜XKšœ-˜-Kšœ žœ˜'Kšœ!˜!Kšœ˜Kšœ"˜"K˜K˜—š  œžœžœžœ˜LKšœ ˜ Kšœžœ˜ š   œžœžœžœžœžœ˜>Kšœ˜Kšžœžœ žœ žœ˜*Kšžœžœ˜—K˜K˜!Kšžœžœžœ˜Kšžœžœžœ˜7KšœA˜AK˜K˜—š  œžœžœ žœ˜:Kšœ ˜ Kšœžœ˜ K˜!Kšžœžœžœ˜šžœž˜Kšœžœ˜Kšœžœ˜šžœ‘+˜8Kšœ˜Kšœžœ˜——K˜—š  œžœžœ˜HKšœ ˜ Kšœžœ˜ K˜!Kšžœžœ žœžœ˜8Kšžœž˜Kšœžœ˜)˜ Kšœ žœžœ˜K˜ K˜ š   œžœžœžœžœ˜6šžœ žœ˜K˜JK˜—Kšœ žœ˜Kšœ˜—Kšœžœ˜1K˜K˜!Kšžœžœž˜$šžœžœž˜Kšœ žœ˜&Kšœ!žœ˜&šžœ˜ K˜K˜PK˜——K˜"Kšœ8žœžœžœ˜SK˜%Kšžœžœžœ.˜@šžœ˜Kšœ6˜6Kšœ˜——˜ Kšœžœ˜-Kšœ˜KšœG˜GKšœI˜I—˜ Kšœžœ˜0Kšœ˜Kšžœ5˜<—šžœ˜ Kšœ(™(Kšœ˜Kšœ žœ˜#—K˜—š  œžœ˜$K˜LK˜K˜—š œžœ%˜3Kšœ ˜ Kšœžœ˜ K˜!Kšžœžœ"žœ˜6Kšžœž˜Kšœ+˜+Kšœ-˜-Kšœ)˜)šœ ˜ Kšœžœžœ˜K˜ š  œžœžœžœžœ˜9šžœžœ˜K˜LK˜—Kšœžœ˜Kšœ˜—Kšœ˜K˜%Kšžœžœžœ1˜Cšžœ˜Kšœ<˜