我有一些触摸处理程序,它响应了一个视图的点击,我已经绘制了一些属性文本。通过这个,我已经到了我有一个CTRunRef
(和相关行)以及该运行中的字形数。
我无法轻易弄清楚,我是如何拍摄这些字形的,并且,鉴于我的属性字符串,将其映射到字符串中的字符。
具体问题是我想知道用户在视图中点击了什么单词,因此我可以处理该单词是否为URL并触发自定义委托方法,以便我可以用它打开Web视图。我有所有可能的子串,我只是不知道如何映射用户点击特定子串的位置。
非常感谢任何帮助。
UPDATE :我实际上是以不同的方式完成了它,根据另一个人的建议离开stackoverflow。基本上我所做的就是设置一个自定义属性@"MyAppLinkAddress"
,其中包含我在将字符串转换为属性字符串时找到的URL的值。这是在我绘制字符串之前发生的。因此,当敲击事件发生时,我只检查该属性是否存在,如果存在,则调用我的委托方法,如果不存在,则忽略它。这是我现在喜欢的方式,但是我要打开这个问题多了几天,如果有人能拿出答案的话,我很高兴接受它,如果它是一个有效的解决方案,那么其他一些或许可以在将来的某个时候找到这些信息。
答案 0 :(得分:7)
正如我在更新中所提到的,我选择了另一条路线。相反,我有想法在属性字符串中使用自定义属性来指定我的链接,因为无论如何我在创建时都有它。所以我做到了。然后在我的触摸处理程序中,当点击一个运行时,我检查该运行是否具有该属性,如果是,则用它来调用我的委托。从那里我很高兴加载带有该URL的webview。
编辑:下面是代码片段,解释了我在这个答案中所做的事情。享受。
// When creating the attribute on your text store. Assumes you have the URL already.
// Filled in for convenience
NSRange urlRange = [tmpString rangeOfString:@"http://www.foo.com/"];
[self.textStore addAttribute:(NSString*)kCTForegroundColorAttributeName value:(id)[UIColor blueColor].CGColor range:urlRange];
[self.textStore addAttribute:@"CustomLinkAddress" value:urlString range:urlRange];
...然后
// Touch handling code — Uses gesture recognizers, not old school touch handling.
// This is just a dump of code actually in use, read through it, ask questions if you
// don't understand it. I'll do my best to put it in context.
- (void)receivedTap:(UITapGestureRecognizer*)tapRecognizer
{
CGPoint point = [tapRecognizer locationInView:self];
if(CGRectContainsPoint(textRect, point))
{
CGContextRef context = UIGraphicsGetCurrentContext();
point.y = CGRectGetHeight(self.contentView.bounds) - kCellNameLabelHeight - point.y;
CFArrayRef lines = CTFrameGetLines(ctframe);
CFIndex lineCount = CFArrayGetCount(lines);
CGPoint origins[lineCount];
CTFrameGetLineOrigins(ctframe, CFRangeMake(0, 0), origins);
for(CFIndex idx = 0; idx < lineCount; idx++)
{
CTLineRef line = CFArrayGetValueAtIndex(lines, idx);
CGRect lineBounds = CTLineGetImageBounds(line, context);
lineBounds.origin.y += origins[idx].y;
if(CGRectContainsPoint(lineBounds, point))
{
CFArrayRef runs = CTLineGetGlyphRuns(line);
for(CFIndex j = 0; j < CFArrayGetCount(runs); j++)
{
CTRunRef run = CFArrayGetValueAtIndex(runs, j);
NSDictionary* attributes = (NSDictionary*)CTRunGetAttributes(run);
NSString* urlString = [attributes objectForKey:@"CustomLinkAddress"];
if(urlString && ![urlString isEqualToString:@""])
{
[self.delegate didReceiveURL:[NSURL URLWithString:urlString]];
UIGraphicsPopContext();
return;
}
}
}
}
UIGraphicsPopContext();
}
}
答案 1 :(得分:3)
找到分接的行后,您可以通过调用CTLineGetStringIndexForPosition()
来索取字符串中的索引。没有必要访问个别运行。