From 78381153755568f86fef8896156ae8b841ef7179 Mon Sep 17 00:00:00 2001 From: Bibiko Date: Sat, 30 Jan 2010 14:42:50 +0000 Subject: =?UTF-8?q?=E2=80=A2=20added=20observer=20for=20all=20Query=20Edit?= =?UTF-8?q?or=20colors=20to=20avoid=20initialising=20colors=20each=20time?= =?UTF-8?q?=20for=20syntax=20highlighting=20which=20speed=20it=20up=20a=20?= =?UTF-8?q?bit;=20now=20if=20one=20changes=20a=20color=20the=20changes=20a?= =?UTF-8?q?re=20done=20in=20view=20after=20a=20delay=20of=200.1=20s=20if?= =?UTF-8?q?=20text=20buffer=20<=20100k=20for=20speed=20reasons=20=E2=80=A2?= =?UTF-8?q?=20fixed:=20before=20highlighting=20the=20current=20query=20ens?= =?UTF-8?q?ure=20that=20the=20text=20storage=20is=20in=20a=20stable=20and?= =?UTF-8?q?=20clean=20status;=20otherwise=20SP=20crashes=20for=20ranges=20?= =?UTF-8?q?which=20aren't=20rendered=20yet?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Source/CMTextView.h | 14 ++++ Source/CMTextView.m | 211 ++++++++++++++++++++++++++++----------------------- Source/CustomQuery.m | 10 +++ 3 files changed, 139 insertions(+), 96 deletions(-) diff --git a/Source/CMTextView.h b/Source/CMTextView.h index 1546d1e8..ea0b36cc 100644 --- a/Source/CMTextView.h +++ b/Source/CMTextView.h @@ -68,6 +68,13 @@ static inline void NSMutableAttributedStringAddAttributeValueRange (NSMutableAtt NSColor *queryHiliteColor; NSColor *queryEditorBackgroundColor; + NSColor *commentColor; + NSColor *quoteColor; + NSColor *keywordColor; + NSColor *backtickColor; + NSColor *numericColor; + NSColor *variableColor; + NSColor *otherTextColor; NSRange queryRange; BOOL shouldHiliteQuery; @@ -75,6 +82,13 @@ static inline void NSMutableAttributedStringAddAttributeValueRange (NSMutableAtt @property(retain) NSColor* queryHiliteColor; @property(retain) NSColor* queryEditorBackgroundColor; +@property(retain) NSColor* commentColor; +@property(retain) NSColor* quoteColor; +@property(retain) NSColor* keywordColor; +@property(retain) NSColor* backtickColor; +@property(retain) NSColor* numericColor; +@property(retain) NSColor* variableColor; +@property(retain) NSColor* otherTextColor; @property(assign) NSRange queryRange; @property(assign) BOOL shouldHiliteQuery; diff --git a/Source/CMTextView.m b/Source/CMTextView.m index c14f5d59..e025296c 100644 --- a/Source/CMTextView.m +++ b/Source/CMTextView.m @@ -86,6 +86,13 @@ static inline NSPoint SPPointOnLine(NSPoint a, NSPoint b, CGFloat t) { return NS @synthesize queryHiliteColor; @synthesize queryEditorBackgroundColor; +@synthesize commentColor; +@synthesize quoteColor; +@synthesize keywordColor; +@synthesize backtickColor; +@synthesize numericColor; +@synthesize variableColor; +@synthesize otherTextColor; @synthesize queryRange; @synthesize shouldHiliteQuery; @@ -166,6 +173,13 @@ NSInteger alphabeticSort(id string1, id string2, void *reverse) [prefs addObserver:self forKeyPath:SPCustomQueryEditorBackgroundColor options:NSKeyValueObservingOptionNew context:NULL]; [prefs addObserver:self forKeyPath:SPCustomQueryEditorHighlightQueryColor options:NSKeyValueObservingOptionNew context:NULL]; [prefs addObserver:self forKeyPath:SPCustomQueryHighlightCurrentQuery options:NSKeyValueObservingOptionNew context:NULL]; + [prefs addObserver:self forKeyPath:SPCustomQueryEditorCommentColor options:NSKeyValueObservingOptionNew context:NULL]; + [prefs addObserver:self forKeyPath:SPCustomQueryEditorQuoteColor options:NSKeyValueObservingOptionNew context:NULL]; + [prefs addObserver:self forKeyPath:SPCustomQueryEditorSQLKeywordColor options:NSKeyValueObservingOptionNew context:NULL]; + [prefs addObserver:self forKeyPath:SPCustomQueryEditorBacktickColor options:NSKeyValueObservingOptionNew context:NULL]; + [prefs addObserver:self forKeyPath:SPCustomQueryEditorNumericColor options:NSKeyValueObservingOptionNew context:NULL]; + [prefs addObserver:self forKeyPath:SPCustomQueryEditorVariableColor options:NSKeyValueObservingOptionNew context:NULL]; + [prefs addObserver:self forKeyPath:SPCustomQueryEditorTextColor options:NSKeyValueObservingOptionNew context:NULL]; } @@ -189,6 +203,35 @@ NSInteger alphabeticSort(id string1, id string2, void *reverse) } else if ([keyPath isEqualToString:SPCustomQueryHighlightCurrentQuery]) { [self setShouldHiliteQuery:[[change objectForKey:NSKeyValueChangeNewKey] boolValue]]; [self setNeedsDisplay:YES]; + } else if ([keyPath isEqualToString:SPCustomQueryEditorCommentColor]) { + [self setCommentColor:[NSUnarchiver unarchiveObjectWithData:[change objectForKey:NSKeyValueChangeNewKey]]]; + if([[self string] length]<100000) + [self performSelector:@selector(doSyntaxHighlighting) withObject:nil afterDelay:0.1]; + } else if ([keyPath isEqualToString:SPCustomQueryEditorQuoteColor]) { + [self setQuoteColor:[NSUnarchiver unarchiveObjectWithData:[change objectForKey:NSKeyValueChangeNewKey]]]; + if([[self string] length]<100000) + [self performSelector:@selector(doSyntaxHighlighting) withObject:nil afterDelay:0.1]; + } else if ([keyPath isEqualToString:SPCustomQueryEditorSQLKeywordColor]) { + [self setKeywordColor:[NSUnarchiver unarchiveObjectWithData:[change objectForKey:NSKeyValueChangeNewKey]]]; + if([[self string] length]<100000) + [self performSelector:@selector(doSyntaxHighlighting) withObject:nil afterDelay:0.1]; + } else if ([keyPath isEqualToString:SPCustomQueryEditorBacktickColor]) { + [self setBacktickColor:[NSUnarchiver unarchiveObjectWithData:[change objectForKey:NSKeyValueChangeNewKey]]]; + if([[self string] length]<100000) + [self performSelector:@selector(doSyntaxHighlighting) withObject:nil afterDelay:0.1]; + } else if ([keyPath isEqualToString:SPCustomQueryEditorNumericColor]) { + [self setNumericColor:[NSUnarchiver unarchiveObjectWithData:[change objectForKey:NSKeyValueChangeNewKey]]]; + if([[self string] length]<100000) + [self performSelector:@selector(doSyntaxHighlighting) withObject:nil afterDelay:0.1]; + } else if ([keyPath isEqualToString:SPCustomQueryEditorVariableColor]) { + [self setVariableColor:[NSUnarchiver unarchiveObjectWithData:[change objectForKey:NSKeyValueChangeNewKey]]]; + if([[self string] length]<100000) + [self performSelector:@selector(doSyntaxHighlighting) withObject:nil afterDelay:0.1]; + } else if ([keyPath isEqualToString:SPCustomQueryEditorTextColor]) { + [self setOtherTextColor:[NSUnarchiver unarchiveObjectWithData:[change objectForKey:NSKeyValueChangeNewKey]]]; + [self setTextColor:[self otherTextColor]]; + if([[self string] length]<100000) + [self performSelector:@selector(doSyntaxHighlighting) withObject:nil afterDelay:0.1]; } } @@ -2816,17 +2859,9 @@ NSInteger alphabeticSort(id string1, id string2, void *reverse) // process syntax highlighting for the entire text view buffer textRange = NSMakeRange(0,strlength); } - + NSColor *tokenColor; - - NSColor *commentColor = [[NSUnarchiver unarchiveObjectWithData:[prefs dataForKey:SPCustomQueryEditorCommentColor]] retain]; - NSColor *quoteColor = [[NSUnarchiver unarchiveObjectWithData:[prefs dataForKey:SPCustomQueryEditorQuoteColor]] retain]; - NSColor *keywordColor = [[NSUnarchiver unarchiveObjectWithData:[prefs dataForKey:SPCustomQueryEditorSQLKeywordColor]] retain]; - NSColor *backtickColor = [[NSUnarchiver unarchiveObjectWithData:[prefs dataForKey:SPCustomQueryEditorBacktickColor]] retain]; - NSColor *numericColor = [[NSUnarchiver unarchiveObjectWithData:[prefs dataForKey:SPCustomQueryEditorNumericColor]] retain]; - NSColor *variableColor = [[NSUnarchiver unarchiveObjectWithData:[prefs dataForKey:SPCustomQueryEditorVariableColor]] retain]; - NSColor *textColor = [[NSUnarchiver unarchiveObjectWithData:[prefs dataForKey:SPCustomQueryEditorTextColor]] retain]; - + BOOL autouppercaseKeywords = [prefs boolForKey:SPCustomQueryAutoUppercaseKeywords]; NSUInteger tokenEnd, token; @@ -2874,7 +2909,7 @@ NSInteger alphabeticSort(id string1, id string2, void *reverse) continue; break; default: - tokenColor = textColor; + tokenColor = otherTextColor; allowToCheckForUpperCase = NO; } @@ -2938,20 +2973,11 @@ NSInteger alphabeticSort(id string1, id string2, void *reverse) } - [commentColor release]; - [quoteColor release]; - [keywordColor release]; - [backtickColor release]; - [numericColor release]; - [variableColor release]; - [textColor release]; - } - (void)drawRect:(NSRect)rect { // Draw textview's background since due to the snippet highlighting we're responsible for it. - [[[NSUnarchiver unarchiveObjectWithData:[prefs dataForKey:SPCustomQueryEditorBackgroundColor]] retain] setFill]; [[self queryEditorBackgroundColor] setFill]; NSRectFill(rect); @@ -2959,6 +2985,7 @@ NSInteger alphabeticSort(id string1, id string2, void *reverse) // and if nothing is selected in the text view if ([self shouldHiliteQuery] && snippetControlCounter<=-1 && ![self selectedRange].length) { NSUInteger rectCount; + [[self textStorage] ensureAttributesAreFixedInRange:[self queryRange]]; NSRectArray queryRects = [[self layoutManager] rectArrayForCharacterRange: [self queryRange] withinSelectedCharacterRange: [self queryRange] inTextContainer: [self textContainer] @@ -2990,67 +3017,67 @@ NSInteger alphabeticSort(id string1, id string2, void *reverse) - (NSBezierPath*)roundedBezierPathAroundRange:(NSRange)aRange { - // parameters for snippet highlighting - CGFloat kappa = 0.5522847498; // magic number from http://www.whizkidtech.redprince.net/bezier/circle/ - CGFloat radius = 6; - CGFloat horzInset = -3; - CGFloat vertInset = 0.3; - BOOL connectDisconnectedPartsWithLine = NO; - - NSBezierPath *funkyPath = [NSBezierPath bezierPath]; - NSUInteger rectCount; - NSRectArray rects = [[self layoutManager] rectArrayForCharacterRange: aRange - withinSelectedCharacterRange: aRange - inTextContainer: [self textContainer] - rectCount: &rectCount ]; - if (rectCount>2 || (rectCount>1 && (SPRectRight(rects[1]) >= SPRectLeft(rects[0]) || connectDisconnectedPartsWithLine))) { - // highlight complicated multiline snippet - NSRect lineRects[4]; - lineRects[0] = rects[0]; - lineRects[1] = rects[1]; - lineRects[2] = rects[rectCount-2]; - lineRects[3] = rects[rectCount-1]; - for(int j=0;j<4;j++) lineRects[j] = NSInsetRect(lineRects[j], horzInset, vertInset); - NSPoint vertices[8]; - vertices[0] = NSMakePoint( SPRectLeft(lineRects[0]), SPRectTop(lineRects[0]) ); // point a - vertices[1] = NSMakePoint( SPRectRight(lineRects[0]), SPRectTop(lineRects[0]) ); // point b - vertices[2] = NSMakePoint( SPRectRight(lineRects[2]), SPRectBottom(lineRects[2]) ); // point c - vertices[3] = NSMakePoint( SPRectRight(lineRects[3]), SPRectBottom(lineRects[2]) ); // point d - vertices[4] = NSMakePoint( SPRectRight(lineRects[3]), SPRectBottom(lineRects[3]) ); // point e - vertices[5] = NSMakePoint( SPRectLeft(lineRects[3]), SPRectBottom(lineRects[3]) ); // point f - vertices[6] = NSMakePoint( SPRectLeft(lineRects[1]), SPRectTop(lineRects[1]) ); // point g - vertices[7] = NSMakePoint( SPRectLeft(lineRects[0]), SPRectTop(lineRects[1]) ); // point h - - for (NSUInteger j=0; j<8; j++) { - NSPoint curr = vertices[j]; - NSPoint prev = vertices[(j+8-1)%8]; - NSPoint next = vertices[(j+1)%8]; - - CGFloat s = radius/SPPointDistance(prev, curr); - if (s>0.5) s = 0.5; - CGFloat t = radius/SPPointDistance(curr, next); - if (t>0.5) t = 0.5; - - NSPoint a = SPPointOnLine(curr, prev, 0.5); - NSPoint b = SPPointOnLine(curr, prev, s); - NSPoint c = curr; - NSPoint d = SPPointOnLine(curr, next, t); - NSPoint e = SPPointOnLine(curr, next, 0.5); - - if (j==0) [funkyPath moveToPoint:a]; - [funkyPath lineToPoint: b]; - [funkyPath curveToPoint:d controlPoint1:SPPointOnLine(b, c, kappa) controlPoint2:SPPointOnLine(d, c, kappa)]; - [funkyPath lineToPoint: e]; - } - } else { - //highlight disconnected snippet parts (or single line snippet) - for (NSUInteger j=0; j2 || (rectCount>1 && (SPRectRight(rects[1]) >= SPRectLeft(rects[0]) || connectDisconnectedPartsWithLine))) { + // highlight complicated multiline snippet + NSRect lineRects[4]; + lineRects[0] = rects[0]; + lineRects[1] = rects[1]; + lineRects[2] = rects[rectCount-2]; + lineRects[3] = rects[rectCount-1]; + for(int j=0;j<4;j++) lineRects[j] = NSInsetRect(lineRects[j], horzInset, vertInset); + NSPoint vertices[8]; + vertices[0] = NSMakePoint( SPRectLeft(lineRects[0]), SPRectTop(lineRects[0]) ); // point a + vertices[1] = NSMakePoint( SPRectRight(lineRects[0]), SPRectTop(lineRects[0]) ); // point b + vertices[2] = NSMakePoint( SPRectRight(lineRects[2]), SPRectBottom(lineRects[2]) ); // point c + vertices[3] = NSMakePoint( SPRectRight(lineRects[3]), SPRectBottom(lineRects[2]) ); // point d + vertices[4] = NSMakePoint( SPRectRight(lineRects[3]), SPRectBottom(lineRects[3]) ); // point e + vertices[5] = NSMakePoint( SPRectLeft(lineRects[3]), SPRectBottom(lineRects[3]) ); // point f + vertices[6] = NSMakePoint( SPRectLeft(lineRects[1]), SPRectTop(lineRects[1]) ); // point g + vertices[7] = NSMakePoint( SPRectLeft(lineRects[0]), SPRectTop(lineRects[1]) ); // point h + + for (NSUInteger j=0; j<8; j++) { + NSPoint curr = vertices[j]; + NSPoint prev = vertices[(j+8-1)%8]; + NSPoint next = vertices[(j+1)%8]; + + CGFloat s = radius/SPPointDistance(prev, curr); + if (s>0.5) s = 0.5; + CGFloat t = radius/SPPointDistance(curr, next); + if (t>0.5) t = 0.5; + + NSPoint a = SPPointOnLine(curr, prev, 0.5); + NSPoint b = SPPointOnLine(curr, prev, s); + NSPoint c = curr; + NSPoint d = SPPointOnLine(curr, next, t); + NSPoint e = SPPointOnLine(curr, next, 0.5); + + if (j==0) [funkyPath moveToPoint:a]; + [funkyPath lineToPoint: b]; + [funkyPath curveToPoint:d controlPoint1:SPPointOnLine(b, c, kappa) controlPoint2:SPPointOnLine(d, c, kappa)]; + [funkyPath lineToPoint: e]; + } + } else { + //highlight disconnected snippet parts (or single line snippet) + for (NSUInteger j=0; j