Skip to content

Commit

Permalink
Add command for toggling checkbox
Browse files Browse the repository at this point in the history
  • Loading branch information
jotaen authored Apr 2, 2022
1 parent 60014b3 commit 09aa8e6
Show file tree
Hide file tree
Showing 4 changed files with 70 additions and 14 deletions.
20 changes: 15 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,32 +18,42 @@ This Sublime Package provides syntax-highlighting, shortcuts, and auto-completio
### Keybindings for Commands

The following commands are available for you to put into your `Default.sublime-keymap` file.
The key combination is up to you, of course.

```js
[
// Toggle item status to checked [x]
// Toggle checkbox status of the item.
// It cycles through the statuses given in the
// `xit_toggle` setting.
{ "keys": ["ctrl+shift+t"], "command": "xit_toggle" },

// Set item status to checked [x]
{ "keys": ["ctrl+shift+x"], "command": "xit_check" },

// Toggle item status to open [ ]
// Set item status to open [ ]
{ "keys": ["ctrl+shift+o"], "command": "xit_open" },

// Toggle item status to ongoing [@]
// Set item status to ongoing [@]
{ "keys": ["ctrl+shift+a"], "command": "xit_ongoing" },

// Toggle item status to obsolete [~]
// Set item status to obsolete [~]
{ "keys": ["ctrl+shift+n"], "command": "xit_obsolete" },
]
```

### Settings (Syntax Specific)

The following settings can be overriden via your syntax-specific `xit.sublime-settings` file.
The values are the default ones.

```js
{
// Auto-save after toggling checkboxes (via the commands `xit_check`, etc.).
// Default: true
"xit_auto_save": true,

// The checkbox statuses that the `xit_toggle` command
// should cycle through.
"xit_toggle": ["[ ]", "[x]"],
}
```

Expand Down
56 changes: 48 additions & 8 deletions toggle_status.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,11 @@


BOX_PATTERN = re.compile('\[[ x~@]\]')
BOX_LENGTH = 3
INDENT_SEQUENCE = ' '


def toggle_status(view, edit, replacement):
def set_status(view, edit, replaceBy):
# Iterate through all selections (there might be
# multiple, due to multi-cursor-action), and all
# their lines.
Expand All @@ -31,12 +32,14 @@ def toggle_status(view, edit, replacement):
break

# If the line doesn’t start with a box, return.
box_candidate = sublime.Region(line.begin(), line.begin() + len(replacement))
if not BOX_PATTERN.match(view.substr(box_candidate)):
checkbox_region = sublime.Region(line.begin(), line.begin() + BOX_LENGTH)
checkbox = view.substr(checkbox_region)
if not BOX_PATTERN.match(checkbox):
return

# Replace status.
view.replace(edit, box_candidate, replacement)
replacement = replaceBy(checkbox)
view.replace(edit, checkbox_region, replacement)

# Auto-save, if enabled, and if there is a backing file.
settings = sublime.load_settings('xit.sublime-settings')
Expand All @@ -54,19 +57,56 @@ def is_enabled(self):

class XitCheckCommand(_XitCommand):
def run(self, edit):
toggle_status(self.view, edit, '[x]')
set_status(self.view, edit, lambda _: '[x]')


class XitOpenCommand(_XitCommand):
def run(self, edit):
toggle_status(self.view, edit, '[ ]')
set_status(self.view, edit, lambda _: '[ ]')


class XitObsoleteCommand(_XitCommand):
def run(self, edit):
toggle_status(self.view, edit, '[~]')
set_status(self.view, edit, lambda _: '[~]')


class XitOngoingCommand(_XitCommand):
def run(self, edit):
toggle_status(self.view, edit, '[@]')
set_status(self.view, edit, lambda _: '[@]')


class XitToggleCommand(_XitCommand):
def _load_toggles(self):
self._toggles = None
settings = sublime.load_settings('xit.sublime-settings')
toggles = settings.get('xit_toggle')

# Setting value must be a non-empty list.
if not isinstance(toggles, list) or len(toggles) == 0:
return None

# List must be checkboxes as string.
for t in toggles:
if (not isinstance(t, str)) or (not len(t) == 3) or (not BOX_PATTERN.match(t)):
return None

self._toggles = toggles

def _cycle(self, status):
# Find current status, or make it fall back to first.
try:
i = self._toggles.index(status)
except ValueError:
i = -1

# Return next status in the “ring”.
try:
return self._toggles[i+1]
except IndexError:
return self._toggles[0]

def run(self, edit):
self._load_toggles()
if not self._toggles:
return
set_status(self.view, edit, self._cycle)
5 changes: 4 additions & 1 deletion xit.sublime-commands
Original file line number Diff line number Diff line change
Expand Up @@ -20,5 +20,8 @@
}, {
"caption": "[x]it!: Mark Item As Obsolete",
"command": "xit_obsolete"
},
}, {
"caption": "[x]it!: Toggle Item Status",
"command": "xit_toggle"
}
]
3 changes: 3 additions & 0 deletions xit.sublime-settings
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,9 @@
// Auto-save after toggling checkboxes from the command palette.
"xit_auto_save": true,

// The checkbox statuses that the `xit_toggle` command cycles through.
"xit_toggle": ["[ ]", "[x]"],

// Always open [x]it! files with a specific theme.
// For Monokai and Mariana, there is language-specific
// syntax highlighting.
Expand Down

0 comments on commit 09aa8e6

Please sign in to comment.