Last active
March 30, 2021 17:16
-
-
Save mattst/cdae8ddc0addbb9fd6c99db919f5dbe3 to your computer and use it in GitHub Desktop.
A Sublime Text plugin to delete the text ahead or behind of the cursor breaking at whitespace characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# | |
# Name: Delete To Whitespace | |
# Requires: Plugin for Sublime Text v3 | |
# Author: mattst - https://github.com/mattst | |
# Command: delete_to_whitespace | |
# Args: forwards: bool (delete backwards if false) | |
# License: MIT License | |
# See Also: https://stackoverflow.com/a/66870369/2102457 | |
# | |
import sublime, sublime_plugin, re | |
class DeleteToWhitespaceCommand(sublime_plugin.TextCommand): | |
""" | |
A Sublime Text plugin that deletes text from the cursor to the next or | |
previous group of characters, the grouping being defined as either | |
whitespace or non-whitespace characters. Thus if run several times in | |
succession it will alternate between deleting groups of whitespace and | |
non-whitespace ahead or behind the cursor. The forwards parameter of the | |
run() method (i.e. the command's arg) controls the deletion direction. | |
""" | |
def run(self, edit, forwards=True): | |
self.edit = edit | |
self.forwards = forwards | |
if forwards: | |
self.delete_forwards() | |
else: | |
self.delete_backwards() | |
def delete_forwards(self): | |
whitespace_regex = "^\s+" | |
non_whitespace_regex = "^\S+" | |
for sel in self.view.sel(): | |
if sel.size() > 0: | |
self.view.erase(self.edit, sel) | |
continue | |
# ∴ sel.a == sel.b == sel.begin() == sel.end() | |
# view.full_line() includes the trailing newline (if any). | |
cursor = sel.a | |
line = self.view.full_line(cursor) | |
cursor_to_eol = sublime.Region(cursor, line.end()) | |
cursor_to_eol_str = self.view.substr(cursor_to_eol) | |
match = re.search(whitespace_regex, cursor_to_eol_str) | |
if match: | |
self.erase_matching_characters(cursor, match) | |
continue | |
match = re.search(non_whitespace_regex, cursor_to_eol_str) | |
if match: | |
self.erase_matching_characters(cursor, match) | |
continue | |
def delete_backwards(self): | |
whitespace_regex = "\s+$" | |
non_whitespace_regex = "\S+$" | |
for sel in self.view.sel(): | |
if sel.size() > 0: | |
self.view.erase(self.edit, sel) | |
continue | |
# ∴ sel.a == sel.b == sel.begin() == sel.end() | |
# view.line() excludes the trailing newline (if any). | |
cursor = sel.a | |
line = self.view.line(cursor) | |
cursor_to_bol = sublime.Region(cursor, line.begin()) | |
cursor_to_bol_str = self.view.substr(cursor_to_bol) | |
# Delete the new line of the 'previous' line. | |
if cursor_to_bol.size() == 0 and cursor > 0: | |
erase_region = sublime.Region(cursor, cursor - 1) | |
self.view.erase(self.edit, erase_region) | |
continue | |
match = re.search(whitespace_regex, cursor_to_bol_str) | |
if match: | |
self.erase_matching_characters(cursor, match) | |
continue | |
match = re.search(non_whitespace_regex, cursor_to_bol_str) | |
if match: | |
self.erase_matching_characters(cursor, match) | |
continue | |
def erase_matching_characters(self, cursor, match): | |
match_len = match.end() - match.start() | |
if self.forwards: | |
erase_region = sublime.Region(cursor, cursor + match_len) | |
else: | |
erase_region = sublime.Region(cursor, cursor - match_len) | |
self.view.erase(self.edit, erase_region) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment