我正在开发一个3标签的iPhone应用程序。我希望每个标签的视图看起来像是共享同一个地图。所以目前,我只想弄清楚如何在点击新标签时重置每个视图的MKMapView区域。 [换句话说,如果你在标签1上并在一个地方完全放大,那么点击标签2,我希望它显示相同的,放大的地图。]
为此,我在app委托中有一个MKCoordinateRegion,每个视图在它消失之前保存,并且每个视图在查看之前都会从中读取。
[换句话说,我的app委托是我的TabBarControllerDelegate,我已经覆盖了tabBarController:shouldSelectViewController:。在有人点击选项卡按钮之后,在调用新选项卡视图的viewWillAppear:函数之前调用此函数。因此,在此函数中,我将当前视图的区域保存到我的AppDelegate :: MKCoordinateRegion变量,然后调用新视图的viewWillAppear :(或viewDidLoad :)。然后,在新视图的viewWillAppear:中,我从app delegate获取MKCoordinateRegion,并将其分配给我的新视图区域。]
然而,来自MKMapKit :: setRegion:的值似乎并不一致,我不知道我是做错了什么,完全错过了什么,或者是否有其他事情发生。
我只是在做iPhone开发。 (和Obj-c等)现在大约2个星期,所以这很可能只是一个新的错误。如果是这样,我会继续道歉,因为浪费你的时间。尽管如此,这里有一些代码(我已经在我正在使用的评论中留下了......以防你自己尝试运行它):
iPhoneTestAppDelegate.h
...
@interface iPhoneTestAppDelegate : NSObject
{
UIWindow* _window;
UITabBarController* _tabBarController;
SubViewController* _subViewController;
MKCoordinateRegion _mapRegion;
}
@property (nonatomic, retain) IBOutlet UIWindow* window;
@property (nonatomic, retain) IBOutlet UITabBarController* tabBarController;
@property (nonatomic, retain) IBOutlet SubViewController* subViewController;
@property (nonatomic, assign) MKCoordinateRegion mapRegion;
@end
iPhoneAppDelegate.m
...
static CLLocationDegrees INITIAL_LATITUDE = 40.754019;
static CLLocationDegrees INITIAL_LONGITUDE = -73.973351;
static CLLocationDegrees INITIAL_SPAN_LAT_DEG = .10767;
static CLLocationDegrees INITIAL_SPAN_LONG_DEG = .109863;
...
- (void)applicationDidFinishLaunching:(UIApplication *)application
{
NSLog(@"Begin");
// initialize the delegate's region
MKCoordinateRegion region = {{0.0f, 0.0f}, {0.0f, 0.0f}};
region.center.latitude = INITIAL_LATITUDE;
region.center.longitude = INITIAL_LONGITUDE;
region.span.latitudeDelta = INITIAL_SPAN_LAT_DEG;
region.span.longitudeDelta = INITIAL_SPAN_LONG_DEG;
self.mapRegion = region;
self.tabBarController.delegate = self;
[self.window addSubview:self.tabBarController.view];
}
- (BOOL)tabBarController:(UITabBarController *)tabBarController
shouldSelectViewController:(UIViewController *)viewController
{
NSLog(@"in UITabBarControllerDelegate: shouldSelectViewController:");
if([tabBarController.viewControllers indexOfObject:viewController] !=
[tabBarController selectedIndex])
{
NSLog(@"different view selected");
BaseViewController* currView = (BaseViewController *)[tabBarController selectedViewController];
NSLog(@"%f %f %f %f",
self.mapRegion.center.latitude, self.mapRegion.center.longitude,
self.mapRegion.span.latitudeDelta, self.mapRegion.span.longitudeDelta);
NSLog(@"%f %f %f %f",
currView.mapView.region.center.latitude, currView.mapView.region.center.longitude,
currView.mapView.region.span.latitudeDelta, currView.mapView.region.span.longitudeDelta);
self.mapRegion = currView.mapView.region;
NSLog(@"%f %f %f %f",
self.mapRegion.center.latitude, self.mapRegion.center.longitude,
self.mapRegion.span.latitudeDelta, self.mapRegion.span.longitudeDelta);
}
else
NSLog(@"same view selected");
return YES;
}
BaseViewController.m
...
- (void)viewDidLoad
{
[super viewDidLoad];
NSLog(@"Base: viewDidLoad");
iPhoneTestAppDelegate* appDelegate = (iPhoneTestAppDelegate *)
[[UIApplication sharedApplication] delegate];
[self.mapView setDelegate:self];
//[self.mapView setRegion:appDelegate.mapRegion animated:YES];
[self.mapView setRegion:[self.mapView regionThatFits:appDelegate.mapRegion]];
NSLog(@"---------------------");
NSLog(@"%f %f %f %f",
appDelegate.mapRegion.center.latitude, appDelegate.mapRegion.center.longitude,
appDelegate.mapRegion.span.latitudeDelta, appDelegate.mapRegion.span.longitudeDelta);
NSLog(@"---------------------");
NSLog(@"%f %f %f %f",
self.mapView.region.center.latitude, self.mapView.region.center.longitude,
self.mapView.region.span.latitudeDelta, self.mapView.region.span.longitudeDelta);
NSLog(@"---------------------");
}
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
NSLog(@"Base: viewWillAppear");
iPhoneTestAppDelegate* appDelegate = (iPhoneTestAppDelegate *)
[[UIApplication sharedApplication] delegate];
//[self.mapView setRegion:appDelegate.mapRegion animated:YES];
[self.mapView setRegion:[self.mapView regionThatFits:appDelegate.mapRegion]];
NSLog(@"*********************");
NSLog(@"%f %f %f %f",
appDelegate.mapRegion.center.latitude, appDelegate.mapRegion.center.longitude,
appDelegate.mapRegion.span.latitudeDelta, appDelegate.mapRegion.span.longitudeDelta);
NSLog(@"*********************");
NSLog(@"%f %f %f %f",
self.mapView.region.center.latitude, self.mapView.region.center.longitude,
self.mapView.region.span.latitudeDelta, self.mapView.region.span.longitudeDelta);
NSLog(@"*********************");
}
...
现在,当我运行它时,我注意到的第一件事是当调用初始视图的viewDidLoad:时,委托的区域和我的新视图的区域是相同的(在我调用setRegion :)之后。但是,在viewWillAppear:中调用setRegion:之后,我的视图的MKMapView区域不再等于委托。不知何故,viewDillLoad中完全相同的代码:在viewWillAppear中运行时会产生不同的结果:!那不是不是这样吗?为什么调用setRegion:来自viewWillAppear:更改视图的MKMapView区域的值?这是否与regionThatFits有关:在内部调用?我不明白!
但是,我认为如果我能弄明白这一部分,我或许可以找出其他问题;所以,我不会在这里详细介绍。但是,如果你做一个快速的应用程序。有了这些功能并运行它,你会看到问题。主要是,视图的地图偶尔会同步,但是当你缩放和移动(并在标签之间来回切换)时,跨度开始缩小,每个新的标签按下只会让我越来越远。
注意:我只在模拟器上运行它(3.0)[我还没有硬件],所以我不知道这是否与它有任何关系。但是,我有点怀疑。
无论如何,感谢您提供的任何帮助。我真的很感激。
答案 0 :(得分:3)
我正在研究一个类似的问题,即在一组点周围实现缩放到适合的功能。我现在能给你的唯一帮助是yes,regionThatFits:实际上是在内部调用的。我正在调用setRegion,其区域精确地适合所有点,因此应该有一个点正好位于每个边的边缘,以及可视区域内的点。在setRegion调用之后mapview实际拥有的区域是不同的,但是如果你使用我想要使用的区域调用regionThatFits,则与你获得的区域完全相同。这个区域通常比我想要的要大一些。
我一直在根据regionThatFits仅仅试图捕捉纵横比的理论进行研究,并且正在调整纵横比校正。但是,有两件事似乎表明这不是唯一发生的事情:首先,regionThatFits返回的区域的宽高比不与地图视图的宽高比相同。其次,当我使用自己的方面校正代码来获得与regionThatFits输出完全相同的宽高比时,我仍然会从regionThatFits(和mapView)中得到错误的大区域。
到目前为止,MapKit非常令人生气。