2013-09-22 73 views
13

Tôi nhúng trang web này vào ứng dụng của tôi như thế này:Tại sao UIWebView có thểGoBack = NO trong iOS7?

NSString *url = [NSString stringWithFormat:@"https://mobile.twitter.com/search?q=%@", @"@test OR #test"]; 
url = [url stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding]; 
[self.twitterWebView loadRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:url]]]; 

self.twitterWebView.scalesPageToFit = YES; 

Và tôi có 2 nút để quay trở lại và chuyển tiếp trong trang web này. Tôi đang gọi số điện thoại


[self.twitterWebView goForward]; tương ứng.

Tính năng này hoạt động tốt trên iOS 6 nhưng trên iOS 7, các thuộc tính của tôi có thể là GoGo và canGoForward là KHÔNG và do đó các nút quay lại và tiến của tôi không hoạt động.

Như một lưu ý phụ, khi ứng dụng được cài đặt lần đầu tiên và trang được tải lần đầu tiên, các nút của tôi hoạt động. Nhưng khi tôi chạy lại ứng dụng của mình và khi tôi nhấn vào liên kết trên trang web, thuộc tính canGoBack của chế độ xem web của tôi bắt đầu trả về luôn là KHÔNG.

Tôi làm cách nào để giải quyết vấn đề này?

EDIT: Tôi đã tải lên một ứng dụng thử nghiệm nhỏ thể hiện sự cố của tôi. Bạn có thể tải xuống từ here. Vui lòng chạy ứng dụng trên trình mô phỏng iOS 7, xem nút quay lại đang hoạt động trên lần cài đặt đầu tiên của ứng dụng. Sau đó, thoát, chạy lại ứng dụng và bạn sẽ thấy rằng nó sẽ ngừng hoạt động.

Bằng cách này, vấn đề dường như là về trang web dành cho thiết bị di động twitter. Bạn có thể thử một địa chỉ trang web khác và thấy điều đó.

Trả lời

18

Điều này dường như liên quan đến HTML5's "Application Cache" functionality. Vào lần khởi chạy đầu tiên, trang web không được lưu trữ và UIWebView phát hiện chính xác nếu nó có thể tiến lên hoặc lùi lại. Ngay khi bộ nhớ đệm được điền, các trường hợp UIWebView mới quyết định rằng, ngay cả khi URL thay đổi (có thể được quan sát trong UIWebViewDelegate 's webView:shouldStartLoadWithRequest:navigationType:), thì không thể chuyển tiếp hoặc quay lại được nữa. canGoForwardcanGoBack sẽ trả về NOgoForwardgoBack sẽ không hoạt động. Điều này vẫn tiếp diễn trong quá trình khởi động lại ứng dụng, miễn là bộ nhớ cache HTML5 cho trang web cụ thể này tồn tại.

Có thể sự cố này bị giới hạn đối với các ứng dụng web sửa đổi URL Fragment identifier after the hashmark của URL thông qua JavaScript. Và có, hành vi của UIWebView trong tình huống này DID thay đổi giữa iOS 6 và iOS 7.

Tôi chưa tìm được giải pháp và có thể chúng ta sẽ phải đợi Apple sửa lỗi này trong iOS 7.1 hoặc là.

Sửa

Những người khác có vấn đề này, quá:

Nếu bạn đang sử dụng ứng dụng Cache và cũng quản lý tiểu bang thông qua băm hoặc kỹ thuật khác, các đối tượng lịch sử sẽ không giữ của bạn lịch sử điều hướng, do đó history.back() sẽ không bao giờ hoạt động và history.length sẽ ở trong 1 mãi mãi.

(từ http://www.mobilexweb.com/blog/safari-ios7-html5-problems-apis-review)

Chỉnh sửa 2

Vấn đề này tồn tại trong Safari 7.0 (9537,71, mặc định trong OS X 10.9 Mavericks), quá. Tuy nhiên, WebKit nightly build (r158339) gần đây nhất có vẻ hoạt động chính xác. Nó rất có thể chỉ là vấn đề thời gian cho đến khi bản sửa lỗi biến nó thành bản phát hành iOS và OS X.

Sửa 3

Vấn đề này vẫn còn tồn tại trong iOS 7.1 và và OS X 10.9.2.

Sửa 4

Lỗi này đã được cố định trong iOS 8 và Safari 7.1 (9537.85.10.17.1) cho OS X!

liên quan:

+0

Liên kết liên quan của bạn cho biết họ đã khắc phục bằng cách tắt bộ nhớ cache của ứng dụng. Làm thế nào là thực hiện? Cảm ơn! – Olie

+1

@Olie Chúng có nghĩa là vô hiệu hóa chức năng bộ nhớ đệm HTML5 hoàn toàn bằng cách không tham chiếu tệp kê khai trong phần 'đầu' của tài liệu HTML. Nó không thực sự là một sửa chữa ... –

+0

Vâng, đó là 'subOptimal' ...: \ Có bất kỳ công việc phong nha xung quanh? – Olie

4

Tôi có vấn đề này quá trong iOS 7. gì làm việc đối với tôi là cách di chuyển "canGoBack" mã và "canGoForward" mã để shouldStartLoadWithRequest như phía dưới. Trước đây, tôi đã có nó trong webViewDidFinishLoad, mà làm việc cho iOS 6, nhưng không dành cho iOS 7.

- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request 
navigationType:(UIWebViewNavigationType)navigationType 
{ 
    if ([webView canGoBack]) 
    { 
     [browserBackItem setEnabled:YES]; 
    } 
    else 
    { 
     [browserBackItem setEnabled:NO]; 
    } 
    if ([webView canGoForward]) 
    { 
     [browserForwardItem setEnabled:YES]; 
    } 
    else 
    { 
     [browserForwardItem setEnabled:NO]; 
    } 
    return YES; 
} 
+1

Không, điều đó cũng không giải quyết được vấn đề cho tôi. Tôi tin rằng vấn đề là như Andreas đã giải thích ở trên. – aslisabanci

-1

Sau khi thay đổi sở hữu để "strong" tài liệu tham khảo, vấn đề của tôi đã biến mất.

trước:

@property (nonatomic, weak) IBOutlet UIWebView *webView; 

sau khi thay đổi sở hữu để "strong":

@property (nonatomic, strong) IBOutlet UIWebView *webView; 
+0

điều này không giải quyết được cho tôi – Jesse

3

tôi đã cùng một vấn đề. Tôi có thể giải quyết nó với những thay đổi sau.

thực hiện một phương pháp mới updateButtons

- (void)updateButtons:(UIWebView*)theWebView { 
    if ([theWebView canGoBack]) 
    { 
     self.backButton.enabled = YES; 
    } 
    else 
    { 
     self.backButton.enabled = NO; 
    } 
    if ([theWebView canGoForward]) 
    { 
     self.forwardButton.enabled = YES; 
    } 
    else 
    { 
     self.forwardButton.enabled = NO; 
    } 
    } 

Added Gọi phương pháp trên trong shouldStartLoadWithRequest, webViewDidFinishLoad, didFailLoadWithError sự kiện.

Bây giờ phần khó khăn đến. Sau khi thực hiện các thay đổi ở trên, các nút quay lại và tiến tiếp hoạt động như mong đợi ngoại trừ trong một trường hợp. Khi chúng ta quay lại trang đầu tiên bằng cách nhấn nút quay lại, nó không bị vô hiệu hóa. Bởi vì nó sẽ không kích hoạt bất kỳ sự kiện nào ở trên khi trang được tải bằng cách nhấn nút quay lại/tiến. nó chỉ tải từ bộ nhớ cache.

Tôi đã thử nhiều cách tiếp cận nhưng chỉ có một cách giải quyết được vấn đề của tôi.

Đã thêm người quan sát trên WebHistoryItemChangedNotification.

[[NSNotificationCenter defaultCenter] addObserver:self 
             selector:@selector(webViewHistoryDidChange:) 
              name:@"WebHistoryItemChangedNotification" 
              object:nil]; 

Được gọi cùng phương thức updatebuttons trong webViewHistoryDidChange.

- (void)webViewHistoryDidChange 
{ 
    [self updateButtons:self.webView]; 
} 
+0

Giải pháp này khắc phục sự cố của tôi với trang trên thiết bị di động của YouTube. Trong thực tế, tôi gọi là updateButtons trong 4 hàm: shouldStartLoadWithRequest, webViewDidFinishLoad, didFailLoadWithError và webViewHistoryDidChange. Ba đầu tiên hoạt động tốt khi trang web là phiên bản dành cho máy tính để bàn. Nhưng khi giao dịch với trang web trên điện thoại di động, tôi cần chức năng thứ 4. –

+1

Đây là câu trả lời đúng. – iOS