add
This commit is contained in:
parent
5b4953665c
commit
9e7d722248
|
@ -0,0 +1,182 @@
|
|||
import {
|
||||
PlusOutlined,
|
||||
DragOutlined,
|
||||
DeleteOutlined,
|
||||
CaretRightOutlined,
|
||||
SaveOutlined,
|
||||
} from "@ant-design/icons";
|
||||
import {
|
||||
Form,
|
||||
Alert,
|
||||
Button,
|
||||
Input,
|
||||
Select,
|
||||
Space,
|
||||
Collapse,
|
||||
message,
|
||||
} from "antd";
|
||||
import React, { useCallback, useEffect, useState } from "react";
|
||||
import {
|
||||
DndContext,
|
||||
closestCenter,
|
||||
KeyboardSensor,
|
||||
PointerSensor,
|
||||
useSensor,
|
||||
useSensors,
|
||||
DragEndEvent,
|
||||
} from "@dnd-kit/core";
|
||||
import { api, emitDataChange } from "@nice/client";
|
||||
import {
|
||||
arrayMove,
|
||||
SortableContext,
|
||||
sortableKeyboardCoordinates,
|
||||
useSortable,
|
||||
verticalListSortingStrategy,
|
||||
} from "@dnd-kit/sortable";
|
||||
import { CSS } from "@dnd-kit/utilities";
|
||||
import QuillEditor from "@web/src/components/common/editor/quill/QuillEditor";
|
||||
import { TusUploader } from "@web/src/components/common/uploader/TusUploader";
|
||||
import { Lecture, LectureType, PostType } from "@nice/common";
|
||||
import { useCourseEditor } from "../../context/CourseEditorContext";
|
||||
import { usePost } from "@nice/client";
|
||||
import toast from "react-hot-toast";
|
||||
import { CourseContentFormHeader } from "./CourseContentFormHeader";
|
||||
import { CourseSectionEmpty } from "./CourseSectionEmpty";
|
||||
import { LectureData, SectionData } from "./interface";
|
||||
interface SortableSectionProps {
|
||||
courseId?: string;
|
||||
field: SectionData;
|
||||
remove: () => void;
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
export const SortableSection: React.FC<SortableSectionProps> = ({
|
||||
field,
|
||||
remove,
|
||||
courseId,
|
||||
children,
|
||||
}) => {
|
||||
const {
|
||||
attributes,
|
||||
listeners,
|
||||
setNodeRef,
|
||||
transform,
|
||||
transition,
|
||||
isDragging,
|
||||
} = useSortable({ id: field?.id });
|
||||
|
||||
const [form] = Form.useForm();
|
||||
const [editing, setEditing] = useState(field.id ? false : true);
|
||||
const [loading, setLoading] = useState(false);
|
||||
const { create, update } = usePost();
|
||||
|
||||
const handleSave = async () => {
|
||||
if (!courseId) {
|
||||
toast.error("课程未创建,请先填写课程基本信息完成创建");
|
||||
return;
|
||||
}
|
||||
try {
|
||||
setLoading(true);
|
||||
const values = await form.validateFields();
|
||||
let result;
|
||||
try {
|
||||
if (!field?.id) {
|
||||
result = await create.mutateAsync({
|
||||
data: {
|
||||
title: values?.title,
|
||||
type: PostType.SECTION,
|
||||
parentId: courseId,
|
||||
},
|
||||
});
|
||||
} else {
|
||||
result = await update.mutateAsync({
|
||||
data: {
|
||||
title: values?.title,
|
||||
},
|
||||
});
|
||||
}
|
||||
} catch (err) {
|
||||
console.log(err);
|
||||
}
|
||||
|
||||
field.id = result.id;
|
||||
setEditing(false);
|
||||
message.success("保存成功");
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
message.error("保存失败");
|
||||
} finally {
|
||||
setLoading(false);
|
||||
}
|
||||
};
|
||||
|
||||
const style = {
|
||||
transform: CSS.Transform.toString(transform),
|
||||
transition,
|
||||
backgroundColor: isDragging ? "#f5f5f5" : undefined,
|
||||
};
|
||||
|
||||
return (
|
||||
<div ref={setNodeRef} style={style} className="mb-4">
|
||||
<Collapse>
|
||||
<Collapse.Panel
|
||||
header={
|
||||
editing ? (
|
||||
<Form
|
||||
form={form}
|
||||
className="flex items-center gap-4">
|
||||
<Form.Item
|
||||
name="title"
|
||||
className="mb-0 flex-1"
|
||||
initialValue={field?.title}>
|
||||
<Input placeholder="章节标题" />
|
||||
</Form.Item>
|
||||
<Space>
|
||||
<Button
|
||||
onClick={handleSave}
|
||||
loading={loading}
|
||||
icon={<SaveOutlined />}
|
||||
type="primary">
|
||||
保存
|
||||
</Button>
|
||||
<Button
|
||||
onClick={() => {
|
||||
setEditing(false);
|
||||
if (!field?.id) {
|
||||
remove();
|
||||
}
|
||||
}}>
|
||||
取消
|
||||
</Button>
|
||||
</Space>
|
||||
</Form>
|
||||
) : (
|
||||
<div className="flex items-center justify-between">
|
||||
<Space>
|
||||
<DragOutlined
|
||||
{...attributes}
|
||||
{...listeners}
|
||||
className="cursor-move"
|
||||
/>
|
||||
<span>{field.title || "未命名章节"}</span>
|
||||
</Space>
|
||||
<Space>
|
||||
<Button
|
||||
type="link"
|
||||
onClick={() => setEditing(true)}>
|
||||
编辑
|
||||
</Button>
|
||||
<Button type="link" danger onClick={remove}>
|
||||
删除
|
||||
</Button>
|
||||
</Space>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
key={field.id || "new"}>
|
||||
{children}
|
||||
</Collapse.Panel>
|
||||
</Collapse>
|
||||
</div>
|
||||
);
|
||||
};
|
Loading…
Reference in New Issue