home *** CD-ROM | disk | FTP | other *** search
- /**********************************************************************
-
- FnTE.cp
-
- ***********************************************************************/
-
- /*
- Displaying text should be easier than it is. This library
- provides a group of functions which allow the basics of displaying
- and editing of text in the form of a TE Record.
-
- Functions Include:
-
- FnTE_SetUpTEWindow Creates TE Record to fill window
- FnTE_MaintainCursor Call this and TEIdle() in event loop
- FnTE_UpdateWindow Redraws window contents
- FnTE_DoActivate Activates/Deactivates window
- FnTE_DoKeyDown Handles keyboard inputs
- FnTE_DoEditMenu Handles cut and paste of TE data
- FnTE_DoContent Handles mousedown in window
- FnTE_DetSBarIncr Refreshes scroll bar parameters
- FnTE_GrowWindow Handles resizing of window
- FnTE_FrameRect Puts frame around text in window
- FnTE_GetTEXT Puts TEXT resource into TE Record
-
- // Semi-private
- FnTE_AdjustText
- FnTE_SetToCursorPos
- FnTE_CheckScrollBar
- FnTE_ScrollProc
- */
-
- #define FnCUT 1
- #define FnCOPY 2
- #define FnPASTE 3
- #define FnCLEAR 4
- #define FnSELECT_ALL 5
-
- #define DEL_KEY 8
- #define DOWN_ARROW 31
- #define UP_ARROW 30
- #define LEFT_ARROW 28
- #define RIGHT_ARROW 29
- #define PAGE_DOWN 12
- #define PAGE_UP 11
- #define HOME 1
- #define END 4
-
- #define MAX_CHAR 32000
-
- TEHandle *tempTEHptr;
- ControlHandle *tempVScrollptr;
- Cursor IBeamCursor;
- Boolean IBeamCursorDefined = FALSE;
-
- // Prototypes
-
- Boolean FnTE_SetUpTEWindow ( WindowPtr w,
- Boolean hasGrowIcon,
- Boolean wordWrap,
- short font,
- short textSize,
- short textInsetPixels,
- // results //
- TEHandle *te,
- ControlHandle *vScroll );
- void FnTE_MaintainCursor ( WindowPtr w,
- TEHandle *te );
- void FnTE_UpdateWindow ( WindowPtr w,
- TEHandle *te,
- Boolean hasGrowIcon );
- void FnTE_DoActivate ( WindowPtr w,
- TEHandle *te,
- ControlHandle *vScroll,
- Boolean hasGrowIcon,
- Boolean activate );
- void FnTE_DoKeyDown ( char theChar,
- TEHandle *te,
- ControlHandle *vScroll,
- char *dirty );
- void FnTE_DoEditMenu ( int item,
- TEHandle *te,
- ControlHandle *vScroll,
- char *dirty,
- int cutCommand,
- int copyCommand,
- int pasteCommand,
- int clearCommand,
- int selectAllCommand );
- void FnTE_DoContent ( WindowPtr w,
- EventRecord *e,
- TEHandle *te,
- ControlHandle *vScroll );
- void FnTE_DetSBarIncr ( TEHandle *te,
- ControlHandle *vScroll );
- void FnTE_GrowWindow ( WindowPtr w,
- TEHandle *te,
- ControlHandle *vScroll,
- short textInsetPixels,
- Point clickLoc );
- void FnTE_FrameRect ( WindowPtr w,
- TEHandle *te,
- short inset );
- void FnTE_GetTEXT ( short rsrcID,
- TEHandle *te,
- ControlHandle *vScroll );
-
- void FnTE_AdjustText ( TEHandle *te, ControlHandle *vScroll );
- void FnTE_SetToCursorPos ( TEHandle *te, ControlHandle *vScroll );
- void FnTE_CheckScrollBar ( TEHandle *te, ControlHandle *vScroll );
- pascal void FnTE_ScrollProc ( ControlHandle theControl,
- short theCode );
-
- extern void FnErr_DisplayStr( Str255 s1,
- Str255 s2,
- Str255 s3,
- Str255 s4,
- int quitFlag );
-
-
- /********** SetUpTEWindow */
-
- Boolean FnTE_SetUpTEWindow(
- WindowPtr w,
- Boolean hasGrowIcon,
- Boolean wordWrap,
- short font,
- short textSize,
- short textInsetPixels,
- // results //
- TEHandle *te,
- ControlHandle *vScroll )
- /*
- FnSetUpWindow takes information you supply about a window
- and it's default text parameters then returns a TEHandle to
- a text pane that fills the window and a ControlHandle to
- a scroll bar that is located at the right of the window.
- Returns FALSE if error detected during routine.
- */
- {
- Rect destRect, viewRect;
- Rect vSBarRect;
- GrafPtr oldPort;
- int SBarWidth = 15;
-
- // define basic te stuff
- GetPort( &oldPort );
- SetPort( w );
- TextFont( font );
- TextSize( textSize );
-
- // set scroll bar rect
- vSBarRect = (*w).portRect;
- vSBarRect.left = vSBarRect.right - SBarWidth;
- vSBarRect.right += 1;
- vSBarRect.top -= 1;
- if( hasGrowIcon )
- vSBarRect.bottom -= 14;
- else
- vSBarRect.bottom += 1;
-
- // create new control
- *vScroll = NewControl( w, &vSBarRect, "\p", 1, 0, 0, 0,
- scrollBarProc, 0L);
- if( *vScroll == NULL )
- return FALSE;
-
- // define te view and dest rects
- viewRect = w->portRect;
- viewRect.right -= SBarWidth;
- if( hasGrowIcon )
- viewRect.bottom -= SBarWidth;
- InsetRect(&viewRect, textInsetPixels, textInsetPixels);
- destRect = viewRect;
-
- // create new te record
- *te = TENew( &destRect, &viewRect );
- if( *te == NULL )
- return FALSE;
- if( wordWrap )
- (***te).crOnly = 1;
- else
- (***te).crOnly = -1;
-
- // set autoview flag for automatic scrolling
- TEAutoView( TRUE, *te );
-
- SetPort( oldPort );
- return TRUE;
- }
-
-
- /********** MaintainCursor */
-
- void FnTE_MaintainCursor( WindowPtr w, TEHandle *te )
- /*
- Maintains cursor icon in TE window. Call this function each time
- through event loop (also call Macintosh function TEIdle to blink
- cursor).
- */
- {
- Point pt;
- WindowPeek wPtr;
- GrafPtr savePort;
- CursHandle hCurs;
-
- /*
- Variables hIBeamCursor and IBeamCursorDefined must be defined
- at top of this FnTELibrary.c file.
- */
-
- if( !IBeamCursorDefined )
- {
- hCurs = GetCursor(1); /* IBeam Cusor ID */
- IBeamCursor = **hCurs;
- IBeamCursorDefined = TRUE;
- }
-
- wPtr = (WindowPeek)FrontWindow();
- if( (WindowPtr)wPtr == w )
- {
- if( wPtr->windowKind >= 0 )
- {
- GetPort( &savePort );
- SetPort( (GrafPtr)wPtr );
- GetMouse( &pt );
- if( PtInRect( pt, &(***te).viewRect ) )
- {
- SetCursor( &IBeamCursor );
- }
- else
- {
- SetCursor( &qd.arrow );
- }
- SetPort( savePort );
- }
- }
- }
-
-
- /********** UpdateWindow */
-
- void FnTE_UpdateWindow( WindowPtr w, TEHandle *te, Boolean hasGrowIcon )
- /*
- Updates a text window.
- */
- {
- GrafPtr savePort;
-
- GetPort(&savePort);
- SetPort(w);
-
- BeginUpdate(w);
- EraseRect(&w->portRect);
- DrawControls(w);
- if( hasGrowIcon )
- DrawGrowIcon(w);
- TEUpdate(&w->portRect, *te);
- EndUpdate(w);
-
- SetPort(savePort);
- }
-
-
- /********** DoActivate */
- void FnTE_DoActivate( WindowPtr w,
- TEHandle *te,
- ControlHandle *vScroll,
- Boolean hasGrowIcon,
- Boolean activate )
- /*
- Handles activateEvt for TE window.
- */
- {
- if( activate )
- {
- TEActivate( *te );
- ShowControl( *vScroll );
- if( hasGrowIcon ) DrawGrowIcon( w );
- TEFromScrap();
- }
- else
- {
- TEDeactivate( *te );
- HideControl( *vScroll );
- if( hasGrowIcon ) DrawGrowIcon( w );
- ZeroScrap();
- TEToScrap();
- }
- }
-
-
- /********** DoKeyDown */
-
- void FnTE_DoKeyDown( char theChar,
- TEHandle *te,
- ControlHandle *vScroll,
- char *dirty )
- /*
- Handles key press in TE region. Uses functions FnTE_SetToCursorPos
- and FnTE_AdjustText to postion text and scroll bar.
- */
- {
- int count = 256; // same as used in FnIO_Library
- tempTEHptr = te; // used in Scroll_Proc
- tempVScrollptr = vScroll; // used in Scroll_Proc
-
- if( (((***te).teLength + count) >= MAX_CHAR) &&
- (theChar != DEL_KEY) )
- {
- FnErr_DisplayStr(
- "\pFile size limits have been exceeded. ",
- "\pPlease save your work and then try to ",
- "\preduce file size.",
- "\p",
- FALSE ); // don't quit
- }
- else
- {
- switch( theChar )
- {
- case DOWN_ARROW:
- case UP_ARROW:
- case LEFT_ARROW:
- case RIGHT_ARROW:
- TEKey( theChar, *te );
- FnTE_SetToCursorPos( te, vScroll );
- FnTE_AdjustText( te, vScroll );
- break;
- case PAGE_DOWN:
- FnTE_ScrollProc( *vScroll, (short)inPageDown );
- break;
- case PAGE_UP:
- FnTE_ScrollProc( *vScroll, (short)inPageUp );
- break;
- case HOME:
- SetCtlValue( *vScroll, 0 );
- FnTE_AdjustText( te, vScroll );
- break;
- case END:
- SetCtlValue( *vScroll, GetCtlMax(*vScroll) );
- FnTE_AdjustText( te, vScroll );
- break;
- default:
- {
- TEKey( theChar, *te );
- FnTE_SetToCursorPos( te, vScroll );
- FnTE_AdjustText( te, vScroll );
- *dirty = 1;
- }
- }
- }
- }
-
-
- /********** DoEditMenu */
-
- void FnTE_DoEditMenu( int theItem,
- TEHandle *te,
- ControlHandle *vScroll,
- char *dirty,
- int cutCommand,
- int copyCommand,
- int pasteCommand,
- int clearCommand,
- int selectAll )
- /*
- Performs cut and paste function of standard Edit menu items.
- */
- {
- if ( theItem == cutCommand ) theItem = FnCUT;
- else if( theItem == copyCommand ) theItem = FnCOPY;
- else if( theItem == pasteCommand ) theItem = FnPASTE;
- else if( theItem == clearCommand ) theItem = FnCLEAR;
- else if( theItem == selectAll ) theItem = FnSELECT_ALL;
-
- switch( theItem )
- {
- case FnCUT:
- TECut( *te );
- FnTE_DetSBarIncr( te, vScroll );
- FnTE_SetToCursorPos( te, vScroll );
- FnTE_AdjustText( te, vScroll );
- *dirty = 1;
- break;
- case FnCOPY:
- TECopy( *te );
- break;
- case FnPASTE:
- if(TEGetScrapLen() + (***te).teLength < MAX_CHAR)
- {
- TEPaste( *te );
- FnTE_DetSBarIncr( te, vScroll );
- FnTE_SetToCursorPos( te, vScroll );
- FnTE_AdjustText( te, vScroll );
- *dirty = 1;
- }
- else
- {
- FnErr_DisplayStr(
- "\pPaste size too large.","\p","\p","\p", FALSE);
- }
- break;
- case FnCLEAR:
- TEDelete( *te );
- FnTE_DetSBarIncr( te, vScroll );
- FnTE_SetToCursorPos( te, vScroll );
- FnTE_AdjustText( te, vScroll );
- *dirty = 1;
- break;
- case FnSELECT_ALL:
- TESetSelect( 0, 32767, *te );
- FnTE_SetToCursorPos( te, vScroll );
- FnTE_AdjustText( te, vScroll );
- break;
- }
- }
-
-
- /********** DoContent */
-
- void FnTE_DoContent( WindowPtr w,
- EventRecord *e,
- TEHandle *te,
- ControlHandle *vScroll )
- /*
- Use this procedure when user clicks in content region of TE window.
- Uses the TnTE_ScrollProc below to take care of scroll bar function.
- Also uses FnTE_AdjustText function.
- */
- {
- int cntlCode;
- ControlHandle cntl;
- int pageSize;
- GrafPtr savePort;
-
- GetPort(&savePort);
- SetPort(w);
-
- GlobalToLocal(&e->where);
- if( (cntlCode = FindControl(e->where, w, &cntl)) == 0 )
- {
- if( PtInRect( e->where, &(***te).viewRect) )
- {
- TEClick( e->where, (e->modifiers & shiftKey) != 0, *te );
- FnTE_CheckScrollBar( te, vScroll );
- }
- }
- else if( cntlCode == inThumb )
- {
- TrackControl( cntl, e->where, 0L );
- FnTE_AdjustText( te, vScroll );
- }
- else
- {
- tempTEHptr = te;
- tempVScrollptr = vScroll;
- TrackControl( cntl, e->where, FnTE_ScrollProc );
- }
-
- SetPort(savePort);
- }
-
-
- /********** DetSBarIncr */
-
- void FnTE_DetSBarIncr( TEHandle *te, ControlHandle *vScroll )
- /*
- Determines number of scroll bar increments based on amount of
- text pointed to in TEHandle te.
- */
- {
- register int nIncr, nLinesDisplayed, len;
-
- nLinesDisplayed = ((***te).viewRect.bottom-(***te).viewRect.top) /
- (***te).lineHeight;
- nIncr = (***te).nLines - nLinesDisplayed;
- len = (***te).teLength;
- if( len <= 1 ) len = 1;
- if( (*((***te).hText))[len-1] == '\r' )
- nIncr++;
-
- if( nIncr < 0 )
- nIncr = 0;
- if( nIncr != GetCtlMax( *vScroll ) )
- SetCtlMax( *vScroll, nIncr );
- }
-
-
- /********** GrowWindow */
-
- void FnTE_GrowWindow( WindowPtr w,
- TEHandle *te,
- ControlHandle *vScroll,
- short textInsetPixels,
- Point clickLoc )
- /*
- Use this function to resize a TE window.
- */
- {
- GrafPtr savePort;
- long theResult;
- Rect oldHorizBar;
- Rect r;
- int SBarWidth = 15;
- float percent;
- float currentValue;
- float currentMax;
-
- GetPort( &savePort );
- SetPort( w );
- // although not used, calculate size of bottom scroll bar
- oldHorizBar = w->portRect;
- oldHorizBar.top = oldHorizBar.bottom - (SBarWidth + 1);
- currentValue = GetCtlValue( *vScroll );
- currentMax = GetCtlMax( *vScroll );
- if( currentMax > 0 )
- percent = currentValue / currentMax;
- else
- percent = 0.0;
- SetRect( &r, 100, 100, qd.screenBits.bounds.right,
- qd.screenBits.bounds.bottom );
- theResult = GrowWindow( w, clickLoc, &r );
- if (theResult == 0)
- return;
- SizeWindow( w, LoWord(theResult), HiWord(theResult), FALSE );
- InvalRect( &w->portRect );
- EraseRect( &w->portRect );
-
- (***te).viewRect = w->portRect;
- (***te).viewRect.right -= SBarWidth;
- (***te).viewRect.bottom -= SBarWidth;
- InsetRect( &(***te).viewRect, textInsetPixels, textInsetPixels );
- (***te).destRect = (***te).viewRect;
- TECalText( *te );
- MoveControl( *vScroll,
- w->portRect.right - SBarWidth,
- w->portRect.top - 1 );
- SizeControl( *vScroll,
- SBarWidth + 1,
- w->portRect.bottom - w->portRect.top - (SBarWidth-2) );
- FnTE_DetSBarIncr( te, vScroll );
- percent = percent * (float)GetCtlMax( *vScroll );
- SetCtlValue( *vScroll, int( percent ) );
- FnTE_AdjustText( te, vScroll );
- DrawGrowIcon( w );
- TEUpdate( &w->portRect, *te );
- ValidRect( &w->portRect );
-
- SetPort( savePort );
- }
-
-
- /********** FrameRect */
-
- void FnTE_FrameRect( WindowPtr w, TEHandle *te, short inset )
- {
- Rect itemRect;
- PenState thePnState;
- GrafPtr oldPort;
-
- GetPort( &oldPort );
- SetPort( w );
- itemRect = (***te).viewRect;
- InsetRect( &itemRect, -inset, -inset );
- itemRect.right += 1;
- GetPenState( &thePnState );
- PenNormal();
- FrameRect( &itemRect );
- SetPenState( &thePnState );
- SetPort( oldPort );
- }
-
-
- /********** GetTEXT */
-
- void FnTE_GetTEXT( short rsrcID, TEHandle *te, ControlHandle *vScroll )
- /*
- Reads in TEXT resource into TE record and resets scroll bar. Need
- to call FnTE_UpdateWindow to display text.
- */
- {
- (**te)->hText = GetResource( 'TEXT', rsrcID );
- TECalText( *te );
- (***te).destRect.top = (***te).viewRect.top;
- SetCtlValue( *vScroll, GetCtlMin( *vScroll ) );
- FnTE_DetSBarIncr( te, vScroll );
- }
-
-
- /********** AdjustText */
-
- void FnTE_AdjustText( TEHandle *te, ControlHandle *vScroll )
- /*
- Takes current value of the scroll bar position and adjusts text
- for specified TextEdit pane. Call this function after user
- clicks in scroll bar.
- */
- {
- int oldScroll, newScroll, delta;
-
- oldScroll = (***te).viewRect.top - (***te).destRect.top;
- newScroll = GetCtlValue( *vScroll ) * (***te).lineHeight;
- delta = oldScroll - newScroll;
- if( delta != 0 )
- TEScroll( 0, delta, *te );
- }
-
-
- /********** SetToCursorPos */
-
- void FnTE_SetToCursorPos( TEHandle *te, ControlHandle *vScroll )
- /*
- Use this function to adjust scroll bar position such that the
- currently selected text and/or insertion cursor position is
- displayed in middle of te window. You must make a call to a
- function like FnTE_AdjustText after calling this function to redraw
- text based on new scroll bar position.
- */
- {
- register int topLine,bottomLine,theLine,nIncr,nLinesDisplayed,len;
-
- // following could be replaced by call to FnDetSBarIncr
- nLinesDisplayed = ((***te).viewRect.bottom-(***te).viewRect.top) /
- (***te).lineHeight;
- nIncr = (***te).nLines - nLinesDisplayed;
-
- len = (***te).teLength;
- if( len <= 1 ) len = 1;
- if( (*((***te).hText))[len-1] == '\r' )
- nIncr++;
-
- if( nIncr < 0 )
- nIncr = 0;
- SetCtlMax( *vScroll, nIncr );
-
- topLine = GetCtlValue( *vScroll );
- bottomLine = topLine + nLinesDisplayed;
- if( (***te).selStart < (***te).lineStarts[topLine] ||
- (***te).selStart >= (***te).lineStarts[bottomLine] )
- {
- for( theLine = 0;
- (***te).selStart >= (***te).lineStarts[theLine];
- theLine++ )
- /* count */ ;
- SetCtlValue( *vScroll, theLine - nLinesDisplayed / 2 );
- }
- }
-
-
- /********** CheckScrollBar */
-
- void FnTE_CheckScrollBar( TEHandle *te, ControlHandle *vScroll )
- /*
- Use this function to check (and adjust) scroll bar such that the
- current top of the TE window matches the scroll bar increment. This
- should be called when a mouseDown occurs in a TE window which has
- auto scrolling enabled.
- */
- {
- register int incr;
-
- incr = ((***te).viewRect.top-(***te).destRect.top) /
- (***te).lineHeight;
- if( incr < 0 )
- incr = 0;
- if( incr > GetCtlMax( *vScroll ) )
- incr = GetCtlMax( *vScroll );
- if( incr != GetCtlValue( *vScroll ) )
- SetCtlValue( *vScroll, incr );
- }
-
-
- /********** PASCAL ScrollProc */
-
- pascal void FnTE_ScrollProc( ControlHandle theControl, short theCode )
- /*
- Scroll procedure used for TE scroll bar. Uses FnTE_AdjustText
- function to update text.
- */
- {
- int pageSize;
- int scrollAmt;
- int oldCtl;
-
- if( theCode == 0 )
- return;
-
- pageSize =
- ((***tempTEHptr).viewRect.bottom -
- (***tempTEHptr).viewRect.top) /
- (***tempTEHptr).lineHeight - 1;
-
- switch( theCode )
- {
- case inUpButton:
- scrollAmt = -1;
- break;
- case inDownButton:
- scrollAmt = 1;
- break;
- case inPageUp:
- scrollAmt = -pageSize;
- break;
- case inPageDown:
- scrollAmt = pageSize;
- break;
- }
-
- oldCtl = GetCtlValue( theControl );
- SetCtlValue( theControl, oldCtl + scrollAmt );
-
- FnTE_AdjustText( tempTEHptr, tempVScrollptr );
- }
-
- // End of File