Chunter: Copy link to message (#2078)

Signed-off-by: Denis Bunakalya <denis.bunakalya@xored.com>
This commit is contained in:
Denis Bunakalya 2022-06-17 10:20:43 +03:00 committed by GitHub
parent e0853ecf99
commit 9d772b786f
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 108 additions and 12 deletions

View File

@ -16,13 +16,16 @@ let currentLocation: string | undefined
location.subscribe((loc) => {
if (loc.fragment !== currentLocation && loc.fragment !== undefined && loc.fragment.trim().length > 0) {
const props = decodeURIComponent(loc.fragment).split('|')
showPanel(
props[0] as AnyComponent,
props[1],
props[2],
(props[3] ?? undefined) as PopupAlignment,
(props[4] ?? undefined) as AnyComponent
)
if (props.length >= 3) {
showPanel(
props[0] as AnyComponent,
props[1],
props[2],
(props[3] ?? undefined) as PopupAlignment,
(props[4] ?? undefined) as AnyComponent
)
}
} else if (
(loc.fragment === undefined || (loc.fragment !== undefined && loc.fragment.trim().length === 0)) &&
currentLocation !== undefined

View File

@ -65,6 +65,7 @@
"ThreadMessage": "Thread message",
"ChunterBrowser": "Search",
"Messages": "Messages",
"NoResults": "No results"
"NoResults": "No results",
"CopyLink": "Copy link"
}
}

View File

@ -64,6 +64,7 @@
"ThreadMessage": "Сообщение в обсуждении",
"ChunterBrowser": "Поиск",
"Messages": "Сообщения",
"NoResults": "Нет результатов"
"NoResults": "Нет результатов",
"CopyLink": "Копировать ссылку"
}
}

View File

@ -19,6 +19,7 @@
import core, { Doc, Ref, Space, Timestamp, WithLookup } from '@anticrm/core'
import { NotificationClientImpl } from '@anticrm/notification-resources'
import { createQuery } from '@anticrm/presentation'
import { getCurrentLocation, navigate } from '@anticrm/ui'
import { afterUpdate, beforeUpdate } from 'svelte'
import chunter from '../plugin'
import { getDay } from '../utils'
@ -34,12 +35,27 @@
let div: HTMLDivElement | undefined
let autoscroll: boolean = false
let messageIdForScroll = ''
let isMessageHighlighted = false
beforeUpdate(() => {
autoscroll = div !== undefined && div.offsetHeight + div.scrollTop > div.scrollHeight - 20
})
afterUpdate(() => {
if (messageIdForScroll && !isMessageHighlighted) {
const messageElement = document.getElementById(messageIdForScroll)
messageElement?.scrollIntoView()
isMessageHighlighted = true
setTimeout(() => {
messageIdForScroll = ''
isMessageHighlighted = false
}, 2000)
return
}
if (div && (autoscroll || isScrollForced)) {
div.scrollTo(0, div.scrollHeight)
isScrollForced = false
@ -85,6 +101,15 @@
messages = res
newMessagesPos = newMessagesStart(messages)
notificationClient.updateLastView(space, chunter.class.ChunterSpace)
const location = getCurrentLocation()
const messageId = location.fragment
if (messageId && location.path.length === 3) {
messageIdForScroll = messageId
location.fragment = undefined
navigate(location)
}
},
{
lookup: {
@ -205,6 +230,7 @@
<JumpToDateSelector selectedDate={message.createOn} on:jumpToDate={handleJumpToDate} />
{/if}
<MessageComponent
isHighlighted={messageIdForScroll === message._id && isMessageHighlighted}
{message}
{employees}
on:openThread

View File

@ -22,7 +22,17 @@
import { NotificationClientImpl } from '@anticrm/notification-resources'
import { getResource } from '@anticrm/platform'
import { Avatar, getClient, MessageViewer } from '@anticrm/presentation'
import ui, { ActionIcon, IconMoreH, Menu, showPopup, Label, Tooltip, Button } from '@anticrm/ui'
import ui, {
ActionIcon,
IconMoreH,
Menu,
showPopup,
Label,
Tooltip,
Button,
getCurrentLocation,
locationToUrl
} from '@anticrm/ui'
import { Action } from '@anticrm/view'
import { getActions, LinkPresenter } from '@anticrm/view-resources'
import { createEventDispatcher } from 'svelte'
@ -42,6 +52,7 @@
export let thread: boolean = false
export let isPinned: boolean = false
export let isSaved: boolean = false
export let isHighlighted = false
let refInput: AttachmentRefInput
@ -95,6 +106,24 @@
}
}
const copyLinkAction = {
label: chunter.string.CopyLink,
action: async () => {
const location = getCurrentLocation()
location.fragment = message._id
location.path[2] = message.space
if (message.attachedToClass === chunter.class.Message) {
location.path.length = 4
location.path[3] = message.attachedTo
} else {
location.path.length = 3
}
await navigator.clipboard.writeText(`${window.location.origin}${locationToUrl(location)}`)
}
}
let menuShowed = false
const showMenu = async (ev: Event): Promise<void> => {
@ -115,6 +144,7 @@
await impl(message, evt)
}
})),
copyLinkAction,
...(getCurrentAccount()._id === message.createBy ? [editAction, deleteAction] : [])
]
},
@ -176,7 +206,7 @@
}
</script>
<div class="container">
<div class="container" class:highlighted={isHighlighted} id={message._id}>
<div class="avatar"><Avatar size={'medium'} avatar={employee?.avatar} /></div>
<div class="message">
<div class="header">
@ -253,11 +283,20 @@
</div>
<style lang="scss">
@keyframes highlight {
50% {
background-color: var(--warning-color);
}
}
.container {
position: relative;
display: flex;
padding: 0.5rem 2rem;
&.highlighted {
animation: highlight 2000ms ease-in-out;
}
.avatar {
min-width: 2.25rem;
}

View File

@ -40,12 +40,27 @@
let div: HTMLDivElement | undefined
let autoscroll: boolean = false
let isScrollForced = false
let messageIdForScroll = ''
let isMessageHighlighted = false
beforeUpdate(() => {
autoscroll = div !== undefined && div.offsetHeight + div.scrollTop > div.scrollHeight - 20
})
afterUpdate(() => {
if (messageIdForScroll && !isMessageHighlighted) {
const messageElement = document.getElementById(messageIdForScroll)
messageElement?.scrollIntoView()
isMessageHighlighted = true
setTimeout(() => {
messageIdForScroll = ''
isMessageHighlighted = false
}, 2000)
return
}
if (div && (autoscroll || isScrollForced)) {
div.scrollTo(0, div.scrollHeight)
isScrollForced = false
@ -97,6 +112,15 @@
comments = res
newMessagesPos = newMessagesStart(comments, $lastViews)
notificationClient.updateLastView(id, chunter.class.Message)
const location = getCurrentLocation()
const messageId = location.fragment
if (messageId && location.path.length === 4) {
messageIdForScroll = messageId
location.fragment = undefined
navigate(location)
}
},
{
lookup
@ -211,6 +235,7 @@
<ChannelSeparator title={chunter.string.New} line reverse isNew />
{/if}
<MsgView
isHighlighted={messageIdForScroll === comment._id && isMessageHighlighted}
message={comment}
{employees}
thread

View File

@ -85,6 +85,7 @@ export default mergeIds(chunterId, chunter, {
MessagesBrowser: '' as IntlString,
ChunterBrowser: '' as IntlString,
Messages: '' as IntlString,
NoResults: '' as IntlString
NoResults: '' as IntlString,
CopyLink: '' as IntlString
}
})