Skip to content

Commit

Permalink
Fix text transformation commands for multiple line, single selection …
Browse files Browse the repository at this point in the history
…cases (#3060)

If you highlight the following block of text (with a single selection):

```
The quick brown
fox jumps over
the lazy dog
```

and run `editor: convert to upper camel case`, you'll get:

```
TheQuickBrown
foxJumpsOver
theLazyDog
```

instead of:

```
TheQuickBrown
FoxJumpsOver
TheLazyDog
```

The same thing happens for `editor: convert to title case`. This happens
because [`to_case` crate](https://crates.io/crates/convert_case) doesn't
allow the user to define '\n' as a boundary. I wanted to fix this at the
lib level, so I filled [an
issue](rutrum/convert-case#16) but I never
heard back. What's strange is VS Code and Sublime I think both exhibit
the same output as we do currently, but I don't personally think this
feels right (happy to hear opposing opinions). I'm just doing the naive
thing to hack around this limitation of the `to_case` crate.

I did some testing and it seems I only need to adjust `editor: convert
to title case` and `editor: convert to upper camel case`. The way the
other transformations are implemented in `to_case` don't seem to have
this issue.

Release Notes:

- Fixed a bug where running certain text transfomration commands on a
single selection covering multiple lines would not transform all
selected lines as expected.
  • Loading branch information
JosephTLyons authored Sep 28, 2023
1 parent a8188a2 commit 3cf7164
Show file tree
Hide file tree
Showing 2 changed files with 42 additions and 2 deletions.
16 changes: 14 additions & 2 deletions crates/editor/src/editor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4653,7 +4653,13 @@ impl Editor {
}

pub fn convert_to_title_case(&mut self, _: &ConvertToTitleCase, cx: &mut ViewContext<Self>) {
self.manipulate_text(cx, |text| text.to_case(Case::Title))
self.manipulate_text(cx, |text| {
// Hack to get around the fact that to_case crate doesn't support '\n' as a word boundary
// https://github.com/rutrum/convert-case/issues/16
text.split("\n")
.map(|line| line.to_case(Case::Title))
.join("\n")
})
}

pub fn convert_to_snake_case(&mut self, _: &ConvertToSnakeCase, cx: &mut ViewContext<Self>) {
Expand All @@ -4669,7 +4675,13 @@ impl Editor {
_: &ConvertToUpperCamelCase,
cx: &mut ViewContext<Self>,
) {
self.manipulate_text(cx, |text| text.to_case(Case::UpperCamel))
self.manipulate_text(cx, |text| {
// Hack to get around the fact that to_case crate doesn't support '\n' as a word boundary
// https://github.com/rutrum/convert-case/issues/16
text.split("\n")
.map(|line| line.to_case(Case::UpperCamel))
.join("\n")
})
}

pub fn convert_to_lower_camel_case(
Expand Down
28 changes: 28 additions & 0 deletions crates/editor/src/editor_tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2792,6 +2792,34 @@ async fn test_manipulate_text(cx: &mut TestAppContext) {
«hello worldˇ»
"});

// Test multiple line, single selection case
// Test code hack that covers the fact that to_case crate doesn't support '\n' as a word boundary
cx.set_state(indoc! {"
«The quick brown
fox jumps over
the lazy dogˇ»
"});
cx.update_editor(|e, cx| e.convert_to_title_case(&ConvertToTitleCase, cx));
cx.assert_editor_state(indoc! {"
«The Quick Brown
Fox Jumps Over
The Lazy Dogˇ»
"});

// Test multiple line, single selection case
// Test code hack that covers the fact that to_case crate doesn't support '\n' as a word boundary
cx.set_state(indoc! {"
«The quick brown
fox jumps over
the lazy dogˇ»
"});
cx.update_editor(|e, cx| e.convert_to_upper_camel_case(&ConvertToUpperCamelCase, cx));
cx.assert_editor_state(indoc! {"
«TheQuickBrown
FoxJumpsOver
TheLazyDogˇ»
"});

// From here on out, test more complex cases of manipulate_text()

// Test no selection case - should affect words cursors are in
Expand Down

0 comments on commit 3cf7164

Please sign in to comment.