mirror of
https://github.com/IRBorisov/ConceptPortal.git
synced 2025-08-13 12:20:36 +03:00
F: Improve Sidepanel UI
This commit is contained in:
parent
176ad744fe
commit
1af6f87824
|
@ -23,6 +23,7 @@ export function ApplicationLayout() {
|
|||
const viewportHeight = useViewportHeight();
|
||||
const noNavigationAnimation = useAppLayoutStore(state => state.noNavigationAnimation);
|
||||
const noNavigation = useAppLayoutStore(state => state.noNavigation);
|
||||
const toastBottom = useAppLayoutStore(state => state.toastBottom);
|
||||
const noFooter = useAppLayoutStore(state => state.noFooter);
|
||||
const activeDialog = useDialogsStore(state => state.active);
|
||||
|
||||
|
@ -35,6 +36,8 @@ export function ApplicationLayout() {
|
|||
autoClose={3000}
|
||||
draggable={false}
|
||||
pauseOnFocusLoss={false}
|
||||
position={toastBottom ? 'bottom-right' : 'top-right'}
|
||||
newestOnTop={toastBottom}
|
||||
/>
|
||||
|
||||
<Suspense fallback={<ModalLoader />}>
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import { Suspense } from 'react';
|
||||
import { Suspense, useEffect } from 'react';
|
||||
import clsx from 'clsx';
|
||||
import { useDebounce } from 'use-debounce';
|
||||
|
||||
|
@ -23,6 +23,7 @@ interface SidePanelProps {
|
|||
|
||||
export function SidePanel({ isMounted, className }: SidePanelProps) {
|
||||
const noNavigationAnimation = useAppLayoutStore(state => state.noNavigationAnimation);
|
||||
const setToastBottom = useAppLayoutStore(state => state.setToastBottom);
|
||||
const { schema, isMutable, selectedItems } = useOssEdit();
|
||||
const selectedOperation =
|
||||
selectedItems.length === 1 && selectedItems[0].nodeType === NodeType.OPERATION ? selectedItems[0] : null;
|
||||
|
@ -32,8 +33,14 @@ export function SidePanel({ isMounted, className }: SidePanelProps) {
|
|||
|
||||
const [debouncedMounted] = useDebounce(isMounted, PARAMETER.moveDuration);
|
||||
const closePanel = usePreferencesStore(state => state.toggleShowOssSidePanel);
|
||||
const showPanel = usePreferencesStore(state => state.showOssSidePanel);
|
||||
const sidePanelHeight = useMainHeight();
|
||||
|
||||
useEffect(() => {
|
||||
setToastBottom(showPanel);
|
||||
return () => setToastBottom(false);
|
||||
}, [setToastBottom, showPanel]);
|
||||
|
||||
return (
|
||||
<aside
|
||||
className={cn(
|
||||
|
|
|
@ -4,18 +4,23 @@ import { CstType, type IConstituentaBasicsDTO, type ICreateConstituentaDTO } fro
|
|||
import { useCreateConstituenta } from '@/features/rsform/backend/use-create-constituenta';
|
||||
import { useMoveConstituents } from '@/features/rsform/backend/use-move-constituents';
|
||||
import { useMutatingRSForm } from '@/features/rsform/backend/use-mutating-rsform';
|
||||
import { useResetAliases } from '@/features/rsform/backend/use-reset-aliases';
|
||||
import { useRestoreOrder } from '@/features/rsform/backend/use-restore-order';
|
||||
import { generateAlias } from '@/features/rsform/models/rsform-api';
|
||||
import { useCstSearchStore } from '@/features/rsform/stores/cst-search';
|
||||
|
||||
import { MiniButton } from '@/components/control';
|
||||
import { Dropdown, DropdownButton, useDropdown } from '@/components/dropdown';
|
||||
import {
|
||||
IconClone,
|
||||
IconDestroy,
|
||||
IconEdit2,
|
||||
IconGenerateNames,
|
||||
IconMoveDown,
|
||||
IconMoveUp,
|
||||
IconNewItem,
|
||||
IconRSForm,
|
||||
IconSortList,
|
||||
IconTree,
|
||||
IconTypeGraph
|
||||
} from '@/components/icons';
|
||||
|
@ -43,6 +48,7 @@ export function ToolbarSchema({
|
|||
isMutable,
|
||||
className
|
||||
}: ToolbarSchemaProps) {
|
||||
const menuSchema = useDropdown();
|
||||
const router = useConceptNavigation();
|
||||
const isProcessing = useMutatingRSForm();
|
||||
const searchText = useCstSearchStore(state => state.query);
|
||||
|
@ -54,6 +60,8 @@ export function ToolbarSchema({
|
|||
const showTermGraph = useDialogsStore(state => state.showShowTermGraph);
|
||||
const { moveConstituents } = useMoveConstituents();
|
||||
const { createConstituenta } = useCreateConstituenta();
|
||||
const { resetAliases } = useResetAliases();
|
||||
const { restoreOrder } = useRestoreOrder();
|
||||
|
||||
function navigateRSForm() {
|
||||
router.push({ path: urls.schema(schema.id) });
|
||||
|
@ -181,14 +189,50 @@ export function ToolbarSchema({
|
|||
showTermGraph({ schema: schema });
|
||||
}
|
||||
|
||||
function handleReindex() {
|
||||
menuSchema.hide();
|
||||
void resetAliases({ itemID: schema.id });
|
||||
}
|
||||
|
||||
function handleRestoreOrder() {
|
||||
menuSchema.hide();
|
||||
void restoreOrder({ itemID: schema.id });
|
||||
}
|
||||
|
||||
return (
|
||||
<div className={cn('flex gap-0.5', className)}>
|
||||
<MiniButton
|
||||
title='Перейти к концептуальной схеме'
|
||||
icon={<IconRSForm size='1rem' className='icon-primary' />}
|
||||
onClick={navigateRSForm}
|
||||
/>
|
||||
|
||||
<div ref={menuSchema.ref} onBlur={menuSchema.handleBlur} className='flex relative items-center'>
|
||||
<MiniButton
|
||||
title='Редактирование концептуальной схемы'
|
||||
hideTitle={menuSchema.isOpen}
|
||||
icon={<IconRSForm size='1rem' className='icon-primary' />}
|
||||
onClick={menuSchema.toggle}
|
||||
/>
|
||||
<Dropdown isOpen={menuSchema.isOpen} margin='mt-0.5'>
|
||||
<DropdownButton
|
||||
text='Упорядочить список'
|
||||
titleHtml='Упорядочить список, исходя из <br/>логики типов и связей конституент'
|
||||
aria-label='Упорядочить список, исходя из логики типов и связей конституент'
|
||||
icon={<IconSortList size='1rem' className='icon-primary' />}
|
||||
onClick={handleRestoreOrder}
|
||||
disabled={!isMutable || isProcessing}
|
||||
/>
|
||||
<DropdownButton
|
||||
text='Порядковые имена'
|
||||
titleHtml='Присвоить порядковые имена <br/>и обновить выражения'
|
||||
aria-label='Присвоить порядковые имена и обновить выражения'
|
||||
icon={<IconGenerateNames size='1rem' className='icon-primary' />}
|
||||
onClick={handleReindex}
|
||||
disabled={!isMutable || isProcessing}
|
||||
/>
|
||||
<DropdownButton
|
||||
title='Перейти к концептуальной схеме'
|
||||
text='перейти к схеме'
|
||||
icon={<IconRSForm size='1rem' className='icon-primary' />}
|
||||
onClick={navigateRSForm}
|
||||
/>
|
||||
</Dropdown>
|
||||
</div>
|
||||
<MiniButton
|
||||
title='Редактировать конституенту'
|
||||
icon={<IconEdit2 size='1rem' className='icon-primary' />}
|
||||
|
|
|
@ -10,6 +10,9 @@ interface AppLayoutStore {
|
|||
|
||||
noFooter: boolean;
|
||||
hideFooter: (value?: boolean) => void;
|
||||
|
||||
toastBottom: boolean;
|
||||
setToastBottom: (value: boolean) => void;
|
||||
}
|
||||
|
||||
export const useAppLayoutStore = create<AppLayoutStore>()(set => ({
|
||||
|
@ -26,7 +29,10 @@ export const useAppLayoutStore = create<AppLayoutStore>()(set => ({
|
|||
}),
|
||||
|
||||
noFooter: false,
|
||||
hideFooter: value => set({ noFooter: value ?? true })
|
||||
hideFooter: value => set({ noFooter: value ?? true }),
|
||||
|
||||
toastBottom: false,
|
||||
setToastBottom: value => set({ toastBottom: value })
|
||||
}));
|
||||
|
||||
/** Utility function that returns the height of the main area. */
|
||||
|
|
Loading…
Reference in New Issue
Block a user