@ynput/ayon-frontend-shared 0.2.2 → 0.2.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (134) hide show
  1. package/dist/_virtual/index.cjs5.js +5 -3
  2. package/dist/_virtual/index.cjs5.js.map +1 -1
  3. package/dist/_virtual/index.cjs6.js +3 -5
  4. package/dist/_virtual/index.cjs6.js.map +1 -1
  5. package/dist/_virtual/index.es5.js +5 -2
  6. package/dist/_virtual/index.es5.js.map +1 -1
  7. package/dist/_virtual/index.es6.js +2 -5
  8. package/dist/_virtual/index.es6.js.map +1 -1
  9. package/dist/node_modules/@reduxjs/toolkit/dist/query/react/rtk-query-react.modern.cjs.js +19 -10
  10. package/dist/node_modules/@reduxjs/toolkit/dist/query/react/rtk-query-react.modern.cjs.js.map +1 -1
  11. package/dist/node_modules/@reduxjs/toolkit/dist/query/react/rtk-query-react.modern.es.js +21 -12
  12. package/dist/node_modules/@reduxjs/toolkit/dist/query/react/rtk-query-react.modern.es.js.map +1 -1
  13. package/dist/node_modules/@reduxjs/toolkit/dist/query/rtk-query.modern.cjs.js +174 -68
  14. package/dist/node_modules/@reduxjs/toolkit/dist/query/rtk-query.modern.cjs.js.map +1 -1
  15. package/dist/node_modules/@reduxjs/toolkit/dist/query/rtk-query.modern.es.js +174 -68
  16. package/dist/node_modules/@reduxjs/toolkit/dist/query/rtk-query.modern.es.js.map +1 -1
  17. package/dist/node_modules/@standard-schema/utils/dist/index.cjs.js +23 -0
  18. package/dist/node_modules/@standard-schema/utils/dist/index.cjs.js.map +1 -0
  19. package/dist/node_modules/@standard-schema/utils/dist/index.es.js +23 -0
  20. package/dist/node_modules/@standard-schema/utils/dist/index.es.js.map +1 -0
  21. package/dist/node_modules/rehype-prism-plus/dist/index.es.cjs.js +1 -1
  22. package/dist/node_modules/rehype-prism-plus/dist/index.es.es.js +1 -1
  23. package/dist/node_modules/remove-accents/index.cjs.js +1 -1
  24. package/dist/node_modules/remove-accents/index.es.js +1 -1
  25. package/dist/shared/src/api/generated/anatomy.cjs.js +13 -0
  26. package/dist/shared/src/api/generated/anatomy.cjs.js.map +1 -1
  27. package/dist/shared/src/api/generated/anatomy.es.js +13 -0
  28. package/dist/shared/src/api/generated/anatomy.es.js.map +1 -1
  29. package/dist/shared/src/api/queries/entities/transformDetailsPanelData.cjs.js +4 -0
  30. package/dist/shared/src/api/queries/entities/transformDetailsPanelData.cjs.js.map +1 -1
  31. package/dist/shared/src/api/queries/entities/transformDetailsPanelData.es.js +4 -0
  32. package/dist/shared/src/api/queries/entities/transformDetailsPanelData.es.js.map +1 -1
  33. package/dist/shared/src/containers/Actions/Actions.cjs.js +10 -6
  34. package/dist/shared/src/containers/Actions/Actions.cjs.js.map +1 -1
  35. package/dist/shared/src/containers/Actions/Actions.es.js +10 -6
  36. package/dist/shared/src/containers/Actions/Actions.es.js.map +1 -1
  37. package/dist/shared/src/containers/Feed/components/CommentInput/CommentInput.cjs.js +5 -3
  38. package/dist/shared/src/containers/Feed/components/CommentInput/CommentInput.cjs.js.map +1 -1
  39. package/dist/shared/src/containers/Feed/components/CommentInput/CommentInput.es.js +5 -3
  40. package/dist/shared/src/containers/Feed/components/CommentInput/CommentInput.es.js.map +1 -1
  41. package/dist/shared/src/containers/ProjectTreeTable/ProjectTreeTableColumns.cjs.js +13 -1
  42. package/dist/shared/src/containers/ProjectTreeTable/ProjectTreeTableColumns.cjs.js.map +1 -1
  43. package/dist/shared/src/containers/ProjectTreeTable/ProjectTreeTableColumns.es.js +13 -1
  44. package/dist/shared/src/containers/ProjectTreeTable/ProjectTreeTableColumns.es.js.map +1 -1
  45. package/dist/shared/src/containers/ProjectTreeTable/context/ClipboardContext.cjs.js +0 -1
  46. package/dist/shared/src/containers/ProjectTreeTable/context/ClipboardContext.cjs.js.map +1 -1
  47. package/dist/shared/src/containers/ProjectTreeTable/context/ClipboardContext.es.js +0 -1
  48. package/dist/shared/src/containers/ProjectTreeTable/context/ClipboardContext.es.js.map +1 -1
  49. package/dist/shared/src/containers/ProjectTreeTable/context/clipboard/clipboardUtils.cjs.js +3 -0
  50. package/dist/shared/src/containers/ProjectTreeTable/context/clipboard/clipboardUtils.cjs.js.map +1 -1
  51. package/dist/shared/src/containers/ProjectTreeTable/context/clipboard/clipboardUtils.es.js +3 -0
  52. package/dist/shared/src/containers/ProjectTreeTable/context/clipboard/clipboardUtils.es.js.map +1 -1
  53. package/dist/shared/src/containers/ProjectTreeTable/widgets/BooleanWidget.cjs.js.map +1 -1
  54. package/dist/shared/src/containers/ProjectTreeTable/widgets/BooleanWidget.es.js.map +1 -1
  55. package/dist/shared/src/containers/ProjectTreeTable/widgets/CellWidget.cjs.js +24 -6
  56. package/dist/shared/src/containers/ProjectTreeTable/widgets/CellWidget.cjs.js.map +1 -1
  57. package/dist/shared/src/containers/ProjectTreeTable/widgets/CellWidget.es.js +24 -6
  58. package/dist/shared/src/containers/ProjectTreeTable/widgets/CellWidget.es.js.map +1 -1
  59. package/dist/shared/src/containers/ProjectTreeTable/widgets/DateWidget.cjs.js +7 -5
  60. package/dist/shared/src/containers/ProjectTreeTable/widgets/DateWidget.cjs.js.map +1 -1
  61. package/dist/shared/src/containers/ProjectTreeTable/widgets/DateWidget.es.js +7 -5
  62. package/dist/shared/src/containers/ProjectTreeTable/widgets/DateWidget.es.js.map +1 -1
  63. package/dist/shared/src/containers/ProjectTreeTable/widgets/EnumWidget.cjs.js +8 -0
  64. package/dist/shared/src/containers/ProjectTreeTable/widgets/EnumWidget.cjs.js.map +1 -1
  65. package/dist/shared/src/containers/ProjectTreeTable/widgets/EnumWidget.es.js +8 -0
  66. package/dist/shared/src/containers/ProjectTreeTable/widgets/EnumWidget.es.js.map +1 -1
  67. package/dist/shared/src/containers/ProjectTreeTable/widgets/TextWidget.cjs.js.map +1 -1
  68. package/dist/shared/src/containers/ProjectTreeTable/widgets/TextWidget.es.js.map +1 -1
  69. package/dist/types/api/generated/access.d.ts +6 -6
  70. package/dist/types/api/generated/actions.d.ts +6 -6
  71. package/dist/types/api/generated/activityFeed.d.ts +8 -8
  72. package/dist/types/api/generated/addons.d.ts +28 -28
  73. package/dist/types/api/generated/anatomy.d.ts +36 -6
  74. package/dist/types/api/generated/attributes.d.ts +5 -5
  75. package/dist/types/api/generated/authentication.d.ts +5 -5
  76. package/dist/types/api/generated/bundles.d.ts +7 -7
  77. package/dist/types/api/generated/configuration.d.ts +7 -7
  78. package/dist/types/api/generated/desktop.d.ts +12 -12
  79. package/dist/types/api/generated/entityLists.d.ts +12 -12
  80. package/dist/types/api/generated/events.d.ts +8 -8
  81. package/dist/types/api/generated/files.d.ts +7 -7
  82. package/dist/types/api/generated/folders.d.ts +8 -8
  83. package/dist/types/api/generated/graphql.d.ts +25 -25
  84. package/dist/types/api/generated/inbox.d.ts +1 -1
  85. package/dist/types/api/generated/links.d.ts +5 -5
  86. package/dist/types/api/generated/market.d.ts +6 -6
  87. package/dist/types/api/generated/onboarding.d.ts +3 -3
  88. package/dist/types/api/generated/operations.d.ts +3 -3
  89. package/dist/types/api/generated/products.d.ts +5 -5
  90. package/dist/types/api/generated/projectDashboard.d.ts +4 -4
  91. package/dist/types/api/generated/projects.d.ts +27 -27
  92. package/dist/types/api/generated/representations.d.ts +5 -5
  93. package/dist/types/api/generated/reviewables.d.ts +7 -7
  94. package/dist/types/api/generated/services.d.ts +6 -6
  95. package/dist/types/api/generated/system.d.ts +12 -12
  96. package/dist/types/api/generated/tasks.d.ts +8 -8
  97. package/dist/types/api/generated/teams.d.ts +6 -6
  98. package/dist/types/api/generated/thumbnails.d.ts +11 -11
  99. package/dist/types/api/generated/uRIs.d.ts +2 -2
  100. package/dist/types/api/generated/users.d.ts +26 -26
  101. package/dist/types/api/generated/versions.d.ts +6 -6
  102. package/dist/types/api/generated/workfiles.d.ts +6 -6
  103. package/dist/types/api/generated/ynputCloud.d.ts +5 -5
  104. package/dist/types/api/queries/actions/getActions.d.ts +29 -29
  105. package/dist/types/api/queries/activities/getActivities.d.ts +72 -71
  106. package/dist/types/api/queries/activities/getMentions.d.ts +18 -18
  107. package/dist/types/api/queries/activities/updateActivities.d.ts +62 -62
  108. package/dist/types/api/queries/activities/updateReaction.d.ts +10 -10
  109. package/dist/types/api/queries/addons/getAddons.d.ts +67 -67
  110. package/dist/types/api/queries/addons/updateAddons.d.ts +35 -35
  111. package/dist/types/api/queries/attributes/getAttributes.d.ts +23 -23
  112. package/dist/types/api/queries/attributes/updateAttributes.d.ts +12 -12
  113. package/dist/types/api/queries/authentication/getAuthentication.d.ts +15 -15
  114. package/dist/types/api/queries/entities/getEntity.d.ts +73 -73
  115. package/dist/types/api/queries/entities/getEntityPanel.d.ts +44 -44
  116. package/dist/types/api/queries/entities/transformDetailsPanelData.d.ts +1 -0
  117. package/dist/types/api/queries/entities/updateEntity.d.ts +32 -32
  118. package/dist/types/api/queries/folders/getFolders.d.ts +26 -26
  119. package/dist/types/api/queries/overview/getOverview.d.ts +72 -72
  120. package/dist/types/api/queries/overview/updateOverview.d.ts +5 -5
  121. package/dist/types/api/queries/project/getProject.d.ts +103 -103
  122. package/dist/types/api/queries/review/getReview.d.ts +36 -36
  123. package/dist/types/api/queries/review/updateReview.d.ts +13 -13
  124. package/dist/types/api/queries/system/getSystem.d.ts +39 -39
  125. package/dist/types/api/queries/userDashboard/getUserDashboard.d.ts +53 -53
  126. package/dist/types/api/queries/users/getUsers.d.ts +110 -110
  127. package/dist/types/api/queries/watchers/getWatchers.d.ts +20 -20
  128. package/dist/types/containers/Actions/Actions.d.ts +5 -1
  129. package/dist/types/containers/ProjectTreeTable/widgets/BooleanWidget.d.ts +1 -2
  130. package/dist/types/containers/ProjectTreeTable/widgets/CellWidget.d.ts +10 -0
  131. package/dist/types/containers/ProjectTreeTable/widgets/DateWidget.d.ts +2 -3
  132. package/dist/types/containers/ProjectTreeTable/widgets/EnumWidget.d.ts +1 -1
  133. package/dist/types/containers/ProjectTreeTable/widgets/TextWidget.d.ts +1 -1
  134. package/package.json +1 -1
@@ -1 +1 @@
1
- {"version":3,"file":"Actions.es.js","sources":["../../../../../src/containers/Actions/Actions.tsx"],"sourcesContent":["import * as Styled from './Actions.styled'\nimport { MouseEvent, useState } from 'react'\nimport clsx from 'clsx'\nimport { toast } from 'react-toastify'\nimport { useMemo, useEffect } from 'react'\nimport { ActionContext, useExecuteActionMutation, useGetActionsFromContextQuery } from '@shared/api'\nimport { ActionsDropdown } from './ActionsDropdown'\nimport ActionIcon from './ActionIcon'\nimport { useActionTriggers } from '@shared/hooks'\nimport { ActionConfigDialog } from './ActionConfigDialog'\nimport { InteractiveActionDialog, InteractiveForm } from './InteractiveActionDialog'\n\nconst placeholder = {\n identifier: 'placeholder',\n label: 'Featured action slot',\n isPlaceholder: true,\n icon: { type: 'material-symbols', name: 'sync' },\n}\n\ntype ActionsProps = {\n entities: any[]\n entityType: ActionContext['entityType']\n entitySubTypes?: string[]\n isLoadingEntity: boolean\n}\n\nexport const Actions = ({\n entities,\n entityType,\n entitySubTypes,\n isLoadingEntity,\n}: ActionsProps) => {\n // special triggers the actions can make to perform stuff on the client\n const { handleActionPayload } = useActionTriggers()\n const [actionBeingConfigured, setActionBeingConfigured] = useState<any>(null)\n const [interactiveForm, setInteractiveForm] = useState<any>(null)\n\n const context: ActionContext | null = useMemo(() => {\n if (!entities.length) return null\n if (!entities[0].projectName) return null\n\n // get a list of unique entity subtypes from loaded data\n const entitySubtypesLoaded = entities\n .map((entity) => entity.entitySubType)\n .filter((value, index, self) => self.indexOf(value) === index && value)\n\n // try and use the passed in entitySubTypes, if not use the loaded ones\n const entitySubTypesToUse = entitySubTypes || entitySubtypesLoaded || []\n\n // all types except version should have subtypes\n if (!entitySubTypesToUse?.length && entityType !== 'version') return null\n\n return {\n projectName: entities[0].projectName,\n entityType: entityType,\n entityIds: entities.map((entity) => entity.id),\n entitySubtypes: entitySubTypesToUse,\n }\n }, [entities, entityType])\n\n useEffect(() => {\n setInteractiveForm(null)\n }, [context])\n\n const { data, isFetching: isFetchingActions } = useGetActionsFromContextQuery(\n { mode: 'simple', actionContext: context as ActionContext },\n { skip: !context },\n )\n const actions = data?.actions || []\n\n const categoryOrder = ['application', 'admin', 'workflow']\n // group actions by category\n // sort by hardcoded category, this will changing the future\n const groupedActions = useMemo(() => {\n // Step 1: Group actions by category\n const grouped = actions.reduce((acc: { [key: string]: any[] }, action) => {\n const category = action.category || 'uncategorized'\n if (!acc[category]) {\n acc[category] = []\n }\n acc[category].push(action)\n return acc\n }, {})\n\n // Step 5: Return the ordered groups\n return grouped\n }, [actions])\n\n // get categories that don't have a specific order (not in categoryOrder)\n // then sort them alphabetically\n const unorderedCategories = useMemo(\n () => [\n ...new Set(\n Object.keys(groupedActions)\n .filter((category) => !categoryOrder.includes(category))\n .sort((a, b) => a.localeCompare(b)),\n ),\n ],\n [groupedActions],\n )\n\n const categories = [...categoryOrder, ...unorderedCategories]\n\n // create the options for the dropdown, each category is separated by a divider and a title\n // for the divider we will use a custom dropdown item template\n const dropdownOptions = useMemo(() => {\n const options = []\n\n categories.forEach((category) => {\n if (!groupedActions[category] || !groupedActions[category].length) return\n\n options.push({\n label: category,\n header: true,\n value: category,\n disabled: true,\n })\n\n const groupOptions = groupedActions[category].map((action) => ({\n value: action.identifier,\n label: action.label,\n icon: action.icon,\n hasConfig: !!action.configFields,\n }))\n\n options.push(...groupOptions)\n })\n\n // if no actions, add placeholder\n if (!options.length) {\n options.push({\n label: 'No actions available',\n value: 'no-actions',\n disabled: true,\n header: true,\n })\n }\n\n return options\n }, [groupedActions, unorderedCategories, categoryOrder])\n\n const featuredNumber = 2\n\n const featuredActions = useMemo(() => {\n // Filter and sort to get initial featured actions\n let tempFeaturedActions = actions\n .filter((action) => action.featured)\n .sort((a, b) => (a.order || 0) - (b.order || 0))\n .slice(0, featuredNumber)\n\n // Check if we need to add more actions to reach featuredNumber\n if (tempFeaturedActions.length < featuredNumber) {\n categories.forEach((category) => {\n if (tempFeaturedActions.length >= featuredNumber) return\n const actions = groupedActions[category]\n if (!actions || !actions.length) return\n\n for (let i = tempFeaturedActions.length; i < featuredNumber; i++) {\n const action = actions[i]\n if (!action) break\n if (!action.icon) continue\n tempFeaturedActions.push(action)\n }\n })\n }\n\n return tempFeaturedActions\n }, [actions, groupedActions, placeholder])\n\n const [executeAction, { isLoading: isLoadingExecution, originalArgs }] =\n useExecuteActionMutation()\n const executingAction = isLoadingExecution && originalArgs?.identifier\n\n const handleExecuteAction = async (\n identifier: string,\n e?: MouseEvent<HTMLElement> | null,\n formData?: InteractiveForm,\n ) => {\n e?.preventDefault()\n const action = actions.find((option) => option.identifier === identifier)\n\n if (!action) {\n toast.error('Action not found')\n console.warn('Action not found', identifier)\n return\n }\n\n const params = {\n addonName: action.addonName as string,\n addonVersion: action.addonVersion as string,\n variant: action.variant,\n identifier: action.identifier,\n }\n\n const actionContext = { ...context }\n if (formData) {\n actionContext.formData = formData\n }\n\n let response = null\n\n try {\n response = await executeAction({ actionContext, ...params }).unwrap()\n } catch (error: any) {\n console.error('Error executing action', error)\n toast.error(error?.data?.detail || 'Error executing action')\n return\n }\n\n try {\n // Toast the message if it is available\n if (response?.message) {\n if (response?.success) {\n toast.success(response.message, { autoClose: 2000 })\n } else {\n toast.error(response.message, { autoClose: 2000 })\n }\n }\n\n // Even if response?.success is false, we still want to handle the payload\n // as it may contain useful information - complex error messages in form,\n // redirect to another page etc. If the action just needs to abort,\n // it raises exception instead of returning a response with success: false\n\n // Use the new hook to handle payload\n if (response?.payload) {\n if (response.type === 'form') {\n // action requests additional information from the user.\n // we show a dialog with the form and when the user submits it we call the action again\n\n // It probably does not make sense to move to the useActionTriggers hook\n // as it need contexts and the dialog\n const intf = {\n identifier,\n // @ts-expect-error\n title: response.payload['title'],\n // @ts-expect-error\n fields: response.payload['fields'],\n // @ts-expect-error\n submitLabel: response.payload['submit_label'],\n // @ts-expect-error\n cancelLabel: response.payload['cancel_label'],\n // @ts-expect-error\n submitIcon: response.payload['submit_icon'],\n // @ts-expect-error\n cancelIcon: response.payload['cancel_icon'],\n }\n setInteractiveForm(intf)\n } else {\n handleActionPayload(response.type as string, response.payload)\n }\n }\n } catch (error) {\n // got response, but failed to process it\n console.warn('Error during action response processing', error)\n toast.error('Error occured during action processing')\n }\n }\n\n const handleConfigureAction = (identifier: string) => {\n const action = actions.find((data) => data.identifier === identifier)\n if (!action) return\n setActionBeingConfigured(action)\n }\n\n const handleSubmitInteractiveForm = async (identifier: string, formData: InteractiveForm) => {\n handleExecuteAction(identifier, null, formData)\n }\n\n const loadingActions = [placeholder, placeholder, placeholder]\n\n const isLoading = isFetchingActions || isLoadingEntity\n const featuredActionsToDisplay = isLoading ? loadingActions : featuredActions\n\n return (\n <Styled.Actions className=\"actions\">\n {featuredActionsToDisplay.map((action, i) => (\n <Styled.FeaturedAction\n key={action.identifier + '-' + i}\n className={clsx('action', {\n loading: isLoading,\n // @ts-expect-error\n isPlaceholder: action.isPlaceholder,\n })}\n data-tooltip={action.label}\n // @ts-expect-error\n disabled={action.isPlaceholder}\n onClick={(e) => handleExecuteAction(action.identifier, e)}\n >\n {/* @ts-ignore */}\n <ActionIcon icon={action.icon} isExecuting={executingAction === action.identifier} />\n </Styled.FeaturedAction>\n ))}\n <ActionsDropdown\n options={dropdownOptions}\n isLoading={isLoading}\n onAction={handleExecuteAction}\n onConfig={handleConfigureAction}\n />\n <ActionConfigDialog\n action={actionBeingConfigured}\n // @ts-expect-error\n context={context}\n onClose={() => setActionBeingConfigured(null)}\n />\n <InteractiveActionDialog\n interactiveForm={interactiveForm}\n onClose={() => setInteractiveForm(null)}\n // @ts-expect-error\n onSubmit={handleSubmitInteractiveForm}\n />\n </Styled.Actions>\n )\n}\n"],"names":["actions","data","jsxs","Styled.Actions","jsx","Styled.FeaturedAction"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAYA,MAAM,cAAc;AAAA,EAClB,YAAY;AAAA,EACZ,OAAO;AAAA,EACP,eAAe;AAAA,EACf,MAAM,EAAE,MAAM,oBAAoB,MAAM,OAAO;AACjD;AASO,MAAM,UAAU,CAAC;AAAA,EACtB;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,MAAoB;AAEZ,QAAA,EAAE,oBAAoB,IAAI,kBAAkB;AAClD,QAAM,CAAC,uBAAuB,wBAAwB,IAAI,SAAc,IAAI;AAC5E,QAAM,CAAC,iBAAiB,kBAAkB,IAAI,SAAc,IAAI;AAE1D,QAAA,UAAgC,QAAQ,MAAM;AAC9C,QAAA,CAAC,SAAS,OAAe,QAAA;AAC7B,QAAI,CAAC,SAAS,CAAC,EAAE,YAAoB,QAAA;AAGrC,UAAM,uBAAuB,SAC1B,IAAI,CAAC,WAAW,OAAO,aAAa,EACpC,OAAO,CAAC,OAAO,OAAO,SAAS,KAAK,QAAQ,KAAK,MAAM,SAAS,KAAK;AAGlE,UAAA,sBAAsB,kBAAkB,wBAAwB,CAAC;AAGvE,QAAI,EAAC,2DAAqB,WAAU,eAAe,UAAkB,QAAA;AAE9D,WAAA;AAAA,MACL,aAAa,SAAS,CAAC,EAAE;AAAA,MACzB;AAAA,MACA,WAAW,SAAS,IAAI,CAAC,WAAW,OAAO,EAAE;AAAA,MAC7C,gBAAgB;AAAA,IAClB;AAAA,EAAA,GACC,CAAC,UAAU,UAAU,CAAC;AAEzB,YAAU,MAAM;AACd,uBAAmB,IAAI;AAAA,EAAA,GACtB,CAAC,OAAO,CAAC;AAEZ,QAAM,EAAE,MAAM,YAAY,kBAAsB,IAAA;AAAA,IAC9C,EAAE,MAAM,UAAU,eAAe,QAAyB;AAAA,IAC1D,EAAE,MAAM,CAAC,QAAQ;AAAA,EACnB;AACM,QAAA,WAAU,6BAAM,YAAW,CAAC;AAElC,QAAM,gBAAgB,CAAC,eAAe,SAAS,UAAU;AAGnD,QAAA,iBAAiB,QAAQ,MAAM;AAEnC,UAAM,UAAU,QAAQ,OAAO,CAAC,KAA+B,WAAW;AAClE,YAAA,WAAW,OAAO,YAAY;AAChC,UAAA,CAAC,IAAI,QAAQ,GAAG;AACd,YAAA,QAAQ,IAAI,CAAC;AAAA,MAAA;AAEf,UAAA,QAAQ,EAAE,KAAK,MAAM;AAClB,aAAA;AAAA,IACT,GAAG,EAAE;AAGE,WAAA;AAAA,EAAA,GACN,CAAC,OAAO,CAAC;AAIZ,QAAM,sBAAsB;AAAA,IAC1B,MAAM;AAAA,MACJ,GAAG,IAAI;AAAA,QACL,OAAO,KAAK,cAAc,EACvB,OAAO,CAAC,aAAa,CAAC,cAAc,SAAS,QAAQ,CAAC,EACtD,KAAK,CAAC,GAAG,MAAM,EAAE,cAAc,CAAC,CAAC;AAAA,MAAA;AAAA,IAExC;AAAA,IACA,CAAC,cAAc;AAAA,EACjB;AAEA,QAAM,aAAa,CAAC,GAAG,eAAe,GAAG,mBAAmB;AAItD,QAAA,kBAAkB,QAAQ,MAAM;AACpC,UAAM,UAAU,CAAC;AAEN,eAAA,QAAQ,CAAC,aAAa;AAC3B,UAAA,CAAC,eAAe,QAAQ,KAAK,CAAC,eAAe,QAAQ,EAAE,OAAQ;AAEnE,cAAQ,KAAK;AAAA,QACX,OAAO;AAAA,QACP,QAAQ;AAAA,QACR,OAAO;AAAA,QACP,UAAU;AAAA,MAAA,CACX;AAED,YAAM,eAAe,eAAe,QAAQ,EAAE,IAAI,CAAC,YAAY;AAAA,QAC7D,OAAO,OAAO;AAAA,QACd,OAAO,OAAO;AAAA,QACd,MAAM,OAAO;AAAA,QACb,WAAW,CAAC,CAAC,OAAO;AAAA,MAAA,EACpB;AAEM,cAAA,KAAK,GAAG,YAAY;AAAA,IAAA,CAC7B;AAGG,QAAA,CAAC,QAAQ,QAAQ;AACnB,cAAQ,KAAK;AAAA,QACX,OAAO;AAAA,QACP,OAAO;AAAA,QACP,UAAU;AAAA,QACV,QAAQ;AAAA,MAAA,CACT;AAAA,IAAA;AAGI,WAAA;AAAA,EACN,GAAA,CAAC,gBAAgB,qBAAqB,aAAa,CAAC;AAEvD,QAAM,iBAAiB;AAEjB,QAAA,kBAAkB,QAAQ,MAAM;AAEhC,QAAA,sBAAsB,QACvB,OAAO,CAAC,WAAW,OAAO,QAAQ,EAClC,KAAK,CAAC,GAAG,OAAO,EAAE,SAAS,MAAM,EAAE,SAAS,EAAE,EAC9C,MAAM,GAAG,cAAc;AAGtB,QAAA,oBAAoB,SAAS,gBAAgB;AACpC,iBAAA,QAAQ,CAAC,aAAa;AAC3B,YAAA,oBAAoB,UAAU,eAAgB;AAC5CA,cAAAA,WAAU,eAAe,QAAQ;AACvC,YAAI,CAACA,YAAW,CAACA,SAAQ,OAAQ;AAEjC,iBAAS,IAAI,oBAAoB,QAAQ,IAAI,gBAAgB,KAAK;AAC1D,gBAAA,SAASA,SAAQ,CAAC;AACxB,cAAI,CAAC,OAAQ;AACT,cAAA,CAAC,OAAO,KAAM;AAClB,8BAAoB,KAAK,MAAM;AAAA,QAAA;AAAA,MACjC,CACD;AAAA,IAAA;AAGI,WAAA;AAAA,EACN,GAAA,CAAC,SAAS,gBAAgB,WAAW,CAAC;AAEnC,QAAA,CAAC,eAAe,EAAE,WAAW,oBAAoB,aAAa,CAAC,IACnE,yBAAyB;AACrB,QAAA,kBAAkB,uBAAsB,6CAAc;AAE5D,QAAM,sBAAsB,OAC1B,YACA,GACA,aACG;;AACH,2BAAG;AACH,UAAM,SAAS,QAAQ,KAAK,CAAC,WAAW,OAAO,eAAe,UAAU;AAExE,QAAI,CAAC,QAAQ;AACX,YAAM,MAAM,kBAAkB;AACtB,cAAA,KAAK,oBAAoB,UAAU;AAC3C;AAAA,IAAA;AAGF,UAAM,SAAS;AAAA,MACb,WAAW,OAAO;AAAA,MAClB,cAAc,OAAO;AAAA,MACrB,SAAS,OAAO;AAAA,MAChB,YAAY,OAAO;AAAA,IACrB;AAEM,UAAA,gBAAgB,EAAE,GAAG,QAAQ;AACnC,QAAI,UAAU;AACZ,oBAAc,WAAW;AAAA,IAAA;AAG3B,QAAI,WAAW;AAEX,QAAA;AACS,iBAAA,MAAM,cAAc,EAAE,eAAe,GAAG,OAAO,CAAC,EAAE,OAAO;AAAA,aAC7D,OAAY;AACX,cAAA,MAAM,0BAA0B,KAAK;AAC7C,YAAM,QAAM,oCAAO,SAAP,mBAAa,WAAU,wBAAwB;AAC3D;AAAA,IAAA;AAGE,QAAA;AAEF,UAAI,qCAAU,SAAS;AACrB,YAAI,qCAAU,SAAS;AACrB,gBAAM,QAAQ,SAAS,SAAS,EAAE,WAAW,KAAM;AAAA,QAAA,OAC9C;AACL,gBAAM,MAAM,SAAS,SAAS,EAAE,WAAW,KAAM;AAAA,QAAA;AAAA,MACnD;AASF,UAAI,qCAAU,SAAS;AACjB,YAAA,SAAS,SAAS,QAAQ;AAM5B,gBAAM,OAAO;AAAA,YACX;AAAA;AAAA,YAEA,OAAO,SAAS,QAAQ,OAAO;AAAA;AAAA,YAE/B,QAAQ,SAAS,QAAQ,QAAQ;AAAA;AAAA,YAEjC,aAAa,SAAS,QAAQ,cAAc;AAAA;AAAA,YAE5C,aAAa,SAAS,QAAQ,cAAc;AAAA;AAAA,YAE5C,YAAY,SAAS,QAAQ,aAAa;AAAA;AAAA,YAE1C,YAAY,SAAS,QAAQ,aAAa;AAAA,UAC5C;AACA,6BAAmB,IAAI;AAAA,QAAA,OAClB;AACe,8BAAA,SAAS,MAAgB,SAAS,OAAO;AAAA,QAAA;AAAA,MAC/D;AAAA,aAEK,OAAO;AAEN,cAAA,KAAK,2CAA2C,KAAK;AAC7D,YAAM,MAAM,wCAAwC;AAAA,IAAA;AAAA,EAExD;AAEM,QAAA,wBAAwB,CAAC,eAAuB;AACpD,UAAM,SAAS,QAAQ,KAAK,CAACC,UAASA,MAAK,eAAe,UAAU;AACpE,QAAI,CAAC,OAAQ;AACb,6BAAyB,MAAM;AAAA,EACjC;AAEM,QAAA,8BAA8B,OAAO,YAAoB,aAA8B;AACvE,wBAAA,YAAY,MAAM,QAAQ;AAAA,EAChD;AAEA,QAAM,iBAAiB,CAAC,aAAa,aAAa,WAAW;AAE7D,QAAM,YAAY,qBAAqB;AACjC,QAAA,2BAA2B,YAAY,iBAAiB;AAE9D,SACGC,kCAAA,KAAAC,WAAA,EAAe,WAAU,WACvB,UAAA;AAAA,IAAyB,yBAAA,IAAI,CAAC,QAAQ,MACrCC,kCAAA;AAAA,MAACC;AAAAA,MAAA;AAAA,QAEC,WAAW,KAAK,UAAU;AAAA,UACxB,SAAS;AAAA;AAAA,UAET,eAAe,OAAO;AAAA,QAAA,CACvB;AAAA,QACD,gBAAc,OAAO;AAAA,QAErB,UAAU,OAAO;AAAA,QACjB,SAAS,CAAC,MAAM,oBAAoB,OAAO,YAAY,CAAC;AAAA,QAGxD,UAAAD,kCAAA,IAAC,cAAW,MAAM,OAAO,MAAM,aAAa,oBAAoB,OAAO,WAAY,CAAA;AAAA,MAAA;AAAA,MAZ9E,OAAO,aAAa,MAAM;AAAA,IAAA,CAclC;AAAA,IACDA,kCAAA;AAAA,MAAC;AAAA,MAAA;AAAA,QACC,SAAS;AAAA,QACT;AAAA,QACA,UAAU;AAAA,QACV,UAAU;AAAA,MAAA;AAAA,IACZ;AAAA,IACAA,kCAAA;AAAA,MAAC;AAAA,MAAA;AAAA,QACC,QAAQ;AAAA,QAER;AAAA,QACA,SAAS,MAAM,yBAAyB,IAAI;AAAA,MAAA;AAAA,IAC9C;AAAA,IACAA,kCAAA;AAAA,MAAC;AAAA,MAAA;AAAA,QACC;AAAA,QACA,SAAS,MAAM,mBAAmB,IAAI;AAAA,QAEtC,UAAU;AAAA,MAAA;AAAA,IAAA;AAAA,EACZ,GACF;AAEJ;"}
1
+ {"version":3,"file":"Actions.es.js","sources":["../../../../../src/containers/Actions/Actions.tsx"],"sourcesContent":["import * as Styled from './Actions.styled'\nimport { MouseEvent, useState } from 'react'\nimport clsx from 'clsx'\nimport { toast } from 'react-toastify'\nimport { useMemo, useEffect } from 'react'\nimport { ActionContext, useExecuteActionMutation, useGetActionsFromContextQuery } from '@shared/api'\nimport { ActionsDropdown } from './ActionsDropdown'\nimport ActionIcon from './ActionIcon'\nimport { useActionTriggers } from '@shared/hooks'\nimport { ActionConfigDialog } from './ActionConfigDialog'\nimport { InteractiveActionDialog, InteractiveForm } from './InteractiveActionDialog'\n\nconst placeholder = {\n identifier: 'placeholder',\n label: 'Featured action slot',\n isPlaceholder: true,\n icon: { type: 'material-symbols', name: 'sync' },\n groupLabel: '',\n}\n\ntype ActionsProps = {\n entities: { id: string; projectName: string; entitySubType?: string }[]\n entityType: ActionContext['entityType']\n entitySubTypes?: string[]\n isLoadingEntity: boolean\n}\n\nexport const Actions = ({\n entities,\n entityType,\n entitySubTypes,\n isLoadingEntity,\n}: ActionsProps) => {\n // special triggers the actions can make to perform stuff on the client\n const { handleActionPayload } = useActionTriggers()\n const [actionBeingConfigured, setActionBeingConfigured] = useState<any>(null)\n const [interactiveForm, setInteractiveForm] = useState<any>(null)\n\n const context: ActionContext | null = useMemo(() => {\n if (!entities.length) return null\n if (!entities[0].projectName) return null\n\n // get a list of unique entity subtypes from loaded data\n const entitySubtypesLoaded = entities\n .filter((entity) => entity.entitySubType)\n .map((entity) => entity.entitySubType as string)\n .filter((value, index, self) => self.indexOf(value) === index && value)\n\n // try and use the passed in entitySubTypes, if not use the loaded ones\n const entitySubTypesToUse = entitySubTypes?.length ? entitySubTypes : entitySubtypesLoaded\n\n // all types except version/representation should have subtypes\n if (\n !entitySubTypesToUse?.length &&\n entityType !== 'version' &&\n entityType !== 'representation'\n ) {\n console.warn('No entity subtypes found')\n return null\n }\n\n return {\n projectName: entities[0].projectName,\n entityType: entityType,\n entityIds: entities.map((entity) => entity.id),\n entitySubtypes: entitySubTypesToUse,\n }\n }, [entities, entityType])\n\n useEffect(() => {\n setInteractiveForm(null)\n }, [context])\n\n const { data, isFetching: isFetchingActions } = useGetActionsFromContextQuery(\n { mode: 'simple', actionContext: context as ActionContext },\n { skip: !context },\n )\n\n const actions = data?.actions || []\n\n const categoryOrder = ['application', 'admin', 'workflow']\n // group actions by category\n // sort by hardcoded category, this will changing the future\n const groupedActions = useMemo(() => {\n // Step 1: Group actions by category\n const grouped = actions.reduce((acc: { [key: string]: any[] }, action) => {\n const category = action.category || 'uncategorized'\n if (!acc[category]) {\n acc[category] = []\n }\n acc[category].push(action)\n return acc\n }, {})\n\n // Step 5: Return the ordered groups\n return grouped\n }, [actions])\n\n // get categories that don't have a specific order (not in categoryOrder)\n // then sort them alphabetically\n const unorderedCategories = useMemo(\n () => [\n ...new Set(\n Object.keys(groupedActions)\n .filter((category) => !categoryOrder.includes(category))\n .sort((a, b) => a.localeCompare(b)),\n ),\n ],\n [groupedActions],\n )\n\n const categories = [...categoryOrder, ...unorderedCategories]\n\n // create the options for the dropdown, each category is separated by a divider and a title\n // for the divider we will use a custom dropdown item template\n const dropdownOptions = useMemo(() => {\n const options = []\n\n categories.forEach((category) => {\n if (!groupedActions[category] || !groupedActions[category].length) return\n\n options.push({\n label: category,\n header: true,\n value: category,\n disabled: true,\n })\n\n const groupOptions = groupedActions[category].map((action) => ({\n value: action.identifier,\n label: action.groupLabel ? action.groupLabel + ' ' + action.label : action.label,\n icon: action.icon,\n hasConfig: !!action.configFields,\n }))\n\n options.push(...groupOptions)\n })\n\n // if no actions, add placeholder\n if (!options.length) {\n options.push({\n label: 'No actions available',\n value: 'no-actions',\n disabled: true,\n header: true,\n })\n }\n\n return options\n }, [groupedActions, unorderedCategories, categoryOrder])\n\n const featuredNumber = 2\n\n const featuredActions = useMemo(() => {\n // Filter and sort to get initial featured actions\n let tempFeaturedActions = actions\n .filter((action) => action.featured)\n .sort((a, b) => (a.order || 0) - (b.order || 0))\n .slice(0, featuredNumber)\n\n // Check if we need to add more actions to reach featuredNumber\n if (tempFeaturedActions.length < featuredNumber) {\n categories.forEach((category) => {\n if (tempFeaturedActions.length >= featuredNumber) return\n const actions = groupedActions[category]\n if (!actions || !actions.length) return\n\n for (let i = tempFeaturedActions.length; i < featuredNumber; i++) {\n const action = actions[i]\n if (!action) break\n if (!action.icon) continue\n tempFeaturedActions.push(action)\n }\n })\n }\n\n return tempFeaturedActions\n }, [actions, groupedActions, placeholder])\n\n const [executeAction, { isLoading: isLoadingExecution, originalArgs }] =\n useExecuteActionMutation()\n const executingAction = isLoadingExecution && originalArgs?.identifier\n\n const handleExecuteAction = async (\n identifier: string,\n e?: MouseEvent<HTMLElement> | null,\n formData?: InteractiveForm,\n ) => {\n e?.preventDefault()\n const action = actions.find((option) => option.identifier === identifier)\n\n if (!action) {\n toast.error('Action not found')\n console.warn('Action not found', identifier)\n return\n }\n\n const params = {\n addonName: action.addonName as string,\n addonVersion: action.addonVersion as string,\n variant: action.variant,\n identifier: action.identifier,\n }\n\n const actionContext = { ...context }\n if (formData) {\n actionContext.formData = formData\n }\n\n let response = null\n\n try {\n response = await executeAction({ actionContext, ...params }).unwrap()\n } catch (error: any) {\n console.error('Error executing action', error)\n toast.error(error?.data?.detail || 'Error executing action')\n return\n }\n\n try {\n // Toast the message if it is available\n if (response?.message) {\n if (response?.success) {\n toast.success(response.message, { autoClose: 2000 })\n } else {\n toast.error(response.message, { autoClose: 2000 })\n }\n }\n\n // Even if response?.success is false, we still want to handle the payload\n // as it may contain useful information - complex error messages in form,\n // redirect to another page etc. If the action just needs to abort,\n // it raises exception instead of returning a response with success: false\n\n // Use the new hook to handle payload\n if (response?.payload) {\n if (response.type === 'form') {\n // action requests additional information from the user.\n // we show a dialog with the form and when the user submits it we call the action again\n\n // It probably does not make sense to move to the useActionTriggers hook\n // as it need contexts and the dialog\n const intf = {\n identifier,\n // @ts-expect-error\n title: response.payload['title'],\n // @ts-expect-error\n fields: response.payload['fields'],\n // @ts-expect-error\n submitLabel: response.payload['submit_label'],\n // @ts-expect-error\n cancelLabel: response.payload['cancel_label'],\n // @ts-expect-error\n submitIcon: response.payload['submit_icon'],\n // @ts-expect-error\n cancelIcon: response.payload['cancel_icon'],\n }\n setInteractiveForm(intf)\n } else {\n handleActionPayload(response.type as string, response.payload)\n }\n }\n } catch (error) {\n // got response, but failed to process it\n console.warn('Error during action response processing', error)\n toast.error('Error occured during action processing')\n }\n }\n\n const handleConfigureAction = (identifier: string) => {\n const action = actions.find((data) => data.identifier === identifier)\n if (!action) return\n setActionBeingConfigured(action)\n }\n\n const handleSubmitInteractiveForm = async (identifier: string, formData: InteractiveForm) => {\n handleExecuteAction(identifier, null, formData)\n }\n\n const loadingActions = [placeholder, placeholder, placeholder]\n\n const isLoading = isFetchingActions || isLoadingEntity\n const featuredActionsToDisplay = isLoading ? loadingActions : featuredActions\n\n return (\n <Styled.Actions className=\"actions\">\n {featuredActionsToDisplay.map((action, i) => (\n <Styled.FeaturedAction\n key={action.identifier + '-' + i}\n className={clsx('action', {\n loading: isLoading,\n // @ts-expect-error\n isPlaceholder: action.isPlaceholder,\n })}\n data-tooltip={action.groupLabel ? action.groupLabel + ' ' + action.label : action.label}\n // @ts-expect-error\n disabled={action.isPlaceholder}\n onClick={(e) => handleExecuteAction(action.identifier, e)}\n >\n {/* @ts-ignore */}\n <ActionIcon icon={action.icon} isExecuting={executingAction === action.identifier} />\n </Styled.FeaturedAction>\n ))}\n <ActionsDropdown\n options={dropdownOptions}\n isLoading={isLoading}\n onAction={handleExecuteAction}\n onConfig={handleConfigureAction}\n />\n <ActionConfigDialog\n action={actionBeingConfigured}\n // @ts-expect-error\n context={context}\n onClose={() => setActionBeingConfigured(null)}\n />\n <InteractiveActionDialog\n interactiveForm={interactiveForm}\n onClose={() => setInteractiveForm(null)}\n // @ts-expect-error\n onSubmit={handleSubmitInteractiveForm}\n />\n </Styled.Actions>\n )\n}\n"],"names":["actions","data","jsxs","Styled.Actions","jsx","Styled.FeaturedAction"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAYA,MAAM,cAAc;AAAA,EAClB,YAAY;AAAA,EACZ,OAAO;AAAA,EACP,eAAe;AAAA,EACf,MAAM,EAAE,MAAM,oBAAoB,MAAM,OAAO;AAAA,EAC/C,YAAY;AACd;AASO,MAAM,UAAU,CAAC;AAAA,EACtB;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,MAAoB;AAEZ,QAAA,EAAE,oBAAoB,IAAI,kBAAkB;AAClD,QAAM,CAAC,uBAAuB,wBAAwB,IAAI,SAAc,IAAI;AAC5E,QAAM,CAAC,iBAAiB,kBAAkB,IAAI,SAAc,IAAI;AAE1D,QAAA,UAAgC,QAAQ,MAAM;AAC9C,QAAA,CAAC,SAAS,OAAe,QAAA;AAC7B,QAAI,CAAC,SAAS,CAAC,EAAE,YAAoB,QAAA;AAG/B,UAAA,uBAAuB,SAC1B,OAAO,CAAC,WAAW,OAAO,aAAa,EACvC,IAAI,CAAC,WAAW,OAAO,aAAuB,EAC9C,OAAO,CAAC,OAAO,OAAO,SAAS,KAAK,QAAQ,KAAK,MAAM,SAAS,KAAK;AAGlE,UAAA,uBAAsB,iDAAgB,UAAS,iBAAiB;AAGtE,QACE,EAAC,2DAAqB,WACtB,eAAe,aACf,eAAe,kBACf;AACA,cAAQ,KAAK,0BAA0B;AAChC,aAAA;AAAA,IAAA;AAGF,WAAA;AAAA,MACL,aAAa,SAAS,CAAC,EAAE;AAAA,MACzB;AAAA,MACA,WAAW,SAAS,IAAI,CAAC,WAAW,OAAO,EAAE;AAAA,MAC7C,gBAAgB;AAAA,IAClB;AAAA,EAAA,GACC,CAAC,UAAU,UAAU,CAAC;AAEzB,YAAU,MAAM;AACd,uBAAmB,IAAI;AAAA,EAAA,GACtB,CAAC,OAAO,CAAC;AAEZ,QAAM,EAAE,MAAM,YAAY,kBAAsB,IAAA;AAAA,IAC9C,EAAE,MAAM,UAAU,eAAe,QAAyB;AAAA,IAC1D,EAAE,MAAM,CAAC,QAAQ;AAAA,EACnB;AAEM,QAAA,WAAU,6BAAM,YAAW,CAAC;AAElC,QAAM,gBAAgB,CAAC,eAAe,SAAS,UAAU;AAGnD,QAAA,iBAAiB,QAAQ,MAAM;AAEnC,UAAM,UAAU,QAAQ,OAAO,CAAC,KAA+B,WAAW;AAClE,YAAA,WAAW,OAAO,YAAY;AAChC,UAAA,CAAC,IAAI,QAAQ,GAAG;AACd,YAAA,QAAQ,IAAI,CAAC;AAAA,MAAA;AAEf,UAAA,QAAQ,EAAE,KAAK,MAAM;AAClB,aAAA;AAAA,IACT,GAAG,EAAE;AAGE,WAAA;AAAA,EAAA,GACN,CAAC,OAAO,CAAC;AAIZ,QAAM,sBAAsB;AAAA,IAC1B,MAAM;AAAA,MACJ,GAAG,IAAI;AAAA,QACL,OAAO,KAAK,cAAc,EACvB,OAAO,CAAC,aAAa,CAAC,cAAc,SAAS,QAAQ,CAAC,EACtD,KAAK,CAAC,GAAG,MAAM,EAAE,cAAc,CAAC,CAAC;AAAA,MAAA;AAAA,IAExC;AAAA,IACA,CAAC,cAAc;AAAA,EACjB;AAEA,QAAM,aAAa,CAAC,GAAG,eAAe,GAAG,mBAAmB;AAItD,QAAA,kBAAkB,QAAQ,MAAM;AACpC,UAAM,UAAU,CAAC;AAEN,eAAA,QAAQ,CAAC,aAAa;AAC3B,UAAA,CAAC,eAAe,QAAQ,KAAK,CAAC,eAAe,QAAQ,EAAE,OAAQ;AAEnE,cAAQ,KAAK;AAAA,QACX,OAAO;AAAA,QACP,QAAQ;AAAA,QACR,OAAO;AAAA,QACP,UAAU;AAAA,MAAA,CACX;AAED,YAAM,eAAe,eAAe,QAAQ,EAAE,IAAI,CAAC,YAAY;AAAA,QAC7D,OAAO,OAAO;AAAA,QACd,OAAO,OAAO,aAAa,OAAO,aAAa,MAAM,OAAO,QAAQ,OAAO;AAAA,QAC3E,MAAM,OAAO;AAAA,QACb,WAAW,CAAC,CAAC,OAAO;AAAA,MAAA,EACpB;AAEM,cAAA,KAAK,GAAG,YAAY;AAAA,IAAA,CAC7B;AAGG,QAAA,CAAC,QAAQ,QAAQ;AACnB,cAAQ,KAAK;AAAA,QACX,OAAO;AAAA,QACP,OAAO;AAAA,QACP,UAAU;AAAA,QACV,QAAQ;AAAA,MAAA,CACT;AAAA,IAAA;AAGI,WAAA;AAAA,EACN,GAAA,CAAC,gBAAgB,qBAAqB,aAAa,CAAC;AAEvD,QAAM,iBAAiB;AAEjB,QAAA,kBAAkB,QAAQ,MAAM;AAEhC,QAAA,sBAAsB,QACvB,OAAO,CAAC,WAAW,OAAO,QAAQ,EAClC,KAAK,CAAC,GAAG,OAAO,EAAE,SAAS,MAAM,EAAE,SAAS,EAAE,EAC9C,MAAM,GAAG,cAAc;AAGtB,QAAA,oBAAoB,SAAS,gBAAgB;AACpC,iBAAA,QAAQ,CAAC,aAAa;AAC3B,YAAA,oBAAoB,UAAU,eAAgB;AAC5CA,cAAAA,WAAU,eAAe,QAAQ;AACvC,YAAI,CAACA,YAAW,CAACA,SAAQ,OAAQ;AAEjC,iBAAS,IAAI,oBAAoB,QAAQ,IAAI,gBAAgB,KAAK;AAC1D,gBAAA,SAASA,SAAQ,CAAC;AACxB,cAAI,CAAC,OAAQ;AACT,cAAA,CAAC,OAAO,KAAM;AAClB,8BAAoB,KAAK,MAAM;AAAA,QAAA;AAAA,MACjC,CACD;AAAA,IAAA;AAGI,WAAA;AAAA,EACN,GAAA,CAAC,SAAS,gBAAgB,WAAW,CAAC;AAEnC,QAAA,CAAC,eAAe,EAAE,WAAW,oBAAoB,aAAa,CAAC,IACnE,yBAAyB;AACrB,QAAA,kBAAkB,uBAAsB,6CAAc;AAE5D,QAAM,sBAAsB,OAC1B,YACA,GACA,aACG;;AACH,2BAAG;AACH,UAAM,SAAS,QAAQ,KAAK,CAAC,WAAW,OAAO,eAAe,UAAU;AAExE,QAAI,CAAC,QAAQ;AACX,YAAM,MAAM,kBAAkB;AACtB,cAAA,KAAK,oBAAoB,UAAU;AAC3C;AAAA,IAAA;AAGF,UAAM,SAAS;AAAA,MACb,WAAW,OAAO;AAAA,MAClB,cAAc,OAAO;AAAA,MACrB,SAAS,OAAO;AAAA,MAChB,YAAY,OAAO;AAAA,IACrB;AAEM,UAAA,gBAAgB,EAAE,GAAG,QAAQ;AACnC,QAAI,UAAU;AACZ,oBAAc,WAAW;AAAA,IAAA;AAG3B,QAAI,WAAW;AAEX,QAAA;AACS,iBAAA,MAAM,cAAc,EAAE,eAAe,GAAG,OAAO,CAAC,EAAE,OAAO;AAAA,aAC7D,OAAY;AACX,cAAA,MAAM,0BAA0B,KAAK;AAC7C,YAAM,QAAM,oCAAO,SAAP,mBAAa,WAAU,wBAAwB;AAC3D;AAAA,IAAA;AAGE,QAAA;AAEF,UAAI,qCAAU,SAAS;AACrB,YAAI,qCAAU,SAAS;AACrB,gBAAM,QAAQ,SAAS,SAAS,EAAE,WAAW,KAAM;AAAA,QAAA,OAC9C;AACL,gBAAM,MAAM,SAAS,SAAS,EAAE,WAAW,KAAM;AAAA,QAAA;AAAA,MACnD;AASF,UAAI,qCAAU,SAAS;AACjB,YAAA,SAAS,SAAS,QAAQ;AAM5B,gBAAM,OAAO;AAAA,YACX;AAAA;AAAA,YAEA,OAAO,SAAS,QAAQ,OAAO;AAAA;AAAA,YAE/B,QAAQ,SAAS,QAAQ,QAAQ;AAAA;AAAA,YAEjC,aAAa,SAAS,QAAQ,cAAc;AAAA;AAAA,YAE5C,aAAa,SAAS,QAAQ,cAAc;AAAA;AAAA,YAE5C,YAAY,SAAS,QAAQ,aAAa;AAAA;AAAA,YAE1C,YAAY,SAAS,QAAQ,aAAa;AAAA,UAC5C;AACA,6BAAmB,IAAI;AAAA,QAAA,OAClB;AACe,8BAAA,SAAS,MAAgB,SAAS,OAAO;AAAA,QAAA;AAAA,MAC/D;AAAA,aAEK,OAAO;AAEN,cAAA,KAAK,2CAA2C,KAAK;AAC7D,YAAM,MAAM,wCAAwC;AAAA,IAAA;AAAA,EAExD;AAEM,QAAA,wBAAwB,CAAC,eAAuB;AACpD,UAAM,SAAS,QAAQ,KAAK,CAACC,UAASA,MAAK,eAAe,UAAU;AACpE,QAAI,CAAC,OAAQ;AACb,6BAAyB,MAAM;AAAA,EACjC;AAEM,QAAA,8BAA8B,OAAO,YAAoB,aAA8B;AACvE,wBAAA,YAAY,MAAM,QAAQ;AAAA,EAChD;AAEA,QAAM,iBAAiB,CAAC,aAAa,aAAa,WAAW;AAE7D,QAAM,YAAY,qBAAqB;AACjC,QAAA,2BAA2B,YAAY,iBAAiB;AAE9D,SACGC,kCAAA,KAAAC,WAAA,EAAe,WAAU,WACvB,UAAA;AAAA,IAAyB,yBAAA,IAAI,CAAC,QAAQ,MACrCC,kCAAA;AAAA,MAACC;AAAAA,MAAA;AAAA,QAEC,WAAW,KAAK,UAAU;AAAA,UACxB,SAAS;AAAA;AAAA,UAET,eAAe,OAAO;AAAA,QAAA,CACvB;AAAA,QACD,gBAAc,OAAO,aAAa,OAAO,aAAa,MAAM,OAAO,QAAQ,OAAO;AAAA,QAElF,UAAU,OAAO;AAAA,QACjB,SAAS,CAAC,MAAM,oBAAoB,OAAO,YAAY,CAAC;AAAA,QAGxD,UAAAD,kCAAA,IAAC,cAAW,MAAM,OAAO,MAAM,aAAa,oBAAoB,OAAO,WAAY,CAAA;AAAA,MAAA;AAAA,MAZ9E,OAAO,aAAa,MAAM;AAAA,IAAA,CAclC;AAAA,IACDA,kCAAA;AAAA,MAAC;AAAA,MAAA;AAAA,QACC,SAAS;AAAA,QACT;AAAA,QACA,UAAU;AAAA,QACV,UAAU;AAAA,MAAA;AAAA,IACZ;AAAA,IACAA,kCAAA;AAAA,MAAC;AAAA,MAAA;AAAA,QACC,QAAQ;AAAA,QAER;AAAA,QACA,SAAS,MAAM,yBAAyB,IAAI;AAAA,MAAA;AAAA,IAC9C;AAAA,IACAA,kCAAA;AAAA,MAAC;AAAA,MAAA;AAAA,QACC;AAAA,QACA,SAAS,MAAM,mBAAmB,IAAI;AAAA,QAEtC,UAAU;AAAA,MAAA;AAAA,IAAA;AAAA,EACZ,GACF;AAEJ;"}
@@ -83,10 +83,12 @@ const CommentInput = ({
83
83
  var _a2, _b, _c;
84
84
  if (isOpen) {
85
85
  (_b = (_a2 = editorRef.current) == null ? void 0 : _a2.getEditor()) == null ? void 0 : _b.enable();
86
- const blockAutoFocus = !!annotations.length && files.length === 0;
87
- !blockAutoFocus && ((_c = editorRef.current) == null ? void 0 : _c.focus());
86
+ if (annotations.length > 0 && files.length === 0) {
87
+ return;
88
+ }
89
+ (_c = editorRef.current) == null ? void 0 : _c.focus();
88
90
  }
89
- }, [isOpen, editorRef, annotations, files]);
91
+ }, [isOpen, editorRef]);
90
92
  mentionTypes.sort((a, b) => b.length - a.length);
91
93
  const mentionOptions = React.useMemo(
92
94
  () => getMentionOptions(
@@ -1 +1 @@
1
- {"version":3,"file":"CommentInput.cjs.js","sources":["../../../../../../../src/containers/Feed/components/CommentInput/CommentInput.tsx"],"sourcesContent":["// React and related hooks\nimport React, { FC, useEffect, useMemo, useRef, useState } from 'react'\n\n// Third-party libraries\nimport clsx from 'clsx'\nimport { toast } from 'react-toastify'\nimport ReactQuill, { Quill } from 'react-quill-ayon'\n\n// Components\nimport { Button, Icon, SaveButton } from '@ynput/ayon-react-components'\nimport CommentMentionSelect from '../CommentMentionSelect/CommentMentionSelect'\nimport InputMarkdownConvert from './InputMarkdownConvert'\nimport FilesGrid from '../FilesGrid'\n\n// Styled components\nimport * as Styled from './CommentInput.styled'\n\n// Helpers and utilities\nimport getMentionOptions from '../../mentionHelpers/getMentionOptions'\nimport getMentionUsers from '../../mentionHelpers/getMentionUsers'\nimport getMentionTasks from '../../mentionHelpers/getMentionTasks'\nimport getMentionVersions from '../../mentionHelpers/getMentionVersions'\nimport { convertToMarkdown } from './quillToMarkdown'\nimport { handleFileDrop, parseImages, typeWithDelay } from './helpers'\nimport { getModules, quillFormats } from './modules'\n\n// Hooks\nimport useInitialValue from './hooks/useInitialValue'\nimport useSetCursorEnd from './hooks/useSetCursorEnd'\nimport useMentionLink from './hooks/useMentionLink'\nimport useAnnotationsSync from './hooks/useAnnotationsSync'\n\n// State management\nimport useAnnotationsUpload from './hooks/useAnnotationsUpload'\nimport { useFeedContext } from '../../context/FeedContext'\n\nvar Delta = Quill.import('delta')\n\nconst mentionTypes = ['@', '@@', '@@@']\nexport const mentionTypeOptions = {\n '@@@': {\n id: 'task',\n },\n '@@': {\n id: 'version',\n },\n '@': {\n id: 'user',\n isCircle: true,\n },\n}\n\ninterface CommentInputProps {\n initValue: string | null\n initFiles?: any[]\n onSubmit: (markdown: string, files: any[]) => Promise<void>\n isEditing?: boolean\n disabled?: boolean\n isLoading?: boolean\n isOpen: boolean\n onOpen?: () => void\n onClose?: () => void\n}\n\nconst CommentInput: FC<CommentInputProps> = ({\n initValue,\n initFiles = [],\n onSubmit,\n isEditing,\n disabled,\n isLoading,\n isOpen,\n onOpen,\n onClose,\n}) => {\n const { projectName, entities, projectInfo, scope, currentTab, mentionSuggestionsData } =\n useFeedContext()\n\n const {\n users: mentionUsers,\n versions: mentionVersions,\n tasks: mentionTasks,\n } = mentionSuggestionsData || {}\n\n const [initHeight, setInitHeight] = useState(88)\n const [editorValue, setEditorValue] = useState('')\n // file uploads\n const [files, setFiles] = useState(initFiles)\n const [filesUploading, setFilesUploading] = useState([])\n const [isDropping, setIsDropping] = useState(false)\n const [isSubmitting, setIsSubmitting] = useState(false)\n\n const { annotations, removeAnnotation, goToAnnotation } = useAnnotationsSync({\n entityId: entities[0]?.id,\n filesUploading,\n })\n\n // MENTION STATES\n const [mention, setMention] = useState<null | any>(null)\n const [mentionSelectedIndex, setMentionSelectedIndex] = useState(0)\n // REFS\n const editorRef = useRef<any>(null)\n const markdownRef = useRef<HTMLDivElement>(null)\n\n // if there is an initial value, set it so the editor is prefilled\n useInitialValue({\n markdownRef,\n initValue,\n setEditorValue,\n setInitHeight,\n isOpen: isOpen,\n filter: currentTab,\n })\n\n // When editing, set selection to the end of the editor\n useSetCursorEnd({ initHeight, editorRef, isEditing })\n // create a new quill format for mentions and registers it\n useMentionLink({ projectName })\n\n // focus on editor when opened\n useEffect(() => {\n if (isOpen) {\n editorRef.current?.getEditor()?.enable()\n // block autofocus if opened from an annotation\n const blockAutoFocus = !!annotations.length && files.length === 0\n !blockAutoFocus && editorRef.current?.focus()\n }\n }, [isOpen, editorRef, annotations, files])\n\n mentionTypes.sort((a, b) => b.length - a.length)\n\n const mentionOptions = useMemo(\n () =>\n getMentionOptions(\n mention?.type,\n {\n '@': () => getMentionUsers(mentionUsers),\n '@@': () => getMentionVersions(mentionVersions),\n '@@@': () => getMentionTasks(mentionTasks, projectInfo.taskTypes),\n },\n mention?.search,\n ),\n [mentionTasks, mentionVersions, mentionUsers, mention?.type, mention?.search],\n )\n\n // show first 5 and filter itself out\n const shownMentionOptions = mentionOptions.slice(0, 5)\n\n // triggered when a mention is selected\n const [newSelection, setNewSelection] = useState<null | number>()\n\n useEffect(() => {\n if (newSelection) {\n setNewSelection(null)\n // now we set selection to the end of the mention\n const quill = editorRef.current.getEditor()\n quill.setSelection(newSelection)\n }\n }, [newSelection])\n\n const handleSelectMention = (selectedOption: any) => {\n // get option text\n const quill = editorRef.current.getEditor()\n\n const typePrefix = mention.type // the type of mention: @, @@, @@@\n const search = typePrefix + (mention.search || '') // the full search string: @Tim\n const mentionLabel = typePrefix + selectedOption.label // the label of the mention: @Tim Bailey\n // @ts-expect-error\n const type = mentionTypeOptions[typePrefix] // the type of mention: user, version, task\n const href = `${type?.id}:${selectedOption.id}` // the href of the mention: user:user.123\n\n // get selection delta\n const selection = quill.getSelection(true)\n const selectionIndex = selection?.index || 0\n const startIndex = selectionIndex - search.length // the start index of the search\n\n // first delete the search string\n quill.deleteText(startIndex, search.length)\n\n // insert embed link\n quill.insertText(startIndex, mentionLabel, 'mention', href)\n\n const endIndex = startIndex + mentionLabel.length\n\n // insert a space after the mention\n quill.updateContents(new Delta().retain(endIndex).insert(' '))\n\n // remove single \\n after mention\n quill.updateContents(new Delta().retain(endIndex + 1).delete(1))\n\n // set selection to the end of the mention + 1\n setNewSelection(endIndex + 1)\n\n // reset mention state\n setMention(null)\n setMentionSelectedIndex(0)\n }\n\n const handleSelectChange = (option: any) => {\n handleSelectMention(option)\n }\n\n const handleChange = (content: string, delta: any, _: any, editor: any) => {\n let currentCharacter =\n (delta.ops[0] && delta.ops[0].insert) || (delta.ops[1] && delta.ops[1].insert)\n\n const tabOrEnter = currentCharacter === '\\n' || currentCharacter === '\\t'\n // find the first option\n const selectedOption = mentionOptions[mentionSelectedIndex]\n\n if (mention && tabOrEnter && selectedOption) {\n // get option text\n const retain = (delta.ops[0] && delta.ops[0].retain) || 0\n // prevent default\n\n // @ts-ignore\n handleSelectMention(selectedOption, retain)\n\n return\n }\n\n setEditorValue(content)\n\n const isDelete = delta.ops.length === 2 && !!delta.ops[1].delete\n\n if (!currentCharacter && isDelete) {\n currentCharacter = editor.getText(delta.ops[0].retain - 1, 1)\n }\n\n const isMention = mentionTypes.includes(currentCharacter)\n\n if (isMention) {\n const mentionIndex = delta.ops.findIndex((op: any) => 'insert' in op || 'delete' in op)\n const mention = currentCharacter\n let retain = mentionIndex === 0 ? 0 : delta.ops[mentionIndex - 1].retain\n if (isDelete) retain = retain - 1\n\n // for each mention denotation char, check if it is a mention\n // sort by length of mention denotation char\n let mentionMatch = null\n\n // loop through each mention denotation char, with longest first. First one to match is the one we want\n for (const chars of mentionTypes) {\n let isMatch = true\n // start with the last character\n if (chars.endsWith(mention)) {\n // loop through the chars backwards\n for (let i = chars.length - 1; i >= 0; i--) {\n // skip first character as that's already been checked\n if (i === 0) continue\n const char = chars[i - 1]\n const indexInDelta = retain - (chars.length - i)\n const valueCharAtIndex = editor.getText(indexInDelta, 1)\n if (valueCharAtIndex !== char) {\n isMatch = false\n break\n }\n }\n } else {\n isMatch = false\n }\n\n if (isMatch) {\n // console.log('match!!!', chars)\n mentionMatch = chars\n break\n }\n }\n\n if (mentionMatch) {\n setMention({\n type: mentionMatch,\n retain: retain,\n })\n } else {\n setMention(null)\n setMentionSelectedIndex(0)\n }\n } else {\n // get full string between mention and new delta\n // This is where SEARCH is handled\n if (mention) {\n const retain = delta.ops[0].retain\n // if space is pressed, remove mention\n if (currentCharacter === ' ' || !retain) {\n setMention(null)\n setMentionSelectedIndex(0)\n return\n }\n\n let distanceMentionToRetain = retain - mention.retain\n if (!isDelete) distanceMentionToRetain++\n const mentionFull = editor.getText(mention.retain, distanceMentionToRetain)\n const mentionSearch = mentionFull.replace(mention.type.slice(-1), '')\n // check for space in mentionFull\n if (mentionFull.includes(' ')) {\n setMention(null)\n setMentionSelectedIndex(0)\n } else {\n setMention({\n ...mention,\n search: mentionSearch?.toLowerCase(),\n })\n }\n } else {\n // just deleting any text\n const quill = editorRef.current.getEditor()\n const currentSelection = quill.getSelection(false)\n const currentFormat = quill.getFormat(currentSelection?.index, currentSelection?.length)\n if (currentFormat.mention) {\n // if format is mention, delete the whole mention\n const [lineBlock] = quill.getLine(currentSelection.index - 1) || []\n const ops = lineBlock?.cache?.delta?.ops || []\n // get last op with attributes mention: true\n const lastMentionOp = ops.reverse().find((op: any) => op.attributes?.mention)\n if (lastMentionOp) {\n const mentionLength = lastMentionOp.insert.length\n quill.deleteText(currentSelection.index - mentionLength, mentionLength)\n }\n }\n }\n }\n }\n\n const addTextToEditor = (type: string) => {\n // get editor retain\n const quill = editorRef.current.getEditor()\n\n let retain = quill.getSelection(true)?.index || 0\n\n // get character at retain\n const currentCharacter = quill.getText(retain - 1, 1)\n\n // if the current character is a character, increment retain\n const addSpace = currentCharacter !== ' ' && currentCharacter\n if (addSpace) {\n quill.insertText(retain, ' ')\n retain++\n }\n\n // This is hack AF, but it works\n typeWithDelay(quill, retain, type)\n }\n\n const handleMentionButton = (type: string) => {\n // first check if mention is already open\n if (mention) {\n const { type, retain, search = '' } = mention\n\n const quill = editorRef.current.getEditor()\n const length = type.length + search.length\n const start = retain - type.length + 1\n // delete the mention\n quill.deleteText(start, length)\n }\n\n addTextToEditor(type)\n }\n\n const handleOpenClick = () => {\n if (isOpen || disabled) return\n\n onOpen && onOpen()\n }\n\n const handleClose = () => {\n // get editor value\n const editor = editorRef.current.getEditor()\n const text = editor.getText()\n if (text.length < 2 || isEditing) {\n setEditorValue('')\n }\n\n // always close editor\n onClose && onClose()\n }\n\n const handleFileUploaded = ({ file, data }: any) => {\n const newFile = {\n id: data.id,\n name: file.name,\n mime: file.type,\n size: file.size,\n order: files.length,\n }\n\n setFiles((prev) => [...prev, newFile])\n // remove from uploading\n setFilesUploading((prev) => prev.filter((uploading: any) => uploading.name !== file.name))\n\n return newFile\n }\n\n const handleFileRemove = (id: string, name: string, isAnnotation: boolean) => {\n if (isAnnotation) {\n // remove from annotations (if it's an annotation)\n removeAnnotation?.(id)\n } else {\n // remove file from files\n setFiles((prev) => prev.filter((file) => file.id !== id))\n // remove from uploading\n setFilesUploading((prev) => {\n return prev.filter((file: any) => file.name !== name)\n })\n }\n }\n\n const handleFileProgress = (e: any, file: any) => {\n const progress = Math.round((e.loaded * 100) / e.total)\n if (progress !== 100) {\n const uploadProgress = {\n name: file.name,\n progress,\n type: file.type,\n order: files.length + filesUploading.length,\n }\n\n // @ts-ignore\n setFilesUploading((prev) => {\n // replace or add new progress\n const newProgress = prev.filter((name: any) => name.name !== file.name)\n return [...newProgress, uploadProgress]\n })\n }\n }\n\n // when a file is not dropped onto the comment input\n const handleDrop = (e: React.DragEvent<HTMLDivElement>) => {\n setIsDropping(false)\n // upload file\n handleFileDrop(e, projectName, handleFileProgress, handleFileUploaded)\n }\n\n const handleDragOver = (e: React.DragEvent<HTMLDivElement>) => {\n e.preventDefault()\n e.stopPropagation()\n setIsDropping(true)\n }\n\n const uploadAnnotations = useAnnotationsUpload({\n projectName,\n onSuccess: handleFileUploaded,\n })\n\n const handleSubmit = async () => {\n try {\n setIsSubmitting(true)\n // upload any annotations first\n let annotationFiles = []\n if (annotations.length) {\n annotationFiles = await uploadAnnotations(annotations)\n }\n\n // convert to markdown\n const [markdown] = convertToMarkdown(editorValue)\n\n // remove img query params\n const markdownParsed = parseImages(markdown)\n\n const uploadedFiles = [...files, ...annotationFiles]\n\n if ((markdownParsed || uploadedFiles.length) && onSubmit) {\n try {\n await onSubmit(markdownParsed, uploadedFiles)\n // only clear if onSubmit is successful\n setEditorValue('')\n setFiles([])\n } catch (error) {\n // error is handled in rtk query mutation\n return\n }\n }\n } catch (error) {\n console.error(error)\n toast.error('Something went wrong')\n } finally {\n setIsSubmitting(false)\n }\n }\n\n const handleKeyDown = (e: React.KeyboardEvent<HTMLElement>) => {\n if (mention) {\n // close mention on escape\n if (e.key === 'Escape') {\n setMention(null)\n setMentionSelectedIndex(0)\n return\n }\n\n // add top search of mention\n if (mention && e.key === 'Tab') {\n // we handle this in the onChange\n }\n\n const arrowDirection = e.key === 'ArrowUp' ? -1 : e.key === 'ArrowDown' ? 1 : 0\n\n if (arrowDirection) {\n // navigate through mentions\n e.preventDefault()\n let newIndex = mentionSelectedIndex + arrowDirection\n if (newIndex < 0) newIndex = shownMentionOptions.length - 1\n if (newIndex >= shownMentionOptions.length) newIndex = 0\n setMentionSelectedIndex(newIndex)\n }\n\n if (e.key === 'Enter') {\n // we handle this in the onChange\n }\n }\n\n if (e.key === 'Enter' && (e.ctrlKey || e.metaKey)) {\n handleSubmit()\n }\n\n if (e.key === 'Escape') {\n handleClose()\n }\n }\n\n let quillMinHeight: number | undefined = isOpen ? initHeight + 41 : 44\n if (isEditing) quillMinHeight = undefined\n\n // QUILL CONFIG\n const modules = useMemo(\n () =>\n getModules({\n imageUploader: {\n projectName,\n onUpload: handleFileUploaded,\n onUploadProgress: handleFileProgress,\n },\n }),\n [projectName, setFiles, setFilesUploading],\n )\n\n const allFiles = [...annotations, ...(files || []), ...filesUploading].sort(\n (a, b) => a.order - b.order,\n )\n const compactGrid = allFiles.length > 6\n\n // disable version mentions for folders\n let mentionsError = null\n if (entities.length && entities[0].entityType === 'folder') {\n if (mention?.type === '@@') {\n mentionsError = 'Version mentions are disabled for folders'\n }\n }\n\n return (\n <>\n <Styled.AutoHeight\n className={clsx('comment-container', { isOpen, isEditing })}\n onDragOver={handleDragOver}\n onDragLeave={() => setIsDropping(false)}\n onDrop={handleDrop}\n onClick={() => setIsDropping(false)}\n onKeyDown={(e) => e.stopPropagation()}\n >\n <Styled.Comment\n className={clsx('block-shortcuts', {\n isOpen,\n isClosed: !isOpen || disabled,\n isEditing,\n isDropping,\n disabled,\n isLoading,\n isSubmitting,\n })}\n onKeyDown={handleKeyDown}\n onClick={handleOpenClick}\n >\n <Styled.Markdown ref={markdownRef}>\n {/* this is purely used to translate the markdown into html for Editor */}\n <InputMarkdownConvert typeOptions={mentionTypeOptions} initValue={initValue} />\n </Styled.Markdown>\n\n {/* file uploads */}\n {isOpen && (\n <FilesGrid\n files={allFiles}\n isCompact={compactGrid}\n onRemove={handleFileRemove}\n style={{ borderBottom: '1px solid var(--md-sys-color-outline-variant)' }}\n projectName={projectName}\n onAnnotationClick={goToAnnotation}\n />\n )}\n {isOpen && !disabled ? (\n <ReactQuill\n theme=\"snow\"\n style={{ minHeight: quillMinHeight, maxHeight: 300 }}\n ref={editorRef}\n value={editorValue}\n onChange={handleChange}\n readOnly={!isOpen}\n placeholder={'Comment or mention with @user, @@version, @@@task...'}\n modules={modules}\n formats={quillFormats}\n />\n ) : (\n <Styled.Placeholder>\n {disabled ? 'Commenting is disabled across multiple projects.' : 'Add a comment...'}\n </Styled.Placeholder>\n )}\n\n <Styled.Footer>\n <Styled.Buttons>\n {/* mention a user */}\n <Button\n icon=\"person\"\n variant=\"text\"\n onClick={() => handleMentionButton('@')}\n data-tooltip={'Mention user'}\n data-shortcut={'@'}\n />\n {/* mention a version */}\n <Button\n icon=\"layers\"\n variant=\"text\"\n onClick={() => handleMentionButton('@@')}\n data-tooltip={'Mention version'}\n data-shortcut={'@@'}\n />\n {/* mention a task */}\n <Button\n icon=\"check_circle\"\n variant=\"text\"\n onClick={() => handleMentionButton('@@@')}\n data-tooltip={'Mention task'}\n data-shortcut={'@@@'}\n />\n </Styled.Buttons>\n <Styled.Buttons>\n {isEditing && (\n <Button variant=\"text\" onClick={handleClose}>\n Cancel\n </Button>\n )}\n <SaveButton\n label={isEditing ? 'Save' : 'Comment'}\n className=\"comment\"\n active={!!editorValue || !!files.length}\n onClick={handleSubmit}\n disabled={isLoading}\n />\n </Styled.Buttons>\n </Styled.Footer>\n\n <Styled.Dropzone className={clsx({ show: isDropping && isOpen })}>\n <Icon icon=\"cloud_upload\" />\n </Styled.Dropzone>\n </Styled.Comment>\n <CommentMentionSelect\n mention={mention}\n options={shownMentionOptions}\n onChange={handleSelectChange}\n types={mentionTypes}\n z\n // @ts-ignore\n config={mentionTypeOptions[mention?.type]}\n noneFound={!shownMentionOptions.length && mention?.search}\n noneFoundAtAll={!shownMentionOptions.length && !mention?.search}\n selectedIndex={mentionSelectedIndex}\n // @ts-ignore\n error={mentionsError}\n />\n </Styled.AutoHeight>\n </>\n )\n}\n\nexport default CommentInput\n"],"names":["Quill","useFeedContext","useState","useAnnotationsSync","useRef","useEffect","_a","useMemo","mention","typeWithDelay","type","handleFileDrop","convertToMarkdown","parseImages","toast","getModules","jsx","Fragment","jsxs","Styled.AutoHeight","Styled.Comment","Styled.Markdown","quillFormats","Styled.Placeholder","Styled.Footer","Styled.Buttons","Button","SaveButton","Styled.Dropzone","Icon"],"mappings":"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"}
1
+ {"version":3,"file":"CommentInput.cjs.js","sources":["../../../../../../../src/containers/Feed/components/CommentInput/CommentInput.tsx"],"sourcesContent":["// React and related hooks\nimport React, { FC, useEffect, useMemo, useRef, useState } from 'react'\n\n// Third-party libraries\nimport clsx from 'clsx'\nimport { toast } from 'react-toastify'\nimport ReactQuill, { Quill } from 'react-quill-ayon'\n\n// Components\nimport { Button, Icon, SaveButton } from '@ynput/ayon-react-components'\nimport CommentMentionSelect from '../CommentMentionSelect/CommentMentionSelect'\nimport InputMarkdownConvert from './InputMarkdownConvert'\nimport FilesGrid from '../FilesGrid'\n\n// Styled components\nimport * as Styled from './CommentInput.styled'\n\n// Helpers and utilities\nimport getMentionOptions from '../../mentionHelpers/getMentionOptions'\nimport getMentionUsers from '../../mentionHelpers/getMentionUsers'\nimport getMentionTasks from '../../mentionHelpers/getMentionTasks'\nimport getMentionVersions from '../../mentionHelpers/getMentionVersions'\nimport { convertToMarkdown } from './quillToMarkdown'\nimport { handleFileDrop, parseImages, typeWithDelay } from './helpers'\nimport { getModules, quillFormats } from './modules'\n\n// Hooks\nimport useInitialValue from './hooks/useInitialValue'\nimport useSetCursorEnd from './hooks/useSetCursorEnd'\nimport useMentionLink from './hooks/useMentionLink'\nimport useAnnotationsSync from './hooks/useAnnotationsSync'\n\n// State management\nimport useAnnotationsUpload from './hooks/useAnnotationsUpload'\nimport { useFeedContext } from '../../context/FeedContext'\n\nvar Delta = Quill.import('delta')\n\nconst mentionTypes = ['@', '@@', '@@@']\nexport const mentionTypeOptions = {\n '@@@': {\n id: 'task',\n },\n '@@': {\n id: 'version',\n },\n '@': {\n id: 'user',\n isCircle: true,\n },\n}\n\ninterface CommentInputProps {\n initValue: string | null\n initFiles?: any[]\n onSubmit: (markdown: string, files: any[]) => Promise<void>\n isEditing?: boolean\n disabled?: boolean\n isLoading?: boolean\n isOpen: boolean\n onOpen?: () => void\n onClose?: () => void\n}\n\nconst CommentInput: FC<CommentInputProps> = ({\n initValue,\n initFiles = [],\n onSubmit,\n isEditing,\n disabled,\n isLoading,\n isOpen,\n onOpen,\n onClose,\n}) => {\n const { projectName, entities, projectInfo, scope, currentTab, mentionSuggestionsData } =\n useFeedContext()\n\n const {\n users: mentionUsers,\n versions: mentionVersions,\n tasks: mentionTasks,\n } = mentionSuggestionsData || {}\n\n const [initHeight, setInitHeight] = useState(88)\n const [editorValue, setEditorValue] = useState('')\n // file uploads\n const [files, setFiles] = useState(initFiles)\n const [filesUploading, setFilesUploading] = useState([])\n const [isDropping, setIsDropping] = useState(false)\n const [isSubmitting, setIsSubmitting] = useState(false)\n\n const { annotations, removeAnnotation, goToAnnotation } = useAnnotationsSync({\n entityId: entities[0]?.id,\n filesUploading,\n })\n\n // MENTION STATES\n const [mention, setMention] = useState<null | any>(null)\n const [mentionSelectedIndex, setMentionSelectedIndex] = useState(0)\n // REFS\n const editorRef = useRef<any>(null)\n const markdownRef = useRef<HTMLDivElement>(null)\n\n // if there is an initial value, set it so the editor is prefilled\n useInitialValue({\n markdownRef,\n initValue,\n setEditorValue,\n setInitHeight,\n isOpen: isOpen,\n filter: currentTab,\n })\n\n // When editing, set selection to the end of the editor\n useSetCursorEnd({ initHeight, editorRef, isEditing })\n // create a new quill format for mentions and registers it\n useMentionLink({ projectName })\n\n // focus on editor when opened\n useEffect(() => {\n if (isOpen) {\n editorRef.current?.getEditor()?.enable()\n // block autofocus if opened from an annotation\n if (annotations.length > 0 && files.length === 0) {\n return\n }\n\n editorRef.current?.focus()\n }\n // We don't set annotations or files as useEffect dependencies, because we don't want to focus\n // the input if it's already open but annotations change (e.g. are removed).\n }, [isOpen, editorRef])\n\n mentionTypes.sort((a, b) => b.length - a.length)\n\n const mentionOptions = useMemo(\n () =>\n getMentionOptions(\n mention?.type,\n {\n '@': () => getMentionUsers(mentionUsers),\n '@@': () => getMentionVersions(mentionVersions),\n '@@@': () => getMentionTasks(mentionTasks, projectInfo.taskTypes),\n },\n mention?.search,\n ),\n [mentionTasks, mentionVersions, mentionUsers, mention?.type, mention?.search],\n )\n\n // show first 5 and filter itself out\n const shownMentionOptions = mentionOptions.slice(0, 5)\n\n // triggered when a mention is selected\n const [newSelection, setNewSelection] = useState<null | number>()\n\n useEffect(() => {\n if (newSelection) {\n setNewSelection(null)\n // now we set selection to the end of the mention\n const quill = editorRef.current.getEditor()\n quill.setSelection(newSelection)\n }\n }, [newSelection])\n\n const handleSelectMention = (selectedOption: any) => {\n // get option text\n const quill = editorRef.current.getEditor()\n\n const typePrefix = mention.type // the type of mention: @, @@, @@@\n const search = typePrefix + (mention.search || '') // the full search string: @Tim\n const mentionLabel = typePrefix + selectedOption.label // the label of the mention: @Tim Bailey\n // @ts-expect-error\n const type = mentionTypeOptions[typePrefix] // the type of mention: user, version, task\n const href = `${type?.id}:${selectedOption.id}` // the href of the mention: user:user.123\n\n // get selection delta\n const selection = quill.getSelection(true)\n const selectionIndex = selection?.index || 0\n const startIndex = selectionIndex - search.length // the start index of the search\n\n // first delete the search string\n quill.deleteText(startIndex, search.length)\n\n // insert embed link\n quill.insertText(startIndex, mentionLabel, 'mention', href)\n\n const endIndex = startIndex + mentionLabel.length\n\n // insert a space after the mention\n quill.updateContents(new Delta().retain(endIndex).insert(' '))\n\n // remove single \\n after mention\n quill.updateContents(new Delta().retain(endIndex + 1).delete(1))\n\n // set selection to the end of the mention + 1\n setNewSelection(endIndex + 1)\n\n // reset mention state\n setMention(null)\n setMentionSelectedIndex(0)\n }\n\n const handleSelectChange = (option: any) => {\n handleSelectMention(option)\n }\n\n const handleChange = (content: string, delta: any, _: any, editor: any) => {\n let currentCharacter =\n (delta.ops[0] && delta.ops[0].insert) || (delta.ops[1] && delta.ops[1].insert)\n\n const tabOrEnter = currentCharacter === '\\n' || currentCharacter === '\\t'\n // find the first option\n const selectedOption = mentionOptions[mentionSelectedIndex]\n\n if (mention && tabOrEnter && selectedOption) {\n // get option text\n const retain = (delta.ops[0] && delta.ops[0].retain) || 0\n // prevent default\n\n // @ts-ignore\n handleSelectMention(selectedOption, retain)\n\n return\n }\n\n setEditorValue(content)\n\n const isDelete = delta.ops.length === 2 && !!delta.ops[1].delete\n\n if (!currentCharacter && isDelete) {\n currentCharacter = editor.getText(delta.ops[0].retain - 1, 1)\n }\n\n const isMention = mentionTypes.includes(currentCharacter)\n\n if (isMention) {\n const mentionIndex = delta.ops.findIndex((op: any) => 'insert' in op || 'delete' in op)\n const mention = currentCharacter\n let retain = mentionIndex === 0 ? 0 : delta.ops[mentionIndex - 1].retain\n if (isDelete) retain = retain - 1\n\n // for each mention denotation char, check if it is a mention\n // sort by length of mention denotation char\n let mentionMatch = null\n\n // loop through each mention denotation char, with longest first. First one to match is the one we want\n for (const chars of mentionTypes) {\n let isMatch = true\n // start with the last character\n if (chars.endsWith(mention)) {\n // loop through the chars backwards\n for (let i = chars.length - 1; i >= 0; i--) {\n // skip first character as that's already been checked\n if (i === 0) continue\n const char = chars[i - 1]\n const indexInDelta = retain - (chars.length - i)\n const valueCharAtIndex = editor.getText(indexInDelta, 1)\n if (valueCharAtIndex !== char) {\n isMatch = false\n break\n }\n }\n } else {\n isMatch = false\n }\n\n if (isMatch) {\n // console.log('match!!!', chars)\n mentionMatch = chars\n break\n }\n }\n\n if (mentionMatch) {\n setMention({\n type: mentionMatch,\n retain: retain,\n })\n } else {\n setMention(null)\n setMentionSelectedIndex(0)\n }\n } else {\n // get full string between mention and new delta\n // This is where SEARCH is handled\n if (mention) {\n const retain = delta.ops[0].retain\n // if space is pressed, remove mention\n if (currentCharacter === ' ' || !retain) {\n setMention(null)\n setMentionSelectedIndex(0)\n return\n }\n\n let distanceMentionToRetain = retain - mention.retain\n if (!isDelete) distanceMentionToRetain++\n const mentionFull = editor.getText(mention.retain, distanceMentionToRetain)\n const mentionSearch = mentionFull.replace(mention.type.slice(-1), '')\n // check for space in mentionFull\n if (mentionFull.includes(' ')) {\n setMention(null)\n setMentionSelectedIndex(0)\n } else {\n setMention({\n ...mention,\n search: mentionSearch?.toLowerCase(),\n })\n }\n } else {\n // just deleting any text\n const quill = editorRef.current.getEditor()\n const currentSelection = quill.getSelection(false)\n const currentFormat = quill.getFormat(currentSelection?.index, currentSelection?.length)\n if (currentFormat.mention) {\n // if format is mention, delete the whole mention\n const [lineBlock] = quill.getLine(currentSelection.index - 1) || []\n const ops = lineBlock?.cache?.delta?.ops || []\n // get last op with attributes mention: true\n const lastMentionOp = ops.reverse().find((op: any) => op.attributes?.mention)\n if (lastMentionOp) {\n const mentionLength = lastMentionOp.insert.length\n quill.deleteText(currentSelection.index - mentionLength, mentionLength)\n }\n }\n }\n }\n }\n\n const addTextToEditor = (type: string) => {\n // get editor retain\n const quill = editorRef.current.getEditor()\n\n let retain = quill.getSelection(true)?.index || 0\n\n // get character at retain\n const currentCharacter = quill.getText(retain - 1, 1)\n\n // if the current character is a character, increment retain\n const addSpace = currentCharacter !== ' ' && currentCharacter\n if (addSpace) {\n quill.insertText(retain, ' ')\n retain++\n }\n\n // This is hack AF, but it works\n typeWithDelay(quill, retain, type)\n }\n\n const handleMentionButton = (type: string) => {\n // first check if mention is already open\n if (mention) {\n const { type, retain, search = '' } = mention\n\n const quill = editorRef.current.getEditor()\n const length = type.length + search.length\n const start = retain - type.length + 1\n // delete the mention\n quill.deleteText(start, length)\n }\n\n addTextToEditor(type)\n }\n\n const handleOpenClick = () => {\n if (isOpen || disabled) return\n\n onOpen && onOpen()\n }\n\n const handleClose = () => {\n // get editor value\n const editor = editorRef.current.getEditor()\n const text = editor.getText()\n if (text.length < 2 || isEditing) {\n setEditorValue('')\n }\n\n // always close editor\n onClose && onClose()\n }\n\n const handleFileUploaded = ({ file, data }: any) => {\n const newFile = {\n id: data.id,\n name: file.name,\n mime: file.type,\n size: file.size,\n order: files.length,\n }\n\n setFiles((prev) => [...prev, newFile])\n // remove from uploading\n setFilesUploading((prev) => prev.filter((uploading: any) => uploading.name !== file.name))\n\n return newFile\n }\n\n const handleFileRemove = (id: string, name: string, isAnnotation: boolean) => {\n if (isAnnotation) {\n // remove from annotations (if it's an annotation)\n removeAnnotation?.(id)\n } else {\n // remove file from files\n setFiles((prev) => prev.filter((file) => file.id !== id))\n // remove from uploading\n setFilesUploading((prev) => {\n return prev.filter((file: any) => file.name !== name)\n })\n }\n }\n\n const handleFileProgress = (e: any, file: any) => {\n const progress = Math.round((e.loaded * 100) / e.total)\n if (progress !== 100) {\n const uploadProgress = {\n name: file.name,\n progress,\n type: file.type,\n order: files.length + filesUploading.length,\n }\n\n // @ts-ignore\n setFilesUploading((prev) => {\n // replace or add new progress\n const newProgress = prev.filter((name: any) => name.name !== file.name)\n return [...newProgress, uploadProgress]\n })\n }\n }\n\n // when a file is not dropped onto the comment input\n const handleDrop = (e: React.DragEvent<HTMLDivElement>) => {\n setIsDropping(false)\n // upload file\n handleFileDrop(e, projectName, handleFileProgress, handleFileUploaded)\n }\n\n const handleDragOver = (e: React.DragEvent<HTMLDivElement>) => {\n e.preventDefault()\n e.stopPropagation()\n setIsDropping(true)\n }\n\n const uploadAnnotations = useAnnotationsUpload({\n projectName,\n onSuccess: handleFileUploaded,\n })\n\n const handleSubmit = async () => {\n try {\n setIsSubmitting(true)\n // upload any annotations first\n let annotationFiles = []\n if (annotations.length) {\n annotationFiles = await uploadAnnotations(annotations)\n }\n\n // convert to markdown\n const [markdown] = convertToMarkdown(editorValue)\n\n // remove img query params\n const markdownParsed = parseImages(markdown)\n\n const uploadedFiles = [...files, ...annotationFiles]\n\n if ((markdownParsed || uploadedFiles.length) && onSubmit) {\n try {\n await onSubmit(markdownParsed, uploadedFiles)\n // only clear if onSubmit is successful\n setEditorValue('')\n setFiles([])\n } catch (error) {\n // error is handled in rtk query mutation\n return\n }\n }\n } catch (error) {\n console.error(error)\n toast.error('Something went wrong')\n } finally {\n setIsSubmitting(false)\n }\n }\n\n const handleKeyDown = (e: React.KeyboardEvent<HTMLElement>) => {\n if (mention) {\n // close mention on escape\n if (e.key === 'Escape') {\n setMention(null)\n setMentionSelectedIndex(0)\n return\n }\n\n // add top search of mention\n if (mention && e.key === 'Tab') {\n // we handle this in the onChange\n }\n\n const arrowDirection = e.key === 'ArrowUp' ? -1 : e.key === 'ArrowDown' ? 1 : 0\n\n if (arrowDirection) {\n // navigate through mentions\n e.preventDefault()\n let newIndex = mentionSelectedIndex + arrowDirection\n if (newIndex < 0) newIndex = shownMentionOptions.length - 1\n if (newIndex >= shownMentionOptions.length) newIndex = 0\n setMentionSelectedIndex(newIndex)\n }\n\n if (e.key === 'Enter') {\n // we handle this in the onChange\n }\n }\n\n if (e.key === 'Enter' && (e.ctrlKey || e.metaKey)) {\n handleSubmit()\n }\n\n if (e.key === 'Escape') {\n handleClose()\n }\n }\n\n let quillMinHeight: number | undefined = isOpen ? initHeight + 41 : 44\n if (isEditing) quillMinHeight = undefined\n\n // QUILL CONFIG\n const modules = useMemo(\n () =>\n getModules({\n imageUploader: {\n projectName,\n onUpload: handleFileUploaded,\n onUploadProgress: handleFileProgress,\n },\n }),\n [projectName, setFiles, setFilesUploading],\n )\n\n const allFiles = [...annotations, ...(files || []), ...filesUploading].sort(\n (a, b) => a.order - b.order,\n )\n const compactGrid = allFiles.length > 6\n\n // disable version mentions for folders\n let mentionsError = null\n if (entities.length && entities[0].entityType === 'folder') {\n if (mention?.type === '@@') {\n mentionsError = 'Version mentions are disabled for folders'\n }\n }\n\n return (\n <>\n <Styled.AutoHeight\n className={clsx('comment-container', { isOpen, isEditing })}\n onDragOver={handleDragOver}\n onDragLeave={() => setIsDropping(false)}\n onDrop={handleDrop}\n onClick={() => setIsDropping(false)}\n onKeyDown={(e) => e.stopPropagation()}\n >\n <Styled.Comment\n className={clsx('block-shortcuts', {\n isOpen,\n isClosed: !isOpen || disabled,\n isEditing,\n isDropping,\n disabled,\n isLoading,\n isSubmitting,\n })}\n onKeyDown={handleKeyDown}\n onClick={handleOpenClick}\n >\n <Styled.Markdown ref={markdownRef}>\n {/* this is purely used to translate the markdown into html for Editor */}\n <InputMarkdownConvert typeOptions={mentionTypeOptions} initValue={initValue} />\n </Styled.Markdown>\n\n {/* file uploads */}\n {isOpen && (\n <FilesGrid\n files={allFiles}\n isCompact={compactGrid}\n onRemove={handleFileRemove}\n style={{ borderBottom: '1px solid var(--md-sys-color-outline-variant)' }}\n projectName={projectName}\n onAnnotationClick={goToAnnotation}\n />\n )}\n {isOpen && !disabled ? (\n <ReactQuill\n theme=\"snow\"\n style={{ minHeight: quillMinHeight, maxHeight: 300 }}\n ref={editorRef}\n value={editorValue}\n onChange={handleChange}\n readOnly={!isOpen}\n placeholder={'Comment or mention with @user, @@version, @@@task...'}\n modules={modules}\n formats={quillFormats}\n />\n ) : (\n <Styled.Placeholder>\n {disabled ? 'Commenting is disabled across multiple projects.' : 'Add a comment...'}\n </Styled.Placeholder>\n )}\n\n <Styled.Footer>\n <Styled.Buttons>\n {/* mention a user */}\n <Button\n icon=\"person\"\n variant=\"text\"\n onClick={() => handleMentionButton('@')}\n data-tooltip={'Mention user'}\n data-shortcut={'@'}\n />\n {/* mention a version */}\n <Button\n icon=\"layers\"\n variant=\"text\"\n onClick={() => handleMentionButton('@@')}\n data-tooltip={'Mention version'}\n data-shortcut={'@@'}\n />\n {/* mention a task */}\n <Button\n icon=\"check_circle\"\n variant=\"text\"\n onClick={() => handleMentionButton('@@@')}\n data-tooltip={'Mention task'}\n data-shortcut={'@@@'}\n />\n </Styled.Buttons>\n <Styled.Buttons>\n {isEditing && (\n <Button variant=\"text\" onClick={handleClose}>\n Cancel\n </Button>\n )}\n <SaveButton\n label={isEditing ? 'Save' : 'Comment'}\n className=\"comment\"\n active={!!editorValue || !!files.length}\n onClick={handleSubmit}\n disabled={isLoading}\n />\n </Styled.Buttons>\n </Styled.Footer>\n\n <Styled.Dropzone className={clsx({ show: isDropping && isOpen })}>\n <Icon icon=\"cloud_upload\" />\n </Styled.Dropzone>\n </Styled.Comment>\n <CommentMentionSelect\n mention={mention}\n options={shownMentionOptions}\n onChange={handleSelectChange}\n types={mentionTypes}\n z\n // @ts-ignore\n config={mentionTypeOptions[mention?.type]}\n noneFound={!shownMentionOptions.length && mention?.search}\n noneFoundAtAll={!shownMentionOptions.length && !mention?.search}\n selectedIndex={mentionSelectedIndex}\n // @ts-ignore\n error={mentionsError}\n />\n </Styled.AutoHeight>\n </>\n )\n}\n\nexport default CommentInput\n"],"names":["Quill","useFeedContext","useState","useAnnotationsSync","useRef","useEffect","_a","useMemo","mention","typeWithDelay","type","handleFileDrop","convertToMarkdown","parseImages","toast","getModules","jsx","Fragment","jsxs","Styled.AutoHeight","Styled.Comment","Styled.Markdown","quillFormats","Styled.Placeholder","Styled.Footer","Styled.Buttons","Button","SaveButton","Styled.Dropzone","Icon"],"mappings":"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"}
@@ -81,10 +81,12 @@ const CommentInput = ({
81
81
  var _a2, _b, _c;
82
82
  if (isOpen) {
83
83
  (_b = (_a2 = editorRef.current) == null ? void 0 : _a2.getEditor()) == null ? void 0 : _b.enable();
84
- const blockAutoFocus = !!annotations.length && files.length === 0;
85
- !blockAutoFocus && ((_c = editorRef.current) == null ? void 0 : _c.focus());
84
+ if (annotations.length > 0 && files.length === 0) {
85
+ return;
86
+ }
87
+ (_c = editorRef.current) == null ? void 0 : _c.focus();
86
88
  }
87
- }, [isOpen, editorRef, annotations, files]);
89
+ }, [isOpen, editorRef]);
88
90
  mentionTypes.sort((a, b) => b.length - a.length);
89
91
  const mentionOptions = useMemo(
90
92
  () => getMentionOptions(
@@ -1 +1 @@
1
- {"version":3,"file":"CommentInput.es.js","sources":["../../../../../../../src/containers/Feed/components/CommentInput/CommentInput.tsx"],"sourcesContent":["// React and related hooks\nimport React, { FC, useEffect, useMemo, useRef, useState } from 'react'\n\n// Third-party libraries\nimport clsx from 'clsx'\nimport { toast } from 'react-toastify'\nimport ReactQuill, { Quill } from 'react-quill-ayon'\n\n// Components\nimport { Button, Icon, SaveButton } from '@ynput/ayon-react-components'\nimport CommentMentionSelect from '../CommentMentionSelect/CommentMentionSelect'\nimport InputMarkdownConvert from './InputMarkdownConvert'\nimport FilesGrid from '../FilesGrid'\n\n// Styled components\nimport * as Styled from './CommentInput.styled'\n\n// Helpers and utilities\nimport getMentionOptions from '../../mentionHelpers/getMentionOptions'\nimport getMentionUsers from '../../mentionHelpers/getMentionUsers'\nimport getMentionTasks from '../../mentionHelpers/getMentionTasks'\nimport getMentionVersions from '../../mentionHelpers/getMentionVersions'\nimport { convertToMarkdown } from './quillToMarkdown'\nimport { handleFileDrop, parseImages, typeWithDelay } from './helpers'\nimport { getModules, quillFormats } from './modules'\n\n// Hooks\nimport useInitialValue from './hooks/useInitialValue'\nimport useSetCursorEnd from './hooks/useSetCursorEnd'\nimport useMentionLink from './hooks/useMentionLink'\nimport useAnnotationsSync from './hooks/useAnnotationsSync'\n\n// State management\nimport useAnnotationsUpload from './hooks/useAnnotationsUpload'\nimport { useFeedContext } from '../../context/FeedContext'\n\nvar Delta = Quill.import('delta')\n\nconst mentionTypes = ['@', '@@', '@@@']\nexport const mentionTypeOptions = {\n '@@@': {\n id: 'task',\n },\n '@@': {\n id: 'version',\n },\n '@': {\n id: 'user',\n isCircle: true,\n },\n}\n\ninterface CommentInputProps {\n initValue: string | null\n initFiles?: any[]\n onSubmit: (markdown: string, files: any[]) => Promise<void>\n isEditing?: boolean\n disabled?: boolean\n isLoading?: boolean\n isOpen: boolean\n onOpen?: () => void\n onClose?: () => void\n}\n\nconst CommentInput: FC<CommentInputProps> = ({\n initValue,\n initFiles = [],\n onSubmit,\n isEditing,\n disabled,\n isLoading,\n isOpen,\n onOpen,\n onClose,\n}) => {\n const { projectName, entities, projectInfo, scope, currentTab, mentionSuggestionsData } =\n useFeedContext()\n\n const {\n users: mentionUsers,\n versions: mentionVersions,\n tasks: mentionTasks,\n } = mentionSuggestionsData || {}\n\n const [initHeight, setInitHeight] = useState(88)\n const [editorValue, setEditorValue] = useState('')\n // file uploads\n const [files, setFiles] = useState(initFiles)\n const [filesUploading, setFilesUploading] = useState([])\n const [isDropping, setIsDropping] = useState(false)\n const [isSubmitting, setIsSubmitting] = useState(false)\n\n const { annotations, removeAnnotation, goToAnnotation } = useAnnotationsSync({\n entityId: entities[0]?.id,\n filesUploading,\n })\n\n // MENTION STATES\n const [mention, setMention] = useState<null | any>(null)\n const [mentionSelectedIndex, setMentionSelectedIndex] = useState(0)\n // REFS\n const editorRef = useRef<any>(null)\n const markdownRef = useRef<HTMLDivElement>(null)\n\n // if there is an initial value, set it so the editor is prefilled\n useInitialValue({\n markdownRef,\n initValue,\n setEditorValue,\n setInitHeight,\n isOpen: isOpen,\n filter: currentTab,\n })\n\n // When editing, set selection to the end of the editor\n useSetCursorEnd({ initHeight, editorRef, isEditing })\n // create a new quill format for mentions and registers it\n useMentionLink({ projectName })\n\n // focus on editor when opened\n useEffect(() => {\n if (isOpen) {\n editorRef.current?.getEditor()?.enable()\n // block autofocus if opened from an annotation\n const blockAutoFocus = !!annotations.length && files.length === 0\n !blockAutoFocus && editorRef.current?.focus()\n }\n }, [isOpen, editorRef, annotations, files])\n\n mentionTypes.sort((a, b) => b.length - a.length)\n\n const mentionOptions = useMemo(\n () =>\n getMentionOptions(\n mention?.type,\n {\n '@': () => getMentionUsers(mentionUsers),\n '@@': () => getMentionVersions(mentionVersions),\n '@@@': () => getMentionTasks(mentionTasks, projectInfo.taskTypes),\n },\n mention?.search,\n ),\n [mentionTasks, mentionVersions, mentionUsers, mention?.type, mention?.search],\n )\n\n // show first 5 and filter itself out\n const shownMentionOptions = mentionOptions.slice(0, 5)\n\n // triggered when a mention is selected\n const [newSelection, setNewSelection] = useState<null | number>()\n\n useEffect(() => {\n if (newSelection) {\n setNewSelection(null)\n // now we set selection to the end of the mention\n const quill = editorRef.current.getEditor()\n quill.setSelection(newSelection)\n }\n }, [newSelection])\n\n const handleSelectMention = (selectedOption: any) => {\n // get option text\n const quill = editorRef.current.getEditor()\n\n const typePrefix = mention.type // the type of mention: @, @@, @@@\n const search = typePrefix + (mention.search || '') // the full search string: @Tim\n const mentionLabel = typePrefix + selectedOption.label // the label of the mention: @Tim Bailey\n // @ts-expect-error\n const type = mentionTypeOptions[typePrefix] // the type of mention: user, version, task\n const href = `${type?.id}:${selectedOption.id}` // the href of the mention: user:user.123\n\n // get selection delta\n const selection = quill.getSelection(true)\n const selectionIndex = selection?.index || 0\n const startIndex = selectionIndex - search.length // the start index of the search\n\n // first delete the search string\n quill.deleteText(startIndex, search.length)\n\n // insert embed link\n quill.insertText(startIndex, mentionLabel, 'mention', href)\n\n const endIndex = startIndex + mentionLabel.length\n\n // insert a space after the mention\n quill.updateContents(new Delta().retain(endIndex).insert(' '))\n\n // remove single \\n after mention\n quill.updateContents(new Delta().retain(endIndex + 1).delete(1))\n\n // set selection to the end of the mention + 1\n setNewSelection(endIndex + 1)\n\n // reset mention state\n setMention(null)\n setMentionSelectedIndex(0)\n }\n\n const handleSelectChange = (option: any) => {\n handleSelectMention(option)\n }\n\n const handleChange = (content: string, delta: any, _: any, editor: any) => {\n let currentCharacter =\n (delta.ops[0] && delta.ops[0].insert) || (delta.ops[1] && delta.ops[1].insert)\n\n const tabOrEnter = currentCharacter === '\\n' || currentCharacter === '\\t'\n // find the first option\n const selectedOption = mentionOptions[mentionSelectedIndex]\n\n if (mention && tabOrEnter && selectedOption) {\n // get option text\n const retain = (delta.ops[0] && delta.ops[0].retain) || 0\n // prevent default\n\n // @ts-ignore\n handleSelectMention(selectedOption, retain)\n\n return\n }\n\n setEditorValue(content)\n\n const isDelete = delta.ops.length === 2 && !!delta.ops[1].delete\n\n if (!currentCharacter && isDelete) {\n currentCharacter = editor.getText(delta.ops[0].retain - 1, 1)\n }\n\n const isMention = mentionTypes.includes(currentCharacter)\n\n if (isMention) {\n const mentionIndex = delta.ops.findIndex((op: any) => 'insert' in op || 'delete' in op)\n const mention = currentCharacter\n let retain = mentionIndex === 0 ? 0 : delta.ops[mentionIndex - 1].retain\n if (isDelete) retain = retain - 1\n\n // for each mention denotation char, check if it is a mention\n // sort by length of mention denotation char\n let mentionMatch = null\n\n // loop through each mention denotation char, with longest first. First one to match is the one we want\n for (const chars of mentionTypes) {\n let isMatch = true\n // start with the last character\n if (chars.endsWith(mention)) {\n // loop through the chars backwards\n for (let i = chars.length - 1; i >= 0; i--) {\n // skip first character as that's already been checked\n if (i === 0) continue\n const char = chars[i - 1]\n const indexInDelta = retain - (chars.length - i)\n const valueCharAtIndex = editor.getText(indexInDelta, 1)\n if (valueCharAtIndex !== char) {\n isMatch = false\n break\n }\n }\n } else {\n isMatch = false\n }\n\n if (isMatch) {\n // console.log('match!!!', chars)\n mentionMatch = chars\n break\n }\n }\n\n if (mentionMatch) {\n setMention({\n type: mentionMatch,\n retain: retain,\n })\n } else {\n setMention(null)\n setMentionSelectedIndex(0)\n }\n } else {\n // get full string between mention and new delta\n // This is where SEARCH is handled\n if (mention) {\n const retain = delta.ops[0].retain\n // if space is pressed, remove mention\n if (currentCharacter === ' ' || !retain) {\n setMention(null)\n setMentionSelectedIndex(0)\n return\n }\n\n let distanceMentionToRetain = retain - mention.retain\n if (!isDelete) distanceMentionToRetain++\n const mentionFull = editor.getText(mention.retain, distanceMentionToRetain)\n const mentionSearch = mentionFull.replace(mention.type.slice(-1), '')\n // check for space in mentionFull\n if (mentionFull.includes(' ')) {\n setMention(null)\n setMentionSelectedIndex(0)\n } else {\n setMention({\n ...mention,\n search: mentionSearch?.toLowerCase(),\n })\n }\n } else {\n // just deleting any text\n const quill = editorRef.current.getEditor()\n const currentSelection = quill.getSelection(false)\n const currentFormat = quill.getFormat(currentSelection?.index, currentSelection?.length)\n if (currentFormat.mention) {\n // if format is mention, delete the whole mention\n const [lineBlock] = quill.getLine(currentSelection.index - 1) || []\n const ops = lineBlock?.cache?.delta?.ops || []\n // get last op with attributes mention: true\n const lastMentionOp = ops.reverse().find((op: any) => op.attributes?.mention)\n if (lastMentionOp) {\n const mentionLength = lastMentionOp.insert.length\n quill.deleteText(currentSelection.index - mentionLength, mentionLength)\n }\n }\n }\n }\n }\n\n const addTextToEditor = (type: string) => {\n // get editor retain\n const quill = editorRef.current.getEditor()\n\n let retain = quill.getSelection(true)?.index || 0\n\n // get character at retain\n const currentCharacter = quill.getText(retain - 1, 1)\n\n // if the current character is a character, increment retain\n const addSpace = currentCharacter !== ' ' && currentCharacter\n if (addSpace) {\n quill.insertText(retain, ' ')\n retain++\n }\n\n // This is hack AF, but it works\n typeWithDelay(quill, retain, type)\n }\n\n const handleMentionButton = (type: string) => {\n // first check if mention is already open\n if (mention) {\n const { type, retain, search = '' } = mention\n\n const quill = editorRef.current.getEditor()\n const length = type.length + search.length\n const start = retain - type.length + 1\n // delete the mention\n quill.deleteText(start, length)\n }\n\n addTextToEditor(type)\n }\n\n const handleOpenClick = () => {\n if (isOpen || disabled) return\n\n onOpen && onOpen()\n }\n\n const handleClose = () => {\n // get editor value\n const editor = editorRef.current.getEditor()\n const text = editor.getText()\n if (text.length < 2 || isEditing) {\n setEditorValue('')\n }\n\n // always close editor\n onClose && onClose()\n }\n\n const handleFileUploaded = ({ file, data }: any) => {\n const newFile = {\n id: data.id,\n name: file.name,\n mime: file.type,\n size: file.size,\n order: files.length,\n }\n\n setFiles((prev) => [...prev, newFile])\n // remove from uploading\n setFilesUploading((prev) => prev.filter((uploading: any) => uploading.name !== file.name))\n\n return newFile\n }\n\n const handleFileRemove = (id: string, name: string, isAnnotation: boolean) => {\n if (isAnnotation) {\n // remove from annotations (if it's an annotation)\n removeAnnotation?.(id)\n } else {\n // remove file from files\n setFiles((prev) => prev.filter((file) => file.id !== id))\n // remove from uploading\n setFilesUploading((prev) => {\n return prev.filter((file: any) => file.name !== name)\n })\n }\n }\n\n const handleFileProgress = (e: any, file: any) => {\n const progress = Math.round((e.loaded * 100) / e.total)\n if (progress !== 100) {\n const uploadProgress = {\n name: file.name,\n progress,\n type: file.type,\n order: files.length + filesUploading.length,\n }\n\n // @ts-ignore\n setFilesUploading((prev) => {\n // replace or add new progress\n const newProgress = prev.filter((name: any) => name.name !== file.name)\n return [...newProgress, uploadProgress]\n })\n }\n }\n\n // when a file is not dropped onto the comment input\n const handleDrop = (e: React.DragEvent<HTMLDivElement>) => {\n setIsDropping(false)\n // upload file\n handleFileDrop(e, projectName, handleFileProgress, handleFileUploaded)\n }\n\n const handleDragOver = (e: React.DragEvent<HTMLDivElement>) => {\n e.preventDefault()\n e.stopPropagation()\n setIsDropping(true)\n }\n\n const uploadAnnotations = useAnnotationsUpload({\n projectName,\n onSuccess: handleFileUploaded,\n })\n\n const handleSubmit = async () => {\n try {\n setIsSubmitting(true)\n // upload any annotations first\n let annotationFiles = []\n if (annotations.length) {\n annotationFiles = await uploadAnnotations(annotations)\n }\n\n // convert to markdown\n const [markdown] = convertToMarkdown(editorValue)\n\n // remove img query params\n const markdownParsed = parseImages(markdown)\n\n const uploadedFiles = [...files, ...annotationFiles]\n\n if ((markdownParsed || uploadedFiles.length) && onSubmit) {\n try {\n await onSubmit(markdownParsed, uploadedFiles)\n // only clear if onSubmit is successful\n setEditorValue('')\n setFiles([])\n } catch (error) {\n // error is handled in rtk query mutation\n return\n }\n }\n } catch (error) {\n console.error(error)\n toast.error('Something went wrong')\n } finally {\n setIsSubmitting(false)\n }\n }\n\n const handleKeyDown = (e: React.KeyboardEvent<HTMLElement>) => {\n if (mention) {\n // close mention on escape\n if (e.key === 'Escape') {\n setMention(null)\n setMentionSelectedIndex(0)\n return\n }\n\n // add top search of mention\n if (mention && e.key === 'Tab') {\n // we handle this in the onChange\n }\n\n const arrowDirection = e.key === 'ArrowUp' ? -1 : e.key === 'ArrowDown' ? 1 : 0\n\n if (arrowDirection) {\n // navigate through mentions\n e.preventDefault()\n let newIndex = mentionSelectedIndex + arrowDirection\n if (newIndex < 0) newIndex = shownMentionOptions.length - 1\n if (newIndex >= shownMentionOptions.length) newIndex = 0\n setMentionSelectedIndex(newIndex)\n }\n\n if (e.key === 'Enter') {\n // we handle this in the onChange\n }\n }\n\n if (e.key === 'Enter' && (e.ctrlKey || e.metaKey)) {\n handleSubmit()\n }\n\n if (e.key === 'Escape') {\n handleClose()\n }\n }\n\n let quillMinHeight: number | undefined = isOpen ? initHeight + 41 : 44\n if (isEditing) quillMinHeight = undefined\n\n // QUILL CONFIG\n const modules = useMemo(\n () =>\n getModules({\n imageUploader: {\n projectName,\n onUpload: handleFileUploaded,\n onUploadProgress: handleFileProgress,\n },\n }),\n [projectName, setFiles, setFilesUploading],\n )\n\n const allFiles = [...annotations, ...(files || []), ...filesUploading].sort(\n (a, b) => a.order - b.order,\n )\n const compactGrid = allFiles.length > 6\n\n // disable version mentions for folders\n let mentionsError = null\n if (entities.length && entities[0].entityType === 'folder') {\n if (mention?.type === '@@') {\n mentionsError = 'Version mentions are disabled for folders'\n }\n }\n\n return (\n <>\n <Styled.AutoHeight\n className={clsx('comment-container', { isOpen, isEditing })}\n onDragOver={handleDragOver}\n onDragLeave={() => setIsDropping(false)}\n onDrop={handleDrop}\n onClick={() => setIsDropping(false)}\n onKeyDown={(e) => e.stopPropagation()}\n >\n <Styled.Comment\n className={clsx('block-shortcuts', {\n isOpen,\n isClosed: !isOpen || disabled,\n isEditing,\n isDropping,\n disabled,\n isLoading,\n isSubmitting,\n })}\n onKeyDown={handleKeyDown}\n onClick={handleOpenClick}\n >\n <Styled.Markdown ref={markdownRef}>\n {/* this is purely used to translate the markdown into html for Editor */}\n <InputMarkdownConvert typeOptions={mentionTypeOptions} initValue={initValue} />\n </Styled.Markdown>\n\n {/* file uploads */}\n {isOpen && (\n <FilesGrid\n files={allFiles}\n isCompact={compactGrid}\n onRemove={handleFileRemove}\n style={{ borderBottom: '1px solid var(--md-sys-color-outline-variant)' }}\n projectName={projectName}\n onAnnotationClick={goToAnnotation}\n />\n )}\n {isOpen && !disabled ? (\n <ReactQuill\n theme=\"snow\"\n style={{ minHeight: quillMinHeight, maxHeight: 300 }}\n ref={editorRef}\n value={editorValue}\n onChange={handleChange}\n readOnly={!isOpen}\n placeholder={'Comment or mention with @user, @@version, @@@task...'}\n modules={modules}\n formats={quillFormats}\n />\n ) : (\n <Styled.Placeholder>\n {disabled ? 'Commenting is disabled across multiple projects.' : 'Add a comment...'}\n </Styled.Placeholder>\n )}\n\n <Styled.Footer>\n <Styled.Buttons>\n {/* mention a user */}\n <Button\n icon=\"person\"\n variant=\"text\"\n onClick={() => handleMentionButton('@')}\n data-tooltip={'Mention user'}\n data-shortcut={'@'}\n />\n {/* mention a version */}\n <Button\n icon=\"layers\"\n variant=\"text\"\n onClick={() => handleMentionButton('@@')}\n data-tooltip={'Mention version'}\n data-shortcut={'@@'}\n />\n {/* mention a task */}\n <Button\n icon=\"check_circle\"\n variant=\"text\"\n onClick={() => handleMentionButton('@@@')}\n data-tooltip={'Mention task'}\n data-shortcut={'@@@'}\n />\n </Styled.Buttons>\n <Styled.Buttons>\n {isEditing && (\n <Button variant=\"text\" onClick={handleClose}>\n Cancel\n </Button>\n )}\n <SaveButton\n label={isEditing ? 'Save' : 'Comment'}\n className=\"comment\"\n active={!!editorValue || !!files.length}\n onClick={handleSubmit}\n disabled={isLoading}\n />\n </Styled.Buttons>\n </Styled.Footer>\n\n <Styled.Dropzone className={clsx({ show: isDropping && isOpen })}>\n <Icon icon=\"cloud_upload\" />\n </Styled.Dropzone>\n </Styled.Comment>\n <CommentMentionSelect\n mention={mention}\n options={shownMentionOptions}\n onChange={handleSelectChange}\n types={mentionTypes}\n z\n // @ts-ignore\n config={mentionTypeOptions[mention?.type]}\n noneFound={!shownMentionOptions.length && mention?.search}\n noneFoundAtAll={!shownMentionOptions.length && !mention?.search}\n selectedIndex={mentionSelectedIndex}\n // @ts-ignore\n error={mentionsError}\n />\n </Styled.AutoHeight>\n </>\n )\n}\n\nexport default CommentInput\n"],"names":["_a","mention","type","jsx","Fragment","jsxs","Styled.AutoHeight","Styled.Comment","Styled.Markdown","Styled.Placeholder","Styled.Footer","Styled.Buttons","Styled.Dropzone"],"mappings":"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"}
1
+ {"version":3,"file":"CommentInput.es.js","sources":["../../../../../../../src/containers/Feed/components/CommentInput/CommentInput.tsx"],"sourcesContent":["// React and related hooks\nimport React, { FC, useEffect, useMemo, useRef, useState } from 'react'\n\n// Third-party libraries\nimport clsx from 'clsx'\nimport { toast } from 'react-toastify'\nimport ReactQuill, { Quill } from 'react-quill-ayon'\n\n// Components\nimport { Button, Icon, SaveButton } from '@ynput/ayon-react-components'\nimport CommentMentionSelect from '../CommentMentionSelect/CommentMentionSelect'\nimport InputMarkdownConvert from './InputMarkdownConvert'\nimport FilesGrid from '../FilesGrid'\n\n// Styled components\nimport * as Styled from './CommentInput.styled'\n\n// Helpers and utilities\nimport getMentionOptions from '../../mentionHelpers/getMentionOptions'\nimport getMentionUsers from '../../mentionHelpers/getMentionUsers'\nimport getMentionTasks from '../../mentionHelpers/getMentionTasks'\nimport getMentionVersions from '../../mentionHelpers/getMentionVersions'\nimport { convertToMarkdown } from './quillToMarkdown'\nimport { handleFileDrop, parseImages, typeWithDelay } from './helpers'\nimport { getModules, quillFormats } from './modules'\n\n// Hooks\nimport useInitialValue from './hooks/useInitialValue'\nimport useSetCursorEnd from './hooks/useSetCursorEnd'\nimport useMentionLink from './hooks/useMentionLink'\nimport useAnnotationsSync from './hooks/useAnnotationsSync'\n\n// State management\nimport useAnnotationsUpload from './hooks/useAnnotationsUpload'\nimport { useFeedContext } from '../../context/FeedContext'\n\nvar Delta = Quill.import('delta')\n\nconst mentionTypes = ['@', '@@', '@@@']\nexport const mentionTypeOptions = {\n '@@@': {\n id: 'task',\n },\n '@@': {\n id: 'version',\n },\n '@': {\n id: 'user',\n isCircle: true,\n },\n}\n\ninterface CommentInputProps {\n initValue: string | null\n initFiles?: any[]\n onSubmit: (markdown: string, files: any[]) => Promise<void>\n isEditing?: boolean\n disabled?: boolean\n isLoading?: boolean\n isOpen: boolean\n onOpen?: () => void\n onClose?: () => void\n}\n\nconst CommentInput: FC<CommentInputProps> = ({\n initValue,\n initFiles = [],\n onSubmit,\n isEditing,\n disabled,\n isLoading,\n isOpen,\n onOpen,\n onClose,\n}) => {\n const { projectName, entities, projectInfo, scope, currentTab, mentionSuggestionsData } =\n useFeedContext()\n\n const {\n users: mentionUsers,\n versions: mentionVersions,\n tasks: mentionTasks,\n } = mentionSuggestionsData || {}\n\n const [initHeight, setInitHeight] = useState(88)\n const [editorValue, setEditorValue] = useState('')\n // file uploads\n const [files, setFiles] = useState(initFiles)\n const [filesUploading, setFilesUploading] = useState([])\n const [isDropping, setIsDropping] = useState(false)\n const [isSubmitting, setIsSubmitting] = useState(false)\n\n const { annotations, removeAnnotation, goToAnnotation } = useAnnotationsSync({\n entityId: entities[0]?.id,\n filesUploading,\n })\n\n // MENTION STATES\n const [mention, setMention] = useState<null | any>(null)\n const [mentionSelectedIndex, setMentionSelectedIndex] = useState(0)\n // REFS\n const editorRef = useRef<any>(null)\n const markdownRef = useRef<HTMLDivElement>(null)\n\n // if there is an initial value, set it so the editor is prefilled\n useInitialValue({\n markdownRef,\n initValue,\n setEditorValue,\n setInitHeight,\n isOpen: isOpen,\n filter: currentTab,\n })\n\n // When editing, set selection to the end of the editor\n useSetCursorEnd({ initHeight, editorRef, isEditing })\n // create a new quill format for mentions and registers it\n useMentionLink({ projectName })\n\n // focus on editor when opened\n useEffect(() => {\n if (isOpen) {\n editorRef.current?.getEditor()?.enable()\n // block autofocus if opened from an annotation\n if (annotations.length > 0 && files.length === 0) {\n return\n }\n\n editorRef.current?.focus()\n }\n // We don't set annotations or files as useEffect dependencies, because we don't want to focus\n // the input if it's already open but annotations change (e.g. are removed).\n }, [isOpen, editorRef])\n\n mentionTypes.sort((a, b) => b.length - a.length)\n\n const mentionOptions = useMemo(\n () =>\n getMentionOptions(\n mention?.type,\n {\n '@': () => getMentionUsers(mentionUsers),\n '@@': () => getMentionVersions(mentionVersions),\n '@@@': () => getMentionTasks(mentionTasks, projectInfo.taskTypes),\n },\n mention?.search,\n ),\n [mentionTasks, mentionVersions, mentionUsers, mention?.type, mention?.search],\n )\n\n // show first 5 and filter itself out\n const shownMentionOptions = mentionOptions.slice(0, 5)\n\n // triggered when a mention is selected\n const [newSelection, setNewSelection] = useState<null | number>()\n\n useEffect(() => {\n if (newSelection) {\n setNewSelection(null)\n // now we set selection to the end of the mention\n const quill = editorRef.current.getEditor()\n quill.setSelection(newSelection)\n }\n }, [newSelection])\n\n const handleSelectMention = (selectedOption: any) => {\n // get option text\n const quill = editorRef.current.getEditor()\n\n const typePrefix = mention.type // the type of mention: @, @@, @@@\n const search = typePrefix + (mention.search || '') // the full search string: @Tim\n const mentionLabel = typePrefix + selectedOption.label // the label of the mention: @Tim Bailey\n // @ts-expect-error\n const type = mentionTypeOptions[typePrefix] // the type of mention: user, version, task\n const href = `${type?.id}:${selectedOption.id}` // the href of the mention: user:user.123\n\n // get selection delta\n const selection = quill.getSelection(true)\n const selectionIndex = selection?.index || 0\n const startIndex = selectionIndex - search.length // the start index of the search\n\n // first delete the search string\n quill.deleteText(startIndex, search.length)\n\n // insert embed link\n quill.insertText(startIndex, mentionLabel, 'mention', href)\n\n const endIndex = startIndex + mentionLabel.length\n\n // insert a space after the mention\n quill.updateContents(new Delta().retain(endIndex).insert(' '))\n\n // remove single \\n after mention\n quill.updateContents(new Delta().retain(endIndex + 1).delete(1))\n\n // set selection to the end of the mention + 1\n setNewSelection(endIndex + 1)\n\n // reset mention state\n setMention(null)\n setMentionSelectedIndex(0)\n }\n\n const handleSelectChange = (option: any) => {\n handleSelectMention(option)\n }\n\n const handleChange = (content: string, delta: any, _: any, editor: any) => {\n let currentCharacter =\n (delta.ops[0] && delta.ops[0].insert) || (delta.ops[1] && delta.ops[1].insert)\n\n const tabOrEnter = currentCharacter === '\\n' || currentCharacter === '\\t'\n // find the first option\n const selectedOption = mentionOptions[mentionSelectedIndex]\n\n if (mention && tabOrEnter && selectedOption) {\n // get option text\n const retain = (delta.ops[0] && delta.ops[0].retain) || 0\n // prevent default\n\n // @ts-ignore\n handleSelectMention(selectedOption, retain)\n\n return\n }\n\n setEditorValue(content)\n\n const isDelete = delta.ops.length === 2 && !!delta.ops[1].delete\n\n if (!currentCharacter && isDelete) {\n currentCharacter = editor.getText(delta.ops[0].retain - 1, 1)\n }\n\n const isMention = mentionTypes.includes(currentCharacter)\n\n if (isMention) {\n const mentionIndex = delta.ops.findIndex((op: any) => 'insert' in op || 'delete' in op)\n const mention = currentCharacter\n let retain = mentionIndex === 0 ? 0 : delta.ops[mentionIndex - 1].retain\n if (isDelete) retain = retain - 1\n\n // for each mention denotation char, check if it is a mention\n // sort by length of mention denotation char\n let mentionMatch = null\n\n // loop through each mention denotation char, with longest first. First one to match is the one we want\n for (const chars of mentionTypes) {\n let isMatch = true\n // start with the last character\n if (chars.endsWith(mention)) {\n // loop through the chars backwards\n for (let i = chars.length - 1; i >= 0; i--) {\n // skip first character as that's already been checked\n if (i === 0) continue\n const char = chars[i - 1]\n const indexInDelta = retain - (chars.length - i)\n const valueCharAtIndex = editor.getText(indexInDelta, 1)\n if (valueCharAtIndex !== char) {\n isMatch = false\n break\n }\n }\n } else {\n isMatch = false\n }\n\n if (isMatch) {\n // console.log('match!!!', chars)\n mentionMatch = chars\n break\n }\n }\n\n if (mentionMatch) {\n setMention({\n type: mentionMatch,\n retain: retain,\n })\n } else {\n setMention(null)\n setMentionSelectedIndex(0)\n }\n } else {\n // get full string between mention and new delta\n // This is where SEARCH is handled\n if (mention) {\n const retain = delta.ops[0].retain\n // if space is pressed, remove mention\n if (currentCharacter === ' ' || !retain) {\n setMention(null)\n setMentionSelectedIndex(0)\n return\n }\n\n let distanceMentionToRetain = retain - mention.retain\n if (!isDelete) distanceMentionToRetain++\n const mentionFull = editor.getText(mention.retain, distanceMentionToRetain)\n const mentionSearch = mentionFull.replace(mention.type.slice(-1), '')\n // check for space in mentionFull\n if (mentionFull.includes(' ')) {\n setMention(null)\n setMentionSelectedIndex(0)\n } else {\n setMention({\n ...mention,\n search: mentionSearch?.toLowerCase(),\n })\n }\n } else {\n // just deleting any text\n const quill = editorRef.current.getEditor()\n const currentSelection = quill.getSelection(false)\n const currentFormat = quill.getFormat(currentSelection?.index, currentSelection?.length)\n if (currentFormat.mention) {\n // if format is mention, delete the whole mention\n const [lineBlock] = quill.getLine(currentSelection.index - 1) || []\n const ops = lineBlock?.cache?.delta?.ops || []\n // get last op with attributes mention: true\n const lastMentionOp = ops.reverse().find((op: any) => op.attributes?.mention)\n if (lastMentionOp) {\n const mentionLength = lastMentionOp.insert.length\n quill.deleteText(currentSelection.index - mentionLength, mentionLength)\n }\n }\n }\n }\n }\n\n const addTextToEditor = (type: string) => {\n // get editor retain\n const quill = editorRef.current.getEditor()\n\n let retain = quill.getSelection(true)?.index || 0\n\n // get character at retain\n const currentCharacter = quill.getText(retain - 1, 1)\n\n // if the current character is a character, increment retain\n const addSpace = currentCharacter !== ' ' && currentCharacter\n if (addSpace) {\n quill.insertText(retain, ' ')\n retain++\n }\n\n // This is hack AF, but it works\n typeWithDelay(quill, retain, type)\n }\n\n const handleMentionButton = (type: string) => {\n // first check if mention is already open\n if (mention) {\n const { type, retain, search = '' } = mention\n\n const quill = editorRef.current.getEditor()\n const length = type.length + search.length\n const start = retain - type.length + 1\n // delete the mention\n quill.deleteText(start, length)\n }\n\n addTextToEditor(type)\n }\n\n const handleOpenClick = () => {\n if (isOpen || disabled) return\n\n onOpen && onOpen()\n }\n\n const handleClose = () => {\n // get editor value\n const editor = editorRef.current.getEditor()\n const text = editor.getText()\n if (text.length < 2 || isEditing) {\n setEditorValue('')\n }\n\n // always close editor\n onClose && onClose()\n }\n\n const handleFileUploaded = ({ file, data }: any) => {\n const newFile = {\n id: data.id,\n name: file.name,\n mime: file.type,\n size: file.size,\n order: files.length,\n }\n\n setFiles((prev) => [...prev, newFile])\n // remove from uploading\n setFilesUploading((prev) => prev.filter((uploading: any) => uploading.name !== file.name))\n\n return newFile\n }\n\n const handleFileRemove = (id: string, name: string, isAnnotation: boolean) => {\n if (isAnnotation) {\n // remove from annotations (if it's an annotation)\n removeAnnotation?.(id)\n } else {\n // remove file from files\n setFiles((prev) => prev.filter((file) => file.id !== id))\n // remove from uploading\n setFilesUploading((prev) => {\n return prev.filter((file: any) => file.name !== name)\n })\n }\n }\n\n const handleFileProgress = (e: any, file: any) => {\n const progress = Math.round((e.loaded * 100) / e.total)\n if (progress !== 100) {\n const uploadProgress = {\n name: file.name,\n progress,\n type: file.type,\n order: files.length + filesUploading.length,\n }\n\n // @ts-ignore\n setFilesUploading((prev) => {\n // replace or add new progress\n const newProgress = prev.filter((name: any) => name.name !== file.name)\n return [...newProgress, uploadProgress]\n })\n }\n }\n\n // when a file is not dropped onto the comment input\n const handleDrop = (e: React.DragEvent<HTMLDivElement>) => {\n setIsDropping(false)\n // upload file\n handleFileDrop(e, projectName, handleFileProgress, handleFileUploaded)\n }\n\n const handleDragOver = (e: React.DragEvent<HTMLDivElement>) => {\n e.preventDefault()\n e.stopPropagation()\n setIsDropping(true)\n }\n\n const uploadAnnotations = useAnnotationsUpload({\n projectName,\n onSuccess: handleFileUploaded,\n })\n\n const handleSubmit = async () => {\n try {\n setIsSubmitting(true)\n // upload any annotations first\n let annotationFiles = []\n if (annotations.length) {\n annotationFiles = await uploadAnnotations(annotations)\n }\n\n // convert to markdown\n const [markdown] = convertToMarkdown(editorValue)\n\n // remove img query params\n const markdownParsed = parseImages(markdown)\n\n const uploadedFiles = [...files, ...annotationFiles]\n\n if ((markdownParsed || uploadedFiles.length) && onSubmit) {\n try {\n await onSubmit(markdownParsed, uploadedFiles)\n // only clear if onSubmit is successful\n setEditorValue('')\n setFiles([])\n } catch (error) {\n // error is handled in rtk query mutation\n return\n }\n }\n } catch (error) {\n console.error(error)\n toast.error('Something went wrong')\n } finally {\n setIsSubmitting(false)\n }\n }\n\n const handleKeyDown = (e: React.KeyboardEvent<HTMLElement>) => {\n if (mention) {\n // close mention on escape\n if (e.key === 'Escape') {\n setMention(null)\n setMentionSelectedIndex(0)\n return\n }\n\n // add top search of mention\n if (mention && e.key === 'Tab') {\n // we handle this in the onChange\n }\n\n const arrowDirection = e.key === 'ArrowUp' ? -1 : e.key === 'ArrowDown' ? 1 : 0\n\n if (arrowDirection) {\n // navigate through mentions\n e.preventDefault()\n let newIndex = mentionSelectedIndex + arrowDirection\n if (newIndex < 0) newIndex = shownMentionOptions.length - 1\n if (newIndex >= shownMentionOptions.length) newIndex = 0\n setMentionSelectedIndex(newIndex)\n }\n\n if (e.key === 'Enter') {\n // we handle this in the onChange\n }\n }\n\n if (e.key === 'Enter' && (e.ctrlKey || e.metaKey)) {\n handleSubmit()\n }\n\n if (e.key === 'Escape') {\n handleClose()\n }\n }\n\n let quillMinHeight: number | undefined = isOpen ? initHeight + 41 : 44\n if (isEditing) quillMinHeight = undefined\n\n // QUILL CONFIG\n const modules = useMemo(\n () =>\n getModules({\n imageUploader: {\n projectName,\n onUpload: handleFileUploaded,\n onUploadProgress: handleFileProgress,\n },\n }),\n [projectName, setFiles, setFilesUploading],\n )\n\n const allFiles = [...annotations, ...(files || []), ...filesUploading].sort(\n (a, b) => a.order - b.order,\n )\n const compactGrid = allFiles.length > 6\n\n // disable version mentions for folders\n let mentionsError = null\n if (entities.length && entities[0].entityType === 'folder') {\n if (mention?.type === '@@') {\n mentionsError = 'Version mentions are disabled for folders'\n }\n }\n\n return (\n <>\n <Styled.AutoHeight\n className={clsx('comment-container', { isOpen, isEditing })}\n onDragOver={handleDragOver}\n onDragLeave={() => setIsDropping(false)}\n onDrop={handleDrop}\n onClick={() => setIsDropping(false)}\n onKeyDown={(e) => e.stopPropagation()}\n >\n <Styled.Comment\n className={clsx('block-shortcuts', {\n isOpen,\n isClosed: !isOpen || disabled,\n isEditing,\n isDropping,\n disabled,\n isLoading,\n isSubmitting,\n })}\n onKeyDown={handleKeyDown}\n onClick={handleOpenClick}\n >\n <Styled.Markdown ref={markdownRef}>\n {/* this is purely used to translate the markdown into html for Editor */}\n <InputMarkdownConvert typeOptions={mentionTypeOptions} initValue={initValue} />\n </Styled.Markdown>\n\n {/* file uploads */}\n {isOpen && (\n <FilesGrid\n files={allFiles}\n isCompact={compactGrid}\n onRemove={handleFileRemove}\n style={{ borderBottom: '1px solid var(--md-sys-color-outline-variant)' }}\n projectName={projectName}\n onAnnotationClick={goToAnnotation}\n />\n )}\n {isOpen && !disabled ? (\n <ReactQuill\n theme=\"snow\"\n style={{ minHeight: quillMinHeight, maxHeight: 300 }}\n ref={editorRef}\n value={editorValue}\n onChange={handleChange}\n readOnly={!isOpen}\n placeholder={'Comment or mention with @user, @@version, @@@task...'}\n modules={modules}\n formats={quillFormats}\n />\n ) : (\n <Styled.Placeholder>\n {disabled ? 'Commenting is disabled across multiple projects.' : 'Add a comment...'}\n </Styled.Placeholder>\n )}\n\n <Styled.Footer>\n <Styled.Buttons>\n {/* mention a user */}\n <Button\n icon=\"person\"\n variant=\"text\"\n onClick={() => handleMentionButton('@')}\n data-tooltip={'Mention user'}\n data-shortcut={'@'}\n />\n {/* mention a version */}\n <Button\n icon=\"layers\"\n variant=\"text\"\n onClick={() => handleMentionButton('@@')}\n data-tooltip={'Mention version'}\n data-shortcut={'@@'}\n />\n {/* mention a task */}\n <Button\n icon=\"check_circle\"\n variant=\"text\"\n onClick={() => handleMentionButton('@@@')}\n data-tooltip={'Mention task'}\n data-shortcut={'@@@'}\n />\n </Styled.Buttons>\n <Styled.Buttons>\n {isEditing && (\n <Button variant=\"text\" onClick={handleClose}>\n Cancel\n </Button>\n )}\n <SaveButton\n label={isEditing ? 'Save' : 'Comment'}\n className=\"comment\"\n active={!!editorValue || !!files.length}\n onClick={handleSubmit}\n disabled={isLoading}\n />\n </Styled.Buttons>\n </Styled.Footer>\n\n <Styled.Dropzone className={clsx({ show: isDropping && isOpen })}>\n <Icon icon=\"cloud_upload\" />\n </Styled.Dropzone>\n </Styled.Comment>\n <CommentMentionSelect\n mention={mention}\n options={shownMentionOptions}\n onChange={handleSelectChange}\n types={mentionTypes}\n z\n // @ts-ignore\n config={mentionTypeOptions[mention?.type]}\n noneFound={!shownMentionOptions.length && mention?.search}\n noneFoundAtAll={!shownMentionOptions.length && !mention?.search}\n selectedIndex={mentionSelectedIndex}\n // @ts-ignore\n error={mentionsError}\n />\n </Styled.AutoHeight>\n </>\n )\n}\n\nexport default CommentInput\n"],"names":["_a","mention","type","jsx","Fragment","jsxs","Styled.AutoHeight","Styled.Comment","Styled.Markdown","Styled.Placeholder","Styled.Footer","Styled.Buttons","Styled.Dropzone"],"mappings":"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"}
@@ -185,7 +185,19 @@ const ProjectTreeTableColumns = ({
185
185
  attributeData: { type: "list_of_strings" },
186
186
  options: options.assignees,
187
187
  isCollapsed: !!row.original.childOnlyMatch,
188
- onChange: (value2) => updateEntities([{ field: column.id, value: value2, id, type }])
188
+ onChange: (value2) => {
189
+ console.log(value2);
190
+ updateEntities([{ field: column.id, value: value2, id, type }]);
191
+ },
192
+ pt: {
193
+ enum: {
194
+ multiSelectClose: (value == null ? void 0 : value.length) === 0,
195
+ // close the dropdown on first assignment
196
+ search: true,
197
+ // enable search at all times
198
+ multipleOverride: false
199
+ }
200
+ }
189
201
  }
190
202
  );
191
203
  }
@@ -1 +1 @@
1
- {"version":3,"file":"ProjectTreeTableColumns.cjs.js","sources":["../../../../../src/containers/ProjectTreeTable/ProjectTreeTableColumns.tsx"],"sourcesContent":["import { useMemo } from 'react'\nimport {\n ColumnDef,\n ColumnSizingState,\n FilterFnOption,\n Row,\n SortingFn,\n sortingFns,\n} from '@tanstack/react-table'\nimport { TableRow } from './types/table'\nimport { AttributeData, AttributeWithPermissions, BuiltInFieldOptions } from './types'\nimport { CellWidget, EntityNameWidget } from './widgets'\nimport { useCellEditing } from './context/CellEditingContext'\nimport { getCellId, getCellValue } from './utils/cellUtils'\nimport { TableCellContent } from './ProjectTreeTable.styled'\nimport clsx from 'clsx'\nimport { SelectionCell } from './components/SelectionCell'\nimport RowSelectionHeader from './components/RowSelectionHeader'\nimport { ROW_SELECTION_COLUMN_ID } from './context/SelectionCellsContext'\n\n// Wrapper function for sorting that pushes isLoading rows to the bottom\nconst withLoadingStateSort = (sortFn: SortingFn<any>): SortingFn<any> => {\n return (rowA, rowB, ...args) => {\n // If row loading states differ, prioritize non-loading rows\n if (rowA.original.isLoading !== rowB.original.isLoading) {\n return rowA.original.isLoading ? 1 : -1\n }\n // Otherwise, use the original sort function\n return sortFn(rowA, rowB, ...args)\n }\n}\n\nconst nameSort: SortingFn<any> = (rowA, rowB) => {\n const labelA = rowA.original.label || rowA.original.name\n const labelB = rowB.original.label || rowB.original.name\n // sort alphabetically by label\n return labelA.localeCompare(labelB)\n}\nconst pathSort: SortingFn<any> = (rowA, rowB) => {\n const labelA = rowA.original.path || rowA.original.name\n const labelB = rowB.original.path || rowB.original.name\n // sort alphabetically by label\n return labelA.localeCompare(labelB)\n}\n\ntype AttribSortingFn = (rowA: any, rowB: any, columnId: string, attribute?: AttributeData) => number\n// sort by the order of the enum options\nconst attribSort: AttribSortingFn = (rowA, rowB, columnId, attrib) => {\n const valueA = getCellValue(rowA.original, columnId)\n const valueB = getCellValue(rowB.original, columnId)\n // if attrib is defined and has enum options, use them\n if (attrib && attrib.enum) {\n const indexA = attrib.enum.findIndex((o) => o.value === valueA)\n const indexB = attrib.enum.findIndex((o) => o.value === valueB)\n return indexA - indexB < 0 ? 1 : -1\n } else if (attrib?.type === 'datetime') {\n return sortingFns.datetime(rowA, rowB, columnId)\n } else if (attrib?.type === 'boolean') {\n const boolA = valueA === true ? 1 : 0\n const boolB = valueB === true ? 1 : 0\n return boolA - boolB\n } else {\n // default sorting\n return sortingFns.alphanumeric(rowA, rowB, columnId)\n }\n}\n\ntype Props = {\n tableData: TableRow[]\n attribs: AttributeWithPermissions[]\n columnSizing: ColumnSizingState\n isLoading: boolean\n showHierarchy: boolean\n sliceId: string\n options: BuiltInFieldOptions\n toggleExpandAll: (id: string) => void\n toggleExpanded: (id: string) => void\n}\n\nconst ProjectTreeTableColumns = ({\n tableData,\n attribs,\n columnSizing = {},\n showHierarchy,\n isLoading,\n sliceId,\n options,\n toggleExpandAll,\n toggleExpanded,\n}: Props) => {\n const { updateEntities } = useCellEditing()\n\n return useMemo<ColumnDef<TableRow, any>[]>(() => {\n const staticColumns: ColumnDef<TableRow>[] = [\n {\n id: ROW_SELECTION_COLUMN_ID,\n header: () => <RowSelectionHeader />,\n cell: () => <SelectionCell />,\n size: 20,\n },\n {\n accessorKey: 'name',\n header: () => 'Folder / Task',\n sortingFn: withLoadingStateSort(showHierarchy ? nameSort : pathSort),\n cell: ({ row, column }) => {\n const cellId = getCellId(row.id, column.id)\n return (\n <TableCellContent\n id={cellId}\n className={clsx('large', row.original.entityType, {\n loading: row.original.isLoading,\n hierarchy: showHierarchy,\n })}\n style={{\n paddingLeft: `calc(${row.depth * 1}rem + 8px)`,\n }}\n tabIndex={0}\n >\n <EntityNameWidget\n id={row.id}\n label={row.original.label}\n name={row.original.name}\n path={!showHierarchy ? row.original.path : undefined}\n showHierarchy={showHierarchy}\n icon={row.original.icon}\n type={row.original.entityType}\n isExpanded={row.getIsExpanded()}\n toggleExpandAll={toggleExpandAll}\n toggleExpanded={() => toggleExpanded(row.id)}\n />\n </TableCellContent>\n )\n },\n },\n {\n accessorKey: 'status',\n header: () => 'Status',\n sortingFn: withLoadingStateSort((a, b, c) =>\n attribSort(a, b, c, { enum: options.statuses, type: 'string' }),\n ),\n sortDescFirst: true,\n size: columnSizing['status'] || 150,\n cell: ({ row, column }) => {\n const { value, id, type } = getValueIdType(row, column.id)\n\n return (\n <CellWidget\n rowId={id}\n className={clsx('status', { loading: row.original.isLoading })}\n columnId={column.id}\n value={value}\n attributeData={{ type: 'string' }}\n options={options.statuses.filter((s) => s.scope?.includes(type))}\n isCollapsed={!!row.original.childOnlyMatch}\n onChange={(value) => updateEntities([{ field: column.id, value, id, type }])}\n />\n )\n },\n },\n {\n accessorKey: 'subType',\n header: () => 'Type',\n size: columnSizing['type'] || 150,\n cell: ({ row, column }) => {\n const { value, id, type } = getValueIdType(row, column.id)\n const fieldId = type === 'folder' ? 'folderType' : 'taskType'\n return (\n <CellWidget\n rowId={id}\n className={clsx('subType', { loading: row.original.isLoading })}\n columnId={column.id}\n value={value}\n attributeData={{ type: 'string' }}\n options={type === 'folder' ? options.folderTypes : options.taskTypes}\n isCollapsed={!!row.original.childOnlyMatch}\n onChange={(value) => updateEntities([{ field: fieldId, value, id, type }])}\n />\n )\n },\n },\n {\n accessorKey: 'assignees',\n header: () => 'Assignees',\n size: columnSizing['assignees'] || 150,\n cell: ({ row, column }) => {\n const { value, id, type } = getValueIdType(row, column.id)\n if (type === 'folder')\n return (\n <CellWidget\n rowId={id}\n className={clsx('assignees', { loading: row.original.isLoading })}\n columnId={column.id}\n value=\"\"\n isPlaceholder\n />\n )\n return (\n <CellWidget\n rowId={id}\n className={clsx('assignees', { loading: row.original.isLoading })}\n columnId={column.id}\n value={value}\n attributeData={{ type: 'list_of_strings' }}\n options={options.assignees}\n isCollapsed={!!row.original.childOnlyMatch}\n onChange={(value) => updateEntities([{ field: column.id, value, id, type }])}\n />\n )\n },\n },\n {\n accessorKey: 'tags',\n header: () => 'Tags',\n size: columnSizing['tags'] || 150,\n cell: ({ row, column }) => {\n const { value, id, type } = getValueIdType(row, column.id)\n return (\n <CellWidget\n rowId={id}\n className={clsx('tags', { loading: row.original.isLoading })}\n columnId={column.id}\n value={value}\n attributeData={{ type: 'list_of_strings' }}\n options={options.tags}\n isCollapsed={!!row.original.childOnlyMatch}\n onChange={(value) => updateEntities([{ field: column.id, value, id, type }])}\n enableCustomValues\n />\n )\n },\n },\n ]\n\n const attributeColumns = attribs.map((attrib) => {\n const attribColumn: ColumnDef<TableRow> = {\n accessorKey: 'attrib.' + attrib.name,\n header: () => attrib.data.title || attrib.name,\n filterFn: 'fuzzy' as FilterFnOption<TableRow>,\n sortingFn: withLoadingStateSort((a, b, c) => attribSort(a, b, c, attrib.data)),\n cell: ({ row, column }) => {\n const columnIdParsed = column.id.replace('attrib_', '')\n const { value, id, type } = getValueIdType(row, columnIdParsed, 'attrib')\n const isInherited = !row.original.ownAttrib.includes(columnIdParsed)\n\n return (\n <CellWidget\n rowId={id}\n className={clsx('attrib', { loading: row.original.isLoading })}\n columnId={column.id}\n value={value}\n attributeData={{ type: attrib.data.type || 'string' }}\n options={attrib.data.enum || []}\n isCollapsed={!!row.original.childOnlyMatch}\n isInherited={isInherited}\n isReadOnly={attrib.readOnly}\n onChange={(value) =>\n updateEntities([{ field: columnIdParsed, value, id, type, isAttrib: true }])\n }\n />\n )\n },\n }\n return attribColumn\n })\n\n return [...staticColumns, ...attributeColumns]\n }, [isLoading, sliceId, tableData, options, attribs, showHierarchy, updateEntities])\n}\n\nexport default ProjectTreeTableColumns\n\nconst getValueIdType = (\n row: Row<TableRow>,\n field: string,\n nestedField?: keyof TableRow,\n): {\n value: any\n id: string\n type: string\n} => ({\n value: nestedField\n ? (row.original[nestedField as keyof TableRow] as any)?.[field]\n : (row.original[field as keyof TableRow] as any),\n id: row.id,\n type: row.original.entityType,\n})\n"],"names":["getCellValue","sortingFns","useCellEditing","useMemo","ROW_SELECTION_COLUMN_ID","jsx","SelectionCell","getCellId","TableCellContent","EntityNameWidget","CellWidget","value"],"mappings":"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"}
1
+ {"version":3,"file":"ProjectTreeTableColumns.cjs.js","sources":["../../../../../src/containers/ProjectTreeTable/ProjectTreeTableColumns.tsx"],"sourcesContent":["import { useMemo } from 'react'\nimport {\n ColumnDef,\n ColumnSizingState,\n FilterFnOption,\n Row,\n SortingFn,\n sortingFns,\n} from '@tanstack/react-table'\nimport { TableRow } from './types/table'\nimport { AttributeData, AttributeWithPermissions, BuiltInFieldOptions } from './types'\nimport { CellWidget, EntityNameWidget } from './widgets'\nimport { useCellEditing } from './context/CellEditingContext'\nimport { getCellId, getCellValue } from './utils/cellUtils'\nimport { TableCellContent } from './ProjectTreeTable.styled'\nimport clsx from 'clsx'\nimport { SelectionCell } from './components/SelectionCell'\nimport RowSelectionHeader from './components/RowSelectionHeader'\nimport { ROW_SELECTION_COLUMN_ID } from './context/SelectionCellsContext'\n\n// Wrapper function for sorting that pushes isLoading rows to the bottom\nconst withLoadingStateSort = (sortFn: SortingFn<any>): SortingFn<any> => {\n return (rowA, rowB, ...args) => {\n // If row loading states differ, prioritize non-loading rows\n if (rowA.original.isLoading !== rowB.original.isLoading) {\n return rowA.original.isLoading ? 1 : -1\n }\n // Otherwise, use the original sort function\n return sortFn(rowA, rowB, ...args)\n }\n}\n\nconst nameSort: SortingFn<any> = (rowA, rowB) => {\n const labelA = rowA.original.label || rowA.original.name\n const labelB = rowB.original.label || rowB.original.name\n // sort alphabetically by label\n return labelA.localeCompare(labelB)\n}\nconst pathSort: SortingFn<any> = (rowA, rowB) => {\n const labelA = rowA.original.path || rowA.original.name\n const labelB = rowB.original.path || rowB.original.name\n // sort alphabetically by label\n return labelA.localeCompare(labelB)\n}\n\ntype AttribSortingFn = (rowA: any, rowB: any, columnId: string, attribute?: AttributeData) => number\n// sort by the order of the enum options\nconst attribSort: AttribSortingFn = (rowA, rowB, columnId, attrib) => {\n const valueA = getCellValue(rowA.original, columnId)\n const valueB = getCellValue(rowB.original, columnId)\n // if attrib is defined and has enum options, use them\n if (attrib && attrib.enum) {\n const indexA = attrib.enum.findIndex((o) => o.value === valueA)\n const indexB = attrib.enum.findIndex((o) => o.value === valueB)\n return indexA - indexB < 0 ? 1 : -1\n } else if (attrib?.type === 'datetime') {\n return sortingFns.datetime(rowA, rowB, columnId)\n } else if (attrib?.type === 'boolean') {\n const boolA = valueA === true ? 1 : 0\n const boolB = valueB === true ? 1 : 0\n return boolA - boolB\n } else {\n // default sorting\n return sortingFns.alphanumeric(rowA, rowB, columnId)\n }\n}\n\ntype Props = {\n tableData: TableRow[]\n attribs: AttributeWithPermissions[]\n columnSizing: ColumnSizingState\n isLoading: boolean\n showHierarchy: boolean\n sliceId: string\n options: BuiltInFieldOptions\n toggleExpandAll: (id: string) => void\n toggleExpanded: (id: string) => void\n}\n\nconst ProjectTreeTableColumns = ({\n tableData,\n attribs,\n columnSizing = {},\n showHierarchy,\n isLoading,\n sliceId,\n options,\n toggleExpandAll,\n toggleExpanded,\n}: Props) => {\n const { updateEntities } = useCellEditing()\n\n return useMemo<ColumnDef<TableRow, any>[]>(() => {\n const staticColumns: ColumnDef<TableRow>[] = [\n {\n id: ROW_SELECTION_COLUMN_ID,\n header: () => <RowSelectionHeader />,\n cell: () => <SelectionCell />,\n size: 20,\n },\n {\n accessorKey: 'name',\n header: () => 'Folder / Task',\n sortingFn: withLoadingStateSort(showHierarchy ? nameSort : pathSort),\n cell: ({ row, column }) => {\n const cellId = getCellId(row.id, column.id)\n return (\n <TableCellContent\n id={cellId}\n className={clsx('large', row.original.entityType, {\n loading: row.original.isLoading,\n hierarchy: showHierarchy,\n })}\n style={{\n paddingLeft: `calc(${row.depth * 1}rem + 8px)`,\n }}\n tabIndex={0}\n >\n <EntityNameWidget\n id={row.id}\n label={row.original.label}\n name={row.original.name}\n path={!showHierarchy ? row.original.path : undefined}\n showHierarchy={showHierarchy}\n icon={row.original.icon}\n type={row.original.entityType}\n isExpanded={row.getIsExpanded()}\n toggleExpandAll={toggleExpandAll}\n toggleExpanded={() => toggleExpanded(row.id)}\n />\n </TableCellContent>\n )\n },\n },\n {\n accessorKey: 'status',\n header: () => 'Status',\n sortingFn: withLoadingStateSort((a, b, c) =>\n attribSort(a, b, c, { enum: options.statuses, type: 'string' }),\n ),\n sortDescFirst: true,\n size: columnSizing['status'] || 150,\n cell: ({ row, column }) => {\n const { value, id, type } = getValueIdType(row, column.id)\n\n return (\n <CellWidget\n rowId={id}\n className={clsx('status', { loading: row.original.isLoading })}\n columnId={column.id}\n value={value}\n attributeData={{ type: 'string' }}\n options={options.statuses.filter((s) => s.scope?.includes(type))}\n isCollapsed={!!row.original.childOnlyMatch}\n onChange={(value) => updateEntities([{ field: column.id, value, id, type }])}\n />\n )\n },\n },\n {\n accessorKey: 'subType',\n header: () => 'Type',\n size: columnSizing['type'] || 150,\n cell: ({ row, column }) => {\n const { value, id, type } = getValueIdType(row, column.id)\n const fieldId = type === 'folder' ? 'folderType' : 'taskType'\n return (\n <CellWidget\n rowId={id}\n className={clsx('subType', { loading: row.original.isLoading })}\n columnId={column.id}\n value={value}\n attributeData={{ type: 'string' }}\n options={type === 'folder' ? options.folderTypes : options.taskTypes}\n isCollapsed={!!row.original.childOnlyMatch}\n onChange={(value) => updateEntities([{ field: fieldId, value, id, type }])}\n />\n )\n },\n },\n {\n accessorKey: 'assignees',\n header: () => 'Assignees',\n size: columnSizing['assignees'] || 150,\n cell: ({ row, column }) => {\n const { value, id, type } = getValueIdType(row, column.id)\n if (type === 'folder')\n return (\n <CellWidget\n rowId={id}\n className={clsx('assignees', { loading: row.original.isLoading })}\n columnId={column.id}\n value=\"\"\n isPlaceholder\n />\n )\n return (\n <CellWidget\n rowId={id}\n className={clsx('assignees', { loading: row.original.isLoading })}\n columnId={column.id}\n value={value}\n attributeData={{ type: 'list_of_strings' }}\n options={options.assignees}\n isCollapsed={!!row.original.childOnlyMatch}\n onChange={(value) => {\n console.log(value)\n updateEntities([{ field: column.id, value, id, type }])\n }}\n pt={{\n enum: {\n multiSelectClose: value?.length === 0, // close the dropdown on first assignment\n search: true, // enable search at all times\n multipleOverride: false,\n },\n }}\n />\n )\n },\n },\n {\n accessorKey: 'tags',\n header: () => 'Tags',\n size: columnSizing['tags'] || 150,\n cell: ({ row, column }) => {\n const { value, id, type } = getValueIdType(row, column.id)\n return (\n <CellWidget\n rowId={id}\n className={clsx('tags', { loading: row.original.isLoading })}\n columnId={column.id}\n value={value}\n attributeData={{ type: 'list_of_strings' }}\n options={options.tags}\n isCollapsed={!!row.original.childOnlyMatch}\n onChange={(value) => updateEntities([{ field: column.id, value, id, type }])}\n enableCustomValues\n />\n )\n },\n },\n ]\n\n const attributeColumns = attribs.map((attrib) => {\n const attribColumn: ColumnDef<TableRow> = {\n accessorKey: 'attrib.' + attrib.name,\n header: () => attrib.data.title || attrib.name,\n filterFn: 'fuzzy' as FilterFnOption<TableRow>,\n sortingFn: withLoadingStateSort((a, b, c) => attribSort(a, b, c, attrib.data)),\n cell: ({ row, column }) => {\n const columnIdParsed = column.id.replace('attrib_', '')\n const { value, id, type } = getValueIdType(row, columnIdParsed, 'attrib')\n const isInherited = !row.original.ownAttrib.includes(columnIdParsed)\n\n return (\n <CellWidget\n rowId={id}\n className={clsx('attrib', { loading: row.original.isLoading })}\n columnId={column.id}\n value={value}\n attributeData={{ type: attrib.data.type || 'string' }}\n options={attrib.data.enum || []}\n isCollapsed={!!row.original.childOnlyMatch}\n isInherited={isInherited}\n isReadOnly={attrib.readOnly}\n onChange={(value) =>\n updateEntities([{ field: columnIdParsed, value, id, type, isAttrib: true }])\n }\n />\n )\n },\n }\n return attribColumn\n })\n\n return [...staticColumns, ...attributeColumns]\n }, [isLoading, sliceId, tableData, options, attribs, showHierarchy, updateEntities])\n}\n\nexport default ProjectTreeTableColumns\n\nconst getValueIdType = (\n row: Row<TableRow>,\n field: string,\n nestedField?: keyof TableRow,\n): {\n value: any\n id: string\n type: string\n} => ({\n value: nestedField\n ? (row.original[nestedField as keyof TableRow] as any)?.[field]\n : (row.original[field as keyof TableRow] as any),\n id: row.id,\n type: row.original.entityType,\n})\n"],"names":["getCellValue","sortingFns","useCellEditing","useMemo","ROW_SELECTION_COLUMN_ID","jsx","SelectionCell","getCellId","TableCellContent","EntityNameWidget","CellWidget","value"],"mappings":"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"}
@@ -184,7 +184,19 @@ const ProjectTreeTableColumns = ({
184
184
  attributeData: { type: "list_of_strings" },
185
185
  options: options.assignees,
186
186
  isCollapsed: !!row.original.childOnlyMatch,
187
- onChange: (value2) => updateEntities([{ field: column.id, value: value2, id, type }])
187
+ onChange: (value2) => {
188
+ console.log(value2);
189
+ updateEntities([{ field: column.id, value: value2, id, type }]);
190
+ },
191
+ pt: {
192
+ enum: {
193
+ multiSelectClose: (value == null ? void 0 : value.length) === 0,
194
+ // close the dropdown on first assignment
195
+ search: true,
196
+ // enable search at all times
197
+ multipleOverride: false
198
+ }
199
+ }
188
200
  }
189
201
  );
190
202
  }