Giriş yöntemi oluşturma

Giriş yöntemi düzenleyici (IME), kullanıcıların metin girmesine olanak tanıyan bir kullanıcı denetimidir. Android, uygulamaların kullanıcılara ekran klavyeleri veya konuşma girişi gibi alternatif giriş yöntemleri sunmasına olanak tanıyan genişletilebilir bir giriş yöntemi çerçevesi sağlar. Kullanıcı, IME'leri yükledikten sonra sistem ayarlarından birini seçip sistemin tamamında kullanabilir. Aynı anda yalnızca bir IME etkinleştirilebilir.

Android sistemine bir IME eklemek için InputMethodService sınıfını genişleten bir sınıf içeren bir Android uygulaması oluşturun. Ayrıca, genellikle IME hizmetine seçenekler aktaran bir "ayarlar" etkinliği oluşturursunuz. Sistem ayarlarının bir parçası olarak görüntülenen bir ayar kullanıcı arayüzü de tanımlayabilirsiniz.

Bu sayfada aşağıdaki konular ele alınmaktadır:

IME'lerle çalışmadıysanız önce Ekran Giriş Yöntemleri başlıklı giriş makalesini okuyun.

IME yaşam döngüsü

Aşağıdaki şemada bir IME'nin yaşam döngüsü açıklanmaktadır:

Bir IME'nin yaşam döngüsünü gösteren resim.
Şekil 1. Bir IME'nin yaşam döngüsü.

Aşağıdaki bölümlerde, bu yaşam döngüsünü izleyen bir IME ile ilişkili kullanıcı arayüzünün ve kodun nasıl uygulanacağı açıklanmaktadır.

Manifest dosyasında IME bileşenlerini bildirme

Android sisteminde IME, özel bir IME hizmeti içeren bir Android uygulamasıdır. Uygulamanın manifest dosyasında hizmet beyan edilmeli, gerekli izinler istenmeli, action.view.InputMethod işlemiyle eşleşen bir intent filtresi sağlanmalı ve IME'nin özelliklerini tanımlayan meta veriler sağlanmalıdır. Ayrıca, kullanıcının IME'nin davranışını değiştirmesine olanak tanıyan bir ayarlar arayüzü sağlamak için Sistem Ayarları'ndan başlatılabilecek bir "ayarlar" etkinliği tanımlayabilirsiniz.

Aşağıdaki snippet'te bir IME hizmeti tanımlanmaktadır. Hizmetin IME'yi sisteme bağlamasına izin vermeBIND_INPUT_METHOD izinini ister, işlemle (android.view.InputMethod) eşleşen bir intent filtresi oluşturur ve IME için meta verileri tanımlar:

<!-- Declares the input method service. -->
<service android:name="FastInputIME"
    android:label="@string/fast_input_label"
    android:permission="android.permission.BIND_INPUT_METHOD">
    <intent-filter>
        <action android:name="android.view.InputMethod" />
    </intent-filter>
    <meta-data android:name="android.view.im"
               android:resource="@xml/method" />
</service>

Aşağıdaki snippet'te, IME için ayarlar etkinliği belirtilmektedir. Bu etkinlik, ACTION_MAIN için bu etkinliğin IME uygulamasının ana giriş noktası olduğunu belirten bir intent filtresine sahiptir:

<!-- Optional: an activity for controlling the IME settings. -->
<activity android:name="FastInputIMESettings"
    android:label="@string/fast_input_settings">
    <intent-filter>
        <action android:name="android.intent.action.MAIN"/>
    </intent-filter>
</activity>

IME'nin ayarlarına doğrudan kullanıcı arayüzünden de erişim sağlayabilirsiniz.

Giriş yöntemi API'si

IME'lere özgü sınıflar android.inputmethodservice ve android.view.inputmethod paketlerinde bulunur. KeyEvent sınıfı, klavye karakterlerini işlemek için önemlidir.

IME'nin merkezi kısmı, InputMethodService sınıfını genişleten bir hizmet bileşenidir. Bu sınıf, normal hizmet yaşam döngüsünü uygulamanın yanı sıra IME'nizin kullanıcı arayüzünü sağlamak, kullanıcı girişini işlemek ve odaktaki alana metin göndermek için geri çağırma işlevlerine sahiptir. Varsayılan olarak InputMethodService sınıfı, IME'nin durumunu ve görünürlüğünü yönetmek ve mevcut giriş alanıyla iletişim kurmak için uygulamanın büyük bir kısmını sağlar.

Aşağıdaki sınıflar da önemlidir:

BaseInputConnection
Bir InputMethod kaynağından girişini alan uygulamaya kadar olan iletişim kanalını tanımlar. İmlecin etrafındaki metni okumak, metni metin kutusuna kaydetmek ve uygulamaya ham önemli etkinlikler göndermek için kullanılır. Uygulamalar, temel InputConnection arayüzünü uygulamak yerine bu sınıfı genişletmelidir.
KeyboardView
View'un, klavye gösteren ve kullanıcı giriş etkinliklerine yanıt veren bir uzantısıdır. Klavye düzeni, bir XML dosyasında tanımlayabileceğiniz Keyboard örneğiyle belirtilir.

Giriş yöntemi kullanıcı arayüzünü tasarlama

IME'de iki ana görsel öğe vardır: giriş görünümü ve adaylar görünümü. Yalnızca tasarladığınız giriş yöntemiyle alakalı öğeleri uygulamanız gerekir.

Giriş görünümü

Giriş görünümü, kullanıcının tuşlara basma, el yazısı veya hareketler şeklinde metin girdiği kullanıcı arayüzüdür. IME ilk kez görüntülendiğinde sistem onCreateInputView() callback'i çağırır. Bu yöntemi uygularken IME penceresinde görüntülemek istediğiniz düzeni oluşturun ve düzeni sisteme döndürün. Aşağıdaki snippet'te onCreateInputView() yönteminin uygulanmasına dair bir örnek gösterilmektedir:

Kotlin

override fun onCreateInputView(): View {
    return layoutInflater.inflate(R.layout.input, null).apply {
        if (this is MyKeyboardView) {
            setOnKeyboardActionListener(this@MyInputMethod)
            keyboard = latinKeyboard
        }
    }
}

Java

@Override
public View onCreateInputView() {
    MyKeyboardView inputView =
        (MyKeyboardView) getLayoutInflater().inflate(R.layout.input, null);

    inputView.setOnKeyboardActionListener(this);
    inputView.setKeyboard(latinKeyboard);

    return inputView;
}

Bu örnekte MyKeyboardView, KeyboardView için Keyboard öğesini oluşturan özel bir uygulama örneğidir.

Adaylar görünümü

Adaylar görünümü, IME'nin kullanıcının seçmesi için olası kelime düzeltmelerini veya önerilerini gösterdiği kullanıcı arayüzüdür. IME yaşam döngüsünde sistem, adayların görünümünü göstermeye hazır olduğunda onCreateCandidatesView() metodunu çağırır. Bu yöntemi uygularken kelime önerilerini gösteren bir düzen döndürün veya hiçbir şey göstermek istemiyorsanız null döndürün. Varsayılan davranış, boş yanıttır. Bu nedenle, öneri sağlamazsanız bunu uygulamanız gerekmez.

Kullanıcı arayüzü tasarımı ile ilgili dikkat edilmesi gereken noktalar

Bu bölümde, IME'lerle ilgili bazı kullanıcı arayüzü tasarımı hususları açıklanmaktadır.

Birden fazla ekran boyutunu işleme

IME'nizin kullanıcı arayüzü, farklı ekran boyutlarına göre ölçeklenebilmeli ve hem yatay hem de dikey yönleri desteklemelidir. Tam ekran olmayan IME modunda, uygulamanın metin alanını ve ilişkili tüm bağlamı göstermesi için yeterli alan bırakın. Böylece, ekranın en fazla yarısı IME tarafından kaplanır. Tam ekran IME modunda bu sorun yaşanmaz.

Farklı giriş türlerini işleme

Android metin alanları, serbest biçimli metin, sayılar, URL'ler, e-posta adresleri ve arama dizeleri gibi belirli bir giriş türü ayarlamanıza olanak tanır. Yeni bir IME uygularken her alanın giriş türünü algılayın ve buna uygun arayüzü sağlayın. Ancak kullanıcının giriş türü için geçerli metin girip girmediğini kontrol etmek üzere IME'nizi ayarlamanıza gerek yoktur. Bu, metin alanının sahibi olan uygulamanın sorumluluğundadır.

Örneğin, Latin IME'nin Android platformu metin girişi için sağladığı arayüz aşağıda verilmiştir:

Latin IME&#39;de metin girişini gösteren resim
Şekil 2. Latin IME metin girişi.

Latin IME'nin Android platformu için sayısal giriş sağlayan arayüzü aşağıda verilmiştir:

Latin IME&#39;de sayısal girişi gösteren bir resim
Şekil 3. Latin IME sayısal girişi.

Bir giriş alanı odaklandığında ve IME'niz başladığında sistem, giriş türü ve metin alanının diğer özellikleriyle ilgili ayrıntıları içeren bir EditorInfo nesnesi göndererek onStartInputView() işlevini çağırır. Bu nesnede, inputType alanı metin alanının giriş türünü içerir.

inputType alanı, çeşitli giriş türü ayarlarının bit kalıplarını içeren bir int'tır. Metin alanının giriş türü için test etmek üzere sabit TYPE_MASK_CLASS ile maskeleyebilirsiniz. Örneğin:

Kotlin

inputType and InputType.TYPE_MASK_CLASS

Java

inputType & InputType.TYPE_MASK_CLASS

Giriş türü bit deseni aşağıdakiler gibi çeşitli değerlerden birine sahip olabilir:

TYPE_CLASS_NUMBER
Sayı girmek için bir metin alanı. Şekil 3'te gösterildiği gibi, Latin IME bu tür alanlar için bir sayı keypad'i gösterir.
TYPE_CLASS_DATETIME
Tarih ve saat girmek için bir metin alanı.
TYPE_CLASS_PHONE
Telefon numaralarının girileceği bir metin alanı.
TYPE_CLASS_TEXT
Desteklenen tüm karakterleri girmek için bir metin alanı.

Bu sabitler, InputType için referans dokümanlarında daha ayrıntılı olarak açıklanmıştır.

inputType alanı, metin alanı türünün bir varyantını belirten diğer bitleri içerebilir. Örneğin:

TYPE_TEXT_VARIATION_PASSWORD
Şifre girmek için kullanılan TYPE_CLASS_TEXT varyantı. Giriş yöntemi, gerçek metin yerine dingbat'lar gösterir.
TYPE_TEXT_VARIATION_URI
Web URL'lerini ve diğer tek tip kaynak tanımlayıcılarını (URI'ler) girmek için TYPE_CLASS_TEXT'nin bir varyantı.
TYPE_TEXT_FLAG_AUTO_COMPLETE
Uygulamanın bir sözlükten, aramadan veya başka bir kaynaktan otomatik olarak tamamladığı metni girmek için TYPE_CLASS_TEXT'un bir varyantı.

Bu varyantları test ederken inputType değerini uygun sabit değerle maskeleyin. Kullanılabilir maske sabitleri, InputType için referans dokümanlarında listelenir.

Uygulamaya metin gönderme

Kullanıcı IME'nizle metin girerken tek tek tuş etkinlikleri göndererek veya uygulamanın metin alanındaki imlecin etrafındaki metni düzenleyerek uygulamaya metin gönderebilirsiniz. Her iki durumda da metni yayınlamak için InputConnection örneği kullanın. Bu örneği almak için InputMethodService.getCurrentInputConnection() numaralı telefonu arayın.

İmlecin etrafındaki metni düzenleme

Mevcut metinleri düzenlerken BaseInputConnection'te kullanabileceğiniz bazı yararlı yöntemler şunlardır:

getTextBeforeCursor()
Mevcut imleç konumundan önce istenen karakterlerin sayısını içeren bir CharSequence döndürür.
getTextAfterCursor()
Mevcut imleç konumundan sonra istenen karakter sayısını içeren bir CharSequence döndürür.
deleteSurroundingText()
Mevcut imleç konumundan önce ve sonra belirtilen sayıda karakteri siler.
commitText()
Metin alanına bir CharSequence gönderir ve yeni bir imleç konumu belirler.

Örneğin, aşağıdaki snippet'te imlecin solunda bulunan dört karakterin "Merhaba" metniyle nasıl değiştirileceği gösterilmektedir:

Kotlin

currentInputConnection.also { ic: InputConnection ->
    ic.deleteSurroundingText(4, 0)
    ic.commitText("Hello", 1)
    ic.commitText("!", 1)
}

Java

InputConnection ic = getCurrentInputConnection();
ic.deleteSurroundingText(4, 0);
ic.commitText("Hello", 1);
ic.commitText("!", 1);

Uygulamadan önce metin oluşturmayı destekleme

IME'niz metni tahmin ediyorsa veya bir karakter veya kelime oluşturmak için birden fazla adım gerekiyorsa kullanıcı kelimeyi gönderene kadar metin alanında ilerleme durumunu gösterebilir ve ardından kısmi oluşumu tamamlanmış metinle değiştirebilirsiniz. Metni setComposingText()'ye iletirken metne span ekleyerek metne özel bir işlem uygulayabilirsiniz.

Aşağıdaki snippet'te, bir metin alanında ilerlemenin nasıl gösterileceği gösterilmektedir:

Kotlin

currentInputConnection.also { ic: InputConnection ->
    ic.setComposingText("Composi", 1)
    ic.setComposingText("Composin", 1)
    ic.commitText("Composing ", 1)
}

Java

InputConnection ic = getCurrentInputConnection();
ic.setComposingText("Composi", 1);
ic.setComposingText("Composin", 1);
ic.commitText("Composing ", 1);

Donanım anahtar etkinliklerini durdurma

Giriş yöntemi penceresi açıkça odaklanmamış olsa bile donanım tuş etkinliklerini ilk olarak alır ve bunları kullanabilir ya da uygulamaya iletebilir. Örneğin, oluşturma sırasında aday seçimi için kullanıcı arayüzünüzde gezinmek üzere yön tuşlarını kullanmak isteyebilirsiniz. Giriş yöntemi penceresinden gelen tüm iletişim kutularını kapatmak için geri tuşunu da tuş tuzağından geçirebilirsiniz.

Donanım anahtarlarını almak için onKeyDown() ve onKeyUp() değerlerini geçersiz kılın.

Kendi başınıza yönetmek istemediğiniz anahtarlar için super() yöntemini çağırın.

IME alt türü oluşturma

Alt türler, IME'nin desteklediği birden fazla giriş modunu ve dili göstermesine olanak tanır. Alt türler aşağıdakileri temsil edebilir:

  • en_US veya fr_FR gibi bir yerel ayar
  • Ses, klavye veya el yazısı gibi bir giriş modu
  • 10 tuşlu veya QWERTY klavye düzenleri gibi IME'ye özgü diğer giriş stilleri, formları veya özellikleri

Mod, "klavye" veya "ses" gibi herhangi bir metin olabilir. Alt türler, bunların bir kombinasyonunu da gösterebilir.

Alt tür bilgileri, bildirim çubuğundan kullanılabilen IME değiştirici iletişim kutusu ve IME ayarları için kullanılır. Bu bilgiler, çerçevenin doğrudan bir IME alt türünü göstermesine de olanak tanır. Bir IME oluştururken alt tür özelliğini kullanın. Bu özellik, kullanıcının farklı IME dillerini ve modlarını tanımlamasına ve bunlar arasında geçiş yapmasına yardımcı olur.

<subtype> öğesini kullanarak giriş yönteminin XML kaynak dosyalarından birinde alt türleri tanımlayın. Aşağıdaki kod snippet'inde, iki alt türü olan bir IME tanımlanmaktadır: ABD İngilizcesi yerel ayarı için bir klavye alt türü ve Fransa'nın Fransızca yerel ayarı için başka bir klavye alt türü:

<input-method xmlns:android="http://schemas.android.com/apk/res/android"
        android:settingsActivity="com.example.softkeyboard.Settings"
        android:icon="@drawable/ime_icon">
    <subtype android:name="@string/display_name_english_keyboard_ime"
            android:icon="@drawable/subtype_icon_english_keyboard_ime"
            android:languageTag="en-US"
            android:imeSubtypeMode="keyboard"
            android:imeSubtypeExtraValue="somePrivateOption=true" />
    <subtype android:name="@string/display_name_french_keyboard_ime"
            android:icon="@drawable/subtype_icon_french_keyboard_ime"
            android:languageTag="fr-FR"
            android:imeSubtypeMode="keyboard"
            android:imeSubtypeExtraValue="someVariable=30,someInternalOption=false" />
    <subtype android:name="@string/display_name_german_keyboard_ime" ... />
</input-method>

Alt türlerinizin kullanıcı arayüzünde doğru şekilde etiketlendiğinden emin olmak için alt türün yerel ayar etiketiyle aynı alt tür etiketini almak üzere "%s" kullanın. Bu durum, sonraki iki kod snippet'inde gösterilmektedir. İlk snippet, giriş yönteminin XML dosyasının bir bölümünü gösterir:

<subtype
    android:label="@string/label_subtype_generic"
    android:imeSubtypeLocale="en_US"
    android:icon="@drawable/icon_en_us"
    android:imeSubtypeMode="keyboard" />

Aşağıdaki snippet, IME'nin strings.xml dosyasının bir parçasıdır. Alt türün etiketini ayarlamak için giriş yöntemi kullanıcı arayüzü tanımı tarafından kullanılan dize kaynağı label_subtype_generic aşağıdaki gibi tanımlanır:

<string name="label_subtype_generic">%s</string>

Bu ayar, alt türün görünen adının yerel ayarıyla eşleşmesine neden olur. Örneğin, İngilizce yerel ayarlarında görünen ad "İngilizce (ABD)" olur.

Bildirim çubuğundan IME alt türlerini seçme

Android sistemi, tüm IME'ler tarafından sunulan tüm alt türleri yönetir. IME alt türleri, ait oldukları IME'nin modları olarak kabul edilir. Kullanıcı, bildirim çubuğundan veya Ayarlar uygulamasından, aşağıdaki şekilde gösterildiği gibi kullanılabilir IME alt türlerinin bulunduğu bir menüye gidebilir:

Diller ve giriş sistem menüsünü gösteren resim
Şekil 4. Diller ve giriş sistem menüsü.

Sistem ayarlarından IME alt türlerini seçme

Kullanıcı, sistem ayarlarındaki Dil ve giriş ayarları panelinde alt türlerin nasıl kullanıldığını da kontrol edebilir:

Dil seçim menüsünü gösteren resim
Şekil 5. Diller sistem menüsü

IME alt türleri arasında geçiş yapma

Klavyedeki dünya şeklindeki dil simgesi gibi bir geçiş tuşu sağlayarak kullanıcıların IME alt türleri arasında kolayca geçiş yapmasına izin verebilirsiniz. Bu, klavyenin kullanılabilirliğini artırır ve kullanıcı için kullanışlıdır. Bu geçişi etkinleştirmek için aşağıdaki adımları uygulayın:

  1. Giriş yönteminin XML kaynak dosyalarında supportsSwitchingToNextInputMethod = "true" öğesini tanımlayın. Beyanınız aşağıdaki kod snippet'ine benzer şekilde görünmelidir:
    <input-method xmlns:android="http://schemas.android.com/apk/res/android"
            android:settingsActivity="com.example.softkeyboard.Settings"
            android:icon="@drawable/ime_icon"
            android:supportsSwitchingToNextInputMethod="true">
  2. shouldOfferSwitchingToNextInputMethod() yöntemini çağırın.
  3. Yöntem true değerini döndürürse bir geçiş anahtarı gösterin.
  4. Kullanıcı geçiş anahtarına dokunduğunda, switchToNextInputMethod() işlevini false parametresini göndererek çağırın. false değeri, sisteme hangi IME'ye ait olduklarına bakılmaksızın tüm alt türleri eşit şekilde işlemesi gerektiğini söyler. Doğru değerini belirtmek, sistemin mevcut IME'deki alt türleri taramasını gerektirir.

Genel IME ile ilgili dikkat edilmesi gereken noktalar

IME'nizi uygularken dikkate almanız gereken diğer noktalar:

  • Kullanıcıların seçenekleri doğrudan IME'nin kullanıcı arayüzünden ayarlayabileceği bir yöntem sağlayın.
  • Cihazda birden fazla IME yüklü olabileceğinden, kullanıcıların doğrudan giriş yöntemi kullanıcı arayüzünden farklı bir IME'ye geçmesini sağlayın.
  • IME'nin kullanıcı arayüzünü hızlıca açın. Kullanıcıların bir metin alanına dokundukları anda IME'yi görmeleri için büyük kaynakları önceden yükleyin veya isteğe bağlı olarak yükleyin. Giriş yönteminin sonraki çağrıları için kaynakları ve görünümleri önbelleğe alır.
  • Uygulamaların çalışacak yeterli belleğe sahip olması için giriş yöntemi penceresi gizlendikten hemen sonra büyük bellek ayırma işlemlerini serbest bırakın. IME birkaç saniye boyunca gizliyse kaynakları serbest bırakmak için gecikmeli mesaj kullanın.
  • Kullanıcıların, IME ile ilişkili dil veya yerel ayar için mümkün olduğunca çok karakter girebildiğinden emin olun. Kullanıcılar şifrelerde veya kullanıcı adlarında noktalama işaretleri kullanabilir. Bu nedenle, IME'nizin kullanıcıların şifre girip cihaza erişmesine izin vermek için birçok farklı karakter sağlaması gerekir.