Bug Fix: company create from people + scroll settings (#545)

This commit is contained in:
Charles Bochet
2023-07-08 18:15:39 -07:00
committed by GitHub
parent ce14d22744
commit 9d25d003ca
9 changed files with 55 additions and 120 deletions

View File

@ -12,7 +12,6 @@ export function useHotkeysScopeStackAutoSync() {
const hotkeysScopeStack = useRecoilValue(hotkeysScopeStackState);
const customHotkeysScopes = useRecoilValue(customHotkeysScopesState);
useEffect(() => {
if (hotkeysScopeStack.length === 0) {
return;

View File

@ -20,9 +20,7 @@ export function PeopleCompanyCell({ people }: OwnProps) {
return (
<EditableCell
editHotkeysScope={
!isCreating ? { scope: InternalHotkeysScope.RelationPicker } : undefined
}
editHotkeysScope={{ scope: InternalHotkeysScope.RelationPicker }}
editModeContent={
isCreating ? (
<PeopleCompanyCreateCell people={people} />

View File

@ -1,12 +1,10 @@
import { useRef, useState } from 'react';
import { useHotkeys } from 'react-hotkeys-hook';
import { useState } from 'react';
import { v4 } from 'uuid';
import { useRecoilScopedState } from '@/recoil-scope/hooks/useRecoilScopedState';
import { relationPickerSearchFilterScopedState } from '@/relation-picker/states/relationPickerSearchFilterScopedState';
import { isCreateModeScopedState } from '@/ui/components/editable-cell/states/isCreateModeScopedState';
import { DoubleTextInput } from '@/ui/components/inputs/DoubleTextInput';
import { useListenClickOutsideArrayOfRef } from '@/ui/hooks/useListenClickOutsideArrayOfRef';
import { EditableCellDoubleTextEditMode } from '@/ui/components/editable-cell/types/EditableCellDoubleTextEditMode';
import { logError } from '@/utils/logs/logError';
import {
Person,
@ -31,8 +29,6 @@ export function PeopleCompanyCreateCell({ people }: OwnProps) {
const [insertCompany] = useInsertCompanyMutation();
const [updatePeople] = useUpdatePeopleMutation();
const containerRef = useRef(null);
function handleDoubleTextChange(leftValue: string, rightValue: string): void {
setCompanyDomainName(leftValue);
setCompanyName(rightValue);
@ -65,34 +61,18 @@ export function PeopleCompanyCreateCell({ people }: OwnProps) {
// TODO: handle error better
logError(error);
}
setIsCreating(false);
}
useHotkeys(
'enter, escape',
() => {
handleCompanyCreate(companyName, companyDomainName);
},
{
enableOnFormTags: true,
enableOnContentEditable: true,
preventDefault: true,
},
[companyName, companyDomainName, handleCompanyCreate],
);
useListenClickOutsideArrayOfRef([containerRef], () => {
handleCompanyCreate(companyName, companyDomainName);
});
return (
<DoubleTextInput
leftValue={companyDomainName}
rightValue={companyName}
leftValuePlaceholder="URL"
rightValuePlaceholder="Name"
<EditableCellDoubleTextEditMode
firstValue={companyDomainName}
secondValue={companyName}
firstValuePlaceholder="URL"
secondValuePlaceholder="Name"
onChange={handleDoubleTextChange}
onSubmit={() => handleCompanyCreate(companyName, companyDomainName)}
onExit={() => setIsCreating(false)}
/>
);
}

View File

@ -1,5 +1,6 @@
import { Key } from 'ts-key-enum';
import { useAddToHotkeysScopeStack } from '@/hotkeys/hooks/useAddToHotkeysScopeStack';
import { useScopedHotkeys } from '@/hotkeys/hooks/useScopedHotkeys';
import { InternalHotkeysScope } from '@/hotkeys/types/internal/InternalHotkeysScope';
import { useRecoilScopedState } from '@/recoil-scope/hooks/useRecoilScopedState';
@ -31,6 +32,8 @@ export function PeopleCompanyPicker({ people }: OwnProps) {
const { closeEditableCell } = useEditableCell();
const addToScopeStack = useAddToHotkeysScopeStack();
const companies = useFilteredSearchEntityQuery({
queryHook: useSearchCompanyQuery,
selectedIds: [people.company?.id ?? ''],
@ -59,6 +62,7 @@ export function PeopleCompanyPicker({ people }: OwnProps) {
function handleCreate() {
setIsCreating(true);
addToScopeStack({ scope: InternalHotkeysScope.CellDoubleTextInput });
}
useScopedHotkeys(

View File

@ -15,6 +15,8 @@ type OwnProps = {
firstValuePlaceholder: string;
secondValuePlaceholder: string;
onChange: (firstValue: string, secondValue: string) => void;
onSubmit?: (firstValue: string, secondValue: string) => void;
onExit?: () => void;
};
const StyledContainer = styled.div`
@ -34,6 +36,8 @@ export function EditableCellDoubleTextEditMode({
firstValuePlaceholder,
secondValuePlaceholder,
onChange,
onSubmit,
onExit,
}: OwnProps) {
const [focusPosition, setFocusPosition] = useState<'left' | 'right'>('left');
@ -53,6 +57,9 @@ export function EditableCellDoubleTextEditMode({
() => {
closeCell();
moveDown();
if (onSubmit) {
onSubmit(firstValue, secondValue);
}
},
InternalHotkeysScope.CellDoubleTextInput,
[closeCell],
@ -61,6 +68,9 @@ export function EditableCellDoubleTextEditMode({
useScopedHotkeys(
Key.Escape,
() => {
if (onExit) {
onExit();
}
closeCell();
},
InternalHotkeysScope.CellDoubleTextInput,
@ -74,6 +84,9 @@ export function EditableCellDoubleTextEditMode({
setFocusPosition('right');
secondValueInputRef.current?.focus();
} else {
if (onExit) {
onExit();
}
closeCell();
moveRight();
}

View File

@ -1,58 +0,0 @@
import { ChangeEvent, useRef } from 'react';
import styled from '@emotion/styled';
type OwnProps = {
leftValue: string;
rightValue: string;
leftValuePlaceholder: string;
rightValuePlaceholder: string;
onChange: (leftValue: string, rightValue: string) => void;
};
const StyledContainer = styled.div`
align-items: center;
display: flex;
justify-content: space-between;
& > input:last-child {
border-left: 1px solid ${({ theme }) => theme.border.color.light};
padding-left: ${({ theme }) => theme.spacing(2)};
}
`;
const StyledEditInplaceInput = styled.input`
height: 18px;
width: 45%;
`;
export function DoubleTextInput({
leftValue,
rightValue,
leftValuePlaceholder,
rightValuePlaceholder,
onChange,
}: OwnProps) {
const firstValueInputRef = useRef<HTMLInputElement>(null);
return (
<StyledContainer>
<StyledEditInplaceInput
autoFocus
placeholder={leftValuePlaceholder}
ref={firstValueInputRef}
value={leftValue}
onChange={(event: ChangeEvent<HTMLInputElement>) => {
onChange(event.target.value, rightValue);
}}
/>
<StyledEditInplaceInput
placeholder={rightValuePlaceholder}
ref={firstValueInputRef}
value={rightValue}
onChange={(event: ChangeEvent<HTMLInputElement>) => {
onChange(leftValue, event.target.value);
}}
/>
</StyledContainer>
);
}

View File

@ -91,12 +91,6 @@ const StyledTableWithHeader = styled.div`
width: 100%;
`;
const StyledTableScrollableContainer = styled.div`
flex: 1;
height: 100%;
overflow: auto;
`;
export function EntityTable<TData extends { id: string }, SortField>({
data,
columns,
@ -137,7 +131,7 @@ export function EntityTable<TData extends { id: string }, SortField>({
availableSorts={availableSorts}
onSortsUpdate={onSortsUpdate}
/>
<StyledTableScrollableContainer ref={tableBodyRef}>
<div ref={tableBodyRef}>
<StyledTable>
<thead>
{table.getHeaderGroups().map((headerGroup) => (
@ -171,7 +165,7 @@ export function EntityTable<TData extends { id: string }, SortField>({
))}
</tbody>
</StyledTable>
</StyledTableScrollableContainer>
</div>
</StyledTableWithHeader>
);
}

View File

@ -7,6 +7,8 @@ const StyledPanel = styled.div`
border-radius: 8px;
display: flex;
flex-direction: row;
height: 100%;
overflow: auto;
width: 100%;
`;

View File

@ -13,6 +13,7 @@ const StyledContainer = styled.div`
display: flex;
flex-direction: column;
padding: ${({ theme }) => theme.spacing(8)};
padding-bottom: ${({ theme }) => theme.spacing(10)};
width: 350px;
> * + * {
margin-top: ${({ theme }) => theme.spacing(8)};
@ -33,27 +34,29 @@ export function SettingsProfile() {
return (
<NoTopBarContainer>
<StyledContainer>
<MainSectionTitle>Profile</MainSectionTitle>
<StyledSectionContainer>
<SubSectionTitle title="Picture" />
<ProfilePictureUploader />
</StyledSectionContainer>
<StyledSectionContainer>
<SubSectionTitle
title="Name"
description="Your name as it will be displayed"
/>
<NameFields />
</StyledSectionContainer>
<StyledSectionContainer>
<SubSectionTitle
title="Email"
description="The email associated to your account"
/>
<EmailField />
</StyledSectionContainer>
</StyledContainer>
<div>
<StyledContainer>
<MainSectionTitle>Profile</MainSectionTitle>
<StyledSectionContainer>
<SubSectionTitle title="Picture" />
<ProfilePictureUploader />
</StyledSectionContainer>
<StyledSectionContainer>
<SubSectionTitle
title="Name"
description="Your name as it will be displayed"
/>
<NameFields />
</StyledSectionContainer>
<StyledSectionContainer>
<SubSectionTitle
title="Email"
description="The email associated to your account"
/>
<EmailField />
</StyledSectionContainer>
</StyledContainer>
</div>
</NoTopBarContainer>
);
}