File: DefaultNutUtilitiesImpl.mesa
CreatedBy: Butler on June 18, 1984 9:25:04 am PDT
Last Edited By:
Butler on August 13, 1984 5:48:50 pm PDT
Widom on June 18, 1984 9:25:39 am PDT
DIRECTORY
DB,
DefaultNutUtilities,
IO,
InputFocus,
Menus USING [MouseButton],
Nut,
NutOps,
NutViewer,
Rope USING [Find, Substr],
VFonts USING [StringWidth, Font, EstablishFont],
ViewerOps,
Buttons;
DefaultNutUtilitiesImpl:
CEDAR
PROGRAM
IMPORTS
DB, Nut, NutOps, NutViewer, InputFocus, ViewerOps, VFonts, Rope
EXPORTS DefaultNutUtilities =
BEGIN
OPEN DB, NutViewer, DefaultNutUtilities;
buttonSize: INT = 125;
xFudge: INT = 4;
attributeFont:
PUBLIC VFonts.Font
← VFonts.EstablishFont[family: "Tioga", size: 10];
relationFont:
PUBLIC VFonts.Font
← VFonts.EstablishFont[family: "Helvetica", size: 8, bold: TRUE];
valueFont:
PUBLIC VFonts.Font
← VFonts.EstablishFont[family: "Cream", size: 12];
SpawnParent:
PROC[v: Viewer]
RETURNS [parent: Viewer] = {
parent ← v; WHILE parent.parent # NIL DO parent ← parent.parent ENDLOOP };
ProcessSelection: PUBLIC Buttons.ButtonProc =
-- A standard ButtonProc that assumes the button's REF ANY data is the FieldHandle above.
-- Insures attribute of tuple is entity-valued and non-NIL, then calls Nut.Display on it.
BEGIN OPEN DB;
otherEntity: Entity;
fd: DefaultNutUtilities.FieldHandle← NARROW[clientData];
viewer: Viewer← NARROW[parent];
IF fd.attribute=NIL THEN -- it was the relation itself
{ otherEntity ← RelationOf[fd.tuple];
IF NOT DB.Null[otherEntity] THEN
[] ← Nut.Display[eName: DB.NameOf[otherEntity], domain: "RelationDomain", parent: SpawnParent[viewer], segment: DB.SegmentOf[otherEntity]] }
ELSE IF NutOps.EntityValued[fd.attribute] THEN -- attribute refs another entity
IF Null[fd.tuple] THEN
Message[viewer, "That relationship has been deleted!"]
ELSE IF Null[otherEntity←V2E[GetF[fd.tuple, fd.attribute]]] THEN
Message[viewer, "That entity has been deleted!"]
ELSE
{ otherEntity ← V2E[GetF[fd.tuple, fd.attribute]];
[] ← Nut.Display[eName: DB.NameOf[otherEntity], domain: DB.NameOf[DB.DomainOf[otherEntity]], parent: SpawnParent[viewer], segment: DB.SegmentOf[otherEntity]] }
ELSE -- attribute is a string or number
Message[viewer, "Not an entity-valued field"];
END;
Reset:
PUBLIC
PROC[eName, domain:
ROPE, seg:
DB.Segment, viewer: Viewer] =
BEGIN
-- Resets contents of editor to its statebefore edits started.
InputFocus.SetInputFocus[]; -- kill the caret
viewer.child ← NIL;
ViewerOps.PaintViewer[viewer, client];
[] ← Nut.Edit[eName: eName, domain: domain, segment: seg, parent: viewer] ;
END;
Edit:
PUBLIC
PROC[eName, domain:
ROPE, seg:
DB.Segment, parent: Viewer] =
BEGIN
-- Invoked when hit the "Edit" button on the default displayer.
-- Should replace the displayer viewer with an editor viewer.
InputFocus.SetInputFocus[];
IF NutOps.IsSystemEntity[eName]
THEN
BEGIN
[] ← NutViewer.Message[NIL, eName, " is a system entity. You may not edit it."];
RETURN;
END;
[] ← Nut.Edit[ eName: eName, domain: domain, segment: seg, parent: parent];
END;
GetTopLevel:
PUBLIC
PROCEDURE [v: Viewer]
RETURNS [ancestor: Viewer] = {
FOR ancestor ← v, ancestor.parent UNTIL ancestor.parent=NIL DO ENDLOOP;
};
AttrButtonLength:
PUBLIC
PROC[
attrString, attrValue: ROPE, button: Menus.MouseButton ← Menus.MouseButton[red] ]
RETURNS[INT] =
BEGIN
width: INT = VFonts.StringWidth[PreColon[attrString], attributeFont] + 2*xFudge;
vWidth: INT = VFonts.StringWidth[attrValue, valueFont];
IF
button=Menus.MouseButton[red] AND vWidth>buttonSize+10 THEN
RETURN[width+buttonSize]
ELSE RETURN[width+vWidth];
END;
PreColon:
PROC[label:
ROPE]
RETURNS[
ROPE] =
BEGIN
colonPos: INT ← Rope.Find[s1: label, s2: ":"];
IF colonPos = -1
THEN
--Not a label
RETURN[label]
ELSE RETURN[ Rope.Substr[base: label, len: colonPos+1] ];
END;
END. . .