diff options
author | Pekka Gehör <pekka.gehor@qt.io> | 2022-06-30 13:40:11 +0300 |
---|---|---|
committer | Bartlomiej Moskal <bartlomiej.moskal@qt.io> | 2022-07-20 09:10:49 +0200 |
commit | 8a25f8d7e496ada0872fa9e0bb169c2bb12ab501 (patch) | |
tree | 2020d155c2e51fcd80fc7df10889d3456c47dea1 /src/plugins/platforms/android | |
parent | 00aabac2b6591ee9f5006169211acc70766def03 (diff) |
Fix select handles disappears issues
Select handles {Left, Right}Point disappears when double click a first
word or select all on QLineEdit without set leftMargin of QLineEdit.
Cursor is not shown if it goes over the widget frame on main window or
on dialog. To prevent this cursor position is not decreased if it is less than one.
Fixes: QTBUG-91139
Change-Id: Ib54eb09e51076f7f41a2fca7eb7630f3c5591fed
Reviewed-by: Assam Boudjelthia <assam.boudjelthia@qt.io>
Diffstat (limited to 'src/plugins/platforms/android')
-rw-r--r-- | src/plugins/platforms/android/androidjniinput.cpp | 5 | ||||
-rw-r--r-- | src/plugins/platforms/android/androidjniinput.h | 2 | ||||
-rw-r--r-- | src/plugins/platforms/android/qandroidinputcontext.cpp | 37 |
3 files changed, 37 insertions, 7 deletions
diff --git a/src/plugins/platforms/android/androidjniinput.cpp b/src/plugins/platforms/android/androidjniinput.cpp index 726caa5015..9e3d7b8062 100644 --- a/src/plugins/platforms/android/androidjniinput.cpp +++ b/src/plugins/platforms/android/androidjniinput.cpp @@ -121,6 +121,11 @@ namespace QtAndroidInput return m_softwareKeyboardRect; } + int getSelectHandleWidth() + { + return QJNIObjectPrivate::callStaticMethod<jint>(applicationClass(), "getSelectHandleWidth"); + } + void updateHandles(int mode, QPoint editMenuPos, uint32_t editButtons, QPoint cursor, QPoint anchor, bool rtl) { QJNIObjectPrivate::callStaticMethod<void>(applicationClass(), "updateHandles", "(IIIIIIIIZ)V", diff --git a/src/plugins/platforms/android/androidjniinput.h b/src/plugins/platforms/android/androidjniinput.h index 5ef57ade61..2259685882 100644 --- a/src/plugins/platforms/android/androidjniinput.h +++ b/src/plugins/platforms/android/androidjniinput.h @@ -60,6 +60,8 @@ namespace QtAndroidInput // cursor/selection handles void updateHandles(int handleCount, QPoint editMenuPos = QPoint(), uint32_t editButtons = 0, QPoint cursor = QPoint(), QPoint anchor = QPoint(), bool rtl = false); + int getSelectHandleWidth(); + bool registerNatives(JNIEnv *env); } diff --git a/src/plugins/platforms/android/qandroidinputcontext.cpp b/src/plugins/platforms/android/qandroidinputcontext.cpp index 1a9f71eabd..4d04db7edd 100644 --- a/src/plugins/platforms/android/qandroidinputcontext.cpp +++ b/src/plugins/platforms/android/qandroidinputcontext.cpp @@ -514,7 +514,12 @@ QAndroidInputContext::QAndroidInputContext() auto im = qGuiApp->inputMethod(); if (!im->inputItemClipRectangle().contains(im->anchorRectangle()) || !im->inputItemClipRectangle().contains(im->cursorRectangle())) { - m_handleMode = Hidden; + // Undoes the hidden request if the only reason for the hidden is that + // X of the cursorRectangle or X of the anchorRectangle is less than 0. + const int rectX = im->inputItemClipRectangle().x(); + if (im->cursorRectangle().x() > rectX && im->anchorRectangle().x() > rectX) + m_handleMode = Hidden; + updateSelectionHandles(); } }); @@ -623,13 +628,13 @@ void QAndroidInputContext::updateSelectionHandles() if (noHandles) return; + QWindow *window = qGuiApp->focusWindow(); auto im = qGuiApp->inputMethod(); - if (!m_focusObject || ((m_handleMode & 0xff) == Hidden)) { + if (!m_focusObject || ((m_handleMode & 0xff) == Hidden) || !window) { // Hide the handles QtAndroidInput::updateHandles(Hidden); return; } - QWindow *window = qGuiApp->focusWindow(); double pixelDensity = window ? QHighDpiScaling::factor(window) : QHighDpiScaling::factor(QtAndroid::androidPlatformIntegration()->screen()); @@ -678,12 +683,30 @@ void QAndroidInputContext::updateSelectionHandles() if (cpos > anchor) std::swap(leftRect, rightRect); + // Move the left or right select handle to the center from the screen edge + // the select handle is close to or over the screen edge. Otherwise, the + // select handle might go out of the screen and it would be impossible to drag. QPoint leftPoint(window->mapToGlobal(leftRect.bottomLeft().toPoint())); - QPoint righPoint(window->mapToGlobal(rightRect.bottomRight().toPoint())); - QPoint editPoint(window->mapToGlobal(leftRect.united(rightRect) - .topLeft().toPoint())); + QPoint rightPoint(window->mapToGlobal(rightRect.bottomRight().toPoint())); + static int m_selectHandleWidth = 0; + // For comparison, get the width of the handle. + // Only half of the width will protrude from the cursor on each side + if (m_selectHandleWidth == 0) + m_selectHandleWidth = QtAndroidInput::getSelectHandleWidth() / 2; + + int rightSideOfScreen = QtAndroid::androidPlatformIntegration()->screen()->availableGeometry().right(); + + // Check if handle will fit the screen on left side. If not, then move it closer to the center + if (leftPoint.x() <= m_selectHandleWidth) + leftPoint.setX(m_selectHandleWidth / pixelDensity); + + // Check if handle will fit the screen on right side. If not, then move it closer to the center + if (rightPoint.x() >= (rightSideOfScreen / pixelDensity) - m_selectHandleWidth) + rightPoint.setX((rightSideOfScreen / pixelDensity) - (m_selectHandleWidth / pixelDensity)); + + QPoint editPoint(window->mapToGlobal(leftRect.united(rightRect).topLeft().toPoint())); QtAndroidInput::updateHandles(m_handleMode, editPoint * pixelDensity, EditContext::AllButtons, - leftPoint * pixelDensity, righPoint * pixelDensity, + leftPoint * pixelDensity, rightPoint * pixelDensity, query.value(Qt::ImCurrentSelection).toString().isRightToLeft()); m_hideCursorHandleTimer.stop(); } |