Merge commit '80a562d90d1d354c580351a2c94d32aa024b139e' into context-menu-vertical

This commit is contained in:
brendanlaschke
2023-08-10 20:27:05 +02:00
53 changed files with 1561 additions and 277 deletions

View File

@ -0,0 +1,17 @@
import { IconCheckbox } from '@/ui/icon/index';
import { EntityTableActionBarButton } from './EntityTableActionBarButton';
type OwnProps = {
onClick: () => void;
};
export function TableActionBarButtonToggleTasks({ onClick }: OwnProps) {
return (
<EntityTableActionBarButton
label="Task"
icon={<IconCheckbox size={16} />}
onClick={onClick}
/>
);
}

View File

@ -5,19 +5,20 @@ import styled from '@emotion/styled';
import { useRecoilCallback, useRecoilState, useRecoilValue } from 'recoil';
import { IconButton } from '@/ui/button/components/IconButton';
import type {
ViewFieldDefinition,
ViewFieldMetadata,
} from '@/ui/editable-field/types/ViewField';
import { IconPlus } from '@/ui/icon';
import { useTrackPointer } from '@/ui/utilities/pointer-event/hooks/useTrackPointer';
import { GET_VIEW_FIELDS } from '@/views/queries/select';
import { currentViewIdState } from '@/views/states/currentViewIdState';
import {
useCreateViewFieldMutation,
useUpdateViewFieldMutation,
} from '~/generated/graphql';
import type {
ViewFieldDefinition,
ViewFieldMetadata,
} from '../../editable-field/types/ViewField';
import { toViewFieldInput } from '../hooks/useLoadView';
import { toViewFieldInput } from '../hooks/useLoadViewFields';
import { resizeFieldOffsetState } from '../states/resizeFieldOffsetState';
import {
addableViewFieldDefinitionsState,
@ -89,6 +90,7 @@ export function EntityTableHeader() {
const theme = useTheme();
const [{ objectName }, setViewFieldsState] = useRecoilState(viewFieldsState);
const currentViewId = useRecoilValue(currentViewIdState);
const viewFields = useRecoilValue(visibleViewFieldsState);
const columnWidths = useRecoilValue(columnWidthByViewFieldIdState);
const addableViewFieldDefinitions = useRecoilValue(
@ -176,15 +178,18 @@ export function EntityTableHeader() {
createViewFieldMutation({
variables: {
data: toViewFieldInput(objectName, {
...viewFieldDefinition,
columnOrder: viewFields.length + 1,
}),
data: {
...toViewFieldInput(objectName, {
...viewFieldDefinition,
columnOrder: viewFields.length + 1,
}),
view: { connect: { id: currentViewId } },
},
},
refetchQueries: [getOperationName(GET_VIEW_FIELDS) ?? ''],
});
},
[createViewFieldMutation, objectName, viewFields.length],
[createViewFieldMutation, currentViewId, objectName, viewFields.length],
);
return (

View File

@ -6,7 +6,7 @@ import {
import { FilterDefinition } from '@/ui/filter-n-sort/types/FilterDefinition';
import { useSetEntityTableData } from '@/ui/table/hooks/useSetEntityTableData';
import { useLoadView } from '../hooks/useLoadView';
import { useLoadViewFields } from '../hooks/useLoadViewFields';
export function GenericEntityTableData({
objectName,
@ -27,7 +27,7 @@ export function GenericEntityTableData({
}) {
const setEntityTableData = useSetEntityTableData();
useLoadView({ objectName, viewFieldDefinitions });
useLoadViewFields({ objectName, viewFieldDefinitions });
useGetRequest({
variables: { orderBy, where: whereFilters },

View File

@ -40,7 +40,8 @@ export function GenericEditableDoubleTextChipCellDisplayMode({
}),
);
const displayName = `${firstValue} ${secondValue}`;
const displayName =
firstValue || secondValue ? `${firstValue} ${secondValue}` : ' ';
switch (viewField.metadata.entityType) {
case Entity.Company: {

View File

@ -7,6 +7,7 @@ import {
import { useCurrentRowEntityId } from '@/ui/table/hooks/useCurrentEntityId';
import { useUpdateEntityField } from '@/ui/table/hooks/useUpdateEntityField';
import { tableEntityFieldFamilySelector } from '@/ui/table/states/tableEntityFieldFamilySelector';
import { isURL } from '~/utils/is-url';
import { TextCellEdit } from './TextCellEdit';
@ -30,6 +31,8 @@ export function GenericEditableURLCellEditMode({ viewField }: OwnProps) {
function handleSubmit(newText: string) {
if (newText === fieldValue) return;
if (!isURL(newText)) return;
setFieldValue(newText);
if (currentRowEntityId && updateField) {

View File

@ -1,18 +1,19 @@
import { getOperationName } from '@apollo/client/utilities';
import { useSetRecoilState } from 'recoil';
import { useRecoilValue, useSetRecoilState } from 'recoil';
import type {
ViewFieldDefinition,
ViewFieldMetadata,
ViewFieldTextMetadata,
} from '@/ui/editable-field/types/ViewField';
import { GET_VIEW_FIELDS } from '@/views/queries/select';
import { currentViewIdState } from '@/views/states/currentViewIdState';
import {
SortOrder,
useCreateViewFieldsMutation,
useGetViewFieldsQuery,
} from '~/generated/graphql';
import type {
ViewFieldDefinition,
ViewFieldMetadata,
ViewFieldTextMetadata,
} from '../../editable-field/types/ViewField';
import { entityTableDimensionsState } from '../states/entityTableDimensionsState';
import { viewFieldsState } from '../states/viewFieldsState';
@ -33,13 +34,14 @@ export const toViewFieldInput = (
sizeInPx: viewFieldDefinition.columnSize,
});
export const useLoadView = ({
export const useLoadViewFields = ({
objectName,
viewFieldDefinitions,
}: {
objectName: 'company' | 'person';
viewFieldDefinitions: ViewFieldDefinition<ViewFieldMetadata>[];
}) => {
const currentViewId = useRecoilValue(currentViewIdState);
const setEntityTableDimensions = useSetRecoilState(
entityTableDimensionsState,
);
@ -50,7 +52,10 @@ export const useLoadView = ({
useGetViewFieldsQuery({
variables: {
orderBy: { index: SortOrder.Asc },
where: { objectName: { equals: objectName } },
where: {
objectName: { equals: objectName },
viewId: { equals: currentViewId ?? null },
},
},
onCompleted: (data) => {
if (data.viewFields.length) {
@ -79,9 +84,10 @@ export const useLoadView = ({
// Populate if empty
createViewFieldsMutation({
variables: {
data: viewFieldDefinitions.map((viewFieldDefinition) =>
toViewFieldInput(objectName, viewFieldDefinition),
),
data: viewFieldDefinitions.map((viewFieldDefinition) => ({
...toViewFieldInput(objectName, viewFieldDefinition),
viewId: currentViewId,
})),
},
refetchQueries: [getOperationName(GET_VIEW_FIELDS) ?? ''],
});

View File

@ -1,12 +1,14 @@
import { ReactNode, useCallback, useState } from 'react';
import { ReactNode, useCallback } from 'react';
import styled from '@emotion/styled';
import { FilterDropdownButton } from '@/ui/filter-n-sort/components/FilterDropdownButton';
import SortAndFilterBar from '@/ui/filter-n-sort/components/SortAndFilterBar';
import { SortDropdownButton } from '@/ui/filter-n-sort/components/SortDropdownButton';
import { sortScopedState } from '@/ui/filter-n-sort/states/sortScopedState';
import { FiltersHotkeyScope } from '@/ui/filter-n-sort/types/FiltersHotkeyScope';
import { SelectedSortType, SortType } from '@/ui/filter-n-sort/types/interface';
import { TopBar } from '@/ui/top-bar/TopBar';
import { useRecoilScopedState } from '@/ui/utilities/recoil-scope/hooks/useRecoilScopedState';
import { OptionsDropdownButton } from '@/views/components/OptionsDropdownButton';
import { TableContext } from '../../states/TableContext';
@ -34,26 +36,26 @@ export function TableHeader<SortField>({
availableSorts,
onSortsUpdate,
}: OwnProps<SortField>) {
const [sorts, innerSetSorts] = useState<Array<SelectedSortType<SortField>>>(
[],
const [sorts, setSorts] = useRecoilScopedState<SelectedSortType<SortField>[]>(
sortScopedState,
TableContext,
);
const handleSortsUpdate = onSortsUpdate ?? setSorts;
const sortSelect = useCallback(
(newSort: SelectedSortType<SortField>) => {
const newSorts = updateSortOrFilterByKey(sorts, newSort);
innerSetSorts(newSorts);
onSortsUpdate && onSortsUpdate(newSorts);
handleSortsUpdate(newSorts);
},
[onSortsUpdate, sorts],
[handleSortsUpdate, sorts],
);
const sortUnselect = useCallback(
(sortKey: string) => {
const newSorts = sorts.filter((sort) => sort.key !== sortKey);
innerSetSorts(newSorts);
onSortsUpdate && onSortsUpdate(newSorts);
handleSortsUpdate(newSorts);
},
[onSortsUpdate, sorts],
[handleSortsUpdate, sorts],
);
return (
@ -88,8 +90,7 @@ export function TableHeader<SortField>({
sorts={sorts}
onRemoveSort={sortUnselect}
onCancelClick={() => {
innerSetSorts([]);
onSortsUpdate && onSortsUpdate([]);
handleSortsUpdate([]);
}}
/>
}