增加可编辑描述组件。

This commit is contained in:
徐涛 2024-12-27 15:44:07 +08:00
parent 0cb158e23d
commit 0b59b0a405
2 changed files with 76 additions and 0 deletions

View File

@ -0,0 +1,27 @@
@layer components {
.editable_description_layout {
display: flex;
flex-direction: row;
align-items: center;
gap: var(--spacing-m);
padding-inline: var(--spacing-xxl);
.content {
font-size: var(--font-size-s);
line-height: 1.2em;
}
textarea {
width: 45em;
height: fit-content;
overflow: hidden;
resize: none;
min-height: calc(1.2em * 2);
max-height: calc(1.2em * 5);
}
.invalid_content {
color: var(--color-neutral-focus);
font-size: var(--font-size-xs);
font-style: italic;
cursor: text;
}
}
}

View File

@ -0,0 +1,49 @@
import { Icon } from '@iconify/react/dist/iconify.js';
import { isEmpty, isNil } from 'lodash-es';
import { useRef, useState } from 'react';
import styles from './EditableDescription.module.css';
type EditableDescriptionProps = {
content?: string | null;
onChange?: (newContent: string) => void;
};
export function EditableDescription({ content, onChange }: EditableDescriptionProps) {
const [isEditing, setIsEditing] = useState(false);
const formRef = useRef<HTMLFormElement>(null);
const cancelEdit = () => {
setIsEditing(false);
formRef.current?.reset();
};
const handleSubmit = (data: FormData) => {
const newDescription = data.get('description') as string;
if (newDescription !== content) {
onChange?.(isEmpty(newDescription) ? null : newDescription);
}
cancelEdit();
};
return isEditing ? (
<form className={styles.editable_description_layout} action={handleSubmit} ref={formRef}>
<textarea name="description" className={styles.content} defaultValue={content} />
<div className="action_icon success" onClick={() => formRef.current?.requestSubmit()}>
<Icon icon="tabler:check" />
</div>
<div className="action_icon danger" onClick={cancelEdit}>
<Icon icon="tabler:x" />
</div>
</form>
) : (
<div className={styles.editable_description_layout}>
<div className={styles.content}>
{isNil(content) || isEmpty(content) ? (
<div className={styles.invalid_content} onClick={() => setIsEditing(true)}>
Click to add description.
</div>
) : (
content
)}
</div>
</div>
);
}