我正在使用自定义 MKOverlay/MKOverlayView 用我自己的异步加载的图 block 完全覆盖 Google basemap 。当我收到对覆盖 View 的 canDrawMapRect:zoomScale: 调用(并在这种情况下返回 FALSE)时,我遵循请求卸载图 block 的模式,然后调用 setNeedsDisplayInMapRect:zoomScale:一旦瓷砖可用。
这一切通常都有效,并且在模拟器中似乎完美运行。
但是,在设备上,我有时会在叠加层中看到一个“洞”——缺失的图 block 。
我可以看到该图 block 已被请求,并且请求已完成。我可以看到我调用了 setNeedsDisplayInMapRect:zoomScale:,并且我正在传递 canDrawMapRect 中提供的原始 。但我也可以看到,从未要求叠加层重绘该图 block (MKMapRect 和 MKZoomScale :缩放比例:canDrawMapRect:zoomScale: 和 drawMapRect:zoomScale:inContext: 都不再为该图 block 调用) .
我需要了解为什么会发生这种情况以及如何纠正它。
这是我的 MKOverlayView 子类的相关代码:
- (BOOL) canDrawMapRect: (MKMapRect) mapRect zoomScale: (MKZoomScale) zoomScale
{
NSUInteger zoomLevel = [self zoomLevelForZoomScale:zoomScale];
CGPoint mercatorPoint = [self mercatorTileOriginForMapRect:mapRect];
NSUInteger tilex = floor(mercatorPoint.x * [self worldTileWidthForZoomLevel:zoomLevel]);
NSUInteger tiley = floor(mercatorPoint.y * [self worldTileWidthForZoomLevel:zoomLevel]);
NSURL* tileUrl = [self tileURLForZoomLevel: zoomLevel tileX: tilex tileY: tiley];
ASIHTTPRequest* tileRequest = [ASIHTTPRequest requestWithURL: tileUrl];
tileRequest.downloadCache = [ASIDownloadCache sharedCache];
[tileRequest setCacheStoragePolicy:ASICachePermanentlyCacheStoragePolicy];
if ( NO == [[ASIDownloadCache sharedCache] isCachedDataCurrentForRequest: tileRequest] )
{
[tileRequest setCachePolicy: ASIAskServerIfModifiedWhenStaleCachePolicy];
tileRequest.delegate = self;
tileRequest.userInfo = [NSDictionary dictionaryWithObjectsAndKeys:
[NSValue value: &mapRect withObjCType: @encode( MKMapRect )], @"mapRect",
[NSValue value: &zoomScale withObjCType: @encode( MKZoomScale )], @"zoomScale",
[NSNumber numberWithInt: tilex], @"tilex",
[NSNumber numberWithInt: tiley], @"tiley",
nil];
[_tileRequestStack addOperation: tileRequest];
NSLog( @"canDrawMapRect: %d, %d - REQUESTING", tilex, tiley );
return NO;
}
NSLog( @"canDrawMapRect: %d, %d - READY", tilex, tiley );
return YES;
}
- (void) drawMapRect: (MKMapRect) mapRect zoomScale: (MKZoomScale) zoomScale inContext: (CGContextRef) context
{
NSUInteger zoomLevel = [self zoomLevelForZoomScale:zoomScale];
CGPoint mercatorPoint = [self mercatorTileOriginForMapRect:mapRect];
NSUInteger tilex = floor(mercatorPoint.x * [self worldTileWidthForZoomLevel:zoomLevel]);
NSUInteger tiley = floor(mercatorPoint.y * [self worldTileWidthForZoomLevel:zoomLevel]);
NSLog( @"drawMapRect: %d, %d", tilex, tiley );
NSURL* tileUrl = [self tileURLForZoomLevel: zoomLevel tileX: tilex tileY: tiley];
NSData* tileData = [[ASIDownloadCache sharedCache] cachedResponseDataForURL: tileUrl];
UIGraphicsPushContext(context);
if ( tileData != nil )
{
UIImage* img = [UIImage imageWithData: tileData];
if ( img != nil )
{
[img drawInRect: [self rectForMapRect: mapRect] blendMode: kCGBlendModeNormal alpha: 1.0 ];
}
else
{
NSLog( @"oops - no image" );
}
CGSize s = CGContextConvertSizeToUserSpace( context, CGSizeMake( 40, 1 ));
UIFont* f = [UIFont systemFontOfSize: s.width];
[[UIColor blackColor] setFill];
[[NSString stringWithFormat: @"%d,%d", tilex, tiley] drawInRect: [self rectForMapRect: mapRect] withFont: f];
}
UIGraphicsPopContext();
}
- (void) requestFinished: (ASIHTTPRequest *) tileRequest
{
NSValue* mapRectValue = [tileRequest.userInfo objectForKey: @"mapRect"];
MKMapRect mapRect; [mapRectValue getValue: &mapRect];
NSValue *zoomScaleValue = [tileRequest.userInfo objectForKey:@"zoomScale"];
MKZoomScale zoomScale; [zoomScaleValue getValue: &zoomScale];
NSLog( @"requestFinished: %d, %d, %lf",
[[tileRequest.userInfo objectForKey:@"tilex"] intValue],
[[tileRequest.userInfo objectForKey:@"tiley"] intValue],
zoomScale );
[self setNeedsDisplayInMapRect: mapRect zoomScale: zoomScale];
}
最佳答案
我遇到的问题与此处描述的问题非常相似。在我的例子中,我无法重现所需的行为(在 http://developer.apple.com/library/ios/documentation/MapKit/Reference/MKOverlayView_class/Reference/Reference.html#//apple_ref/occ/instm/MKOverlayView/setNeedsDisplayInMapRect:zoomScale 中描述),即使是最简单的代码也是如此:
- (BOOL)canDrawMapRect:(MKMapRect)mapRect zoomScale:(MKZoomScale)zoomScale {
NSLog(@"This should trace forever");
[self setNeedsDisplayInMapRect:mapRect zoomScale:zoomScale];
return NO;
}
或更接近我的原始代码:
- (BOOL)canDrawMapRect:(MKMapRect)mapRect zoomScale:(MKZoomScale)zoomScale {
NSLog(@"This should trace forever");
[SomeAsynchronousRequestWithCompletionHandler:^{
[self setNeedsDisplayInMapRect:mapRect zoomScale:zoomScale];
}];
return NO;
}
在这两种情况下,setNeedsDisplayInMapRect:zoomScale: 从未被调用过一次。
情况发生了变化,当我开始在 dispatch_async 中运行 setNeedsDisplayInMapRect:zoomScale: 时,dispatch_async 被调度到 canDrawMapRect 运行所在的同一队列,例如:
- (BOOL)canDrawMapRect:(MKMapRect)mapRect zoomScale:(MKZoomScale)zoomScale {
dispatch_queue_t queue = dispatch_get_current_queue();
NSLog(@"This should trace forever");
dispatch_async(queue, ^{
[self setNeedsDisplayInMapRect:mapRect zoomScale:zoomScale];
});
return NO;
}
或包含异步作业:
- (BOOL)canDrawMapRect:(MKMapRect)mapRect zoomScale:(MKZoomScale)zoomScale {
NSLog(@"This should trace forever");
dispatch_queue_t queue = dispatch_get_current_queue();
[SomeAsynchronousRequestWithCompletionHandler:^{
dispatch_async(queue, ^{
[self setNeedsDisplayInMapRect:mapRect zoomScale:zoomScale];
});
}];
return NO;
}
使用 dispatch_async - 我可以看到 “This should trace forever” 字符串被无休止地跟踪。我原来的问题也完全消失了。
稍后更新:目前,我使用 dispatch_get_main_queue() 来调用 setNeedsDisplayInMapRect:zoomScale: 就像
- (BOOL)canDrawMapRect:(MKMapRect)mapRect zoomScale:(MKZoomScale)zoomScale {
NSLog(@"This should trace forever");
[SomeAsynchronousRequestWithCompletionHandler:^{
dispatch_async(dispatch_get_main_queue(), ^{
[self setNeedsDisplayInMapRect:mapRect zoomScale:zoomScale];
});
}];
return NO;
}
关于ios - setNeedsDisplayInMapRect 不触发新的 drawMapRect : call,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10128447/
我正在尝试测试是否存在表单。我是Rails新手。我的new.html.erb_spec.rb文件的内容是:require'spec_helper'describe"messages/new.html.erb"doit"shouldrendertheform"dorender'/messages/new.html.erb'reponse.shouldhave_form_putting_to(@message)with_submit_buttonendendView本身,new.html.erb,有代码:当我运行rspec时,它失败了:1)messages/new.html.erbshou
我怎样才能完成http://php.net/manual/en/function.call-user-func-array.php在ruby中?所以我可以这样做:classAppdeffoo(a,b)putsa+benddefbarargs=[1,2]App.send(:foo,args)#doesn'tworkApp.send(:foo,args[0],args[1])#doeswork,butdoesnotscaleendend 最佳答案 尝试分解数组App.send(:foo,*args)
使用带有Rails插件的vim,您可以创建一个迁移文件,然后一次性打开该文件吗?textmate也可以这样吗? 最佳答案 你可以使用rails.vim然后做类似的事情::Rgeneratemigratonadd_foo_to_bar插件将打开迁移生成的文件,这正是您想要的。我不能代表textmate。 关于ruby-使用VimRails,您可以创建一个新的迁移文件并一次性打开它吗?,我们在StackOverflow上找到一个类似的问题: https://sta
请帮助我理解范围运算符...和..之间的区别,作为Ruby中使用的“触发器”。这是PragmaticProgrammersguidetoRuby中的一个示例:a=(11..20).collect{|i|(i%4==0)..(i%3==0)?i:nil}返回:[nil,12,nil,nil,nil,16,17,18,nil,20]还有:a=(11..20).collect{|i|(i%4==0)...(i%3==0)?i:nil}返回:[nil,12,13,14,15,16,17,18,nil,20] 最佳答案 触发器(又名f/f)是
我正在学习Rails,并阅读了关于乐观锁的内容。我已将类型为integer的lock_version列添加到我的articles表中。但现在每当我第一次尝试更新记录时,我都会收到StaleObjectError异常。这是我的迁移:classAddLockVersionToArticle当我尝试通过Rails控制台更新文章时:article=Article.first=>#我这样做:article.title="newtitle"article.save我明白了:(0.3ms)begintransaction(0.3ms)UPDATE"articles"SET"title"='dwdwd
这里有一个很好的答案解释了如何在Ruby中下载文件而不将其加载到内存中:https://stackoverflow.com/a/29743394/4852737require'open-uri'download=open('http://example.com/image.png')IO.copy_stream(download,'~/image.png')我如何验证下载文件的IO.copy_stream调用是否真的成功——这意味着下载的文件与我打算下载的文件完全相同,而不是下载一半的损坏文件?documentation说IO.copy_stream返回它复制的字节数,但是当我还没有下
我有一个rubyonrails应用程序。我按照facebook的说明添加了一个像素。但是,要跟踪转化,Facebook要求您将页面置于达到预期结果时出现的转化中。即,如果我想显示客户已注册,我会将您注册后转到的页面作为成功对象进行跟踪。我的问题是,当客户注册时,在我的应用程序中没有登陆页面。该应用程序将用户带回主页。它在主页上显示了一条消息,所以我想看看是否有一种方法可以跟踪来自Controller操作而不是实际页面的转化。我需要计数的Action没有页面,它们是ControllerAction。是否有任何人都知道的关于如何执行此操作的gem、文档或最佳实践?这是进入布局文件的像素
我正在尝试解析一个文本文件,该文件每行包含可变数量的单词和数字,如下所示:foo4.500bar3.001.33foobar如何读取由空格而不是换行符分隔的文件?有什么方法可以设置File("file.txt").foreach方法以使用空格而不是换行符作为分隔符? 最佳答案 接受的答案将slurp文件,这可能是大文本文件的问题。更好的解决方案是IO.foreach.它是惯用的,将按字符流式传输文件:File.foreach(filename,""){|string|putsstring}包含“thisisanexample”结果的
给定以下方法:defsome_method:valueend以下语句按我的预期工作:some_method||:other#=>:valuex=some_method||:other#=>:value但是下面语句的行为让我感到困惑:some_method=some_method||:other#=>:other它按预期创建了一个名为some_method的局部变量,随后对some_method的调用返回该局部变量的值。但为什么它分配:other而不是:value呢?我知道这可能不是一件明智的事情,并且可以看出它可能有多么模棱两可,但我认为应该在考虑作业之前评估作业的右侧...我已经在R
有人知道在发布新版本的Ruby和Rails时收到电子邮件的方法吗?他们有邮件列表,RubyonRails有一个推特,但我不想听到那些随之而来的喧嚣,我只想知道什么时候发布新版本,尤其是那些有安全修复的版本。 最佳答案 从therailsblog获取提要.http://weblog.rubyonrails.org/feed/atom.xml 关于ruby-on-rails-如何在发布新的Ruby或Rails版本时收到通知?,我们在StackOverflow上找到一个类似的问题: