fix: fix pendant color error, fixed #537

This commit is contained in:
qishaoxuan
2022-07-26 15:44:34 +08:00
parent a7c76c0bce
commit 23b31b327f
11 changed files with 224 additions and 192 deletions

View File

@@ -1,4 +1,9 @@
import React from 'react';
import React, {
FC,
FunctionComponent,
PropsWithChildren,
CSSProperties,
} from 'react';
import { Tag, type TagProps } from '@toeverything/components/ui';
import {
DateValue,
@@ -18,7 +23,7 @@ import {
} from '../recast-block';
import { IconNames, PendantTypes } from './types';
import format from 'date-fns/format';
import { IconMap, pendantColors } from './config';
import { IconMap, defaultPendantColors } from './config';
type PendantTagProps = {
value: RecastBlockValue;
@@ -28,37 +33,33 @@ type PendantTagProps = {
const MultiSelectRender = ({
options,
tagProps,
property,
}: {
options: SelectOption[];
tagProps: TagProps;
property: RecastMetaProperty;
}) => {
const { style, ...otherProps } = tagProps;
return (
<>
{options.map((option: SelectOption) => {
const Icon = IconMap[option.iconName as IconNames];
const { background, color, icon, content } = getOptionInfo({
option,
property,
});
return (
<Tag
key={option.id}
{...otherProps}
style={{
background: style?.background || option.background,
color: style?.color || option.color,
background: style?.background || background,
color: style?.color || color,
...style,
}}
startElement={
Icon && (
<Icon
style={{
fontSize: 12,
color: style?.color || option.color,
marginRight: '4px',
}}
/>
)
}
startElement={icon}
>
{option.name}
{content}
</Tag>
);
})}
@@ -66,23 +67,80 @@ const MultiSelectRender = ({
);
};
export const PendantTag = (props: PendantTagProps) => {
const { value, property, ...tagProps } = props;
const getOptionInfo = ({
option,
property,
}: {
option: SelectOption;
property: RecastMetaProperty;
}) => {
const { type } = property;
const {
background: defaultBackground,
color: defaultColor,
iconName: defaultIconName,
} = defaultPendantColors[type];
const Icon =
IconMap[option?.iconName as IconNames] ||
IconMap[defaultIconName as IconNames];
return {
background: option?.background || defaultBackground,
color: option?.color || defaultColor,
icon: Icon && (
<Icon
style={{
fontSize: 12,
marginRight: '4px',
}}
/>
),
content: option?.name || property.name,
};
};
const getNormalInfo = (
value: RecastBlockValue,
property: RecastMetaProperty
) => {
const type = value.type;
const {
background: defaultBackground,
color: defaultColor,
iconName: defaultIconName,
} = defaultPendantColors[type];
const {
background: customBackground,
color: customColor,
iconName,
} = property;
const { style: styleTagStyle, ...otherTagProps } = tagProps;
const type = value.type;
const { background: defaultBackground, color: defaultColor } =
pendantColors[type];
const background = customBackground || defaultBackground;
const color = customColor || defaultColor;
const Icon = IconMap[iconName as IconNames];
const Icon =
IconMap[iconName as IconNames] || IconMap[defaultIconName as IconNames];
return {
background,
color,
icon: Icon && (
<Icon
style={{
fontSize: 12,
marginRight: '4px',
}}
/>
),
};
};
export const PendantTag = (props: PendantTagProps) => {
const { value, property, ...tagProps } = props;
const { style: styleTagStyle, ...otherTagProps } = tagProps;
if (value.type === PendantTypes.Text) {
const { value: textValue } = value as TextValue;
const { background, color, icon } = getNormalInfo(value, property);
return (
<Tag
style={{
@@ -90,17 +148,7 @@ export const PendantTag = (props: PendantTagProps) => {
color,
...styleTagStyle,
}}
startElement={
Icon && (
<Icon
style={{
fontSize: 12,
color: color || '#fff',
marginRight: '4px',
}}
/>
)
}
startElement={icon}
{...otherTagProps}
>
{textValue}
@@ -110,32 +158,14 @@ export const PendantTag = (props: PendantTagProps) => {
if (value.type === PendantTypes.Date) {
const { value: dateValue } = value as DateValue;
if (Array.isArray(dateValue)) {
return (
<Tag
style={{
background,
color,
...styleTagStyle,
}}
startElement={
Icon && (
<Icon
style={{
fontSize: 12,
color: color || '#fff',
marginRight: '4px',
}}
/>
)
}
{...otherTagProps}
>
{format(dateValue[0], 'yyyy-MM-dd')} ~{' '}
{format(dateValue[1], 'yyyy-MM-dd')}
</Tag>
);
}
const { background, color, icon } = getNormalInfo(value, property);
const content = Array.isArray(dateValue)
? `${format(dateValue[0], 'yyyy-MM-dd')} ~ ${format(
dateValue[1],
'yyyy-MM-dd'
)}`
: format(dateValue, 'yyyy-MM-dd');
return (
<Tag
style={{
@@ -143,20 +173,10 @@ export const PendantTag = (props: PendantTagProps) => {
color,
...styleTagStyle,
}}
startElement={
Icon && (
<Icon
style={{
fontSize: 12,
color: color || '#fff',
marginRight: '4px',
}}
/>
)
}
startElement={icon}
{...otherTagProps}
>
{format(dateValue, 'yyyy-MM-dd')}
{content}
</Tag>
);
}
@@ -166,14 +186,32 @@ export const PendantTag = (props: PendantTagProps) => {
const selectedOptions = (
property as MultiSelectProperty
).options.filter(o => multiSelectValue.includes(o.id));
const { style, ...otherProps } = tagProps;
if (selectedOptions.length) {
return (
<MultiSelectRender
options={selectedOptions}
tagProps={tagProps}
property={property}
/>
);
} else {
const { background, color, icon } = getNormalInfo(value, property);
return (
<Tag
style={{
background,
color,
...styleTagStyle,
}}
startElement={icon}
{...otherTagProps}
>
{property.name}
</Tag>
);
}
}
@@ -184,28 +222,23 @@ export const PendantTag = (props: PendantTagProps) => {
const option = (property as SelectProperty).options.find(
o => o.id === selectValue
);
const OptionIcon = IconMap[option.iconName as IconNames];
const { background, color, icon, content } = getOptionInfo({
option,
property,
});
return (
<Tag
style={{
background: option.background,
color: option.color,
background,
color,
...style,
}}
startElement={
OptionIcon && (
<OptionIcon
style={{
fontSize: 12,
color: option.color || '#fff',
marginRight: '4px',
}}
/>
)
}
startElement={icon}
{...otherProps}
>
{option.name}
{content}
</Tag>
);
}
@@ -217,35 +250,29 @@ export const PendantTag = (props: PendantTagProps) => {
const option = (property as StatusProperty).options.find(
o => o.id === statusValue
);
const OptionIcon = IconMap[option.iconName as IconNames];
const { background, color, icon, content } = getOptionInfo({
option,
property,
});
return (
<Tag
style={{
background: option.background,
color: option.color,
background,
color,
...style,
}}
startElement={
OptionIcon && (
<OptionIcon
style={{
fontSize: 12,
color: option.color || '#fff',
marginRight: '4px',
}}
/>
)
}
startElement={icon}
{...otherProps}
>
{option.name}
{content}
</Tag>
);
}
if (value.type === PendantTypes.Mention) {
const { value: mentionValue } = value as MentionValue;
const { background, color, icon } = getNormalInfo(value, property);
return (
<Tag
@@ -254,20 +281,10 @@ export const PendantTag = (props: PendantTagProps) => {
color,
...styleTagStyle,
}}
startElement={
Icon && (
<Icon
style={{
fontSize: 12,
color: color || '#fff',
marginRight: '4px',
}}
/>
)
}
startElement={icon}
{...otherTagProps}
>
@{mentionValue}
{mentionValue}
</Tag>
);
}
@@ -299,17 +316,36 @@ export const PendantTag = (props: PendantTagProps) => {
<MultiSelectRender
options={emailSelectedOptions}
tagProps={tagProps}
property={property}
/>
<MultiSelectRender
options={phoneSelectedOptions}
tagProps={tagProps}
property={property}
/>
<MultiSelectRender
options={locationSelectedOptions}
tagProps={tagProps}
property={property}
/>
</>
);
} else {
const { background, color, icon } = getNormalInfo(value, property);
return (
<Tag
style={{
background,
color,
...styleTagStyle,
}}
startElement={icon}
{...otherTagProps}
>
{property.name}
</Tag>
);
}
}

View File

@@ -1,5 +1,5 @@
import {
PendantIconConfig,
PendantConfig,
PendantOptions,
PendantTypes,
IconNames,
@@ -34,34 +34,41 @@ import {
// { background: '#E3DEFF', color: '#511AAB' },
// ];
export const pendantColors = {
export const defaultPendantColors = {
[PendantTypes.Text]: {
background: '#7389FD',
iconName: IconNames.TEXT,
background: '#67dcaa',
color: '#FFF',
},
[PendantTypes.Date]: {
background: '#5DC6CD',
iconName: IconNames.DATE,
background: '#6880FF',
color: '#FFF',
},
[PendantTypes.Select]: {
background: '#EAAE14',
color: '#FFF',
iconName: IconNames.SINGLE_SELECT,
background: '#C3DBFF',
color: '#253486',
},
[PendantTypes.MultiSelect]: {
background: '#A691FC',
color: '#FFF',
iconName: IconNames.MULTI_SELECT,
background: '#C6F1F3',
color: '#0C6066',
},
[PendantTypes.Mention]: {
background: '#57C696',
iconName: IconNames.COLLABORATOR,
background: '#FFD568',
color: '#FFF',
},
[PendantTypes.Status]: {
background: '#57C696',
color: '#FFF',
iconName: IconNames.STATUS,
background: '#C5FBE0',
color: '#05683D',
},
[PendantTypes.Information]: {
background: '#57C696',
color: '#FFF',
iconName: IconNames.INFORMATION,
background: '#ffcca7',
color: '#8f4400',
},
};
@@ -78,20 +85,24 @@ export const IconMap = {
[IconNames.EMAIL]: EmailIcon,
};
export const pendantIconConfig: { [key: string]: PendantIconConfig } = {
export const pendantConfig: { [key: string]: PendantConfig } = {
[PendantTypes.Text]: {
name: IconNames.TEXT,
iconName: IconNames.TEXT,
background: '#67dcaa',
color: '#FFF',
},
[PendantTypes.Date]: { name: IconNames.DATE, background: '', color: '' },
[PendantTypes.Date]: {
iconName: IconNames.DATE,
background: '#6880FF',
color: '#fff',
},
[PendantTypes.Status]: {
name: IconNames.STATUS,
iconName: IconNames.STATUS,
background: ['#C5FBE0', '#FFF5AB', '#FFCECE', '#E3DEFF'],
color: ['#05683D', '#896406', '#AF1212', '#511AAB'],
},
[PendantTypes.Select]: {
name: IconNames.SINGLE_SELECT,
iconName: IconNames.SINGLE_SELECT,
background: [
'#C3DBFF',
'#C6F1F3',
@@ -113,7 +124,7 @@ export const pendantIconConfig: { [key: string]: PendantIconConfig } = {
},
[PendantTypes.MultiSelect]: {
name: IconNames.MULTI_SELECT,
iconName: IconNames.MULTI_SELECT,
background: [
'#C3DBFF',
'#C6F1F3',
@@ -134,27 +145,27 @@ export const pendantIconConfig: { [key: string]: PendantIconConfig } = {
],
},
[PendantTypes.Mention]: {
name: IconNames.COLLABORATOR,
iconName: IconNames.COLLABORATOR,
background: '#FFD568',
color: '#FFFFFF',
},
[PendantTypes.Information]: {
name: IconNames.INFORMATION,
iconName: IconNames.INFORMATION,
background: '#FFD568',
color: '#FFFFFF',
},
Phone: {
name: IconNames.PHONE,
iconName: IconNames.PHONE,
background: '#c3dbff',
color: '#263486',
},
Location: {
name: IconNames.LOCATION,
iconName: IconNames.LOCATION,
background: '#c5f1f3',
color: '#263486',
},
Email: {
name: IconNames.EMAIL,
iconName: IconNames.EMAIL,
background: '#ffcca7',
color: '#8f4400',
},

View File

@@ -27,7 +27,7 @@ export default ({
placeholder={
<>
<PendantIcon
iconName={iconConfig?.name}
iconName={iconConfig?.iconName}
color={iconConfig?.color as CSSProperties['color']}
background={
iconConfig?.background as CSSProperties['background']

View File

@@ -9,12 +9,8 @@ import { Add, Delete, Close } from '@mui/icons-material';
import { ModifyPanelContentProps } from './types';
import {
MultiSelectProperty,
MultiSelectValue,
SelectOption,
SelectProperty,
SelectOptionId,
RecastBlockValue,
RecastMetaProperty,
} from '../../recast-block';
import {
Checkbox,
@@ -24,12 +20,7 @@ import {
Tooltip,
} from '@toeverything/components/ui';
import { HighLightIconInput } from './IconInput';
import {
PendantIconConfig,
IconNames,
OptionIdType,
OptionType,
} from '../types';
import { PendantConfig, IconNames, OptionIdType, OptionType } from '../types';
import { genBasicOption } from '../utils';
type OptionItemType = {
@@ -67,7 +58,7 @@ export const BasicSelect = ({
initialOptions: OptionType[];
onValueChange: (value: any) => void;
onPropertyChange?: (newProperty: any) => void;
iconConfig?: PendantIconConfig;
iconConfig?: PendantConfig;
onEnter?: (e: KeyboardEvent) => void;
}) => {
const [options, setOptions] = useState<OptionType[]>(initialOptions);

View File

@@ -11,7 +11,7 @@ export default ({
const [text, setText] = useState(initialValue?.value || '');
return (
<HighLightIconInput
iconName={iconConfig?.name}
iconName={iconConfig?.iconName}
color={iconConfig?.color as CSSProperties['color']}
background={iconConfig?.background as CSSProperties['background']}
value={text}

View File

@@ -1,6 +1,5 @@
import { OptionType, PendantIconConfig, PendantTypes } from '../types';
import { OptionType, PendantConfig, PendantTypes } from '../types';
import type { RecastBlockValue, RecastMetaProperty } from '../../recast-block';
import { FunctionComponent } from 'react';
export type ModifyPanelProps = {
type: PendantTypes | PendantTypes[];
@@ -9,7 +8,7 @@ export type ModifyPanelProps = {
onCancel?: () => void;
initialValue?: RecastBlockValue;
initialOptions?: OptionType[];
iconConfig?: PendantIconConfig;
iconConfig?: PendantConfig;
isStatusSelect?: boolean;
property?: RecastMetaProperty;
};
@@ -20,7 +19,7 @@ export type ModifyPanelContentProps = {
onPropertyChange?: (newProperty: any) => void;
initialValue?: RecastBlockValue;
initialOptions?: OptionType[];
iconConfig?: PendantIconConfig;
iconConfig?: PendantConfig;
isStatusSelect?: boolean;
property?: RecastMetaProperty;
};

View File

@@ -3,7 +3,7 @@ import { Input, Option, Select, Tooltip } from '@toeverything/components/ui';
import { HelpCenterIcon } from '@toeverything/components/icons';
import { AsyncBlock } from '../../editor';
import { pendantOptions, IconMap, pendantIconConfig } from '../config';
import { pendantOptions, IconMap } from '../config';
import { OptionType, PendantOptions, PendantTypes } from '../types';
import { PendantModifyPanel } from '../pendant-modify-panel';
import {
@@ -25,7 +25,7 @@ import {
import {
genInitialOptions,
getOfficialSelected,
getPendantIconsConfigByType,
getPendantConfigByType,
} from '../utils';
import { usePendant } from '../use-pendant';
@@ -101,9 +101,9 @@ export const CreatePendantPanel = ({
// Select, MultiSelect, Status use this props as initial property
initialOptions={genInitialOptions(
selectedOption.type,
getPendantIconsConfigByType(selectedOption.type)
getPendantConfigByType(selectedOption.type)
)}
iconConfig={getPendantIconsConfigByType(
iconConfig={getPendantConfigByType(
selectedOption.type
)}
// isStatusSelect={selectedOption.name === 'Status'}
@@ -178,7 +178,7 @@ export const CreatePendantPanel = ({
} else {
// TODO: Color and background should use pendant config, but ui is not design now
const iconConfig =
getPendantIconsConfigByType(type);
getPendantConfigByType(type);
// TODO: Color and background should be choose by user in the future
const newProperty = await addProperty({
type: type,
@@ -186,7 +186,7 @@ export const CreatePendantPanel = ({
background:
iconConfig.background as CSSProperties['background'],
color: iconConfig.color as CSSProperties['color'],
iconName: iconConfig.name,
iconName: iconConfig.iconName,
});
await setPendant(newProperty, newValue);

View File

@@ -15,7 +15,7 @@ import {
import { OptionType, PendantTypes, TempInformationType } from '../types';
import {
getOfficialSelected,
getPendantIconsConfigByType,
getPendantConfigByType,
// getPendantIconsConfigByNameOrType,
} from '../utils';
import { usePendant } from '../use-pendant';
@@ -52,8 +52,8 @@ export const UpdatePendantPanel = ({
const { updateSelect } = useSelectProperty();
const { setPendant, removePendant } = usePendant(block);
const pendantOption = pendantOptions.find(v => v.type === property.type);
const iconConfig = getPendantIconsConfigByType(property.type);
const Icon = IconMap[iconConfig.name];
const iconConfig = getPendantConfigByType(property.type);
const Icon = IconMap[iconConfig.iconName];
const { updateProperty } = useRecastBlockMeta();
return (
@@ -84,7 +84,7 @@ export const UpdatePendantPanel = ({
value: value.value,
} as RecastBlockValue
}
iconConfig={getPendantIconsConfigByType(property.type)}
iconConfig={getPendantConfigByType(property.type)}
property={property}
type={property.type}
onSure={async (type, newPropertyItem, newValue) => {

View File

@@ -10,7 +10,7 @@ import {
import { Popover, PopperHandler, styled } from '@toeverything/components/ui';
import { PendantTag } from '../PendantTag';
import { pendantColors } from '../config';
import { defaultPendantColors } from '../config';
import { UpdatePendantPanel } from '../pendant-operation-panel';
import { AddPendantPopover } from '../AddPendantPopover';
import { PendantTypes } from '../types';

View File

@@ -34,8 +34,8 @@ export type PendantOptions = {
subTitle: string;
};
export type PendantIconConfig = {
name: IconNames;
export type PendantConfig = {
iconName: IconNames;
// background: CSSProperties['background'];
// color: CSSProperties['color'];
background: CSSProperties['background'] | CSSProperties['background'][];

View File

@@ -1,14 +1,11 @@
import {
PropertyType,
RecastBlockValue,
RecastPropertyId,
RecastMetaProperty,
SelectOption,
SelectOptionId,
} from '../recast-block';
import { OptionIdType, OptionType } from './types';
import { pendantIconConfig } from './config';
import { PendantIconConfig, PendantTypes } from './types';
import { pendantConfig } from './config';
import { PendantConfig, PendantTypes } from './types';
type Props = {
recastBlockId: string;
blockId: string;
@@ -24,12 +21,12 @@ type StorageMap = {
};
};
const LOCAL_STROAGE_NAME = 'TEMPORARY_PENDANT_DATA';
const LOCAL_STORAGE_NAME = 'TEMPORARY_PENDANT_DATA';
const ensureLocalStorage = () => {
const data = localStorage.getItem(LOCAL_STROAGE_NAME);
const data = localStorage.getItem(LOCAL_STORAGE_NAME);
if (!data) {
localStorage.setItem(LOCAL_STROAGE_NAME, JSON.stringify({}));
localStorage.setItem(LOCAL_STORAGE_NAME, JSON.stringify({}));
}
};
@@ -40,7 +37,7 @@ export const setLatestPropertyValue = ({
}: Props) => {
ensureLocalStorage();
const data: StorageMap = JSON.parse(
localStorage.getItem(LOCAL_STROAGE_NAME) as string
localStorage.getItem(LOCAL_STORAGE_NAME) as string
);
if (!data[recastBlockId]) {
@@ -53,7 +50,7 @@ export const setLatestPropertyValue = ({
value,
};
localStorage.setItem(LOCAL_STROAGE_NAME, JSON.stringify(data));
localStorage.setItem(LOCAL_STORAGE_NAME, JSON.stringify(data));
};
export const getLatestPropertyValue = ({
@@ -68,7 +65,7 @@ export const getLatestPropertyValue = ({
}> => {
ensureLocalStorage();
const data: StorageMap = JSON.parse(
localStorage.getItem(LOCAL_STROAGE_NAME) as string
localStorage.getItem(LOCAL_STORAGE_NAME) as string
);
if (!data[recastBlockId]) {
@@ -95,7 +92,7 @@ export const removePropertyValueRecord = ({
}) => {
ensureLocalStorage();
const data: StorageMap = JSON.parse(
localStorage.getItem(LOCAL_STROAGE_NAME) as string
localStorage.getItem(LOCAL_STORAGE_NAME) as string
);
if (!data[recastBlockId]) {
return;
@@ -103,7 +100,7 @@ export const removePropertyValueRecord = ({
delete data[recastBlockId][propertyId];
localStorage.setItem(LOCAL_STROAGE_NAME, JSON.stringify(data));
localStorage.setItem(LOCAL_STORAGE_NAME, JSON.stringify(data));
};
/**
@@ -146,16 +143,14 @@ export const getOfficialSelected = ({
return selectedId;
};
export const getPendantIconsConfigByType = (
pendantType: string
): PendantIconConfig => {
return pendantIconConfig[pendantType];
export const getPendantConfigByType = (pendantType: string): PendantConfig => {
return pendantConfig[pendantType];
};
export const getPendantIconsConfigByName = (
pendantName?: string
): PendantIconConfig => {
return pendantIconConfig[pendantName];
): PendantConfig => {
return pendantConfig[pendantName];
};
export const genBasicOption = ({
@@ -164,10 +159,10 @@ export const genBasicOption = ({
name = '',
}: {
index: number;
iconConfig: PendantIconConfig;
iconConfig: PendantConfig;
name?: string;
}): OptionType => {
const iconName = iconConfig.name;
const iconName = iconConfig.iconName;
const background = Array.isArray(iconConfig.background)
? iconConfig.background[index % iconConfig.background.length]
: iconConfig.background;
@@ -189,7 +184,7 @@ export const genBasicOption = ({
* **/
export const genInitialOptions = (
type: PendantTypes,
iconConfig: PendantIconConfig
iconConfig: PendantConfig
) => {
if (type === PendantTypes.Status) {
return [