Reduce the scope for toggling a checkbox on/off when not clicking precisely on it (must be to the left of the first letter)
All checks were successful
CI / test (push) Successful in 9m34s
Lint / test (push) Successful in 41s
Trivy / test (push) Successful in 23s

This commit is contained in:
Miguel Jacq 2025-12-12 14:10:43 +11:00
parent 7a75d33bb0
commit c1c95ca0ca
Signed by: mig5
GPG key ID: 59B3F0C24135C6A9
2 changed files with 43 additions and 9 deletions

View file

@ -1,3 +1,7 @@
# 0.7.1
* Reduce the scope for toggling a checkbox on/off when not clicking precisely on it (must be to the left of the first letter)
# 0.7.0 # 0.7.0
* New Invoicing feature! This is tied to time logging and (optionally) documents and reminders features. * New Invoicing feature! This is tied to time logging and (optionally) documents and reminders features.

View file

@ -1317,15 +1317,43 @@ class MarkdownEditor(QTextEdit):
if icon: if icon:
# absolute document position of the icon # absolute document position of the icon
doc_pos = block.position() + i doc_pos = block.position() + i
r = char_rect_at(doc_pos, icon) r_icon = char_rect_at(doc_pos, icon)
# ---------- Relax the hit area here ---------- # --- Find where the first non-space "real text" starts ---
# Expand the clickable area horizontally so you don't have to first_idx = i + len(icon) + 1 # skip icon + trailing space
# land exactly on the glyph. This makes the "checkbox zone" while first_idx < len(text) and text[first_idx].isspace():
# roughly 3× the glyph width, centered on it. first_idx += 1
pad = r.width() # one glyph width on each side
hit_rect = r.adjusted(-pad, 0, pad, 0) # Start with some padding around the icon itself
# --------------------------------------------- left_pad = r_icon.width() // 2
right_pad = r_icon.width() // 2
hit_left = r_icon.left() - left_pad
# If there's actual text after the checkbox, clamp the
# clickable area so it stops *before* the first letter.
if first_idx < len(text):
first_doc_pos = block.position() + first_idx
c_first = QTextCursor(self.document())
c_first.setPosition(first_doc_pos)
first_x = self.cursorRect(c_first).x()
expanded_right = r_icon.right() + right_pad
hit_right = min(expanded_right, first_x)
else:
# No text after the checkbox on this line
hit_right = r_icon.right() + right_pad
# Make sure the rect is at least 1px wide
if hit_right <= hit_left:
hit_right = r_icon.right()
hit_rect = QRect(
hit_left,
r_icon.top(),
max(1, hit_right - hit_left),
r_icon.height(),
)
if hit_rect.contains(pt): if hit_rect.contains(pt):
# Build the replacement: swap ☐ <-> ☑ (keep trailing space) # Build the replacement: swap ☐ <-> ☑ (keep trailing space)
@ -1339,7 +1367,9 @@ class MarkdownEditor(QTextEdit):
edit.setPosition(doc_pos) edit.setPosition(doc_pos)
# icon + space # icon + space
edit.movePosition( edit.movePosition(
QTextCursor.Right, QTextCursor.KeepAnchor, len(icon) + 1 QTextCursor.Right,
QTextCursor.KeepAnchor,
len(icon) + 1,
) )
edit.insertText(f"{new_icon} ") edit.insertText(f"{new_icon} ")
edit.endEditBlock() edit.endEditBlock()