Чи можливо записати у буфер обміну пристрою за допомогою ADB?


26

Мені цікаво навчитися писати в буфер обміну пристрою Android, а якщо це можливо, читати.

Я сподіваюся зробити це за допомогою ADB через USB, і я не зацікавлений у встановленні будь-яких додатків, які допоможуть мені це зробити, оскільки це те, що я планую рідко робити.

Будемо дуже вдячні за будь-які пропозиції чи допомогу, що направляють мене в правильному напрямку.


Для тих , хто що шукає легше підходить для емуляторів, дивіться тут: stackoverflow.com/questions/3391160 / ...
Mygod

Відповіді:


21

Так, ви насправді можете це зробити. Це дивовижно виглядає, коли ви оглядаєте буфер обміну, але це працює просто чудово.

Спочатку ви можете перевірити поточний вміст буфера обміну з service call clipboard 1оболонки adb (або, не спочатку обстріляючи adb shell service call clipboard 1). Він може початися спочатку порожнім після перезавантаження, наприклад:

# service call clipboard 1
Result: Parcel(
  0x00000000: 00000000 00000001 00000000 00000000 '................'
  0x00000010: 00000000 00000000                   '........        ')
#

Ви можете помістити текст у буфер обміну за допомогою service call clipboard 2, який в основному займає 3 параметри - два вставки та рядок, який ви хочете помістити в буфер обміну:

# service call clipboard 2 i32 1 i32 0 s16 "Hi there"
Result: Parcel(00000000    '....')

Якщо чесно, я не впевнений, що таке перші два параметри. Одна відповідь на переповнення стека підказує , що перший int - це "кількість елементів у посилці" (один у цьому випадку), а другий - довжина рядка. Однак я використав 0 для другого параметра, і він працює чудово, і я не можу знайти жодної документації, яка б відповідала цій конкретній функції ... тому прийміть це за те, що воно варто.

У будь-якому випадку, це в основному створення об'єкта Parcel з 3-х полів, а потім передавання його в буфер обміну. Потім буфер обміну розпаковує посилку і встановлює значення рядка, передане як вміст буфера обміну. Це можна побачити, коли ви перейдете до отримання значення згодом:

# service call clipboard 1
Result: Parcel(
  0x00000000: 00000000 00000001 00000000 00000008 '................'
  0x00000010: 00690048 00740020 00650068 00650072 'H.i. .t.h.e.r.e.'
  0x00000020: 00000000 00000000                   '........        ')
#

Так само, якщо довго натиснути на поле для введення тексту і натиснути «Вставити» після цього, ви отримаєте текст, який було встановлено через call service clipboard 2рядок вище (і він буде виглядати цілком нормально).

(Наведені вище приклади походять з мого HTC EVO, запустивши CyanogenMod 7)


1
Нарешті я можу вставити свій ключ WPA і підключитися до маршрутизатора: D. Дякую.
earthmeLon

3
@earthmeLon, якщо ви просто намагалися знайти простий спосіб скопіювати свій ключ WPA, то наступного разу вам може бути легше зробити таке, як надіслати його електронною поштою та скопіювати / вставити з електронної пошти або скопіювати текстовий файл, що містить його на свій пристрою через USB, потім відкрийте та скопіюйте звідти. Існують і інші варіанти, наприклад Wifi Keyboard, які дозволяють вводити (або вставляти) з ПК і відображати його на телефоні.
GAThrawn

4
Мій ключ WPA є чутливим. Він не повинен транслюватись через будь-яку не локальну мережу. Дякуємо за пропозиції @GAThrawn. Зрештою, я знайду більше користі для цієї функціональності: D
earthmeLon

6
Я отримую '........U.n.k.n.' 'o.w.n. .p.a.c.k.' 'a.g.e. ..... ')при виготовленніcall service clipboard 2
cprcrack

3
Якщо вам потрібно скопіювати свій пароль або будь-який текст у текстове поле на android, ви також можете "abd ввести текст оболонки" String "" - Я відмовився від буфера обміну ...
Philippe

14

Я використовував цю методологію, і вона прекрасно спрацювала в 4.х, але не вдалася для мене в льодянику. Шукаючи альтернативного рішення, я знайшов таке: /programming/3391160/paste-text-on-android-emulator

це не зовсім так, як ви цього хотіли, але для себе більшість часу я хочу скопіювати текст у буфер обміну, тому що я хочу вставити його в поле пароля.

як додатковий бонус, ось мій сценарій ( відредаговано 2015-04-24, щоб дозволити пробіли в тексті ):

#!/bin/bash

if [[ "$1" != "" ]]
then
    TEXT=$1
else
    read -s -p "Enter text you want to insert: " TEXT
fi

ESCAPED_TEXT=`echo $TEXT | sed "s/\s/\%s/g"`
adb shell input text "$ESCAPED_TEXT"

Причина, що вам потрібно подвоїти рядок у тому, що це дві оболонки: ваша оболонка та оболонка adb . Однак я підозрюю, що це не вдасться до інших символів, які мають особливе значення в оболонці, як, наприклад, амперсанд .
Дан Даскалеску

Насправді завдання adb shell було б правильно виконати це втечу, але, мабуть, це не повністю. У моїй версії (1.0.31) використовуваний вище пробіл не потрібен, але всі види спеціальних символів потребують втечі (але це неможливо зробити надійно).
Matthijs Kooijman

Кращим способом обробки спеціальних символів буде передача через stdin, щось на кшталт: echo "$TEXT" | adb shell xargs -0 input textЯкий повинен обробляти будь-який текст, крім символів \ 0 (NUL). На жаль, старі версії adb не пересилають stdin до команди, вказаної в командному рядку adb. Це виправлено в нових версіях ADB, але це необхідно для Android N працювати .
Matthijs Kooijman

Що стосується простору, який залишається, це, очевидно, потрібно для inputкоманди на пристрої Android, а не для оболонки, яку використовує adb shell. Крім того, він потрібен лише для SDK версії 22 і нижче (Lollipop і нижче, я вважаю) відповідно до цієї відповіді .
Matthijs Kooijman

4

Ось вдосконалена версія сценарію, розміщена вище. Як і у цьому сценарії, він не записує у буфер обміну, але надсилає вхід у сфокусоване на даний момент поле введення, що часто так і хочеться.

Цей скрипт вдосконалений, щоб уникнути спеціальних символів, щоб не плутати оболонку Android з ними. Це повинно дозволити надсилання будь-якого рядка в незмінному вигляді. Для того, щоб readкоманда не інтерпретувала (зворотний) ривок, я додав туди -r.

Це було протестовано за допомогою наступного списку спеціальних символів:

./adb-send-string ' \`~!@#$%^&*()-_=+[{]}|;:",<.>/?'\'

Ось сценарій:

#!/bin/bash
# Send text to android device using adb, emulating keyboard input.
# Based on a script from /android//a/105881/223695
# extended to support special characters

if [[ "$1" != "" ]]
then
    TEXT="$1"
else
    read -s -r -p "Enter text you want to insert: " TEXT
fi

escape() {
    # Encapsulate the string in $'', which enables interpretation of
    # \xnn escapes in the string. This is not POSIX-sh, but an extension
    # documented by bash and also supported by the Android sh.
    echo -n "$'"

    # Process each character in $1 one by one
    for (( i=0 ; i<${#1}; i++ )); do
        # Extract the i'th character
        C="${1:$i:1}"
        if [ "$C" = ' ' ]; then
            # Encode spaces as %s, which is needed for Android's
            # "input text" command below 6.0 Marshmellow
            # See /programming//documentation/android/9408/adb-shell/3958/send-text-key-pressed-and-touch-events-to-android-device-via-adb
            echo -n '%s'
        else
            # Encode everything else as \xnn, to prevent them from being
            # interpreted by the Android shell
            printf '\\x%02x' "'$C"
        fi
    done
    # Terminate the $''
    echo -n "'"
}

ESCAPED_TEXT=`escape "$TEXT"`
adb shell input text "$ESCAPED_TEXT"

3

Я трохи спробував і гугл, і здається, що підхід до служби викликів-буфер обміну перестав працювати в нових андроїдах, він не зміг для мене на версії Android 4.4.4. Тобто вам знадобиться додаток, щоб отримати доступ до буфера обміну (читання та запис) з adb-shell. Я використовую машинку з majido на GitHub . Апк також розміщений, тому не потрібно складати його самостійно. Після встановлення ви можете зв’язатися з ним за допомогою команд широкомовної передачі (додаток підкаже точні команди). Додаток не потребує root.


Оскільки ми не знаємо, яка ваша мета: чи можете ви, будь ласка, відредагувати свою публікацію та включити, що робить цей додаток, і як він повинен ним користуватися? Люди вже починають позначати вашу публікацію як "не відповідь", оскільки вони, очевидно, пропускають точку, яку ви хочете зробити. Спасибі заздалегідь!
Izzy

clipper працював для мене краще, ніж використання "adb shell text text". Навіть краще, ніж сценарій Python AdbPaste github.com/gcb/AdbPaste, щоб обернути "вхідний текст оболонки adb". Я вдосконалив машинку для інсталяції, щоб підтримувати параметр файлу, і тепер я можу надсилати декілька сторінок у буфер обміну лише за секунду-дві. Розширений код тут: github.com/RoundSparrow/clipper
RoundSparrow hilltx

0

Ще один сценарій, який використовується adb shell inputдля надсилання символів, можна знайти тут: https://github.com/gcb/AdbPaste

Це сценарій Python, який можна клонувати з github, а також безпосередньо завантажити та запустити:

$ wget https://github.com/gcb/AdbPaste/raw/master/AdbPaste.py
$ chmod a+x AdbPaste.py
$ ./AdbPaste.py "some text to paste"
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.