import QtQuick import Sloposk // One key, drawn from the LayoutModel roles. Purely visual. Item { id: key required property string label required property string flickLabel required property string keyType required property real keyX required property real keyY required property real keyWidth required property real keyHeight required property bool pressed required property real flickProgress property int shiftMode: KeyboardController.Off property bool blank: false // labels hidden, e.g. in trackpad mode readonly property bool isCharacter: keyType === "char" || keyType === "space" readonly property bool shiftActive: keyType === "shift" && shiftMode !== KeyboardController.Off // Character keys darken when pressed; function keys lighten (as on iPad). readonly property bool lit: (isCharacter !== pressed) || shiftActive readonly property var defaultGlyphs: ({ backspace: "⌫", globe: "🌐", dismiss: "⌨", enter: "return", }) readonly property string displayLabel: { if (keyType === "shift") return ["⇧", "⬆", "⇪"][shiftMode] return label !== "" ? label : (defaultGlyphs[keyType] ?? "") } // Count code points, not UTF-16 units, so emoji glyphs aren't treated as words. readonly property bool isWord: [...displayLabel].length > 1 && !isCharacter x: keyX y: keyY width: keyWidth height: keyHeight Rectangle { anchors { fill: face; topMargin: 1; bottomMargin: -1 } radius: Theme.keyRadius color: Theme.keyShadow } Rectangle { id: face anchors.fill: parent radius: Theme.keyRadius color: key.lit ? Theme.characterKey : Theme.functionKey } // Flicking slides the secondary symbol down into the main position. Text { id: flick readonly property real restY: key.height * 0.1 readonly property real centerY: (key.height - height) / 2 visible: text !== "" && !key.blank text: key.flickLabel anchors.horizontalCenter: parent.horizontalCenter y: restY + (centerY - restY) * key.flickProgress font.pixelSize: key.height * (0.24 + 0.16 * key.flickProgress) color: key.flickProgress >= 1 ? Theme.text : Theme.secondaryText } Text { text: key.displayLabel anchors { horizontalCenter: parent.horizontalCenter verticalCenter: parent.verticalCenter verticalCenterOffset: flick.visible ? key.height * 0.14 : 0 } font.pixelSize: key.height * (key.isWord ? 0.24 : flick.visible ? 0.34 : 0.4) color: Theme.text visible: !key.blank opacity: 1 - key.flickProgress } }