mirror of
https://github.com/hcengineering/platform.git
synced 2024-12-23 03:22:19 +03:00
UBER-1249 Make document Todos work with Heap (#4886)
This commit is contained in:
parent
4a85b0ad13
commit
e003fb29fb
@ -89,7 +89,9 @@ class SvelteNodeView extends NodeView<SvelteNodeViewComponent, Editor, SvelteNod
|
||||
})
|
||||
|
||||
this.renderer = new SvelteRenderer(this.component, { element: target, props, context })
|
||||
|
||||
this.editor.on('update', this.handleEditorUpdate.bind(this))
|
||||
this.editor.on('selectionUpdate', this.handleSelectionUpdate.bind(this))
|
||||
}
|
||||
|
||||
override get dom (): HTMLElement {
|
||||
@ -131,10 +133,12 @@ class SvelteNodeView extends NodeView<SvelteNodeViewComponent, Editor, SvelteNod
|
||||
|
||||
selectNode (): void {
|
||||
this.renderer.updateProps({ selected: true })
|
||||
this.renderer.element.classList.add('ProseMirror-selectednode')
|
||||
}
|
||||
|
||||
deselectNode (): void {
|
||||
this.renderer.updateProps({ selected: false })
|
||||
this.renderer.element.classList.remove('ProseMirror-selectednode')
|
||||
}
|
||||
|
||||
handleEditorUpdate (): void {
|
||||
@ -144,10 +148,29 @@ class SvelteNodeView extends NodeView<SvelteNodeViewComponent, Editor, SvelteNod
|
||||
}
|
||||
}
|
||||
|
||||
handleSelectionUpdate (): void {
|
||||
const { from, to } = this.editor.state.selection
|
||||
|
||||
if (from <= this.getPos() && to >= this.getPos() + this.node.nodeSize) {
|
||||
if (this.renderer.props.selected === true) {
|
||||
return
|
||||
}
|
||||
|
||||
this.selectNode()
|
||||
} else {
|
||||
if (this.renderer.props.selected !== true) {
|
||||
return
|
||||
}
|
||||
|
||||
this.deselectNode()
|
||||
}
|
||||
}
|
||||
|
||||
destroy (): void {
|
||||
this.renderer.destroy()
|
||||
this.contentDOMElement = null
|
||||
this.editor.off('update', this.handleEditorUpdate.bind(this))
|
||||
this.editor.off('selectionUpdate', this.handleSelectionUpdate.bind(this))
|
||||
this.contentDOMElement = null
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -20,17 +20,19 @@ export type SvelteRendererComponent = typeof SvelteComponent | ComponentType
|
||||
|
||||
export interface SvelteRendererOptions {
|
||||
element: HTMLElement
|
||||
props?: any
|
||||
props?: Record<string, any>
|
||||
context?: any
|
||||
}
|
||||
|
||||
export class SvelteRenderer {
|
||||
private readonly component: SvelteComponent
|
||||
element: HTMLElement
|
||||
props: Record<string, any>
|
||||
|
||||
constructor (component: SvelteRendererComponent, { element, props, context }: SvelteRendererOptions) {
|
||||
this.element = element
|
||||
this.element.classList.add('svelte-renderer')
|
||||
this.props = props ?? {}
|
||||
|
||||
const options = { target: element, props, context }
|
||||
const Component = component
|
||||
|
@ -29,7 +29,8 @@
|
||||
} from '@hcengineering/text-editor'
|
||||
import { createEventDispatcher } from 'svelte'
|
||||
|
||||
import ToDoNodeView from './node-view/ToDoNodeView.svelte'
|
||||
import ToDoItemNodeView from './node-view/ToDoItemNodeView.svelte'
|
||||
import ToDoListNodeView from './node-view/ToDoListNodeView.svelte'
|
||||
|
||||
export let object: Document
|
||||
export let readonly = false
|
||||
@ -55,14 +56,23 @@
|
||||
}),
|
||||
TodoItemExtension.extend({
|
||||
addNodeView () {
|
||||
return SvelteNodeViewRenderer(ToDoNodeView, { contentAs: 'li', componentProps: { object } })
|
||||
return SvelteNodeViewRenderer(ToDoItemNodeView, {
|
||||
contentAs: 'li',
|
||||
contentClass: 'todo-item',
|
||||
componentProps: { object },
|
||||
ignoreMutation: () => true
|
||||
})
|
||||
}
|
||||
}).configure({
|
||||
HTMLAttributes: {
|
||||
class: 'todo-item'
|
||||
}
|
||||
}),
|
||||
TodoListExtension.configure({
|
||||
TodoListExtension.extend({
|
||||
addNodeView () {
|
||||
return SvelteNodeViewRenderer(ToDoListNodeView, { ignoreMutation: () => true })
|
||||
}
|
||||
}).configure({
|
||||
HTMLAttributes: {
|
||||
class: 'todo-list'
|
||||
}
|
||||
|
@ -18,6 +18,11 @@
|
||||
const client = getClient()
|
||||
const query = createQuery()
|
||||
|
||||
$: todoId = node.attrs.todoid as Ref<ToDo>
|
||||
$: userId = node.attrs.userid as Ref<Person>
|
||||
$: checked = node.attrs.checked ?? false
|
||||
$: readonly = !editor.isEditable || object === undefined
|
||||
|
||||
let todo: ToDo | undefined = undefined
|
||||
$: query.query(
|
||||
time.class.ToDo,
|
||||
@ -26,15 +31,10 @@
|
||||
},
|
||||
(res) => {
|
||||
;[todo] = res
|
||||
syncTodo(todo)
|
||||
void syncTodo(todo)
|
||||
}
|
||||
)
|
||||
|
||||
$: todoId = node.attrs.todoid as Ref<ToDo>
|
||||
$: userId = node.attrs.userid as Ref<Person>
|
||||
$: checked = node.attrs.checked ?? false
|
||||
$: readonly = !editor.isEditable || object === undefined
|
||||
|
||||
async function syncTodo (todo: ToDo | undefined): Promise<void> {
|
||||
if (todo !== undefined) {
|
||||
const todoChecked = todo.doneOn != null
|
||||
@ -59,7 +59,7 @@
|
||||
if (todo !== undefined) {
|
||||
await client.update(todo, { doneOn: todo.doneOn == null ? Date.now() : null })
|
||||
} else {
|
||||
updateAttributes({ checked: !node.attrs.checked })
|
||||
updateAttributes({ checked: node.attrs.checked !== true })
|
||||
}
|
||||
}
|
||||
|
||||
@ -72,7 +72,7 @@
|
||||
const ops = client.apply('todo')
|
||||
|
||||
if (todo !== undefined) {
|
||||
await ops.removeDoc(todo._class, todo.space, todo._id)
|
||||
await ops.remove(todo)
|
||||
}
|
||||
|
||||
const id = await ops.addCollection(time.class.ProjectToDo, time.space.ToDos, object._id, object._class, 'todos', {
|
||||
@ -101,7 +101,7 @@
|
||||
})
|
||||
|
||||
if (todo !== undefined) {
|
||||
await client.removeDoc(todo._class, todo.space, todo._id)
|
||||
await client.remove(todo)
|
||||
}
|
||||
}
|
||||
|
||||
@ -164,12 +164,13 @@
|
||||
await changeAssignee(result?._id)
|
||||
}
|
||||
hovered = false
|
||||
editor.commands.focus()
|
||||
}
|
||||
)
|
||||
}
|
||||
</script>
|
||||
|
||||
<NodeViewWrapper data-drag-handle="">
|
||||
<NodeViewWrapper data-drag-handle="" data-type="todoItem">
|
||||
<div
|
||||
class="todo-item flex-row-top flex-gap-3"
|
||||
class:empty={node.textContent.length === 0}
|
||||
@ -197,6 +198,10 @@
|
||||
|
||||
<style lang="scss">
|
||||
.todo-item {
|
||||
.assignee {
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
&.unassigned {
|
||||
.assignee {
|
||||
opacity: 0;
|
@ -0,0 +1,7 @@
|
||||
<script lang="ts">
|
||||
import { NodeViewContent, NodeViewWrapper } from '@hcengineering/text-editor'
|
||||
</script>
|
||||
|
||||
<NodeViewWrapper data-drag-handle="">
|
||||
<NodeViewContent as="ul" class="todo-list" data-type="todoList" />
|
||||
</NodeViewWrapper>
|
Loading…
Reference in New Issue
Block a user