2011-10-10 11 views
29

Tôi đang sử dụng các đối tượng UITableViewCell theo phong cách UITableViewCellStyleSubtitle (tức là một cái nhìn hình ảnh trên bên trái, nhãn văn bản in đậm và dưới đó một nhãn văn bản chi tiết) để tạo bàn của tôi. Bây giờ tôi cần phải phát hiện các chạm trên UIImageView và cũng để biết đường dẫn/ô trong đó chế độ xem hình ảnh được nhấp vào. Tôi đã thử sử dụngLàm thế nào để phát hiện chạm vào UIImageView của đối tượng UITableViewCell theo phong cách UITableViewCellStyleSubtitle

cell.textLabel.text = @"Sometext"; 
NSString *path = [[NSBundle mainBundle] pathForResource:@"emptystar1" ofType:@"png"]; 
UIImage *theImage = [UIImage imageWithContentsOfFile:path]; 
cell.imageView.image = theImage; 
cell.imageView.userInteractionEnabled = YES; 

Nhưng nó không hoạt động. Bất cứ khi nào hình ảnh được nhấp, didSelectRowAtIndexPath: được gọi. Tôi không muốn tạo một UITableViewCell riêng biệt và thêm nút tùy chỉnh vào nó. Có cách nào để phát hiện các chạm trên chính bản thân số UIImageView không?

Trả lời

75

Trong phương pháp cellForRowAtIndexPath bạn thêm mã này

cell.imageView.userInteractionEnabled = YES; 
cell.imageView.tag = indexPath.row; 

UITapGestureRecognizer *tapped = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(myFunction:)]; 
tapped.numberOfTapsRequired = 1; 
[cell.imageView addGestureRecognizer:tapped]; 
[tapped release]; 

Và sau đó để kiểm tra imageView được nhấp, kiểm tra cờ trong selector phương pháp

-(void)myFunction :(id) sender 
{ 
    UITapGestureRecognizer *gesture = (UITapGestureRecognizer *) sender; 
    NSLog(@"Tag = %d", gesture.view.tag); 
} 
+3

Điều này bị hỏng trong iOS 5.0 (có thể 5.0.1 quá). Xem câu trả lời bằng cách @Andrew – bandejapaisa

+0

Sử dụng UILabel thay vì UIImageView và tính năng này hoạt động trong iOS 5.1 – ChrisP

+0

Bạn đã thể hiện một cách tuyệt vời. Cảm ơn bạn. –

6

Một cách bạn có thể làm là tạo một UIImageView từ hình ảnh của bạn và thêm trình nhận dạng cử chỉ vào đó. Xem ví dụ dưới đây

//Create ImageView 
UIImageView *theImageView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"emptystar1.png"]]; 
theImageView.userInteractionEnabled = YES; 

//Add Gesture Recognizer 
UITapGestureRecognizer *tapped = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(imageSelectedInTable)]; 
tapped.numberOfTapsRequired = 1; 
[theImageView addGestureRecognizer:tapped]; 
[cell addSubview:theImageView]; 

//Memory Cleanup 
[tapped release]; 
[theImageView release]; 

-(void)imageSelectedInTable 
{ 
    NSLog(@"Selected an Image"); 
} 

Tuy nhiên, bây giờ bạn sẽ phải bố trí các tế bào của bạn hơn vì bạn không thể chỉ cần sử dụng UIImageView tài sản của UITableViewCell vì nó chỉ đọc.

+0

Gắn trình nhận dạng cử chỉ vào 'cell.imageView' sẽ hoạt động. Chỉ đọc 'imageView' không có nghĩa là không thể gọi phương thức trên đó. –

+2

Thanx aahrens .. Nó hoạt động tốt .. :) Vấn đề duy nhất tôi đang phải đối mặt ngay bây giờ là biết hình ảnh đã được chọn. Có cách nào để gửi các đối số đến @selector (imageSelectedInTable :) ?? Tôi đã kiểm tra "id" bằng cách sử dụng dấu hai chấm, nhưng đối tượng UITapGestureRecognizer của nó. Tôi cần đường dẫn chỉ mục trong đó hiển thị hình ảnh. Khi tôi đã thử @selector (imageSelectedInTable: indexPath) ứng dụng bị lỗi .. – Shri

+1

Nó hoạt động !! Tôi chỉ quên thêm "imageView.userInteractionEnabled = YES;" – jovhenni19

18

Các giải pháp chấp nhận hiện đang bị phá vỡ trong iOS 5.0. Lỗi này làm cho trình nhận dạng cử chỉ của chế độ xem hình ảnh không bao giờ được kích hoạt. Thông qua nghiên cứu trên diễn đàn nhà phát triển chính thức, tôi thấy rằng đây là lỗi đã biết trong iOS 5.0. Nguyên nhân là do việc triển khai nội bộ gây ra -gestureRecognizerShouldBegin: để trả lại NO. Lỗi xuất hiện khi bạn đang thiết lập đại biểu của trình nhận dạng cử chỉ cho chính lớp con tùy chỉnh UITableViewCell.

Các sửa chữa là để ghi đè -gestureRecognizerShouldBegin: trong đại biểu cử chỉ nhận dạng và trở YES. Lỗi này phải được khắc phục trong phiên bản iOS 5.x tương lai. Điều này chỉ an toàn miễn là bạn không sử dụng API sao chép/dán UITableViewCell mới.

- (BOOL)gestureRecognizerShouldBegin:(UIGestureRecognizer *)gestureRecognizer 
{ 
    return YES; 
} 
+0

Rất thú vị! Vì vậy, sửa chữa để cung cấp một đại biểu cho bộ nhận dạng cử chỉ, cho nó một phương thức 'gestureRecognizerShouldBegin:' và trả về 'YES'? – dasblinkenlight

+0

@dasblinkenlight vâng, chính xác. Cần lưu ý rằng điều này là an toàn miễn là bạn không sử dụng bản sao ô mới và dán API. – Andrew

+5

Tôi đã thực hiện phương pháp này và thiết lập các đại biểu để tự, nhưng không có gì từng cháy.Có ai biết trạng thái của vấn đề này trong iOS 5.1 không? – Rob

0

Vấn đề này là:

  • Add ImageView vào TableViewCell
  • tổ chức sự kiện nhấp vào ImageView khác với sự kiện nhấp vào TableViewCell

-> Các mã dưới đây làm việc một cách chính xác với tôi :

cell.imageView.image = [UIImage imageNamed:@"my_image.png"]; 
[cell.imageView setUserInteractionEnabled:YES]; 
UITapGestureRecognizer *singleTap = [[UITapGestureRecognizer alloc]initWithTarget:self action:@selector(singleTapGestureCaptured:)];  
[cell.imageView addGestureRecognizer:singleTap]; 

và "singleTapGestureCaptured" chức năng

- (void)singleTapGestureCaptured:(UITapGestureRecognizer*)gesture{ 
    NSLog(@"Left Image clicked"); 
} 
15

Đối với Swift, trong phương pháp cellForRowAtIndexPath của bạn thêm mã này

cell.imageView?.userInteractionEnabled = true 
cell.imageView?.tag = indexPath.row 

var tapped:UITapGestureRecognizer = UITapGestureRecognizer(target: self, action: "TappedOnImage:") 
tapped.numberOfTapsRequired = 1 
cell.imageView?.addGestureRecognizer(tapped) 

Và sau đó để kiểm tra IMAGExem được nhấp, kiểm tra cờ trong phương pháp chọn

func TappedOnImage(sender:UITapGestureRecognizer){ 
    println(sender.view?.tag) 
} 
+0

tại sao điều này lại được giảm giá? – Esqarrouth

+0

Điều này đã trở thành thủ thuật cho tôi. Tương tác của người dùng đã bị vô hiệu hóa đối với tôi. Cảm ơn bạn đã kết thúc giờ gỡ lỗi =) –

2

Chỉ cách thông tin bổ sung, trong trường hợp của tôi, tôi phải trả lời một thao tác nhấn trên tệp hình ảnh của ô bảng được truy xuất từ ​​NSFetchedResultsContro ller, vì vậy chúng ta cần indexPath, không phải hàng, vì vậy tôi quyết định sử dụng hình ảnh đã khai thác chính nó thay vì thông tin hàng. Tôi định nghĩa một biến cho hình ảnh:

var imgSelected: UIImageView? = nil 

tôi đã thêm các nhận dạng cử chỉ đến IMAGExem (imgZona):

public override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell { 
    let cell = tableView.dequeueReusableCellWithIdentifier(Storyboard.CellReuseIdentifier, forIndexPath: indexPath) as! ZonasTableViewCell 
    let zona = fetchedResultsController.objectAtIndexPath(indexPath) as! Zona 

    cell.infoZona = zona 

    let tapGestureRecognizer = UITapGestureRecognizer(target:self, action:Selector("imageTapped:")) 

    cell.imgZona?.addGestureRecognizer(tapGestureRecognizer) 
    cell.imgZona?.userInteractionEnabled = true 

    return cell 
} 

và trong phương pháp "imageTapped" Tôi lấy hình ảnh và lưu vào biến "imgSelected":

func imageTapped(sender: UITapGestureRecognizer) { 

    imgSelected = sender.view as? UIImageView 
    self.performSegueWithIdentifier("MuestraImagen", sender: self) 
} 

Cuối cùng, trong phương pháp "prepareForSegue" tôi đã gửi hình ảnh của viewController dành để hiển thị các hình ảnh khai thác:

override public func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) { 
    if let identifier = segue.identifier { 
     switch identifier { 
     case "MuestraImagen": 
      if let vc = segue.destinationViewController as? MuestraImagenViewController { 
       if imgSelected != nil { 
        if let img = imgSelected!.image { 
         vc.imgPuente = img 
        } 
       } 
      } 
     default: break 
     } 
    } 
}