show reactions per user, allow only one reaction per message per user
This commit is contained in:
Vendored
+2
-2
@@ -733,7 +733,7 @@ body[showing-chat] #chat-page-wrapper {
|
|||||||
display: none !important;
|
display: none !important;
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
}
|
}
|
||||||
.message-bubble > .message-reaction-row:has(button:not([zero])) {
|
.message-bubble > .message-reaction-row:has(button:not([count="0"])) {
|
||||||
display: grid !important;
|
display: grid !important;
|
||||||
}
|
}
|
||||||
.message-bubble > .message-reaction-row button {
|
.message-bubble > .message-reaction-row button {
|
||||||
@@ -745,7 +745,7 @@ body[showing-chat] #chat-page-wrapper {
|
|||||||
flex: 1 !important;
|
flex: 1 !important;
|
||||||
animation: slide-up var(--animation-duration);
|
animation: slide-up var(--animation-duration);
|
||||||
}
|
}
|
||||||
.message-bubble > .message-reaction-row button[zero] {
|
.message-bubble > .message-reaction-row button[count="0"] {
|
||||||
display: none;
|
display: none;
|
||||||
}
|
}
|
||||||
.message-reaction-row {
|
.message-reaction-row {
|
||||||
|
|||||||
Vendored
+54
-85
@@ -1498,11 +1498,7 @@
|
|||||||
const fileContent = FileModel2.createFileContent(v4_default(), "reaction");
|
const fileContent = FileModel2.createFileContent(v4_default(), "reaction");
|
||||||
const reaction = {
|
const reaction = {
|
||||||
...fileContent,
|
...fileContent,
|
||||||
fileId: _ChatModel.createMessageReactionId(
|
fileId: _ChatModel.createMessageReactionId(messageId, sender),
|
||||||
messageId,
|
|
||||||
content,
|
|
||||||
sender
|
|
||||||
),
|
|
||||||
messageId,
|
messageId,
|
||||||
sender,
|
sender,
|
||||||
content,
|
content,
|
||||||
@@ -1512,24 +1508,11 @@
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
static {
|
static {
|
||||||
this.createMessageReactionId = (messageId, content, sender) => {
|
this.createMessageReactionId = (messageId, sender) => {
|
||||||
return messageId + sender + reactionStringMap[content];
|
return messageId + sender;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
var ReactionSymbols = /* @__PURE__ */ ((ReactionSymbols2) => {
|
|
||||||
ReactionSymbols2["ThumbsUp"] = "\u{1F44D}";
|
|
||||||
ReactionSymbols2["Check"] = "\u2705";
|
|
||||||
ReactionSymbols2["Stop"] = "\u{1F6D1}";
|
|
||||||
ReactionSymbols2["Attention"] = "\u2757\uFE0F";
|
|
||||||
ReactionSymbols2["DoubleAttention"] = "\u203C\uFE0F";
|
|
||||||
ReactionSymbols2["Question"] = "\u2753";
|
|
||||||
return ReactionSymbols2;
|
|
||||||
})(ReactionSymbols || {});
|
|
||||||
var reactionStringMap = {};
|
|
||||||
Object.entries(ReactionSymbols).forEach((value) => {
|
|
||||||
reactionStringMap[value[1]] = value[0];
|
|
||||||
});
|
|
||||||
var ChatInfoReference = {
|
var ChatInfoReference = {
|
||||||
dataVersion: DATA_VERSION,
|
dataVersion: DATA_VERSION,
|
||||||
primaryChannel: "",
|
primaryChannel: "",
|
||||||
@@ -2038,35 +2021,39 @@
|
|||||||
this.status = new State(
|
this.status = new State(
|
||||||
void 0
|
void 0
|
||||||
);
|
);
|
||||||
this.reactionsThumbsUp = new MapState();
|
this.allReactions = new MapState();
|
||||||
this.reactionsCheck = new MapState();
|
this.userReaction = new State(void 0);
|
||||||
this.reactionsStop = new MapState();
|
this.reactionsThumbsUp = MapState;
|
||||||
this.reactionsAttention = new MapState();
|
this.reactionsCheck = MapState;
|
||||||
this.reactionsDoubleAttention = new MapState();
|
this.reactionsStop = MapState;
|
||||||
this.reactionsQuestion = new MapState();
|
this.reactionsAttention = MapState;
|
||||||
this.reactionsThumbsUpCount = createProxyState(
|
this.reactionsDoubleAttention = MapState;
|
||||||
[this.reactionsThumbsUp],
|
this.reactionsQuestion = MapState;
|
||||||
() => this.reactionsThumbsUp.value.size
|
this.generateReactionCountProxyState = (content) => {
|
||||||
|
return createProxyState(
|
||||||
|
[this.allReactions],
|
||||||
|
() => [...this.allReactions.value.values()].filter(
|
||||||
|
(x) => x.content == content
|
||||||
|
).length
|
||||||
);
|
);
|
||||||
this.reactionsCheckCount = createProxyState(
|
};
|
||||||
[this.reactionsCheck],
|
this.reactionsThumbsUpCount = this.generateReactionCountProxyState(
|
||||||
() => this.reactionsCheck.value.size
|
"\u{1F44D}" /* ThumbsUp */
|
||||||
);
|
);
|
||||||
this.reactionsStopCount = createProxyState(
|
this.reactionsCheckCount = this.generateReactionCountProxyState(
|
||||||
[this.reactionsStop],
|
"\u2705" /* Check */
|
||||||
() => this.reactionsStop.value.size
|
|
||||||
);
|
);
|
||||||
this.reactionsAttentionCount = createProxyState(
|
this.reactionsStopCount = this.generateReactionCountProxyState(
|
||||||
[this.reactionsAttention],
|
"\u{1F6D1}" /* Stop */
|
||||||
() => this.reactionsAttention.value.size
|
|
||||||
);
|
);
|
||||||
this.reactionsDoubleAttentionCount = createProxyState(
|
this.reactionsAttentionCount = this.generateReactionCountProxyState(
|
||||||
[this.reactionsDoubleAttention],
|
"\u2757\uFE0F" /* Attention */
|
||||||
() => this.reactionsDoubleAttention.value.size
|
|
||||||
);
|
);
|
||||||
this.reactionsQuestionCount = createProxyState(
|
this.reactionsDoubleAttentionCount = this.generateReactionCountProxyState(
|
||||||
[this.reactionsQuestion],
|
"\u203C\uFE0F" /* DoubleAttention */
|
||||||
() => this.reactionsQuestion.value.size
|
);
|
||||||
|
this.reactionsQuestionCount = this.generateReactionCountProxyState(
|
||||||
|
"\u2753" /* Question */
|
||||||
);
|
);
|
||||||
// state
|
// state
|
||||||
this.isPresentingInfoModal = new State(false);
|
this.isPresentingInfoModal = new State(false);
|
||||||
@@ -2089,27 +2076,13 @@
|
|||||||
};
|
};
|
||||||
// reactions
|
// reactions
|
||||||
this.handleReaction = (reaction) => {
|
this.handleReaction = (reaction) => {
|
||||||
function setReaction(mapState) {
|
|
||||||
if (reaction.isDeleting) {
|
if (reaction.isDeleting) {
|
||||||
mapState.remove(reaction.sender);
|
this.allReactions.remove(reaction.sender);
|
||||||
} else {
|
} else {
|
||||||
mapState.set(reaction.sender, reaction);
|
this.allReactions.set(reaction.sender, reaction);
|
||||||
}
|
|
||||||
}
|
|
||||||
switch (reaction.content) {
|
|
||||||
case "\u{1F44D}" /* ThumbsUp */:
|
|
||||||
return setReaction(this.reactionsThumbsUp);
|
|
||||||
case "\u2705" /* Check */:
|
|
||||||
return setReaction(this.reactionsCheck);
|
|
||||||
case "\u{1F6D1}" /* Stop */:
|
|
||||||
return setReaction(this.reactionsStop);
|
|
||||||
case "\u2757\uFE0F" /* Attention */:
|
|
||||||
return setReaction(this.reactionsAttention);
|
|
||||||
case "\u203C\uFE0F" /* DoubleAttention */:
|
|
||||||
return setReaction(this.reactionsDoubleAttention);
|
|
||||||
case "\u2753" /* Question */:
|
|
||||||
return setReaction(this.reactionsQuestion);
|
|
||||||
}
|
}
|
||||||
|
if (reaction.sender != this.coreViewModel.settingsModel.username) return;
|
||||||
|
this.userReaction.value = reaction.isDeleting ? void 0 : reaction.content;
|
||||||
};
|
};
|
||||||
this.sendReaction = (content, isDeleting) => {
|
this.sendReaction = (content, isDeleting) => {
|
||||||
this.messagePageViewModel.sendReaction(
|
this.messagePageViewModel.sendReaction(
|
||||||
@@ -3434,60 +3407,42 @@
|
|||||||
function MessageReactionButton(coreViewModel2, chatMessageViewModel, content) {
|
function MessageReactionButton(coreViewModel2, chatMessageViewModel, content) {
|
||||||
let audioLabel;
|
let audioLabel;
|
||||||
let count;
|
let count;
|
||||||
let reactionState;
|
let isActive = createProxyState([chatMessageViewModel.userReaction], () => chatMessageViewModel.userReaction.value == content);
|
||||||
let isActive = new State(false);
|
|
||||||
let isZero = new State(true);
|
|
||||||
function sendReaction() {
|
function sendReaction() {
|
||||||
chatMessageViewModel.sendReaction(content, isActive.value);
|
chatMessageViewModel.sendReaction(content, isActive.value);
|
||||||
}
|
}
|
||||||
function getUsername() {
|
|
||||||
return chatMessageViewModel.messagePageViewModel.chatViewModel.settingsViewModel.username.value;
|
|
||||||
}
|
|
||||||
function checkIsHighlighted() {
|
|
||||||
return reactionState.value.has(getUsername());
|
|
||||||
}
|
|
||||||
switch (content) {
|
switch (content) {
|
||||||
case "\u{1F44D}" /* ThumbsUp */: {
|
case "\u{1F44D}" /* ThumbsUp */: {
|
||||||
audioLabel = coreViewModel2.translations.chatPage.message.thumbsUpReaction;
|
audioLabel = coreViewModel2.translations.chatPage.message.thumbsUpReaction;
|
||||||
count = chatMessageViewModel.reactionsThumbsUpCount;
|
count = chatMessageViewModel.reactionsThumbsUpCount;
|
||||||
reactionState = chatMessageViewModel.reactionsThumbsUp;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case "\u2705" /* Check */: {
|
case "\u2705" /* Check */: {
|
||||||
audioLabel = coreViewModel2.translations.chatPage.message.checkReaction;
|
audioLabel = coreViewModel2.translations.chatPage.message.checkReaction;
|
||||||
count = chatMessageViewModel.reactionsCheckCount;
|
count = chatMessageViewModel.reactionsCheckCount;
|
||||||
reactionState = chatMessageViewModel.reactionsCheck;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case "\u{1F6D1}" /* Stop */: {
|
case "\u{1F6D1}" /* Stop */: {
|
||||||
audioLabel = coreViewModel2.translations.chatPage.message.stopReaction;
|
audioLabel = coreViewModel2.translations.chatPage.message.stopReaction;
|
||||||
count = chatMessageViewModel.reactionsStopCount;
|
count = chatMessageViewModel.reactionsStopCount;
|
||||||
reactionState = chatMessageViewModel.reactionsStop;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case "\u2757\uFE0F" /* Attention */: {
|
case "\u2757\uFE0F" /* Attention */: {
|
||||||
audioLabel = coreViewModel2.translations.chatPage.message.attentionReaction;
|
audioLabel = coreViewModel2.translations.chatPage.message.attentionReaction;
|
||||||
count = chatMessageViewModel.reactionsAttentionCount;
|
count = chatMessageViewModel.reactionsAttentionCount;
|
||||||
reactionState = chatMessageViewModel.reactionsAttention;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case "\u203C\uFE0F" /* DoubleAttention */: {
|
case "\u203C\uFE0F" /* DoubleAttention */: {
|
||||||
audioLabel = coreViewModel2.translations.chatPage.message.doubleAttentionReaction;
|
audioLabel = coreViewModel2.translations.chatPage.message.doubleAttentionReaction;
|
||||||
count = chatMessageViewModel.reactionsDoubleAttentionCount;
|
count = chatMessageViewModel.reactionsDoubleAttentionCount;
|
||||||
reactionState = chatMessageViewModel.reactionsDoubleAttention;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case "\u2753" /* Question */: {
|
case "\u2753" /* Question */: {
|
||||||
audioLabel = coreViewModel2.translations.chatPage.message.questionReaction;
|
audioLabel = coreViewModel2.translations.chatPage.message.questionReaction;
|
||||||
count = chatMessageViewModel.reactionsQuestionCount;
|
count = chatMessageViewModel.reactionsQuestionCount;
|
||||||
reactionState = chatMessageViewModel.reactionsQuestion;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
reactionState.subscribe(() => {
|
|
||||||
isActive.value = checkIsHighlighted();
|
|
||||||
isZero.value = reactionState.value.size == 0;
|
|
||||||
});
|
|
||||||
return /* @__PURE__ */ createElement(
|
return /* @__PURE__ */ createElement(
|
||||||
"button",
|
"button",
|
||||||
{
|
{
|
||||||
@@ -3495,7 +3450,7 @@
|
|||||||
"on:click": sendReaction,
|
"on:click": sendReaction,
|
||||||
"aria-label": audioLabel,
|
"aria-label": audioLabel,
|
||||||
"toggle:selected": isActive,
|
"toggle:selected": isActive,
|
||||||
"toggle:zero": isZero
|
"set:count": count
|
||||||
},
|
},
|
||||||
content,
|
content,
|
||||||
/* @__PURE__ */ createElement("span", { "subscribe:innerText": count })
|
/* @__PURE__ */ createElement("span", { "subscribe:innerText": count })
|
||||||
@@ -3542,6 +3497,11 @@
|
|||||||
return /* @__PURE__ */ createElement("div", { class: "tile" }, /* @__PURE__ */ createElement("span", { class: "icon" }, icon), /* @__PURE__ */ createElement("div", null, /* @__PURE__ */ createElement("span", null, label), /* @__PURE__ */ createElement("b", { class: "break-word", "subscribe:innerText": contentState })));
|
return /* @__PURE__ */ createElement("div", { class: "tile" }, /* @__PURE__ */ createElement("span", { class: "icon" }, icon), /* @__PURE__ */ createElement("div", null, /* @__PURE__ */ createElement("span", null, label), /* @__PURE__ */ createElement("b", { class: "break-word", "subscribe:innerText": contentState })));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// src/View/Components/messageReactionEntry.tsx
|
||||||
|
function MessageReactionEntry(reaction) {
|
||||||
|
return /* @__PURE__ */ createElement("div", { class: "tile flex-row" }, /* @__PURE__ */ createElement("span", { class: "flex width-100" }, reaction.sender), /* @__PURE__ */ createElement("span", null, reaction.content));
|
||||||
|
}
|
||||||
|
|
||||||
// src/View/Modals/chatMessageInfoModal.tsx
|
// src/View/Modals/chatMessageInfoModal.tsx
|
||||||
function ChatMessageInfoModal(coreViewModel2, chatMessageViewModel) {
|
function ChatMessageInfoModal(coreViewModel2, chatMessageViewModel) {
|
||||||
return /* @__PURE__ */ createElement(
|
return /* @__PURE__ */ createElement(
|
||||||
@@ -3566,10 +3526,19 @@
|
|||||||
"description",
|
"description",
|
||||||
coreViewModel2.translations.chatPage.message.messageContent,
|
coreViewModel2.translations.chatPage.message.messageContent,
|
||||||
chatMessageViewModel.body
|
chatMessageViewModel.body
|
||||||
)), /* @__PURE__ */ createElement("hr", null), /* @__PURE__ */ createElement("div", { class: "flex-column gap" }, /* @__PURE__ */ createElement("button", { "on:click": chatMessageViewModel.copyMessage }, coreViewModel2.translations.chatPage.message.copyMessageButton, /* @__PURE__ */ createElement("span", { class: "icon" }, "content_copy")), /* @__PURE__ */ createElement("button", { "on:click": chatMessageViewModel.resendMessage }, coreViewModel2.translations.chatPage.message.resendMessageButton, /* @__PURE__ */ createElement("span", { class: "icon" }, "redo")), /* @__PURE__ */ createElement("button", { "on:click": chatMessageViewModel.decryptMessage }, coreViewModel2.translations.chatPage.message.decryptMessageButton, /* @__PURE__ */ createElement("span", { class: "icon" }, "key"))), /* @__PURE__ */ createElement("hr", null), MessageReactionButtonRow(
|
)), /* @__PURE__ */ createElement("hr", null), /* @__PURE__ */ createElement("div", { class: "flex-column gap" }, /* @__PURE__ */ createElement("button", { "on:click": chatMessageViewModel.copyMessage }, coreViewModel2.translations.chatPage.message.copyMessageButton, /* @__PURE__ */ createElement("span", { class: "icon" }, "content_copy")), /* @__PURE__ */ createElement("button", { "on:click": chatMessageViewModel.resendMessage }, coreViewModel2.translations.chatPage.message.resendMessageButton, /* @__PURE__ */ createElement("span", { class: "icon" }, "redo")), /* @__PURE__ */ createElement("button", { "on:click": chatMessageViewModel.decryptMessage }, coreViewModel2.translations.chatPage.message.decryptMessageButton, /* @__PURE__ */ createElement("span", { class: "icon" }, "key"))), /* @__PURE__ */ createElement("hr", null), /* @__PURE__ */ createElement("div", { class: "flex-column gap" }, MessageReactionButtonRow(
|
||||||
coreViewModel2,
|
coreViewModel2,
|
||||||
chatMessageViewModel
|
chatMessageViewModel
|
||||||
)), /* @__PURE__ */ createElement("button", { "on:click": chatMessageViewModel.hideInfoModal }, coreViewModel2.translations.general.closeButton, /* @__PURE__ */ createElement("span", { class: "icon" }, "close")))
|
), /* @__PURE__ */ createElement(
|
||||||
|
"div",
|
||||||
|
{
|
||||||
|
class: "flex-column gap",
|
||||||
|
"children:append": [
|
||||||
|
chatMessageViewModel.allReactions,
|
||||||
|
MessageReactionEntry
|
||||||
|
]
|
||||||
|
}
|
||||||
|
))), /* @__PURE__ */ createElement("button", { "on:click": chatMessageViewModel.hideInfoModal }, coreViewModel2.translations.general.closeButton, /* @__PURE__ */ createElement("span", { class: "icon" }, "close")))
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -5623,7 +5592,7 @@
|
|||||||
this.connectionModel = connectionModel2;
|
this.connectionModel = connectionModel2;
|
||||||
this.chatListModel = chatListModel2;
|
this.chatListModel = chatListModel2;
|
||||||
this.fileTransferModel = fileTransferModel2;
|
this.fileTransferModel = fileTransferModel2;
|
||||||
this.BUILD = "Build 26.04.10.A";
|
this.BUILD = "Build 26.04.10.B";
|
||||||
// DRAG & DROP
|
// DRAG & DROP
|
||||||
this.draggedObject = new State(void 0);
|
this.draggedObject = new State(void 0);
|
||||||
// SUGGESTIONS
|
// SUGGESTIONS
|
||||||
|
|||||||
@@ -416,11 +416,7 @@ export default class ChatModel {
|
|||||||
const fileContent = FileModel.createFileContent(v4(), "reaction");
|
const fileContent = FileModel.createFileContent(v4(), "reaction");
|
||||||
const reaction: ChatMessageReaction = {
|
const reaction: ChatMessageReaction = {
|
||||||
...fileContent,
|
...fileContent,
|
||||||
fileId: ChatModel.createMessageReactionId(
|
fileId: ChatModel.createMessageReactionId(messageId, sender),
|
||||||
messageId,
|
|
||||||
content,
|
|
||||||
sender,
|
|
||||||
),
|
|
||||||
|
|
||||||
messageId,
|
messageId,
|
||||||
sender,
|
sender,
|
||||||
@@ -432,10 +428,9 @@ export default class ChatModel {
|
|||||||
|
|
||||||
static createMessageReactionId = (
|
static createMessageReactionId = (
|
||||||
messageId: string,
|
messageId: string,
|
||||||
content: ReactionSymbols,
|
|
||||||
sender: string,
|
sender: string,
|
||||||
): string => {
|
): string => {
|
||||||
return messageId + sender + reactionStringMap[content];
|
return messageId + sender;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -449,11 +444,6 @@ export enum ReactionSymbols {
|
|||||||
Question = "❓",
|
Question = "❓",
|
||||||
}
|
}
|
||||||
|
|
||||||
const reactionStringMap: { [key: ReactionSymbols | string]: string } = {};
|
|
||||||
Object.entries(ReactionSymbols).forEach((value) => {
|
|
||||||
reactionStringMap[value[1]] = value[0];
|
|
||||||
});
|
|
||||||
|
|
||||||
export interface ChatInfo extends ValidObject {
|
export interface ChatInfo extends ValidObject {
|
||||||
primaryChannel: string;
|
primaryChannel: string;
|
||||||
secondaryChannels: string[];
|
secondaryChannels: string[];
|
||||||
|
|||||||
@@ -181,7 +181,7 @@
|
|||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
}
|
}
|
||||||
|
|
||||||
.message-bubble > .message-reaction-row:has(button:not([zero])) {
|
.message-bubble > .message-reaction-row:has(button:not([count="0"])) {
|
||||||
display: grid !important;
|
display: grid !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -195,7 +195,7 @@
|
|||||||
animation: slide-up var(--animation-duration);
|
animation: slide-up var(--animation-duration);
|
||||||
}
|
}
|
||||||
|
|
||||||
.message-bubble > .message-reaction-row button[zero] {
|
.message-bubble > .message-reaction-row button[count="0"] {
|
||||||
display: none;
|
display: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -13,50 +13,35 @@ export function MessageReactionButton(
|
|||||||
) {
|
) {
|
||||||
let audioLabel: string;
|
let audioLabel: string;
|
||||||
let count: React.State<number>;
|
let count: React.State<number>;
|
||||||
let reactionState: React.MapState<ChatMessageReaction>;
|
let isActive = React.createProxyState([chatMessageViewModel.userReaction], (() => chatMessageViewModel.userReaction.value == content))
|
||||||
let isActive = new React.State(false);
|
|
||||||
let isZero = new React.State(true);
|
|
||||||
|
|
||||||
function sendReaction() {
|
function sendReaction() {
|
||||||
chatMessageViewModel.sendReaction(content, isActive.value);
|
chatMessageViewModel.sendReaction(content, isActive.value);
|
||||||
}
|
}
|
||||||
|
|
||||||
function getUsername(): string {
|
|
||||||
return chatMessageViewModel.messagePageViewModel.chatViewModel
|
|
||||||
.settingsViewModel.username.value;
|
|
||||||
}
|
|
||||||
|
|
||||||
function checkIsHighlighted(): boolean {
|
|
||||||
return reactionState.value.has(getUsername());
|
|
||||||
}
|
|
||||||
|
|
||||||
switch (content) {
|
switch (content) {
|
||||||
case ReactionSymbols.ThumbsUp: {
|
case ReactionSymbols.ThumbsUp: {
|
||||||
audioLabel =
|
audioLabel =
|
||||||
coreViewModel.translations.chatPage.message.thumbsUpReaction;
|
coreViewModel.translations.chatPage.message.thumbsUpReaction;
|
||||||
count = chatMessageViewModel.reactionsThumbsUpCount;
|
count = chatMessageViewModel.reactionsThumbsUpCount;
|
||||||
reactionState = chatMessageViewModel.reactionsThumbsUp;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case ReactionSymbols.Check: {
|
case ReactionSymbols.Check: {
|
||||||
audioLabel =
|
audioLabel =
|
||||||
coreViewModel.translations.chatPage.message.checkReaction;
|
coreViewModel.translations.chatPage.message.checkReaction;
|
||||||
count = chatMessageViewModel.reactionsCheckCount;
|
count = chatMessageViewModel.reactionsCheckCount;
|
||||||
reactionState = chatMessageViewModel.reactionsCheck;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case ReactionSymbols.Stop: {
|
case ReactionSymbols.Stop: {
|
||||||
audioLabel =
|
audioLabel =
|
||||||
coreViewModel.translations.chatPage.message.stopReaction;
|
coreViewModel.translations.chatPage.message.stopReaction;
|
||||||
count = chatMessageViewModel.reactionsStopCount;
|
count = chatMessageViewModel.reactionsStopCount;
|
||||||
reactionState = chatMessageViewModel.reactionsStop;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case ReactionSymbols.Attention: {
|
case ReactionSymbols.Attention: {
|
||||||
audioLabel =
|
audioLabel =
|
||||||
coreViewModel.translations.chatPage.message.attentionReaction;
|
coreViewModel.translations.chatPage.message.attentionReaction;
|
||||||
count = chatMessageViewModel.reactionsAttentionCount;
|
count = chatMessageViewModel.reactionsAttentionCount;
|
||||||
reactionState = chatMessageViewModel.reactionsAttention;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case ReactionSymbols.DoubleAttention: {
|
case ReactionSymbols.DoubleAttention: {
|
||||||
@@ -64,30 +49,23 @@ export function MessageReactionButton(
|
|||||||
coreViewModel.translations.chatPage.message
|
coreViewModel.translations.chatPage.message
|
||||||
.doubleAttentionReaction;
|
.doubleAttentionReaction;
|
||||||
count = chatMessageViewModel.reactionsDoubleAttentionCount;
|
count = chatMessageViewModel.reactionsDoubleAttentionCount;
|
||||||
reactionState = chatMessageViewModel.reactionsDoubleAttention;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case ReactionSymbols.Question: {
|
case ReactionSymbols.Question: {
|
||||||
audioLabel =
|
audioLabel =
|
||||||
coreViewModel.translations.chatPage.message.questionReaction;
|
coreViewModel.translations.chatPage.message.questionReaction;
|
||||||
count = chatMessageViewModel.reactionsQuestionCount;
|
count = chatMessageViewModel.reactionsQuestionCount;
|
||||||
reactionState = chatMessageViewModel.reactionsQuestion;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
reactionState.subscribe(() => {
|
|
||||||
isActive.value = checkIsHighlighted();
|
|
||||||
isZero.value = reactionState.value.size == 0;
|
|
||||||
});
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<button
|
<button
|
||||||
class="flex"
|
class="flex"
|
||||||
on:click={sendReaction}
|
on:click={sendReaction}
|
||||||
aria-label={audioLabel}
|
aria-label={audioLabel}
|
||||||
toggle:selected={isActive}
|
toggle:selected={isActive}
|
||||||
toggle:zero={isZero}
|
set:count={count}
|
||||||
>
|
>
|
||||||
{content}
|
{content}
|
||||||
<span subscribe:innerText={count}></span>
|
<span subscribe:innerText={count}></span>
|
||||||
|
|||||||
@@ -0,0 +1,13 @@
|
|||||||
|
import * as React from "bloatless-react";
|
||||||
|
import CoreViewModel from "../../ViewModel/Global/coreViewModel";
|
||||||
|
import ChatMessageViewModel from "../../ViewModel/Chat/chatMessageViewModel";
|
||||||
|
import { ChatMessageReaction } from "../../Model/Chat/chatModel";
|
||||||
|
|
||||||
|
export function MessageReactionEntry(reaction: ChatMessageReaction) {
|
||||||
|
return (
|
||||||
|
<div class="tile flex-row">
|
||||||
|
<span class="flex width-100">{reaction.sender}</span>
|
||||||
|
<span>{reaction.content}</span>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -4,6 +4,7 @@ import ChatMessageViewModel from "../../ViewModel/Chat/chatMessageViewModel";
|
|||||||
import { MessageReactionButtonRow } from "../Components/messageReactionButtonRow";
|
import { MessageReactionButtonRow } from "../Components/messageReactionButtonRow";
|
||||||
import { InfoTile } from "../Components/infoTile";
|
import { InfoTile } from "../Components/infoTile";
|
||||||
import CoreViewModel from "../../ViewModel/Global/coreViewModel";
|
import CoreViewModel from "../../ViewModel/Global/coreViewModel";
|
||||||
|
import { MessageReactionEntry } from "../Components/messageReactionEntry";
|
||||||
|
|
||||||
export function ChatMessageInfoModal(
|
export function ChatMessageInfoModal(
|
||||||
coreViewModel: CoreViewModel,
|
coreViewModel: CoreViewModel,
|
||||||
@@ -76,10 +77,20 @@ export function ChatMessageInfoModal(
|
|||||||
|
|
||||||
<hr></hr>
|
<hr></hr>
|
||||||
|
|
||||||
|
<div class="flex-column gap">
|
||||||
{MessageReactionButtonRow(
|
{MessageReactionButtonRow(
|
||||||
coreViewModel,
|
coreViewModel,
|
||||||
chatMessageViewModel,
|
chatMessageViewModel,
|
||||||
)}
|
)}
|
||||||
|
|
||||||
|
<div
|
||||||
|
class="flex-column gap"
|
||||||
|
children:append={[
|
||||||
|
chatMessageViewModel.allReactions,
|
||||||
|
MessageReactionEntry,
|
||||||
|
]}
|
||||||
|
></div>
|
||||||
|
</div>
|
||||||
</main>
|
</main>
|
||||||
<button on:click={chatMessageViewModel.hideInfoModal}>
|
<button on:click={chatMessageViewModel.hideInfoModal}>
|
||||||
{coreViewModel.translations.general.closeButton}
|
{coreViewModel.translations.general.closeButton}
|
||||||
|
|||||||
@@ -3,7 +3,6 @@ import * as React from "bloatless-react";
|
|||||||
import {
|
import {
|
||||||
ChatMessage,
|
ChatMessage,
|
||||||
ChatMessageReaction,
|
ChatMessageReaction,
|
||||||
ChatMessageReactionReference,
|
|
||||||
ChatMessageStatuses,
|
ChatMessageStatuses,
|
||||||
ReactionSymbols,
|
ReactionSymbols,
|
||||||
} from "../../Model/Chat/chatModel";
|
} from "../../Model/Chat/chatModel";
|
||||||
@@ -23,36 +22,44 @@ export default class ChatMessageViewModel {
|
|||||||
);
|
);
|
||||||
sentByUser: boolean;
|
sentByUser: boolean;
|
||||||
|
|
||||||
reactionsThumbsUp = new React.MapState<ChatMessageReaction>();
|
allReactions = new React.MapState<ChatMessageReaction>();
|
||||||
reactionsCheck = new React.MapState<ChatMessageReaction>();
|
userReaction = new React.State<ReactionSymbols | string | undefined>(undefined);
|
||||||
reactionsStop = new React.MapState<ChatMessageReaction>();
|
reactionsThumbsUp = React.MapState<ChatMessageReaction>;
|
||||||
reactionsAttention = new React.MapState<ChatMessageReaction>();
|
reactionsCheck = React.MapState<ChatMessageReaction>;
|
||||||
reactionsDoubleAttention = new React.MapState<ChatMessageReaction>();
|
reactionsStop = React.MapState<ChatMessageReaction>;
|
||||||
reactionsQuestion = new React.MapState<ChatMessageReaction>();
|
reactionsAttention = React.MapState<ChatMessageReaction>;
|
||||||
|
reactionsDoubleAttention = React.MapState<ChatMessageReaction>;
|
||||||
|
reactionsQuestion = React.MapState<ChatMessageReaction>;
|
||||||
|
|
||||||
reactionsThumbsUpCount = React.createProxyState(
|
generateReactionCountProxyState = (
|
||||||
[this.reactionsThumbsUp],
|
content: ReactionSymbols,
|
||||||
() => this.reactionsThumbsUp.value.size,
|
): React.State<number> => {
|
||||||
|
return React.createProxyState(
|
||||||
|
[this.allReactions],
|
||||||
|
() =>
|
||||||
|
[...this.allReactions.value.values()].filter(
|
||||||
|
(x) => x.content == content,
|
||||||
|
).length,
|
||||||
);
|
);
|
||||||
reactionsCheckCount = React.createProxyState(
|
};
|
||||||
[this.reactionsCheck],
|
|
||||||
() => this.reactionsCheck.value.size,
|
reactionsThumbsUpCount = this.generateReactionCountProxyState(
|
||||||
|
ReactionSymbols.ThumbsUp,
|
||||||
);
|
);
|
||||||
reactionsStopCount = React.createProxyState(
|
reactionsCheckCount = this.generateReactionCountProxyState(
|
||||||
[this.reactionsStop],
|
ReactionSymbols.Check,
|
||||||
() => this.reactionsStop.value.size,
|
|
||||||
);
|
);
|
||||||
reactionsAttentionCount = React.createProxyState(
|
reactionsStopCount = this.generateReactionCountProxyState(
|
||||||
[this.reactionsAttention],
|
ReactionSymbols.Stop,
|
||||||
() => this.reactionsAttention.value.size,
|
|
||||||
);
|
);
|
||||||
reactionsDoubleAttentionCount = React.createProxyState(
|
reactionsAttentionCount = this.generateReactionCountProxyState(
|
||||||
[this.reactionsDoubleAttention],
|
ReactionSymbols.Attention,
|
||||||
() => this.reactionsDoubleAttention.value.size,
|
|
||||||
);
|
);
|
||||||
reactionsQuestionCount = React.createProxyState(
|
reactionsDoubleAttentionCount = this.generateReactionCountProxyState(
|
||||||
[this.reactionsQuestion],
|
ReactionSymbols.DoubleAttention,
|
||||||
() => this.reactionsQuestion.value.size,
|
);
|
||||||
|
reactionsQuestionCount = this.generateReactionCountProxyState(
|
||||||
|
ReactionSymbols.Question,
|
||||||
);
|
);
|
||||||
|
|
||||||
// state
|
// state
|
||||||
@@ -80,28 +87,14 @@ export default class ChatMessageViewModel {
|
|||||||
|
|
||||||
// reactions
|
// reactions
|
||||||
handleReaction = (reaction: ChatMessageReaction): void => {
|
handleReaction = (reaction: ChatMessageReaction): void => {
|
||||||
function setReaction(mapState: React.MapState<any>) {
|
|
||||||
if (reaction.isDeleting) {
|
if (reaction.isDeleting) {
|
||||||
mapState.remove(reaction.sender);
|
this.allReactions.remove(reaction.sender);
|
||||||
} else {
|
} else {
|
||||||
mapState.set(reaction.sender, reaction);
|
this.allReactions.set(reaction.sender, reaction);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
switch (reaction.content) {
|
if (reaction.sender != this.coreViewModel.settingsModel.username) return;
|
||||||
case ReactionSymbols.ThumbsUp:
|
this.userReaction.value = reaction.isDeleting ? undefined : reaction.content;
|
||||||
return setReaction(this.reactionsThumbsUp);
|
|
||||||
case ReactionSymbols.Check:
|
|
||||||
return setReaction(this.reactionsCheck);
|
|
||||||
case ReactionSymbols.Stop:
|
|
||||||
return setReaction(this.reactionsStop);
|
|
||||||
case ReactionSymbols.Attention:
|
|
||||||
return setReaction(this.reactionsAttention);
|
|
||||||
case ReactionSymbols.DoubleAttention:
|
|
||||||
return setReaction(this.reactionsDoubleAttention);
|
|
||||||
case ReactionSymbols.Question:
|
|
||||||
return setReaction(this.reactionsQuestion);
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
sendReaction = (content: ReactionSymbols, isDeleting: boolean): void => {
|
sendReaction = (content: ReactionSymbols, isDeleting: boolean): void => {
|
||||||
|
|||||||
Reference in New Issue
Block a user