1E67E6FD0F3C052000E68F1B /* PreferencesPathsArrayController.m in Sources */ = {isa = PBXBuildFile; fileRef = 1E67E6FC0F3C052000E68F1B /* PreferencesPathsArrayController.m */; };
1E6B5947116106FE001189D2 /* LoggingController.m in Sources */ = {isa = PBXBuildFile; fileRef = 1E6B5946116106FE001189D2 /* LoggingController.m */; };
1E6B594C11610993001189D2 /* Log.xib in Resources */ = {isa = PBXBuildFile; fileRef = 1E6B594A11610993001189D2 /* Log.xib */; };
- 1E7188690D839F6300969277 /* BSSourceView.mm in Sources */ = {isa = PBXBuildFile; fileRef = 1E7188650D839F6300969277 /* BSSourceView.mm */; };
+ 1E7188690D839F6300969277 /* BSSourceView.m in Sources */ = {isa = PBXBuildFile; fileRef = 1E7188650D839F6300969277 /* BSSourceView.m */; };
1E822CDD0DA28AC30027A23F /* Breakpoint.m in Sources */ = {isa = PBXBuildFile; fileRef = 1E822CDC0DA28AC30027A23F /* Breakpoint.m */; };
1E87EFD1232B800900FF6348 /* BreakpointManager.m in Sources */ = {isa = PBXBuildFile; fileRef = 1E4C7AF80DA401C7000A9DC7 /* BreakpointManager.m */; };
1E87EFD4232B806D00FF6348 /* Breakpoint.m in Sources */ = {isa = PBXBuildFile; fileRef = 1E822CDC0DA28AC30027A23F /* Breakpoint.m */; };
1E6B5945116106FE001189D2 /* LoggingController.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = LoggingController.h; path = Source/LoggingController.h; sourceTree = "<group>"; };
1E6B5946116106FE001189D2 /* LoggingController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = LoggingController.m; path = Source/LoggingController.m; sourceTree = "<group>"; };
1E7188640D839F6300969277 /* BSSourceView.h */ = {isa = PBXFileReference; explicitFileType = sourcecode.c.h; fileEncoding = 4; name = BSSourceView.h; path = Source/BSSourceView.h; sourceTree = "<group>"; };
- 1E7188650D839F6300969277 /* BSSourceView.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = BSSourceView.mm; path = Source/BSSourceView.mm; sourceTree = "<group>"; };
+ 1E7188650D839F6300969277 /* BSSourceView.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = BSSourceView.m; path = Source/BSSourceView.m; sourceTree = "<group>"; };
1E822CDB0DA28AC30027A23F /* Breakpoint.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Breakpoint.h; path = Source/Breakpoint.h; sourceTree = "<group>"; };
1E822CDC0DA28AC30027A23F /* Breakpoint.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; name = Breakpoint.m; path = Source/Breakpoint.m; sourceTree = "<group>"; };
1E87EFD2232B805800FF6348 /* AppKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AppKit.framework; path = System/Library/Frameworks/AppKit.framework; sourceTree = SDKROOT; };
isa = PBXGroup;
children = (
1E7188640D839F6300969277 /* BSSourceView.h */,
- 1E7188650D839F6300969277 /* BSSourceView.mm */,
+ 1E7188650D839F6300969277 /* BSSourceView.m */,
1EDA9CF612DD13B300596211 /* BSLineNumberRulerView.h */,
1EDA9CF712DD13B300596211 /* BSLineNumberRulerView.mm */,
1E1181481319805E003BFEF1 /* BSSourceViewTextView.h */,
1E02C5F60C610724006F1752 /* DebuggerController.m in Sources */,
1E35FC760C6579CA0030F527 /* NSXMLElementAdditions.m in Sources */,
1E3F9D941CBAB57B005D896B /* PreferenceNames.m in Sources */,
- 1E7188690D839F6300969277 /* BSSourceView.mm in Sources */,
+ 1E7188690D839F6300969277 /* BSSourceView.m in Sources */,
1E822CDD0DA28AC30027A23F /* Breakpoint.m in Sources */,
1E4C7AF90DA401C7000A9DC7 /* BreakpointManager.m in Sources */,
1EFF70C30DFDC018006B9D33 /* BreakpointController.m in Sources */,
*/
#import <Cocoa/Cocoa.h>
-#include <vector>
@class BSSourceView;
// http://www.noodlesoft.com/blog/2008/10/05/displaying-line-numbers-with-nstextview/
// However, all code is original.
@interface BSLineNumberRulerView : NSRulerView
-{
- @private
- BSSourceView* sourceView_; // Weak, owns this.
-
- // A vector (thus 0-based) map of line numbers (indices) to character indices
- // in the text storage.
- std::vector<NSUInteger> lineIndex_;
-}
// Designated initializer.
-- (id)initWithSourceView:(BSSourceView*)sourceView;
+- (instancetype)initWithSourceView:(BSSourceView*)sourceView;
// Performs layout and redraws the line number view.
- (void)performLayout;
#import "BSLineNumberRulerView.h"
#include <algorithm>
+#include <vector>
#import "Breakpoint.h"
#import "BSSourceView.h"
// }}
+@implementation BSLineNumberRulerView {
+ BSSourceView* _sourceView; // Weak, owns this.
-@implementation BSLineNumberRulerView
+ // A vector (thus 0-based) map of line numbers (indices) to character indices
+ // in the text storage.
+ std::vector<NSUInteger> _lineIndex;
+}
-- (id)initWithSourceView:(BSSourceView*)sourceView
+- (instancetype)initWithSourceView:(BSSourceView*)sourceView
{
if (self = [super initWithScrollView:[sourceView scrollView]
orientation:NSVerticalRuler]) {
- sourceView_ = sourceView;
- [self setClientView:[[sourceView_ scrollView] documentView]];
+ _sourceView = sourceView;
+ [self setClientView:[[_sourceView scrollView] documentView]];
[self setRuleThickness:kDefaultWidth];
}
return self;
- (void)awakeFromNib
{
- [self setClientView:[[sourceView_ scrollView] documentView]];
+ [self setClientView:[[_sourceView scrollView] documentView]];
[self setRuleThickness:kDefaultWidth];
}
toPoint:NSMakePoint(NSMaxX(rect), NSMaxY(rect))];
// Get some common elements of the source view.
- NSTextView* textView = [sourceView_ textView];
+ NSTextView* textView = [_sourceView textView];
NSLayoutManager* layoutManager = [textView layoutManager];
NSTextContainer* textContainer = [textView textContainer];
NSRect visibleRect = [[[self scrollView] contentView] bounds];
// Load any markers. The superview takes care of filtering out for just the
// curently displayed file.
- NSSet<NSNumber*>* markers = [sourceView_ markers];
+ NSSet<NSNumber*>* markers = [_sourceView markers];
// Go through the lines.
const NSRange kNullRange = NSMakeRange(NSNotFound, 0);
const CGFloat yOffset = [textView textContainerInset].height;
- const size_t lineCount = lineIndex_.size();
+ const size_t lineCount = _lineIndex.size();
std::vector<NSUInteger>::iterator element =
- std::lower_bound(lineIndex_.begin(),
- lineIndex_.end(),
+ std::lower_bound(_lineIndex.begin(),
+ _lineIndex.end(),
characterRange.location);
- for (NSUInteger line = std::distance(lineIndex_.begin(), element);
+ for (NSUInteger line = std::distance(_lineIndex.begin(), element);
line < lineCount; ++line) {
- NSUInteger firstCharacterIndex = lineIndex_[line];
+ NSUInteger firstCharacterIndex = _lineIndex[line];
// Stop after iterating past the end of the visible range.
if (firstCharacterIndex > NSMaxRange(characterRange))
break;
if ([markers containsObject:@(lineNumber)]) {
[self drawBreakpointInRect:drawRect];
}
- if (sourceView_.markedLine == lineNumber) {
+ if (_sourceView.markedLine == lineNumber) {
[self drawProgramCounterInRect:drawRect];
}
}
[self computeLineIndex];
// Determine the width of the ruler based on the line count.
- if (lineIndex_.empty()) {
+ if (_lineIndex.empty()) {
[self setRuleThickness:kDefaultWidth];
} else {
- NSUInteger lastElement = lineIndex_.back() + 1;
+ NSUInteger lastElement = _lineIndex.back() + 1;
NSAttributedString* lastElementString = [self attributedStringForLineNumber:lastElement];
NSSize boundingSize = [lastElementString size];
[self setRuleThickness:std::max(kDefaultWidth, boundingSize.width)];
- (NSUInteger)lineNumberAtPoint:(NSPoint)point
{
// Get some common elements of the source view.
- NSTextView* textView = [sourceView_ textView];
+ NSTextView* textView = [_sourceView textView];
NSLayoutManager* layoutManager = [textView layoutManager];
NSTextContainer* textContainer = [textView textContainer];
NSRect visibleRect = [[[self scrollView] contentView] bounds];
const CGFloat kWidth = NSWidth([self bounds]);
const NSRange kNullRange = NSMakeRange(NSNotFound, 0);
- const size_t lineCount = lineIndex_.size();
+ const size_t lineCount = _lineIndex.size();
for (NSUInteger line = 0; line < lineCount; ++line) {
- NSUInteger firstCharacterIndex = lineIndex_[line];
+ NSUInteger firstCharacterIndex = _lineIndex[line];
NSUInteger rectCount;
NSRectArray frameRects =
point = [self convertPoint:point fromView:nil];
NSUInteger line = [self lineNumberAtPoint:point];
if (line != NSNotFound)
- [sourceView_.delegate gutterClickedAtLine:line forFile:sourceView_.file];
+ [_sourceView.delegate gutterClickedAtLine:line forFile:_sourceView.file];
}
// Private /////////////////////////////////////////////////////////////////////
*/
- (void)computeLineIndex
{
- lineIndex_.clear();
+ _lineIndex.clear();
- NSString* text = [[sourceView_ textView] string];
+ NSString* text = [[_sourceView textView] string];
NSUInteger stringLength = [text length];
NSUInteger index = 0;
while (index < stringLength) {
- lineIndex_.push_back(index);
+ _lineIndex.push_back(index);
index = NSMaxRange([text lineRangeForRange:NSMakeRange(index, 0)]);
}
- if (lineIndex_.empty())
+ if (_lineIndex.empty())
return;
NSUInteger lineEnd, contentEnd;
[text getLineStart:NULL
end:&lineEnd
contentsEnd:&contentEnd
- forRange:NSMakeRange(lineIndex_.back(), 0)];
+ forRange:NSMakeRange(_lineIndex.back(), 0)];
if (contentEnd < lineEnd)
- lineIndex_.push_back(index);
+ _lineIndex.push_back(index);
}
/**
//
// Rather than setting the string of the text view directly, use the provided
// methods to load from a file path or to load a string as a virtual file.
-@interface BSSourceView : NSView {
- @private
- BSSourceViewTextView* textView_;
- BSLineNumberRulerView* ruler_;
- NSScrollView* scrollView_;
-
- // Line numbers to mark.
- NSSet<NSNumber*>* markers_;
-
- NSString* file_;
- NSUInteger markedLine_;
-
- id<BSSourceViewDelegate> __weak delegate_;
-}
+@interface BSSourceView : NSView
@property (nonatomic, readonly) NSTextView* textView;
@property (nonatomic, readonly) NSScrollView* scrollView;
-@property (nonatomic, retain) NSSet<NSNumber*>* markers;
-@property (nonatomic, retain) NSString* file;
+@property (nonatomic, copy) NSSet<NSNumber*>* markers;
+@property (nonatomic, copy) NSString* file;
@property (nonatomic, assign) NSUInteger markedLine;
@property (nonatomic, weak) id delegate;
- (void)setPlainTextStringFromFile:(NSString*)filePath;
@end
-@implementation BSSourceView
+@implementation BSSourceView {
+ BSSourceViewTextView* _textView;
+ BSLineNumberRulerView* _ruler;
+ NSScrollView* _scrollView;
-@synthesize textView = textView_;
-@synthesize scrollView = scrollView_;
-@synthesize markers = markers_;
-@synthesize markedLine = markedLine_;
-@synthesize delegate = delegate_;
-@synthesize file = file_;
+ // Line numbers to mark.
+ NSSet<NSNumber*>* _markers;
+
+ NSString* _file;
+}
-/**
- * Initializes the source view with the path of a file
- */
- (id)initWithFrame:(NSRect)frame
{
if (self = [super initWithFrame:frame]) {
[self setupViews];
- [[NSNotificationCenter defaultCenter]
- addObserver:self
- selector:@selector(errorHighlightingFile:)
- name:NSFileHandleReadToEndOfFileCompletionNotification
- object:nil
- ];
}
return self;
}
- (void)setMarkers:(NSSet*)markers {
- markers_ = [markers copy];
- [ruler_ setNeedsDisplay:YES];
+ _markers = [markers copy];
+ [_ruler setNeedsDisplay:YES];
}
- (void)setMarkedLine:(NSUInteger)markedLine {
- markedLine_ = markedLine;
- [ruler_ setNeedsDisplay:YES];
- [textView_ setNeedsDisplay:YES];
+ _markedLine = markedLine;
+ [_ruler setNeedsDisplay:YES];
+ [_textView setNeedsDisplay:YES];
}
/**
*/
- (void)setFile:(NSString*)f
{
- file_ = f;
+ _file = [f copy];
if (![[NSFileManager defaultManager] fileExistsAtPath:f]) {
- [textView_ setString:@""];
+ [_textView setString:@""];
return;
}
*/
- (void)setString:(NSString*)source asFile:(NSString*)path
{
- file_ = path;
+ _file = [path copy];
// Write the source out as a temporary file so it can be highlighted.
NSError* error = nil;
NSString* tmpPath = [NSTemporaryDirectory() stringByAppendingPathComponent:@"MacGDBpHighlighter"];
[source writeToFile:tmpPath atomically:NO encoding:NSUTF8StringEncoding error:&error];
if (error) {
- [textView_ setString:source];
+ [_textView setString:source];
return;
}
*/
- (void)scrollToLine:(NSUInteger)line
{
- if ([[textView_ textStorage] length] == 0)
+ if ([[_textView textStorage] length] == 0)
return;
// go through the document until we find the NSRange for the line we want
NSUInteger rangeIndex = 0;
for (NSUInteger i = 0; i < line; i++) {
- rangeIndex = NSMaxRange([[textView_ string] lineRangeForRange:NSMakeRange(rangeIndex, 0)]);
+ rangeIndex = NSMaxRange([[_textView string] lineRangeForRange:NSMakeRange(rangeIndex, 0)]);
}
// now get the true start/end markers for it
NSUInteger lineStart, lineEnd;
- [[textView_ string] getLineStart:&lineStart
+ [[_textView string] getLineStart:&lineStart
end:NULL
contentsEnd:&lineEnd
forRange:NSMakeRange(rangeIndex - 1, 0)];
- [textView_ scrollRangeToVisible:[[textView_ string]
+ [_textView scrollRangeToVisible:[[_textView string]
lineRangeForRange:NSMakeRange(lineStart, lineEnd - lineStart)]];
}
- (void)setupViews
{
// Create the scroll view.
- scrollView_ = [[NSScrollView alloc] initWithFrame:[self bounds]];
- [scrollView_ setHasHorizontalScroller:YES];
- [scrollView_ setHasVerticalScroller:YES];
- [scrollView_ setAutohidesScrollers:YES];
- [scrollView_ setBorderType:NSBezelBorder];
- [scrollView_ setAutoresizingMask:(NSViewWidthSizable | NSViewHeightSizable)];
- [[scrollView_ contentView] setAutoresizesSubviews:YES];
- [self addSubview:scrollView_];
+ _scrollView = [[NSScrollView alloc] initWithFrame:[self bounds]];
+ [_scrollView setHasHorizontalScroller:YES];
+ [_scrollView setHasVerticalScroller:YES];
+ [_scrollView setAutohidesScrollers:YES];
+ [_scrollView setBorderType:NSBezelBorder];
+ [_scrollView setAutoresizingMask:(NSViewWidthSizable | NSViewHeightSizable)];
+ [[_scrollView contentView] setAutoresizesSubviews:YES];
+ [self addSubview:_scrollView];
// add the text view to the scroll view
NSRect textFrame;
textFrame.origin = NSMakePoint(0.0, 0.0);
- textFrame.size = [scrollView_ contentSize];
- textView_ = [[BSSourceViewTextView alloc] initWithFrame:textFrame];
- [textView_ setSourceView:self];
- [textView_ setEditable:NO];
- [textView_ setFont:[[self class] sourceFont]];
- [textView_ setHorizontallyResizable:YES];
- [textView_ setVerticallyResizable:YES];
- [textView_ setMinSize:textFrame.size];
- [textView_ setMaxSize:NSMakeSize(FLT_MAX, FLT_MAX)];
- [[textView_ textContainer] setContainerSize:NSMakeSize(FLT_MAX, FLT_MAX)];
- [[textView_ textContainer] setWidthTracksTextView:NO];
- [[textView_ textContainer] setHeightTracksTextView:NO];
- [textView_ setAutoresizingMask:NSViewNotSizable];
- [scrollView_ setDocumentView:textView_];
+ textFrame.size = [_scrollView contentSize];
+ _textView = [[BSSourceViewTextView alloc] initWithFrame:textFrame];
+ [_textView setSourceView:self];
+ [_textView setEditable:NO];
+ [_textView setFont:[[self class] sourceFont]];
+ [_textView setHorizontallyResizable:YES];
+ [_textView setVerticallyResizable:YES];
+ [_textView setMinSize:textFrame.size];
+ [_textView setMaxSize:NSMakeSize(FLT_MAX, FLT_MAX)];
+ [[_textView textContainer] setContainerSize:NSMakeSize(FLT_MAX, FLT_MAX)];
+ [[_textView textContainer] setWidthTracksTextView:NO];
+ [[_textView textContainer] setHeightTracksTextView:NO];
+ [_textView setAutoresizingMask:NSViewNotSizable];
+ [_scrollView setDocumentView:_textView];
// Set up the ruler.
- ruler_ = [[BSLineNumberRulerView alloc] initWithSourceView:self];
- [scrollView_ setVerticalRulerView:ruler_];
- [scrollView_ setHasHorizontalRuler:NO];
- [scrollView_ setHasVerticalRuler:YES];
- [scrollView_ setRulersVisible:YES];
-
- NSArray* types = [NSArray arrayWithObject:NSFilenamesPboardType];
- [self registerForDraggedTypes:types];
+ _ruler = [[BSLineNumberRulerView alloc] initWithSourceView:self];
+ [_scrollView setVerticalRulerView:_ruler];
+ [_scrollView setHasHorizontalRuler:NO];
+ [_scrollView setHasVerticalRuler:YES];
+ [_scrollView setRulersVisible:YES];
+
+ [self registerForDraggedTypes:@[ NSFilenamesPboardType ]];
}
NSString* ColorHEXStringINIDirective(NSString* directive, NSColor* color) {
}
if (source) {
- [[textView_ textStorage] setAttributedString:source];
+ [[_textView textStorage] setAttributedString:source];
} else {
[self setPlainTextStringFromFile:filePath];
}
- [ruler_ performLayout];
+ [_ruler performLayout];
if (handler) {
handler();
error:&error];
if (error) {
NSLog(@"Error reading file at %@: %@", filePath, error);
- if ([delegate_ respondsToSelector:@selector(error:whileHighlightingFile:)]) {
- [delegate_ error:error whileHighlightingFile:filePath];
+ if ([_delegate respondsToSelector:@selector(error:whileHighlightingFile:)]) {
+ [_delegate error:error whileHighlightingFile:filePath];
}
return;
}
- [textView_ setString:contents];
+ [_textView setString:contents];
}
// Drag Handlers ///////////////////////////////////////////////////////////////
@implementation BSSourceViewTextView
-@synthesize sourceView = sourceView_;
-
- (void)drawRect:(NSRect)rect
{
[super drawRect:rect];
NSRange fragRange;
NSRect fragRect = [layoutManager lineFragmentRectForGlyphAtIndex:i
effectiveRange:&fragRange];
- if ([sourceView_ markedLine] == line) {
+ if ([_sourceView markedLine] == line) {
fragRect = [self convertRect:fragRect fromView:self];
fragRect.origin.x = rect.origin.x; // Flush all the way to the edge.
[[[NSColor redColor] colorWithAlphaComponent:0.25] set];