WordDetectLabel.h
#import <UIKit/UIKit.h>
NS_ASSUME_NONNULL_BEGIN
@interface WordDetectLabel : UILabel
@end
NS_ASSUME_NONNULL_END
WordDetectLabel.m
#import "WordDetectLabel.h"
@interface WordDetectLabel()
@property (nonatomic, strong) UILabel *highlightLabel; // 用于显示放大的单词
@property (nonatomic, strong) NSString *selectedWord; // 被选中的单词
@end
@implementation WordDetectLabel
// 初始化
- (instancetype)initWithFrame:(CGRect)frame {
self = [super initWithFrame:frame];
if (self) {
[self initialize];
}
return self;
}
- (void)awakeFromNib {
[super awakeFromNib];
}
- (void)initialize {
self.userInteractionEnabled = YES;
UILongPressGestureRecognizer *longPress = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(handleLongPress:)];
[self addGestureRecognizer:longPress];
}
// 布局更新时调整文本容器大小
- (void)layoutSubviews {
[super layoutSubviews];
}
// 长按手势处理
- (void)handleLongPress:(UILongPressGestureRecognizer *)gesture {
CGPoint touchPoint = [gesture locationInView:self];
if (gesture.state == UIGestureRecognizerStateBegan) {
// 更新 textStorage 数据
NSLayoutManager *layoutManager = [[NSLayoutManager alloc] init];
NSTextContainer *textContainer = [[NSTextContainer alloc] initWithSize:CGSizeZero];
NSTextStorage *textStorage;
NSMutableParagraphStyle *paragraphStyle = NSMutableParagraphStyle.new;
paragraphStyle.alignment = self.textAlignment;
// Configure textContainer
textContainer.lineFragmentPadding = 0.0;
textContainer.lineBreakMode = self.lineBreakMode;
textContainer.maximumNumberOfLines = self.numberOfLines;
CGPoint locationOfTouchInLabel = touchPoint;
CGSize labelSize = gesture.view.bounds.size;
textContainer.size = self.bounds.size;
NSMutableAttributedString *attributedText = [[NSMutableAttributedString alloc] initWithAttributedString:self.attributedText];
[attributedText addAttributes:@{NSFontAttributeName: self.font, NSParagraphStyleAttributeName: paragraphStyle} range:NSMakeRange(0,self.attributedText.string.length)];
textStorage = [[NSTextStorage alloc] initWithAttributedString:attributedText];
// Configure layoutManager and textStorage
[layoutManager addTextContainer:textContainer];
[textStorage addLayoutManager:layoutManager];
CGRect textBoundingBox = [layoutManager usedRectForTextContainer:textContainer];
CGPoint textContainerOffset = CGPointMake((labelSize.width - textBoundingBox.size.width) * 0.5 - textBoundingBox.origin.x,
(labelSize.height - textBoundingBox.size.height) * 0.5 - textBoundingBox.origin.y);
CGPoint locationOfTouchInTextContainer = CGPointMake(locationOfTouchInLabel.x - textContainerOffset.x,
locationOfTouchInLabel.y - textContainerOffset.y);
NSInteger indexOfCharacter = [layoutManager characterIndexForPoint:locationOfTouchInTextContainer
inTextContainer:textContainer
fractionOfDistanceBetweenInsertionPoints:nil];
NSRange range = [self wordRangeAtIndex:indexOfCharacter inText:self.text];
if (range.location != NSNotFound) {
NSString *value = [self.text substringWithRange:range];
NSLog(@"选中的单词%@" , value);
} else {
NSLog(@"未获取到单词");
}
} else if (gesture.state == UIGestureRecognizerStateEnded || gesture.state == UIGestureRecognizerStateCancelled) {
[self removeHighlightedWord];
}
}
// 正则匹配触摸点所在的单词范围
- (NSRange)wordRangeAtIndex:(NSUInteger)index inText:(NSString *)text {
NSRange range = NSMakeRange(0, text.length);
NSRegularExpression *regex = [NSRegularExpression regularExpressionWithPattern:@"\\b\\w+\\b" options:0 error:nil];
NSArray *matches = [regex matchesInString:text options:0 range:range];
for (NSTextCheckingResult *result in matches) {
if (NSLocationInRange(index, result.range)) {
return result.range; // 返回匹配单词的范围
}
}
return NSMakeRange(NSNotFound, 0);
}
// 显示高亮的单词
- (void)showHighlightedWord:(NSString *)word atPoint:(CGPoint)point {
}
// 移除高亮显示
- (void)removeHighlightedWord {
}