[READ-ONLY] Mirror of https://github.com/improsocial/impro An extensible Bluesky client for web impro.social
6

Configure Feed

Select the types of activity you want to include in your feed.

Update post composer emoji method

Grace Kind (Jul 15, 2026, 7:19 PM -0500) 77e2b41f faefa69f

+44 -23
+1 -1
package.json
··· 1 1 { 2 2 "name": "impro", 3 - "version": "0.17.168", 3 + "version": "0.17.169", 4 4 "type": "module", 5 5 "scripts": { 6 6 "start": "rm -rf \"${BUILD_DIR:-build}\" && NODE_ENV=development eleventy --serve",
+1 -4
src/js/components/chat-input.js
··· 112 112 handleEmojiSelect(emoji) { 113 113 const richTextInput = this.querySelector("rich-text-input"); 114 114 if (!richTextInput) return; 115 - const text = richTextInput.text; 116 - const cursor = this._emojiCursor ?? text.length; 117 - richTextInput.setText(text.slice(0, cursor) + emoji + text.slice(cursor)); 115 + richTextInput.insertText(emoji, this._emojiCursor); 118 116 richTextInput.focus(); 119 - richTextInput.setCursor(cursor + emoji.length); 120 117 } 121 118 122 119 handleKeyDown(e) {
+3 -18
src/js/components/post-composer.js
··· 438 438 dialog.close(); 439 439 return; 440 440 } 441 - const selection = window.getSelection(); 442 441 const richTextInput = this.querySelector("rich-text-input"); 443 - const editable = richTextInput?.querySelector(".rich-text-input"); 444 - if ( 445 - editable && 446 - selection?.rangeCount && 447 - editable.contains(selection.getRangeAt(0).commonAncestorContainer) 448 - ) { 449 - this._savedEmojiRange = selection.getRangeAt(0).cloneRange(); 450 - } else { 451 - this._savedEmojiRange = null; 452 - } 442 + this._savedEmojiCursor = richTextInput?.getCursor() ?? null; 453 443 dialog.open(event.currentTarget); 454 444 } 455 445 456 446 handleEmojiSelect(emoji) { 457 447 const richTextInput = this.querySelector("rich-text-input"); 458 448 if (!richTextInput) return; 449 + richTextInput.insertText(emoji, this._savedEmojiCursor); 459 450 richTextInput.focus(); 460 - if (this._savedEmojiRange) { 461 - const selection = window.getSelection(); 462 - selection.removeAllRanges(); 463 - selection.addRange(this._savedEmojiRange); 464 - } 465 - document.execCommand("insertText", false, emoji); 466 - this._savedEmojiRange = null; 451 + this._savedEmojiCursor = null; 467 452 } 468 453 469 454 handleExternalLinkEmbedPreviewClose() {
+6
src/js/components/rich-text-input.js
··· 405 405 setCursorPosition(input, position); 406 406 } 407 407 408 + insertText(str, position) { 409 + const at = position ?? this.getCursor() ?? this.text.length; 410 + this.setText(this.text.slice(0, at) + str + this.text.slice(at)); 411 + this.setCursor(at + str.length); 412 + } 413 + 408 414 render() { 409 415 render( 410 416 html`
+33
tests/unit/specs/components/rich-text-input.test.js
··· 599 599 }); 600 600 }); 601 601 602 + describe("RichTextInput - insertText", () => { 603 + it("inserts at the given position and moves the caret past the inserted text", () => { 604 + const element = document.createElement("rich-text-input"); 605 + document.body.appendChild(element); 606 + element.setText("abcdef"); 607 + element.insertText("XY", 2); 608 + assert.deepEqual(element.text, "abXYcdef"); 609 + }); 610 + 611 + it("falls back to the current cursor when position is null", () => { 612 + const element = document.createElement("rich-text-input"); 613 + document.body.appendChild(element); 614 + element.setText("abcdef"); 615 + const input = element.querySelector(".rich-text-input"); 616 + const textNode = [...input.querySelector("div").childNodes].find( 617 + (node) => node.nodeType === Node.TEXT_NODE, 618 + ); 619 + const originalGetSelection = window.getSelection; 620 + window.getSelection = () => ({ 621 + rangeCount: 1, 622 + getRangeAt: () => ({ endContainer: textNode, endOffset: 3 }), 623 + removeAllRanges: () => {}, 624 + addRange: () => {}, 625 + }); 626 + try { 627 + element.insertText("Z", null); 628 + } finally { 629 + window.getSelection = originalGetSelection; 630 + } 631 + assert.deepEqual(element.text, "abcZdef"); 632 + }); 633 + }); 634 + 602 635 describe("RichTextInput - typeahead direction", () => { 603 636 let originalRangeRect; 604 637