Modify request popup (#2676)

Signed-off-by: Denis Maslennikov <denis.maslennikov@gmail.com>
This commit is contained in:
Denis Maslennikov 2023-02-22 12:42:14 +07:00 committed by GitHub
parent 4a5532af10
commit 0dcd81bf5b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 59 additions and 14 deletions

View File

@ -31,11 +31,12 @@ import {
TypeString, TypeString,
UX UX
} from '@hcengineering/model' } from '@hcengineering/model'
import core, { TAttachedDoc } from '@hcengineering/model-core' import core, { TAttachedDoc, TClass } from '@hcengineering/model-core'
import { Request, RequestDecisionComment, RequestStatus } from '@hcengineering/request' import { Request, RequestDecisionComment, RequestStatus, RequestPresenter } from '@hcengineering/request'
import request from './plugin' import request from './plugin'
import view from '@hcengineering/model-view' import view from '@hcengineering/model-view'
import { TComment } from '@hcengineering/model-chunter' import { TComment } from '@hcengineering/model-chunter'
import { AnyComponent } from '@hcengineering/ui'
export const DOMAIN_REQUEST = 'request' as Domain export const DOMAIN_REQUEST = 'request' as Domain
@ -69,8 +70,13 @@ export class TRequest extends TAttachedDoc implements Request {
@Mixin(request.mixin.RequestDecisionComment, chunter.class.Comment) @Mixin(request.mixin.RequestDecisionComment, chunter.class.Comment)
export class TRequestDecisionComment extends TComment implements RequestDecisionComment {} export class TRequestDecisionComment extends TComment implements RequestDecisionComment {}
@Mixin(request.mixin.RequestPresenter, core.class.Class)
export class TRequestPresenter extends TClass implements RequestPresenter {
presenter!: AnyComponent
}
export function createModel (builder: Builder): void { export function createModel (builder: Builder): void {
builder.createModel(TRequest, TRequestDecisionComment) builder.createModel(TRequest, TRequestDecisionComment, TRequestPresenter)
builder.mixin(request.class.Request, core.class.Class, view.mixin.ObjectEditor, { builder.mixin(request.class.Request, core.class.Class, view.mixin.ObjectEditor, {
editor: request.component.EditRequest editor: request.component.EditRequest
@ -80,6 +86,10 @@ export function createModel (builder: Builder): void {
presenter: request.component.RequestPresenter presenter: request.component.RequestPresenter
}) })
builder.mixin(request.class.Request, core.class.Class, request.mixin.RequestPresenter, {
presenter: request.component.RequestView
})
builder.createDoc( builder.createDoc(
activity.class.TxViewlet, activity.class.TxViewlet,
core.space.Model, core.space.Model,

View File

@ -27,8 +27,7 @@ export default mergeIds(requestId, request, {
RequestLabel: '' as AnyComponent RequestLabel: '' as AnyComponent
}, },
component: { component: {
EditRequest: '' as AnyComponent, EditRequest: '' as AnyComponent
RequestPresenter: '' as AnyComponent
}, },
ids: { ids: {
TxRequestCreate: '' as Ref<TxViewlet> TxRequestCreate: '' as Ref<TxViewlet>

View File

@ -14,12 +14,11 @@
--> -->
<script lang="ts"> <script lang="ts">
import { EmployeeAccount } from '@hcengineering/contact' import { EmployeeAccount } from '@hcengineering/contact'
import { getCurrentAccount, Ref } from '@hcengineering/core' import { Class, getCurrentAccount, Ref } from '@hcengineering/core'
import { createQuery } from '@hcengineering/presentation' import { createQuery, getClient } from '@hcengineering/presentation'
import { Request, RequestStatus } from '@hcengineering/request' import { Request, RequestStatus } from '@hcengineering/request'
import { Label, Scroller, deviceOptionsStore as deviceInfo } from '@hcengineering/ui' import { Label, Scroller, deviceOptionsStore as deviceInfo, AnyComponent, Component } from '@hcengineering/ui'
import request from '../plugin' import request from '../plugin'
import RequestView from './RequestView.svelte'
let requests: Request[] = [] let requests: Request[] = []
const me = getCurrentAccount()._id as Ref<EmployeeAccount> const me = getCurrentAccount()._id as Ref<EmployeeAccount>
@ -35,6 +34,31 @@
(p) => p.requested.filter((a) => a === me).length > p.approved.filter((a) => a === me).length (p) => p.requested.filter((a) => a === me).length > p.approved.filter((a) => a === me).length
)) ))
) )
const client = getClient()
const hierarchy = client.getHierarchy()
const defaultPresenter = request.component.RequestPresenter
$: classes = new Set(requests.map((r) => r._class))
const presenters: Record<Ref<Class<Request>>, AnyComponent> = {}
function getEditor (_class: Ref<Class<Request>>): AnyComponent {
const clazz = hierarchy.getClass(_class)
const mixin = hierarchy.as(clazz, request.mixin.RequestPresenter)
if (mixin?.presenter == null && clazz.extends != null) return getEditor(clazz.extends)
return mixin.presenter
}
$: updatePresenters(classes)
function updatePresenters (classes: Set<Ref<Class<Request>>>) {
classes.forEach((cl) => {
const presenter = getEditor(cl)
presenters[cl] = presenter || defaultPresenter
})
}
$: isMobile = $deviceInfo.isMobile $: isMobile = $deviceInfo.isMobile
</script> </script>
@ -44,8 +68,8 @@
</div> </div>
{#if requests.length > 0} {#if requests.length > 0}
<Scroller padding={'0 .5rem'}> <Scroller padding={'0 .5rem'}>
{#each requests as request (request._id)} {#each requests as request}
<RequestView value={request} /> <Component is={presenters[request._class]} props={{ value: request }} />
{/each} {/each}
</Scroller> </Scroller>
{:else} {:else}

View File

@ -19,6 +19,7 @@ import TxCreateRequest from './components/activity/TxCreateRequest.svelte'
import RequestLabel from './components/activity/TxRequestLabel.svelte' import RequestLabel from './components/activity/TxRequestLabel.svelte'
import EditRequest from './components/EditRequest.svelte' import EditRequest from './components/EditRequest.svelte'
import RequestPresenter from './components/RequestPresenter.svelte' import RequestPresenter from './components/RequestPresenter.svelte'
import RequestView from './components/RequestView.svelte'
export default async (): Promise<Resources> => ({ export default async (): Promise<Resources> => ({
activity: { activity: {
@ -28,6 +29,7 @@ export default async (): Promise<Resources> => ({
component: { component: {
RequestsPopup, RequestsPopup,
EditRequest, EditRequest,
RequestPresenter RequestPresenter,
RequestView
} }
}) })

View File

@ -47,6 +47,13 @@ export enum RequestStatus {
Rejected = 'Rejected' Rejected = 'Rejected'
} }
/**
* @public
*/
export interface RequestPresenter extends Class<Doc> {
presenter: AnyComponent
}
/** /**
* @public * @public
*/ */
@ -60,10 +67,13 @@ const request = plugin(requestId, {
Request: '' as Ref<Class<Request>> Request: '' as Ref<Class<Request>>
}, },
mixin: { mixin: {
RequestDecisionComment: '' as Ref<Mixin<RequestDecisionComment>> RequestDecisionComment: '' as Ref<Mixin<RequestDecisionComment>>,
RequestPresenter: '' as Ref<Mixin<RequestPresenter>>
}, },
component: { component: {
RequestsPopup: '' as AnyComponent RequestsPopup: '' as AnyComponent,
RequestPresenter: '' as AnyComponent,
RequestView: '' as AnyComponent
}, },
string: { string: {
Requests: '' as IntlString Requests: '' as IntlString