Article 12669 of alt.sources:
Path: nntpd.lkg.dec.com!pa.dec.com!decwrl!spool.mu.edu!uwm.edu!vixen.cso.uiuc.edu!news.uoregon.edu!tank.news.pipex.net!pipex!demon!not-for-mail
From: Bob Smith <bob@snuffy.penfield.ny.us>
Newsgroups: alt.sources
Subject: Notes-1.0.7 part.02/03
Date: Sat, 22 Jul 95 11:47:53 EDT
Lines: 1932
Message-ID: <9507221547.AA07820@snuffy.penfield.ny.us>
X-NNTP-Posting-Host: valhalla.ee.rochester.edu

#!/bin/sh
# This is `part.02' (part 2 of notes-1.0.6).
# Do not concatenate these parts, unpack them in order with `/bin/sh'.
# File `TODO' is being continued...
#
touch -am 1231235999 $$.touch >/dev/null 2>&1
if test ! -f 1231235999 && test -f $$.touch; then
  shar_touch=touch
else
  shar_touch=:
  echo
  echo 'WARNING: not restoring timestamps.  Consider getting and'
  echo "installing GNU \`touch', distributed in GNU File Utilities..."
  echo
fi
rm -f 1231235999 $$.touch
#
if test ! -r _sharseq.tmp; then
  echo 'Please unpack part 1 first!'
  exit 1
fi
shar_sequence=`cat _sharseq.tmp`
if test "$shar_sequence" != 2; then
  echo "Please unpack part $shar_sequence next!"
  exit 1
fi
if test ! -f _sharnew.tmp; then
  echo 'x - still skipping TODO'
else
  echo 'x - continuing file TODO'
  sed 's/^X//' << 'SHAR_EOF' >> 'TODO' &&
X	hang off the screen, switch to multiple columns
X	or add a scrollbar (pending a final decision here)
X
Xo	Find a better way to get a windows geometry while
X	it's mapped and eliminate the need for h_offset
X	and v_offset in the app_res file.
X
Xo	Make saveOnExit a little smarter...
SHAR_EOF
  echo 'File TODO is complete' &&
  $shar_touch -am 0613212295 'TODO' &&
  chmod 0644 'TODO' ||
  echo 'restore of TODO failed'
  rm -f _sharnew.tmp
fi
# ============= callbacks.c ==============
if test -f 'callbacks.c' && test X"$1" != X"-c"; then
  echo 'x - skipping callbacks.c (file already exists)'
  rm -f _sharnew.tmp
else
  > _sharnew.tmp
  echo 'x - extracting callbacks.c (text)'
  sed 's/^X//' << 'SHAR_EOF' > 'callbacks.c' &&
X#ifndef lint
Xstatic char sccs_id[] = "callbacks.c -- Mon May 30 01:20:12 EDT 1994";
X#endif
X/*
X * callbacks.c -- Mon May 30 01:20:12 EDT 1994
X *
X * Copyright (c) 1994 -- Bob Smith <bob@snuffy.penfield.ny.us>
X *
X * I hate copyright notices...  They're generally of a lot of words
X * that end up saying -- You can do whatever you want with this
X * as long as you don't rip me off!  So with that said, enjoy, and
X * have a good day!
X *
X */
X
X#include <stdio.h>
X#include <stdlib.h>
X#include <malloc.h>
X
X#include <X11/IntrinsicP.h>
X#include <X11/Intrinsic.h>
X#include <X11/StringDefs.h>
X#include <X11/Shell.h>
X
X#include <X11/Xaw/Box.h>
X#include <X11/Xaw/Cardinals.h>
X#include <X11/Xaw/Command.h>
X#include <X11/Xaw/Label.h>
X#include <X11/Xaw/Form.h>
X#include <X11/Xaw/List.h>
X#include <X11/Xaw/AsciiText.h>
X
X#define CALLBACKS_C
X#include "notes.h"
X
X
X/*
X * globals for callback.c
X */
Xstatic Widget note_to_create, title_to_change, title_parent;
X
X
X/*
X * external functions
X */
Xextern void sensitize_start_button();
X
X
X/*
X * forward declarations
X */
Xvoid show_list(), destroy_list();
X
X
X/*
X * null ()
X * just a stub to redirect some actions to when you don't really
X * want anything to happen -- used by the input dialogs to keep
X * carriage return, newline, and tab from doing anything
X */
Xvoid
Xnull(widget, client_data, call_data)
X     Widget widget;
X     XtPointer client_data, call_data;
X{
X}
X
X
X/*
X * quit ()
X * self explanatory
X */
Xvoid
Xquit(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	if (app_resources.saveOnExit)
X		write_notefile();
X	XtDestroyApplicationContext(app_con);
X	exit(0);
X}
X
X
X/*
X * desensitize_all ()
X */
Xstatic void
Xdesensitize_all(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget button;
X	int i;
X	XWindowAttributes atribs;
X
X	if ((button = XtNameToWidget(toplevel, "Notes.list_form.new_button")) != NULL) {
X		XtVaSetValues(button, XtNsensitive, False, NULL);
X		button = XtNameToWidget(toplevel, "Notes.list_form.dismiss_button");
X		XtVaSetValues(button, XtNsensitive, False, NULL);
X		button = XtNameToWidget(toplevel, "Notes.list_form.save_button");
X		XtVaSetValues(button, XtNsensitive, False, NULL);
X		button = XtNameToWidget(toplevel, "Notes.list_form.quit_button");
X		XtVaSetValues(button, XtNsensitive, False, NULL);
X		button = XtNameToWidget(toplevel, "Notes.list_form.revert_button");
X		XtVaSetValues(button, XtNsensitive, False, NULL);
X		button = XtNameToWidget(toplevel, "Notes.list_form.list");
X		XtVaSetValues(button, XtNsensitive, False, NULL);
X	}
X
X	i = 0;
X	while (Notes[i]) {
X		XGetWindowAttributes(XtDisplay(*Notes[i]),
X			XtWindow(*Notes[i]), &atribs);
X		if (atribs.map_state != IsUnmapped) {
X			button = XtNameToWidget(*Notes[i], "form.dismiss_button");
X			XtVaSetValues(button, XtNsensitive, False, NULL);
X			button = XtNameToWidget(*Notes[i], "form.title_button");
X			XtVaSetValues(button, XtNsensitive, False, NULL);
X			button = XtNameToWidget(*Notes[i], "form.clear_button");
X			XtVaSetValues(button, XtNsensitive, False, NULL);
X			button = XtNameToWidget(*Notes[i], "form.delete_button");
X			XtVaSetValues(button, XtNsensitive, False, NULL);
X			button = XtNameToWidget(*Notes[i], "form.select_button");
X			XtVaSetValues(button, XtNsensitive, False, NULL);
X		}
X		i++;
X	}
X}
X
X
X/*
X * sensitize_all ()
X */
Xvoid
Xsensitize_all(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget button;
X	int i;
X	XWindowAttributes atribs;
X
X	if ((button = XtNameToWidget(toplevel, "Notes.list_form.new_button")) != NULL) {
X		XtVaSetValues(button, XtNsensitive, True, NULL);
X		button = XtNameToWidget(toplevel, "Notes.list_form.dismiss_button");
X		XtVaSetValues(button, XtNsensitive, True, NULL);
X		button = XtNameToWidget(toplevel, "Notes.list_form.save_button");
X		XtVaSetValues(button, XtNsensitive, True, NULL);
X		button = XtNameToWidget(toplevel, "Notes.list_form.quit_button");
X		XtVaSetValues(button, XtNsensitive, True, NULL);
X		button = XtNameToWidget(toplevel, "Notes.list_form.revert_button");
X		XtVaSetValues(button, XtNsensitive, True, NULL);
X		button = XtNameToWidget(toplevel, "Notes.list_form.list");
X		XtVaSetValues(button, XtNsensitive, True, NULL);
X	}
X
X	i = 0;
X	while (Notes[i]) {
X		XGetWindowAttributes(XtDisplay(*Notes[i]),
X			XtWindow(*Notes[i]), &atribs);
X		if (atribs.map_state != IsUnmapped) {
X			button = XtNameToWidget(*Notes[i], "form.dismiss_button");
X			XtVaSetValues(button, XtNsensitive, True, NULL);
X			button = XtNameToWidget(*Notes[i], "form.title_button");
X			XtVaSetValues(button, XtNsensitive, True, NULL);
X			button = XtNameToWidget(*Notes[i], "form.clear_button");
X			XtVaSetValues(button, XtNsensitive, True, NULL);
X			button = XtNameToWidget(*Notes[i], "form.delete_button");
X			XtVaSetValues(button, XtNsensitive, True, NULL);
X			button = XtNameToWidget(*Notes[i], "form.select_button");
X			XtVaSetValues(button, XtNsensitive, True, NULL);
X		}
X		i++;
X	}
X}
X
X
X/*
X * destroy_widget ()
X * used by a number of the popups to get rid of themselves --
X * the assumption is that the button being pressed is 2 levels
X * deep into the popup we want to destroy - hence the
X * usage of XtGrandParent
X */
Xvoid
Xdestroy_widget(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	XtPopdown(XtGrandParent(widget));
X	XtDestroyWidget(XtGrandParent(widget));
X}
X
X
X/*
X * save_callback ()
X * just a callback to get to write_notefile
X */
Xstatic void
Xsave_callback(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	write_notefile();
X}
X
X
X/*
X * confirm_clear_note ()
X * clear the note widget if confirm is pressed in the dialog box
X */
Xstatic void
Xconfirm_clear_note(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	XtVaSetValues((Widget) client_data, XtNstring, NULL, NULL);
X}
X
X
X/*
X * clear_note ()
X * put up a dialog asking if you really want to clear the
X * associated note
X */
Xstatic void
Xclear_note(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget note = (Widget) client_data;
X	Widget popup, form, prompt;
X	Widget confirm_button, cancel_button;
X	Dimension note_w, popup_w;
X	Position x, y;
X
X	popup = XtCreatePopupShell("Clear Note",
X		transientShellWidgetClass, toplevel,
X		NULL, ZERO);
X
X	form = XtCreateManagedWidget("form",
X		formWidgetClass, popup,
X		NULL, ZERO);
X
X	prompt = XtCreateManagedWidget("prompt",
X		labelWidgetClass, form,
X		NULL, ZERO);
X
X	confirm_button = XtCreateManagedWidget("confirm_button",
X		commandWidgetClass, form,
X		NULL, ZERO);
X		AddCallback(confirm_button, confirm_clear_note, note);
X		AddCallback(confirm_button, destroy_widget, NULL);
X		AddCallback(confirm_button, sensitize_all, NULL);
X
X	cancel_button = XtCreateManagedWidget("cancel_button",
X		commandWidgetClass, form,
X		NULL, ZERO);
X		AddCallback(cancel_button, destroy_widget, NULL);
X		AddCallback(cancel_button, sensitize_all, NULL);
X
X	XtRealizeWidget(popup);
X
X	if (app_resources.fascistClear_Note)
X	{
X		XtVaGetValues(XtGrandParent(note), XtNwidth, &note_w, NULL);
X		XtVaGetValues(popup, XtNwidth, &popup_w, NULL);
X		XtTranslateCoords(XtGrandParent(note), (note_w - popup_w)/2, 0, &x, &y);
X		XtVaSetValues(popup, XtNx, x, XtNy, y, NULL);
X	}
X
X	XtPopup(popup, XtGrabNone);
X}
X
X
X/*
X * confirm_delete_note ()
X * delete the associated note -- unalloc_note does the real work
X */
Xstatic void
Xconfirm_delete_note(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	XtPopdown((Widget) client_data);
X	XtDestroyWidget((Widget) client_data);
X
X	if (widget = XtNameToWidget(toplevel, "Notes.list_form")) {
X		XtPopdown(XtParent(widget));
X		XtDestroyWidget(XtParent(widget));
X	}
X
X	unalloc_note((Widget) client_data);
X
X	if (widget)
X		show_list(widget, client_data, call_data);
X}
X
X
X/*
X * delete_note ()
X * put up a dialog asking if you really want to delete the
X * associated note
X */
Xstatic void
Xdelete_note(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget note = (Widget) client_data;
X	Widget popup, form, prompt;
X	Widget confirm_button, cancel_button;
X	Dimension note_w, popup_w;
X	Position x, y;
X
X	popup = XtCreatePopupShell("Destroy Note",
X		transientShellWidgetClass, toplevel,
X		NULL, ZERO);
X
X	form = XtCreateManagedWidget("form",
X		formWidgetClass, popup,
X		NULL, ZERO);
X
X	prompt = XtCreateManagedWidget("prompt",
X		labelWidgetClass, form,
X		NULL, ZERO);
X
X	confirm_button = XtCreateManagedWidget("confirm_button",
X		commandWidgetClass, form,
X		NULL, ZERO);
X		AddCallback(confirm_button, confirm_delete_note, note);
X		AddCallback(confirm_button, destroy_widget, NULL);
X		AddCallback(confirm_button, sensitize_all, NULL);
X
X	cancel_button = XtCreateManagedWidget("cancel_button",
X		commandWidgetClass, form,
X		NULL, ZERO);
X		AddCallback(cancel_button, destroy_widget, NULL);
X		AddCallback(cancel_button, sensitize_all, NULL);
X
X	XtRealizeWidget(popup);
X
X	if (app_resources.fascistDestroy_Note)
X	{
X		XtVaGetValues(note, XtNwidth, &note_w, NULL);
X		XtVaGetValues(popup, XtNwidth, &popup_w, NULL);
X		XtTranslateCoords(note, (note_w - popup_w)/2, 0, &x, &y);
X		XtVaSetValues(popup, XtNx, x, XtNy, y, NULL);
X	}
X
X	XtPopup(popup, XtGrabNone);
X}
X
X
X/*
X * confirm_new_title ()
X * change the title of associated note
X */
Xvoid
Xconfirm_new_title(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget w;
X	String str;
X	int i;
X
X	XtVaGetValues(title_to_change, XtNstring, &str, NULL);
X
X	if (strlen(str)) {
X		i = 0;
X		while (Notes[i]) {
X			if (title_parent == *Notes[i]) {
X				Titles[i] = (char *) realloc(Titles[i], strlen(str)+1);
X				if (!Titles[i])
X					die("Realloc in confirm_new_title failed.");
X				strcpy(Titles[i], str);
X				XtVaSetValues(title_parent, XtNtitle, str, NULL);
X				(void) sort_titles(0);
X				if ((w = XtNameToWidget(toplevel, "Notes.list_form.list")) != NULL)
X					XawListChange(w, Titles, 0, 0, False);
X				break;
X			}
X			i++;
X		}
X	}
X}
X
X
X/*
X * new_title ()
X * put up a prompt asking for a new title for the
X * associated note
X */
Xstatic void
Xnew_title(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget popup, form, prompt, input;
X	Widget confirm_button, cancel_button;
X	Dimension client_w, popup_w;
X	Position x, y;
X	String str;
X
X	title_parent = (Widget) client_data;
X
X	popup = XtCreatePopupShell("Change Title",
X		transientShellWidgetClass, toplevel,
X		NULL, ZERO);
X
X	form = XtCreateManagedWidget("form",
X		formWidgetClass, popup,
X		NULL, ZERO);
X
X	prompt = XtCreateManagedWidget("prompt",
X		labelWidgetClass, form,
X		NULL, ZERO);
X
X	XtVaGetValues((Widget) client_data, XtNtitle, &str, NULL);
X
X	title_to_change = input = XtVaCreateManagedWidget("input",
X		asciiTextWidgetClass, form,
X		XtNeditType, XawtextEdit,
X		NULL);
X
X	confirm_button = XtCreateManagedWidget("confirm_button",
X		commandWidgetClass, form,
X		NULL, ZERO);
X		AddCallback(confirm_button, confirm_new_title, NULL);
X		AddCallback(confirm_button, destroy_widget, NULL);
X		AddCallback(confirm_button, sensitize_all, NULL);
X
X	cancel_button = XtCreateManagedWidget("cancel_button",
X		commandWidgetClass, form,
X		NULL, ZERO);
X		AddCallback(cancel_button, destroy_widget, NULL);
X		AddCallback(cancel_button, sensitize_all, NULL);
X
X	XtRealizeWidget(popup);
X
X	if (app_resources.fascistChange_Title)
X	{
X		XtVaGetValues((Widget) client_data, XtNwidth, &client_w, NULL);
X		XtVaGetValues(popup, XtNwidth, &popup_w, NULL);
X		XtTranslateCoords((Widget) client_data, (client_w - popup_w)/2, 0,
X			&x, &y);
X		XtVaSetValues(popup, XtNx, x, XtNy, y, NULL);
X	}
X
X	XtPopup(popup, XtGrabNone);
X}
X
X
X/*
X * confirm_new_note ()
X * create a new note -- alloc_new_note does the bulk
X * of the work
X */
Xvoid
Xconfirm_new_note(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	String str;
X	int i;
X
X	XtVaGetValues(note_to_create, XtNstring, &str, NULL);
X
X	if (strlen(str)) {
X		i = alloc_new_note(str);
X		destroy_list();
X		show_list(widget, client_data, call_data);
X		XtPopup(*Notes[i], XtGrabNone);
X	}
X}
X
X
X/*
X * new_note ()
X * put up a dialog asking for the title of a new note
X */
Xstatic void
Xnew_note(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget popup, form, prompt, input;
X	Widget confirm_button, cancel_button;
X	Dimension top_w, popup_w;
X	Position x, y;
X
X	popup = XtCreatePopupShell("New Note",
X		transientShellWidgetClass, toplevel,
X		NULL, ZERO);
X
X	form = XtCreateManagedWidget("form",
X		formWidgetClass, popup,
X		NULL, ZERO);
X
X	prompt = XtCreateManagedWidget("prompt",
X		labelWidgetClass, form,
X		NULL, ZERO);
X
X	note_to_create = input = XtVaCreateManagedWidget("input",
X		asciiTextWidgetClass, form,
X		XtNeditType, XawtextEdit,
X		NULL);
X
X	confirm_button = XtCreateManagedWidget("confirm_button",
X		commandWidgetClass, form,
X		NULL, ZERO);
X		AddCallback(confirm_button, confirm_new_note, NULL);
X		AddCallback(confirm_button, destroy_widget, NULL);
X		AddCallback(confirm_button, sensitize_all, NULL);
X
X	cancel_button = XtCreateManagedWidget("cancel_button",
X		commandWidgetClass, form,
X		NULL, ZERO);
X		AddCallback(cancel_button, destroy_widget, NULL);
X		AddCallback(cancel_button, sensitize_all, NULL);
X
X	XtRealizeWidget(popup);
X
X	if (app_resources.fascistNew_Note)
X	{
X		XtVaGetValues(toplevel, XtNwidth, &top_w, NULL);
X		XtVaGetValues(popup, XtNwidth, &popup_w, NULL);
X		XtTranslateCoords(toplevel, (top_w - popup_w)/2, 0, &x, &y);
X		XtVaSetValues(popup, XtNx, x, XtNy, y, NULL);
X	}
X
X	XtPopup(popup, XtGrabNone);
X}
X
X
X/*
X * dismiss_show_note ()
X * unmap a note from the display -- note it does not destroy
X * the note widget
X */
Xstatic void 
Xdismiss_show_note(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	XtPopdown(XtGrandParent(widget));
X	XtUnmapWidget(XtGrandParent(widget));
X}
X
X
X/*
X * show_note ()
X * map a note to the display
X */
Xstatic void
Xshow_note(widget, client_data, call_data)
X     Widget widget;
X     XtPointer client_data, call_data;
X{
X	XawListReturnStruct *item = (XawListReturnStruct*) call_data;
X	Widget w;
X	XWindowAttributes atribs;
X
X	w = *Notes[item->list_index];
X	XGetWindowAttributes(XtDisplay(w), XtWindow(w), &atribs);
X
X	if (atribs.map_state == IsUnmapped)
X		XtPopup(w, XtGrabNone);
X	else
X		XRaiseWindow(XtDisplay(w), XtWindow(w));
X}
X
X
X/*
X * select_note ()
X */
Xstatic void
Xselect_note(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget w = (Widget) client_data;
X	Display *d;
X	String str;
X
X	d = XtDisplay(XtGrandParent(widget));
X	XtVaGetValues(w, XtNstring, &str, NULL);
X	if (strlen(str)) {
X		XawTextSetSelection(w, 0, strlen(str));
X		XStoreBytes(d, str, strlen(str));
X	}
X}
X
X
X/*
X * make_note_widget ()
X * dynamically allocate a widget, create a new note, and
X * return a pointer to the widget -- remember that it's a
X * pointer, not a widget itself
X */
XWidget *
Xmake_note_widget(title, x, y, w, h, text)
X	char *title, *text;
X	int x, y, w, h;
X{
X	Widget *popup, form, note;
X	Widget dismiss_button, title_button, clear_button, delete_button;
X	Widget select_button;
X
X	popup = (Widget *) malloc(sizeof(Widget));
X	if (!popup)
X		die("Malloc in make_note_widget failed.");
X
X	*popup = XtVaCreatePopupShell(title,
X		transientShellWidgetClass, toplevel,
X		XtNx, x, XtNy, y, NULL);
X
X	form = XtCreateManagedWidget("form",
X		formWidgetClass, *popup,
X		NULL, ZERO);
X
X	dismiss_button = XtVaCreateManagedWidget("dismiss_button",
X		commandWidgetClass, form,
X		XtNlabel, "Dismiss",
X		XtNwidth, 64,
X		XtNtop, XawChainTop,
X		XtNbottom, XawChainTop,
X		XtNleft, XawChainLeft,
X		XtNright, XawChainLeft,
X		NULL);
X		AddCallback(dismiss_button, dismiss_show_note, NULL);
X
X	note = XtVaCreateManagedWidget("note",
X		asciiTextWidgetClass, form,
X		XtNfromVert, dismiss_button,
X		XtNstring, text,
X		XtNwidth, w,
X		XtNheight, h,
X		XtNscrollVertical, XawtextScrollAlways,
X		XtNeditType, XawtextEdit,
X		XtNwrap, XawtextWrapLine,
X		XtNtop, XawChainTop,
X		XtNbottom, XawChainBottom,
X		XtNleft, XawChainLeft,
X		XtNright, XawChainRight,
X		NULL);
X
X	title_button = XtVaCreateManagedWidget("title_button",
X		commandWidgetClass, form,
X		XtNfromHoriz, dismiss_button,
X		XtNlabel, "Title",
X		XtNwidth, 64,
X		XtNtop, XawChainTop,
X		XtNbottom, XawChainTop,
X		XtNleft, XawChainLeft,
X		XtNright, XawChainLeft,
X		NULL);
X		AddCallback(title_button, desensitize_all, NULL);
X		AddCallback(title_button, new_title, *popup);
X
X	clear_button = XtVaCreateManagedWidget("clear_button",
X		commandWidgetClass, form,
X		XtNfromHoriz, title_button,
X		XtNlabel, "Clear",
X		XtNwidth, 64,
X		XtNtop, XawChainTop,
X		XtNbottom, XawChainTop,
X		XtNleft, XawChainLeft,
X		XtNright, XawChainLeft,
X		NULL);
X		AddCallback(clear_button, desensitize_all, NULL);
X		AddCallback(clear_button, clear_note, note);
X
X	delete_button = XtVaCreateManagedWidget("delete_button",
X		commandWidgetClass, form,
X		XtNfromHoriz, clear_button,
X		XtNlabel, "Destroy",
X		XtNwidth, 64,
X		XtNtop, XawChainTop,
X		XtNbottom, XawChainTop,
X		XtNleft, XawChainLeft,
X		XtNright, XawChainLeft,
X		NULL);
X		AddCallback(delete_button, desensitize_all, NULL);
X		AddCallback(delete_button, delete_note, *popup);
X
X	select_button = XtVaCreateManagedWidget("select_button",
X		commandWidgetClass, form,
X		XtNfromHoriz, delete_button,
X		XtNlabel, "Select",
X		XtNwidth, 64,
X		XtNtop, XawChainTop,
X		XtNbottom, XawChainTop,
X		XtNleft, XawChainLeft,
X		XtNright, XawChainLeft,
X		NULL);
X		AddCallback(select_button, select_note, note);
X
X	XtRealizeWidget(*popup);
X
X	return popup;
X}
X
X
X/*
X * destroy_list ()
X * this destroy_list is called by confirm_new_note
X */
Xvoid
Xdestroy_list()
X{
X	Widget w;
X
X	if ((w = XtNameToWidget(toplevel, "Notes.list_form")) != NULL) {
X		XtPopdown(XtParent(w));
X		XtDestroyWidget(XtParent(w));
X	}
X}
X
X
X/*
X * revert ()
X * revert the internal notes to what is stored in the note file.
X */
Xvoid
Xrevert(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	revert_notefile();
X}
X
X
X/*
X * show_list ()
X * desensitize the toplevel startup button and put up
X * the list of notes
X */
Xvoid
Xshow_list(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget popup, list_form, list, revert_button;
X	Widget dismiss_button, new_button, save_button, quit_button;
X	Dimension top_w, popup_w;
X	Position x, y;
X
X	popup = XtCreatePopupShell("Notes",
X		transientShellWidgetClass, toplevel,
X		NULL, ZERO);
X
X	list_form = XtCreateManagedWidget("list_form",
X		formWidgetClass, popup,
X		NULL, ZERO);
X
X	new_button = XtCreateManagedWidget("new_button",
X		commandWidgetClass, list_form,
X		NULL, ZERO);
X		AddCallback(new_button, desensitize_all, NULL);
X		AddCallback(new_button, new_note, NULL);
X
X	dismiss_button = XtCreateManagedWidget("dismiss_button",
X		commandWidgetClass, list_form,
X		NULL, ZERO);
X		AddCallback(dismiss_button, destroy_widget, NULL);
X		AddCallback(dismiss_button, sensitize_start_button, NULL);
X
X	save_button = XtCreateManagedWidget("save_button",
X		commandWidgetClass, list_form,
X		NULL, ZERO);
X		AddCallback(save_button, save_callback, NULL);
X
X	list = XtVaCreateManagedWidget("list",
X		listWidgetClass, list_form,
X		XtNlist, Titles,
X		NULL);
X		AddCallback(list, show_note, NULL);
X
X	quit_button = XtCreateManagedWidget("quit_button",
X		commandWidgetClass, list_form,
X		NULL, ZERO);
X		AddCallback(quit_button, quit, NULL);
X
X	revert_button = XtCreateManagedWidget("revert_button",
X		commandWidgetClass, list_form,
X		NULL, ZERO);
X		AddCallback(revert_button, revert, NULL);
X		AddCallback(revert_button, destroy_widget, NULL);
X		AddCallback(revert_button, show_list, NULL);
X
X	XtRealizeWidget(popup);
X
X	if (app_resources.fascistNotes)
X	{
X		XtVaGetValues(toplevel, XtNwidth, &top_w, NULL);
X		XtVaGetValues(popup, XtNwidth, &popup_w, NULL);
X		XtTranslateCoords(toplevel, (top_w - popup_w)/2, 0, &x, &y);
X		XtVaSetValues(popup, XtNx, x, XtNy, y, NULL);
X	}
X
X	XtPopup(popup, XtGrabNone);
X}
SHAR_EOF
  $shar_touch -am 0722105995 'callbacks.c' &&
  chmod 0644 'callbacks.c' ||
  echo 'restore of callbacks.c failed'
  rm -f _sharnew.tmp
fi
# ============= main.c ==============
if test -f 'main.c' && test X"$1" != X"-c"; then
  echo 'x - skipping main.c (file already exists)'
  rm -f _sharnew.tmp
else
  > _sharnew.tmp
  echo 'x - extracting main.c (text)'
  sed 's/^X//' << 'SHAR_EOF' > 'main.c' &&
X#ifndef lint
Xstatic char sccs_id[] = "main.c -- Mon May 30 01:22:28 EDT 1994";
X#endif
X/*
X * main.c -- Mon May 30 01:22:28 EDT 1994
X *
X * Copyright (c) 1994 -- Bob Smith <bob@snuffy.penfield.ny.us>
X *
X * I hate copyright notices...  They're generally of a lot of words
X * that end up saying -- You can do whatever you want with this
X * as long as you don't rip me off!  So with that said, enjoy, and
X * have a good day!
X *
X */
X
X#include <stdio.h>
X#include <stdlib.h>
X#include <patchlevel.h>
X#ifdef SVR4
X#include <string.h>
X#else
X#include <strings.h>
X#endif
X#include <malloc.h>
X#include <signal.h>
X#ifndef SYSV
X#include <sys/param.h>		/* for MAXPATHLEN */
X#endif
X#include <sys/types.h>
X#include <sys/stat.h>
X
X#include <X11/Intrinsic.h>
X#include <X11/StringDefs.h>
X#include <X11/Shell.h>
X#include <X11/Xatom.h>
X
X#include <X11/Xaw/Box.h>
X#include <X11/Xaw/Cardinals.h>
X#include <X11/Xaw/Command.h>
X#include <X11/Xaw/Label.h>
X#include <X11/Xaw/Form.h>
X#include <X11/Xaw/List.h>
X
X#define MAIN_C
X#include "notes.h"
X
X
X/*
X * local variables
X */
XWidget start_button;
Xstatic char notefile[MAXPATHLEN];
Xstatic int notefile_loaded = FALSE;
X
X
X/*
X * forward declarations
X */
Xvoid die(), write_notefile(), sensitize_start_button();
Xstatic void dismiss_all(), dismiss_note(), save_dismiss_all();
Xstatic void version(), ask_quit(), desensitize_start_button();
X
X
X/*
X * external functions
X */
Xextern void confirm_new_note(), confirm_new_title();
Xextern void destroy_widget(), sensitize_all();
Xextern void null(), quit(), show_list(), destroy_list();
Xextern Widget *make_note_widget();
X
X
X/*
X * XtActionsRec actionTable
X */
Xstatic XtActionsRec actionTable[] = {
X	{ "null",				null },
X	{ "quit",				quit },
X	{ "ask_quit",			ask_quit },
X	{ "version",			version },
X	{ "dismiss_all",		dismiss_all },
X	{ "dismiss_note",		dismiss_note },
X	{ "save_dismiss_all",	save_dismiss_all },
X	{ "confirm_new_note",	confirm_new_note },
X	{ "confirm_new_title",	confirm_new_title },
X	{ "destroy_widget",		destroy_widget },
X	{ "sensitize_all",		sensitize_all },
X};
X
X#define offset(field) XtOffset(struct _app_resources*, field)
X
Xstatic XtResource x_resources[] = {
X	{"defaultsInstalled", "DefaultsInstalled",  XtRBoolean, sizeof(Boolean),
X		offset(defaultsInstalled), XtRBoolean, False},
X	{"fascistQuit", "FascistQuit",  XtRBoolean, sizeof(Boolean),
X		offset(fascistQuit), XtRBoolean, False},
X	{"fascistVersion", "FascistVersion",  XtRBoolean, sizeof(Boolean),
X		offset(fascistVersion), XtRBoolean, False},
X	{"fascistClear_Note", "FascistClear_Note",  XtRBoolean, sizeof(Boolean),
X		offset(fascistClear_Note), XtRBoolean, False},
X	{"fascistDestroy_Note", "FascistDestroy_Note",  XtRBoolean, sizeof(Boolean),
X		offset(fascistDestroy_Note), XtRBoolean, False},
X	{"fascistChange_Title", "FascistChange_Title",  XtRBoolean, sizeof(Boolean),
X		offset(fascistChange_Title), XtRBoolean, False},
X	{"fascistNew_Note", "FascistNew_Note",  XtRBoolean, sizeof(Boolean),
X		offset(fascistNew_Note), XtRBoolean, False},
X	{"fascistNotes", "FascistNotes",  XtRBoolean, sizeof(Boolean),
X		offset(fascistNotes), XtRBoolean, False},
X	{"fascistNewNote", "FascistNewNote", XtRBoolean, sizeof(Boolean),
X		offset(fascistNewNote), XtRBoolean, False},
X	{"newNoteX", "NewNoteX", XtRPosition, sizeof(Position),
X		offset(newNoteX), XtRPosition, 0},
X	{"newNoteY", "NewNoteY", XtRPosition, sizeof(Position),
X		offset(newNoteY), XtRPosition, 0},
X	{"newNoteWidth", "NewNoteWidth", XtRDimension, sizeof(Dimension),
X		offset(newNoteWidth), XtRDimension, 0},
X	{"newNoteHeight", "NewNoteHeight", XtRDimension, sizeof(Dimension),
X		offset(newNoteHeight), XtRDimension, 0},
X	{"h_offset", "H_offset", XtRDimension, sizeof(Dimension),
X		offset(h_offset), XtRDimension, 0},
X	{"v_offset", "V_offset", XtRDimension, sizeof(Dimension),
X		offset(v_offset), XtRDimension, 0},
X	{"noteFile", "NoteFile", XtRString, sizeof(String),
X		offset(noteFile), XtRString, ".notes"},
X	{"saveOnExit", "SaveOnExit", XtRBoolean, sizeof(Boolean),
X		offset(saveOnExit), XtRBoolean, False},
X	{"createBackup", "CreateBackup", XtRBoolean, sizeof(Boolean),
X		offset(createBackup), XtRBoolean, False},
X};
X
X
X#ifdef NEED_STRDUP
X/*
X * strdup ()
X */
Xchar *
Xstrdup(s)
X	char *s;
X{
X	char *t;
X
X	if ((t = malloc(strlen(s)+1)) == NULL)
X		die("Malloc in strdup failed.");
X	strcpy(t, s);
X	return t;
X}
X#endif
X
X
X/*
X * die ()
X */
Xvoid
Xdie(s)
X	char *s;
X{
X	fprintf(stderr, "%s\n", s);
X	fflush(stderr);
X	XtDestroyApplicationContext(app_con);
X	exit(1);
X}
X
X
X/*
X * sig_quit ()
X */
Xstatic void
Xsig_quit(sig, code, scp)
X	int sig, code;
X	struct sigcontext *scp;
X{
X	signal(SIGHUP, SIG_IGN);
X	signal(SIGINT, SIG_IGN);
X	signal(SIGQUIT, SIG_IGN);
X	signal(SIGTERM, SIG_IGN);
X	quit();
X}
X
X
X/*
X * dismiss_all ()
X * dismiss all notes and the list widget
X */
Xstatic void
Xdismiss_all(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	int i;
X	XWindowAttributes atribs;
X
X	i = 0;
X	while (Notes[i]) {
X		XGetWindowAttributes(XtDisplay(*Notes[i]),
X			XtWindow(*Notes[i]), &atribs);
X		if (atribs.map_state != IsUnmapped) {
X			XtPopdown(*Notes[i]);
X			XtUnmapWidget(*Notes[i]);
X		}
X		i++;
X	}
X	destroy_list();
X	sensitize_start_button(widget, client_data, call_data);
X}
X
X
X/*
X * save_dismiss_all ()
X * save the notefile and dismiss all notes and the list
X */
Xstatic void
Xsave_dismiss_all(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	write_notefile();
X	dismiss_all(NULL, NULL, NULL);
X}
X
X
X/*
X * dismiss_note ()
X * dismiss a note
X */
Xstatic void
Xdismiss_note(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	XawListReturnStruct *item;
X	Widget w;
X	XWindowAttributes atribs;
X
X	item = XawListShowCurrent(widget);
X	if (item->list_index == -1)
X		return;
X
X	w = *Notes[item->list_index];
X	XGetWindowAttributes(XtDisplay(w), XtWindow(w), &atribs);
X
X	if (atribs.map_state != IsUnmapped) {
X		XtPopdown(w);
X		XtUnmapWidget(w);
X	}
X}
X
X
X/*
X * ask_quit()
X */
Xstatic void
Xask_quit(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget popup, form, prompt;
X	Widget confirm_button, cancel_button;
X	Dimension top_w, pop_w;
X	Position x, y;
X
X	desensitize_start_button(NULL, NULL, NULL);
X
X	popup = XtCreatePopupShell("Quit",
X		transientShellWidgetClass, toplevel,
X		NULL, ZERO);
X
X	form = XtCreateManagedWidget("form",
X		formWidgetClass, popup,
X		NULL, ZERO);
X
X	prompt = XtCreateManagedWidget("prompt",
X		labelWidgetClass, form,
X		NULL, ZERO);
X
X	confirm_button = XtCreateManagedWidget("confirm_button",
X		commandWidgetClass, form,
X		NULL, ZERO);
X		AddCallback(confirm_button, quit, NULL);
X
X	cancel_button = XtCreateManagedWidget("cancel_button",
X		commandWidgetClass, form,
X		NULL, ZERO);
X		AddCallback(cancel_button, destroy_widget, NULL);
X		AddCallback(cancel_button, sensitize_start_button, NULL);
X
X	XtRealizeWidget(popup);
X
X	if (app_resources.fascistQuit)
X	{
X		XtVaGetValues(toplevel, XtNwidth, &top_w, NULL);
X		XtVaGetValues(popup, XtNwidth, &pop_w, NULL);
X		XtTranslateCoords(toplevel, (top_w-pop_w)/2, 0, &x, &y);
X		XtVaSetValues(popup, XtNx, x, XtNy, y, NULL);
X	}
X
X	XtPopup(popup, XtGrabNone);
X}
X
X/*
X * sort_titles ()
X * sort the titles and return the new index of where widget
X * `j' ended up
X */
Xint
Xsort_titles(j)
X	int j;
X{
X	int i;
X	char *s;
X
X	i = 0;
X	while (Titles[i] && Titles[i+1]) {
X		if (strcmp(Titles[i], Titles[i+1]) > 0) {
X			if (j == i)
X				j++;
X			else
X				if (j == i+1)
X					j--;
X			s = Titles[i];
X			Titles[i] = Titles[i+1];
X			Titles[i+1] = s;
X			s = (char *) Notes[i];
X			Notes[i] = Notes[i+1];
X			Notes[i+1] = (Widget *) s;
X			i = 0;
X		} else
X			i++;
X	}
X	return j;
X}
X
X
X/*
X * read_notefile ()
X * read the notefile and make a note widget for each note
X */
Xvoid
Xread_notefile()
X{
X	FILE *fp;
X	char title[80];
X	char *buffer, *s, *t;
X	int i, x, y, w, h;
X	char *getenv();
X	struct stat sbuf;
X
X	notefile_loaded = FALSE;
X
X	Notes = (Widget **) malloc(sizeof(char *));
X	Titles = (char **) malloc(sizeof(char *));
X	if (!Notes || !Titles)
X		die("Malloc in read_notefile failed.");
X	*Notes = NULL;
X	*Titles = NULL;
X
X	/*
X	 * check the current directory, and then the HOME
X	 * directory...  if there is no .notes file, free the
X	 * temp buffer and get out of here leaving notefile
X	 * pointing to the HOME directory
X	 */
X	strcpy(notefile, app_resources.noteFile);
X	if ((fp = fopen(notefile, "r")) == NULL) {
X		if ((s = getenv("HOME")) == NULL)
X			return;
X		strcpy(notefile, s);
X		strcat(notefile, "/");
X		strcat(notefile, app_resources.noteFile);
X		if ((fp = fopen(notefile, "r")) == NULL)
X		{
X			notefile_loaded = TRUE;
X			return;
X		}
X	}
X
X	/*
X	 * check the size of the notes file and allocate a buffer
X	 * of appropriate size
X	 */
X	if (fstat(fileno(fp), &sbuf) == 0) {
X		if ((buffer = malloc(sbuf.st_size+1)) == NULL) {
X			fclose(fp);
X			die("Malloc of buffer in read_notefile failed.");
X		}
X	} else {
X		fclose(fp);
X		die("Can't stat notes file.");
X	}
X
X	/*
X	 * read the notes file into the temp buffer
X	 */
X	fread(buffer, sbuf.st_size, 1, fp);
X	buffer[sbuf.st_size] = '\0';
X	fclose(fp);
X
X	/*
X	 * spin through the temp buffer and setup the initial
X	 * state of the NoteStruct pointers...
X	 */
X	s = buffer;
X	i = 0;
X	while (*s) {
X		if (*s == '\f') {
X			*s = '\0';
Xspeed_hack:;
X			i++;
X			Notes = (Widget **) realloc(Notes, (i+1)*sizeof(char *));
X			Titles = (char **) realloc(Titles, (i+1)*sizeof(char *));
X			if (!Notes || !Titles)
X				die("Realloc in read_notefile failed.");
X			s++;
X			if ((t = index(s, '\n')) == NULL)
X				die("Oops! No newline at end of title?");
X			else {
X				sscanf(s, "%d %d %d %d %[^\n]", &x, &y, &w, &h, title);
X				s = ++t;
X				if ((t = index(s, '\f')) != NULL) *t = '\0';
X				Notes[i-1] = make_note_widget(title, x, y, w, h, s);
X				Notes[i] = NULL;
X				Titles[i-1] = strdup(title);
X				Titles[i] = NULL;
X				if (t) {
X					s = t;
X					/* this is ugly, but it works...  */
X					goto speed_hack;
X				}
X			}
X		} else
X			s++;
X	}
X	free(buffer);
X	(void) sort_titles(0);
X
X	notefile_loaded = TRUE;
X}
X
X
X/*
X * alloc_new_note ()
X * make a new note
X */
Xint
Xalloc_new_note(title)
X	char *title;
X{
X	int i;
X	Position top_w, x, y;
X
X	if (app_resources.fascistNewNote)
X	{
X		XtVaGetValues(toplevel, XtNwidth, &top_w, NULL);
X		XtTranslateCoords(toplevel, (top_w - 512)/2, 0, &x, &y);
X	}
X	else
X	{
X		x = app_resources.newNoteX;
X		y = app_resources.newNoteY;
X	}
X
X	i = 0;
X	while (Notes[i]) i++;
X	i++;
X	Notes = (Widget **) realloc(Notes, (i+1)*sizeof(char *));
X	Titles = (char **) realloc(Titles, (i+1)*sizeof(char *));
X	if (!Notes || !Titles)
X		die("Realloc in alloc_new_note failed.");
X	Notes[i-1] = make_note_widget(title, x, y,
X		app_resources.newNoteWidth, app_resources.newNoteHeight, "");
X	Notes[i] = NULL;
X	Titles[i-1] = strdup(title);
X	Titles[i] = NULL;
X	return sort_titles(i-1);
X}
X
X
X/*
X * unalloc_note ()
X */
Xvoid
Xunalloc_note(widget)
X	Widget widget;
X{
X	int i;
X
X	i = 0;
X	while (Notes[i]) {
X		if (*Notes[i] == widget) {
X			while (Notes[i+1]) {
X				Notes[i] = Notes[i+1];
X				Titles[i] = Titles[i+1];
X				i++;
X			}
X			Notes[i] = NULL;
X			Titles[i] = NULL;
X			Notes = (Widget **) realloc(Notes, (i+1)*sizeof(char *));
X			Titles = (char **) realloc(Titles, (i+1)*sizeof(char *));
X			if (!Notes || !Titles)
X				die("Realloc in unalloc_note failed.");
X			return;
X		}
X		i++;
X	}
X}
X
X
X/*
X * revert_notefile ()
X */
Xvoid
Xrevert_notefile()
X{
X	int i;
X
X	dismiss_all(NULL, NULL, NULL);
X  
X	i = 0;
X	while (Notes[i]) {
X		XtDestroyWidget((Widget) *Notes[i]);
X		free(Titles[i]);
X		Notes[i] = NULL;
X		Titles[i] = NULL;
X		i++;
X	}
X  
X	free(Notes);
X	free(Titles);
X	Notes = NULL;
X	Titles = NULL;
X
X	read_notefile();
X}
X
X
X/*
X * write_notefile ()
X */
Xvoid
Xwrite_notefile()
X{
X	FILE *fp;
X	int i;
X	Dimension w, h;
X	Position x, y;
X	String title, text;
X	XWindowAttributes atribs;
X	char backup_notefile[MAXPATHLEN];
X
X	if (!notefile_loaded)
X		return;
X
X	if (app_resources.createBackup)
X	{
X		sprintf(backup_notefile, "%s.bak", notefile);
X		rename(notefile, backup_notefile);
X	}
X
X	if ((fp = fopen(notefile, "w")) == NULL)
X		return;
X
X	i = 0;
X	while (Notes[i]) {
X		XtVaGetValues(*Notes[i], XtNtitle, &title,
X			XtNx, &x, XtNy, &y, NULL);
X		XGetWindowAttributes(XtDisplay(*Notes[i]),
X			XtWindow(*Notes[i]), &atribs);
X		/*
X		 * this hack is the only way I know for now of eliminating
X		 * 'creeping' windows caused by the offset injected into
X		 * the x and y values of a window when they're mapped by
X		 * a window manager such as twm...  there's undoubtedly
X		 * a more elegant approach, but I don't know how to
X		 * do it yet! :-)
X		 */
X		if (atribs.map_state == IsViewable) {
X			x -= app_resources.h_offset;
X			y -= app_resources.v_offset;
X		}
X		XtVaGetValues(XtNameToWidget(*Notes[i], "form.note"),
X			XtNstring, &text, XtNwidth, &w, XtNheight, &h, NULL);
X		w = max(w, 5*66+4*4);
X		h = max(h, 64);
X		fprintf(fp, "\f%d %d %d %d %s\n%s", x, y, w, h, title, text);
X		i++;
X	}
X	fclose(fp);
X}
X
X
X/*
X * desensitize_start_button ()
X */
Xstatic void
Xdesensitize_start_button(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget w;
X
X	w = XtNameToWidget(toplevel, "start_button");
X	if (w)
X		XtVaSetValues(w, XtNsensitive, False, NULL);
X}
X
X
X/*
X * sensitize_start_button ()
X */
Xvoid
Xsensitize_start_button(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget w;
X
X	w = XtNameToWidget(toplevel, "start_button");
X	if (w)
X		XtVaSetValues(w, XtNsensitive, True, NULL);
X}
X
X/*
X * version ()
X */
Xstatic void
Xversion(widget, client_data, call_data)
X	Widget widget;
X	XtPointer client_data, call_data;
X{
X	Widget w, popup, form, prompt, dismiss_button;
X	Position top_w, pop_w, x, y;
X	static char version_label[256];
X
X	desensitize_start_button(NULL, NULL, NULL);
X
X	popup = XtCreatePopupShell("Version",
X		transientShellWidgetClass, toplevel,
X		NULL, ZERO);
X
X	form = XtCreateManagedWidget("form",
X		formWidgetClass, popup,
X		NULL, ZERO);
X
X	prompt = XtCreateManagedWidget("prompt",
X		labelWidgetClass, form,
X		NULL, ZERO);
X
X	sprintf(version_label, "Notes v %d.%d.%d\n%s",
X		VERSION, SUBVERSION, PATCHLEVEL, AUTHOR);
X
X	XtVaSetValues(prompt, XtNlabel, version_label, NULL);
X
X	dismiss_button = XtCreateManagedWidget("dismiss_button",
X		commandWidgetClass, form,
X		NULL, ZERO);
X		AddCallback(dismiss_button, destroy_widget, NULL);
X		AddCallback(dismiss_button, sensitize_start_button, NULL);
X
X	XtRealizeWidget(popup);
X
X	if (app_resources.fascistVersion)
X	{
X		XtVaGetValues(toplevel, XtNwidth, &top_w, NULL);
X		XtVaGetValues(popup, XtNwidth, &pop_w, NULL);
X		XtTranslateCoords(toplevel, (top_w-pop_w)/2, 0, &x, &y);
X		XtVaSetValues(popup, XtNx, x, XtNy, y, NULL);
X	}
X
X	XtPopup(popup, XtGrabNone);
X}
X
X
X/*
X * main ()
X */
Xmain(argc, argv)
X	int argc;
X	char *argv[];
X{
X	Widget start_button;
X
X	toplevel = XtAppInitialize(&app_con, "Notes",
X		NULL, ZERO,				/* options, option count */
X		&argc, argv,			/* command line options */
X		NULL,					/* fallback resources */
X		NULL, ZERO);			/* other args */
X
X	XtGetApplicationResources(toplevel, &app_resources,
X		x_resources, XtNumber(x_resources),
X		NULL, ZERO);
X
X	if (!app_resources.defaultsInstalled)
X	{
X		fprintf(stderr, "X resources not properly installed.\n");
X		exit(1);
X	}
X
X	XtAppAddActions(app_con, actionTable, XtNumber(actionTable));
X
X	start_button = XtCreateManagedWidget("start_button",
X		commandWidgetClass, toplevel,
X		NULL, ZERO);
X		AddCallback(start_button, desensitize_start_button, NULL);
X		AddCallback(start_button, show_list, NULL);
X
X	XtRealizeWidget(toplevel);
X
X	read_notefile();
X
X	signal(SIGHUP, sig_quit);
X	signal(SIGINT, sig_quit);
X	signal(SIGQUIT, sig_quit);
X	signal(SIGTERM, sig_quit);
X
X	XSetIOErrorHandler((XIOErrorHandler) quit);
X
X	XtAppMainLoop(app_con);
X}
SHAR_EOF
  $shar_touch -am 0722112495 'main.c' &&
  chmod 0644 'main.c' ||
  echo 'restore of main.c failed'
  rm -f _sharnew.tmp
fi
# ============= notes.el ==============
if test -f 'notes.el' && test X"$1" != X"-c"; then
  echo 'x - skipping notes.el (file already exists)'
  rm -f _sharnew.tmp
else
  > _sharnew.tmp
  echo 'x - extracting notes.el (text)'
  sed 's/^X//' << 'SHAR_EOF' > 'notes.el' &&
X(defconst notes-line-numbers "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ")
X(defconst notes-num-line-numbers 36)
X
X(setq notes-last-seen 1)
X
X(defconst notes-flag-list
X  '((mod 5 "*")
X    (tag 3 "T")
X    (del 3 "D")
X    (new 4 "+")
X    (vis 6 ".")))
X
X
X(defvar notes-file "~/.notes"
X  "The default note file to use.")
X
X(defvar notes-real-file nil
X  "The current notes file in use.")
X
X(defvar notes-old-windows nil
X  "The old window configuration.")
X
X(defvar notes-edit-map nil "")
X(defvar notes-mode-map nil "")
X(setq notes-mode-map nil)
X(setq notes-edit-map nil)
X
X
X(defvar notes-magic-x-min 354 "")
X(defvar notes-magic-y-min 50 "")
X(defvar notes-magic-x-offset 6 "")
X(defvar notes-magic-y-offset 6 "")
X(defvar notes-magic-x-incr 20 "")
X(defvar notes-magic-y-incr 10 "")
X(defvar notes-magic-x-size 7 "")
X(defvar notes-magic-y-size 14 "")
X(defvar notes-magic-screen-x 1024 "")
X(defvar notes-magic-screen-y 845 "")
X
X
X
X(if notes-mode-map ()
X  (setq notes-mode-map (make-keymap))
X  (define-key notes-mode-map "\C-n"        'notes-next-line)
X  (define-key notes-mode-map "\C-p"        'notes-previous-line)
X  (define-key notes-mode-map "\C-m"        'notes-select-next)
X  (define-key notes-mode-map "\C-d"        'notes-do-deletes)
X  (define-key notes-mode-map " "           'notes-select-current)
X  (define-key notes-mode-map "\177"        'notes-select-previous)
X  (define-key notes-mode-map "q"           'notes-quit)
X  (define-key notes-mode-map "\C-c\C-c"    'notes-exit)
X  (define-key notes-mode-map "\C-x\C-s"    'notes-save)
X  (define-key notes-mode-map "e"           'notes-edit)
X  (define-key notes-mode-map "n"           'notes-new)
X  (define-key notes-mode-map "v"           'notes-view)
X  (define-key notes-mode-map "t"           'notes-tag)
X  (define-key notes-mode-map "d"           'notes-tag-delete)
X  (define-key notes-mode-map "u"           'notes-untag)
X  (define-key notes-mode-map "?"           'notes-help)
X
X  (let ((index 0) (char))
X    (while (< index notes-num-line-numbers)
X      (setq char (char-to-string (aref notes-line-numbers index)))
X      (define-key notes-mode-map char 'notes-jump-to-line)
X      (setq index (1+ index))))
X  )
X
X
X;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
X
X(defmacro notes-excursion (buffer &rest body)
X  "This macro is for internal use.  It sets the current buffer to BUFFER,
Xsaves the read-only and modified states of it, makes it writable, then
Xexecutes BODY in a save-excursion form.  Finally, the original states of
Xthe buffer are restored and the selected buffer befored this call is
Xreselected.  The result of BODY is returned."
X  (` (let ((oldbuff (current-buffer))
X           (result nil))
X       (set-buffer (, buffer))
X       (let ((modified (buffer-modified-p))
X             (rwstatus buffer-read-only))
X         (setq buffer-read-only nil)
X         (setq result 
X               (save-excursion
X                 (,@ body)))
X         (set-buffer-modified-p modified)
X         (setq buffer-read-only rwstatus))
X       (set-buffer oldbuff)
X       result)))
X
X;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
X
X(defun notes-title (index)
X  "Returns the title string of the note at the INDEX, starting at 1."
X  (notes-excursion 
X   "*notes-titles*"
X   (goto-line index)
X   (forward-char 8)
X   (buffer-substring (point) (progn (end-of-line) (point)))))
X  
X;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
X
X(defun notes-fix-line-numbers ()
X  "Used to redo the numbers after a new note is added."
X  (notes-excursion 
X   "*notes-titles*"
X   (let ((lines (count-lines (point-min) (point-max)))
X         (index 0))
X     (goto-char (point-min))
X     (while (< index lines)
X       (delete-char 1)
X       (if (< index notes-num-line-numbers)
X           (insert (aref notes-line-numbers index))
X         (insert " "))
X       (forward-line 1)
X       (setq index (1+ index))))))
X
X;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
X
X(defun notes-new (title)
X  "Inserts the note entitled TITLE lexicographically into the notes
Xbuffers.  The note is blank with size and position information being
Xall zero."
X  (interactive "snew note title: ")
X  (set-buffer "*notes-titles*")
X  (if (string= title "") nil
X    (let ((index 1)
X          (entry nil)
X          (done nil)
X          (limit (count-lines (point-min) (point-max))))
X      (notes-set (count-lines (point-min) (point)) 'vis nil)
X      ;;
X      ;; Search for the proper position.
X      ;;
X      (save-excursion
X        (goto-char (point-min))
X        (while (and (<= index limit) (not done))
X          (setq entry (notes-title index))
X          (if (string-lessp title entry)
X              (setq done t)
X            (setq index (1+ index))
X            (forward-line 1))))
X      ;;
X      ;; INDEX at the stage is the position that the new note should be in.
X      ;; We now add the title to the title buffer.
X      ;;
X      (notes-excursion
X       "*notes-titles*"
X       (if (= index (1+ limit))
X           (progn
X             (goto-char (point-max))
X             (insert "\C-j?:      " title))
X         (goto-line index)
X         (insert "?:      " title "\C-j")))
X      ;;
X      ;; Add the empty text information.
X      ;;
X      (notes-excursion
X       "*notes-text*"
X       (widen)
X       (if (= index (1+ limit))
X           (progn
X             (goto-char (point-max))
X             (insert "\C-j0 0 500 300 " title "\C-j\C-j"))
X
X         (goto-char (point-min))
X         (search-forward "" (point-max) t index)
X         (beginning-of-line)
X         (insert "0 0 500 300 " title "\C-j\C-j")))
X      ;;
X      ;; Almost done.  Now fix the numbers, resixe the window, jump
X      ;; to the new notes, etc.
X      ;;
X      (notes-fix-line-numbers)
X      (notes-make-windows-fit)
X      (notes-jump-to-line index)
X      (notes-set index 'new t)
X      (notes-set index 'mod t)
X      (notes-select-current))))
X
X;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
X
X(defun notes-tag-delete ()
X  "Tags the note at on the current line for deletion."
X  (interactive)
X  (notes-set (count-lines (point-min) (point)) 'del t))
X
X(defun notes-tag ()
X  "Tags the note on the current line."
X  (interactive)
X  (notes-set (count-lines (point-min) (point)) 'tag t))
X
X(defun notes-untag ()
X  "Removes generic and delete tags from the note at the current line."
X  (interactive)
X  (notes-set (count-lines (point-min) (point)) 'tag nil))
X
X;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
X
X(defun notes-set (which att val)
X  "Sets the note at line WHICH, attribute ATT to VAL."
X  (notes-excursion 
X   "*notes-titles*"
X   (if (or (< (- (count-lines (point-min) (point-max)) 0) which)
X           (< which 1))
X       nil
X     (let ((tag (assoc att notes-flag-list)))
X       (if (not tag) ()
X         (goto-line which)
X         (beginning-of-line)
X         (forward-char (car (cdr tag)))
X         (delete-char 1)
X         (if val
X             (insert (car (cdr (cdr tag))))
X           (insert " ")))))))
X
X;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
X
X(defun notes-get (which att)
X  "Returns the value of the note at line WHICH, attribute ATT."
X  (notes-excursion
X   "*notes-titles*"
X   (if (or (> which (count-lines (point-min) (point-max)))
X           (< which 1))
X       nil
X     (let ((tag (assoc att notes-flag-list)))
X       (if (not tag) ()
X         (goto-line which)
X         (beginning-of-line)
X         (forward-char (car (cdr tag)))
X         (looking-at (car (cdr (cdr tag)))))))))
X
X;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
X
X;; Note to myself: this function needs to have the keymap stuff
X;; cleaned up.
X;;
X
X(defun notes-edit ()
X  "Jump into the current note, and allows you to edit it."
X  (interactive)
X  (notes-select-current)
X  (set-buffer "*notes-text*")
X  (setq buffer-read-only nil)
X  (set-buffer-modified-p nil)
X  (setq notes-edit-map nil)
X  (if notes-edit-map ()
X    (setq notes-edit-map (make-sparse-keymap))
X    (define-key notes-edit-map "\C-c\C-c" 'notes-edit-finish)
X    (use-local-map notes-edit-map))
X  (select-window (get-buffer-window "*notes-text*"))
X  (switch-to-buffer "*notes-text*")
X  (message "C-c C-c to finish."))
X
X;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
X
X;; Note to myself: this function needs to have the keymap stuff
X;; cleaned up.
X;;
X
X(defun notes-view ()
X  "Jump into the current note, and view it."
X  (interactive)
X  (notes-select-current)
X  (set-buffer "*notes-text*")
X  (setq notes-edit-map nil)
X  (if notes-edit-map ()
X    (setq notes-edit-map (make-sparse-keymap))
X    (define-key notes-edit-map "\C-c\C-c" 'notes-edit-finish)
X    (define-key notes-edit-map "<" 'beginning-of-buffer)
X    (define-key notes-edit-map ">" 'end-of-buffer)
X    (define-key notes-edit-map "\ev" 'scroll-down)
X    (define-key notes-edit-map "\C-v" 'scroll-up)
X    (define-key notes-edit-map " " 'scroll-up)
X    (define-key notes-edit-map "\177" 'scroll-down-one)
X    (define-key notes-edit-map "\n" 'scroll-up-one)
X    (define-key notes-edit-map "\r" 'scroll-up-one)
X    (define-key notes-edit-map "\C-l" 'recenter)
X    (define-key notes-edit-map "g" 'view-goto-line)
X    (define-key notes-edit-map "=" 'what-line)
X    (define-key notes-edit-map "." 'set-mark-command)
X    (define-key notes-edit-map "\C-@" 'set-mark-command)
X    (define-key notes-edit-map "x" 'exchange-point-and-mark)
X    (define-key notes-edit-map "h" 'Helper-describe-bindings)
X    (define-key notes-edit-map "?" 'Helper-describe-bindings)
X    (define-key notes-edit-map "\C-h" 'Helper-help)
X    (define-key notes-edit-map "\C-n" 'next-line)
X    (define-key notes-edit-map "\C-p" 'previous-line)
X    (define-key notes-edit-map "\C-s" 'isearch-forward)
X    (define-key notes-edit-map "\C-r" 'isearch-backward)
X    (define-key notes-edit-map "s" 'isearch-forward)
X    (define-key notes-edit-map "r" 'isearch-backward)
X    (define-key notes-edit-map "q" 'notes-edit-finish)
X    (use-local-map notes-edit-map))
X  (select-window (get-buffer-window "*notes-text*"))
X  (switch-to-buffer "*notes-text*")
X  (message "C-c C-c or q to finish."))
X
X;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
X
X(defun notes-edit-finish ()
X  "Jump back into the note title window, and set modification flags,
Xif needed."
X  (interactive)
X  (if (buffer-modified-p)
X      (notes-set notes-last-seen 'mod t))
X  (set-buffer "*notes-text*")
X  (set-buffer-modified-p nil)
X  (setq buffer-read-only t)
X  (notes-make-windows-fit)
X  (select-window (get-buffer-window "*notes-titles*"))
X  (use-local-map notes-mode-map))
X
X;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
X
X(defun notes-jump-to-line (&optional arg)
X  "Jump to a note.  If the optional argument is nil, the position is
Xbased on last-command-char.  This should nicely jump you to the note
Xwhich is indexed by the key you hit to activate this function. If you
Xcall this from a program, the argument must be the line number."
SHAR_EOF
  : || echo 'restore of notes.el failed'
fi
echo 'End of notes-1.0.6 part 2'
echo 'File notes.el is continued in part 3'
echo 3 > _sharseq.tmp
exit 0


