Użytkownicy często chcą się komunikować przy użyciu emotikonów, naklejek i innych rodzajów bogatych treści. treści. W poprzednich wersjach Androida klawiatury ekranowe – nazywane też edytorów metod wprowadzania lub edytory IME – mogą wysyłać do aplikacji tylko emotikony w formacie Unicode. Do tworzenia treści multimedialnych interfejsów API przeznaczonych do określonych aplikacji, których nie można używać w innych aplikacjach, lub które obejmują obejścia, takie jak wysyłanie obrazów za pomocą prostego udostępniania, lub ze schowka.
Począwszy od Androida w wersji 7.1 (poziom interfejsu API 25) pakiet Android SDK zawiera zatwierdzenie Content API, który zapewnia uniwersalny sposób wysyłania obrazów i innych plików szczegółowe treści bezpośrednio do edytora tekstu w aplikacji. Ten interfejs API jest również dostępny w i Bibliotekę pomocy w wersji 13 od wersji 25.0.0. Zalecamy skorzystanie z pomocy Biblioteka, bo zawiera metody pomocnicze, które upraszczają implementację.
Za jego pomocą można tworzyć aplikacje do obsługi wiadomości, które akceptują treści multimedialne klawiatury, które umożliwiają wysyłanie szczegółowych treści do dowolnej aplikacji. Google Klawiatura i aplikacji takich jak Wiadomości firmy Google obsługiwać interfejsu Commit Content API na Androidzie 7.1, jak pokazano na ilustracji 1.
Z tego dokumentu dowiesz się, jak wdrożyć interfejs Commit Content API zarówno w edytorach IME, jak i aplikacji.
Jak to działa
Wstawianie obrazu klawiatury wymaga użycia edytora IME i aplikacji. Poniżej opisujemy każdy krok procesu wstawiania obrazu:
Gdy użytkownik kliknie
EditText
, redaktor wysyła listę typów treści MIME, które akceptuje wEditorInfo.contentMimeTypes
edytor IME odczytuje listę obsługiwanych typów i wyświetla zawartość akceptowanej przez edytor.
Gdy użytkownik wybiera obraz, IME wywołuje
commitContent()
i wysyłaInputContentInfo
do redaktora. WywołaniecommitContent()
jest analogiczne do wywołaniacommitText()
, ale w przypadku szczegółowych treści.InputContentInfo
zawiera identyfikator URI, który identyfikuje treść dostawcy usług.
Proces ten pokazano na rys. 2:
Dodawanie obsługi obrazów do aplikacji
Aby akceptować treści sformatowane za pomocą IME, aplikacja musi poinformować IME, jakiego typu treści dotyczy
akceptuje i określa metodę wywołania zwrotnego, która jest wykonywana po odebraniu treści.
Poniższy przykład pokazuje, jak utworzyć plik EditText
, który akceptuje pliki PNG
obrazy:
Kotlin
var editText: EditText = object : EditText(this) { override fun onCreateInputConnection(outAttrs: EditorInfo): InputConnection { var ic = super.onCreateInputConnection(outAttrs) EditorInfoCompat.setContentMimeTypes(outAttrs, arrayOf("image/png")) val mimeTypes = ViewCompat.getOnReceiveContentMimeTypes(this) if (mimeTypes != null) { EditorInfoCompat.setContentMimeTypes(outAttrs, mimeTypes) ic = InputConnectionCompat.createWrapper(this, ic, outAttrs) } return ic } }
Java
EditText editText = new EditText(this) { @Override public InputConnection onCreateInputConnection(EditorInfo outAttrs) { InputConnection ic = super.onCreateInputConnection(outAttrs); EditorInfoCompat.setContentMimeTypes(outAttrs, new String[]{"image/png"}); String[] mimeTypes = ViewCompat.getOnReceiveContentMimeTypes(this); if (mimeTypes != null) { EditorInfoCompat.setContentMimeTypes(outAttrs, mimeTypes); ic = InputConnectionCompat.createWrapper(this, ic, outAttrs); } return ic; } };
Dalsze wyjaśnienie:
Ten przykład korzysta z biblioteki pomocy, więc zawiera ona pewne odniesienia
android.support.v13.view.inputmethod
zamiastandroid.view.inputmethod
W tym przykładzie tworzymy pole
EditText
i zastępujemy jegoonCreateInputConnection(EditorInfo)
. do modyfikowaniaInputConnection
InputConnection
to kanał komunikacji między IME a interfejsem która odbiera dane wejściowe.Rozmowa
super.onCreateInputConnection()
zachowuje wbudowane działanie (wysyłanie i odbieranie tekstu) oraz zawiera odniesienie do elementuInputConnection
.setContentMimeTypes()
dodaje listę obsługiwanych typów MIME do polaEditorInfo
Zadzwoń do nassuper.onCreateInputConnection()
przedsetContentMimeTypes()
.Pole
callback
jest wykonywane za każdym razem, gdy IME zatwierdzi treść. MetodaonCommitContent()
zawiera odwołanie doInputContentInfoCompat
, , który zawiera identyfikator URI treści.- Wysyłanie próśb o uprawnienia i ich publikowanie, jeśli aplikacja działa na poziomie interfejsu API 25.
lub wyższej, a
INPUT_CONTENT_GRANT_READ_URI_PERMISSION
flaga jest ustawiana przez IME. W przeciwnym razie masz już dostęp do tych treści Identyfikator URI, ponieważ jest przyznawany przez IME lub dostawca treści nie ogranicza dostępu. Więcej informacji znajdziesz w artykule Dodawanie obsługi obrazów do usługi IME.
- Wysyłanie próśb o uprawnienia i ich publikowanie, jeśli aplikacja działa na poziomie interfejsu API 25.
lub wyższej, a
createWrapper()
otaczaInputConnection
, zmodyfikowanyEditorInfo
i wywołanie zwrotne w nowyInputConnection
i zwraca go.
Oto zalecane metody:
Edytorzy, którzy nie obsługują szczegółowych treści, nie zadzwonią
setContentMimeTypes()
i opuszczają zestawEditorInfo.contentMimeTypes
donull
.Edytorzy ignorują treść, jeśli typ MIME jest określony w polu
InputContentInfo
nie pasuje do żadnego z akceptowanych typów.Szczegółowe treści nie mają na nie wpływu i nie mają na nie wpływu kursora. Edytorzy mogą ignorować pozycję kursora podczas pracy z treścią.
W
OnCommitContentListener.onCommitContent()
, możesz zwrócićtrue
asynchronicznie, nawet przed wczytaniem treści.W przeciwieństwie do tekstu, który można edytować w IME przed zatwierdzeniem, bogatym od razu po publikacji. Jeśli chcesz zezwolić użytkownikom na edytowanie lub usuwanie treści, samodzielnie zaimplementuj daną logikę.
Aby przetestować aplikację, upewnij się, że urządzenie lub emulator ma klawiaturę, która może wysyłać szczegółowe treści. Klawiatury Google możesz używać w Androidzie 7.1 lub nowszym.
Dodawanie obsługi obrazów do IME
edytory IME, które chcą wysyłać do aplikacji szczegółowe treści, muszą zaimplementować zatwierdzanie treści API zgodnie z tym przykładem:
- Zastąp
onStartInput()
lubonStartInputView()
i przeczytaj listę obsługiwanych typów treści w środowisku docelowym redaktorem. Fragment kodu poniżej pokazuje, jak sprawdzić, czy element docelowy Edytor akceptuje obrazy GIF.
Kotlin
override fun onStartInputView(editorInfo: EditorInfo, restarting: Boolean) { val mimeTypes: Array<String> = EditorInfoCompat.getContentMimeTypes(editorInfo) val gifSupported: Boolean = mimeTypes.any { ClipDescription.compareMimeTypes(it, "image/gif") } if (gifSupported) { // The target editor supports GIFs. Enable the corresponding content. } else { // The target editor doesn't support GIFs. Disable the corresponding // content. } }
Java
@Override public void onStartInputView(EditorInfo info, boolean restarting) { String[] mimeTypes = EditorInfoCompat.getContentMimeTypes(editorInfo); boolean gifSupported = false; for (String mimeType : mimeTypes) { if (ClipDescription.compareMimeTypes(mimeType, "image/gif")) { gifSupported = true; } } if (gifSupported) { // The target editor supports GIFs. Enable the corresponding content. } else { // The target editor doesn't support GIFs. Disable the corresponding // content. } }
- Zatwierdzanie treści w aplikacji, gdy użytkownik wybiera obraz. Nie dzwoń
commitContent()
. może spowodować utratę zaznaczenia przez edytora. Fragment kodu poniżej pokazuje, aby zatwierdzić obraz GIF.
Kotlin
// Commits a GIF image. // @param contentUri = Content URI of the GIF image to be sent. // @param imageDescription = Description of the GIF image to be sent. fun commitGifImage(contentUri: Uri, imageDescription: String) { val inputContentInfo = InputContentInfoCompat( contentUri, ClipDescription(imageDescription, arrayOf("image/gif")), null ) val inputConnection = currentInputConnection val editorInfo = currentInputEditorInfo var flags = 0 if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N_MR1) { flags = flags or InputConnectionCompat.INPUT_CONTENT_GRANT_READ_URI_PERMISSION } InputConnectionCompat.commitContent(inputConnection, editorInfo, inputContentInfo, flags, null) }
Java
// Commits a GIF image. // @param contentUri = Content URI of the GIF image to be sent. // @param imageDescription = Description of the GIF image to be sent. public static void commitGifImage(Uri contentUri, String imageDescription) { InputContentInfoCompat inputContentInfo = new InputContentInfoCompat( contentUri, new ClipDescription(imageDescription, new String[]{"image/gif"}), null ); InputConnection inputConnection = getCurrentInputConnection(); EditorInfo editorInfo = getCurrentInputEditorInfo(); Int flags = 0; if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N_MR1) { flags |= InputConnectionCompat.INPUT_CONTENT_GRANT_READ_URI_PERMISSION; } InputConnectionCompat.commitContent( inputConnection, editorInfo, inputContentInfo, flags, null); }
Autor edytora IME musi najprawdopodobniej wdrożyć własnego dostawcę treści,
odpowiadać na żądania URI treści. Wyjątkiem jest sytuacja, gdy edytor IME obsługuje treści
od obecnych dostawców treści, takich jak
MediaStore
Informacje na temat:
tworzenia dostawców treści, zobacz materiały
dostawcy i file
dla dostawcy.
Jeśli tworzysz własnego dostawcę treści, odradzamy jego eksportowanie.
przez ustawienie
android:exported
do
false
Zamiast tego włącz przyznawanie uprawnień u dostawcy przez ustawienie
android:grantUriPermission
do true
. Następnie edytor IME może przyznać uprawnienia dostępu do identyfikatora URI treści,
że treści są objęte zasadą. Można to zrobić na dwa sposoby:
Na Androidzie 7.1 (poziom interfejsu API 25) i nowszych podczas wywoływania funkcji
commitContent()
ustaw parametr flagi naINPUT_CONTENT_GRANT_READ_URI_PERMISSION
Następnie obiektInputContentInfo
odbierany przez aplikację może zażądać żądania i zwolnij tymczasowe uprawnienia do odczytu, wywołującrequestPermission()
. orazreleasePermission()
W Androidzie 7.0 (poziom interfejsu API 24) i starszych Pole
INPUT_CONTENT_GRANT_READ_URI_PERMISSION
jest ignorowane, więc przyznaj je ręcznie dostępu do treści. Można to zrobić na przykład za pomocągrantUriPermission()
, ale możesz wdrożyć własny mechanizm, który który spełnia Twoje potrzeby.
Aby przetestować edytor IME, upewnij się, że na urządzeniu lub emulatorze jest aplikacja, która odbiera szczegółowe treści. Aplikacja Google Messenger działa na Androidzie 7.1 lub nowszym.