From a065c6bfe0e18436fe828bf3c5a1b2df710acbf2 Mon Sep 17 00:00:00 2001 From: Soheil Armin Date: Thu, 17 Oct 2024 10:41:36 +0300 Subject: [PATCH] Android: Add OnDataChangedListerner callback interface Adds a new interface to QtAbstractItemModel Java class that can be used as a callback to listen to the changes of an editable model. The model can be an implementation of QtAbstractItemModel with an underlaying C++ QAndroidAbstractModelProxy instance, or it can be an instance of QtAbstractItemModel that proxies and refers to a QAbstractItemModel instance. This also adds setOnDataChangedListener() to QtAbstractItemModel so that it can call the interface callback function by connecting dataChanged() signal of the native instance to a lambda that invokes the handleDataChanged() private method of the JVM instance. Task-number: QTBUG-129387 Task-number: QTBUG-130251 Task-number: QTBUG-130252 Change-Id: I23da9e980b5402f4dcf7446560155271ccd8809e Reviewed-by: Assam Boudjelthia --- .../qt/android/QtAbstractItemModel.java | 31 +++++++++++++++++++ .../android/qandroiditemmodelproxy.cpp | 13 ++++++++ 2 files changed, 44 insertions(+) diff --git a/src/android/jar/src/org/qtproject/qt/android/QtAbstractItemModel.java b/src/android/jar/src/org/qtproject/qt/android/QtAbstractItemModel.java index 83c9448c9cb..49205e82840 100644 --- a/src/android/jar/src/org/qtproject/qt/android/QtAbstractItemModel.java +++ b/src/android/jar/src/org/qtproject/qt/android/QtAbstractItemModel.java @@ -263,6 +263,27 @@ public abstract class QtAbstractItemModel public void dataChanged(QtModelIndex topLeft, QtModelIndex bottomRight, int[] roles) { jni_dataChanged(topLeft, bottomRight, roles); } + /** + * Interface for a callback to be invoked when the data in an existing item changes. + */ + public interface OnDataChangedListener { + /** + * Called when the data in an existing item changes. + * + * @param topLeft The top-left index of changed items + * @param bottomRight The bottom-right index of changed items + * @param roles Changed roles; Empty array indicates all roles + */ + void onDataChanged(QtModelIndex topLeft, QtModelIndex bottomRight, int[] roles); + } + /** + * Register a callback to be invoked when the data in an existing item changes. + * + * @param listener The data change listener + */ + public void setOnDataChangedListener(OnDataChangedListener listener) { + m_OnDataChangedListener = listener; + } /** * Begins a column insertion operation. @@ -503,6 +524,15 @@ public abstract class QtAbstractItemModel */ protected final void endResetModel() { jni_endResetModel(); } + private void handleDataChanged(QtModelIndex topLeft, QtModelIndex bottomRight, int[] roles) + { + if (m_OnDataChangedListener != null) { + QtNative.runAction(() -> { + if (m_OnDataChangedListener != null) + m_OnDataChangedListener.onDataChanged(topLeft, bottomRight, roles); + }); + } + } private native void jni_beginInsertColumns(QtModelIndex parent, int first, int last); private native void jni_beginInsertRows(QtModelIndex parent, int first, int last); private native boolean jni_beginMoveColumns(QtModelIndex sourceParent, int sourceFirst, @@ -529,6 +559,7 @@ public abstract class QtAbstractItemModel int[] roles); private long m_nativeReference = 0; + private OnDataChangedListener m_OnDataChangedListener; private QtAbstractItemModel(long nativeReference) { m_nativeReference = nativeReference; } private void detachFromNative() { m_nativeReference = 0; } diff --git a/src/corelib/platform/android/qandroiditemmodelproxy.cpp b/src/corelib/platform/android/qandroiditemmodelproxy.cpp index f1877d72792..f17d417b1f1 100644 --- a/src/corelib/platform/android/qandroiditemmodelproxy.cpp +++ b/src/corelib/platform/android/qandroiditemmodelproxy.cpp @@ -160,6 +160,19 @@ QAndroidItemModelProxy::createNativeProxy(QJniObject itemModel) if (proxy) proxy->jInstance.callMethod("detachFromNative"); }); + + connect(nativeProxy, &QAndroidItemModelProxy::dataChanged, nativeProxy, + [nativeProxy](const QModelIndex &topLeft, const QModelIndex &bottomRight, + const QList &roles) { + auto proxy = qobject_cast(nativeProxy); + if (proxy) { + QJniObject jInstance = proxy->jInstance; + jInstance.callMethod("handleDataChanged", + QAndroidModelIndexProxy::jInstance(topLeft), + QAndroidModelIndexProxy::jInstance(bottomRight), + QJniArray(roles)); + } + }); } return nativeProxy; }