2011-05-19 33 views
13

tôi muốn cho phép người dùng chọn một số văn bản từ webview và nó cần phải được gửi dưới dạng tin nhắn văn bản. xin tìm cách để chọn văn bản và sao chép vào clipboard và trích xuất từ ​​clipboard. tôi thấy nhiều ví dụ nhưng không giúp tôi thực sự ... TIAAndroid: cách chọn văn bản từ webview

Sửa
sử dụng mã được cung cấp trong liên kết từ @ orangmoney52. với các thay đổi sau

tham số thứ hai của getmethod và gọi tham số thứ hai của phương thức. nếu tôi cung cấp cho null có cảnh báo sẽ đến .. đó là một trong những chính xác?

public void selectAndCopyText() { 
    try { 
     Method m = WebView.class.getMethod("emulateShiftHeld", Boolean.TYPE); 
      m.invoke(BookView.mWebView, false); 
     } catch (Exception e) { 
      e.printStackTrace(); 
      // fallback 
      KeyEvent shiftPressEvent = new KeyEvent(0,0, 
       KeyEvent.ACTION_DOWN,KeyEvent.KEYCODE_SHIFT_LEFT,0,0); 
      shiftPressEvent.dispatch(this); 
     } 

} 

Bắt lỗi này:

05-26 16:41:01.121: WARN/System.err(1096): java.lang.NoSuchMethodException: emulateShiftHeld 
+0

hãy thêm đoạn mã hoàn chỉnh –

Trả lời

14

Câu trả lời ở trên trông hoàn toàn ổn và có vẻ như bạn đang thiếu thứ gì đó trong khi chọn văn bản. Vì vậy, bạn cần phải kiểm tra kỹ mã và tìm ghi đè của bạn bất kỳ TouchEvent của chế độ xem web.

tôi đã cố gắng bên dưới mã nó hoạt động tốt ...

Chức năng là

private void emulateShiftHeld(WebView view) 
    { 
     try 
     { 
      KeyEvent shiftPressEvent = new KeyEvent(0, 0, KeyEvent.ACTION_DOWN, 
                KeyEvent.KEYCODE_SHIFT_LEFT, 0, 0); 
      shiftPressEvent.dispatch(view); 
      Toast.makeText(this, "select_text_now", Toast.LENGTH_SHORT).show(); 
     } 
     catch (Exception e) 
     { 
      Log.e("dd", "Exception in emulateShiftHeld()", e); 
     } 
    } 

Gọi Trên phương pháp bất cứ nơi nào bạn muốn (Bạn có thể đặt một nút và gọi phương pháp này trong sự kiện click của nó): emulateShiftHeld (mWebView);

+1

Trên Android 4+ không hoạt động. http://stackoverflow.com/questions/21101181/android-webview-how-to-correctly-copy-selected-text –

+10

Tôi thậm chí không hiểu câu trả lời này đang cố gắng nói gì. – Michael

+0

xin vui lòng thêm toàn bộ đoạn mã ở đây để người mới có thể sử dụng nó một cách dễ dàng –

0

@vnshetty, bằng cách sử dụng mã được cung cấp trong liên kết từ @ orangmoney52, tôi đã có thể hoàn thành vấn đề này cách đây vài tháng. Bạn có thể tạo một nút trong menu cho phép bạn sao chép văn bản. Sau đó, trong onOptionsItemSelected, bạn có thể có một mệnh đề như sau:

case R.id.select_and_copy: { 
     Toast.makeText(getApplicationContext(), "Select Text", Toast.LENGTH_SHORT).show(); 
     selectAndCopyText(); 
     return true; 
    } 
+0

Có Sau khi bánh mì nướng được hiển thị tôi nhấn phím shift và cố gắng chọn nội dung webview bằng chuột nhưng không có gì được chọn? Tôi có thiếu gì không? – vnshetty

+0

Không cần nhấn phím shift. Đơn giản chỉ cần chọn văn bản sau khi tin nhắn bánh mì nướng được hiển thị. – Phil

5

Cách đơn giản nhất, mặc dù không xinh đẹp như những gì có vẻ như một mỗi nhà sản xuất thực hiện tính năng copy/paste, như sau:

https://bugzilla.wikimedia.org/show_bug.cgi?id=31484

Về cơ bản, nếu bạn đang thiết của riêng bạn WebChromeClient qua webview.setWebChromeClient(...) sau đó lựa chọn văn bản bị tắt theo mặc định. Để kích hoạt nó WebChromeClient nhu cầu của bạn để có phương pháp thực hiện như sau:

//@Override 
/** 
* Tell the client that the selection has been initiated. 
*/ 
public void onSelectionStart(WebView view) { 
    // Parent class aborts the selection, which seems like a terrible default. 
    //Log.i("DroidGap", "onSelectionStart called"); 
} 
+0

Trong trường hợp của tôi nó cũng không workng.Tôi đang ghi đè onTouch() nhưng nó trở về sai. Vấn đề thực sự là gì, bạn có ghi đè các sự kiện liên lạc không? – DroidBot

+0

Đề xuất của tôi không được ghi đè lênTouch(). Bạn có cài đặt riêng, tùy chỉnh, WebChromeClient không? –

+0

Hey điều này thực sự hoạt động! – Bruce

6

Bước: 1 Tạo lớp WebView tùy chỉnh. Lớp này sẽ ghi đè thanh tác vụ gốc trên báo chí dài trên văn bản webview. Ngoài ra nó xử lý các trường hợp lựa chọn cho phiên bản khác nhau của android (thử nghiệm trên 4.0 trở đi) Mã này có văn bản được lựa chọn bằng cách sử dụng javascript.

public class CustomWebView extends WebView { 
private Context context; 
// override all other constructor to avoid crash 
public CustomWebView(Context context) { 
    super(context); 
    this.context = context; 
    WebSettings webviewSettings = getSettings(); 
    webviewSettings.setJavaScriptEnabled(true); 
    // add JavaScript interface for copy 
    addJavascriptInterface(new WebAppInterface(context), "JSInterface"); 
} 

// setting custom action bar 
private ActionMode mActionMode; 
private ActionMode.Callback mSelectActionModeCallback; 
private GestureDetector mDetector; 

// this will over ride the default action bar on long press 
@Override 
public ActionMode startActionMode(Callback callback) { 
    ViewParent parent = getParent(); 
    if (parent == null) { 
     return null; 
    } 
    if (Build.VERSION.SDK_INT < Build.VERSION_CODES.KITKAT) { 
     String name = callback.getClass().toString(); 
     if (name.contains("SelectActionModeCallback")) { 
      mSelectActionModeCallback = callback; 
      mDetector = new GestureDetector(context, 
        new CustomGestureListener()); 
     } 
    } 
    CustomActionModeCallback mActionModeCallback = new CustomActionModeCallback(); 
    return parent.startActionModeForChild(this, mActionModeCallback); 
} 

private class CustomActionModeCallback implements ActionMode.Callback { 

    @Override 
    public boolean onCreateActionMode(ActionMode mode, Menu menu) { 
     mActionMode = mode; 
     MenuInflater inflater = mode.getMenuInflater(); 
     inflater.inflate(R.menu.menu, menu); 
     return true; 
    } 

    @Override 
    public boolean onPrepareActionMode(ActionMode mode, Menu menu) { 
     return false; 
    } 

    @Override 
    public boolean onActionItemClicked(ActionMode mode, MenuItem item) { 

     switch (item.getItemId()) { 
     case R.id.copy: 
      getSelectedData(); 
      mode.finish(); 
      return true; 
     case R.id.share: 
      mode.finish(); 
      return true; 
     default: 
      mode.finish(); 
      return false; 
     } 
    } 
    @Override 
    public void onDestroyActionMode(ActionMode mode) { 
     if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) { 
      clearFocus(); 
     }else{ 
      if (mSelectActionModeCallback != null) { 
       mSelectActionModeCallback.onDestroyActionMode(mode); 
      } 
      mActionMode = null; 
     } 
    } 
} 
private void getSelectedData(){ 

    String js= "(function getSelectedText() {"+ 
      "var txt;"+ 
      "if (window.getSelection) {"+ 
       "txt = window.getSelection().toString();"+ 
      "} else if (window.document.getSelection) {"+ 
       "txt = window.document.getSelection().toString();"+ 
      "} else if (window.document.selection) {"+ 
       "txt = window.document.selection.createRange().text;"+ 
      "}"+ 
      "JSInterface.getText(txt);"+ 
      "})()"; 
    // calling the js function 
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) { 
     evaluateJavascript("javascript:"+js, null); 
    }else{ 
     loadUrl("javascript:"+js); 
    } 
} 

private class CustomGestureListener extends GestureDetector.SimpleOnGestureListener { 
    @Override 
    public boolean onSingleTapUp(MotionEvent e) { 
     if (mActionMode != null) { 
      mActionMode.finish(); 
      return true; 
     } 
     return false; 
    } 
} 

@Override 
public boolean onTouchEvent(MotionEvent event) { 
    // Send the event to our gesture detector 
    // If it is implemented, there will be a return value 
    if(mDetector !=null) 
     mDetector.onTouchEvent(event); 
    // If the detected gesture is unimplemented, send it to the superclass 
    return super.onTouchEvent(event); 
} 

}

Bước 2: tạo lớp học riêng cho giao diện WebView. Lớp này listnes cho sự kiện từ khi mã javascript được nhận được thực hiện

public class WebAppInterface { 
Context mContext; 

WebAppInterface(Context c) { 
    mContext = c; 
} 

@JavascriptInterface 
public void getText(String text) { 
    // put selected text into clipdata 
    ClipboardManager clipboard = (ClipboardManager) 
      mContext.getSystemService(Context.CLIPBOARD_SERVICE); 
    ClipData clip = ClipData.newPlainText("simple text",text); 
    clipboard.setPrimaryClip(clip); 
    // gives the toast for selected text 
    Toast.makeText(mContext, text, Toast.LENGTH_SHORT).show(); 
} 
} 

Bước 3: Thêm menu.xml cho menu tùy chỉnh trong res> Thư mục trình đơn

<?xml version="1.0" encoding="utf-8"?> 
<menu xmlns:android="http://schemas.android.com/apk/res/android" > 
<item 
    android:id="@+id/copy" 
    android:icon="@drawable/ic_action_copy" 
    android:showAsAction="always" 
    android:title="copy"> 
</item> 
<item 
    android:id="@+id/share" 
    android:icon="@drawable/ic_action_share" 
    android:showAsAction="always" 
    android:title="share"> 
</item> 

tôi đã giúp đỡ của một số liên kết được liệt kê dưới đây để đạt được điều này: Nhờ các bạn.

làm thế nào để sử dụng javascript trên webview http://developer.android.com/guide/webapps/webview.html#UsingJavaScript

cho tiêm javascript Why can't I inject this javascript in the webview on android?

cho trọng thanh hành động mặc định How to override default text selection of android webview os 4.1+?

cho phiên bản 4.0. đến 4.3 lựa chọn văn bản Webview text selection not clearing

+0

làm thế nào để kích hoạt lựa chọn trên báo chí dài của webview? hãy giúp tôi ra cho rằng :) –

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