home *** CD-ROM | disk | FTP | other *** search
- #import "ToyView.h"
- #import <dpsclient/wraps.h>
- #import <dpsclient/event.h>
- #import <appkit/publicWraps.h>
- #import <appkit/NXImage.h>
- #import <appkit/NXBitmapImageRep.h>
- #import <appkit/Application.h>
- #import <appkit/NXCursor.h>
- #import <appkit/TextField.h>
- #import <stdlib.h>
- #import "PrefControl.h"
-
- #define CrossCursor "cross.tiff"
-
- static NXCursor *xCursor = nil;
- static BOOL originUpperLeft = NO;
-
-
- @implementation ToyView (EventHandling)
-
- + cursor
- {
- if (!xCursor) {
- NXPoint spot;
- xCursor = [NXCursor newFromImage:[NXImage newFromSection:CrossCursor]];
- spot.x = 7.0; spot.y = 7.0;
- [xCursor setHotSpot:&spot];
- }
- return xCursor;
- }
-
- + (BOOL)setOriginUpperLeft:(BOOL)flag
- {
- BOOL oldflag = originUpperLeft;
- originUpperLeft = flag;
- return oldflag;
- }
-
- - (BOOL)acceptsFirstResponder
- {
- return YES;
- }
-
- - (BOOL)acceptsFirstMouse
- {
- return YES;
- }
-
- - resetCursorRects
- {
- NXRect visible;
-
- if ([self getVisibleRect:&visible])
- [self addCursorRect:&visible cursor:xCursor];
- return self;
- }
-
- /* Local Method */
- - drawDraggedLine: (NXCoord)x : (NXCoord)y : (int)dx : (int)dy
- {
- char buf[20], points[64];
- int y1, y2;
-
- if (originUpperLeft) {
- y1 = curSize.height - y - dy;
- y2 = curSize.height - y - 1;
- }else {
- y1 = y, y2 = y + dy - 1;
- }
- sprintf(points, "%d x %d (%d, %d : %d, %d)",
- dx, dy, (int)x, y1, (int)x + dx - 1, y2);
- [commText setStringValue: points];
-
- // already 'lockFocus'ed
- PSnewinstance();
- PSsetinstance(YES);
- PSsetlinewidth(0.0);
- PSsetgray(0.1667);
- PSrectstroke(x, y+1, dx-1, dy-1); /* Why +1 ?? */
- if ( dx >= 18 && dy >= 10 ) {
- sprintf(buf, "%d x %d", dx, dy);
- PSmoveto(x+1, y+2);
- PSselectfont("Times-Roman", 12.0);
- PSshow(buf);
- }
- PSsetinstance(NO);
- NXPing();
- return self;
- }
-
- - clearDraggedLine
- {
- NXSize *sz = &selectRect.size;
- if (sz->width > 0.0 || sz->height > 0.0) {
- [self lockFocus];
- PSnewinstance();
- [self unlockFocus];
- sz->width = 0.0;
- sz->height = 0.0;
- [commText setStringValue: comInfo->memo];
- }
- return self;
- }
-
- - setDraggedLine: sender
- {
- NXSize *sz = &selectRect.size;
- if (sz->width > 0.0 && sz->height > 0.0) {
- [self lockFocus];
- [self drawDraggedLine: selectRect.origin.x
- : selectRect.origin.y : sz->width : sz->height];
- [self unlockFocus];
- }
- return self;
- }
-
- - rewriteComment
- {
- [commText setStringValue: comInfo->memo];
- return self;
- }
-
- #define DRAG_MASK (NX_MOUSEUPMASK|NX_MOUSEDRAGGEDMASK)
- #define PRESS_MASK (NX_MOUSEUPMASK|NX_MOUSEDOWNMASK)
-
- /* Local Method */
- - mousePress: (int)count
- {
- NXRect rect;
-
- if (!comInfo->alpha)
- return self;
- if (count <= 1) {
- if (backgray == 1.0) return self;
- backgray = 1.0;
- }else if (count > 3) backgray = 0.0;
- else backgray = (4 - count) / 3.0;
- // Double-click = Light Gray, Triple click = Dark Gray
- rect.origin.x = rect.origin.y = 0;
- rect.size = curSize;
- [self lockFocus];
- [self drawSelf:&rect : 1];
- [self unlockFocus];
- [window flushWindow];
- return self;
- }
-
- /* Code based on pCD.app (H. Danisch & D. Phillips) */
-
- - mouseDown:(NXEvent *)event
- {
- NXPoint p, start, lowerleft;
- BOOL altDrag = NO, sftDrag = NO;
- int oldMask, cn;
- int xn = 0, yn = 0, xs, ys;
-
- [self mousePress: (cn = event->data.mouse.click)];
- if (cn > 1) return self;
- oldMask = [window addToEventMask:DRAG_MASK];
- p = event->location;
- [self convertPoint:&p fromView:nil]; /* View based point */
- if (p.x < 0.0) p.x = 0.0;
- else if (p.x >= curSize.width) p.x = curSize.width - 1;
- p.y--;
- if (p.y < 0.0) p.y = 0.0;
- else if (p.y > curSize.height) p.y = curSize.height - 1;
- start.x = (int)p.x;
- start.y = (int)p.y;
- if (NX_ALTERNATEMASK & event->flags)
- altDrag = YES;
-
- [self lockFocus];
- PSnewinstance();
- PSsetinstance(YES);
- event = [NXApp getNextEvent:DRAG_MASK];
-
- while( event->type != NX_MOUSEUP ) {
- if (NX_ALTERNATEMASK & event->flags)
- altDrag = YES;
- if (NX_SHIFTMASK & event->flags)
- sftDrag = YES;
- p = event->location;
- [self convertPoint:&p fromView:nil];
- if (p.x < 0.0) p.x = 0.0;
- else if (p.x >= curSize.width) p.x = curSize.width - 1;
- p.y--;
- if (p.y < 0.0) p.y = 0.0;
- else if (p.y > curSize.height) p.y = curSize.height - 1;
-
- if (p.x > start.x)
- xn = (int)p.x - start.x + 1, xs = 1;
- else
- xn = start.x - (int)p.x + 1, xs = -1;
- if (p.y > start.y)
- yn = (int)p.y - start.y + 1, ys = 1;
- else
- yn = start.y - (int)p.y + 1, ys = -1;
- if (altDrag) {
- if (xn < yn) yn = xn;
- else xn = yn;
- }
- if (sftDrag) {
- xn = (xn + 1) & ~3;
- yn = (yn + 1) & ~3;
- }
- p.x = start.x + (xn-1)*xs;
- p.y = start.y + (yn-1)*ys;
- lowerleft.x = (start.x < p.x) ? start.x : p.x;
- lowerleft.y = (start.y < p.y) ? start.y : p.y;
- [self drawDraggedLine: lowerleft.x : lowerleft.y : xn : yn];
- event = [NXApp getNextEvent:DRAG_MASK];
- }
- [self unlockFocus];
-
- selectRect.origin.x = lowerleft.x;
- selectRect.origin.y = lowerleft.y;
- selectRect.size.width = xn;
- selectRect.size.height = yn;
- if (xn == 0 && yn == 0) /* only click */
- [commText setStringValue: comInfo->memo];
- else if (xn < 3 && yn < 3) /* Too small area */
- [self clearDraggedLine];
-
- [window flushWindow];
- [window setEventMask:oldMask];
-
- return self;
- }
-
- - selectAll:sender
- {
- [self clearDraggedLine];
- selectRect.size = curSize;
- selectRect.origin.x = selectRect.origin.y = 0.0;
- [self setDraggedLine: sender];
- return self;
- }
-
- - copy:sender
- {
- NXStream *st;
- NXBitmapImageRep *bm;
- int i = 0;
- const char *types[2];
- id pb = [Pasteboard new];
-
- if (selectRect.size.width < 1.0 || selectRect.size.height < 1.0) {
- NXBeep();
- return self;
- }
-
- // note that "owner:" in the following can not be "self", or the
- // id of anything else which might be freed inbetween "Copy"
- // operations.
- types[i++] = NXTIFFPboardType;
- [pb declareTypes:types num:i owner:NXApp];
-
- [self lockFocus];
- bm = [[NXBitmapImageRep alloc] initData:NULL fromRect:&selectRect];
- [self unlockFocus];
-
- st = NXOpenMemory(NULL, 0, NX_WRITEONLY);
- [bm writeTIFF:st];
- [pb writeType:NXTIFFPboardType fromStream:st];
- NXCloseMemory(st, NX_FREEBUFFER);
- [bm free];
-
- return self;
- }
-
- - drawSelf:(NXRect *)r :(int) count
- {
- NXSize *sz;
-
- if (comInfo->alpha) {
- PSsetgray(backgray);
- NXRectFill(r);
- [image composite:NX_SOVER fromRect:r toPoint:&(r->origin)];
- }else
- [image composite:NX_COPY fromRect:r toPoint:&(r->origin)];
-
- sz = &selectRect.size;
- if (sz->width > 0.0 && sz->height > 0.0)
- [self perform:@selector(setDraggedLine:) with:self
- afterDelay:30 cancelPrevious:YES];
- return self;
- }
-
- @end
-