2011-05-19 6 views
13

Je veux permettre à l'utilisateur de sélectionner des textes de webview et il doit être envoyé comme un message texte. pls trouver le moyen de sélectionner le texte et copier dans le presse-papiers et l'extraction du presse-papiers. je l'ai vu de nombreux exemples, mais rien ne m'a aidé vraiment ... TIAAndroid: comment sélectionner les textes de webview

Modifier
en utilisant le code fourni dans le lien de @ orangmoney52. avec les modifications suivantes

getmethod est le deuxième paramètre et appelle le deuxième paramètre de la méthode. si je donne un avertissement, un avertissement viendra ... lequel est correct?

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); 
     } 

} 

Obtenir cette erreur:

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

Veuillez ajouter l'extrait complet –

Répondre

14

Les réponses ci-dessus semble parfaitement bien et il semble que vous manque quelque chose lors de la sélection du texte. Donc, vous devez vérifier le code et trouver votre TouchEvent Webview.

i Essayé ci-dessous le code il fonctionne très bien ...

Fonction est

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); 
     } 
    } 

Appel méthode ci-dessus chaque fois que vous voulez (vous pouvez mettre un bouton et appeler cette méthode dans son événement click): emulateShiftHeld (mWebView);

+1

Sur Android 4+ ne fonctionne pas. http://stackoverflow.com/questions/21101181/android-webview-how-to-correctly-copy-selected-text –

+10

Je ne comprends même pas ce que cette réponse essaie de dire. – Michael

+0

s'il vous plaît ajouter l'extrait entier ici si novice peut l'utiliser facilement –

0

@vnshetty, en utilisant le code fourni dans le lien de @ orangmoney52, j'ai pu compléter ce problème il y a quelques mois. Vous pouvez créer un bouton dans votre menu qui vous permet de copier du texte. Puis, en onOptionsItemSelected, vous pouvez avoir une clause comme celui-ci:

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

Oui Une fois le toast affiché, appuyez sur Maj et essayez de sélectionner le contenu de la page Web à l'aide de la souris, mais rien n'est sélectionné? Est-ce que je manque quelque chose? – vnshetty

+0

Il n'est pas nécessaire d'appuyer sur la touche Maj. Sélectionnez simplement le texte après l'affichage du message toast. – Phil

5

La meilleure façon, mais pas aussi jolie que ce qui semble être un par fabricant mis en œuvre fonction copier/coller, est la suivante:

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

En fait, si vous configurez votre propre WebChromeClient via webview.setWebChromeClient(...) la sélection de texte est désactivée par défaut. Pour lui permettre à vos besoins WebChromeClient d'avoir à suivre la méthode mise en œuvre:

//@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

Dans mon cas, il est également pas workng.Je suis prioritaire onTouch() mais il retourne faux. Quel était le vrai problème, avez-vous ignoré les événements tactiles? – DroidBot

+0

Ma suggestion était de ne pas surcharger onTouch(). Êtes-vous les paramètres de votre propre, personnalisé, WebChromeClient? –

+0

Hey ça fonctionne réellement! – Bruce

6

Étape: 1 Créer classe personnalisée WebView. Cette classe remplacera la barre d'actions native lors d'une pression longue sur le texte de la vue Web. Aussi il gère le cas de sélection pour la version différente d'android (testé à partir de 4.0) Ce code prend le texte sélectionné en utilisant 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); 
} 

}

Étape 2: créer une catégorie distincte pour l'interface WebView. Cette classe listnes pour l'événement d'une fois le code javascript est CHAISE

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(); 
} 
} 

Étape 3: Ajouter menu.xml pour le menu personnalisé dans res> dossier de menu

<?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> 

J'ai pris aide de plusieurs liens ci-dessous pour y parvenir: Merci à vous les gars.

comment utiliser javascript sur WebView http://developer.android.com/guide/webapps/webview.html#UsingJavaScript

pour injecter javascript Why can't I inject this javascript in the webview on android?

pour des raisons impérieuses barre d'action par défaut How to override default text selection of android webview os 4.1+?

pour la version 4.0. à 4.3 sélection de texte Webview text selection not clearing

+0

comment activer la sélection sur une pression longue de webview? aidez-moi s'il vous plaît pour ça :) –