从 UIScrollview UIView SubView 推送到另一个 ViewController
Posted
技术标签:
【中文标题】从 UIScrollview UIView SubView 推送到另一个 ViewController【英文标题】:Pushing to another ViewController from UIScrollview UIView SubView 【发布时间】:2014-05-20 18:48:42 【问题描述】:我有一个以轮播方式显示信息的滚动视图,我现在要做的是在轮播中的每个视图上添加点击事件,我可以通过添加 UITapGestureRecongnizer* 每次推送时,都会记录一个错误*嵌套推送动画会导致导航栏损坏,并且会显示错误信息 下面是我加载 Carousel View 和添加 Click 事件的代码,Carousel 上的数据也是从 jSON 获取并与 NSObject 一起存储在 **NSMutableArray* ...
-(void)updateUI:(NSMutableArray *)array
CGFloat contentOffset = 0.0f;
for (NSString *dis in carouselArray)
CGRect frame = CGRectMake(contentOffset, 0.0f, responseScroll.frame.size.width, responseScroll.frame.size.height);
UIView *views = [[UIView alloc] initWithFrame:frame];
views.backgroundColor = [UIColor clearColor];
UIImageView *imageView = [[UIImageView alloc] initWithFrame:CGRectMake(0, 0, 320, 130)];
imageView.contentMode = UIViewContentModeScaleToFill;
//imageView.image = [UIImage imageNamed:@"banner.png"];
UITapGestureRecognizer *imageMove = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(moreViewMove)];
imageMove.cancelsTouchesInView = NO;
NSString *urls = [dis valueForKey:@"imageURL"];
if ([urls isEqual: @""])
imageView.image = [UIImage imageNamed:@"banner.png"];
else
[imageView setImageWithURL:[NSURL URLWithString:urls]];
UILabel *name = [[UILabel alloc] initWithFrame:CGRectMake(10, 132, 152, 21)];
name.font = [UIFont fontWithName:@"Helvetica Bold" size:13];
name.textColor = [UIColor blackColor];
name.text = [dis valueForKey:@"name"];
UILabel *address = [[UILabel alloc] initWithFrame:CGRectMake(10, 149, 194, 21)];
address.font = [UIFont fontWithName:@"Helvetica Light" size:12];
address.textColor = [UIColor blackColor];
address.text = [dis valueForKey:@"address"];
UILabel *km = [[UILabel alloc] initWithFrame:CGRectMake(278, 133, 42, 21)];
km.font = [UIFont fontWithName:@"Helvetica" size:11];
CLLocation *current = [[CLLocation alloc] initWithLatitude:locationManager.location.coordinate.latitude longitude:locationManager.location.coordinate.longitude];
CLLocation *itemLoc = [[CLLocation alloc] initWithLatitude:[[dis valueForKey:@"lat"] doubleValue] longitude:[[dis valueForKey:@"lon"] doubleValue]];
CLLocationDistance itemDist = [itemLoc distanceFromLocation:current]/1000;
//NSLog(@"Distance: %f", itemDist);
km.text = [[NSString alloc] initWithFormat:@"%.2fkm", itemDist];
views.userInteractionEnabled = YES;
[views addGestureRecognizer:imageMove];
_starRating = [[EDStarRating alloc] initWithFrame:CGRectMake(234, 149, 78, 16)];
_starRating.starImage = [UIImage imageNamed:@"star.png"] ;
_starRating.starHighlightedImage = [UIImage imageNamed:@"starhighlighted.png"];
_starRating.maxRating = 5.0;
_starRating.delegate = self;
_starRating.horizontalMargin = 0;
_starRating.editable=NO;
_starRating.rating= [[dis valueForKey:@"rating"] floatValue];
_starRating.displayMode=EDStarRatingDisplayHalf;
[views addSubview:imageView];
[views addSubview:name];
[views addSubview:address];
[views addSubview:km];
[views addSubview:_starRating];
[responseScroll setUserInteractionEnabled:YES];
[responseScroll addSubview:views];
[responseScroll addGestureRecognizer:imageMove];
contentOffset += views.frame.size.width;
responseScroll.contentSize = CGSizeMake(contentOffset, views.frame.size.height);
处理查看点击事件的代码如下,我知道我做错了但我不知道该怎么做。
-(void)moreViewMove
for (NSString *dat in carouselArray)
NSString *path = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
path = [path stringByAppendingPathComponent:@"u_id.plist"];
NSMutableDictionary *dico = [[NSMutableDictionary alloc] initWithContentsOfFile:path];
NSString *place_id = [dat valueForKey:@"place_id"];
NSString *place_reference = [dat valueForKey:@"place_reference"];
CLLocation *current = [[CLLocation alloc] initWithLatitude:startLocation.coordinate.latitude longitude:startLocation.coordinate.longitude];
CLLocation *itemLoc = [[CLLocation alloc] initWithLatitude:[[dat valueForKey:@"lat"] floatValue] longitude:[[dat valueForKey:@"lon"] floatValue]];
CLLocationDistance itemDist = [itemLoc distanceFromLocation:current]/1000;
UIDevice *device = [UIDevice currentDevice];
NSString *u_id = [[device identifierForVendor] UUIDString];
if ([dico objectForKey:@"u_id"])
moreView *more = [self.storyboard instantiateViewControllerWithIdentifier:@"MoreView"];
more.names = [dat valueForKey:@"name"];
more.currentLat = [[NSString alloc] initWithFormat:@"%f", locationManager.location.coordinate.latitude];
more.currentLon = [[NSString alloc] initWithFormat:@"%f", locationManager.location.coordinate.longitude];
more.destinationLon = [dat valueForKey:@"lon"];
more.destinationLat = [dat valueForKey:@"lat"];
more.addressL = [dat valueForKey:@"address"];
more.kilo = [[NSString alloc] initWithFormat:@"%.2fkm", itemDist];
more.dataURL = @@"type": @"details",@"u_id":[dico objectForKey:@"u_id"], @"place_id": place_id, @"place_reference": place_reference, @"device":@"server";
[self.navigationController pushViewController:more animated:YES];
请,任何帮助将不胜感激...谢谢
【问题讨论】:
【参考方案1】:代码中最不寻常的部分是moreViewMove
中的循环。看起来它将分配并推送到 N 个视图控制器,其中 N 是 carouselArray
中的元素数。
这类事情的一般模式是有一个基于模型创建视图的循环,一个获取点击的手势识别器,以及将点击映射回模型的方法。然后点击处理程序只查找单个模型项并执行导航。
updateUI:
中的循环创建子视图和手势识别器。将视图映射回模型的常用方法是使用视图的tag
属性。在你的 updateUI 中,你会做这样的事情:
UIView *views = [[UIView alloc] initWithFrame:frame];
views.tag = [carouselArray indexOfObject:dis];
// ...
// change the gesture recognizer selector to take a parameter
// notice the colon on the selector moreViewMove:
UITapGestureRecognizer *imageMove = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(moreViewMove:)];
现在在 moreViewMove: 中,您可以找出点击了哪个索引,因为手势识别器将作为参数发送...
- (void)moreViewMove:(UITapGestureRecognizer *)gr
// don't put a loop in here.
// probably don't build a dictionary in here that doesn't depend on which item was tapped
UIView *theViewThatWasTapped = gr.view;
NSInteger tag = theViewThatWasTapped.tag;
// now, we can know what part of our model was tapped
NSString *dis = carouselArray[tag];
// check how you're doing with an NSLog
NSLog(@"user tapped view with tag %ld model is %@", tag, dis);
// your job now is to allocate a single view controller,
// configure it with your model (dis) and push it
尽可能少地配置新的 vc。任何与选择模型的哪个部分无关的 init 内容都应该移到其他地方,希望能移到新视图控制器的初始化中。
【讨论】:
拜托,你让我很开心,Hommie,loooooolllllll 今天我在工作的一个朋友实际上告诉了我同样的事情,但不能很好地理解他。谢谢一堆人,非常感谢,但现在的问题是它只选择滚动中的第一个视图,如果我点击下一个视图,它会给我第一个视图的信息 很高兴您取得了进展。在moreViewMove: 方法中,能否将我在编辑中建议的日志记录添加到上面的moreViewMove 方法中。 总是选择 Tag 0 接下来,当你在updateUI中设置标签时,NSLog标签。您还可以记录手势识别器(使用 %@ 或 %p)并将其与 moveViewMove 中发送的手势识别器进行比较: 是的,它很好地标记了它。它非常准确地标记它,现在数组中只有四个字典,它给每个字典一个标签号以上是关于从 UIScrollview UIView SubView 推送到另一个 ViewController的主要内容,如果未能解决你的问题,请参考以下文章
在 iPhone SDK 中将 UIButton 从 UIScrollView 移动到 UIView
将 UIView 从 xib 添加到 UIScrollView
将捏合手势从自定义 UIView 传递到父 UIScrollView
iOS:在故事板中将子类从 UIView 更改为 UIScrollView
将 UIView 从 UIPopOverController 中的 UIScrollView 拖放到主 UIViewController?