home *** CD-ROM | disk | FTP | other *** search
- #include "SpellHandler.h"
- #include "SpellWright.h"
- #include "ctype.h"
- #include "string.h"
- #include "WindowHandler.h"
- #include "Globals.h"
- #include "Strings.h"
- #include "TEHandler.h"
-
- char *GetNextWord(TEHandle theTE);
- void SpellIgnore(char *word, TEHandle theTE, DialogPtr SpellDialog);
- void SpellIgnoreAll(char *word, TEHandle theTE, DialogPtr SpellDialog);
- void SpellReplace(char *word, TEHandle theTE, DialogPtr SpellDialog);
- void SpellReplaceAll(char *word, TEHandle theTE, DialogPtr SpellDialog);
- void SpellSuggest(char *word, TEHandle theTE, DialogPtr SpellDialog);
- void SpellAdd(char *word, TEHandle theTE, DialogPtr SpellDialog);
- void DialogSuggestion(DialogPtr SpellDialog);
- void SpellOptions(void );
- void InitializeList(ListHandle theList);
- void DoSuggest(DialogPtr SpellDialog);
- pascal Boolean ListHandler( DialogPtr theDialog, EventRecord *theEvent, short *itemHit);
- Boolean GetNextMisspell(TEHandle theTE, DialogPtr theDialog);
- void MakeSpellWindow(void);
-
- // ----------------------------------------------------------------------------------
- // Moveable Dialog Stuff
- // Copywrite 1994 Jim Stout
- // ----------------------------------------------------------------------------------
-
-
-
- typedef pascal char (*filterProc)(DialogPtr, EventRecord *, short *);
-
- pascal void movableModalDialog (filterProc filter, short *theItem);
- static short preFilterEvent (DialogPtr d, EventRecord *theEvent);
- static short doMouseDialog (DialogPtr d, EventRecord * theEvent);
- extern void diskEvent (EventRecord *theEvent);
-
-
- extern Boolean TrapAvailable ( short tNum, short tType);
- extern void DrawClippedGrowIcon(WindowPtr theWindow);
-
- // ----------------------------------------------------------------------------------
-
- ListHandle theList;
- short listCount = 0;
- static short where;
- static short oldwhere;
- static short whereEnd;
- char *currentWord;
- Boolean newCheck;
- SWChecker gtheSpeller;
- short theCase;
- short Duplicate;
- short toReplace;
- WordInfo theInfo;
-
- static unsigned long theDocDict = 0;
- static unsigned long theMainDict = 0;
- static unsigned long theUserDict = 0;
- static unsigned long theSkipDict = 0;
- static unsigned long theAutoDict = 0;
- static unsigned long theSuggestDict = 0;
- static unsigned long gMain = 0;
-
- // ----------------------------------------------------------------------------------
- // Moveable Modal Windows
- // Copywrite Jim Stout 1994
- //
- // These enable the modal dialog to be moved around
- // ----------------------------------------------------------------------------------
-
- // ----------------------------------------------------------------------------------
- // UpdateWindow
- // ----------------------------------------------------------------------------------
- // Handles updating the window. Nothing done here
-
- void updateWindow(WindowPtr theWindow)
- {
- GrafPtr savePort;
- TEHandle theTE;
-
- theTE = GetTE(theWindow);
- BeginUpdate(theWindow);
-
- GetPort(&savePort); // Save the port
- SetPort(theWindow);
- EraseRect(&theWindow->portRect); // Erase the window
- TEUpdate( &(theWindow->portRect), theTE );
- DrawClippedGrowIcon(theWindow); // Draw the grow icon
- DrawControls(theWindow); // Draw the window's controls
- UpdateDocWindow(theWindow);
- SetPort(savePort); // Restore the port
-
- EndUpdate(theWindow);
-
- }
-
- // ----------------------------------------------------------------------------------
- // moveableModalDialog
- // ----------------------------------------------------------------------------------
- // Replaces the ModalDialog toolbox call and lets you move your window around.
-
- pascal void movableModalDialog(filterProc filter, short *theItem)
- {
- EventRecord theEvent;
- DialogPtr d,thisDialog;
-
- thisDialog = FrontWindow();
-
- for(;;) {
- WaitNextEvent(everyEvent, &theEvent, 20, 0L);
- if(*theItem = preFilterEvent(thisDialog, &theEvent))
- break;
-
- if (filter != nil)
- if (filter(thisDialog, &theEvent, theItem))
- break;
-
- if (IsDialogEvent(&theEvent))
- if (DialogSelect(&theEvent, &d, theItem))
- break;
- }
- }
-
- // ----------------------------------------------------------------------------------
- // preFilterEvent
- // ----------------------------------------------------------------------------------
- // Handles events before the filter routine of the dialog manager
-
- static short preFilterEvent(DialogPtr d, EventRecord *theEvent)
- {
- short ret=0;
-
- switch (theEvent->what) {
- case mouseDown:
- ret = doMouseDialog(d,theEvent); /* handle drag etc. of dialog */
- break;
- case diskEvt:
- diskEvent(theEvent);
- break;
- case updateEvt:
- if(d != (DialogPtr)theEvent->message)
- /* pass update evt back to mainline */
- updateWindow((WindowPtr)theEvent->message);
- break;
- }
- return (ret);
- }
-
- // ----------------------------------------------------------------------------------
- // doMouseDialog
- // ----------------------------------------------------------------------------------
- // handle mouse events in the dialog box
-
- static short doMouseDialog(DialogPtr d, EventRecord *theEvent)
- {
- WindowPtr theWindow;
- short partCode, ret=0;
-
- switch (partCode = FindWindow(theEvent->where,&theWindow)) {
- case inDrag:
- if(theWindow == d) {
- DragWindow(d, theEvent->where, &qd.screenBits.bounds);
- theEvent->what = nullEvent;
- }
- break;
-
- case inMenuBar:
- MenuSelect(theEvent->where);
- HiliteMenu(0);
- break;
-
- case inGoAway:
- if (TrackBox (theWindow, theEvent->where, partCode)) {
- ret = cancel;
- theEvent->what = nullEvent;
- }
- break;
- case inGrow:
- break;
- case inZoomIn:
- case inZoomOut:
- break;
- case inContent:
- break;
- default:
- break;
- }
- return(ret);
- }
-
- // ----------------------------------------------------------------------------------
- // Handle disk events
- // ----------------------------------------------------------------------------------
- // Handles disk insertion events
-
- void diskEvent(EventRecord *theEvent)
- {
- Point diskInitPt;
-
- if (HiWord (theEvent->message) != noErr) {
- diskInitPt.v = 120;
- diskInitPt.h = 100;
- DILoad ();
- (void) DIBadMount (diskInitPt, theEvent->message);
- DIUnload ();
- theEvent->what = nullEvent;
- }
- }
-
-
- // ----------------------------------------------------------------------------------
- // Initialize Main Dictionary
- // ----------------------------------------------------------------------------------
- // By popular demand this is an automatically opened main dictionary. This function
- // looks for a dictionary named "Main Dictionary" and if it exists automatically
- // opens it, storing it's number in gMain.
-
- void InitMainDict(void)
- {
- short vRefNum;
- FSSpec theFile;
- StandardFileReply reply;
-
- SFTypeList types = {'Dict'};
-
- if ( GetVol(0, &vRefNum) )
- return;
-
- if ( FSMakeFSSpec( vRefNum, 0, "\p:Main Dictionary", &theFile) )
- { // file doesn't exist
- // prompt for a dictionary
- StandardGetFile(nil, 1, types, &reply);
- if (reply.sfGood)
- DictOpen(gtheSpeller, &gMain, MAIN_DICT, 15, &reply.sfFile);
-
- if (GetSpellError())
- DictClose(gtheSpeller, gMain);
-
- return;
- }
-
- DictOpen(gtheSpeller, &gMain, MAIN_DICT, 15, &theFile);
-
- }
-
-
- // ----------------------------------------------------------------------------------
- // GetNextWord
- // ----------------------------------------------------------------------------------
- // This gets the next word in the TE text. A globals keep track of where we are
- // in the text. Right now the word delineator is merely any non-alphanum char.
- // The string returned by this function is stored internally as a static variable,
- // so don't mangle the pointer by trying to free it or something.
-
- char *GetNextWord(TEHandle theTE)
- {
- CharsHandle theText;
- short counter = 0;
- static char word[60];
- short finish;
-
- theText = TEGetText(theTE);
-
- finish = whereEnd - 1;
-
- // skip white space & punctuation
- while (( !isalnum(*(*theText + where)) ) && (where <= finish))
- { where++;
- }
-
- if (where >= whereEnd)
- return nil;
-
- oldwhere = where;
- while (( isalnum(*(*theText + where + counter)) ) && (counter<59) && (where + counter <= finish))
- { word[counter] = *(*theText + where + counter);
- counter++;
- } // while
-
- where += counter;
- word[counter] = '\0';
- TESetSelect(oldwhere, where, theTE);
- return (word);
-
- } // GetNextWord
-
- // ----------------------------------------------------------------------------------
- // SpellIgnore
- // ----------------------------------------------------------------------------------
- // Does nothing, as the word is being ignored. I could add something here in the
- // future if I wanted.
-
- void SpellIgnore(char *word, TEHandle theTE, DialogPtr SpellDialog)
- {
- return; // gets next word
- } // SpellIgnore
-
- // ----------------------------------------------------------------------------------
- // SpellIgnoreAll
- // ----------------------------------------------------------------------------------
- // Ignores the word and also adds it to the Skip Dictionary. If a skip dictionary
- // hasn't been opened then this doesn't work too well. I'll probably create a
- // specific skip dictionary for this soon.
- //
-
- void SpellIgnoreAll(char *word, TEHandle theTE, DialogPtr SpellDialog)
- {
- if (theSkipDict)
- AddToDictionary(gtheSpeller, theSkipDict, word, nil, nil);
- return;
- }
-
- // ----------------------------------------------------------------------------------
- // SpellReplace
- // ----------------------------------------------------------------------------------
- // This gets the text of the replacement field and replaces the current word with
- // it, updating the selection and our location counters. Basically it selects
- // the current word, deletes it, and inserts some more text. Other than the
- // Dialog munging there are only really three commands.
-
- void SpellReplace(char *word, TEHandle theTE, DialogPtr SpellDialog)
- {
- short tempItem;
- Handle tempHandle;
- Rect tempRect;
- Str255 theWord;
- GrafPtr oldport;
-
- TESetSelect(oldwhere, where, theTE);
-
- GetDItem(SpellDialog, edReplace, &tempItem, &tempHandle, &tempRect);
- GetIText(tempHandle, theWord);
-
-
- TEDelete(theTE); // delete the old word
- TEInsert(theWord +1 , theWord[0], theTE); // insert the replacement word
-
- TESetSelect(oldwhere, oldwhere + theWord[0] + 1, theTE);
- whereEnd = whereEnd - (where - oldwhere) + theWord[0]; // adjust end for new word
-
-
- where = oldwhere; // check this word
-
- // Clean up windowing artifacts
- GetPort(&oldport);
- SetPort(gDocWindow);
-
- SetPort(oldport);
-
- } // SpellReplace
-
- // ----------------------------------------------------------------------------------
- // SpellReplaceAll
- // ----------------------------------------------------------------------------------
- // This replaces the word and then adds it to the Auto Dictionary. It will then
- // be automatically replaced. Right now you have to open the dictionary yourself
- // in the options menu. The next version will do this automatically, or more likely
- // have a second dictionary.
-
- void SpellReplaceAll(char *word, TEHandle theTE, DialogPtr SpellDialog)
- {
-
- SpellReplace(word, theTE, SpellDialog);
- if (theAutoDict)
- AddToDictionary(gtheSpeller, theAutoDict, word, nil, nil);
-
- } // SpellReplaceAll
-
- // ----------------------------------------------------------------------------------
- // SpellSuggest
- // ----------------------------------------------------------------------------------
- // This replaces the misspelled word with the replacement word. At the moment
- // that is about all it does, other than changing the current word as well.
-
- void SpellSuggest(char *word, TEHandle theTE, DialogPtr SpellDialog)
- {
- short tempItem;
- Handle tempHandle;
- Rect tempRect;
- Str255 theWord;
-
- GetDItem(SpellDialog, edReplace, &tempItem, &tempHandle, &tempRect);
- GetIText(tempHandle, theWord);
-
- GetDItem(SpellDialog, edUnknown, &tempItem, &tempHandle, &tempRect);
- SetIText(tempHandle, theWord);
-
- currentWord = P2CStr(theWord);
-
-
- }
-
- // ----------------------------------------------------------------------------------
- // SpellAdd
- // ----------------------------------------------------------------------------------
- // Not currently used.
-
- void SpellAdd(char *word, TEHandle theTE, DialogPtr SpellDialog)
- {
-
- }
-
-
- // ----------------------------------------------------------------------------------
- // DialogSuggestion
- // ----------------------------------------------------------------------------------
- // This brings up a dialog box to add words to a dictionary.
-
- void DialogSuggestion(DialogPtr SpellDialog)
- {
- DialogPtr SuggestDialog = nil;
- short theHit = 0;
- Boolean dDone = 0;
- short tempItem;
- Handle tempHandle;
- Rect tempRect;
- Str255 addWord;
- Str255 addSuggest;
- Str255 addComment;
-
-
- InitCursor();
-
- SuggestDialog = GetNewDialog(rSuggestion, nil, (WindowPtr) -1);
- ShowWindow((WindowPtr) SuggestDialog);
-
-
- if (SpellDialog)
- {
- GetDItem(SpellDialog, edUnknown, &tempItem, &tempHandle, &tempRect);
- GetIText(tempHandle, addWord);
- GetDItem(SuggestDialog, eAddWord, &tempItem, &tempHandle, &tempRect);
- SetIText(tempHandle, addWord);
-
- GetDItem(SpellDialog, edReplace, &tempItem, &tempHandle, &tempRect);
- GetIText(tempHandle, addSuggest);
- GetDItem(SuggestDialog, eAddSuggest, &tempItem, &tempHandle, &tempRect);
- SetIText(tempHandle, addSuggest);
-
- GetDItem(SuggestDialog, eAddWord, &tempItem, &tempHandle, &tempRect);
- GetIText(tempHandle, C2PStr(currentWord));
- currentWord = P2CStr((StringPtr) currentWord);
-
-
- } // if
-
- DrawDialog(SuggestDialog);
-
- do
- { movableModalDialog( nil, &theHit);
- switch (theHit)
- { case iUserAdd:
- case iAutoAdd:
- case iSuggestAdd:
- GetDItem(SuggestDialog, eAddWord, &tempItem, &tempHandle, &tempRect);
- GetIText(tempHandle, addWord);
-
- GetDItem(SuggestDialog, eAddSuggest, &tempItem, &tempHandle, &tempRect);
- GetIText(tempHandle, addSuggest);
-
- GetDItem(SuggestDialog, eAddComment, &tempItem, &tempHandle, &tempRect);
- GetIText(tempHandle, addComment);
-
-
- if ( (theHit == iUserAdd) && theUserDict)
- { AddToDictionary(gtheSpeller, theUserDict, P2CStr(addWord),
- P2CStr(addSuggest), P2CStr(addComment));
-
- } else if ( (theHit == iAutoAdd) && theAutoDict)
- { AddToDictionary(gtheSpeller, theAutoDict, P2CStr(addWord),
- P2CStr(addSuggest), P2CStr(addComment));
-
- } else if ( (theHit == iSuggestAdd) && theSuggestDict)
- { AddToDictionary(gtheSpeller, theSuggestDict, P2CStr(addWord),
- P2CStr(addSuggest), P2CStr(addComment));
-
- }
- dDone = true;
- break;
- case iCancelAdd:
- dDone = true;
- break;
-
- } // switch
-
-
- } while (!dDone);
-
- DisposeDialog( SuggestDialog );
-
- } // DialogSuggestion
-
-
- // ----------------------------------------------------------------------------------
- // SpellOptions
- // ----------------------------------------------------------------------------------
- // This brings up a dialog box to open or create dictionaries. Note that I can
- // get my own icon in the dictionary by creating it myself and then passing it
- // to the library. (Those creator and type values ought to be #defined)
-
- void SpellOptions(void )
- {
- DialogPtr OptionDialog = nil;
- short theHit = 0;
- Boolean dDone = 0;
- Boolean error;
- OSErr err;
-
- StandardFileReply reply;
- SFTypeList types = {'Dict'};
-
- OptionDialog = GetNewDialog(rDictionary, nil, (WindowPtr) -1);
- ShowWindow((WindowPtr) OptionDialog);
- DrawDialog(OptionDialog);
-
- do
- { ModalDialog( nil, &theHit);
- switch (theHit)
- { case iMain: StandardGetFile(nil, 1, types, &reply);
- if (reply.sfGood)
- DictOpen(gtheSpeller, &theMainDict, MAIN_DICT, 15, &reply.sfFile);
- error = GetSpellError();
- break;
- case iUser: StandardGetFile(nil, 1, types, &reply);
- if (reply.sfGood)
- DictOpen(gtheSpeller, &theUserDict, USER_DICT, 200, &reply.sfFile);
- error = GetSpellError();
- break;
-
- case iSuggest: StandardGetFile(nil, 1, types, &reply);
- if (reply.sfGood)
- DictOpen(gtheSpeller, &theAutoDict, SUGGEST_DICT, 200, &reply.sfFile);
- break;
-
- case iAuto: StandardGetFile(nil, 1, types, &reply);
- if (reply.sfGood)
- DictOpen(gtheSpeller, &theSuggestDict, AUTO_DICT, 200, &reply.sfFile);
- break;
-
- case iNSuggest: StandardPutFile("\pSuggest Dictionary to Create", "\pSuggest", &reply);
- if (reply.sfGood)
- { err = FSpCreate(&reply.sfFile, 'DLLL', 'Dict', reply.sfScript);
- DictOpen(gtheSpeller, &theSuggestDict, SUGGEST_DICT, 200, &reply.sfFile);
- }
- break;
-
- case iNAuto: StandardPutFile("\pSuggest Dictionary to Create", "\pSuggest", &reply);
- if (reply.sfGood)
- { err = FSpCreate(&reply.sfFile, 'DLLL', 'Dict', reply.sfScript);
- DictOpen(gtheSpeller, &theAutoDict, AUTO_DICT, 200, &reply.sfFile);
- }
- break;
-
- case iNUser: StandardPutFile("\pSuggest Dictionary to Create", "\pSuggest", &reply);
- if (reply.sfGood)
- { err = FSpCreate(&reply.sfFile, 'DLLL', 'Dict', reply.sfScript);
- DictOpen(gtheSpeller, &theUserDict, USER_DICT, 200, &reply.sfFile);
- }
- break;
-
- case iNAdd: { DialogSuggestion(nil);
- break;
- }
-
- case iCancel: dDone = true;
- break;
-
-
- } // switch
-
-
- } while (!dDone);
-
- DisposeDialog( OptionDialog );
-
- } // SpellOptions
-
- // ----------------------------------------------------------------------------------
- // InitializeList
- // ----------------------------------------------------------------------------------
- // Not currently utilized. If I do something odd to the list before using it
- // I can do it here. I'll probably remove this code.
-
- void InitializeList(ListHandle theList)
- {
-
- }
-
- // ----------------------------------------------------------------------------------
- // DoSuggest
- // ----------------------------------------------------------------------------------
- // This is the main routine. It finds a misspelled word, enters suggestions in
- // a dialog's list, and then lets the user select a suggestion and replace the
- // misspelling with it. More functionality is needed here. In practice you
- // would probably just use our interface which is much nicer than these
- // modal dialog boxes. Ideally we'd allow selection and replacement while
- // we were still getting suggestions. It would be fairly easy to do, but I've
- // opted for simplicity and clarity rather than functionality in the demo. If
- // you don't want to code that yourself, use our interface that does it all for
- // you (and will hopefully support threads under Sys7.5).
- //
- // Note: the handling of the dialog's clicks isn't done here. This only adds
- // the suggestions, comments, and errors to the dialog. The main dialog
- // routines are in MakeSpellWindow.
-
- void DoSuggest(DialogPtr SpellDialog)
- {
- Cell cp;
- Str255 theString;
- Rect tempRect;
- short tempItem;
- Handle tempHandle;
- char replace[60];
- char comment[255];
-
- // clear current list
- LDelRow(0, 0, theList);
- // Update the list
- LDraw(cp, theList);
-
- listCount = 0;
-
- if (Duplicate)
- { GetDItem(SpellDialog, edSuggest, &tempItem, &tempHandle, &tempRect);
- SetIText(tempHandle, "\pDuplicate Word");
- return;
- } // if
-
- // Add the first suggestion. (This resets the suggestion indicator)
- if (FindFirstSuggestion(gtheSpeller, gMain + theDocDict + theMainDict + theUserDict + theSkipDict +
- theAutoDict + theSuggestDict, 0, currentWord, replace, comment, &toReplace))
- {
- // check to see if there was an error (due to a number)
- if (GetSpellError())
- return;
-
- // make sure the case matches
- FixCase(gtheSpeller, replace, theInfo.Case);
-
- listCount = LAddRow(1, listCount + 1, theList);
-
- cp.h = 0;
- cp.v = listCount;
-
- LAddToCell(replace, strlen(replace), cp, theList);
-
- // Update the list
- LDraw(cp, theList);
-
- // put in replace
- GetDItem(SpellDialog, edReplace, &tempItem, &tempHandle, &tempRect);
- SetIText(tempHandle, C2PStr(replace) );
-
-
- if (comment[0] != '\0')
- { GetDItem(SpellDialog, edSuggest, &tempItem, &tempHandle, &tempRect);
- SetIText(tempHandle, C2PStr(comment));
- } // if
-
-
-
- } // if
-
- // Add all the suggestions. NOT_FOUND = 0, so we can use FindNextSuggestion like
- // this. Here we merely add the suggestions to the list.
-
- while (FindNextSuggestion(gtheSpeller, gMain + theDocDict + theMainDict + theUserDict + theSkipDict +
- theAutoDict + theSuggestDict, 0, currentWord, replace, comment, &toReplace))
- {
- // make sure the case is correct
- FixCase(gtheSpeller, replace, theInfo.Case);
-
- // clear current list
-
- listCount = LAddRow(1, listCount + 1, theList);
-
- cp.h = 0;
- cp.v = listCount;
-
- LAddToCell(replace, strlen(replace), cp, theList);
- // Update the list
- LDraw(cp, theList);
- } // while
-
- } // DoSuggest
-
-
-
- // ----------------------------------------------------------------------------------
- // ListHandler
- // ----------------------------------------------------------------------------------
- // This handles clicks in the list. It is passed to the Dialog manager as a callback
- // routine. This way we can update the list and dialog box. Here we merely check
- // for a click and update the replacement word with the clicked cell. A double
- // click replaces the misspelled word with the suggestion double clicked on.
-
- pascal Boolean ListHandler( DialogPtr theDialog, EventRecord *theEvent, short *itemHit)
- {
-
- Rect tempR;
- Boolean returnValue = false;
- Boolean theBoolean;
- WindowPtr oldP;
- char theWord[60];
- Rect tempRect;
- short tempItem;
- Handle tempHandle;
- Cell theCell;
- short size;
-
-
- // get the current port, set the port to this dialog
- GetPort(&oldP);
- SetPort(theDialog);
-
- // was this an update event for this dialog?
- if ( (theEvent->what == updateEvt) && ( theEvent->message == (long) theDialog))
- {
-
- // Update the list.
- LUpdate(theDialog->visRgn, theList);
-
- // get the list rectangle
- tempR = (*theList)->rView;
-
- // push it outwards one pixel and frame the list
- InsetRect(&tempR, -1, -1);
- FrameRect(&tempR);
-
- } else {
- // see if this was a mouseDown event
- if (theEvent->what == mouseDown) {
- Point theP;
-
- // we set the port to the dialog on entry to the filter, so a GetMouse will work
- GetMouse(&theP);
-
- // get the list rectangle
- tempR = (*theList)->rView;
-
- // add the scroll bar back in for hit testing (remember we took it out earlier)
- tempR.right += 16;
-
- // See if they clicked in our list!
- if (PtInRect(theP, &tempR)) {
- theBoolean = LClick(theP, nil, theList);
- // if they double-clicked the list, replace the suggestion
- size = 60;
- tempR.right -= 15; // take the scroll bar out.
- if (theBoolean)
- { if (PtInRect(theP, &tempR))
- {
- *itemHit = bReplace; // double click does a replace
-
- theCell = LLastClick(theList); // get the cell clicked in
- LGetCell((Ptr) theWord, &size, theCell, theList); // get the word of that cell
- theWord[size] = '\0'; // make it a c string
-
- if (*theWord != '\0')
- { GetDItem(theDialog, edReplace, &tempItem, &tempHandle, &tempRect);
- C2PStr(theWord);
- SetIText(tempHandle, (StringPtr) theWord);
- } // if
- } else
- *itemHit = uList;
- } // if
- else
- { *itemHit = uList;
- if (PtInRect(theP, &tempR))
- {
-
- theCell = LLastClick(theList); // get the cell clicked in
- LGetCell((Ptr) theWord, &size, theCell, theList); // get the word of that cell
- theWord[size] = '\0'; // make it a c string
-
- if (*theWord != '\0')
- { GetDItem(theDialog, edReplace, &tempItem, &tempHandle, &tempRect);
- C2PStr(theWord);
- SetIText(tempHandle, (StringPtr) theWord);
- } // if
- } // if
- } // if/else
-
- // tell the Dialog Manager that we handled this click, it can stop searching for a click-owner
- returnValue = true;
- } // if
- } // if
- } // if
-
- // reset the original port
-
- SetPort(oldP);
-
- return(returnValue);
-
- } // ListHandler
-
- // ----------------------------------------------------------------------------------
- // AutoReplace
- // ----------------------------------------------------------------------------------
-
- void AutoReplace(TEHandle theTE, DialogPtr SpellDialog)
- {
- char replace[60], comment[255];
- int t;
-
- t = oldwhere;
-
- // Get suggestion (only takes first one)
- if (FindFirstSuggestion(gtheSpeller, theAutoDict, 0, currentWord, replace, comment, &toReplace))
- {
- // check to see if there was an error
- if (GetSpellError())
- return;
-
- // make sure the case matches
- FixCase(gtheSpeller, replace, theInfo.Case);
-
- // select the word
- TESetSelect(oldwhere, where, theTE);
-
- // delete the old word
- TEDelete(theTE);
-
- // insert the new word and select it
- C2PStr(replace);
- TEInsert(replace +1 , replace[0], theTE);
- TESetSelect(oldwhere, oldwhere + replace[0] + 1, theTE);
- whereEnd = whereEnd - (where - oldwhere) + replace[0];
- where = oldwhere; // to check this word
-
- } // if
- } // AutoReplace
-
- // ----------------------------------------------------------------------------------
- // GetNextMisspell
- // ----------------------------------------------------------------------------------
- // This reads words repeatedly, checking the word with the open dictionaries. It
- // stops when it reaches the end of the text or when it finds a misspelling. It
- // sets the 'toReplace' flag to determine if a word is to be automatically replaced.
- // That functionality needs a little cleanup in the code here, as it depends upon
- // a user opened AutoDict. Right now though if a word is flagged as toReplace, it
- // calls the replace function.
- //
- // Note: we can send all our dictionaries to the spelling routines as each dictionary
- // is a long whose bit represents the dictionary. Thus we add them all together to
- // get the dictionaries to be searched. As the unused dictionaries are zero, they
- // add nothing to the routine.
-
- Boolean GetNextMisspell(TEHandle theTE, DialogPtr theDialog)
- {
- Boolean SpelledRight;
- Rect tempRect;
- short tempItem;
- Handle tempHandle;
-
- Duplicate = WORD_NOT_DUPLICATED;
- SpelledRight = FOUND;
-
- while ( (SpelledRight == FOUND) && (Duplicate == WORD_NOT_DUPLICATED ) && (currentWord != nil))
- { currentWord = GetNextWord(theTE);
- if (currentWord == nil)
- return false; // finished, no more text
-
- SpelledRight = CheckWord(gtheSpeller, gMain + theDocDict + theMainDict + theUserDict + theSkipDict +
- theAutoDict + theSuggestDict, 0, currentWord, &theInfo);
-
- if (newCheck && Duplicate) // ignore first duplicate
- { newCheck = false;
- Duplicate = WORD_NOT_DUPLICATED;
- SpelledRight = FOUND;
- } // if
-
- Duplicate = theInfo.Duplicate;
- toReplace = theInfo.Replace;
- theCase = theInfo.Case;
-
- if (!SpelledRight && toReplace)
- {
- AutoReplace(theTE, theDialog);
- SpelledRight = FOUND; // we've corrected it now
- }
- } // while
-
-
-
- // display misspelled word
- GetDItem(theDialog, edUnknown, &tempItem, &tempHandle, &tempRect);
- SetIText(tempHandle, C2PStr(currentWord));
- currentWord = P2CStr((StringPtr)currentWord);
- return true;
-
- } // GetNextMisspell
-
- // ----------------------------------------------------------------------------------
- // MakeSpellWindow
- // ----------------------------------------------------------------------------------
- // This brings up a dialog box, finds each misspelling,creates a list for each of
- // suggestions, and allows the user to fix the text. Most of this is done by
- // calling other routines. The main part of this routine is initializing the
- // dialog and then the switch statement dealing with the user choices. We also
- // create a DocDict that is basically a buffer of 'found' words. This speeds
- // up the checking of words as we don't need to scan through the physical dictionary
- // to find the word. Our routines make that extremely fast, but this buffer is
- // even faster.
-
- void MakeSpellWindow(void)
- {
- short hitItem = 0;
- Rect listRect = { 0, 0, 0, 1 }; // data boundaries of the list (1 column list)
- Cell theCell = { 0, 0 };
- Str255 theString;
-
- Boolean sugDone = false;
- Boolean dDone = false; // done with dialog
-
- DialogPtr SpellDialog = nil; // the window
- // ModalFilterUPP theFilter;
-
- Rect tempRect;
- short tempItem;
- Handle tempHandle;
- TEHandle theTE;
-
- Boolean SpelledRight = false;
-
- newCheck = true;
-
- InitCursor();
-
- if (!gDocWindow)
- return;
-
- theTE = (TEHandle) GetTE(gDocWindow);
-
- where = (*theTE)->selStart;
- whereEnd = (*theTE)->selEnd;
-
- if (whereEnd <= where)
- { whereEnd = (*theTE)->teLength;
- where = 0;
- }
-
-
- SpellDialog = GetNewDialog(rSpellDlog, nil, (WindowPtr) -1);
-
- // Setup the list
- GetDItem(SpellDialog, uList, &tempItem, &tempHandle, &tempRect);
- tempRect.right -= 16;
-
- SetPort(SpellDialog);
- theList = LNew( &tempRect, &listRect, theCell, nil, SpellDialog,
- false, false, false, true);
-
- InitializeList(theList);
- LDoDraw(true, theList);
-
-
- // Supposedly these are Sys7 routines that automatically set the default item.
- if ( TrapAvailable(_DialogDispatch, ToolTrap))
- { SetDialogDefaultItem(SpellDialog, bReplace);
- SetDialogCancelItem(SpellDialog, bClose);
- SetDialogTracksCursor(SpellDialog, true);
- }
-
-
-
- ShowWindow((WindowPtr) SpellDialog);
- DrawDialog(SpellDialog);
- // theFilter = NewModalFilterProc( ListHandler );
-
-
- // Open the Document Dictionary as a buffer (buffering is automatically done)
- DictOpen(gtheSpeller, &theDocDict, DOCUMENT_DICT, 100, NULL);
- if ( GetSpellError() < eNo_Err)
- { DisposeDialog( SpellDialog );
- EndSpellCheckSession(gtheSpeller);
- return;
- }
-
- currentWord = " "; // just to get started
-
- // find first wrong word before dialog
- dDone = !GetNextMisspell(theTE, SpellDialog); // if no misspelled word then done
-
-
-
- // if there was a misspelling put up the suggestions.
- if (!dDone)
- DoSuggest(SpellDialog);
-
- while (!dDone)
- { // ModalDialog(theFilter, &hitItem);
- movableModalDialog ((filterProc) ListHandler, &hitItem );
-
- switch (hitItem) {
- case bIgnore:
- {
- SpellIgnore(currentWord, theTE, SpellDialog);
- dDone = !GetNextMisspell(theTE, SpellDialog);
- if (!dDone)
- DoSuggest(SpellDialog);
- break;
- }
- case bIgnoreAll:
- {
- SpellIgnoreAll(currentWord, theTE, SpellDialog);
- dDone = !GetNextMisspell(theTE, SpellDialog);
- if (!dDone)
- DoSuggest(SpellDialog);
- break;
- }
- case bReplace:
- {
- // Get replacement word
- SpellReplace(currentWord, theTE, SpellDialog);
- dDone = !GetNextMisspell(theTE, SpellDialog);
- if (!dDone)
- DoSuggest(SpellDialog);
- break;
- }
- case bReplaceAll:
- {
- SpellReplaceAll(currentWord, theTE, SpellDialog);
- dDone = !GetNextMisspell(theTE, SpellDialog);
- if (!dDone)
- DoSuggest(SpellDialog);
- break;
- }
- case bSuggest:
- {
- GetDItem(SpellDialog, edReplace, &tempItem, &tempHandle, &tempRect);
- GetIText(tempHandle, theString);
- GetDItem(SpellDialog, edUnknown, &tempItem, &tempHandle, &tempRect);
- SetIText(tempHandle, theString);
- currentWord = P2CStr(theString);
- DoSuggest(SpellDialog);
- break;
- }
- case bAdd:
- { DialogSuggestion(SpellDialog);
- break;
- }
- case bOptions:
- { SpellOptions();
- break;
- }
- case bClose:
- {
- dDone = true;
- break;
- }
- default:
- break;
- } // case
-
-
- } // while
-
- DisposeDialog( SpellDialog );
-
- // close our document dictionary (We could alternatively make this a global,
- // and use it for all our windows, but this way saves money and there really
- // isn't much of an advantage of keeping around anyway)
- DictClose(gtheSpeller, theDocDict);
-
- } // MakeSpellWindow