// --------------------------------------------------------------------------
// Citadel: CSysUser.CPP
//
// Console Sysop User

#ifndef WINCIT
#include "ctdl.h"
#pragma hdrstop

#include "log.h"

#include "cwindows.h"
#include "consysop.h"

Bool listHandler(EVENT evt, long param, int more, CITWINDOW *wnd);

typedef enum
	{
	LST_DRAW,	LST_UP, 	LST_DOWN,	LST_GET,	LST_PGUP,	LST_PGDN,
	LST_HOME,	LST_END,	LST_NEW,	LST_DESTROY,LST_REFRESH,
	} LISTCMDS;

typedef struct
	{
	const char *(*lister)(CITWINDOW *, LISTCMDS);	// the lister to use
	int on; 								// which entry is on
	int top;								// which entry is at top
	int bottom; 							// which entry is at bottom
	void *ptr;								// in case you need more data
	} listerData;

// all of the control IDs used in this module
typedef enum
	{
	CTRL_USERKILLSTR,	CTRL_USERKILLYN,
	};

const char *userLister(CITWINDOW *wnd, LISTCMDS cmd)
	{
	listerData *ld = (listerData *) wnd->LocalData;

	switch (cmd)
		{
		case LST_DRAW:
			{
			int i, j;

			if (!LogTab->GetEntry(ld->on)->IsInuse())
				{
				ld->on = 0; 	// root
				}

			if (ld->on < ld->top)
				{
				ld->top = ld->on;
				}

			if (buildClipArray(wnd))
				{
				for (j = 1, i = ld->top; i < cfg.MAXLOGTAB; i++)
					{
					if (j >= wnd->extents.bottom - wnd->extents.top)
						{
						break;
						}

					if (LogTab->GetEntry(i)->IsInuse())
						{
						int x;

						ld->bottom = i;

						CitWindowOutChr(wnd, 1, j, ' ',
								i == ld->on ? cfg.cattr : cfg.attr);

						CitWindowOutStr(wnd, 2, j, LogTab->GetEntry(i)->GetName(),
								i == ld->on ? cfg.cattr : cfg.attr);

						for (x = strlen(LogTab->GetEntry(i)->GetName()) + 2;
								x < wnd->extents.right - wnd->extents.left;
								x++)
							{
							CitWindowOutChr(wnd, x, j, ' ',
									i == ld->on ? cfg.cattr : cfg.attr);
							}

						j++;
						}
					}

				for (; j < wnd->extents.bottom - wnd->extents.top; j++)
					{
					CitWindowClearLine(wnd, j, cfg.attr);
					}

				freeClipArray();
				}

			break;
			}

		case LST_DOWN:
			{
			int tmp = ld->on;

			while (++ld->on < cfg.MAXLOGTAB && !LogTab->GetEntry(ld->on)->IsInuse());
			if (ld->on >= cfg.MAXLOGTAB)
				{
				ld->on = tmp;
				}

			if (ld->on > ld->bottom)
				{
				while (!LogTab->GetEntry(++ld->top)->IsInuse());
				}

			userLister(wnd, LST_DRAW);
			break;
			}

		case LST_UP:
			{
			while (ld->on && !LogTab->GetEntry(--ld->on)->IsInuse());
			userLister(wnd, LST_DRAW);
			break;
			}

		case LST_PGDN:
			{
			int i, j = wnd->extents.bottom - wnd->extents.top - 2;

			for (i = 0; i < j; i++)
				{
				int tmp = ld->on;

				while (++ld->on < cfg.MAXLOGTAB && !LogTab->GetEntry(ld->on)->IsInuse());
				if (ld->on >= cfg.MAXLOGTAB)
					{
					ld->on = tmp;
					}

				if (ld->on > ld->bottom)
					{
					while (!LogTab->GetEntry(++ld->top)->IsInuse());
					}
				}

			userLister(wnd, LST_DRAW);
			break;
			}

		case LST_PGUP:
			{
			int i, j = wnd->extents.bottom - wnd->extents.top - 2;

			for (i = 0; i < j; i++)
				{
				while (ld->on && !LogTab->GetEntry(--ld->on)->IsInuse());
				}

			userLister(wnd, LST_DRAW);
			break;
			}

		case LST_GET:
			{
			return (LogTab->GetEntry(ld->on)->GetName());
			}

		case LST_HOME:
			{
			ld->on = 0;
			ld->top = 0;
			userLister(wnd, LST_DRAW);
			break;
			}

		case LST_END:
			{
			int i, j = wnd->extents.bottom - wnd->extents.top - 2;
			int tmp;

			for (tmp = ld->on; ; tmp = ld->on)
				{
				while (++ld->on < cfg.MAXLOGTAB && !LogTab->GetEntry(ld->on)->IsInuse());

				if (ld->on >= cfg.MAXLOGTAB)
					{
					ld->on = tmp;
					break;
					}
				}

			ld->top = ld->on;
			for (i = 0; i < j; i++)
				{
				while (ld->top && !LogTab->GetEntry(--ld->top)->IsInuse());
				}

			userLister(wnd, LST_DRAW);
			break;
			}
		}

	return (NULL);
	}

void UserControlHandler(CITWINDOW *wnd, long param)
	{
	CONTROLINFO *ci = (CONTROLINFO *) param;

	switch (ci->id)
		{
		case CTRL_USERKILLSTR:
			{
			if (*((char *)(ci->ptr)))
				{
				int ls;

				ls = FindPersonByPartialName((char *) (ci->ptr));

				if (ls != CERROR)
					{
					l_slot *lsp;

					if (TI()loggedIn && TI()ThisSlot == ls)
						{
						CitWindowsError(wnd, getsysmsg(345),
								TI()CurrentUser->GetName());
						}
					else
						{
						if ((lsp = new l_slot) != NULL)
							{
							char pmt[80];
							label ln;

							CopyStringToBuffer(ln,
									LogTab->GetEntry(ls)->GetName(),
									LABELSIZE);

							sprintf(pmt, getsysmsg(346), ln);

							*lsp = ls;

							CitWindowsGetYN(pmt, 0, wnd, CTRL_USERKILLYN,
									lsp);
							}
						}
					}
				else
					{
					CitWindowsError(wnd, getsysmsg(347), ci->ptr);
					}
				}

			break;
			}

		case CTRL_USERKILLYN:
			{
			if (*((int *)(ci->ptr)))
				{
				label ln;

				CopyStringToBuffer(ln,
						LogTab->GetEntry(*((int *)(ci->more)))->GetName(),
						LABELSIZE);

				if (!killuser(ln))
					{
					CitWindowsError(wnd, getsysmsg(348), ln);
					}
				else
					{
					if (wnd->children)
						{
						if (wnd->children->wnd->func == listHandler)
							{
							(wnd->children->wnd->func)(EVT_DRAWINT, 0, 0,
									wnd->children->wnd);
							}
						}
					}
				}

			break;
			}
		}
	}

Bool UserKeyHandler(CITWINDOW *wnd, int key)
	{
	switch (key)
		{
		case CSUM_EXIT:
		case MK_ESC:
			{
			// exit user menu stuff
			return (FALSE);
			}

		case CSUM_NEW:
			{
			break;
			}

		case CSUM_EDIT:
			{
			break;
			}

		case CSUM_KILL:
			{
			label df;

			if (wnd->children && wnd->children->wnd->func == listHandler)
				{
				CopyStringToBuffer(df, (((listerData *)
						(wnd->children->wnd->LocalData))->lister)
						(wnd->children->wnd, LST_GET), LABELSIZE);
				}
			else
				{
				df[0] = 0;
				}

			CitWindowsGetString(getsysmsg(349), LABELSIZE, df, wnd,
					CTRL_USERKILLSTR, NULL, FALSE);

			break;
			}
		}

	return (TRUE);
	}

#endif
