home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
OS/2 Professional
/
OS2PRO194.ISO
/
os2
/
editor
/
pmedit5
/
pmedit5.c
< prev
next >
Wrap
C/C++ Source or Header
|
1994-01-31
|
56KB
|
2,039 lines
#define INCL_GPI
#define INCL_WIN
#include <OS2.H>
#include <STDIO.H>
#include <PROCESS.H>
#include <IO.H>
#include <STRING.H>
#include <STDLIB.H>
#include "PMEDIT5.H"
MRESULT EXPENTRY WndProc (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
#define LINEBUFSIZ 255
#define ERROPEN 1
#define ERRTOOBIG 2
#define ERRMAXLINES 3
#define ERRALLOC 4
void BufInit (void);
int DeleteChar (SHORT Line, SHORT Column);
void DeleteLine (SHORT Line);
char *ErrorMessage (int ErrorNumber);
PCH GetLineAddr (int Line);
SHORT GetLineLength (int Line);
void GetTempBuf (int Line);
int InsertChar (SHORT Line, USHORT Character,SHORT Column, int Overwrite);
void InsertLine (SHORT Line, SHORT Column);
int JoinLine (SHORT Line);
void NewFile (void);
int ReadFile (char *FileName);
void ReleaseFile (void);
void ReleaseTempBuf (int Line);
int SaveFile (char *Filename);
int SearchBuf (char *Findstring, PSHORT Line, PSHORT Col);
int LastLine = -1;
HHEAP HHeap = NULL;
void ErrorQuit (char *Message);
char *Extension (char *FileName);
void GetPath (char *Path, unsigned PathLength);
void InitWindow (void);
void Qualify (char *Unqual, char *Qual);
void Quit (int ErrorCode);
void ShowFileName (void);
char *Unqualify (char *Qual);
#define PATHLENGTH 128
HWND HFrame;
HWND HMenu;
HAB HAncBlk;
HMQ HMesQue;
char Message [64];
char FileName [PATHLENGTH];
char Title [25] = "";
unsigned char Modified = 0;
HWND HClient;
void main (int argc, char *argv[])
{
int ReadError = 0;
QMSG QueMess;
ULONG CtlData =
FCF_HORZSCROLL |
FCF_MENU |
FCF_MINMAX |
FCF_SHELLPOSITION |
FCF_SIZEBORDER |
FCF_SYSMENU |
FCF_TASKLIST |
FCF_TITLEBAR |
FCF_VERTSCROLL;
BufInit ();
if (argc < 2)
{
FileName [0] = '\0';
NewFile ();
}
else
{
Qualify (argv [1],FileName);
ReadError = ReadFile (FileName);
}
HAncBlk = WinInitialize (0);
HMesQue = WinCreateMsgQueue (HAncBlk,0);
WinRegisterClass
(HAncBlk,
"MAIN",
WndProc,
0L,
0);
HFrame = WinCreateStdWindow
(HWND_DESKTOP,
FS_ACCELTABLE |
WS_VISIBLE,
&CtlData,
"MAIN",
Title,
0L,
0,
ID_FRAME_RESOURCE,
&HClient);
if (HFrame == NULL)
ErrorQuit ("WinCreateStdWindow");
ShowFileName ();
HMenu = WinWindowFromID
(HFrame,
FID_MENU);
if (ReadError)
ErrorQuit (ErrorMessage (ReadError));
WinSetFocus
(HWND_DESKTOP,
HClient);
while (WinGetMsg
(HAncBlk,
&QueMess,
0,
0,
0))
WinDispatchMsg (HAncBlk,&QueMess);
Quit (0);
}
MRESULT EXPENTRY Character (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY Command (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY Create (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY Help (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY HScroll (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY InitMenu (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY Paint (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY SetFocus (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY Size (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY VirtKey (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY VScroll (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY OpenProc (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY SaveasProc (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY AboutProc (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY FindProc (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
MRESULT EXPENTRY GotoProc (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2);
void NotYet (char *Message);
static SHORT xChar;
static SHORT yCharTot;
static SHORT yCharDesc;
static SHORT xWin;
static SHORT yWin;
static HWND HVScroll;
static HWND HHScroll;
static int FirstCol;
static int FirstColMax;
static SHORT TopLine = 0;
static SHORT TopLineMax;
static FATTRS FontAttributes;
static SHORT CursorLine = 0;
static SHORT CursorCol = 0;
static SHORT LastCursorLine = 0;
static int Insert = 1;
static BlockMarked = 0;
static ClipData = 0;
static FindString [33] = {'\0'};
#define ID_COURIER 99L
MRESULT EXPENTRY WndProc
(HWND hwnd,
USHORT msg,
MPARAM mp1,
MPARAM mp2)
{
switch (msg)
{
case WM_CHAR:
if (CHARMSG (&msg)->fs & KC_KEYUP)
return FALSE;
else if (CHARMSG (&msg)->fs & KC_CHAR)
return Character (hwnd, msg, mp1, mp2);
else if (CHARMSG (&msg)->fs & KC_VIRTUALKEY)
return VirtKey (hwnd, msg, mp1, mp2);
else
return FALSE;
case WM_COMMAND:
return Command (hwnd, msg, mp1, mp2);
case WM_CREATE:
return Create (hwnd, msg, mp1, mp2);
case WM_HELP:
return Help (hwnd, msg, mp1, mp2);
case WM_HSCROLL:
return HScroll (hwnd, msg, mp1, mp2);
case WM_INITMENU:
return InitMenu (hwnd, msg, mp1, mp2);
case WM_PAINT:
return Paint (hwnd, msg, mp1, mp2);
case WM_SETFOCUS:
return SetFocus (hwnd, msg, mp1, mp2);
case WM_SIZE:
return Size (hwnd, msg, mp1, mp2);
case WM_VSCROLL:
return VScroll (hwnd, msg, mp1, mp2);
default:
return WinDefWindowProc (hwnd, msg, mp1, mp2);
}
}
MRESULT EXPENTRY Character (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
register int Col;
RECTL Rect;
Modified = 1;
if (LastCursorLine != CursorLine)
{
ReleaseTempBuf (LastCursorLine);
GetTempBuf (CursorLine);
LastCursorLine = CursorLine;
}
if (CHARMSG(&msg)->chr == '\b')
{
if (CursorCol == 0)
{
if (CursorLine == 0)
return TRUE;
WinSendMsg
(hwnd,
WM_CHAR,
MPFROM2SHORT (KC_VIRTUALKEY, 1),
MPFROM2SHORT (0, VK_UP));
WinSendMsg
(hwnd,
WM_CHAR,
MPFROM2SHORT (KC_VIRTUALKEY, 1),
MPFROM2SHORT (0, VK_END));
if (!Insert)
return TRUE;
if (!JoinLine (CursorLine + 1))
{
WinAlarm (HWND_DESKTOP, WA_ERROR);
return TRUE;
}
LastCursorLine = CursorLine;
TopLineMax = max (0,LastLine - yWin / yCharTot + 1);
WinSendMsg
(HVScroll,
SBM_SETSCROLLBAR,
MPFROM2SHORT (TopLine, 0),
MPFROM2SHORT (0, TopLineMax));
WinEnableWindow
(HVScroll,
TopLineMax ? 1 : 0);
Rect.xLeft = 0;
Rect.xRight = xWin;
Rect.yTop = yWin - (CursorLine - TopLine) * yCharTot;
Rect.yBottom = 0;
WinInvalidateRect
(hwnd,
&Rect,
FALSE);
WinUpdateWindow (hwnd);
return TRUE;
}
WinSendMsg
(hwnd,
WM_CHAR,
MPFROM2SHORT (KC_VIRTUALKEY, 1),
MPFROM2SHORT (0, VK_LEFT));
if (Insert)
WinSendMsg
(hwnd,
WM_CHAR,
MPFROM2SHORT (KC_VIRTUALKEY, 1),
MPFROM2SHORT (0, VK_DELETE));
else
{
WinSendMsg
(hwnd,
WM_CHAR,
MPFROM2SHORT (KC_CHAR, 1),
MPFROM2SHORT (' ',0));
WinSendMsg
(hwnd,
WM_CHAR,
MPFROM2SHORT (KC_VIRTUALKEY, 1),
MPFROM2SHORT (0, VK_LEFT));
}
return TRUE;
}
if (CHARMSG(&msg)->chr == '\t')
{
Col = 5 - CursorCol % 5;
while (Col--)
WinSendMsg
(hwnd,
WM_CHAR,
MPFROM2SHORT (KC_CHAR, 1),
MPFROM2SHORT (' ',0));
return TRUE;
}
if (CHARMSG (&msg)->chr == '\r')
{
if (Insert)
{
InsertLine (CursorLine, CursorCol);
TopLineMax = max (0,LastLine - yWin / yCharTot + 1);
WinSendMsg
(HVScroll,
SBM_SETSCROLLBAR,
MPFROM2SHORT (TopLine, 0),
MPFROM2SHORT (0, TopLineMax));
WinEnableWindow
(HVScroll,
TopLineMax ? 1 : 0);
Rect.xLeft = 0;
Rect.xRight = xWin;
Rect.yTop = yWin - (CursorLine - TopLine) * yCharTot;
Rect.yBottom = 0;
WinInvalidateRect
(hwnd,
&Rect,
FALSE);
WinUpdateWindow (hwnd);
}
WinSendMsg
(hwnd,
WM_CHAR,
MPFROM2SHORT (KC_VIRTUALKEY, 1),
MPFROM2SHORT (0, VK_DOWN));
if (Insert)
LastCursorLine = CursorLine;
WinSendMsg
(hwnd,
WM_CHAR,
MPFROM2SHORT (KC_VIRTUALKEY, 1),
MPFROM2SHORT (0, VK_HOME));
return TRUE;
}
if (!InsertChar
(CursorLine,
CHARMSG(&msg) -> chr,
CursorCol,
Insert))
{
WinAlarm (HWND_DESKTOP, WA_ERROR);
return TRUE;
}
Rect.xLeft = (CursorCol - FirstCol) * xChar;
Rect.xRight = min ((GetLineLength (CursorLine) - FirstCol) * xChar, xWin);
Rect.yBottom = yWin - (CursorLine - TopLine + 1) * yCharTot;
Rect.yTop = Rect.yBottom + yCharTot;
WinInvalidateRect
(hwnd,
&Rect,
FALSE);
WinUpdateWindow (hwnd);
WinSendMsg
(hwnd,
WM_CHAR,
MPFROM2SHORT (KC_VIRTUALKEY, 1),
MPFROM2SHORT (0, VK_RIGHT));
return TRUE;
}
MRESULT EXPENTRY Command (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
USHORT Result;
USHORT Update = FALSE;
USHORT Reply;
switch (COMMANDMSG (&msg) -> cmd)
{
case ID_NEW:
if (Modified)
{
Reply = WinMessageBox
(HWND_DESKTOP,
hwnd,
"File Unsaved; Save?",
"PM Text Editor",
0,
MB_YESNO |
MB_ICONQUESTION);
if (Reply == MBID_YES)
while (Modified)
WinSendMsg
(hwnd,
WM_COMMAND,
MPFROM2SHORT (ID_SAVE, 0),
0L);
}
ReleaseFile ();
NewFile ();
FileName [0] = '\0';
ShowFileName ();
Modified = 0;
InitWindow ();
return FALSE;
case ID_OPEN:
WinDlgBox
(HWND_DESKTOP,
hwnd,
OpenProc,
NULL,
ID_OPENDLG,
NULL);
return FALSE;
case ID_SAVE:
if (FileName [0])
{
if (SaveFile (FileName) == FALSE)
WinMessageBox
(HWND_DESKTOP,
HFrame,
"Error -- Cannot Save File",
"PM Text Editor",
0,
MB_OK |
MB_ICONASTERISK);
else
Modified = 0;
return FALSE;
}
case ID_SAVEAS:
WinDlgBox
(HWND_DESKTOP,
hwnd,
SaveasProc,
NULL,
ID_SAVEASDLG,
NULL);
return FALSE;
case ID_PRINT:
NotYet ("Print File Command");
return FALSE;
case ID_EXIT:
Quit (0);
return FALSE;
case ID_ABOUT:
WinDlgBox
(HWND_DESKTOP,
hwnd,
AboutProc,
NULL,
ID_ABOUTDLG,
NULL);
return FALSE;
case ID_CUT:
case ID_COPY:
case ID_PASTE:
NotYet ("Clipboard Commands");
return FALSE;
case ID_FIND:
Result = WinDlgBox
(HWND_DESKTOP,
hwnd,
FindProc,
NULL,
ID_FINDDLG,
NULL);
if (Result)
{
WinInvalidateRect
(hwnd,
NULL,
FALSE);
WinUpdateWindow (hwnd);
WinSendMsg
(HHScroll,
SBM_SETPOS,
MPFROM2SHORT (FirstCol, 0),
0);
WinSendMsg
(HVScroll,
SBM_SETPOS,
MPFROM2SHORT (TopLine, 0),
0);
}
return FALSE;
case ID_FINDNEXT:
if (SearchBuf (FindString, &CursorLine, &CursorCol) == FALSE)
{
WinMessageBox
(HWND_DESKTOP,
HFrame,
"String not found",
"PM Test Editor",
0,
MB_OK |
MB_ICONASTERISK);
return FALSE;
}
if (CursorLine < TopLine || CursorLine >= TopLine + yWin/yCharTot)
{
TopLine = max (0,CursorLine - (yWin/yCharTot)/2);
TopLine = min (TopLine,TopLineMax);
Update = TRUE;
}
if (CursorCol < FirstCol || CursorCol >= FirstCol + xWin/xChar)
{
FirstCol = max (0,CursorCol - (xWin/xChar)/2);
FirstCol = min (FirstCol,FirstColMax);
Update = TRUE;
}
if (Update)
{
WinInvalidateRect
(hwnd,
NULL,
FALSE);
WinUpdateWindow (hwnd);
WinSendMsg
(HHScroll,
SBM_SETPOS,
MPFROM2SHORT (FirstCol, 0),
0);
WinSendMsg
(HVScroll,
SBM_SETPOS,
MPFROM2SHORT (TopLine, 0),
0);
}
WinCreateCursor
(hwnd,
(CursorCol - FirstCol) * xChar,
yWin - (CursorLine - TopLine + 1) * yCharTot,
0,
0,
CURSOR_SETPOS,
NULL);
return FALSE;
case ID_GOTOLINE:
Result = WinDlgBox
(HWND_DESKTOP,
hwnd,
GotoProc,
NULL,
ID_GOTODLG,
NULL);
if (Result)
{
WinInvalidateRect
(hwnd,
NULL,
FALSE);
WinUpdateWindow (hwnd);
WinSendMsg
(HHScroll,
SBM_SETPOS,
MPFROM2SHORT (FirstCol, 0),
0);
WinSendMsg (HVScroll, SBM_SETPOS, MPFROM2SHORT (TopLine, 0), 0);
}
return FALSE;
case ID_INSERT:
Insert ^= 1;
return FALSE;
default:
return FALSE;
}
}
MRESULT EXPENTRY Create (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
HPS HPresSpace;
FONTMETRICS Metrics;
LONG NumberStructs = 1;
GpiLoadFonts
(HAncBlk,
"\\OS2\\DLL\\COURIER.FON");
HPresSpace = WinGetPS (hwnd);
GpiQueryFonts
(HPresSpace,
QF_PRIVATE,
"Courier",
&NumberStructs,
(long)sizeof (FONTMETRICS),
&Metrics);
xChar = (SHORT)Metrics.lAveCharWidth;
yCharTot = (SHORT)Metrics.lMaxBaselineExt;
yCharDesc = (SHORT)Metrics.lMaxDescender;
FontAttributes.usRecordLength = sizeof (FontAttributes);
FontAttributes.fsSelection = Metrics.fsSelection;
FontAttributes.lMatch = Metrics.lMatch;
strcpy (FontAttributes.szFacename,Metrics.szFacename);
FontAttributes.idRegistry = Metrics.idRegistry;
FontAttributes.usCodePage = Metrics.usCodePage;
FontAttributes.lMaxBaselineExt = Metrics.lMaxBaselineExt;
FontAttributes.lAveCharWidth = Metrics.lAveCharWidth;
FontAttributes.fsType = FATTR_TYPE_FIXED;
FontAttributes.fsFontUse = 0;
WinReleasePS (HPresSpace);
HHScroll = WinWindowFromID
(WinQueryWindow (hwnd, QW_PARENT,FALSE), FID_HORZSCROLL);
HVScroll = WinWindowFromID
(WinQueryWindow (hwnd, QW_PARENT,FALSE),
FID_VERTSCROLL);
return FALSE;
}
MRESULT EXPENTRY Help (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
NotYet ("Help Window");
return FALSE;
}
MRESULT EXPENTRY HScroll (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
SHORT Delta;
switch (SHORT2FROMMP (mp2))
{
case SB_LINELEFT:
Delta = -1;
break;
case SB_LINERIGHT:
Delta = 1;
break;
case SB_PAGELEFT:
Delta = -6;
break;
case SB_PAGERIGHT:
Delta = 6;
break;
case SB_SLIDERPOSITION:
Delta = SHORT1FROMMP (mp2) - FirstCol;
break;
default:
Delta = 0;
break;
}
Delta = max (-FirstCol, min(Delta,FirstColMax - FirstCol));
if (Delta)
{
FirstCol += Delta;
CursorCol += Delta;
WinShowCursor
(hwnd,
FALSE);
WinScrollWindow
(hwnd,
-Delta * xChar,
0,
0,
0,
0,
0,
SW_INVALIDATERGN);
WinUpdateWindow
(hwnd);
WinSendMsg
(HHScroll,
SBM_SETPOS,
MPFROM2SHORT (FirstCol,0),
0);
WinCreateCursor
(hwnd,
(CursorCol - FirstCol) * xChar,
yWin - (CursorLine - TopLine + 1) * yCharTot,
0,
0,
CURSOR_SETPOS,
NULL);
WinShowCursor
(hwnd,
TRUE);
}
return FALSE;
}
MRESULT EXPENTRY InitMenu (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
switch (SHORT1FROMMP (mp1))
{
case ID_EDIT:
WinSendMsg (HMenu, MM_SETITEMATTR, MPFROM2SHORT (ID_CUT, TRUE),
MPFROM2SHORT (MIA_DISABLED, BlockMarked ? 0 : MIA_DISABLED));
WinSendMsg (HMenu, MM_SETITEMATTR, MPFROM2SHORT (ID_COPY,TRUE),
MPFROM2SHORT (MIA_DISABLED, BlockMarked ? 0 : MIA_DISABLED));
WinSendMsg (HMenu, MM_SETITEMATTR,MPFROM2SHORT (ID_PASTE, TRUE),
MPFROM2SHORT (MIA_DISABLED, ClipData ? 0 :MIA_DISABLED));
return FALSE;
case ID_SEARCH:
WinSendMsg (HMenu, MM_SETITEMATTR, MPFROM2SHORT (ID_FINDNEXT, TRUE),
MPFROM2SHORT (MIA_DISABLED, FindString [0] ? 0 : MIA_DISABLED));
return FALSE;
case ID_OPTIONS:
WinSendMsg (HMenu, MM_SETITEMTEXT, MPFROM2SHORT (ID_INSERT,0),
Insert ? (MPARAM)(PCH)"Overwrite Mode\tIns"
: (MPARAM)(PCH)"Insert Mode\tIns");
return FALSE;
default:
return FALSE;
}
}
MRESULT EXPENTRY Paint (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
register int Line;
HPS HPresSpace;
RECTL Rect;
SHORT StartLine;
SHORT StopLine;
POINTL Start;
SHORT LineLength;
HPresSpace = WinBeginPaint (hwnd, 0, &Rect);
GpiCreateLogFont (HPresSpace, (PSTR8)NULL, ID_COURIER, &FontAttributes);
GpiSetCharSet (HPresSpace, ID_COURIER);
WinFillRect (HPresSpace, &Rect, CLR_WHITE);
GpiSetColor (HPresSpace, CLR_BLACK);
StartLine = TopLine + (yWin - (SHORT)Rect.yTop) / yCharTot;
StopLine = min(LastLine, TopLine + (yWin - (SHORT)Rect.yBottom) / yCharTot);
Start.y = yWin - yCharTot * (StartLine - TopLine + 1) + yCharDesc;
Start.x = xChar * (-FirstCol);
for (Line = StartLine; Line <= StopLine; ++Line, Start.y -= yCharTot)
{
if ((LineLength = GetLineLength (Line)) == 0)
continue;
GpiCharStringAt (HPresSpace, &Start, (LONG)LineLength,
GetLineAddr (Line));
}
WinEndPaint (HPresSpace);
return FALSE;
}
MRESULT EXPENTRY SetFocus (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
if (LONGFROMMP (mp2))
{
WinCreateCursor
(hwnd,
(CursorCol - FirstCol) * xChar,
yWin - (CursorLine - TopLine + 1) * yCharTot,
0,
yCharTot,
CURSOR_SOLID |
CURSOR_FLASH,
NULL);
WinShowCursor (hwnd, TRUE);
}
else
WinDestroyCursor (hwnd);
return FALSE;
}
MRESULT EXPENTRY Size (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
int Update = 0;
yWin = SHORT2FROMMP (mp2);
xWin = SHORT1FROMMP (mp2);
if (CursorLine >= TopLine + yWin / yCharTot)
{
TopLine = CursorLine - yWin / yCharTot + 1;
Update = 1;
}
if (CursorCol >= FirstCol + xWin / xChar)
{
FirstCol = CursorCol - xWin / xChar + 1;
Update = 1;
}
if (Update)
WinInvalidateRect (hwnd,0,FALSE);
if (hwnd == WinQueryFocus (HWND_DESKTOP,FALSE))
{
WinDestroyCursor (hwnd);
WinCreateCursor (hwnd,
(CursorCol - FirstCol) * xChar,
yWin - (CursorLine - TopLine + 1) * yCharTot,
0,
yCharTot,
CURSOR_SOLID |
CURSOR_FLASH,
NULL);
WinShowCursor
(hwnd, TRUE);
}
TopLineMax = max (0,LastLine - yWin / yCharTot + 1);
TopLine = min (TopLine, TopLineMax);
WinSendMsg
(HVScroll,
SBM_SETSCROLLBAR,
MPFROM2SHORT (TopLine, 0),
MPFROM2SHORT (0, TopLineMax));
WinEnableWindow
(HVScroll, TopLineMax ? TRUE : FALSE);
FirstColMax = LINEBUFSIZ - 2 - xWin / xChar;
FirstCol = min (FirstCol, FirstColMax);
WinSendMsg
(HHScroll,
SBM_SETSCROLLBAR,
MPFROM2SHORT (FirstCol, 0),
MPFROM2SHORT (0, FirstColMax));
return FALSE;
}
MRESULT EXPENTRY VirtKey (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
RECTL Rect;
SHORT NewFirstCol;
SHORT NewCursorCol;
int Update;
switch (CHARMSG (&msg) -> vkey)
{
case VK_UP:
if (CursorLine == TopLine)
{
WinSendMsg (hwnd, WM_VSCROLL, 0L, MPFROM2SHORT (0,SB_LINEUP));
return TRUE;
}
else
--CursorLine;
break;
case VK_DOWN:
if (CursorLine == LastLine)
return TRUE;
else if (CursorLine == TopLine + yWin / yCharTot - 1)
{
WinSendMsg (hwnd, WM_VSCROLL,0L,MPFROM2SHORT (0, SB_LINEDOWN));
return TRUE;
}
else
++CursorLine;
break;
case VK_LEFT:
if (CursorCol == FirstCol)
{
WinSendMsg (hwnd, WM_HSCROLL,0L,MPFROM2SHORT (0,SB_LINELEFT));
return TRUE;
}
else
--CursorCol;
break;
case VK_RIGHT:
if (CursorCol == FirstCol + xWin / xChar - 1)
{
WinSendMsg (hwnd, WM_HSCROLL, 0L, MPFROM2SHORT (0,SB_LINERIGHT));
return TRUE;
}
else
++CursorCol;
break;
case VK_PAGEUP:
WinSendMsg (hwnd, WM_VSCROLL,0L,MPFROM2SHORT (0,SB_PAGEUP));
return TRUE;
case VK_PAGEDOWN:
WinSendMsg (hwnd, WM_VSCROLL,0L,MPFROM2SHORT (0,SB_PAGEDOWN));
return TRUE;
case VK_HOME:
if (FirstCol != 0)
{
WinSendMsg (hwnd, WM_HSCROLL,0L,MPFROM2SHORT (0,SB_SLIDERPOSITION));
}
CursorCol = 0;
break;
case VK_END:
NewCursorCol = (int)GetLineLength (CursorLine);
Update = 0;
if (NewCursorCol > FirstCol + xWin / xChar - 1)
{
NewFirstCol = NewCursorCol - xWin / xChar + 1;
Update = 1;
}
else if (NewCursorCol < FirstCol)
{
NewFirstCol = NewCursorCol;
Update = 1;
}
if (Update)
WinSendMsg (hwnd, WM_HSCROLL,0L,MPFROM2SHORT
(NewFirstCol,SB_SLIDERPOSITION));
CursorCol = NewCursorCol;
break;
case VK_DELETE:
Modified = 1;
if (LastCursorLine != CursorLine)
{
ReleaseTempBuf (LastCursorLine);
GetTempBuf (CursorLine);
LastCursorLine = CursorLine;
}
if (DeleteChar (CursorLine, CursorCol))
{
Rect.xLeft = (CursorCol - FirstCol) * xChar;
Rect.xRight = min ((GetLineLength(CursorLine) + 1 -
FirstCol) * xChar,xWin);
Rect.yBottom = yWin - (CursorLine - TopLine + 1) * yCharTot;
Rect.yTop = Rect.yBottom + yCharTot;
WinInvalidateRect (hwnd, &Rect, FALSE);
WinUpdateWindow (hwnd);
}
return TRUE;
case VK_F9:
Modified = 1;
if (LastCursorLine != CursorLine)
{
ReleaseTempBuf (LastCursorLine);
GetTempBuf (CursorLine);
LastCursorLine = CursorLine;
}
DeleteLine (CursorLine);
TopLineMax = max (0, LastLine - yWin / yCharTot + 1);
WinSendMsg (HVScroll, SBM_SETSCROLLBAR,MPFROM2SHORT (TopLine, 0),
MPFROM2SHORT (0, TopLineMax));
WinEnableWindow (HVScroll, TopLineMax ? 1 : 0);
Rect.xLeft = 0;
Rect.xRight = xWin;
Rect.yTop = yWin - (CursorLine - TopLine) * yCharTot;
Rect.yBottom = 0;
WinInvalidateRect (hwnd, &Rect, FALSE);
WinUpdateWindow (hwnd);
return TRUE;
default:
return FALSE;
}
WinCreateCursor
(hwnd,
(CursorCol - FirstCol) * xChar,
yWin - (CursorLine - TopLine + 1) * yCharTot,
0,
0,
CURSOR_SETPOS,
NULL);
return TRUE;
}
MRESULT EXPENTRY VScroll (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
SHORT Delta;
switch (SHORT2FROMMP (mp2))
{
case SB_LINEUP:
Delta = -1;
break;
case SB_LINEDOWN:
Delta = 1;
break;
case SB_PAGEUP:
Delta = -yWin / yCharTot;
break;
case SB_PAGEDOWN:
Delta = yWin / yCharTot;
break;
case SB_SLIDERPOSITION:
Delta = SHORT1FROMMP (mp2) - TopLine;
break;
default:
Delta = 0;
break;
}
Delta = max (-TopLine, min(Delta,TopLineMax - TopLine));
if (Delta)
{
TopLine += Delta;
CursorLine += Delta;
WinShowCursor (hwnd, FALSE);
WinScrollWindow
(hwnd,
0,
yCharTot * Delta,
0,
0,
0,
0,
SW_INVALIDATERGN);
WinUpdateWindow (hwnd);
WinSendMsg (HVScroll, SBM_SETPOS,MPFROM2SHORT (TopLine,0), 0);
WinCreateCursor
(hwnd,
(CursorCol - FirstCol) * xChar,
yWin - (CursorLine - TopLine + 1) * yCharTot,
0,
0,
CURSOR_SETPOS,
NULL);
WinShowCursor (hwnd, TRUE);
}
return FALSE;
}
MRESULT EXPENTRY AboutProc (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
switch (msg)
{
case WM_COMMAND:
switch (COMMANDMSG(&msg)->cmd)
{
case DID_OK:
case DID_CANCEL:
WinDismissDlg(hwnd,TRUE);
return FALSE;
default:
return FALSE;
}
default:
return WinDefDlgProc (hwnd, msg, mp1, mp2);
}
}
MRESULT EXPENTRY FindProc (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
char Buffer [2];
USHORT Update = FALSE;
switch (msg)
{
case WM_COMMAND:
switch (COMMANDMSG(&msg)->cmd)
{
case DID_OK:
WinQueryWindowText (WinWindowFromID (hwnd, ID_FINDEDIT),
sizeof (FindString),
FindString);
if (FindString [0] == '\0')
return FALSE;
if (SearchBuf (FindString, &CursorLine, &CursorCol) == FALSE)
{
WinMessageBox
(HWND_DESKTOP,
hwnd,
"String not found",
"PM Text Editor",
0,
MB_OK |
MB_ICONASTERISK);
WinDismissDlg (hwnd, FALSE);
return FALSE;
}
if (CursorLine < TopLine || CursorLine >= TopLine +
yWin/yCharTot)
{
TopLine = max (0,CursorLine - (yWin/yCharTot)/2);
TopLine = min (TopLine, TopLineMax);
Update = TRUE;
}
if (CursorCol < FirstCol || CursorCol >= FirstCol + xWin / xChar)
{
FirstCol = max (0, CursorCol - (xWin/xChar)/2);
FirstCol = min (FirstCol,FirstColMax);
Update = TRUE;
}
WinDismissDlg (hwnd,FALSE);
return FALSE;
case DID_CANCEL:
WinDismissDlg (hwnd,FALSE);
return FALSE;
default:
return FALSE;
}
case WM_CONTROL:
switch (SHORT1FROMMP (mp1))
{
case ID_FINDEDIT:
switch (SHORT2FROMMP (mp1))
{
case EN_CHANGE:
WinQueryWindowText ((HWND) mp2, 2, Buffer);
WinEnableWindow (WinWindowFromID (hwnd, DID_OK),
Buffer [0]);
return FALSE;
default:
return FALSE;
}
default:
return FALSE;
}
case WM_INITDLG:
WinSetWindowText (WinWindowFromID (hwnd,ID_FINDEDIT), FindString);
default:
return WinDefDlgProc (hwnd, msg, mp1, mp2);
}
}
MRESULT EXPENTRY GotoProc (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
char NumberBuf [33];
char Buffer [2];
SHORT LineNumber;
switch (msg)
{
case WM_COMMAND:
switch (COMMANDMSG (&msg)->cmd)
{
case DID_OK:
WinQueryWindowText (WinWindowFromID(hwnd, ID_GOTOEDIT),
sizeof (NumberBuf),
NumberBuf);
LineNumber = atoi (NumberBuf);
if (LineNumber <= 0)
return FALSE;
--LineNumber;
CursorLine = min(LastLine,LineNumber);
TopLine = max (0,CursorLine - (yWin/yCharTot)/2);
TopLine = min(TopLine,TopLineMax);
CursorCol = FirstCol = 0;
WinDismissDlg (hwnd, TRUE);
return FALSE;
case DID_CANCEL:
WinDismissDlg (hwnd,FALSE);
return FALSE;
default:
return FALSE;
}
case WM_CONTROL:
switch (SHORT1FROMMP (mp1))
{
case ID_GOTOEDIT:
switch (SHORT2FROMMP (mp1))
{
case EN_CHANGE:
WinQueryWindowText ((HWND) mp2, 2, Buffer);
WinEnableWindow (WinWindowFromID (hwnd, DID_OK),
Buffer [0]);
return FALSE;
default:
return FALSE;
}
default:
return FALSE;
}
case WM_INITDLG:
WinEnableWindow (WinWindowFromID (hwnd, DID_OK), FALSE);
return FALSE;
default:
return WinDefDlgProc (hwnd, msg, mp1, mp2);
}
}
VOID InitDlg (HWND hwnd);
MRESULT EXPENTRY OpenProc (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
SHORT SelectIndex;
char Buffer [16];
static char FilePath [PATHLENGTH];
USHORT Reply;
switch (msg)
{
case WM_COMMAND:
switch (COMMANDMSG(&msg)->cmd)
{
case DID_OK:
WinQueryWindowText (WinWindowFromID (hwnd, ID_OPENEDIT),
sizeof (FilePath),
FilePath);
if (FilePath [0])
{
if (Modified)
{
Reply = WinMessageBox (HWND_DESKTOP,
hwnd,
"File Unsaved; Save?",
"PM Text Editor",
0,
MB_YESNO |
MB_ICONQUESTION);
if (Reply == MBID_YES)
while (Modified)
WinSendMsg (HClient, WM_COMMAND,
MPFROM2SHORT (ID_SAVE, 0),
0L);
}
ReleaseFile ();
if (ReadFile (FilePath))
{
WinMessageBox (HWND_DESKTOP, hwnd,
"Error -- Cannot Read File",
"PM Text Editor",
0,
MB_OK |
MB_ICONASTERISK);
FileName [0] = '\0';
NewFile ();
}
else
Qualify (FilePath, FileName);
ShowFileName ();
Modified = 0;
InitWindow ();
WinDismissDlg (hwnd, TRUE);
return FALSE;
}
return FALSE;
case DID_CANCEL:
WinDismissDlg (hwnd, TRUE);
return FALSE;
default:
return FALSE;
}
case WM_CONTROL:
switch (SHORT1FROMMP (mp1))
{
case ID_OPENEDIT:
switch (SHORT2FROMMP (mp1))
{
case EN_CHANGE:
WinQueryWindowText ((HWND) mp2, 2, Buffer);
WinEnableWindow (WinWindowFromID(hwnd, DID_OK),
Buffer [0]);
return FALSE;
default:
return FALSE;
}
case ID_OPENLIST:
SelectIndex = (SHORT) WinSendDlgItemMsg
(hwnd,ID_OPENLIST,
LM_QUERYSELECTION,
0L,
0L);
WinSendDlgItemMsg (hwnd,ID_OPENLIST,LM_QUERYITEMTEXT,
MPFROM2SHORT (SelectIndex, sizeof (Buffer)),
MPFROMP (Buffer));
switch (SHORT2FROMMP (mp1))
{
case LN_ENTER:
if (Buffer [0] == '[' && Buffer [1] == '-')
{
DosSelectDisk (Buffer [2] - 64);
InitDlg (hwnd);
}
else if (Buffer [0] == '[')
{
Buffer [strlen (Buffer) - 1] = '\0';
DosChDir (Buffer + 1, 0L);
InitDlg (hwnd);
}
else if (Buffer [0])
{
WinSendMsg (hwnd, WM_COMMAND,
MPFROM2SHORT (DID_OK,0),
0L);
WinDismissDlg (hwnd, TRUE);
return FALSE;
}
return FALSE;
case LN_SELECT:
if (Buffer [0] == '[')
Buffer [0] = '\0';
WinSetWindowText (WinWindowFromID (hwnd,ID_OPENEDIT),
Buffer);
return FALSE;
default:
return FALSE;
}
default:
return FALSE;
}
case WM_INITDLG:
WinSendDlgItemMsg (hwnd,ID_OPENEDIT,EM_SETTEXTLIMIT,
MPFROM2SHORT (PATHLENGTH, 0),
0);
WinEnableWindow (WinWindowFromID (hwnd, DID_OK),
FALSE);
InitDlg (hwnd);
return FALSE;
default:
return WinDefDlgProc (hwnd, msg, mp1, mp2);
}
}
VOID InitDlg (HWND hwnd)
{
register int Drive;
USHORT DriveNumber;
ULONG LogicalDrives;
char Buffer [PATHLENGTH];
HDIR HSearch = 1;
FILEFINDBUF FindBuf;
USHORT FileCount = 1;
char *PtrCh;
GetPath (Buffer, sizeof (Buffer));
WinSetWindowText (WinWindowFromID (hwnd, ID_OPENCD), Buffer);
DosQCurDisk (&DriveNumber,&LogicalDrives);
WinSendDlgItemMsg (hwnd, ID_OPENLIST,LM_DELETEALL, 0, 0);
for (Drive = 'A'; Drive <= 'Z';++Drive)
{
if (LogicalDrives & 1)
{
sprintf (Buffer,"[-%c-]",Drive);
WinSendDlgItemMsg (hwnd, ID_OPENLIST,
LM_INSERTITEM,MPFROM2SHORT (LIT_SORTASCENDING, 0),
MPFROMP (Buffer));
}
LogicalDrives >>= 1;
}
DosFindFirst ("*.*", &HSearch, 0x0010, &FindBuf, sizeof (FindBuf),
&FileCount, 0L);
while (FileCount)
{
if (FindBuf.attrFile & 0x0010 && !(FindBuf.achName [0] == '.' &&
FindBuf.achName [1] == '\0'))
{
sprintf (Buffer,"[%s]",FindBuf.achName);
WinSendDlgItemMsg (hwnd, ID_OPENLIST, LM_INSERTITEM,
MPFROM2SHORT (LIT_SORTASCENDING, 0), MPFROMP (Buffer));
}
else if (strcmp ((PtrCh = Extension (FindBuf.achName)),"TXT") == 0
|| strcmp (PtrCh,"C") == 0)
WinSendDlgItemMsg (hwnd, ID_OPENLIST, LM_INSERTITEM,
MPFROM2SHORT (LIT_SORTASCENDING, 0),
MPFROMP (FindBuf.achName));
DosFindNext (HSearch, &FindBuf,sizeof (FindBuf),&FileCount);
}
}
MRESULT EXPENTRY SaveasProc (HWND hwnd, USHORT msg, MPARAM mp1, MPARAM mp2)
{
char FilePath [PATHLENGTH];
char CurDir [PATHLENGTH + 22];
char Buffer [2];
switch (msg)
{
case WM_COMMAND:
switch (COMMANDMSG(&msg)->cmd)
{
case DID_OK:
WinQueryWindowText (WinWindowFromID (hwnd, ID_SAVEASEDIT),
sizeof (FilePath), FilePath);
if (FilePath [0])
{
if (SaveFile (FilePath) == FALSE)
WinMessageBox
(HWND_DESKTOP, hwnd,
"Error -- Cannot Save File",
"PM Text Editor",
0,
MB_OK |
MB_ICONASTERISK);
else
{
Qualify (FilePath, FileName);
ShowFileName ();
Modified = 0;
}
WinDismissDlg (hwnd, TRUE);
return FALSE;
}
return FALSE;
case DID_CANCEL:
WinDismissDlg (hwnd, TRUE);
return FALSE;
default:
return FALSE;
}
case WM_CONTROL:
switch (SHORT1FROMMP (mp1))
{
case ID_SAVEASEDIT:
switch (SHORT2FROMMP (mp1))
{
case EN_CHANGE:
WinQueryWindowText ((HWND) mp2, 2, Buffer);
WinEnableWindow (WinWindowFromID (hwnd, DID_OK),
Buffer [0]);
return FALSE;
default:
return FALSE;
}
default:
return FALSE;
}
case WM_INITDLG:
WinSendDlgItemMsg( hwnd,ID_SAVEASEDIT,EM_SETTEXTLIMIT,
MPFROM2SHORT (PATHLENGTH,0),
0);
WinEnableWindow (WinWindowFromID (hwnd, DID_OK), FALSE);
GetPath (FilePath, sizeof (FilePath));
sprintf (CurDir,"Current Directory: %s",FilePath);
WinSetWindowText (WinWindowFromID (hwnd, ID_SAVEASCD), CurDir);
return FALSE;
default:
return WinDefDlgProc (hwnd, msg, mp1, mp2);
}
}
void NotYet (char *Message)
{
char Buffer [60];
sprintf (Buffer,"Not yet Implemented: %s",Message);
WinMessageBox (HWND_DESKTOP, HFrame, Buffer,
"PM Text Editor",
0,
MB_OK |
MB_ICONASTERISK);
}
#define MAXLINES 4096
static struct
{
PCH LineAddress;
unsigned char LineLength;
}
LineTable [MAXLINES];
static char LineBuffer [LINEBUFSIZ];
static unsigned LineSelector;
static unsigned LineOffset;
static SEL HeapSelector;
void BufInit (void)
{
PCH FarPtr;
FarPtr = (char far *)LineBuffer;
LineSelector = SELECTOROF (FarPtr);
LineOffset = OFFSETOF (FarPtr);
}
int DeleteChar (SHORT Line, SHORT Column)
{
if (LineTable [Line].LineLength < 3 ||Column >
LineTable [Line].LineLength - 3)
return FALSE;
memmove (LineBuffer + Column, LineBuffer + Column + 1,
LineTable [Line].LineLength - Column - 1);
--LineTable [Line].LineLength;
return TRUE;
}
void DeleteLine (SHORT Line)
{
if (Line == LastLine)
{
LineBuffer [0] = '\n';
LineBuffer [1] = '\0';
LineTable [Line].LineLength = 2;
}
else
{
GetTempBuf (Line + 1);
memmove (&LineTable [Line], &LineTable [Line + 1], (LastLine - Line)
* sizeof (LineTable [0]));
--LastLine;
}
}
char *ErrorMessage (int ErrorNumber)
{
static char *MessageTable [] = {
"no error",
"file open failure",
"file too large",
"maximum lines exceeded",
"heap memory allocation failed",
"unidentified error"
};
if (ErrorNumber >= sizeof (MessageTable) / sizeof (char *))
ErrorNumber = sizeof (MessageTable) / sizeof (char *) - 1;
return MessageTable [ErrorNumber];
}
PCH GetLineAddr (int Line)
{
if (Line < 0 || Line > LastLine)
return NULL;
else
return LineTable [Line].LineAddress;
}
SHORT GetLineLength (int Line)
{
if (Line < 0 || Line > LastLine)
return 0;
else
return LineTable [Line].LineLength - 2;
}
void GetTempBuf (int Line)
{
movedata (SELECTOROF (LineTable[Line].LineAddress),
OFFSETOF (LineTable[Line].LineAddress),
LineSelector, LineOffset,
LineTable [Line].LineLength);
if (WinFreeMem (HHeap,
(BYTE NEAR *)OFFSETOF (LineTable [Line].LineAddress),
LineTable [Line].LineLength)
!= NULL)
{
sprintf (Message,"managing heap; line %d",__LINE__);
ErrorQuit(Message);
}
LineTable [Line].LineAddress = MAKEP (LineSelector,LineOffset);
}
int InsertChar (SHORT Line, USHORT Character, SHORT Column, int Insert)
{
unsigned char LineLength;
LineLength = LineTable [Line].LineLength;
if (Column > LINEBUFSIZ - 3 || LineLength >= LINEBUFSIZ && Insert)
return FALSE;
else if (Column == LineLength - 2)
{
LineBuffer [Column + 2] = LineBuffer [Column + 1];
LineBuffer [Column + 1] = LineBuffer [Column];
LineBuffer [Column] = (char)Character;
++LineTable [Line].LineLength;
return TRUE;
}
else if (Column > LineLength - 2)
{
LineBuffer [Column + 2] = LineBuffer [LineLength - 1];
LineBuffer [Column + 1] = LineBuffer [LineLength - 2];
memset (LineBuffer + LineLength - 2,' ', Column - LineLength + 2);
LineBuffer [Column] = (char)Character;
LineTable [Line].LineLength = (unsigned char)Column + 3;
return TRUE;
}
else
{
if (Insert)
{
memmove (LineBuffer + Column + 1,
LineBuffer + Column, LineLength - Column);
++LineTable [Line].LineLength;
}
LineBuffer [Column] = (char)Character;
return TRUE;
}
}
void InsertLine (SHORT Line, SHORT Column)
{
NPCH HeapOffset;
PCH HeapPointer;
if (++LastLine >= MAXLINES)
{
sprintf (Message,"maximum lines reached; line %d",__LINE__);
ErrorQuit (Message);
}
if (Column > LineTable [Line].LineLength - 2)
Column = LineTable [Line].LineLength - 2;
HeapOffset = WinAllocMem (HHeap, Column + 2);
if (HeapOffset == NULL)
{
sprintf (Message,"out of heap memory; line %d",__LINE__);
ErrorQuit (Message);
}
movedata (LineSelector, LineOffset, HeapSelector, (unsigned)HeapOffset,
Column);
HeapPointer = MAKEP (HeapSelector, HeapOffset);
*(HeapPointer + Column) = '\n';
*(HeapPointer + Column + 1) = '\0';
memmove (LineBuffer, LineBuffer + Column, LineTable [Line].LineLength
- Column);
LineTable [Line].LineLength -= (unsigned char)Column;
memmove (&LineTable [Line + 1], &LineTable [Line],
(LastLine - Line) * sizeof (LineTable [0]));
LineTable [Line].LineAddress = HeapPointer;
LineTable [Line].LineLength = (unsigned char)(Column + 2);
}
int JoinLine (SHORT Line)
{
if (Line == 0)
return FALSE;
if (LineTable [Line].LineLength + LineTable [Line - 1].LineLength - 2 >
LINEBUFSIZ)
return FALSE;
memmove (LineBuffer + LineTable [Line - 1].LineLength - 2, LineBuffer,
LineTable [Line].LineLength);
movedata (SELECTOROF (LineTable [Line - 1].LineAddress),
OFFSETOF (LineTable [Line - 1].LineAddress),
LineSelector, LineOffset, LineTable [Line - 1].LineLength - 2);
LineTable [Line].LineLength += LineTable [Line - 1].LineLength - 2;
if (WinFreeMem(HHeap, (BYTE NEAR *) OFFSETOF (LineTable [Line - 1].LineAddress),
LineTable [Line - 1].LineLength) != NULL)
{
sprintf (Message,"managing heap; line %d",__LINE__);
ErrorQuit (Message);
}
memmove (&LineTable [Line - 1], &LineTable [Line], (LastLine - Line + 1) *
sizeof (LineTable [0]));
--LastLine;
return TRUE;
}
void NewFile (void)
{
PCH FarPtr;
LineBuffer [0] = '\n';
LineBuffer [1] = '\0';
LineTable [0].LineAddress = MAKEP (LineSelector, LineOffset);
LineTable [0].LineLength = 2;
LastLine = 0;
HHeap = WinCreateHeap (0, 4096, 0, 0, 0, HM_MOVEABLE);
FarPtr = WinLockHeap (HHeap);
HeapSelector = SELECTOROF (FarPtr);
}
int ReadFile (char *FileName)
{
FILE *PtrFile;
long FileLength;
USHORT HeapSize;
NPCH HeapOffset;
unsigned char LineLength;
PCH FarPtr;
if ((PtrFile = fopen (FileName,"r")) == NULL)
return (ERROPEN);
if ((FileLength = filelength (fileno (PtrFile))) == -1)
return (ERROPEN);
if (FileLength > 50000)
return (ERRTOOBIG);
HeapSize = (USHORT)(FileLength + FileLength / 5);
HHeap = WinCreateHeap (0, HeapSize, 0, 0, 0, 0);
FarPtr = WinLockHeap (HHeap);
HeapSelector = SELECTOROF (FarPtr);
LastLine = -1;
while (fgets(LineBuffer,LINEBUFSIZ-1,PtrFile) != NULL)
{
if (++LastLine >= MAXLINES)
return (ERRMAXLINES);
LineLength = (unsigned char)strlen (LineBuffer) + 1;
if (LineLength == LINEBUFSIZ - 1 && LineBuffer [LINEBUFSIZ - 3]
!= '\n')
{
LineBuffer [LINEBUFSIZ - 2] = '\n';
LineBuffer [LINEBUFSIZ - 1] = '\0';
++LineLength;
}
HeapOffset = WinAllocMem (HHeap, LineLength);
if (HeapOffset == NULL)
return (ERRALLOC);
movedata (LineSelector,LineOffset,HeapSelector,(unsigned)HeapOffset,
LineLength);
LineTable [LastLine].LineAddress = MAKEP (HeapSelector,HeapOffset);
LineTable [LastLine].LineLength = LineLength;
}
GetTempBuf (0);
fclose (PtrFile);
return (0);
}
void ReleaseFile (void)
{
if (HHeap != NULL)
WinDestroyHeap (HHeap);
return;
}
void ReleaseTempBuf (int Line)
{
NPCH HeapOffset;
HeapOffset = WinAllocMem (HHeap, LineTable [Line].LineLength);
if (HeapOffset == NULL)
{
sprintf (Message,"Out of heap memory; line %d",__LINE__);
ErrorQuit (Message);
}
movedata (LineSelector, LineOffset,HeapSelector,(unsigned)HeapOffset,
LineTable [Line].LineLength);
LineTable [Line].LineAddress = MAKEP (HeapSelector, HeapOffset);
}
int SaveFile (char *FileName)
{
register int i;
FILE *PtrFile;
char TempBuffer [LINEBUFSIZ];
PCH FarPtr;
unsigned BufSel;
if ((PtrFile = fopen (FileName,"w")) == NULL)
return FALSE;
FarPtr = (char far *)TempBuffer;
BufSel = SELECTOROF (FarPtr);
for (i = 0; i <= LastLine; ++i)
{
movedata (SELECTOROF (LineTable [i].LineAddress),
OFFSETOF (LineTable [i].LineAddress), BufSel,
(unsigned int) TempBuffer, LineTable [i].LineLength);
fputs (TempBuffer, PtrFile);
}
fclose (PtrFile);
return TRUE;
}
int SearchBuf (char *FindString, PSHORT Line, PSHORT Col)
{
register int i, j;
char far *FPtrCh;
FPtrCh = LineTable [*Line].LineAddress + *Col;
i = *Line;
for (;;)
{
while (*FPtrCh)
{
for (j = 0; FindString [j] == FPtrCh [j] && FindString [j]; ++j)
;
if (FindString [j] == '\0')
{
*Line = i;
*Col = FPtrCh + j - LineTable [i].LineAddress;
return TRUE;
}
++FPtrCh;
}
if (++i > LastLine)
return FALSE;
FPtrCh = LineTable [i].LineAddress;
}
}
void ErrorQuit (char *Message)
{
char Buffer [60];
sprintf (Buffer,"Program Error: %s",Message);
WinMessageBox (HWND_DESKTOP,HFrame, Buffer, "PM Text Editor",
0, MB_OK |
MB_ICONHAND);
Quit (1);
}
char *Extension (char *FileName)
{
while (*FileName)
if (*FileName++ == '.')
return (FileName);
return (FileName);
}
void GetPath (char *Path, unsigned PathSize)
{
USHORT DriveNumber;
ULONG LogicalDrives;
if (PathSize < 3)
return;
DosQCurDisk (&DriveNumber, &LogicalDrives);
sprintf (Path,"%c:\\",DriveNumber + 64);
PathSize -= 3;
DosQCurDir (DriveNumber, Path + 3, &(USHORT)PathSize);
return;
}
void InitWindow (void)
{
CursorCol = CursorLine = 0;
TopLine = FirstCol = 0;
TopLineMax = max (0,LastLine - yWin / yCharTot + 1);
FirstColMax = LINEBUFSIZ - 2 - xWin / xChar;
WinSendMsg (HVScroll, SBM_SETSCROLLBAR,
MPFROM2SHORT (TopLine, 0),
MPFROM2SHORT (0, TopLineMax));
WinEnableWindow (HVScroll, TopLineMax ? TRUE : FALSE);
WinSendMsg (HHScroll, SBM_SETSCROLLBAR,
MPFROM2SHORT (FirstCol, 0),
MPFROM2SHORT (0, FirstColMax));
if (HClient == WinQueryFocus (HWND_DESKTOP,FALSE))
WinCreateCursor (HClient, (CursorCol - FirstCol) * xChar,
yWin - (CursorLine - TopLine + 1) * yCharTot, 0, 0,
CURSOR_SETPOS,
NULL);
WinInvalidateRect (HClient, 0, FALSE);
}
void Qualify (char *Unqual, char *Qual)
{
char PathBuffer [PATHLENGTH];
char *PtrPath = PathBuffer;
GetPath (PathBuffer, sizeof (PathBuffer));
if (*(Unqual + 1) == ':')
{
*Qual++ = *Unqual++;
*Qual++ = *Unqual++;
PtrPath += 2;
}
else
{
*Qual++ = *PtrPath++;
*Qual++ = *PtrPath++;
}
if (*Unqual != '\\')
{
while (*Qual++ = *PtrPath++)
;
if (*(Qual - 2) == '\\')
--Qual;
else
*(Qual - 1) = '\\';
}
while (*Qual++ = *Unqual++)
;
}
void Quit (int ErrorCode)
{
USHORT Reply;
if (Modified)
{
Reply = WinMessageBox (HWND_DESKTOP, HClient,
"File Unsaved; Save?",
"PM Text Editor",
0,
MB_YESNO |
MB_ICONQUESTION);
if (Reply == MBID_YES)
while (Modified)
WinSendMsg (HClient, WM_COMMAND, MPFROM2SHORT (ID_SAVE, 0), 0L);
}
if (HHeap != NULL)
WinDestroyHeap (HHeap);
WinDestroyWindow (HFrame);
WinDestroyMsgQueue (HMesQue);
WinTerminate (HAncBlk);
exit (ErrorCode);
}
void ShowFileName (void)
{
sprintf (Title,"PM Editor - %s", FileName [0] ? Unqualify (FileName)
: "(Untitled)");
WinSetWindowText (HFrame, Title);
}
char *Unqualify (char *Qual)
{
char *PtrCh;
PtrCh = Qual + strlen (Qual);
while (PtrCh != Qual && *(PtrCh-1) != '\\' && *(PtrCh-1) != ':')
--PtrCh;
WinUpper (HAncBlk, NULL, NULL, PtrCh);
return (PtrCh);
}