Browse Source

qml/ControlLayout: Update keyboard navigation implementation

Our prior implementation couldn't handle a model invalidate() properly and ended up corrupting
the keyboard navigation.
pull/134/head
Benjamin Arnaud 5 years ago
committed by Jean-Baptiste Kempf
parent
commit
dcc4520cd9
  1. 65
      modules/gui/qt/player/qml/ControlLayout.qml

65
modules/gui/qt/player/qml/ControlLayout.qml

@ -92,7 +92,13 @@ FocusScope {
Repeater {
id: repeater
// NOTE: We apply the 'navigation chain' after adding the item.
onItemAdded: item.applyNavigation()
onItemRemoved: {
// NOTE: We update the 'navigation chain' after removing the item.
item.removeNavigation()
item.recoverFocus(index)
}
@ -129,23 +135,7 @@ FocusScope {
value: (loader.x + minimumWidth <= rowLayout.width)
}
function buildFocusChain() {
// rebuild the focus chain:
if (typeof repeater === "undefined")
return
var rightItem = repeater.itemAt(index + 1)
var leftItem = repeater.itemAt(index - 1)
item.Navigation.rightItem = !!rightItem ? rightItem.item : null
item.Navigation.leftItem = !!leftItem ? leftItem.item : null
}
Component.onCompleted: {
repeater.countChanged.connect(loader.buildFocusChain)
repeater.modelChanged.connect(loader.buildFocusChain)
repeater.countChanged.connect(controlLayout._handleFocus)
}
Component.onCompleted: repeater.countChanged.connect(controlLayout._handleFocus)
onActiveFocusChanged: {
if (activeFocus && (!!item && !item.focus)) {
@ -190,6 +180,47 @@ FocusScope {
item.visible = Qt.binding(function() { return loader.visible })
}
function applyNavigation() {
var itemLeft = repeater.itemAt(index - 1)
var itemRight = repeater.itemAt(index + 1)
if (itemLeft) {
var componentLeft = itemLeft.item;
item.Navigation.leftItem = componentLeft
componentLeft.Navigation.rightItem = item
}
if (itemRight) {
var componentRight = itemRight.item;
item.Navigation.rightItem = componentRight
componentRight.Navigation.leftItem = item
}
}
function removeNavigation() {
var itemLeft = repeater.itemAt(index - 1)
// NOTE: The current item was removed from the repeater so we test against the
// same index.
var itemRight = repeater.itemAt(index)
if (itemLeft) {
if (itemRight) {
itemLeft.item.Navigation.rightItem = itemRight.item
itemRight.item.Navigation.leftItem = itemLeft.item
}
else
itemLeft.item.Navigation.rightItem = null
}
else if (itemRight) {
itemRight.item.Navigation.leftItem = null
}
}
function _focusIfFocusable(_loader) {
if (!!_loader && !!_loader.item && _loader.item.focus) {
if (item.focusReason !== undefined)

Loading…
Cancel
Save