<> <> <> <> <> <<>> DIRECTORY IO USING [STREAM, PutChar], Commander USING [Register, CommandProc], List USING [Append, Assoc, PutAssoc], Rope USING [ROPE, Cat], JaM USING [Any, Create, Execute, ExecuteRope, LineComplete, Register, RopeToAtom, SetAbort, State, Store, Stop], ReadEvalPrint USING [ClientProc, CreateStreamEvaluator, Handle, MainLoop], Menus USING [MenuProc, InsertMenuEntry], MBQueue USING [Create, CreateMenuEntry], TypeScript USING [Create], ViewerIO USING [CreateViewerStreams], ViewerClasses USING [Viewer], ViewerOps USING [AddProp, ComputeColumn], ProcessProps USING [GetPropList], JaMTS USING [JaMData, JaMDataRec], Convert USING [RopeFromInt]; JaMTSImpl: CEDAR PROGRAM IMPORTS JaM, ReadEvalPrint, Rope, Convert, Commander, List, ProcessProps, IO, Menus, MBQueue, TypeScript, ViewerIO, ViewerOps EXPORTS JaMTS = BEGIN STREAM: TYPE = IO.STREAM; ROPE: TYPE = Rope.ROPE; DefaultPrompt: PROC[self: JaM.State] = { JaM.ExecuteRope[self, "(*) .print"]; }; prompt: ATOM = JaM.RopeToAtom[".prompt"]; JaMPromptProc: PROC[h: ReadEvalPrint.Handle] = { data: JaMTS.JaMData = NARROW[h.clientData]; JaM.Execute[data.state, prompt ! JaM.Stop => CONTINUE]; }; JaMClientProc: ReadEvalPrint.ClientProc = { <<[h: Handle, command: Rope.ROPE] RETURNS [result: Rope.ROPE _ NIL]>> data: JaMTS.JaMData = NARROW[h.clientData]; data.input _ Rope.Cat[data.input, command]; IF JaM.LineComplete[data.input] THEN {ENABLE UNWIND => {data.input _ NIL; CONTINUE}; JaM.ExecuteRope[data.state, data.input ! JaM.Stop => CONTINUE]; data.input _ NIL; } ELSE IO.PutChar[h.out,'*]; --indicates inside a string or array. }; lastHandle: ReadEvalPrint.Handle _ NIL; GetLastHandle: PUBLIC PROC RETURNS[ReadEvalPrint.Handle] = {RETURN[lastHandle]}; <> SetAbort: Menus.MenuProc = { <<[parent: REF, clientData: REF, mouseButton: MouseButton, shift, control: BOOL]>> data: JaMTS.JaMData = NARROW[clientData]; JaM.SetAbort[data.state, TRUE]; }; <<>> CreateJaMTS: PUBLIC PROC [name: Rope.ROPE, commandLine: Rope.ROPE, searchRules: LIST OF REF ANY] RETURNS[ReadEvalPrint.Handle]= { <> <> in, out: STREAM; h: ReadEvalPrint.Handle; state: JaM.State; wd: REF ANY _ List.Assoc[key: $WorkingDirectory, aList: ProcessProps.GetPropList[]]; viewer: ViewerClasses.Viewer _ TypeScript.Create[ info: [name: name, iconic: FALSE, column: right], paint: FALSE]; [in: in, out: out] _ ViewerIO.CreateViewerStreams[name: NIL, viewer: viewer, editedStream: TRUE]; h _ ReadEvalPrint.CreateStreamEvaluator[clientProc: JaMClientProc, prompt: "%l%l", in: in, out: out, topLevel: TRUE]; h.viewer _ viewer; state _ JaM.Create[h.out]; h.clientData _ NEW[JaMTS.JaMDataRec _ [state: state, input: NIL]]; h.promptProc _ JaMPromptProc; h.menuHitQueue _ MBQueue.Create[]; Menus.InsertMenuEntry [menu: h.viewer.menu, line: 0, entry: MBQueue.CreateMenuEntry[q: h.menuHitQueue, name: "ABORT!", proc: SetAbort, clientData: h.clientData]]; ViewerOps.ComputeColumn[column: right]; ViewerOps.AddProp[h.viewer, $ReadEvalPrint, h]; JaM.Register[state, ".prompt", DefaultPrompt]; JaM.Store[self: state, key: JaM.RopeToAtom[".searchrules"],val: searchRules]; JaM.ExecuteRope[state, "(JaMBasics.jam) .run"]; JaM.ExecuteRope[state, commandLine]; ReadEvalPrint.MainLoop[h: h, forkAndDetach: TRUE, properties: List.PutAssoc[key: $WorkingDirectory, val: wd, aList: NIL]]; lastHandle _ h; RETURN[h]; }; called: INT _ 0; NewJaMTS: Commander.CommandProc = { name: Rope.ROPE _ "JaM"; rules: LIST OF REF ANY _ List.Append[NARROW[List.Assoc[key: $SearchRules, aList: cmd.propertyList]]]; IF called#0 THEN name _ Rope.Cat[name,Convert.RopeFromInt[from: called, showRadix: FALSE]]; result _ CreateJaMTS[name, cmd.commandLine, rules]; called _ called+1; }; Commander.Register[key: "JaM", proc: NewJaMTS, doc: "Start JaM and its typescript"]; END.