kde/gui: add Acme-style mouse chording to prompt input
Implement proper Plan 9/Acme mouse chording in the input area: - B1 = select (TextArea default) - B2 = execute selection as prompt - B3 = plumb selection or context menu - B1+B2 = cut (chord while selecting) - B1+B3 = paste (chord while selecting) Uses MouseArea overlay that detects when B1 is held while B2/B3 is pressed to trigger chord actions. Context menu items now show the chord shortcuts (Cut B1+B2, Paste B1+B3). Placeholder text shows the mouse action reference.
This commit is contained in:
parent
eb12627ea0
commit
b25b99be4d
|
|
@ -307,7 +307,7 @@ Item {
|
|||
ToolTip.text: "Clear input"
|
||||
}
|
||||
|
||||
// TextArea in ScrollView for overflow, with context menu overlay
|
||||
// TextArea in ScrollView for overflow, with mouse chording
|
||||
Item {
|
||||
Layout.fillWidth: true
|
||||
Layout.maximumHeight: 200
|
||||
|
|
@ -327,7 +327,7 @@ Item {
|
|||
if (!ollie.activeSessionId) return "No session"
|
||||
if (!ollie.activeAgentId) return "No agent"
|
||||
if (ollie.isSessionPaused(ollie.activeSessionId)) return "Session paused"
|
||||
return "Message... (B2=execute selection, B3=plumb)"
|
||||
return "B1=sel B2=exec B3=plumb B1+B2=cut B1+B3=paste"
|
||||
}
|
||||
enabled: ollie.daemonConnected && ollie.activeSessionId !== "" && ollie.activeAgentId !== "" && !ollie.isSessionPaused(ollie.activeSessionId)
|
||||
wrapMode: TextEdit.Wrap
|
||||
|
|
@ -350,23 +350,76 @@ Item {
|
|||
event.accepted = true
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Acme-style mouse handling in input
|
||||
TapHandler {
|
||||
acceptedButtons: Qt.MiddleButton
|
||||
onTapped: {
|
||||
// B2: Execute selection as prompt immediately
|
||||
var sel = promptInput.selectedText
|
||||
if (sel && sel.trim() !== "") {
|
||||
ollie.submit(sel.trim())
|
||||
}
|
||||
// Acme-style mouse chording overlay
|
||||
// B1 = select (handled by TextArea)
|
||||
// B2 = execute selection
|
||||
// B3 = plumb selection / context menu
|
||||
// B1+B2 = cut (snarf)
|
||||
// B1+B3 = paste
|
||||
MouseArea {
|
||||
id: chordArea
|
||||
anchors.fill: parent
|
||||
acceptedButtons: Qt.MiddleButton | Qt.RightButton
|
||||
propagateComposedEvents: true
|
||||
cursorShape: Qt.IBeamCursor
|
||||
|
||||
// Track if B1 (left) is currently held for chord detection
|
||||
property bool leftHeld: false
|
||||
|
||||
// We can't directly detect B1 here since TextArea handles it,
|
||||
// but we can check mouse.buttons in the handlers
|
||||
onPressed: function(mouse) {
|
||||
// Check if this is a chord (B1 already held)
|
||||
if (mouse.buttons & Qt.LeftButton) {
|
||||
leftHeld = true
|
||||
if (mouse.button === Qt.MiddleButton) {
|
||||
// B1+B2 = cut
|
||||
promptInput.cut()
|
||||
mouse.accepted = true
|
||||
return
|
||||
} else if (mouse.button === Qt.RightButton) {
|
||||
// B1+B3 = paste
|
||||
promptInput.paste()
|
||||
mouse.accepted = true
|
||||
return
|
||||
}
|
||||
}
|
||||
leftHeld = false
|
||||
mouse.accepted = false // Let it propagate for non-chord
|
||||
}
|
||||
|
||||
TapHandler {
|
||||
acceptedButtons: Qt.RightButton
|
||||
onTapped: promptContextMenu.popup()
|
||||
onClicked: function(mouse) {
|
||||
// Only handle non-chord clicks
|
||||
if (leftHeld) {
|
||||
leftHeld = false
|
||||
return
|
||||
}
|
||||
|
||||
if (mouse.button === Qt.MiddleButton) {
|
||||
// B2: Execute selection as prompt
|
||||
var sel = promptInput.selectedText
|
||||
if (sel && sel.trim() !== "") {
|
||||
ollie.submit(sel.trim())
|
||||
} else {
|
||||
// No selection - paste from clipboard and execute?
|
||||
// Or just ignore. For now, ignore.
|
||||
}
|
||||
} else if (mouse.button === Qt.RightButton) {
|
||||
// B3: Plumb selection or show context menu
|
||||
var sel = promptInput.selectedText
|
||||
if (sel && sel.trim() !== "" && plumber.available()) {
|
||||
plumber.plumb(sel.trim())
|
||||
} else {
|
||||
promptContextMenu.popup()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
onReleased: {
|
||||
leftHeld = false
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -390,7 +443,7 @@ Item {
|
|||
}
|
||||
MenuSeparator {}
|
||||
MenuItem {
|
||||
text: "Cut"
|
||||
text: "Cut (B1+B2)"
|
||||
enabled: promptInput.selectedText.length > 0
|
||||
onTriggered: promptInput.cut()
|
||||
}
|
||||
|
|
@ -400,7 +453,7 @@ Item {
|
|||
onTriggered: promptInput.copy()
|
||||
}
|
||||
MenuItem {
|
||||
text: "Paste"
|
||||
text: "Paste (B1+B3)"
|
||||
enabled: promptInput.canPaste
|
||||
onTriggered: promptInput.paste()
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue