/* * Name: MicroEmacs * Commodore Amiga Intuition menus * Version: 31 * Last edit: 20-Apr-86 ...!ihnp4!seismo!ut-sally!ut-ngp!mic * Created: 20-Apr-86 ...!ihnp4!seismo!ut-sally!ut-ngp!mic */ #include #include #include #include #include #undef TRUE #undef FALSE #include "def.h" /* Also includes "sysdef.h" and "ttydef.h" */ /* * When ttgetc() sees a menu selection event, it stuffs * the sequence M~ into the input buffer, and * caches the menu number and item number for later. * This sequence is translated into the internal key code * KMENU, similar to KHELP and the other function keys. * * The menu item names are chosen to be relatively close * to the extended function names, so a user can usually * figure out the key binding of a menu item by searching * through the "display-bindings" buffer for something * that's close. */ /* * Commands for managing files */ static struct MenuBinding FileItems[] = { { "Read File", "file-file-read-only", }, { "Save File", "file-buffer", }, { "Find File", "find-file", }, { "Write File", "write-file" }, { "Insert File", "insert-file" }, { "Set File Name", "set-visited-file-name" }, { "Save And Exit", "save-buffers-kill-emacs" }, { "Kill Emacs", "kill-emacs", } }; /* * Commands for various editing functions */ static struct MenuBinding EditItems[] = { { "Delete Char", "delete-char" }, { "Kill Line", "kill-line" }, { "Yank", "yank" }, { "Delete Blank Lines", "delete-blank-lines" }, { "Newline And Indent", "newline-and-indent" }, { "Transpose Characters", "transpose-characters" }, { "Quoted Insert", "quoted-insert" } }; /* * Movement commands */ static struct MenuBinding MoveItems[] = { { "Beginning Of Line", "beginning-of-line" }, #ifdef AS_DISTRIBUTED { "Beg. Of Paragraph", "goto-bop" }, #endif { "Beginning Of Buffer", "beginning-of-buffer" }, { "End Of Line", "end-of-line" }, #ifdef AS_DISTRIBUTED { "End Of Paragraph", "goto-eop" }, #endif { "End Of Buffer", "end-of-buffer" }, { "Goto Line", "goto-line" }, { "Show Cursor Pos", "what-cursor-position" } }; /* * Commands for searching and replacing */ static struct MenuBinding SearchItems[] = { { "Search Again", "search-again" }, { "I-Search Forward", "isearch-forward" }, { "I-Search Backward", "isearch-backward" }, { "Search Forward", "search-forward" }, { "Search Backward", "search-backward" }, { "Query Replace", "query-replace" }, }; /* * Commands that manipulate words */ static struct MenuBinding WordItems[] = { #ifdef AS_DISTRIBUTED { "Fill Paragraph", "fill-paragraph" }, { "Set Fill Column", "set-fill-column" }, #endif { "Forward Word", "forward-word" }, { "Backward Word", "backward-word" }, { "Kill Word", "kill-word" }, { "Backward Kill Word", "backward-kill-word" }, { "Capitalize Word", "capitalize-word" }, { "Downcase Word", "downcase-word" }, { "Upcase Word", "upcase-word" } }; /* * Region management */ static struct MenuBinding RegionItems[] = { { "Set Mark Command", "set-mark-command" }, { "Exch Point And Mark", "exchange-point-and-mark" }, { "Kill Region", "kill-region" }, { "Copy Region As Kill", "copy-region-as-kill" }, { "Downcase Region", "downcase-region" }, { "Upcase Region", "upcase-region" } }; /* * Buffer management */ static struct MenuBinding BufferItems[] = { #ifdef NOTIMPLEMENTED { "Rename Buffer", "rename-buffer" }, #endif { "Switch To Buffer", "switch-to-buffer" }, { "Kill Buffer", "kill-buffer" }, { "List Buffers", "list-buffers" } }; /* * Commands for manipulating windows */ static struct MenuBinding WindowItems[] = { { "Recenter", "recenter" }, { "Move To Window Line", "move-to-window-line" }, { "Split Window Vertically", "split-window-vertically" }, { "Delete Other Windows", "delete-other-windows" }, { "Other Window", "other-window" }, { "Back Window", "back-window" }, { "Down Window", "down-window" }, { "Up Window", "up-window" }, { "Enlarge Window", "enlarge-window" }, { "Shrink Window", "shrink-window" } }; /* * Miscellaneous commands */ static struct MenuBinding MiscItems[] = { { "Emacs Version", "emacs-version" }, { "Start Kbd Macro", "start-kbd-macro" }, { "End Kbd Macro", "end-kbd-macro" }, { "Call Kbd Macro", "call-last-kbd-macro" }, { "Execute Command", "execute-extended-command" }, { "Global Set Key", "global-set-key" }, { "Describe Bindings", "describe-bindings" }, { "Suspend Emacs", "suspend-emacs" } }; /* * The following table contains the titles, number of * items, and pointers to, the individual menus. * * The MenuWidth field is the number of characters * in the longest item name. */ static struct MenuInfo EMInfo[] = { { "File", NITEMS(FileItems), 13, &FileItems[0] }, { "Edit", NITEMS(EditItems), 20, &EditItems[0] }, { "Move", NITEMS(MoveItems), 19, &MoveItems[0] }, { "Search", NITEMS(SearchItems), 17, &SearchItems[0] }, { "Word", NITEMS(WordItems), 18, &WordItems[0] }, { "Region", NITEMS(RegionItems), 19, &RegionItems[0] }, { "Buffer", NITEMS(BufferItems), 16, &BufferItems[0] }, { "Window", NITEMS(WindowItems), 23, &WindowItems[0] }, { "Misc", NITEMS(MiscItems), 17, &MiscItems[0] } }; /* * Initialize the MicroEmacs menus. * * Returns a pointer to the first menu header in * the menu list back to the caller. * * Makes the assumption that the font for * the window being used is 8 pixels wide -- * a safe bet with the version 1.1 ROM Kernel. */ struct Menu *InitEmacsMenu() { struct Menu *EMMenu, *NewMenu(), *AddMenu(); struct MenuItem *AddNewMenuItem(), *AddItem(), *AddNewSubItem(); register struct Menu *cm; register struct MenuInfo *cinf, *lastinfo;/* current menu info */ lastinfo = &EMInfo[NITEMS(EMInfo)]; /* sentinel for loop */ for (cinf = EMInfo; cinf < lastinfo; cinf++) { if (cinf == EMInfo) /* create menu header */ EMMenu = cm = NewMenu(cinf->Name, strlen(cinf->Name) * 8 + 6, 10); else cm = AddMenu(cm, cinf->Name,strlen(cinf->Name) * 8 + 6, 10); MakeMenu(cinf,cm,cinf->MenuWidth * 8 + 2, 10); } return EMMenu; } /* * Put menu items in a menu. Width and * height control the respective * sizes of the menu items. */ static MakeMenu(cinf,cm,width,height) struct MenuInfo *cinf; struct Menu *cm; int width, height; { struct Menu *NewMenu(), *AddMenu(); struct MenuItem *AddNewMenuItem(), *AddItem(), *AddNewSubItem(); register struct MenuBinding *cb, *lastbinding; register struct MenuItem *ci; lastbinding = &cinf->Items[cinf->NumItems]; for (cb = cinf->Items; cb < lastbinding; cb++) { if (cb == cinf->Items) ci = AddNewMenuItem(cm, cb->Command, width, height); else ci = AddItem(ci, cb->Command); } } /* * Menu command. Get the name of the command to * perform from the menu binding table, then * run the command if it is found and has the * right type. Print an error if there is anything * wrong. */ extern ttmenu(); /* Defined in "ttyio.c" */ /* Returns last menu selection */ amigamenu(f, n, k) { register SYMBOL *sp, *symlookup(); char *xname; int MenuNum, ItemNum, SubItem; ttmenu(&MenuNum,&ItemNum,&SubItem); /* check for spurious numbers */ if ((MenuNum < 0) || (MenuNum >= NITEMS(EMInfo))) return (FALSE); if ((ItemNum < 0) || (ItemNum >= EMInfo[MenuNum].NumItems)) return (FALSE); xname = EMInfo[MenuNum].Items[ItemNum].Binding; if ((sp=symlookup(xname)) != NULL) return ((*sp->s_funcp)(f, n, KRANDOM)); eprintf("Unknown menu command"); return (ABORT); }