<> <> <> <> <> DIRECTORY CD, CDApplications, CDBasics, CDCells, CDCommandOps, CDDirectory, CDMarkObjects, CDOps, CDOrient, CDSequencer, Process, Rope, TerminalIO; CDMacroImpl: CEDAR PROGRAM IMPORTS CD, CDApplications, CDBasics, CDCells, CDCommandOps, CDMarkObjects, CDOps, CDOrient, CDSequencer, Process, Rope, TerminalIO SHARES CD, CDDirectory = BEGIN pForMacro: REF CD.ObjectProcs = CD.RegisterObjectType[$Macro]; pForCells: REF READONLY CD.ObjectProcs = CDCells.CreateEmptyCell[].p; CellToMacro: PROC[ob: CD.ObPtr] = BEGIN TerminalIO.WriteRope["**CellToMacro called "]; IF ob=NIL OR ob.specificRef=NIL THEN TerminalIO.WriteRope["bad object\n"] ELSE IF NOT ISTYPE[ob.specificRef, CD.CellPtr] THEN TerminalIO.WriteRope["object not cell\n"] ELSE { ob.p _ pForMacro; TerminalIO.WriteRope[" done\n"] } END; <> <> <> <> <> <> <> <> <> <> <<}>> <> Describe: PROC[me: CD.ObPtr] RETURNS [Rope.ROPE] = BEGIN cptr: CD.CellPtr = NARROW[me.specificRef]; RETURN [Rope.Concat["special cell ", cptr.name]] END; <> <<-- PROC [objToReposition: CD.ObPtr, newBound: CD.DesignRect] -- =>> <> <<--don't do that accidently>> <> <<>> <> <<-- PROC [me: CD.ObPtr, objToReposition: CD.ObPtr, oldSize: CD.DesignPosition, newBound: CD.DesignRect, design: CD.Design] -- =>> <> <<--don't do that>> <> <<>> <> <<-- PROC [ob: CD.ObPtr] RETURNS [CD.DesignRect] -- =>> <> <<--here you cheat; therefore this tye is made !!!!!!!>> <> <> InternalRead: CD.InternalReadProc --PROC [] RETURNS [ObPtr]-- = BEGIN ob: CD.ObPtr _ pForCells.internalRead[]; ob.p _ pForMacro; RETURN [ob] END; MakeSubClass: PROC[me: REF CD.ObjectProcs, from: REF READONLY CD.ObjectProcs] = <<--me, from must have been registered!>> <<--does NOT subClass the furtherprocs>> BEGIN dummy: REF CD.ObjectProcs _ NEW[CD.ObjectProcs_from^]; <<--handle the following fields specially>> dummy.further _ me.further; dummy.technology _ me.technology; dummy.objectType _ me.objectType; <<--handle directory>> IF dummy.inDirectory THEN { dummy.directoryProcs _ NEW[CDDirectory.DirectoryProcs_ NARROW[from.directoryProcs, REF CDDirectory.DirectoryProcs]^ ]; }; <<--do overwrite all the other fields>> me^ _ dummy^; END; DrawSelection: PROC [aptr: CD.ApplicationPtr, pos: CD.DesignPosition, orient: CD.Orientation, pr: CD.DrawRef] = BEGIN pr.drawRect[CDOrient.RectAt[pos, aptr.ob.size, orient], CD.highLightShade, pr] END; Init: PROC [] = INLINE BEGIN dp: REF CDDirectory.DirectoryProcs; MakeSubClass[me: pForMacro, from: pForCells]; dp _ NARROW[pForMacro.directoryProcs]; <> <> <> pForMacro.describe _ Describe; pForMacro.internalRead _ InternalRead; pForMacro.showMeSelected _ DrawSelection; CDSequencer.ImplementCommand[$TModifyMacroS, ModifyMacroS]; CDSequencer.ImplementCommand[$ModifyMacroS, SetMacroRectComm]; END; <<--xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx>> <<--commands>> ModifyMacroS: PROC [comm: CDSequencer.Command] = BEGIN ap: CD.ApplicationPtr; multiple: BOOL; TerminalIO.WriteRope["Macro modifications\n"]; [ap, multiple] _ CDOps.SelectedApplication[comm.design]; IF multiple THEN TerminalIO.WriteRope[" multiple selection; not done\n"] ELSE IF ap=NIL THEN TerminalIO.WriteRope[" no selection; not done\n"] ELSE { rect: CD.DesignRect _ CDApplications.ARectO[ap]; TerminalIO.WriteRope[ap.ob.p.describe[ap.ob]]; IF ISTYPE[ap.ob.specificRef, CD.CellPtr] THEN { cptr: CD.CellPtr ~ NARROW[ap.ob.specificRef]; IF ap.ob.p=pForCells THEN { TerminalIO.WriteRope[" is ordinary cell\n"]; IF TerminalIO.UserSaysYes[label: "transform to macro", text: "transform cell to macro "] THEN { CellToMacro[ap.ob] } ELSE TerminalIO.WriteRope[" no\n"]; }; IF ap.ob.p#pForMacro THEN { TerminalIO.WriteRope[" not a macro; not done\n"]; RETURN }; <<--now do it>> pForMacro.showMeSelected _ pForCells.showMeSelected; DO m: INT; n: CARDINAL; rect _ CDBasics.Surround[rect, CDApplications.ARectO[ap]]; CDOps.Redraw[comm.design, rect]; CDOps.DoTheDelayedRedraws[comm.design]; Process.Pause[Process.MsecToTicks[100]]; -- to allow drawing n _ TerminalIO.RequestSelection[label: "macro commands", choice: LIST["exit macro commands", "x-position", "y-position", "x-size", "y-size", "pause for redraw"] ]; SELECT n FROM 1 => EXIT; 2 => { m _ TerminalIO.RequestInt["change x position > "]; <> TerminalIO.WriteLn[]; }; 3 => { m _ TerminalIO.RequestInt["change y position > "]; <> TerminalIO.WriteLn[]; }; 4 => { m _ TerminalIO.RequestInt["change x size > "]; <> TerminalIO.WriteLn[]; }; 5 => { m _ TerminalIO.RequestInt["change y size > "]; <> TerminalIO.WriteLn[]; }; 6 => Process.Pause[Process.MsecToTicks[200]]; ENDCASE => TerminalIO.WriteRope[" no selection\n"]; ENDLOOP; pForMacro.showMeSelected _ DrawSelection; TerminalIO.WriteRope[" end macro commands\n"]; } ELSE TerminalIO.WriteRope[" not a cell; not done\n"]; } END; SetMacroRect: PROC [mOb: CD.ObPtr] = <<--uses the marks "BottomLeft" and "UpperRight" to overide>> <<--coordinates, initialized with innerrect>> BEGIN rect: CD.DesignRect _ mOb.p.insideRect[mOb]; bl, ur: BOOL_FALSE; Enumerate: PROC [markApp: CD.ApplicationPtr] RETURNS [quit: BOOL_FALSE] = BEGIN pos: CD.DesignPosition; name: Rope.ROPE = CDMarkObjects.GetMarkName[markApp]; IF Rope.Equal[name, "0"] THEN { IF bl THEN TerminalIO.WriteRope["multiple 0 marks\n"]; bl _ TRUE; pos _ CDMarkObjects.GetMarkPosition[markApp]; rect.x1 _ pos.x; rect.y1 _ pos.y } ELSE IF Rope.Equal[name, "1"] THEN { IF ur THEN TerminalIO.WriteRope["multiple 1 marks\n"]; ur _ TRUE; pos _ CDMarkObjects.GetMarkPosition[markApp]; rect.x2 _ pos.x; rect.y2 _ pos.y } END; [] _ CDMarkObjects.EnumerateMarks[cellOb: mOb, proc: Enumerate]; IF rect.x1>rect.x2 OR rect.y1>rect.y2 THEN { TerminalIO.WriteRope["bad rectangle\n"]; rect_CDBasics.empty; }; IF rect.x1>rect.x2 OR rect.y1>rect.y2 THEN { TerminalIO.WriteRope["marks are badly placed\n"]; rect _ CDBasics.empty; }; <> <> END; SetMacroRectComm: PROC [comm: CDSequencer.Command] = BEGIN aptr: CD.ApplicationPtr = CDCommandOps.TheApplication[comm, "Recompute interestrect"]; IF aptr#NIL THEN { IF ISTYPE[aptr.ob.specificRef, CD.CellPtr] THEN { IF aptr.ob.p=pForCells THEN { TerminalIO.WriteRope[" is ordinary cell\n"]; IF TerminalIO.UserSaysYes[label: "transform to macro", text: "transform cell to macro "] THEN CellToMacro[aptr.ob] ELSE { TerminalIO.WriteRope[" no\n"]; RETURN }; }; SetMacroRect[aptr.ob]; CDCommandOps.RedrawApplication[comm.design, aptr]; } ELSE TerminalIO.WriteRope[" not done; Selected object is not macro or cell\n"]; } END; <<>> <<--xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx>> Init[]; END.