diff --git a/.changeset/many-trains-cheat.md b/.changeset/many-trains-cheat.md
new file mode 100644
index 00000000..9e9eeaa0
--- /dev/null
+++ b/.changeset/many-trains-cheat.md
@@ -0,0 +1,5 @@
+---
+'playroom': patch
+---
+
+Fix issue with "Toggle comment" command commenting certain code outside JSX tags with incorrect syntax.
diff --git a/cypress/e2e/keymaps.cy.js b/cypress/e2e/keymaps.cy.js
index 620ded93..1198ce4b 100644
--- a/cypress/e2e/keymaps.cy.js
+++ b/cypress/e2e/keymaps.cy.js
@@ -412,7 +412,7 @@ describe('Keymaps', () => {
>
Text
- `);
+ `);
moveBy(0, 2);
@@ -429,6 +429,76 @@ describe('Keymaps', () => {
`);
});
+
+ it('block - expression slot outside tags', () => {
+ loadPlayroom(`
+ {testFn('test')}
+
First line
+ Second line
+ Third line
+ `);
+
+ executeToggleCommentCommand();
+
+ assertCodePaneContains(dedent`
+ {/* {testFn('test')} */}
+ First line
+ Second line
+ Third line
+ `);
+ });
+
+ it('line - inside multi-line expression slot outside tags', () => {
+ loadPlayroom(`
+ {
+ testFn('test')
+ }
+ First line
+ Second line
+ Third line
+ `);
+
+ moveBy(0, 1);
+
+ executeToggleCommentCommand();
+
+ assertCodePaneContains(dedent`
+ {
+ // testFn('test')
+ }
+ First line
+ Second line
+ Third line
+ `);
+ });
+
+ it('line - full line expression slot inside tags', () => {
+ loadPlayroom(`
+
+ First line
+
+ Second line
+ Third line
+ `);
+
+ moveBy(0, 2);
+
+ executeToggleCommentCommand();
+
+ assertCodePaneContains(dedent`
+
+ First line
+
+ Second line
+ Third line
+ `);
+ });
});
describe('should wrap a single line selection in a comment', () => {
diff --git a/src/Playroom/CodeEditor/keymaps/comment.ts b/src/Playroom/CodeEditor/keymaps/comment.ts
index 3da03d3e..b963f401 100644
--- a/src/Playroom/CodeEditor/keymaps/comment.ts
+++ b/src/Playroom/CodeEditor/keymaps/comment.ts
@@ -198,6 +198,19 @@ function getUpdatedContent(existingContent: string, range: TagRange) {
type CommentType = 'line' | 'block';
+const isOnlyWhitespace = (input: string) => /^\s+$/.test(input);
+
+const isFullExpressionSlot = (tokens: CodeMirror.Token[]) => {
+ const formattedLineTokens = tokens.filter(
+ (token) => token.type !== 'comment' && !isOnlyWhitespace(token.string)
+ );
+
+ return (
+ formattedLineTokens.at(0)?.string === '{' &&
+ formattedLineTokens.at(-1)?.string === '}'
+ );
+};
+
interface TagRange {
from: CodeMirror.Position;
to: CodeMirror.Position;
@@ -219,7 +232,9 @@ const determineCommentType = (
(token) => token.type === 'attribute'
);
- const isJavaScriptMode = cm.getModeAt(from).name === 'javascript';
+ const isJavaScriptMode =
+ cm.getModeAt(new Pos(from.line, 0)).name === 'javascript';
+
const isInlineComment = cm
.getLine(from.line)
.trimStart()
@@ -228,6 +243,10 @@ const determineCommentType = (
cm.getLine(from.line).trimStart().startsWith(BLOCK_COMMENT_START) &&
cm.getLine(to.line).trimEnd().endsWith(BLOCK_COMMENT_END);
+ if (!isBlockComment && isFullExpressionSlot(lineTokens)) {
+ return isJavaScriptMode ? 'block' : 'line';
+ }
+
if (isInlineComment) {
return 'line';
}