Bu konuda, giriş çevirisi modunun ideal bir oyuncu deneyimi sunmadığı oyunlar için PC Üzerinde Google Play Games'de fare girişinin nasıl uygulanacağı ele alınmaktadır.
PC oyuncularında genellikle dokunmatik ekran yerine klavye ve fare bulunur. Bu nedenle, oyununuzun fare girdisine uygun olup olmadığını değerlendirmeniz önemlidir. PC Üzerinde Google Play Games varsayılan olarak tüm sol tıklama fare etkinliklerini tek bir sanal dokunma etkinliğine dönüştürür. Bu, "giriş çeviri modu" olarak bilinir.
Bu mod birkaç değişiklikle oyununuzu çalışır hale getirse de PC oyuncularına yerel hissi veren bir deneyim sunmaz. Bunun için aşağıdakileri uygulamanızı öneririz:
- Açma ve basılı tutma işlemleri yerine içerik menüleri için fareyle üzerine gelme durumları
- Uzun basıldığında veya bir içerik menüsünde gerçekleşen alternatif işlemler için sağ tıklayın.
- Basın ve sürükleme etkinliği yerine birinci veya üçüncü şahıs aksiyon oyunları için fareyle üzerine gelme
PC'lerde yaygın olan kullanıcı arayüzü kalıplarını desteklemek için giriş çevirisi modunu devre dışı bırakmanız gerekir.
PC Üzerinde Google Play Games giriş işleme şekli, ChromeOS ile aynıdır. PC'leri destekleyen değişiklikler aynı zamanda oyununuzu tüm Android oyuncuları için daha iyi hale getirir.
Giriş çevirisi modunu devre dışı bırak
AndroidManifest.xml
dosyanızda android.hardware.type.pc
özelliğini beyan edin.
Bu, oyununuzun PC donanımı kullandığını ve giriş çevirisi modunu devre dışı bıraktığını gösterir. Ayrıca required="false"
eklemek, oyununuzun telefon ve tabletlere fare olmadan yüklenebilmesini sağlar. Örneğin:
<manifest ...>
<uses-feature
android:name="android.hardware.type.pc"
android:required="false" />
...
</manifest>
PC Üzerinde Google Play Games'in üretim sürümü, bir oyun kullanıma sunulduğunda doğru moda geçer. Geliştirici emülatöründe çalışırken ham fare girişini almak için görev çubuğu simgesini sağ tıklayıp Geliştirici Seçenekleri'ni ve ardından PC modunu(KiwiMouse) seçmeniz gerekir.
Bunu yapmanızdan sonra, fare hareketi View.onGeneralMotionEvent tarafından, kaynak SOURCE_MOUSE
ile raporlanarak bunun bir fare etkinliği olduğunu belirtir.
Kotlin
gameView.setOnGenericMotionListener { _, motionEvent -> var handled = false if (motionEvent.isFromSource(InputDevice.SOURCE_CLASS_POINTER)) { // handle the mouse event here handled = true } handled }
Java
gameView.setOnGenericMotionListener((view, motionEvent) -> { if (motionEvent.isFromSource(InputDevice.SOURCE_CLASS_POINTER)) { // handle the mouse event here return true; } return false; });
Fare girişini işleme hakkında ayrıntılı bilgi için ChromeOS belgelerine bakın.
Fare hareketlerini işleme
Fare hareketlerini algılamak için ACTION_HOVER_ENTER
, ACTION_HOVER_EXIT
ve ACTION_HOVER_MOVE
etkinliklerini dinleyin.
Bu, bir oyunda kullanıcıyı düğmelerin veya nesnelerin üzerine getirdiğini algılamak için en iyi seçenektir. Size, bir ipucu kutusu görüntüleme veya bir oyuncunun seçmek üzere olduğu öğeyi vurgulamak için fareyle üzerine gelme durumu uygulama şansı verir. Örneğin:
Kotlin
gameView.setOnGenericMotionListener { _, motionEvent -> var handled = false if (motionEvent.isFromSource(InputDevice.SOURCE_CLASS_POINTER)) { when(motionEvent.action) { MotionEvent.ACTION_HOVER_ENTER -> Log.d("MA", "Mouse entered at ${motionEvent.x}, ${motionEvent.y}") MotionEvent.ACTION_HOVER_EXIT -> Log.d("MA", "Mouse exited at ${motionEvent.x}, ${motionEvent.y}") MotionEvent.ACTION_HOVER_MOVE -> Log.d("MA", "Mouse hovered at ${motionEvent.x}, ${motionEvent.y}") } handled = true } handled }
Java
gameView.setOnGenericMotionListener((view, motionEvent) -> { if (motionEvent.isFromSource(InputDevice.SOURCE_CLASS_POINTER)) { switch (motionEvent.getAction()) { case MotionEvent.ACTION_HOVER_ENTER: Log.d("MA", "Mouse entered at " + motionEvent.getX() + ", " + motionEvent.getY()); break; case MotionEvent.ACTION_HOVER_EXIT: Log.d("MA", "Mouse exited at " + motionEvent.getX() + ", " + motionEvent.getY()); break; case MotionEvent.ACTION_HOVER_MOVE: Log.d("MA", "Mouse hovered at " + motionEvent.getX() + ", " + motionEvent.getY()); break; } return true; } return false; });
Fare düğmelerini kullanma
PC'lerde uzun zamandır hem sol hem sağ fare düğmeleri olduğu için, birincil ve ikincil işlemlere etkileşimli öğeler ekledik. Bir oyunda, bir düğmeye dokunma gibi dokunma eylemlerinin en uygun olduğu yer, dokunma ve basılı tutma işlemlerinin sağ tıklamayla en doğal olduğu durum. Gerçek zamanlı strateji oyunlarında seçim yapmak için sol tıklama ve hareket etmek için sağ tıklama da kullanılabilir. Birinci şahıs nişancı oyunlarında sol tarafa birincil ve ikincil ateşleme ve sağ tıklama atanır. Sonsuz koşucu, zıplamak için sol tıklamayı, koşmak için sağ tıklamayı kullanabilir. Orta tıklama etkinliği için destek eklemedik.
Düğmelere basmaları işlemek için ACTION_DOWN
ve ACTION_UP
kullanın. Ardından, işlemi hangi düğmenin tetiklediğini belirlemek için getActionButton
veya tüm düğmelerin durumunu almak için getButtonState
işlevini kullanın.
Bu örnekte, getActionButton
sonucunun gösterilmesine yardımcı olmak için bir enum kullanılmıştır:
Kotlin
enum class MouseButton { LEFT, RIGHT, UNKNOWN; companion object { fun fromMotionEvent(motionEvent: MotionEvent): MouseButton { return when (motionEvent.actionButton) { MotionEvent.BUTTON_PRIMARY -> LEFT MotionEvent.BUTTON_SECONDARY -> RIGHT else -> UNKNOWN } } } }
Java
enum MouseButton { LEFT, RIGHT, MIDDLE, UNKNOWN; static MouseButton fromMotionEvent(MotionEvent motionEvent) { switch (motionEvent.getActionButton()) { case MotionEvent.BUTTON_PRIMARY: return MouseButton.LEFT; case MotionEvent.BUTTON_SECONDARY: return MouseButton.RIGHT; default: return MouseButton.UNKNOWN; } } }
Bu örnekte, işlem fareyle üzerine gelme etkinliklerine benzer şekilde işlenir:
Kotlin
// Handle the generic motion event gameView.setOnGenericMotionListener { _, motionEvent -> var handled = false if (motionEvent.isFromSource(InputDevice.SOURCE_CLASS_POINTER)) { when (motionEvent.action) { MotionEvent.ACTION_BUTTON_PRESS -> Log.d( "MA", "${MouseButton.fromMotionEvent(motionEvent)} pressed at ${motionEvent.x}, ${motionEvent.y}" ) MotionEvent.ACTION_BUTTON_RELEASE -> Log.d( "MA", "${MouseButton.fromMotionEvent(motionEvent)} released at ${motionEvent.x}, ${motionEvent.y}" ) } handled = true } handled }
Java
gameView.setOnGenericMotionListener((view, motionEvent) -> { if (motionEvent.isFromSource(InputDevice.SOURCE_CLASS_POINTER)) { switch (motionEvent.getAction()) { case MotionEvent.ACTION_BUTTON_PRESS: Log.d("MA", MouseButton.fromMotionEvent(motionEvent) + " pressed at " + motionEvent.getX() + ", " + motionEvent.getY()); break; case MotionEvent.ACTION_BUTTON_RELEASE: Log.d("MA", MouseButton.fromMotionEvent(motionEvent) + " released at " + motionEvent.getX() + ", " + motionEvent.getY()); break; } return true; } return false; });
Fare tekerleği kaydırmasını kullanın
Hareketleri yakınlaştırmak veya oyununuzdaki kaydırma alanlarına dokunup sürüklemek için sıkıştırmak yerine fare kaydırma tekerleğini kullanmanızı öneririz.
Kaydırma tekerleği değerlerini okumak için ACTION_SCROLL
etkinliğini dinleyin. Son kareden bu yana olan delta, dikey ofset için AXIS_VSCROLL
ve yatay ofset için AXIS_HSCROLL
ile getAxisValue
kullanılarak alınabilir. Örneğin:
Kotlin
gameView.setOnGenericMotionListener { _, motionEvent -> var handled = false if (motionEvent.isFromSource(InputDevice.SOURCE_CLASS_POINTER)) { when (motionEvent.action) { MotionEvent.ACTION_SCROLL -> { val scrollX = motionEvent.getAxisValue(MotionEvent.AXIS_HSCROLL) val scrollY = motionEvent.getAxisValue(MotionEvent.AXIS_VSCROLL) Log.d("MA", "Mouse scrolled $scrollX, $scrollY") } } handled = true } handled }
Java
gameView.setOnGenericMotionListener((view, motionEvent) -> { if (motionEvent.isFromSource(InputDevice.SOURCE_CLASS_POINTER)) { switch (motionEvent.getAction()) { case MotionEvent.ACTION_SCROLL: float scrollX = motionEvent.getAxisValue(MotionEvent.AXIS_HSCROLL); float scrollY = motionEvent.getAxisValue(MotionEvent.AXIS_VSCROLL); Log.d("MA", "Mouse scrolled " + scrollX + ", " + scrollY); break; } return true; } return false; });
Fare girişini yakala
Fare hareketini kamera hareketleriyle eşleştiren birinci veya üçüncü şahıs aksiyon oyunları gibi bazı oyunların fare imlecinin tam kontrolünü gerçekleştirmesi gerekir. Farenin tamamen kontrolünü almak için View.requestPointerCapture()
çağırın.
requestPointerCapture()
, yalnızca görünümünüzü içeren görünüm hiyerarşisine odaklanıldığında çalışır. Bu nedenle, onCreate
geri çağırmasında işaretçi yakalaması alamazsınız. Ana menüyle etkileşimde bulunurken oyuncu etkileşiminin fare işaretçisini yakalamasını beklemeniz veya onWindowFocusChanged
geri çağırmasını kullanmanız gerekir. Örneğin:
Kotlin
override fun onWindowFocusChanged(hasFocus: Boolean) { super.onWindowFocusChanged(hasFocus) if (hasFocus) { gameView.requestPointerCapture() } }
Java
@Override public void onWindowFocusChanged(boolean hasFocus) { super.onWindowFocusChanged(hasFocus); if (hasFocus) { View gameView = findViewById(R.id.game_view); gameView.requestPointerCapture(); } }
requestPointerCapture()
tarafından yakalanan etkinlikler, OnCapturedPointerListener
alanını kaydeden odaklanılabilir görünüme gönderilir. Örneğin:
Kotlin
gameView.focusable = View.FOCUSABLE gameView.setOnCapturedPointerListener { _, motionEvent -> Log.d("MA", "${motionEvent.x}, ${motionEvent.y}, ${motionEvent.actionButton}") true }
Java
gameView.setFocusable(true); gameView.setOnCapturedPointerListener((view, motionEvent) -> { Log.d("MA", motionEvent.getX() + ", " + motionEvent.getY() + ", " + motionEvent.getActionButton()); return true; });
Oyuncuların bir duraklatma menüsüyle etkileşim kurmasına izin vermek gibi özel fare yakalama özelliğini etkinleştirmek için View.releasePointerCapture()
yöntemini çağırın.