2015-05-03 6 views
18

Wenn ich meinen Code auf API22 ausführen funktioniert es gut, Einfügen der "Testing Testing" in meiner erforderlichen EditText in der App, die die initiiert. Aber wenn ich es auf API 17 ausführe, funktioniert es nicht. Er kopiert die Daten in den Clip, kann sie jedoch nicht einfügen. Ich benötige den Mechanismus, um mit API 16 und höher zu arbeiten.Einfügen von AccessibilityService funktioniert in API22 funktioniert nicht in API17

Dies ist mein Code so weit:

public class MyAccessibilityService extends AccessibilityService { 
    @Override 
    public void onAccessibilityEvent(AccessibilityEvent event) { 
     AccessibilityNodeInfo nodeInf = null; 
     AccessibilityNodeInfo nodeInfo = null; 
     final int eventType = event.getEventType(); 
     String eventText = null; 
     switch(eventType) { 
      case AccessibilityEvent.TYPE_VIEW_CLICKED: 
       eventText = "Clicked: "; 
       nodeInf = this.getRootInActiveWindow(); 
       Log.d("AccessibilityNodeInfo", ""+ nodeInf.getChildCount()); 
       nodeInf.recycle(); 
       break; 
      case AccessibilityEvent.TYPE_VIEW_FOCUSED: 
       AccessibilityRecordCompat record = AccessibilityEventCompat.asRecord(event); 
       AccessibilityNodeInfoCompat source = record.getSource(); 

       ClipboardManager clipboard = (ClipboardManager) this.getSystemService(Context.CLIPBOARD_SERVICE); 
       ClipData clip = ClipData.newPlainText("label", "TESTING TESTING"); 
       clipboard.setPrimaryClip(clip); 

       source.performAction(AccessibilityNodeInfoCompat.ACTION_PASTE); 
       //} 

       Log.d("AccessibilityNodeInfo", ""+ source.getClassName()); 
       Intent intent = new Intent(MyAccessibilityService.this, TestActivity.class); 
       intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 
       intent.addFlags(Intent.FLAG_ACTIVITY_MULTIPLE_TASK); 
       startActivity(intent); 
       break; 
     } 


     eventText = eventText + event.getText(); 

     // Do something nifty with this text, like speak the composed string 
     // back to the user. 
     Log.d("Information", eventText); 
     Toast.makeText(getApplicationContext(), eventText + " " + android.os.Build.VERSION.SDK_INT, 
       Toast.LENGTH_LONG).show(); 
    } 
} 
+0

Haben Sie diese Frage geprüft [AccessibilityService gestartet wird aber nicht erhalten AccessibilityEvents auf JellyBean] (http://stackoverflow.com/questions/12019848/accessibilityservice-is-started-but-does-not-receive-accessibilityevents-on-jell)? – Sufian

Antwort

8

Leider AccessibilityNodeInfo.ACTION_PASTE ist in API-Ebene 18 hinzugefügt, aus diesem Grund funktioniert es nicht mit API 17 und niedriger. AccessibilityNodeInfoCompat ist nur ein Wrapper für vorhandene Features, es bietet keine benutzerdefinierte Implementierung fehlender Features.

Die Quellen der v4 Support-Bibliothek sind ziemlich klar:

Wenn Sie performAction in AccessibilityNodeInfoCompat die Support-Bibliothek IMPL.performAction[1]

public boolean performAction(int action) { 
    return IMPL.performAction(mInfo, action); 
} 

IMPL ist AccessibilityNodeInfoJellybeanImpl wenn API-Ebene ruft 16 und 17 ist [2]

nennen
if (Build.VERSION.SDK_INT >= 22) { 
    IMPL = new AccessibilityNodeInfoApi22Impl(); 
} else if (Build.VERSION.SDK_INT >= 21) { 
    IMPL = new AccessibilityNodeInfoApi21Impl(); 
} else if (Build.VERSION.SDK_INT >= 19) { // KitKat 
    IMPL = new AccessibilityNodeInfoKitKatImpl(); 
} else if (Build.VERSION.SDK_INT >= 18) { // JellyBean MR2 
    IMPL = new AccessibilityNodeInfoJellybeanMr2Impl(); 
} else if (Build.VERSION.SDK_INT >= 16) { // JellyBean 
    IMPL = new AccessibilityNodeInfoJellybeanImpl(); 
} else if (Build.VERSION.SDK_INT >= 14) { // ICS 
    IMPL = new AccessibilityNodeInfoIcsImpl(); 
} else { 
    IMPL = new AccessibilityNodeInfoStubImpl(); 
} 

Dies ist performAction in AccessibilityNodeInfoJellybeanImpl[3]

public static boolean performAction(Object info, int action, Bundle arguments) { 
    return ((AccessibilityNodeInfo) info).performAction(action, arguments); 
} 

Wie Sie die der Support-Bibliothek Aufruf performAction des Standard android.view.accessibility.AccessibilityNodeInfo sehen können, so dass, wenn das System nicht ACTION_PASTE unterstützt leider auch die v4 Support-Bibliothek nicht ACTION_PASTE unterstützen.

können Sie überprüfen, ob ACTION_PASTE mit diesem Code unterstützt:

AccessibilityNodeInfoCompat source = record.getSource(); 
int supportedActions = source.getActions(); 
boolean isSupported = (supportedActions & AccessibilityNodeInfoCompat.ACTION_PASTE) == AccessibilityNodeInfoCompat.ACTION_PASTE; 
Log.d(TAG, String.format("AccessibilityNodeInfoCompat.ACTION_PASTE %1$s supported", isSupported ? "is" : "is NOT")); 
+0

Der Zweck der Kompatibilitäts-Android-Bibliothek besteht darin, dem Entwickler zu ermöglichen, Funktionen in seinen Apps zu erstellen, die in der vorherigen Version nicht verfügbar sind. Daher sollte AccessibilityNodeInfoCompat die Funktionen bereitstellen, die nach API18 in API 17 android verfügbar sind. [AccessibilityNodeInfoCompat] (http://developer.android.com/reference/android/support/v4/view/accessibility/AccessibilityNodeInfoCompat.html) Dokumentation bestätigt es – RehanZahoor

+0

Ich weiß, was der Zweck der Compatibility Android Library ist, leider ist das nicht der Fall. Wie Sie in dem Link sehen können, den Sie gerade in der Klassenübersicht _ "Hilfsprogramm für den Zugriff auf AccessibilityNodeInfo freigegeben haben, das nach API Level 4 rückwärtskompatibel eingeführt wurde." _. AccessibilityNodeInfoCompat stellt keine zusätzlichen Funktionen bereit und ermöglicht Ihnen den Zugriff auf vorhandene Funktionen. –

+0

Der Code, den Sie angegeben haben, um zu überprüfen, ob ACTION_PASTE unterstützt wird, funktioniert nicht. Android Studio kennzeichnet supportedActions. – RehanZahoor

2

Vielleicht sollten Sie Ihre Antwort verbessern und einige weitere Details über Ihre Importe hinzufügen.


Einfügen: Wie Sie in Ihrem Kommentar erwähnt, es geht mehr um die Sache aus der Zwischenablage wieder zu bekommen?

Ab dem Android Copy and Paste Documentation können Sie den kopierten Inhalt als Text wie diese:

// Examines the item on the clipboard. If getText() does not return null, the clip item contains the 
// text. Assumes that this application can only handle one item at a time. 
ClipData.Item item = clipboard.getPrimaryClip().getItemAt(0); 

// Gets the clipboard as text. 
pasteData = item.getText(); 

// If the string contains data, then the paste operation is done 
if (pasteData != null) { 
    return; 

// The clipboard does not contain text. If it contains a URI, attempts to get data from it 
} else { 
    Uri pasteUri = item.getUri(); 

    // If the URI contains something, try to get text from it 
    if (pasteUri != null) { 

     // calls a routine to resolve the URI and get data from it. This routine is not 
     // presented here. 
     pasteData = resolveUri(Uri); 
     return; 
    } else { 

    // Something is wrong. The MIME type was plain text, but the clipboard does not contain either 
    // text or a Uri. Report an error. 
    Log.e("Clipboard contains an invalid data type"); 
    return; 
    } 
} 

Kopieren:

Es gibt zwei verschiedene Varianten des ClipBoardManager. Der neue wurde mit Honeycomb eingeführt. Sie müssen sicherstellen, dass Ihr Code die richtige Variante verwendet.

Schauen Sie sich das Codebeispiel:

int sdk = android.os.Build.VERSION.SDK_INT; 
if(sdk < android.os.Build.VERSION_CODES.HONEYCOMB) { 
    android.text.ClipboardManager clipboard = (android.text.ClipboardManager) getSystemService(Context.CLIPBOARD_SERVICE); 
    clipboard.setText("text to clip"); 
} else { 
    android.content.ClipboardManager clipboard = (android.content.ClipboardManager) getSystemService(Context.CLIPBOARD_SERVICE); 
    android.content.ClipData clip = android.content.ClipData.newPlainText("text label","text to clip"); 
    clipboard.setPrimaryClip(clip); 
} 

Dies ist nur eine Annahme, wie die Frage, vermisst einige Informationen.

+0

Kein Problem mit der Kopiermethode. Ich möchte, dass mein Code auf API16 und höher funktioniert. HoneyComb ist API11. Nebenbei, wenn ich meine App starte und versuche, in das Feld "Browser-Adresse" einzufügen, fügt sie ein, was vom AccessibilityService eingefügt wird. Das ist der AccessibilityService hat erforderlichen Text in die Zwischenablage kopiert. und es ist nur eine Frage von 'source.performAction (AccessibilityNodeInfoCompat.ACTION_PASTE);' funktioniert nicht. – RehanZahoor

+0

@RehanZahoor können Sie eine kleine Beispiel-App zur Verfügung stellen, die einige Tests erlaubt? – mikepenz

Verwandte Themen