mirror of
				https://github.com/vcmi/vcmi.git
				synced 2025-10-31 00:07:39 +02:00 
			
		
		
		
	Better android input handling: sending notifications about CInputText changes to java so that we can display textinput overlay there; (#354)
This commit is contained in:
		| @@ -18,6 +18,10 @@ | ||||
|  | ||||
| #include "../../lib/CGeneralTextHandler.h" //for Unicode related stuff | ||||
|  | ||||
| #ifdef VCMI_ANDROID | ||||
| #include "lib/CAndroidVMHelper.h" | ||||
| #endif | ||||
|  | ||||
| std::string CLabel::visibleText() | ||||
| { | ||||
| 	return text; | ||||
| @@ -427,6 +431,9 @@ CTextInput::CTextInput(const Rect &Pos, SDL_Surface *srf) | ||||
| void CTextInput::focusGot() | ||||
| { | ||||
| 	CSDL_Ext::startTextInput(&pos); | ||||
| #ifdef VCMI_ANDROID | ||||
| 	notifyAndroidTextInputChanged(text); | ||||
| #endif | ||||
| } | ||||
|  | ||||
| void CTextInput::focusLost() | ||||
| @@ -485,6 +492,9 @@ void CTextInput::keyPressed( const SDL_KeyboardEvent & key ) | ||||
| 	{ | ||||
| 		redraw(); | ||||
| 		cb(text); | ||||
| #ifdef VCMI_ANDROID | ||||
| 		notifyAndroidTextInputChanged(text); | ||||
| #endif | ||||
| 	} | ||||
| } | ||||
|  | ||||
| @@ -493,6 +503,10 @@ void CTextInput::setText( const std::string &nText, bool callCb ) | ||||
| 	CLabel::setText(nText); | ||||
| 	if(callCb) | ||||
| 		cb(text); | ||||
|  | ||||
| #ifdef VCMI_ANDROID | ||||
| 	notifyAndroidTextInputChanged(text); | ||||
| #endif | ||||
| } | ||||
|  | ||||
| bool CTextInput::captureThisEvent(const SDL_KeyboardEvent & key) | ||||
| @@ -518,6 +532,10 @@ void CTextInput::textInputed(const SDL_TextInputEvent & event) | ||||
| 		cb(text); | ||||
| 	} | ||||
| 	newText = ""; | ||||
|  | ||||
| #ifdef VCMI_ANDROID | ||||
| 	notifyAndroidTextInputChanged(text); | ||||
| #endif | ||||
| } | ||||
|  | ||||
| void CTextInput::textEdited(const SDL_TextEditingEvent & event) | ||||
| @@ -528,6 +546,11 @@ void CTextInput::textEdited(const SDL_TextEditingEvent & event) | ||||
| 	newText = event.text; | ||||
| 	redraw(); | ||||
| 	cb(text+newText); | ||||
|  | ||||
| #ifdef VCMI_ANDROID | ||||
| 	auto editedText = text + newText; | ||||
| 	notifyAndroidTextInputChanged(editedText); | ||||
| #endif | ||||
| } | ||||
|  | ||||
| void CTextInput::filenameFilter(std::string & text, const std::string &) | ||||
| @@ -574,6 +597,24 @@ void CTextInput::numberFilter(std::string & text, const std::string & oldText, i | ||||
| 	} | ||||
| } | ||||
|  | ||||
| #ifdef VCMI_ANDROID | ||||
| void CTextInput::notifyAndroidTextInputChanged(std::string & text) | ||||
| { | ||||
| 	if (!focus) | ||||
| 		return; | ||||
|  | ||||
| 	auto fun = [&text](JNIEnv * env, jclass cls, jmethodID method) | ||||
| 	{ | ||||
| 		auto jtext = env->NewStringUTF(text.c_str()); | ||||
| 		env->CallStaticObjectMethod(cls, method, jtext); | ||||
| 		env->DeleteLocalRef(jtext); | ||||
| 	}; | ||||
| 	CAndroidVMHelper vmHelper; | ||||
| 	vmHelper.callCustomMethod(CAndroidVMHelper::NATIVE_METHODS_DEFAULT_CLASS, "notifyTextInputChanged", | ||||
| 		"(Ljava/lang/String;)V", fun); | ||||
| } | ||||
| #endif //VCMI_ANDROID | ||||
|  | ||||
| CFocusable::CFocusable() | ||||
| { | ||||
| 	focus = false; | ||||
|   | ||||
| @@ -160,6 +160,10 @@ protected: | ||||
|  | ||||
| 	void focusGot() override; | ||||
| 	void focusLost() override; | ||||
|  | ||||
| #ifdef VCMI_ANDROID | ||||
| 	void notifyAndroidTextInputChanged(std::string & text); | ||||
| #endif | ||||
| public: | ||||
| 	CFunctionList<void(const std::string &)> cb; | ||||
| 	CFunctionList<void(std::string &, const std::string &)> filters; | ||||
|   | ||||
| @@ -83,6 +83,16 @@ std::string CAndroidVMHelper::callStaticStringMethod(const std::string & cls, co | ||||
| 	return std::string(env->GetStringUTFChars(jres, nullptr)); | ||||
| } | ||||
|  | ||||
| void CAndroidVMHelper::callCustomMethod(const std::string & cls, const std::string & method, | ||||
| 										const std::string & signature, | ||||
| 										std::function<void(JNIEnv *, jclass, jmethodID)> fun, bool classloaded) | ||||
| { | ||||
| 	auto env = get(); | ||||
| 	auto javaHelper = findClass(cls, classloaded); | ||||
| 	auto methodId = env->GetStaticMethodID(javaHelper, method.c_str(), signature.c_str()); | ||||
| 	fun(env, javaHelper, methodId); | ||||
| } | ||||
|  | ||||
| jclass CAndroidVMHelper::findClass(const std::string & name, bool classloaded) | ||||
| { | ||||
| 	if(classloaded) | ||||
|   | ||||
| @@ -12,6 +12,7 @@ | ||||
| #include "Global.h" | ||||
|  | ||||
| #ifdef VCMI_ANDROID | ||||
|  | ||||
| #include <jni.h> | ||||
| #include <string> | ||||
|  | ||||
| @@ -36,6 +37,9 @@ public: | ||||
|  | ||||
| 	std::string callStaticStringMethod(const std::string & cls, const std::string & method, bool classloaded = false); | ||||
|  | ||||
| 	void callCustomMethod(const std::string & cls, const std::string & method, const std::string & signature, | ||||
| 						  std::function<void(JNIEnv *, jclass, jmethodID)> fun, bool classloaded = false); | ||||
|  | ||||
| 	static void cacheVM(JNIEnv * env); | ||||
|  | ||||
| 	static void cacheVM(JavaVM * vm); | ||||
|   | ||||
		Reference in New Issue
	
	Block a user