【问题标题】:How to enable "select all" in UIWebView in an IPhone App?如何在 iPhone 应用程序的 UIWebView 中启用“全选”?
【发布时间】:2011-06-13 14:39:40
【问题描述】:

我正在编写一个嵌入 UIWebView 的 iPhone 应用程序。有各种类似 Safari 的功能,如导航等。我正在寻找的任务之一是当用户在 Web 视图上选择一段文本时显示“全选”选项。目前,我只看到一个“复制”选项。有没有一种简单的方法来启用“全选”菜单项?我当然尝试将菜单项添加到共享菜单控制器,但这并不一定实现原始的 safari“全选”功能。任何帮助和指示都会非常有用。

提前致谢。

【问题讨论】:

    标签: ios4 uiwebview iphone uiwebviewdelegate


    【解决方案1】:

    您可以在运行时为不可编辑的webView 实现selectAll 行为(相当于Apple Mail.app 中的行为),使用UIWebView 的以下类别。

    主要思想是使用暗示UIWebBrowserViewUIWebView的子视图是UIWebDocumentView的子类,符合UITextInputPrivate协议,相当于公共UITextInput协议

    //  UIWebView+SelectAll.h
    //  Created by Alexey Matveev on 28.03.15.
    //  Copyright (c) 2015 Alexey Matveev. All rights reserved.
    
    @interface UIWebView (SelectAll)
    + (void)setEnableSelectAll:(BOOL)enabled;
    @end
    
    
    #import "UIWebView+SelectAll.h"
    #import <objc/runtime.h>
    
    /*
     UIWebDocumentView is the superclass for UIWebBrowserView.
     UIWebDocumentView conforms UITextInputPrivate protocol which is identival to UITextInput
    */
    
    static IMP canPerformActionWithSenderImp;
    
    @implementation UIWebView (SelectAll)
    
    @dynamic enableSelectAll;
    
    - (BOOL)customCanPerformAction:(SEL)action withSender:(id)sender
    {
        if (action == @selector(selectAll:)) {
            return ! self.isSelectedAll;
        }
        else {
            BOOL(*imp)(id, SEL, SEL, id) = (BOOL(*)(id, SEL, SEL, id))canPerformActionWithSenderImp;
            return imp(self, @selector(canPerformAction:withSender:),  action, sender);
        }
    }
    
    - (void)selectAll:(id)sender
    {
        [self.browserView selectAll:sender];
    }
    
    - (UIView<UITextInput> *)browserView
    {
        UIView *browserView;
        for (UIView *subview in self.scrollView.subviews) {
            if ([subview isKindOfClass:NSClassFromString(@"UIWebBrowserView")]) {
                browserView = subview;
                break;
            }
        }
    
        return (UIView<UITextInput> *)browserView;
    }
    
    - (BOOL)isSelectedAll
    {
        UITextRange *currentRange = self.browserView.selectedTextRange;
        if ([self.browserView comparePosition:currentRange.start toPosition:self.browserView.beginningOfDocument] == NSOrderedSame) {
            if ([self.browserView comparePosition:currentRange.end toPosition:self.browserView.endOfDocument] == NSOrderedSame) {
                return YES;
            }
        }
        return NO;
    }
    
    + (void)setEnableSelectAll:(BOOL)enabled
    {
        SEL canPerformActionSelector = @selector(canPerformAction:withSender:);
    
        if (!canPerformActionWithSenderImp) {
            canPerformActionWithSenderImp = [self instanceMethodForSelector:canPerformActionSelector];
        }
    
        IMP newCanPerformActionWithSenderImp = enabled ? [self instanceMethodForSelector:@selector(customCanPerformAction:withSender:)] : canPerformActionWithSenderImp;
    
        Method canPerformActionMethod = class_getInstanceMethod([self class], canPerformActionSelector);
        class_replaceMethod([self class], canPerformActionSelector, newCanPerformActionWithSenderImp, method_getTypeEncoding(canPerformActionMethod));
    }
    
    @end
    

    当然,你可以使用全局方法调配

    - (BOOL)canPerformAction:(SEL)action withSender:(id)sender;
    

    以标准方式,但它会不可逆转地影响项目中的所有 webView。

    【讨论】:

      【解决方案2】:

      简短的回答是不,这是不可能的。

      您可以通过子类化 UIWebView 并覆盖来做到这一点(无需自己向菜单控制器添加任何内容):

      -(BOOL) canPerformAction:(SEL)action withSender:(id)sender 
      

      并检查选择器是否为selectAll:

      像这样:

      -(BOOL) canPerformAction:(SEL)action withSender:(id)sender {
          if (action == @selector(selectAll:)) {
              return YES;
          } else {
              return [super canPerformAction:action withSender:sender];
          }
      }
      

      这将在“保留”菜单上显示“全选”选项。然而,这不是 webView 的默认行为,虽然当您按下全选时应用不会崩溃,但按下它什么也不做。

      你甚至不能创建一个 selectAll 方法,然后在 webview 中选择所有内容,因为 javascript 方法 .select() 在 Mobile Safari/UIWebView 上不起作用。

      【讨论】:

      • 还应注意,文档中不允许子类化 UIWebView。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-08-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多