compact mode for messages
This commit is contained in:
parent
686e6a4911
commit
c3374a612e
1
front/src/assets/svg/contract-up-down-line.svg
Normal file
1
front/src/assets/svg/contract-up-down-line.svg
Normal file
@ -0,0 +1 @@
|
|||||||
|
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M5.79297 5.20718L12.0001 11.4143L18.2072 5.20718L16.793 3.79297L12.0001 8.58586L7.20718 3.79297L5.79297 5.20718Z M18.2073 18.7928L12.0002 12.5857L5.79312 18.7928L7.20733 20.207L12.0002 15.4141L16.7931 20.207L18.2073 18.7928Z"></path></svg>
|
After Width: | Height: | Size: 308 B |
1
front/src/assets/svg/expand-up-down-line.svg
Normal file
1
front/src/assets/svg/expand-up-down-line.svg
Normal file
@ -0,0 +1 @@
|
|||||||
|
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M18.2073 9.04304L12.0002 2.83594L5.79312 9.04304L7.20733 10.4573L12.0002 5.66436L16.7931 10.4573L18.2073 9.04304Z M5.79297 14.9574L12.0001 21.1646L18.2072 14.9574L16.793 13.5432L12.0001 18.3361L7.20718 13.5432L5.79297 14.9574Z"></path></svg>
|
After Width: | Height: | Size: 310 B |
@ -1,17 +1,25 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { defineProps, PropType } from "vue";
|
import { defineProps, withDefaults, ref } from "vue";
|
||||||
import { decodeEmojis } from "../../../utils/string";
|
import { decodeEmojis } from "../../../utils/string";
|
||||||
import { removeDuplicates } from "../../../utils/array";
|
import { removeDuplicates } from "../../../utils/array";
|
||||||
import { Address, Message } from "@/store/models/model";
|
import { Address, Message } from "@/store/models/model";
|
||||||
import Content from "./Content.vue";
|
import Content from "./Content.vue";
|
||||||
import Options from "./Options.vue";
|
import Options from "./Options.vue";
|
||||||
import { isSeenFc } from "@/utils/flagsUtils";
|
import { isSeenFc } from "@/utils/flagsUtils";
|
||||||
|
import SvgLoader from "@/components/utils/SvgLoader.vue";
|
||||||
|
|
||||||
const props = defineProps({
|
export interface Props {
|
||||||
msg: Object as PropType<Message>,
|
msg: Message;
|
||||||
members: Array as PropType<Address[]>,
|
members: Address[];
|
||||||
|
compact: boolean;
|
||||||
|
}
|
||||||
|
|
||||||
|
const props = withDefaults(defineProps<Props>(), {
|
||||||
|
compact: () => true,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const compact = ref(props.compact);
|
||||||
|
|
||||||
const displayAddresses = (addressIds: string[] | undefined): string => {
|
const displayAddresses = (addressIds: string[] | undefined): string => {
|
||||||
if (!addressIds) return "";
|
if (!addressIds) return "";
|
||||||
addressIds = removeDuplicates(addressIds);
|
addressIds = removeDuplicates(addressIds);
|
||||||
@ -63,7 +71,14 @@ const classes = (): string => {
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="content" :class="[classes()]">
|
<div class="content" :class="[classes()]">
|
||||||
<Content :content="props.msg?.content" />
|
<Content v-if="!compact" :content="props.msg?.content" />
|
||||||
|
<SvgLoader
|
||||||
|
v-if="compact"
|
||||||
|
classes="selectable"
|
||||||
|
class="expand-contract"
|
||||||
|
svg="expand-up-down-line"
|
||||||
|
@click="compact = false"
|
||||||
|
/>
|
||||||
<Options class="options" :msg="props.msg" />
|
<Options class="options" :msg="props.msg" />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -101,6 +116,10 @@ const classes = (): string => {
|
|||||||
flex-direction: row;
|
flex-direction: row;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.expand-contract {
|
||||||
|
margin: 0 50px;
|
||||||
|
}
|
||||||
|
|
||||||
.msg-important {
|
.msg-important {
|
||||||
background-color: #ec7a4342;
|
background-color: #ec7a4342;
|
||||||
}
|
}
|
||||||
|
@ -84,14 +84,14 @@ const deleteRemoteOnly = () => {
|
|||||||
<SvgLoader
|
<SvgLoader
|
||||||
v-if="isSeenFc(props.msg?.flags)"
|
v-if="isSeenFc(props.msg?.flags)"
|
||||||
svg="mail-check-line"
|
svg="mail-check-line"
|
||||||
class="option"
|
classes="selectable"
|
||||||
v-tooltip="'Mark unread'"
|
v-tooltip="'Mark unread'"
|
||||||
:loading="seenLoading"
|
:loading="seenLoading"
|
||||||
/>
|
/>
|
||||||
<SvgLoader
|
<SvgLoader
|
||||||
v-if="!isSeenFc(props.msg?.flags)"
|
v-if="!isSeenFc(props.msg?.flags)"
|
||||||
svg="mail-unread-line"
|
svg="mail-unread-line"
|
||||||
class="option"
|
classes="selectable"
|
||||||
v-tooltip="'Mark as read'"
|
v-tooltip="'Mark as read'"
|
||||||
:loading="seenLoading"
|
:loading="seenLoading"
|
||||||
/>
|
/>
|
||||||
@ -99,38 +99,33 @@ const deleteRemoteOnly = () => {
|
|||||||
<span @click="setFlaggedFlag()">
|
<span @click="setFlaggedFlag()">
|
||||||
<SvgLoader
|
<SvgLoader
|
||||||
svg="flag-line"
|
svg="flag-line"
|
||||||
class="option"
|
|
||||||
:loading="flaggedLoading"
|
:loading="flaggedLoading"
|
||||||
:classes="hasFlag(props.msg?.flags, '\\Flagged') ? 'warn' : ''"
|
:classes="(hasFlag(props.msg?.flags, '\\Flagged') ? 'warn' : '') + ',selectable'"
|
||||||
v-tooltip="hasFlag(props.msg?.flags, '\\Flagged') ? 'Unflag' : 'Flag'"
|
v-tooltip="hasFlag(props.msg?.flags, '\\Flagged') ? 'Unflag' : 'Flag'"
|
||||||
/>
|
/>
|
||||||
</span>
|
</span>
|
||||||
<SvgLoader svg="reply-line" class="option" />
|
<SvgLoader svg="reply-line" classes="selectable" />
|
||||||
<span @click="deleteRemoteOnly()">
|
<span @click="deleteRemoteOnly()">
|
||||||
<SvgLoader
|
<SvgLoader
|
||||||
svg="delete-bin-4-line"
|
svg="delete-bin-4-line"
|
||||||
class="option"
|
|
||||||
:loading="deletionLoading"
|
:loading="deletionLoading"
|
||||||
classes="danger"
|
classes="danger,selectable"
|
||||||
v-tooltip="'Delete from remote'"
|
v-tooltip="'Delete from remote'"
|
||||||
/>
|
/>
|
||||||
</span>
|
</span>
|
||||||
<span @click="deleteEverywhere()">
|
<span @click="deleteEverywhere()">
|
||||||
<SvgLoader
|
<SvgLoader
|
||||||
svg="delete-bin-6-line"
|
svg="delete-bin-6-line"
|
||||||
class="option"
|
|
||||||
:loading="deletionLoading"
|
:loading="deletionLoading"
|
||||||
classes="danger"
|
classes="danger,selectable"
|
||||||
v-tooltip="'Delete everywhere'"
|
v-tooltip="'Delete everywhere'"
|
||||||
/>
|
/>
|
||||||
</span>
|
</span>
|
||||||
<SvgLoader svg="share-forward-line" class="option" />
|
<SvgLoader svg="share-forward-line" classes="selectable" />
|
||||||
<SvgLoader svg="reply-all-line" class="option" />
|
<SvgLoader svg="reply-all-line" classes="selectable" />
|
||||||
|
<div>{{ props.msg?.flags }}</div>
|
||||||
</div>
|
</div>
|
||||||
<div>reply</div>
|
<!-- <div>see source</div> -->
|
||||||
<div>transfer</div>
|
|
||||||
<div>see source</div>
|
|
||||||
<div>{{ props.msg?.flags }}</div>
|
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
@ -143,6 +138,7 @@ const deleteRemoteOnly = () => {
|
|||||||
display: flex;
|
display: flex;
|
||||||
flex-wrap: wrap;
|
flex-wrap: wrap;
|
||||||
justify-content: center;
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
.button {
|
.button {
|
||||||
@ -156,14 +152,4 @@ const deleteRemoteOnly = () => {
|
|||||||
background-color: var(--selected);
|
background-color: var(--selected);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.option {
|
|
||||||
border-radius: 6px;
|
|
||||||
cursor: pointer;
|
|
||||||
|
|
||||||
&:hover,
|
|
||||||
&.is-active {
|
|
||||||
background-color: var(--selected);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</style>
|
</style>
|
||||||
|
@ -5,23 +5,34 @@ const props = defineProps({
|
|||||||
svg: { type: String, required: true },
|
svg: { type: String, required: true },
|
||||||
isDisabled: Boolean,
|
isDisabled: Boolean,
|
||||||
classes: String,
|
classes: String,
|
||||||
loading: { type: Boolean, default: false },
|
loading: { type: Boolean },
|
||||||
});
|
});
|
||||||
|
|
||||||
console.log(props.loading);
|
|
||||||
const pathSvg = () => require(`@/assets/svg/${props.svg}.svg`);
|
const pathSvg = () => require(`@/assets/svg/${props.svg}.svg`);
|
||||||
|
const classes = () => props.classes?.split(",") ?? "";
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
<div class="mainSvg">
|
<div class="mainSvg" :class="classes()">
|
||||||
<div class="lds-dual-ring" v-if="loading"></div>
|
<div class="lds-dual-ring" v-if="loading"></div>
|
||||||
<img v-if="!loading" :disabled="props.isDisabled" :src="pathSvg()" :class="props.classes" />
|
<img v-if="!loading" :disabled="props.isDisabled" :src="pathSvg()" :class="classes()" />
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<style lang="scss" scoped>
|
<style lang="scss" scoped>
|
||||||
.mainSvg {
|
.mainSvg {
|
||||||
display: inherit;
|
display: inherit;
|
||||||
|
min-width: 26px;
|
||||||
|
min-height: 26px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.mainSvg.selectable {
|
||||||
|
border-radius: 6px;
|
||||||
|
cursor: pointer;
|
||||||
|
&:hover,
|
||||||
|
&.is-active {
|
||||||
|
background-color: var(--selected);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
img {
|
img {
|
||||||
|
@ -12,12 +12,14 @@ const store = useStore();
|
|||||||
const route = useRoute();
|
const route = useRoute();
|
||||||
const messageIdView = ref(-1);
|
const messageIdView = ref(-1);
|
||||||
const message = ref(undefined);
|
const message = ref(undefined);
|
||||||
|
const messages = ref([]);
|
||||||
const id = ref(parseInt(route.params.id));
|
const id = ref(parseInt(route.params.id));
|
||||||
let room = ref();
|
let room = ref();
|
||||||
|
|
||||||
onBeforeMount(async () => {
|
onBeforeMount(async () => {
|
||||||
store.commit("setActiveRoom", id.value);
|
store.commit("setActiveRoom", id.value);
|
||||||
room.value = store.getters.room(id.value);
|
room.value = store.getters.room(id.value);
|
||||||
|
messages.value = store.getters.messages(room.value?.id);
|
||||||
console.log(room.value);
|
console.log(room.value);
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -26,6 +28,8 @@ onBeforeRouteUpdate(async (to, from) => {
|
|||||||
id.value = parseInt(to.params.id);
|
id.value = parseInt(to.params.id);
|
||||||
store.commit("setActiveRoom", id.value);
|
store.commit("setActiveRoom", id.value);
|
||||||
room.value = await store.getters.room(id.value);
|
room.value = await store.getters.room(id.value);
|
||||||
|
messages.value = store.getters.messages(room.value?.id);
|
||||||
|
|
||||||
console.log(room.value);
|
console.log(room.value);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@ -45,6 +49,12 @@ function openMessageView(messageId) {
|
|||||||
message.value = store.getters.message(room.value.id, messageId);
|
message.value = store.getters.message(room.value.id, messageId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const shouldBeCompact = (index) => {
|
||||||
|
// show last three messages
|
||||||
|
if (messages.value?.length - 4 < index) return false;
|
||||||
|
return true;
|
||||||
|
};
|
||||||
|
|
||||||
provide("room", room);
|
provide("room", room);
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
@ -53,10 +63,11 @@ provide("room", room);
|
|||||||
<Header :id="id" :room="room"></Header>
|
<Header :id="id" :room="room"></Header>
|
||||||
<div class="messages">
|
<div class="messages">
|
||||||
<Message
|
<Message
|
||||||
v-for="(message, index) in store.getters.messages(room?.id)"
|
v-for="(message, index) in messages"
|
||||||
:key="index"
|
:key="index"
|
||||||
:msg="message"
|
:msg="message"
|
||||||
:members="room?.members"
|
:members="room?.members"
|
||||||
|
:compact="shouldBeCompact(index)"
|
||||||
@open-message-view="(id) => openMessageView(id)"
|
@open-message-view="(id) => openMessageView(id)"
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
Loading…
Reference in New Issue
Block a user