diff --git a/app/assets/javascripts/discourse/app/components/user-status-picker.js b/app/assets/javascripts/discourse/app/components/user-status-picker.js index 691a4e683c3..602f4b1679b 100644 --- a/app/assets/javascripts/discourse/app/components/user-status-picker.js +++ b/app/assets/javascripts/discourse/app/components/user-status-picker.js @@ -8,12 +8,18 @@ export default class UserStatusPicker extends Component { tagName = ""; isFocused = false; emojiPickerIsActive = false; - emoji = null; - description = null; - @computed("emoji") + didInsertElement() { + this._super(...arguments); + + if (!this.status) { + this.set("status", {}); + } + } + + @computed("status.emoji") get emojiHtml() { - const emoji = escapeExpression(`:${this.emoji}:`); + const emoji = escapeExpression(`:${this.status.emoji}:`); return emojiUnescape(emoji); } @@ -24,7 +30,7 @@ export default class UserStatusPicker extends Component { @action emojiSelected(emoji) { - this.set("emoji", emoji); + this.set("status.emoji", emoji); this.set("emojiPickerIsActive", false); scheduleOnce("afterRender", () => { @@ -44,8 +50,8 @@ export default class UserStatusPicker extends Component { @action setDefaultEmoji() { - if (!this.emoji) { - this.set("emoji", "speech_balloon"); + if (!this.status.emoji) { + this.set("status.emoji", "speech_balloon"); } } diff --git a/app/assets/javascripts/discourse/app/controllers/user-status.js b/app/assets/javascripts/discourse/app/controllers/user-status.js index c438ac9c0d2..b4a1bc61f35 100644 --- a/app/assets/javascripts/discourse/app/controllers/user-status.js +++ b/app/assets/javascripts/discourse/app/controllers/user-status.js @@ -12,25 +12,18 @@ import { export default Controller.extend(ModalFunctionality, { userStatusService: service("user-status"), - - emoji: null, - description: null, - endsAt: null, - showDeleteButton: false, prefilledDateTime: null, timeShortcuts: null, _itsatrap: null, onShow() { - const status = this.currentUser.status; + const currentStatus = { ...this.currentUser.status }; this.setProperties({ - emoji: status?.emoji, - description: status?.description, - endsAt: status?.ends_at, - showDeleteButton: !!status, + status: currentStatus, + showDeleteButton: !!this.currentUser.status, timeShortcuts: this._buildTimeShortcuts(), - prefilledDateTime: status?.ends_at, + prefilledDateTime: currentStatus?.ends_at, }); this.set("_itsatrap", new ItsATrap()); @@ -42,7 +35,7 @@ export default Controller.extend(ModalFunctionality, { this.set("timeShortcuts", null); }, - @discourseComputed("emoji", "description") + @discourseComputed("status.emoji", "status.description") statusIsSet(emoji, description) { return !!emoji && !!description; }, @@ -69,18 +62,18 @@ export default Controller.extend(ModalFunctionality, { @action onTimeSelected(_, time) { - this.set("endsAt", time); + this.set("status.endsAt", time); }, @action saveAndClose() { - const status = { - description: this.description, - emoji: this.emoji, - ends_at: this.endsAt?.toISOString(), + const newStatus = { + description: this.status.description, + emoji: this.status.emoji, + ends_at: this.status.endsAt?.toISOString(), }; this.userStatusService - .set(status) + .set(newStatus) .then(() => { this.send("closeModal"); }) diff --git a/app/assets/javascripts/discourse/app/templates/components/user-status-picker.hbs b/app/assets/javascripts/discourse/app/templates/components/user-status-picker.hbs index d1b6d1002d0..4737847fe8d 100644 --- a/app/assets/javascripts/discourse/app/templates/components/user-status-picker.hbs +++ b/app/assets/javascripts/discourse/app/templates/components/user-status-picker.hbs @@ -7,7 +7,7 @@ {{on "focus" this.focus}} {{on "blur" this.blur}} > - {{#if @emoji}} + {{#if @status.emoji}} {{html-safe this.emojiHtml}} {{else}} {{d-icon "discourse-emojis"}} @@ -15,11 +15,15 @@ - + diff --git a/app/assets/javascripts/discourse/app/templates/modal/user-status.hbs b/app/assets/javascripts/discourse/app/templates/modal/user-status.hbs index 95d16a7f192..1d2adb7c5f0 100644 --- a/app/assets/javascripts/discourse/app/templates/modal/user-status.hbs +++ b/app/assets/javascripts/discourse/app/templates/modal/user-status.hbs @@ -1,7 +1,7 @@ - + diff --git a/app/assets/javascripts/discourse/tests/integration/components/user-status-picker-test.js b/app/assets/javascripts/discourse/tests/integration/components/user-status-picker-test.js new file mode 100644 index 00000000000..12c579bdf46 --- /dev/null +++ b/app/assets/javascripts/discourse/tests/integration/components/user-status-picker-test.js @@ -0,0 +1,54 @@ +import { module, test } from "qunit"; +import { click, fillIn, render } from "@ember/test-helpers"; +import { setupRenderingTest } from "discourse/tests/helpers/component-test"; +import { hbs } from "ember-cli-htmlbars"; +import { query } from "discourse/tests/helpers/qunit-helpers"; + +module("Integration | Component | user-status-picker", function (hooks) { + setupRenderingTest(hooks); + + test("it renders current status", async function (assert) { + const status = { + emoji: "tooth", + description: "off to dentist", + }; + this.set("status", status); + await render(hbs``); + assert.equal( + query(".emoji").alt, + status.emoji, + "the status emoji is shown" + ); + assert.equal( + query(".user-status-description").value, + status.description, + "the status description is shown" + ); + }); + + test("it picks emoji", async function (assert) { + const status = { + emoji: "tooth", + description: "off to dentist", + }; + this.set("status", status); + await render(hbs``); + + const newEmoji = "mega"; + await click(".btn-emoji"); + await fillIn(".emoji-picker-content .filter", newEmoji); + await click(".results .emoji"); + + assert.equal(query(".emoji").alt, newEmoji); + }); + + test("it sets default emoji when user starts typing a description", async function (assert) { + const defaultEmoji = "speech_balloon"; + + this.set("status", null); + await render(hbs``); + await fillIn(".user-status-description", "s"); + + assert.equal(query(".emoji").alt, defaultEmoji); + }); +});