From 0149f98c8b9cdc49039504813f1c0327e3a2bd80 Mon Sep 17 00:00:00 2001 From: Ivan <8611739+IRBorisov@users.noreply.github.com> Date: Sat, 14 Sep 2024 16:25:39 +0300 Subject: [PATCH] F: Add schemas coloring option for TermGraph --- .../backend/apps/rsform/serializers/basics.py | 2 +- .../src/components/info/BadgeHelp.tsx | 2 +- rsconcept/frontend/src/models/RSFormLoader.ts | 11 ++- .../frontend/src/models/miscellaneous.ts | 2 +- rsconcept/frontend/src/models/rsform.ts | 4 + rsconcept/frontend/src/models/rsformAPI.ts | 1 + .../EditorTermGraph/EditorTermGraph.tsx | 3 +- .../EditorTermGraph/GraphSelectors.tsx | 7 +- .../EditorTermGraph/SchemasGuide.tsx | 74 +++++++++++++++++++ .../RSFormPage/EditorTermGraph/TermGraph.tsx | 8 +- rsconcept/frontend/src/styling/color.ts | 20 +++++ rsconcept/frontend/src/utils/constants.ts | 4 +- rsconcept/frontend/src/utils/labels.ts | 3 +- 13 files changed, 125 insertions(+), 16 deletions(-) create mode 100644 rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/SchemasGuide.tsx diff --git a/rsconcept/backend/apps/rsform/serializers/basics.py b/rsconcept/backend/apps/rsform/serializers/basics.py index 4dbe7e5b..d9ebe782 100644 --- a/rsconcept/backend/apps/rsform/serializers/basics.py +++ b/rsconcept/backend/apps/rsform/serializers/basics.py @@ -126,7 +126,7 @@ class InheritanceDataSerializer(serializers.Serializer): ''' Serializer: inheritance data. ''' child = serializers.IntegerField() child_source = serializers.IntegerField() - parent = serializers.IntegerField() + parent = serializers.IntegerField() # type: ignore parent_source = serializers.IntegerField() diff --git a/rsconcept/frontend/src/components/info/BadgeHelp.tsx b/rsconcept/frontend/src/components/info/BadgeHelp.tsx index e57be9da..16bafee4 100644 --- a/rsconcept/frontend/src/components/info/BadgeHelp.tsx +++ b/rsconcept/frontend/src/components/info/BadgeHelp.tsx @@ -4,8 +4,8 @@ import TextURL from '@/components/ui/TextURL'; import Tooltip, { PlacesType } from '@/components/ui/Tooltip'; import { useConceptOptions } from '@/context/ConceptOptionsContext'; import { HelpTopic } from '@/models/miscellaneous'; +import TopicPage from '@/pages/ManualsPage/TopicPage'; -import TopicPage from '../../pages/ManualsPage/TopicPage'; import { IconHelp } from '../Icons'; import { CProps } from '../props'; diff --git a/rsconcept/frontend/src/models/RSFormLoader.ts b/rsconcept/frontend/src/models/RSFormLoader.ts index 6685a9e4..39a8070c 100644 --- a/rsconcept/frontend/src/models/RSFormLoader.ts +++ b/rsconcept/frontend/src/models/RSFormLoader.ts @@ -60,10 +60,14 @@ export class RSFormLoader { } private inferCstAttributes() { - const parent_schemas = new Map(); + const schemaByCst = new Map(); + const parents: LibraryItemID[] = []; this.schema.inheritance.forEach(item => { if (item.child_source === this.schema.id) { - parent_schemas.set(item.child, item.parent_source); + schemaByCst.set(item.child, item.parent_source); + if (!parents.includes(item.parent_source)) { + parents.push(item.parent_source); + } } }); const inherit_children = new Set(this.schema.inheritance.map(item => item.child)); @@ -75,7 +79,8 @@ export class RSFormLoader { cst.cst_class = inferClass(cst.cst_type, cst.is_template); cst.spawn = []; cst.spawn_alias = []; - cst.parent_schema = parent_schemas.get(cst.id); + cst.parent_schema = schemaByCst.get(cst.id); + cst.parent_schema_index = cst.parent_schema ? parents.indexOf(cst.parent_schema) + 1 : 0; cst.is_inherited = inherit_children.has(cst.id); cst.has_inherited_children = inherit_parents.has(cst.id); cst.is_simple_expression = this.inferSimpleExpression(cst); diff --git a/rsconcept/frontend/src/models/miscellaneous.ts b/rsconcept/frontend/src/models/miscellaneous.ts index 3962dabd..248555eb 100644 --- a/rsconcept/frontend/src/models/miscellaneous.ts +++ b/rsconcept/frontend/src/models/miscellaneous.ts @@ -48,7 +48,7 @@ export interface OssNodeInternal { /** * Represents graph node coloring scheme. */ -export type GraphColoring = 'none' | 'status' | 'type'; +export type GraphColoring = 'none' | 'status' | 'type' | 'schemas'; /** * Represents graph node sizing scheme. diff --git a/rsconcept/frontend/src/models/rsform.ts b/rsconcept/frontend/src/models/rsform.ts index 9fdf612c..68c60614 100644 --- a/rsconcept/frontend/src/models/rsform.ts +++ b/rsconcept/frontend/src/models/rsform.ts @@ -111,6 +111,10 @@ export interface IConstituenta extends IConstituentaData { /** Indicates if this {@link IConstituenta} has a simple expression. */ is_simple_expression: boolean; + /** Index of {@link LibraryItemID} that contains this cst (or inheritance parent). + * 0 - not inherited, 1 - inherited by 1st schema, 2 - inherited by 2nd schema, etc. + */ + parent_schema_index: number; /** {@link LibraryItemID} that contains parent of this inherited {@link IConstituenta}. */ parent_schema?: LibraryItemID; /** Indicates if this {@link IConstituenta} is inherited. */ diff --git a/rsconcept/frontend/src/models/rsformAPI.ts b/rsconcept/frontend/src/models/rsformAPI.ts index 96615d17..81839749 100644 --- a/rsconcept/frontend/src/models/rsformAPI.ts +++ b/rsconcept/frontend/src/models/rsformAPI.ts @@ -132,6 +132,7 @@ export function createMockConstituenta(id: ConstituentaID, alias: string, commen definition_raw: '', definition_resolved: '', status: ExpressionStatus.INCORRECT, + parent_schema_index: 0, is_template: false, is_inherited: false, has_inherited_children: false, diff --git a/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/EditorTermGraph.tsx b/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/EditorTermGraph.tsx index c6084658..f63d7a3a 100644 --- a/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/EditorTermGraph.tsx +++ b/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/EditorTermGraph.tsx @@ -261,6 +261,7 @@ function EditorTermGraph({ onOpenEdit }: EditorTermGraphProps) { const selectors = useMemo( () => ( ), - [coloring, layout, sizing, handleChangeLayout, setColoring, setSizing] + [coloring, controller.schema, layout, sizing, handleChangeLayout, setColoring, setSizing] ); const viewHidden = useMemo( () => ( diff --git a/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/GraphSelectors.tsx b/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/GraphSelectors.tsx index 9ad38fc0..efb6d277 100644 --- a/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/GraphSelectors.tsx +++ b/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/GraphSelectors.tsx @@ -3,10 +3,14 @@ import { GraphLayout } from '@/components/ui/GraphUI'; import Overlay from '@/components/ui/Overlay'; import SelectSingle from '@/components/ui/SelectSingle'; import { GraphColoring, GraphSizing, HelpTopic } from '@/models/miscellaneous'; +import { IRSForm } from '@/models/rsform'; import { mapLabelColoring, mapLabelLayout, mapLabelSizing } from '@/utils/labels'; import { SelectorGraphColoring, SelectorGraphLayout, SelectorGraphSizing } from '@/utils/selectors'; +import SchemasGuide from './SchemasGuide'; + interface GraphSelectorsProps { + schema?: IRSForm; coloring: GraphColoring; layout: GraphLayout; sizing: GraphSizing; @@ -16,7 +20,7 @@ interface GraphSelectorsProps { setSizing: (newValue: GraphSizing) => void; } -function GraphSelectors({ coloring, setColoring, layout, setLayout, sizing, setSizing }: GraphSelectorsProps) { +function GraphSelectors({ schema, coloring, setColoring, layout, setLayout, sizing, setSizing }: GraphSelectorsProps) { return (
{coloring === 'status' ? : null} {coloring === 'type' ? : null} + {coloring === 'schemas' && !!schema ? : null} { + const processed = new Set(); + const aliases: string[] = []; + const indexes: number[] = []; + schema.items.forEach(cst => { + if (cst.parent_schema && !processed.has(cst.parent_schema)) { + const item = library.items.find(item => item.id === cst.parent_schema); + if (item) { + aliases.push(item.alias); + } else { + aliases.push(`Схема ${cst.parent_schema_index}`); + } + processed.add(cst.parent_schema); + indexes.push(cst.parent_schema_index); + } + }); + const result: string[] = []; + for (let i = 1; i <= aliases.length; i++) { + const trueIndex = indexes.findIndex(index => index === i); + result.push(aliases[trueIndex]); + } + return result; + }, [schema, library.items]); + + return ( +
+ + +
+ + Текущая схема +
+ {schemas.map((alias, index) => ( +
+ + {alias} +
+ ))} +
+
+ ); +} + +export default SchemasGuide; diff --git a/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/TermGraph.tsx b/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/TermGraph.tsx index b09cb528..14178fda 100644 --- a/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/TermGraph.tsx +++ b/rsconcept/frontend/src/pages/RSFormPage/EditorTermGraph/TermGraph.tsx @@ -1,6 +1,6 @@ 'use client'; -import { RefObject, useCallback, useLayoutEffect, useMemo } from 'react'; +import { RefObject, useCallback, useLayoutEffect } from 'react'; import GraphUI, { CollapseProps, @@ -107,12 +107,8 @@ function TermGraph({ setSelections(newSelections); }, [selectedIDs, setSelections, nodes]); - const canvasWidth = useMemo(() => { - return 'calc(100vw - 1rem)'; - }, []); - return ( -
+
([ export const mapLabelColoring = new Map([ ['none', 'Цвет: Моно'], ['status', 'Цвет: Статус'], - ['type', 'Цвет: Класс'] + ['type', 'Цвет: Класс'], + ['schemas', 'Цвет: Схемы'] ]); /**