2014-09-20 17 views
6

CẬP NHẬT:NSMutableAttributedString sẽ không hiển thị thuộc tính bắt đầu tại chỉ mục không đồng bộ

Tôi đã tạo một dự án độc lập thực sự đơn giản để chứng minh lỗi. Nếu bất cứ ai muốn kéo cùng và xem họ có thể phát hiện ra nơi tôi đã đi sai, tôi chắc chắn sẽ đánh giá cao nó. Không có nhiều mã để xem xét. Công khai repo ở đây: https://github.com/reidnez/NSAttributedStringBugDemo

Tôi gặp vấn đề rất lạ ở đây: Tôi có một cái nhìn bàn. Mỗi ô có nhãn tiêu đề với 1-3 từ và một từ khóa từ khóa với một số từ khóa CSV. Tôi cũng có một thanh tìm kiếm. Yêu cầu là khi người dùng nhập vào thanh tìm kiếm, mọi kết quả khớp một phần trên cả tiêu đề và từ khóa cho mỗi ô được hiển thị được đánh dấu. Ảnh chụp màn hình:

Everything looks as it should searching on "Fa"

"an" highlights keyword, but not title

hình ảnh đầu tiên là A-Okay. Trong hình ảnh thứ hai, dấu "an" của nhãn tiêu đề sẽ được tô sáng. Nhưng, như bạn có thể thấy, không quá nhiều ...

Điều này hoạt động hoàn toàn tốt trên nhãn "từ khóa", như bạn có thể thấy ở trên. Các chuỗi được gán cho cả hai nhãn này được tạo bởi một danh mục tôi đã viết (mã bên dưới). Phương thức tương tự được gọi trên cả hai chuỗi và dường như hoạt động giống như những gì trình gỡ lỗi đang nói với tôi. Giao diện người dùng kể một câu chuyện khác.

Tôi đã duyệt qua trình gỡ lỗi nhiều lần và trong mọi trường hợp, chuỗi được phân bổ xuất hiện đã được định cấu hình chính xác. Tôi cũng đã xác minh rằng có điều gì khác không gọi số [tableView reloadData] và không có nơi nào khác trong mã của tôi ghi đè giá trị của nhãn. Đây là cách phù hợp về "an" cho "Fang" trông trong trình gỡ lỗi, ngay trước khi tế bào được trả vào cuối cellForRowAtIndexPath:

(lldb) po customCell.entryTitleLabel.attributedText 
F{ 
}an{ 
NSBackgroundColor = "UIDeviceRGBColorSpace 0.533333 0.835294 0.156863 1"; 
}g{ 
} 

Trông tốt với tôi ... đó là chính xác những gì tôi muốn. Nhưng khi các tế bào render, không có điểm nổi bật để được nhìn thấy! Tuy nhiên, khi thử nghiệm, tôi đã cố gắng đặt nhãn thành một thuộc tính hoàn toàn tùy ý mà tôi đã tạo ngay trong cellForRow:

NSMutableAttributedString *fake = [[NSMutableAttributedString alloc] initWithString:@"Fang"]; 
      [fake addAttribute:NSBackgroundColorAttributeName value:MATCH_TEXT_HILIGHT_COLOR range:NSMakeRange(1, 2)]; 
      customCell.entryTitleLabel.attributedText = fake; 

Điều này cũng không thành công. Không đánh dấu gì cả ... nhưng tôi CÓ THỂ đánh dấu bất kỳ chuỗi con nào trong phạm vi {0, 1} đến {0, fake.length} và nó hoạt động như mong đợi. Một lần nữa, dường như từ chối làm nổi bật bất kỳ chuỗi con nào không bắt đầu ở chỉ mục 0 - nhưng chỉ cho nhãn tiêu đề.

Tôi có bị mất trí? Tôi đang thiếu gì?

Dưới đây là danh mục của tôi ... nhưng tôi khá tự tin về vấn đề không nằm ở đây, bởi vì nó hoạt động hoàn hảo cho chuỗi từ khóa và (một lần nữa) các thuộc tính dường như được đặt chính xác ngay trước khi ô trả về:

-(void)hilightMatchingSubstring:(NSString*)substring color:(UIColor*)hilightColor range:(NSRange)range 
{ 
    if ([self.string compare:substring options:NSCaseInsensitiveSearch] == NSOrderedSame) { 
     [self addAttribute:NSBackgroundColorAttributeName value:hilightColor range:NSMakeRange(0, self.length)]; 
     return; 
    } 

    // Sanity check. Make sure a valid range has been passed so that we don't get out-of-bounds crashes. Default to return self wrapped in an attributed string with no attributes. 
    NSRange selfRange = NSMakeRange(0, self.length); 
    if (NSIntersectionRange(selfRange, range).length == 0) { 
     NSLog(@" \n\n\n*** Match range {%lu, %lu} does not intersect main string's range {%lu, %lu}. Aborting *** \n\n\n", (unsigned long)range.location, (unsigned long)range.length, (unsigned long)selfRange.location, (unsigned long)selfRange.length); 
     return; 
    } 

    if (substring.length > 0) { 
     NSRange movingRange = NSMakeRange(range.location, substring.length); 
     if (NSMaxRange(movingRange) > self.length) { 
      return; 
     } 

     NSString *movingString = [self.string substringWithRange:movingRange]; 

     while (NSMaxRange(movingRange) < NSMaxRange(range)) { 
      if ([movingString compare:substring options:NSCaseInsensitiveSearch] == NSOrderedSame) { 
       [self addAttribute:NSBackgroundColorAttributeName value:hilightColor range:movingRange]; 
      } 
      movingRange = NSMakeRange(movingRange.location + 1, substring.length); 
      movingString = [self.string substringWithRange:movingRange]; 
     } 
    } // This is fine...string leaves properly attributed. 
} 
+0

Bạn không thích nhận xét? Đồng ý, cảm ơn. Siêu xây dựng! Tôi sẽ không làm điều đó một lần nữa ... bất cứ điều gì tôi đã làm? –

+2

Tôi thấy điều tương tự với nhãn của các ô xem bảng. Tôi có thể nhấn mạnh phần bắt đầu của văn bản chứ không phải phần giữa. Tôi đề nghị làm một ứng dụng thử nghiệm đơn giản và gửi nó với một báo cáo lỗi cho Apple. – rmaddy

+0

"Đó là lỗi của Apple" luôn là câu trả lời cuối cùng của tôi ... Tôi thực sự phải chứng minh với chính mình rằng đó là trường hợp (nhiều khả năng là một chút-ole-me đã phạm sai lầm ở đâu đó). Nhưng nếu bạn đã gặp phải một vấn đề tương tự, nó thực sự có thể là kết luận đúng đắn. Ứng dụng thử nghiệm độc lập là một ý tưởng tuyệt vời, tôi sẽ làm điều đó. Cảm ơn! –

Trả lời

2

Cảm ơn bạn đã viết thư này ... Tôi cũng nghĩ rằng tôi cũng phát điên!

Tôi đã tìm ra cách giải quyết (đọc: hack) trong khi chờ đợi một điều gì đó chính thức từ Apple.

NSDictionary *hackAttribute = [NSDictionary dictionaryWithObjectsAndKeys: 
          [UIColor clearColor], NSBackgroundColorAttributeName, nil]; 

NSMutableAttributedString *attributedText = 
    [[NSMutableAttributedString alloc] initWithString:@"some text..."]; 
    [attributedAddressText setAttributes:hackAttribute range:NSMakeRange(0, attributedText.length)]; 
// Then set your other attributes as per normal 

Hy vọng điều đó sẽ hữu ích.

+0

Cảm ơn! Tôi thực sự đã từ bỏ việc sửa lỗi này từ lâu và bắt đầu làm việc trên những thứ khác. Nhưng ... ngay sau khi tôi về nhà, tôi sẽ kiểm tra điều này và (giả sử nó hoạt động) chấp nhận câu trả lời của bạn. –

+0

Hack này làm việc cho tôi .. –

+0

@ReidBelton: lemme biết làm thế nào nó đi :) –

Các vấn đề liên quan