我正试图在NSTextView
中获取所选范围的方向。换句话说,当您使用shift+leftarrow
和shift+rightarrow
时,所选范围是否会更改其位置或长度。我的第一个问题是selectionAffinity
表示方向,但它似乎只适用于多行选择。
如何获得所选范围的方向?
答案 0 :(得分:6)
第1步:声明属性
@property (nonatomic) NSRange lastRange;
步骤2:在TextView Delegate中,添加:
- (void) textViewDidChangeSelection:(UITextView *)textView
NSRange currentRange = NSMakeRange(textView.selectedRange.location, textView.selectedRange.length);
if (currentRange.length == 0) {
NSLog(@"Nothing selected");
_lastRange = currentRange;
}
else {
if (currentRange.location < _lastRange.location) {
NSLog(@"Selecting LEFT");
}
else {
NSLog(@"Selecting RIGHT");
}
}
}
OSX具有所需的所有功能,需要更多的工作,但这就是我想出的一个可行的,一致的解决方案。重命名是可选的,或者更确切地说......鼓励...
第1步:对NSTextView进行子类化在SubClass.h
:
#import <Cocoa/Cocoa.h>
@interface TheSelectionizer : NSTextView
@property (nonatomic) NSRange lastAnchorPoint;
@end
在SubClass.m
#import "TheSelectionizer.h"
- (void)setSelectedRange:(NSRange)charRange affinity:(NSSelectionAffinity)affinity stillSelecting:(BOOL)stillSelectingFlag {
if (charRange.length == 0) {
_lastAnchorPoint = charRange;
}
[super setSelectedRange:charRange affinity:affinity stillSelecting:stillSelectingFlag];
}
@end
第2步:实现NSTextViewDelegate
- (NSRange) textView:(NSTextView *)textView willChangeSelectionFromCharacterRange:(NSRange)oldSelectedCharRange toCharacterRange:(NSRange)newSelectedCharRange {
if (newSelectedCharRange.length != 0) {
TheSelectionizer * selectionizer = (TheSelectionizer *)textView;
int anchorStart = (int)selectionizer.lastAnchorPoint.location;
int selectionStart = (int)newSelectedCharRange.location;
int selectionLength = (int)newSelectedCharRange.length;
/*
If mouse selects left, and then a user arrows right, or the opposite, anchor point flips.
*/
int difference = anchorStart - selectionStart;
if (difference > 0 && difference != selectionLength) {
if (oldSelectedCharRange.location == newSelectedCharRange.location) {
// We were selecting left via mouse, but now we are selecting to the right via arrows
anchorStart = selectionStart;
}
else {
// We were selecting right via mouse, but now we are selecting to the left via arrows
anchorStart = selectionStart + selectionLength;
}
selectionizer.lastAnchorPoint = NSMakeRange(anchorStart, 0);
}
// Evaluate Selection Direction
if (anchorStart == selectionStart) {
if (oldSelectedCharRange.length < newSelectedCharRange.length) {
// Bigger
NSLog(@"Will select right in overall right selection");
}
else {
// Smaller
NSLog(@"Will select left in overall right selection");
}
}
else {
if (oldSelectedCharRange.length < newSelectedCharRange.length) {
// Bigger
NSLog(@"Will select left in overall left selection");
}
else {
// Smaller
NSLog(@"Will select right in overall left selection");
}
}
}
return newSelectedCharRange;
}
我发布了一个项目,以防万一有人想尝试或希望看到它。
完整&#34;项目&#34;可用HERE
答案 1 :(得分:0)
假设声明了NSRange yourPreviousRange。
//Check when NSTextView changed its value
@interface delegateAppDelegate : NSObject <NSApplicationDelegate, NSTextViewDelegate> {
NSWindow *window;
}
-(void)textDidChange:(NSNotification *)notification {
NSRange yourRange = notification.object.selectedRange;
if (yourRange.location == yourPreviousRange.location - 1 || yourRange.length == yourPreviousRange.length){
//left direction
} else if (yourRange.location == yourPreviousRange.location || yourRange.length == yourPreviousRange.length + 1){
//right direction
}
yourPreviousRange = yourRange;
}
答案 2 :(得分:0)
使用NSTextViewDelegate
方法:
如果您需要多项选择支持,请-textView:willChangeSelectionFromCharacterRange:toCharacterRange:或-textView:willChangeSelectionFromCharacterRanges:toCharacterRanges:。
请注意,如果您仅实施-textView:willChangeSelectionFromCharacterRange:toCharacterRange:
,则不允许进行多项选择。
例如,没有多选:
- (NSRange)textView:(NSTextView *)aTextView willChangeSelectionFromCharacterRange:(NSRange)oldSelectedCharRange toCharacterRange:(NSRange)newSelectedCharRange
{
if (newSelectedCharRange.length == 0 && oldSelectedCharRange.length == 0)
{
/* move the insertion point */
if (newSelectedCharRange.location < oldSelectedCharRange.location)
NSLog(@"insertion point move left");
else
NSLog(@"insertion point move right");
}
else if (newSelectedCharRange.length == 0 && oldSelectedCharRange.length != 0)
{
/* end a selection and move insertion point */
if (newSelectedCharRange.location == oldSelectedCharRange.location)
NSLog(@"insertion point at start from previous selection");
else if (newSelectedCharRange.location < oldSelectedCharRange.location)
NSLog(@"insertion point move left");
else
NSLog(@"insertion point move right");
}
else if (oldSelectedCharRange.length == 0 && newSelectedCharRange.length != 0)
{
/* start a selection */
if (newSelectedCharRange.location == oldSelectedCharRange.location)
NSLog(@"start a selection at insertion point, move right");
else if (newSelectedCharRange.location < oldSelectedCharRange.location)
NSLog(@"start a selection, move left");
else
NSLog(@"start a selection, move right");
}
else
{
if (newSelectedCharRange.location < oldSelectedCharRange.location)
NSLog(@"selection move left");
else
NSLog(@"selection move right");
}
return newSelectedCharRange;
}