Điều gì sẽ khiến một ô xem bảng vẫn được tô sáng sau khi được chạm vào? Tôi bấm vào ô và có thể thấy nó vẫn được tô sáng khi chế độ xem chi tiết được đẩy. Khi chế độ xem chi tiết được bật, ô vẫn được tô sáng.
Điều gì sẽ khiến một ô xem bảng vẫn được tô sáng sau khi được chạm vào? Tôi bấm vào ô và có thể thấy nó vẫn được tô sáng khi chế độ xem chi tiết được đẩy. Khi chế độ xem chi tiết được bật, ô vẫn được tô sáng.
Câu trả lời:
Trong didSelectRowAtIndexPath
bạn cần gọi deselectRowAtIndexPath
để bỏ chọn ô.
Vì vậy, bất cứ điều gì khác bạn đang làm trong didSelectRowAtIndexPath
bạn chỉ cần có nó deselectRowAtIndexPath
là tốt.
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
// Do some stuff when the row is selected
[tableView deselectRowAtIndexPath:indexPath animated:YES];
}
-deselectRowAtIndexPath:animated:
phương thức trên thuộc tính tableView của nó từ -viewDidAppear
. Tuy nhiên, nếu bạn có chế độ xem bảng trong lớp con UIViewControll, bạn nên gọi -deselectRowAtIndexPath:animated:
từ -viewDidAppear
chính mình. :)
-viewWillAppear:
nó đã phá vỡ nó. Thêm một cuộc gọi để làm cho [super viewWillAppear:animated]
nó hoạt động trở lại.
UITableViewController
's clearsSelectionOnViewWillAppear
tài sản được thiết lập để YES
(đó là mặc định), và bạn đã không ngăn cản [super viewWillAppear]
khỏi bị gọi.
Cách rõ ràng nhất để làm điều đó là trên viewWillAppear:
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
// Unselect the selected row if any
NSIndexPath* selection = [self.tableView indexPathForSelectedRow];
if (selection) {
[self.tableView deselectRowAtIndexPath:selection animated:YES];
}
}
Bằng cách này, bạn có hình ảnh động mờ dần lựa chọn khi bạn quay lại bộ điều khiển, như nó phải vậy.
Lấy từ http://forums.macrumors.com/showthread.php?t=577677
Phiên bản Swift
override func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
// deselect the selected row if any
let selectedRow: IndexPath? = tableView.indexPathForSelectedRow
if let selectedRowNotNill = selectedRow {
tableView.deselectRow(at: selectedRowNotNill, animated: true)
}
}
viewDidAppear
thay thế.
indexPathForSelectedRow
gọi có thể trả về nil vì vậy cần kiểm tra lại. Tài liệu nêu rõ : Đường dẫn chỉ mục xác định chỉ mục hàng và phần của hàng đã chọn hoặc không nếu đường dẫn chỉ mục không hợp lệ.
Bạn đã phân lớp -(void)viewWillAppear:(BOOL)animated
? UITableViewCell đã chọn sẽ không bỏ chọn khi bạn không gọi [super viewWillAppear:animated];
trong phương thức tùy chỉnh của mình.
Đối với người dùng Swift, hãy thêm mã này vào mã của bạn:
func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
tableView.deselectRowAtIndexPath(indexPath, animated: true)
}
Đó là câu trả lời của paulthenerd ngoại trừ trong Swift thay vì Obj-C.
Giải pháp Swift 3
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
tableView.deselectRow(at: indexPath as IndexPath, animated: true)
}
Cập nhật với Swift 4
Sau một vài thử nghiệm, cũng dựa trên các câu trả lời trước đó, tôi đã có kết luận rằng hành vi tốt nhất có thể đạt được theo 2 cách: (gần như giống hệt nhau trong thực tế)
// First Solution: delegate of the table View
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
tableView.deselectRow(at: indexPath, animated: false)
}
// Second Solution: With the life cycle of the view.
override func viewDidDisappear(_ animated: Bool) {
super.viewDidDisappear(animated)
let selectedRow: IndexPath? = tableView.indexPathForSelectedRow
if let selectedRow = selectedRow {
tableView.deselectRow(at: selectedRow, animated: false)
}
}
Cá nhân tôi đang áp dụng giải pháp đầu tiên, vì đơn giản là nó ngắn gọn hơn. Một khả năng khác, nếu bạn cần một hình ảnh động nhỏ khi bạn quay lại bảngView, là sử dụng viewWillAppear
:
override func viewWillAppear(_ animated: Bool) {
super.viewWillAppear(animated)
let selectedRow: IndexPath? = _view.tableView.indexPathForSelectedRow
if let selectedRow = selectedRow {
_view.tableView.deselectRow(at: selectedRow, animated: true)
}
}
Cuối cùng nhưng không kém phần quan trọng, nếu bạn đang sử dụng UITableViewCont kiểm soát, bạn cũng có thể tận dụng lợi thế của thuộc tính xóaSelectionOnViewWillAppear .
Để có được hành vi mà Kendall Helmstetter Gelner mô tả trong bình luận của mình, bạn có thể không muốn deselectRowAtIndexPath mà thay vào đó là thuộc tính ClearsSelectionOnViewWillAppear trên bộ điều khiển của bạn. Có lẽ điều này đã được đặt thành CÓ một cách tình cờ?
Xem bình luận trong mẫu Apple mặc định cho các lớp con UITableViewControll mới:
- (void)viewDidLoad
{
[super viewDidLoad];
// Uncomment the following line to preserve selection between presentations.
// self.clearsSelectionOnViewWillAppear = NO;
}
Tôi đã nhận được vấn đề này cũng như cho ứng dụng đi sâu của tôi. Sau một trình điều khiển khung nhìn, mà tôi sẽ gọi VC, trả về sau khi đẩy một ViewContoder khác, ô được chọn trong VC vẫn được tô sáng. Trong ứng dụng của mình, tôi đã tạo ra VC để xử lý cấp độ thứ hai (trong số ba cấp độ) trong quá trình truy sâu của tôi.
Vấn đề trong trường hợp của tôi là VC là một UIViewContoder (có chứa Chế độ xem có chứa TableView). Thay vào đó, tôi đã biến VC thành UITableViewControll (có chứa TableView). Lớp UITableViewCont kiểm soát tự động xử lý khử sáng của ô bảng sau khi trở về từ một lần đẩy. Câu trả lời thứ hai cho bài viết " Vấn đề với deselectRowAtIndexPath trong bảngView " đưa ra câu trả lời đầy đủ hơn cho vấn đề này.
Sự cố không xảy ra đối với trình điều khiển xem gốc vì khi tôi tạo ứng dụng dưới dạng "Ứng dụng dựa trên điều hướng" trong XCode, trình điều khiển xem gốc đã được tạo cho lớp con UITableViewContaptor.
Nếu không có cách nào trong số này phù hợp với bạn, hãy xem xét cách giải quyết này:
Sử dụng một segue thư giãn để gọi:
@IBAction func unwind_ToTableVC (segue: UIStoryboardSegue) {
if let index = tableView.indexPathForSelectedRow {
tableView.deselectRowAtIndexPath(index, animated: true)
}
}
Tại sao làm điều này? Chủ yếu nếu bạn gặp khó khăn khi lấy mã bỏ chọn để chạy đúng lúc. Tôi gặp sự cố với nó không hoạt động trên viewWillAppear vì vậy thư giãn hoạt động tốt hơn rất nhiều.
Các bước:
Viết segue thư giãn (hoặc dán từ trên xuống) vào VC đầu tiên của bạn (cái có bảng)
Chuyển đến VC thứ 2. Điều khiển kéo từ nút Hủy / Xong / Vv mà bạn đang sử dụng để loại bỏ VC đó và kéo đến Biểu tượng Thoát ở trên cùng.
Chọn segue thư giãn bạn đã tạo ở bước 1
Chúc may mắn.
Tôi đang sử dụng CoreData vì vậy mã làm việc cho tôi là sự kết hợp các ý tưởng từ nhiều câu trả lời khác nhau, trong Swift:
override func viewDidAppear(_ animated: Bool) {
if let testSelected = yourTable.indexPathForSelectedRow {
yourTable.deselectRow(at: testSelected, animated: true)
}
super.viewDidAppear(true)
}
Tôi đã có cùng một vấn đề trong một thời gian dài vì vậy trong trường hợp có ai khác đang vật lộn:
Hãy nhìn vào của bạn -tableView: cellForRowAtIndexPath:
và xem nếu bạn đang tạo các ô hoặc sử dụng 'định danh tái sử dụng'. Nếu sau này, hãy chắc chắn rằng bảng của bạn trong IB có một ô có mã định danh đó. Nếu bạn không sử dụng Mã định danh tái sử dụng, chỉ cần tạo một ô mới cho mỗi hàng.
Điều này sau đó sẽ cung cấp cho bảng của bạn 'hàng được chọn mờ' dự kiến xuất hiện.
Đối với Swift 3: Tôi muốn sử dụng nó trong viewDidDisappear
Định nghĩa:-
var selectedIndexPath = IndexPath()
Trong viewDidDisappear: -
override func viewDidDisappear(_ animated: Bool) {
yourTableView.deselectRow(at: selectedIndexPath, animated: true)
}
Trong didSelectRowAtIndexPath: -
func tableView(_ tableView: UITableView, didSelectRowAtIndexPath indexPath: IndexPath) {
selectedIndexPath = indexPath
}
nếu ô còn lại được tô sáng sau khi chạm vào nó, bạn có thể gọi phương thức UITabelView,
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
`[tableView deselectRowAtIndexPath:indexPath animated:YES];`
}
Hoặc, bạn có thể sử dụng phương pháp sau và sửa đổi nó theo yêu cầu của bạn,
// Đánh dấu: UITableViewDelegate
func tableView(tableView: UITableView, didHighlightRowAtIndexPath indexPath: NSIndexPath) {
if let cell = tableView.cellForRowAtIndexPath(indexPath) {
cell.backgroundColor = UIColor.greenColor()
}
}
func tableView(tableView: UITableView, didUnhighlightRowAtIndexPath indexPath: NSIndexPath) {
if let cell = tableView.cellForRowAtIndexPath(indexPath) {
cell.backgroundColor = UIColor.blackColor()
}
}
Xcode 10, Swift 4
Tôi gặp vấn đề tương tự và phát hiện ra tôi đã để lại một cuộc gọi trống để xemWillAppear ở cuối bảngViewControll của tôi. Khi tôi loại bỏ chức năng ghi đè trống, hàng không còn được tô sáng khi quay lại chế độ xem bảng.
vấn đề
override func viewWillAppear(_ animated: Bool) {
// need to remove this function if not being used.
}
loại bỏ chức năng trống đã giải quyết vấn đề của tôi.
deselectRowAtIndexPath
trong viewDidAppear của tôi, nếu chọn hàng sẽ hiển thị một chế độ xem mới.