web: the placeholder hides once the empty draft is already a block (#932)
Typing '- ' turns the paragraph into a list item — visible structure — but pm-empty only checked text content, so the placeholder kept rendering under the bullet. It now shows only over a bare empty paragraph. (The iOS twin of this bug is fixed on the stage-3a branch.)
Co-authored-by: Claude Fable 5 <noreply@anthropic.com>
1 file changed,
+12
−1
web/static/composer-pm.js+12 −1
diff --git a/web/static/composer-pm.js b/web/static/composer-pm.js| index f049576..162016a 100644 |
| --- a/web/static/composer-pm.js |
| +++ b/web/static/composer-pm.js |
| @@ -174,7 +174,18 @@ export function createRichComposer(opts = {}) { |
| view.dom.addEventListener("blur", () => opts.onBlur && opts.onBlur()); |
| const isEmptyDoc = () => docText(view.state.doc).trim() === ""; |
| - const refreshEmpty = () => view.dom.classList.toggle("pm-empty", isEmptyDoc()); |
| + // The placeholder shows only over a bare empty paragraph — an empty list |
| + // item or fence is already visible structure, and the two would overlap. |
| + const showsPlaceholder = () => { |
| + const doc = view.state.doc; |
| + return ( |
| + isEmptyDoc() && |
| + doc.childCount === 1 && |
| + doc.firstChild.type.name === "paragraph" && |
| + doc.firstChild.childCount === 0 |
| + ); |
| + }; |
| + const refreshEmpty = () => view.dom.classList.toggle("pm-empty", showsPlaceholder()); |
| if (opts.placeholder) view.dom.setAttribute("data-placeholder", opts.placeholder); |
| refreshEmpty(); |