PeanutTopImpl.mesa; Written by Bill Paxton, February 1983
Last edited by Paxton on April 4, 1983 9:10 am
Last edited by Wyatt on April 14, 1983 2:38 pm
Last Edited by: Pausch, July 18, 1983 1:37 pm
DIRECTORY
CedarSnapshot USING [CheckpointProc, Register, RollbackProc],
CIFS USING [Enumerate, EProc],
Commander USING [CommandProc, Register],
Process USING [Detach],
Menus USING [ClickProc, MenuProc],
PeanutSendMail,
RefText USING [Match],
Rope USING [Equal, Find, FromProc, ROPE, Substr],
PeanutRetrieve,
PeanutWindow,
UserProfile,
ViewerClasses,
ViewerOps,
VirtualDesktops;
PeanutTopImpl: CEDAR PROGRAM
IMPORTS PeanutWindow, PeanutRetrieve, PeanutSendMail, CedarSnapshot, CIFS, Process, RefText, Rope, Commander, UserProfile, VirtualDesktops, ViewerOps =
BEGIN
NewForm: Menus.MenuProc = {
PeanutSendMail.NewMsgForm[mouseButton, shift, control] };
AnswerMessage: Menus.MenuProc = {
PeanutSendMail.AnswerMsg[mouseButton, shift, control] };
ForwardMessage: Menus.MenuProc = {
PeanutSendMail.ForwardMsg[mouseButton, shift, control] };
SendMessage: Menus.MenuProc = {
PeanutSendMail.SendMsg[mouseButton, shift, control] };
NewMail: Menus.MenuProc = {
PeanutRetrieve.GetNewMsgs[] };
Abort: Menus.MenuProc = {
PeanutWindow.abortFlag ← TRUE };
SaveAll: Menus.MenuProc = {
files: LIST OF Rope.ROPE ← mailFiles;
killThem: BOOLEAN ← UserProfile.Boolean[key: "Peanut.KillViewersOnSaveall", default: FALSE];
activeName: Rope.ROPE ← UserProfile.Token[key:"Peanut.ActiveMailFile", default:"Active.mail"];
outgoingName: Rope.ROPE ← UserProfile.Token[key:"Peanut.OutGoingMailFile", default:""];
PeanutWindow.OutputRope["\nSaving all message sets:"];
WHILE files # NIL DO
viewer: ViewerClasses.Viewer ← VirtualDesktops.FindViewer[files.first].viewer;
IF viewer # NIL THEN {
IF viewer.newVersion THEN {
PeanutWindow.OutputRope["\nSaving "];
PeanutWindow.OutputRope[files.first];
ViewerOps.SaveViewer[viewer];
};
IF killThem THEN {
IF Rope.Equal[viewer.name,activeName] OR Rope.Equal[viewer.name,outgoingName] THEN ViewerOps.CloseViewer[viewer]
ELSE ViewerOps.DestroyViewer[viewer];
};
};
files ← files.rest;
ENDLOOP;
PeanutWindow.OutputRope["\nDone saving all message sets."];
};
MailFileButton: Menus.ClickProc = {
IF mouseButton=yellow THEN -- open the message file
ViewerOps.OpenIcon[PeanutRetrieve.GetMailViewer[NARROW[clientData]]]
ELSE PeanutRetrieve.CopyMessages[to: NARROW[clientData], delete: mouseButton=blue] };
restartAfterRollback: BOOLFALSE;
PeanutCheckpointProc: CedarSnapshot.CheckpointProc = {
CloseDown[]; restartAfterRollback ← TRUE };
PeanutRollbackProc: CedarSnapshot.RollbackProc = {
IF restartAfterRollback THEN TRUSTED {Process.Detach[FORK StartPeanut[]]}};
BuildPeanut: Commander.CommandProc = {StartPeanut[]};
CloseDown: PROC = {
PeanutRetrieve.CloseConnection[] };
mailFiles: LIST OF Rope.ROPE;
GetMatchingFileList: PROC[pattern: REF TEXT] RETURNS[LIST OF Rope.ROPE] = {
list: LIST OF Rope.ROPENIL;
tail: LIST OF Rope.ROPENIL;
proc: CIFS.EProc --[name, link, comment: REF TEXT] RETURNS[stop: BOOL]-- = {
IF RefText.Match[pattern: pattern, object: name, case: FALSE] THEN {
ShortFileName: PROC[name: REF READONLY TEXT] RETURNS[Rope.ROPE] = {
index: NAT ← 0;
p: PROC RETURNS[CHAR] = { c: CHAR = name[index]; index ← index+1; RETURN[c] };
FOR i: NAT IN[0..name.length) DO
IF name[i]='> THEN index ← i+1;
ENDLOOP;
RETURN[Rope.FromProc[len: name.length-index, p: p]];
};
rope: Rope.ROPE = ShortFileName[name];
item: LIST OF Rope.ROPE = CONS[rope, NIL];
IF list=NIL THEN list ← item ELSE tail.rest ← item;
tail ← item;
};
RETURN[stop: FALSE];
};
CIFS.Enumerate[dir: NIL, pattern: "*", p: proc]; -- "*" is the only pattern that works!
RETURN[list];
};
StartPeanut: PROC = {
files: LIST OF Rope.ROPE;
AddName: PROC [fileName: Rope.ROPE, redisplay: BOOL] = {
name: Rope.ROPE ← Rope.Substr[fileName, 0, Rope.Find[fileName, "."]];
PeanutWindow.AddButton[name: name, proc: MailFileButton, data: fileName, redisplay: redisplay] };
IF PeanutSendMail.AuthenticateUser[] THEN
[] ← PeanutRetrieve.NewUser[PeanutSendMail.userRName];
IF PeanutWindow.Create[] THEN { -- created a new one
files ← mailFiles ← GetMatchingFileList["*.Mail"];
WHILE files # NIL DO
AddName[files.first, (files.rest = NIL)];
files ← files.rest;
ENDLOOP;
PeanutWindow.OutputRope["MIDDLE click mail file button to open the file\n"];
PeanutWindow.OutputRope["LEFT click to copy selected message(s)\n"];
PeanutWindow.OutputRope["RIGHT click to move selected message(s)\n"] }
ELSE { -- restarting, probably after Rollback; check for new Mail files
IsOld: PROC [name: Rope.ROPE] RETURNS [yes: BOOL] = {
fileList: LIST OF Rope.ROPE ← mailFiles;
WHILE fileList # NIL DO
IF Rope.Equal[name, fileList.first] THEN RETURN [TRUE];
fileList ← fileList.rest;
ENDLOOP;
RETURN [FALSE] };
files ← GetMatchingFileList["*.Mail"];
WHILE files # NIL DO
IF ~IsOld[files.first] THEN {
PeanutWindow.Destroy[];
[] ← PeanutWindow.Create[];
files ← mailFiles ← GetMatchingFileList["*.Mail"];
WHILE files # NIL DO
AddName[files.first, (files.rest = NIL)];
files ← files.rest;
ENDLOOP;
EXIT };
files ← files.rest;
ENDLOOP };
};
PeanutWindow.AddCommand[name: "NewMail", proc: NewMail];
PeanutWindow.AddCommand[name: "NewForm", proc: NewForm];
PeanutWindow.AddCommand[name: "Answer", proc: AnswerMessage];
PeanutWindow.AddCommand[name: "Forward", proc: ForwardMessage];
PeanutWindow.AddCommand[name: "Send", proc: SendMessage];
PeanutWindow.AddCommand[name: "Abort", proc: Abort];
PeanutWindow.AddCommand[name: "SaveAll", proc: SaveAll];
Commander.Register["Peanut", BuildPeanut, "For retrieving and sending mail"];
TRUSTED {CedarSnapshot.Register[c: PeanutCheckpointProc, r: PeanutRollbackProc]};
StartPeanut[];
END.