openlearn-next 0.2.7 → 0.2.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/assets/{AdminDirectoryView-Cai0cQqi.js → AdminDirectoryView-CD7tW4mc.js} +1 -1
- package/dist/assets/BatchPickerModal-Bt8Qx0Av.js +1 -0
- package/dist/assets/{ClassesView-Cxgfcrx1.js → ClassesView-B1B3wlkx.js} +2 -2
- package/dist/assets/CloudDriveModal-BSZaWIex.js +1 -0
- package/dist/assets/{ComputerLabView-CUCO2VIV.js → ComputerLabView-B6-twB0u.js} +1 -1
- package/dist/assets/CourseManagement-Bnezm9Vv.js +1 -0
- package/dist/assets/CourseWizardModal-BvfTvcQT.js +3 -0
- package/dist/assets/{CoursewareHubPanel-CAaf22Qm.js → CoursewareHubPanel-Cb1mAqHS.js} +1 -1
- package/dist/assets/{Dashboard-vSYAYoji.js → Dashboard-DQ91dQio.js} +2 -2
- package/dist/assets/ExportWeightModal-al1iIVxb.js +1 -0
- package/dist/assets/{HelpTour-ZgEkRnin.js → HelpTour-DwM9UBiA.js} +1 -1
- package/dist/assets/{HelpView-D3WIxMoB.js → HelpView-DLAKVpwf.js} +5 -5
- package/dist/assets/ImportLessonsModal-DwhvqzY_.js +1 -0
- package/dist/assets/{ImportModal-mkWuDoAN.js → ImportModal-CmUt1YeX.js} +1 -1
- package/dist/assets/InteractiveCoursewareViewer-DWnzq20c.js +1 -0
- package/dist/assets/{InteractiveWhiteboard-bmT1LKD6.js → InteractiveWhiteboard-CQ-4meYj.js} +12 -12
- package/dist/assets/{LazyCourseware-Bcxn_20f.js → LazyCourseware-g7b8EXR_.js} +1 -1
- package/dist/assets/{LazyWhiteboard-CJA7aRIM.js → LazyWhiteboard-B6rDWBFb.js} +1 -1
- package/dist/assets/{LessonEditorView-hdJblhmb.js → LessonEditorView-DixwX1Kw.js} +1 -1
- package/dist/assets/{LiveClassroomView-ByyIOLJC.js → LiveClassroomView-j93YOxSh.js} +1 -1
- package/dist/assets/NotificationDetailModal-CQ9PIqkD.js +1 -0
- package/dist/assets/{PluginView-B3ZolNGQ.js → PluginView-DCY4yi2h.js} +1 -1
- package/dist/assets/{ProcessLogsModal-8mVp07ic.js → ProcessLogsModal-B-PY780w.js} +1 -1
- package/dist/assets/QuizGeneratorModal-BvTcmD68.js +1 -0
- package/dist/assets/StudentAssignmentView-4R0WxStx.js +1 -0
- package/dist/assets/StudentLessonView-DZ0i9-tX.js +1 -0
- package/dist/assets/StudentPreviewModal-CfsB1dPY.js +1 -0
- package/dist/assets/StudentView-D7GtUiYR.js +2 -0
- package/dist/assets/SystemResourceLibraryModal-Ilnthwpw.js +1 -0
- package/dist/assets/TeacherView-DjnjsQ_3.js +2 -0
- package/dist/assets/{TimetableView-zce3okQn.js → TimetableView-BMsjwi-s.js} +3 -3
- package/dist/assets/index-D8x6bUeG.js +150 -0
- package/dist/assets/{index-CDTw8wSY.js → index-wdWIWwbg.js} +1 -1
- package/dist/assets/{vendor-icons-BvCtGbt1.js → vendor-icons-_c3xpwjZ.js} +1 -1
- package/dist/assets/vendor-motion-DjY2czvL.js +1 -0
- package/dist/index.html +1 -1
- package/dist/server.cjs +72 -20
- package/package.json +1 -1
- package/dist/assets/BatchPickerModal-CKQyeY6R.js +0 -1
- package/dist/assets/CloudDriveModal-TFWlPh8x.js +0 -1
- package/dist/assets/CourseManagement-DSCOjuIC.js +0 -1
- package/dist/assets/CourseWizardModal-B3QnFxvj.js +0 -3
- package/dist/assets/ExportWeightModal-BlS2auLs.js +0 -1
- package/dist/assets/ImportLessonsModal-BZZRDBRU.js +0 -1
- package/dist/assets/InteractiveCoursewareViewer-01PS40_x.js +0 -1
- package/dist/assets/NotificationDetailModal-dndFrE7p.js +0 -1
- package/dist/assets/QuizGeneratorModal-DpTFYbVJ.js +0 -1
- package/dist/assets/StudentAssignmentView-DDY7C092.js +0 -1
- package/dist/assets/StudentLessonView-BcQ7q4QF.js +0 -1
- package/dist/assets/StudentPreviewModal-ETJBF1Vc.js +0 -1
- package/dist/assets/StudentView-BOqPntx-.js +0 -1
- package/dist/assets/SystemResourceLibraryModal-tg8xnblT.js +0 -1
- package/dist/assets/TeacherView-CrbllHIm.js +0 -2
- package/dist/assets/index-BrEBeWAQ.js +0 -14
- package/dist/assets/index-eXp-qZdm.js +0 -129
- package/dist/assets/vendor-motion-Dz5URUo4.js +0 -9
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import{j as jsxRuntimeExports,r as reactExports,R as React,b as reactDomExports}from"./vendor-react-0Lg0vA-4.js";import{S as Stage,L as Layer,G as Group,H as Html,a as Line,R as Rect,C as Circle$1,T as Text}from"./vendor-konva-CzxOmTv9.js";/* empty css */import{u as usePluginHostStore,E as ExtensionPointRenderer,d as getSocketInstance}from"./index-
|
|
2
|
-
`)),console.log=originalLog}catch(s){setOutput(`Error: ${s.message}`)}},handleBlur=()=>{onElementUpdate&&code!==data.code&&onElementUpdate(elementId,{...data,code})};return jsxRuntimeExports.jsxs("div",{className:"w-full h-full bg-gray-900 border border-gray-700 rounded-lg shadow-xl overflow-hidden flex flex-col font-mono text-sm",style:{pointerEvents:"auto"},children:[jsxRuntimeExports.jsxs("div",{className:"bg-gray-800 text-gray-300 px-3 py-1.5 flex justify-between items-center text-xs border-b border-gray-700 cursor-move select-none shrink-0",onPointerDown,onPointerMove,onPointerUp,children:[jsxRuntimeExports.jsx("span",{className:"flex items-center gap-1",children:"JS Sandbox"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5",onPointerDown:s=>s.stopPropagation(),children:[jsxRuntimeExports.jsx("button",{onClick:runCode,className:"bg-green-600 hover:bg-green-500 text-white px-2 py-0.5 rounded shadow text-[10px] cursor-pointer",children:"Run"}),jsxRuntimeExports.jsx("button",{onClick:onDelete,className:"p-0.5 hover:bg-gray-700 rounded text-gray-400 hover:text-red-500 transition-colors cursor-pointer",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:13})})]})]}),jsxRuntimeExports.jsx("textarea",{value:code,onChange:s=>setCode(s.target.value),onBlur:handleBlur,className:"w-full flex-1 min-h-0 bg-gray-900 text-green-400 p-3 focus:outline-none resize-none font-mono text-xs",placeholder:"// Write JS here",onPointerDown:s=>{s.stopPropagation()},onKeyDown:s=>{s.stopPropagation()}}),output&&jsxRuntimeExports.jsx("div",{className:"bg-black text-gray-400 p-2 border-t border-gray-800 h-24 overflow-y-auto whitespace-pre-wrap text-[10px] shrink-0",children:output})]})}function MathGraphWrapper({elementId,data,onElementUpdate,onPointerDown,onPointerMove,onPointerUp,onDelete}){const[equation,setEquation]=reactExports.useState(data.equation||"Math.sin(x)"),[points,setPoints]=reactExports.useState(""),[error,setError]=reactExports.useState(""),[containerDimensions,setContainerDimensions]=reactExports.useState({width:400,height:300}),graphContainerRef=reactExports.useRef(null);reactExports.useEffect(()=>{if(!graphContainerRef.current)return;const s=new ResizeObserver(
|
|
1
|
+
import{j as jsxRuntimeExports,r as reactExports,R as React,b as reactDomExports}from"./vendor-react-0Lg0vA-4.js";import{S as Stage,L as Layer,G as Group,H as Html,a as Line,R as Rect,C as Circle$1,T as Text}from"./vendor-konva-CzxOmTv9.js";/* empty css */import{u as usePluginHostStore,M as Markdown,E as ExtensionPointRenderer,d as getSocketInstance,F as FullscreenOverlay,p as propertyEditorRegistry,f as fullscreenRendererRegistry}from"./index-D8x6bUeG.js";import{l as LoaderCircle,f as Sparkles,aa as Trash2,b3 as UserCheck,s as CircleQuestionMark,k as Shuffle,W as WandSparkles,P as Presentation,a3 as ChevronLeft,_ as ChevronRight,o as Play,p as BookOpen,aB as PenLine,a4 as Upload,a8 as Maximize2,F as FileText,b4 as MousePointer2,a1 as PenTool,aO as Highlighter,aw as Square,b5 as Circle,b6 as Type,T as Terminal,i as Activity,h as Globe,aT as Grid3x3,b7 as Eraser,aU as RotateCcw,aS as LayoutGrid,b as ChevronDown,aC as Copy,a7 as Plus,X,ax as Settings,b8 as Undo2,b9 as Redo2,ba as Paintbrush,x as Minimize2}from"./vendor-icons-_c3xpwjZ.js";import{t as tt,v as v7}from"./vendor-pptx-B0hlo0eh.js";import"./vendor-utils-4FcTwKPj.js";import"./vendor-pdf-CVyNPGVr.js";import"./vendor-motion-DjY2czvL.js";import"./vendor-charts-B7ViBL9w.js";const SOCKET_FORWARD_PREFIXES=["whiteboard.","courseware.","quiz.","rollcall."];class FrontendEventBus{constructor(){this.handlers=new Map}setSocketBridge(l){this.socketBridge=l}hasSocketBridge(){return!!this.socketBridge}subscribe(l,g){return this.handlers.has(l)||this.handlers.set(l,new Set),this.handlers.get(l).add(g),()=>{this.handlers.get(l)?.delete(g)}}async publish(l){const g=this.handlers.get(l.type);if(g)for(const d of g)try{d(l)}catch(E){console.error("[FrontendEventBus] handler error:",E)}this.socketBridge&&SOCKET_FORWARD_PREFIXES.some(d=>l.type.startsWith(d))&&this.socketBridge(l)}}const frontendEventBus=new FrontendEventBus;function PluginCardRenderer({pluginId:s,slot:l,widgetId:g,elementId:d,lessonId:E}){const f=usePluginHostStore(S=>S.extensionPoints).get(l)||[],N=f.find(S=>S.id===g)??f.find(S=>S.pluginId===s&&S.id===g);if(!N)return jsxRuntimeExports.jsxs("div",{className:"text-center py-6 text-xs text-gray-400 italic flex flex-col justify-center items-center h-full",children:[jsxRuntimeExports.jsx(LoaderCircle,{size:16,className:"animate-spin mb-1"}),jsxRuntimeExports.jsxs("span",{children:["组件 [",g,"] 正在加载或未启用..."]})]});const c=reactExports.useRef(null);return reactExports.useEffect(()=>{c.current&&(c.current.innerHTML="",!N.component&&N.render&&Promise.resolve(N.render(c.current,{elementId:d,lessonId:E})).catch(console.error))},[N,s,g,d,E]),N.component?React.createElement(N.component,{elementId:d,lessonId:E}):jsxRuntimeExports.jsx("div",{ref:c,className:"w-full h-full min-h-0"})}function RollCallWrapper({elementId:s,data:l,onElementUpdate:g,onPointerDown:d,onPointerMove:E,onPointerUp:O,onDelete:f}){const N=l.allStudents||[{id:"mock-s-1",name:"张明",email:"zhangming@edu-os.org"},{id:"mock-s-2",name:"李华",email:"lihua@edu-os.org"},{id:"mock-s-3",name:"王超",email:"wangchao@edu-os.org"},{id:"mock-s-4",name:"赵丽",email:"zhaoli@edu-os.org"},{id:"mock-s-5",name:"钱科",email:"qianke@edu-os.org"},{id:"mock-s-6",name:"孙雪",email:"sunxue@edu-os.org"}],[c,S]=reactExports.useState(l.selectedStudent||null),[k,J]=reactExports.useState(!1),[ce,T]=reactExports.useState(""),R=()=>{if(N.length===0||k)return;J(!0);let P=0;const de=16,p=setInterval(()=>{const z=Math.floor(Math.random()*N.length);if(T(N[z].name),P++,P>=de){clearInterval(p);const C=Math.floor(Math.random()*N.length),_=N[C];S(_),J(!1),g&&g(s,{...l,selectedStudent:_,pickedTime:new Date().toISOString(),status:"picked"})}},80)};return jsxRuntimeExports.jsxs("div",{className:"w-full h-full bg-gradient-to-br from-indigo-950 via-slate-900 to-indigo-900 border border-indigo-500/50 rounded-xl shadow-2xl overflow-hidden flex flex-col font-sans select-none",style:{pointerEvents:"auto"},children:[jsxRuntimeExports.jsxs("div",{className:"bg-indigo-950/80 text-indigo-200 px-3 py-2 flex justify-between items-center text-xs font-semibold border-b border-indigo-900/50 cursor-move select-none shrink-0",onPointerDown:d,onPointerMove:E,onPointerUp:O,children:[jsxRuntimeExports.jsxs("span",{className:"flex items-center gap-1.5 text-indigo-300",children:[jsxRuntimeExports.jsx(Sparkles,{size:13,className:"animate-pulse text-indigo-400"}),jsxRuntimeExports.jsx("span",{children:"随机点名助手 (Picker Ext)"})]}),jsxRuntimeExports.jsx("button",{onClick:f,onPointerDown:P=>P.stopPropagation(),className:"p-1 hover:bg-indigo-900/60 rounded text-indigo-400 hover:text-red-450 transition-colors cursor-pointer",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:13})})]}),jsxRuntimeExports.jsxs("div",{className:"flex-1 p-3.5 flex flex-col justify-between min-h-0 text-white gap-2",children:[jsxRuntimeExports.jsx("div",{className:"w-full flex-1 flex flex-col items-center justify-center p-2 rounded-lg bg-indigo-950/50 border border-indigo-900/30",children:k?jsxRuntimeExports.jsxs("div",{className:"text-center space-y-2",children:[jsxRuntimeExports.jsx("div",{className:"text-[10px] text-indigo-300 uppercase tracking-widest animate-pulse font-semibold",children:"检索班级学生中..."}),jsxRuntimeExports.jsx("div",{className:"text-2xl font-extrabold text-amber-300 scale-105 tracking-wider font-sans",children:ce})]}):c?jsxRuntimeExports.jsxs("div",{className:"text-center space-y-1.5",children:[jsxRuntimeExports.jsxs("div",{className:"text-[9px] text-indigo-400 uppercase tracking-widest font-semibold flex items-center justify-center gap-1",children:[jsxRuntimeExports.jsx(UserCheck,{size:11,className:"text-emerald-400 animate-bounce"}),jsxRuntimeExports.jsx("span",{children:"抽中的幸运学生"})]}),jsxRuntimeExports.jsx("div",{className:"text-2xl font-extrabold text-transparent bg-clip-text bg-gradient-to-r from-amber-200 via-yellow-400 to-amber-300 tracking-wider",children:c.name}),jsxRuntimeExports.jsx("div",{className:"text-[9px] text-indigo-300/70 font-mono overflow-hidden text-ellipsis max-w-full",children:c.email||"No Email Account"})]}):jsxRuntimeExports.jsxs("div",{className:"text-center space-y-1",children:[jsxRuntimeExports.jsx(CircleQuestionMark,{size:28,className:"text-indigo-400/80 mx-auto animate-pulse"}),jsxRuntimeExports.jsx("div",{className:"text-xs text-indigo-300 font-semibold",children:"随机抽取摇奖板"}),jsxRuntimeExports.jsx("p",{className:"text-[9px] text-indigo-400/60 leading-tight",children:"将在白板上演示随机滚动,对课堂提问大有裨益"})]})}),jsxRuntimeExports.jsxs("div",{className:"w-full shrink-0 flex flex-col items-center gap-1",onPointerDown:P=>P.stopPropagation(),children:[jsxRuntimeExports.jsxs("button",{onClick:R,disabled:k,className:"w-full py-1.5 bg-gradient-to-r from-indigo-500 to-purple-600 hover:from-indigo-650 hover:to-purple-750 text-white font-bold text-[11px] uppercase tracking-wider rounded-lg shadow-md active:scale-97 disabled:opacity-50 transition-all flex items-center justify-center gap-1.5",children:[jsxRuntimeExports.jsx(Shuffle,{size:12,className:k?"animate-spin":""}),jsxRuntimeExports.jsx("span",{children:k?"滚轮运转中...":c?"重新随机点名":"开始随机点名"})]}),jsxRuntimeExports.jsxs("div",{className:"text-[8.5px] text-indigo-400/60 text-center font-mono",children:["班级人数:",N.length," 人 • 内核总线热同步"]})]})]})]})}function CodeSandboxWrapper({elementId,data,onElementUpdate,onPointerDown,onPointerMove,onPointerUp,onDelete}){const[code,setCode]=reactExports.useState(data.code||"console.log('Hello from sandbox!');"),[output,setOutput]=reactExports.useState(""),runCode=()=>{try{const logs=[],originalLog=console.log;console.log=(...s)=>{logs.push(s.map(l=>typeof l=="object"?JSON.stringify(l):String(l)).join(" ")),originalLog(...s)};const result=eval(code);result!==void 0&&logs.push(`Return: ${result}`),setOutput(logs.join(`
|
|
2
|
+
`)),console.log=originalLog}catch(s){setOutput(`Error: ${s.message}`)}},handleBlur=()=>{onElementUpdate&&code!==data.code&&onElementUpdate(elementId,{...data,code})};return jsxRuntimeExports.jsxs("div",{className:"w-full h-full bg-gray-900 border border-gray-700 rounded-lg shadow-xl overflow-hidden flex flex-col font-mono text-sm",style:{pointerEvents:"auto"},children:[jsxRuntimeExports.jsxs("div",{className:"bg-gray-800 text-gray-300 px-3 py-1.5 flex justify-between items-center text-xs border-b border-gray-700 cursor-move select-none shrink-0",onPointerDown,onPointerMove,onPointerUp,children:[jsxRuntimeExports.jsx("span",{className:"flex items-center gap-1",children:"JS Sandbox"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5",onPointerDown:s=>s.stopPropagation(),children:[jsxRuntimeExports.jsx("button",{onClick:runCode,className:"bg-green-600 hover:bg-green-500 text-white px-2 py-0.5 rounded shadow text-[10px] cursor-pointer",children:"Run"}),jsxRuntimeExports.jsx("button",{onClick:onDelete,className:"p-0.5 hover:bg-gray-700 rounded text-gray-400 hover:text-red-500 transition-colors cursor-pointer",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:13})})]})]}),jsxRuntimeExports.jsx("textarea",{value:code,onChange:s=>setCode(s.target.value),onBlur:handleBlur,className:"w-full flex-1 min-h-0 bg-gray-900 text-green-400 p-3 focus:outline-none resize-none font-mono text-xs",placeholder:"// Write JS here",onPointerDown:s=>{s.stopPropagation()},onKeyDown:s=>{s.stopPropagation()}}),output&&jsxRuntimeExports.jsx("div",{className:"bg-black text-gray-400 p-2 border-t border-gray-800 h-24 overflow-y-auto whitespace-pre-wrap text-[10px] shrink-0",children:output})]})}function MathGraphWrapper({elementId,data,onElementUpdate,onPointerDown,onPointerMove,onPointerUp,onDelete}){const[equation,setEquation]=reactExports.useState(data.equation||"Math.sin(x)"),[points,setPoints]=reactExports.useState(""),[error,setError]=reactExports.useState(""),[containerDimensions,setContainerDimensions]=reactExports.useState({width:400,height:300}),graphContainerRef=reactExports.useRef(null);reactExports.useEffect(()=>{if(!graphContainerRef.current)return;const s=new ResizeObserver(l=>{for(const g of l)setContainerDimensions({width:g.contentRect.width||400,height:g.contentRect.height||300})});return s.observe(graphContainerRef.current),()=>s.disconnect()},[]),reactExports.useEffect(()=>{try{const generatedPoints=[],centerX=containerDimensions.width/2,centerY=containerDimensions.height/2;for(let xUnit=-10;xUnit<=10;xUnit+=.2){const x=xUnit,y=eval(equation);if(typeof y!="number"||isNaN(y))continue;const px=centerX+x*20,py=centerY-y*20;generatedPoints.push(`${px},${py}`)}setPoints(generatedPoints.join(" ")),setError("")}catch(s){setError(s.message)}},[equation,containerDimensions]);const handleBlur=()=>{onElementUpdate&&equation!==data.equation&&onElementUpdate(elementId,{...data,equation})};return jsxRuntimeExports.jsxs("div",{className:"w-full h-full bg-white border border-gray-300 rounded-lg shadow-xl overflow-hidden flex flex-col font-mono text-sm",style:{pointerEvents:"auto"},children:[jsxRuntimeExports.jsxs("div",{className:"bg-gray-100 text-gray-700 px-3 py-1.5 flex justify-between items-center text-xs border-b border-gray-300 cursor-move select-none shrink-0",onPointerDown,onPointerMove,onPointerUp,children:[jsxRuntimeExports.jsx("span",{className:"flex items-center gap-1 font-semibold text-gray-600",children:"Math Graph Sandbox"}),jsxRuntimeExports.jsx("button",{onClick:onDelete,onPointerDown:s=>s.stopPropagation(),className:"p-1 hover:bg-gray-200 rounded-full text-gray-500 hover:text-red-500 transition-colors cursor-pointer flex items-center justify-center",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:13})})]}),jsxRuntimeExports.jsxs("div",{className:"p-3 border-b border-gray-200 flex-none flex flex-col gap-1",children:[jsxRuntimeExports.jsx("span",{className:"text-gray-500 text-xs",children:"y = f(x)"}),jsxRuntimeExports.jsx("input",{type:"text",value:equation,onChange:s=>setEquation(s.target.value),onBlur:handleBlur,className:"w-full border border-gray-300 rounded px-2 py-1 focus:outline-none focus:border-indigo-500 font-mono text-xs",placeholder:"e.g. Math.sin(x) * x",onPointerDown:s=>s.stopPropagation(),onKeyDown:s=>s.stopPropagation()}),error&&jsxRuntimeExports.jsx("div",{className:"text-red-500 text-[10px] mt-1",children:error})]}),jsxRuntimeExports.jsx("div",{className:"flex-1 relative overflow-hidden bg-white min-h-0",ref:graphContainerRef,children:jsxRuntimeExports.jsxs("svg",{width:containerDimensions.width,height:containerDimensions.height,viewBox:`0 0 ${containerDimensions.width} ${containerDimensions.height}`,className:"absolute top-0 left-0",children:[jsxRuntimeExports.jsx("line",{x1:containerDimensions.width/2,y1:"0",x2:containerDimensions.width/2,y2:containerDimensions.height,stroke:"#e5e7eb",strokeWidth:"1"}),jsxRuntimeExports.jsx("line",{x1:"0",y1:containerDimensions.height/2,x2:containerDimensions.width,y2:containerDimensions.height/2,stroke:"#e5e7eb",strokeWidth:"1"}),points&&jsxRuntimeExports.jsx("polyline",{points,fill:"none",stroke:"#6366f1",strokeWidth:"2",strokeLinejoin:"round"})]})})]})}function HelloWorldWrapper({elementId:s,data:l,onElementUpdate:g,onPointerDown:d,onPointerMove:E,onPointerUp:O,onDelete:f,lessonId:N}){const[c,S]=reactExports.useState(!1),k=async()=>{S(!0);try{await fetch("/api/commands",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({commandType:"hello.say",payload:{lessonId:N,username:"World",shout:!0}})})}catch(J){console.error("Failed to trigger hello.say command:",J)}finally{S(!1)}};return jsxRuntimeExports.jsxs("div",{className:"w-full h-full bg-white border border-slate-200/80 rounded-xl shadow-lg overflow-hidden flex flex-col font-sans select-none",style:{pointerEvents:"auto"},children:[jsxRuntimeExports.jsxs("div",{className:"bg-slate-50 text-slate-700 px-2 py-1.5 flex justify-between items-center text-[10px] font-semibold border-b border-slate-150 cursor-move select-none shrink-0",onPointerDown:d,onPointerMove:E,onPointerUp:O,children:[jsxRuntimeExports.jsxs("span",{className:"flex items-center gap-1.5 text-slate-650",children:[jsxRuntimeExports.jsx(Sparkles,{size:11,className:"text-amber-500 animate-pulse"}),jsxRuntimeExports.jsx("span",{children:"Hello World 插件"})]}),jsxRuntimeExports.jsx("button",{onClick:f,onPointerDown:J=>J.stopPropagation(),className:"p-1 hover:bg-slate-150 rounded text-slate-400 hover:text-red-500 transition-colors cursor-pointer",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:11})})]}),jsxRuntimeExports.jsx("div",{className:"flex-1 p-2 flex items-center justify-center bg-slate-50/20",children:jsxRuntimeExports.jsxs("button",{onClick:k,disabled:c,onPointerDown:J=>J.stopPropagation(),className:"w-full py-1 bg-gradient-to-r from-indigo-500 to-purple-600 hover:from-indigo-650 hover:to-purple-750 text-white font-bold text-[10px] rounded-lg shadow-sm active:scale-95 transition-all flex items-center justify-center gap-1 cursor-pointer",children:[jsxRuntimeExports.jsx(WandSparkles,{size:11,className:c?"animate-spin":""}),jsxRuntimeExports.jsx("span",{children:c?"输出中...":"点击输出"})]})})]})}function RevealPresentationWrapper({elementId:s,data:l,userRole:g="teacher",onElementUpdate:d}){const[E,O]=reactExports.useState("ppt"),[f,N]=reactExports.useState(l.markdown||`# Title Slide
|
|
3
3
|
---
|
|
4
|
-
## Slide 2`),[c,
|
|
4
|
+
## Slide 2`),[c,S]=reactExports.useState(l.slideX||0),[k,J]=reactExports.useState(!1),[ce,T]=reactExports.useState(4),[R,P]=reactExports.useState(!1),de=reactExports.useRef(null),L=g==="teacher",p=g==="student",z=l.fileUrl||"",C=l.fileType||"md",_=l.fileName||"",G=!!z,[pe,Z]=reactExports.useState(!1),fe=reactExports.useRef(null),Ne=reactExports.useRef(null),oe=reactExports.useRef(null),ee=!!l.isFullscreenSynced,se=!!l.isFullscreenForced,H=R||p&&ee&&se,je=f.split(/(?:\r?\n|^)---(?:\r?\n|$)/).map(h=>h.trim()).filter(h=>h.length>0),ie=C==="md"?Math.max(1,je.length):l.slideCount||1;reactExports.useEffect(()=>{C!=="md"&&E!=="ppt"&&O("ppt")},[C,E]),reactExports.useEffect(()=>{l.slideX!==void 0&&l.slideX!==c&&S(l.slideX)},[l.slideX]),reactExports.useEffect(()=>{l.markdown!==void 0&&l.markdown!==f&&N(l.markdown)},[l.markdown]),reactExports.useEffect(()=>{if(C!=="pptx"||!z){oe.current&&(oe.current.destroy(),oe.current=null);return}let h=!0;return fetch(z).then(v=>v.arrayBuffer()).then(async v=>{if(h&&(oe.current&&(oe.current.destroy(),oe.current=null),Ne.current)){Ne.current.innerHTML="";try{const A=tt(Ne.current,{mode:"slide"});oe.current=A,await A.load(v),h&&(L&&d&&l.slideCount!==A.slideCount&&d(s,{...l,slideCount:A.slideCount}),A.renderSingleSlide(c))}catch(A){console.error("PPTX preview init failed",A)}}}).catch(v=>console.error("Fetch PPTX failed",v)),()=>{h=!1,oe.current&&(oe.current.destroy(),oe.current=null)}},[z,C,H]),reactExports.useEffect(()=>{if(C==="pptx"&&oe.current)try{oe.current.renderSingleSlide(c)}catch(h){console.error("PPTX renderSingleSlide failed",h)}},[c,C]),reactExports.useEffect(()=>{if(!k||E!=="ppt"||C!=="md")return;const h=setInterval(()=>{S(v=>{const A=(v+1)%Math.max(1,je.length);return d&&d(s,{...l,slideX:A}),A})},ce*1e3);return()=>clearInterval(h)},[k,ce,je.length,E,C]),reactExports.useEffect(()=>{const h=v=>{p&&ee&&se||(v.key==="ArrowRight"||v.key===" "?(v.preventDefault(),be(c+1)):v.key==="ArrowLeft"?(v.preventDefault(),be(c-1)):v.key==="Escape"&&H&&(v.preventDefault(),ze(!1)))};return window.addEventListener("keydown",h),()=>window.removeEventListener("keydown",h)},[c,H,p,ee,se,ie]);const be=h=>{if(p&&ee&&se)return;const v=Math.min(Math.max(0,h),ie-1);S(v),L&&d&&d(s,{...l,slideX:v})},Ee=h=>{N(h),d&&d(s,{...l,markdown:h})},Ie=async h=>{const v=h.target.files?.[0];if(!v)return;const A=v.name.split(".").pop()?.toLowerCase();if(A!=="pdf"&&A!=="pptx"){alert("仅支持上传 PDF 或 PPTX 格式的课件文件!");return}Z(!0);try{const K=new FileReader;K.onload=async ge=>{const ye=(ge.target?.result).split(",")[1],M=await fetch("/api/upload",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({filename:v.name,base64Data:ye})});if(!M.ok)throw new Error("服务器上传文件失败");const U=await M.json();d&&(await d(s,{...l,fileUrl:U.url,fileName:v.name,fileType:U.type,slideX:0,slideCount:U.pageCount||1,isFullscreenSynced:l.isFullscreenSynced!==void 0?l.isFullscreenSynced:!0,isFullscreenForced:!1}),S(0))},K.readAsDataURL(v)}catch(K){console.error(K),alert("课件文件上传失败,请重试")}finally{Z(!1)}},He=()=>{window.confirm("确定要清除已上传的课件并恢复为 Markdown 编辑模式吗?")&&d&&(d(s,{...l,fileUrl:"",fileName:"",fileType:"md",slideX:0,slideCount:0,isFullscreenForced:!1}),S(0))},ze=h=>{P(h),L&&d&&d(s,{...l,isFullscreenForced:h})},Te=h=>{d&&d(s,{...l,isFullscreenSynced:h,isFullscreenForced:h?R:!1})},Ye=[{name:"基础通用课件",desc:"标准的课件 structure",content:`# 物理学原理与探究
|
|
5
5
|
---
|
|
6
6
|
## 课程介绍
|
|
7
7
|
1. 经典力学基础
|
|
@@ -44,13 +44,13 @@ The teacher used the virtual whiteboard to ___ classroom active learning slides.
|
|
|
44
44
|
3. 会发现:不管拉力如何变化,A 的读数总是等于 B 的读数。
|
|
45
45
|
|
|
46
46
|
## 问题思考
|
|
47
|
-
当马拉着车在水平路面上加速前进时,马拉车的力与车拉马的力,哪一个更大?`}],
|
|
48
|
-
`),k=[];return f.forEach((I,K)=>{const ge=I.match(/^(#{1,3})\s+(.*)$/);ge&&k.push({text:ge[2].trim(),level:ge[1].length,lineIndex:K})}),k})();if(Y&&typeof document<"u")return jsxRuntimeExports.jsxs("div",{className:"w-full h-full flex flex-col items-center justify-center bg-slate-900/10 text-slate-400 font-sans p-4",children:[jsxRuntimeExports.jsxs("div",{className:"flex flex-col items-center gap-2",children:[jsxRuntimeExports.jsx(Presentation,{size:24,className:"text-indigo-500 animate-pulse"}),jsxRuntimeExports.jsx("span",{className:"text-xs",children:"演示文稿正在全屏放映中"})]}),reactDomExports.createPortal(jsxRuntimeExports.jsxs("div",{className:"fixed inset-0 z-[99999] bg-neutral-950 flex flex-col items-center justify-center font-sans p-6",children:[jsxRuntimeExports.jsxs("div",{className:"absolute top-4 left-4 right-4 flex items-center justify-between text-white/80 select-none z-[100001] px-4 py-2 bg-neutral-900/60 backdrop-blur-md rounded-xl border border-neutral-800",children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("span",{className:"w-2.5 h-2.5 rounded-full bg-emerald-500 animate-pulse"}),jsxRuntimeExports.jsxs("span",{className:"font-bold text-xs tracking-wider uppercase",children:[C==="md"?"Markdown Slides":`${C.toUpperCase()} Presentation`," ",p&&"(Synced)"]})]}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-4",children:[jsxRuntimeExports.jsxs("span",{className:"text-xs font-mono text-white/50",children:["Slide ",c+1," / ",ie]}),L&&jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[C==="md"&&jsxRuntimeExports.jsx("button",{onClick:()=>_(f=>!f),className:`px-2.5 py-1 rounded-md text-[10px] uppercase font-bold tracking-wider transition-colors border cursor-pointer ${R?"bg-emerald-50 border-emerald-400 text-white animate-pulse":"bg-transparent border-neutral-700 text-neutral-400 hover:bg-neutral-850"}`,children:R?"Autoplay Live":"Autoplay"}),jsxRuntimeExports.jsxs("label",{className:"flex items-center gap-1.5 text-xs text-white/70 cursor-pointer",children:[jsxRuntimeExports.jsx("input",{type:"checkbox",checked:ee,onChange:f=>Te(f.target.checked),className:"rounded border-neutral-700 bg-neutral-800 text-indigo-500 focus:ring-0 focus:ring-offset-0 cursor-pointer"}),jsxRuntimeExports.jsx("span",{children:"同步学生全屏"})]})]}),(!p||!se||!ee||N)&&jsxRuntimeExports.jsx("button",{onClick:()=>ze(!1),className:"p-1 px-2.5 bg-red-600 text-white text-xs font-bold rounded-lg transition-colors cursor-pointer border-0 hover:bg-red-700",title:"退出放映",children:"退出放映 (Esc)"})]})]}),jsxRuntimeExports.jsx("div",{className:"w-full flex-1 min-h-0 flex items-center justify-center relative",children:C==="pdf"?jsxRuntimeExports.jsx("div",{className:"w-full h-full flex items-center justify-center p-2 bg-slate-100 max-w-[90vw] max-h-[82vh] aspect-video rounded-2xl overflow-hidden shadow-2xl border border-neutral-850",children:jsxRuntimeExports.jsx("iframe",{src:`${z}#page=${c+1}&toolbar=0&navpanes=0`,className:"w-full h-full border-0 rounded-xl"},`${z}-fs-${c}`)}):C==="pptx"?jsxRuntimeExports.jsx("div",{className:"w-full h-full flex items-center justify-center p-2 bg-slate-900/5 max-w-[90vw] max-h-[82vh] aspect-video rounded-2xl overflow-hidden shadow-2xl border border-neutral-850",children:jsxRuntimeExports.jsx("div",{ref:Ne,className:"w-full h-full overflow-auto rounded-xl bg-white border border-slate-100 shadow-md flex items-center justify-center"})}):jsxRuntimeExports.jsx("div",{className:"flex-1 w-full flex items-center justify-center max-w-[90vw] min-h-0",children:jsxRuntimeExports.jsxs("div",{className:"w-full bg-white rounded-xl shadow-md border border-slate-100 flex flex-col overflow-y-auto p-6 md:p-8 aspect-video relative transition-all duration-300 hover:shadow-lg max-h-[82vh] max-w-none p-12 md:p-16 border-neutral-850 rounded-3xl shadow-2xl",children:[jsxRuntimeExports.jsxs("div",{className:"flex justify-between items-center text-[10px] font-semibold text-slate-400 border-b border-slate-100 pb-2 mb-4 shrink-0",children:[jsxRuntimeExports.jsx("span",{className:"tracking-wide uppercase text-indigo-650",children:"SMART CLASS SLIDE DECK"}),jsxRuntimeExports.jsxs("span",{className:"font-mono",children:["SLIDE ",c+1," / ",ie]})]}),jsxRuntimeExports.jsx("div",{className:"flex-1 min-h-0 overflow-y-auto pr-1",children:jsxRuntimeExports.jsx("div",{className:"markdown-body text-slate-800 leading-relaxed font-sans prose prose-neutral max-w-none text-xs",children:je[c]?jsxRuntimeExports.jsx(Markdown,{children:je[c]}):jsxRuntimeExports.jsx("div",{className:"text-center text-slate-400 italic py-8",children:"幻灯片没有内容,请在“编辑文档”中添加。"})})}),jsxRuntimeExports.jsxs("div",{className:"mt-4 pt-2 border-t border-slate-50 flex items-center justify-between text-[10px] text-slate-400 shrink-0 font-sans",children:[jsxRuntimeExports.jsx("span",{children:"智慧互动教室白板演示系统"}),jsxRuntimeExports.jsxs("span",{children:["Page ",c+1]})]})]})})}),!(p&&ee&&se)&&jsxRuntimeExports.jsxs("div",{className:"absolute bottom-6 bg-neutral-900/80 backdrop-blur-md px-6 py-2.5 rounded-full border border-neutral-800 shadow-2xl z-[100001]",children:[jsxRuntimeExports.jsx("button",{disabled:c===0||p,onClick:()=>be(c-1),className:`p-1.5 rounded-full border transition-colors cursor-pointer ${c===0||p?"border-neutral-800 text-neutral-600 bg-neutral-950/20 cursor-not-allowed":"border-neutral-700 text-neutral-300 hover:bg-neutral-800"}`,title:"上一张 (ArrowLeft)",children:jsxRuntimeExports.jsx(ChevronLeft,{size:18})}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5 px-1 font-mono text-xs text-neutral-200",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-white text-base",children:c+1}),jsxRuntimeExports.jsx("span",{className:"text-neutral-600",children:"/"}),jsxRuntimeExports.jsx("span",{children:ie})]}),jsxRuntimeExports.jsx("button",{disabled:c>=ie-1||p,onClick:()=>be(c+1),className:`p-1.5 rounded-full border transition-colors cursor-pointer ${c>=ie-1||p?"border-neutral-800 text-neutral-600 bg-neutral-950/20 cursor-not-allowed":"border-neutral-700 text-neutral-300 hover:bg-neutral-800"}`,title:"下一张 (ArrowRight)",children:jsxRuntimeExports.jsx(ChevronRight,{size:18})})]})]}),document.body)]});const me=Y?"fixed inset-0 z-[99999] bg-neutral-950 flex flex-col items-center justify-center font-sans p-6":"flex-1 flex flex-col items-center justify-between p-4 bg-slate-900/5 relative min-w-0";return jsxRuntimeExports.jsxs("div",{className:"w-full h-full flex flex-col bg-slate-50 text-slate-800 overflow-hidden text-xs relative font-sans",children:[!Y&&jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between px-3 py-1.5 bg-slate-100 border-b border-slate-200 shrink-0 select-none relative z-10",children:[jsxRuntimeExports.jsx("div",{className:"flex items-center gap-1",children:C==="md"?jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsxs("button",{onClick:()=>M("ppt"),className:`px-2 py-1 rounded flex items-center gap-1 font-medium transition-colors cursor-pointer ${g==="ppt"?"bg-indigo-600 text-white shadow-sm":"text-slate-600 hover:bg-slate-200"}`,title:"播放课件幻灯片 (PPT Mode)",children:[jsxRuntimeExports.jsx(Play,{size:11}),jsxRuntimeExports.jsx("span",{children:"PPT 播放"})]}),jsxRuntimeExports.jsxs("button",{onClick:()=>M("doc"),className:`px-2 py-1 rounded flex items-center gap-1 font-medium transition-colors cursor-pointer ${g==="doc"?"bg-indigo-600 text-white shadow-sm":"text-slate-600 hover:bg-slate-200"}`,title:"以精美文档形式阅读 (Markdown Document mode)",children:[jsxRuntimeExports.jsx(BookOpen,{size:11}),jsxRuntimeExports.jsx("span",{children:"文档阅读"})]}),jsxRuntimeExports.jsxs("button",{onClick:()=>M("edit"),className:`px-2 py-1 rounded flex items-center gap-1 font-medium transition-colors cursor-pointer ${g==="edit"?"bg-indigo-600 text-white shadow-sm":"text-slate-600 hover:bg-slate-200"}`,title:"在线编辑 Markdown 内容",children:[jsxRuntimeExports.jsx(PenLine,{size:11}),jsxRuntimeExports.jsx("span",{children:"编辑文档"})]})]}):jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1 bg-indigo-50 border border-indigo-200/50 text-indigo-700 px-2 py-0.5 rounded text-[10px] font-semibold",children:[jsxRuntimeExports.jsx(Presentation,{size:10}),jsxRuntimeExports.jsxs("span",{children:[C.toUpperCase()," 课件演示中"]})]})}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-3",children:[L&&jsxRuntimeExports.jsx("div",{className:"flex items-center gap-1.5 border-r border-slate-200 pr-3",children:pe?jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1 text-[10px] text-slate-500 font-medium",children:[jsxRuntimeExports.jsx(LoaderCircle,{size:10,className:"animate-spin"}),jsxRuntimeExports.jsx("span",{children:"上传解析中..."})]}):G?jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5 bg-slate-200/50 pl-2 pr-1.5 py-0.5 rounded border border-slate-300/30",children:[jsxRuntimeExports.jsx("span",{className:"text-[10px] font-medium text-slate-600 max-w-[120px] truncate font-mono",title:A,children:A}),jsxRuntimeExports.jsx("button",{onClick:He,className:"p-0.5 hover:bg-slate-300 rounded text-red-500 cursor-pointer border-0 bg-transparent",title:"清除并切换回 Markdown",children:jsxRuntimeExports.jsx(Trash2,{size:10})})]}):jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsxs("button",{onClick:()=>fe.current?.click(),className:"px-2 py-1 rounded bg-indigo-50 border border-indigo-200 text-indigo-700 hover:bg-indigo-100 flex items-center gap-1 font-semibold text-[10px] cursor-pointer",title:"上传 PPTX 或 PDF 课件",children:[jsxRuntimeExports.jsx(Upload,{size:10}),jsxRuntimeExports.jsx("span",{children:"上传课件"})]}),jsxRuntimeExports.jsx("input",{type:"file",ref:fe,onChange:Ie,accept:".pdf,.pptx",className:"hidden"})]})}),g==="ppt"&&C==="md"&&jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5",children:[jsxRuntimeExports.jsxs("button",{onClick:()=>_(f=>!f),className:`p-1 rounded flex items-center gap-1 font-semibold text-[10px] transition-colors border cursor-pointer ${R?"bg-emerald-50 border-emerald-300 text-emerald-700":"bg-white border-slate-200 text-slate-500 hover:bg-slate-50"}`,title:"开启/关闭幻灯片自动播放",children:[R?jsxRuntimeExports.jsx("span",{className:"w-1.5 h-1.5 rounded-full bg-emerald-500 animate-ping"}):null,jsxRuntimeExports.jsx("span",{children:R?"自动播放中":"自动播放"})]}),R&&jsxRuntimeExports.jsxs("select",{value:ce,onChange:f=>$(Number(f.target.value)),className:"bg-white border border-slate-200 rounded px-1 text-[10px] py-0.5 text-slate-700 font-medium",children:[jsxRuntimeExports.jsx("option",{value:2,children:"2秒"}),jsxRuntimeExports.jsx("option",{value:4,children:"4秒"}),jsxRuntimeExports.jsx("option",{value:6,children:"6秒"}),jsxRuntimeExports.jsx("option",{value:10,children:"10秒"})]})]}),L&&g==="ppt"&&jsxRuntimeExports.jsxs("label",{className:"flex items-center gap-1 text-[10px] text-slate-500 font-medium cursor-pointer",children:[jsxRuntimeExports.jsx("input",{type:"checkbox",checked:ee,onChange:f=>Te(f.target.checked),className:"rounded border-slate-300 text-indigo-650 focus:ring-0 focus:ring-offset-0 cursor-pointer"}),jsxRuntimeExports.jsx("span",{children:"同步学生全屏"})]}),g==="ppt"&&(!p||!(ee&&se))&&jsxRuntimeExports.jsx("button",{onClick:()=>ze(!0),className:"p-1 rounded-lg text-slate-655 hover:bg-slate-200 border border-slate-200 bg-white transition-colors cursor-pointer",title:"全屏放映",children:jsxRuntimeExports.jsx(Maximize2,{size:11})})]})]}),jsxRuntimeExports.jsxs("div",{className:"flex-1 min-h-0 relative flex flex-row overflow-hidden",children:[g==="ppt"&&jsxRuntimeExports.jsxs("div",{className:me,children:[Y&&jsxRuntimeExports.jsxs("div",{className:"absolute top-4 left-4 right-4 flex items-center justify-between text-white/80 select-none z-[100001] px-4 py-2 bg-neutral-900/60 backdrop-blur-md rounded-xl border border-neutral-800",children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("span",{className:"w-2.5 h-2.5 rounded-full bg-emerald-500 animate-pulse"}),jsxRuntimeExports.jsxs("span",{className:"font-bold text-xs tracking-wider uppercase",children:[C==="md"?"Markdown Slides":`${C.toUpperCase()} Presentation`," ",p&&"(Synced)"]})]}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-4",children:[jsxRuntimeExports.jsxs("span",{className:"text-xs font-mono text-white/50",children:["Slide ",c+1," / ",ie]}),L&&jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[C==="md"&&jsxRuntimeExports.jsx("button",{onClick:()=>_(f=>!f),className:`px-2.5 py-1 rounded-md text-[10px] uppercase font-bold tracking-wider transition-colors border cursor-pointer ${R?"bg-emerald-50 border-emerald-400 text-white animate-pulse":"bg-transparent border-neutral-700 text-neutral-400 hover:bg-neutral-850"}`,children:R?"Autoplay Live":"Autoplay"}),jsxRuntimeExports.jsxs("label",{className:"flex items-center gap-1.5 text-xs text-white/70 cursor-pointer",children:[jsxRuntimeExports.jsx("input",{type:"checkbox",checked:ee,onChange:f=>Te(f.target.checked),className:"rounded border-neutral-700 bg-neutral-800 text-indigo-500 focus:ring-0 focus:ring-offset-0 cursor-pointer"}),jsxRuntimeExports.jsx("span",{children:"同步学生全屏"})]}),jsxRuntimeExports.jsx("button",{onClick:()=>ze(!1),className:"p-1 px-2.5 bg-red-655 text-white text-xs font-bold rounded-md transition-colors cursor-pointer border-0",title:"退出放映",children:"退出放映 (Esc)"})]})]})]}),jsxRuntimeExports.jsx("div",{className:"w-full flex-1 min-h-0 flex items-center justify-center relative",children:C==="pdf"?jsxRuntimeExports.jsx("div",{className:`w-full h-full flex items-center justify-center p-2 bg-slate-100 ${Y?"max-w-5xl aspect-video rounded-2xl overflow-hidden shadow-2xl border border-neutral-850":""}`,children:jsxRuntimeExports.jsx("iframe",{src:`${z}#page=${c+1}&toolbar=0&navpanes=0`,className:"w-full h-full border-0 rounded-xl"},`${z}-${Y?"fs":"card"}-${c}`)}):C==="pptx"?jsxRuntimeExports.jsx("div",{className:`w-full h-full flex items-center justify-center p-2 bg-slate-900/5 ${Y?"max-w-5xl aspect-video rounded-2xl overflow-hidden shadow-2xl border border-neutral-850":""}`,children:jsxRuntimeExports.jsx("div",{ref:Ne,className:"w-full h-full overflow-auto rounded-xl bg-white border border-slate-100 shadow-md flex items-center justify-center"})}):jsxRuntimeExports.jsx("div",{className:"flex-1 w-full flex items-center justify-center max-w-2xl min-h-0",children:jsxRuntimeExports.jsxs("div",{className:`w-full bg-white rounded-xl shadow-md border border-slate-100 flex flex-col overflow-y-auto p-6 md:p-8 aspect-video relative transition-all duration-300 hover:shadow-lg max-h-full ${Y?"max-w-4xl p-12 md:p-16 border-neutral-850 rounded-3xl shadow-2xl":""}`,children:[jsxRuntimeExports.jsxs("div",{className:"flex justify-between items-center text-[10px] font-semibold text-slate-400 border-b border-slate-100 pb-2 mb-4 shrink-0",children:[jsxRuntimeExports.jsx("span",{className:"tracking-wide uppercase text-indigo-650",children:"SMART CLASS SLIDE DECK"}),jsxRuntimeExports.jsxs("span",{className:"font-mono",children:["SLIDE ",c+1," / ",ie]})]}),jsxRuntimeExports.jsx("div",{className:"flex-1 min-h-0 overflow-y-auto pr-1",children:jsxRuntimeExports.jsx("div",{className:"markdown-body text-slate-800 leading-relaxed font-sans prose prose-neutral max-w-none text-xs",children:je[c]?jsxRuntimeExports.jsx(Markdown,{children:je[c]}):jsxRuntimeExports.jsx("div",{className:"text-center text-slate-400 italic py-8",children:"幻灯片没有内容,请在“编辑文档”中添加。"})})}),jsxRuntimeExports.jsxs("div",{className:"mt-4 pt-2 border-t border-slate-50 flex items-center justify-between text-[10px] text-slate-400 shrink-0 font-sans",children:[jsxRuntimeExports.jsx("span",{children:"智慧互动教室白板演示系统"}),jsxRuntimeExports.jsxs("span",{children:["Page ",c+1]})]})]})})}),!(p&&ee&&se)&&jsxRuntimeExports.jsxs("div",{className:`mt-4 flex items-center justify-center gap-3 select-none shrink-0 ${Y?"absolute bottom-6 bg-neutral-900/80 backdrop-blur-md px-6 py-2.5 rounded-full border border-neutral-800 shadow-2xl z-[100001]":"bg-white px-4 py-2 rounded-full border border-slate-200/80 shadow-md relative z-10"}`,children:[jsxRuntimeExports.jsx("button",{disabled:c===0||p&&ee&&se,onClick:()=>be(c-1),className:`p-1.5 rounded-full border transition-colors cursor-pointer ${c===0||p&&ee&&se?Y?"border-neutral-800 text-neutral-600 bg-neutral-950/20 cursor-not-allowed":"border-slate-100 bg-slate-50 text-slate-300 cursor-not-allowed":Y?"border-neutral-700 text-neutral-300 hover:bg-neutral-800":"border-slate-205 text-slate-655 hover:bg-slate-50"}`,title:"上一张 (ArrowLeft)",children:jsxRuntimeExports.jsx(ChevronLeft,{size:Y?18:14})}),jsxRuntimeExports.jsxs("div",{className:`flex items-center gap-1.5 px-1 font-mono text-xs ${Y?"text-neutral-200":"text-slate-700"}`,children:[jsxRuntimeExports.jsx("span",{className:`font-bold ${Y?"text-white text-base":"text-slate-900"}`,children:c+1}),jsxRuntimeExports.jsx("span",{className:Y?"text-neutral-600":"text-slate-350",children:"/"}),jsxRuntimeExports.jsx("span",{children:ie})]}),jsxRuntimeExports.jsx("button",{disabled:c>=ie-1||p&&ee&&se,onClick:()=>be(c+1),className:`p-1.5 rounded-full border transition-colors cursor-pointer ${c>=ie-1||p&&ee&&se?Y?"border-neutral-800 text-neutral-600 bg-neutral-950/20 cursor-not-allowed":"border-slate-100 bg-slate-50 text-slate-300 cursor-not-allowed":Y?"border-neutral-700 text-neutral-300 hover:bg-neutral-800":"border-slate-205 text-slate-655 hover:bg-slate-50"}`,title:"下一张 (ArrowRight)",children:jsxRuntimeExports.jsx(ChevronRight,{size:Y?18:14})})]})]}),g==="doc"&&C==="md"&&jsxRuntimeExports.jsxs("div",{className:"flex-1 flex flex-row min-h-0 bg-white",children:[q.length>0&&jsxRuntimeExports.jsxs("div",{className:"w-1/4 min-w-[120px] max-w-[200px] border-r border-slate-200 bg-slate-50/50 flex flex-col py-3 px-2 overflow-y-auto shrink-0 select-none",children:[jsxRuntimeExports.jsxs("span",{className:"text-[10px] font-bold text-slate-400 uppercase tracking-widest px-2 mb-2 flex items-center gap-1",children:[jsxRuntimeExports.jsx(FileText,{size:10}),"文档大纲"]}),jsxRuntimeExports.jsx("div",{className:"flex flex-col gap-0.5",children:q.map((f,k)=>jsxRuntimeExports.jsx("button",{onClick:()=>{const I=de.current?.querySelector(`[data-line-index="${f.lineIndex}"]`);I&&I.scrollIntoView({behavior:"smooth",block:"start"})},className:"text-left text-[11px] py-1 px-2 rounded hover:bg-slate-100 text-slate-600 hover:text-slate-900 truncate cursor-pointer font-medium whitespace-nowrap border-0 bg-transparent",style:{paddingLeft:`${Math.max(8,f.level*6)}px`},title:f.text,children:f.text},k))})]}),jsxRuntimeExports.jsx("div",{className:"flex-1 min-h-0 overflow-y-auto p-6 md:p-8",ref:de,children:jsxRuntimeExports.jsx("div",{className:"markdown-body prose prose-neutral max-w-none text-xs leading-relaxed text-slate-700",children:j.split(`
|
|
49
|
-
`).map((
|
|
47
|
+
当马拉着车在水平路面上加速前进时,马拉车的力与车拉马的力,哪一个更大?`}],Y=(()=>{const h=f.split(`
|
|
48
|
+
`),v=[];return h.forEach((A,K)=>{const ge=A.match(/^(#{1,3})\s+(.*)$/);ge&&v.push({text:ge[2].trim(),level:ge[1].length,lineIndex:K})}),v})();if(H&&typeof document<"u")return jsxRuntimeExports.jsxs("div",{className:"w-full h-full flex flex-col items-center justify-center bg-slate-900/10 text-slate-400 font-sans p-4",children:[jsxRuntimeExports.jsxs("div",{className:"flex flex-col items-center gap-2",children:[jsxRuntimeExports.jsx(Presentation,{size:24,className:"text-indigo-500 animate-pulse"}),jsxRuntimeExports.jsx("span",{className:"text-xs",children:"演示文稿正在全屏放映中"})]}),reactDomExports.createPortal(jsxRuntimeExports.jsxs("div",{className:"fixed inset-0 z-[99999] bg-neutral-950 flex flex-col items-center justify-center font-sans p-6",children:[jsxRuntimeExports.jsxs("div",{className:"absolute top-4 left-4 right-4 flex items-center justify-between text-white/80 select-none z-[100001] px-4 py-2 bg-neutral-900/60 backdrop-blur-md rounded-xl border border-neutral-800",children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("span",{className:"w-2.5 h-2.5 rounded-full bg-emerald-500 animate-pulse"}),jsxRuntimeExports.jsxs("span",{className:"font-bold text-xs tracking-wider uppercase",children:[C==="md"?"Markdown Slides":`${C.toUpperCase()} Presentation`," ",p&&"(Synced)"]})]}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-4",children:[jsxRuntimeExports.jsxs("span",{className:"text-xs font-mono text-white/50",children:["Slide ",c+1," / ",ie]}),L&&jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[C==="md"&&jsxRuntimeExports.jsx("button",{onClick:()=>J(h=>!h),className:`px-2.5 py-1 rounded-md text-[10px] uppercase font-bold tracking-wider transition-colors border cursor-pointer ${k?"bg-emerald-50 border-emerald-400 text-white animate-pulse":"bg-transparent border-neutral-700 text-neutral-400 hover:bg-neutral-850"}`,children:k?"Autoplay Live":"Autoplay"}),jsxRuntimeExports.jsxs("label",{className:"flex items-center gap-1.5 text-xs text-white/70 cursor-pointer",children:[jsxRuntimeExports.jsx("input",{type:"checkbox",checked:ee,onChange:h=>Te(h.target.checked),className:"rounded border-neutral-700 bg-neutral-800 text-indigo-500 focus:ring-0 focus:ring-offset-0 cursor-pointer"}),jsxRuntimeExports.jsx("span",{children:"同步学生全屏"})]})]}),(!p||!se||!ee||R)&&jsxRuntimeExports.jsx("button",{onClick:()=>ze(!1),className:"p-1 px-2.5 bg-red-600 text-white text-xs font-bold rounded-lg transition-colors cursor-pointer border-0 hover:bg-red-700",title:"退出放映",children:"退出放映 (Esc)"})]})]}),jsxRuntimeExports.jsx("div",{className:"w-full flex-1 min-h-0 flex items-center justify-center relative",children:C==="pdf"?jsxRuntimeExports.jsx("div",{className:"w-full h-full flex items-center justify-center p-2 bg-slate-100 max-w-[90vw] max-h-[82vh] aspect-video rounded-2xl overflow-hidden shadow-2xl border border-neutral-850",children:jsxRuntimeExports.jsx("iframe",{src:`${z}#page=${c+1}&toolbar=0&navpanes=0`,className:"w-full h-full border-0 rounded-xl"},`${z}-fs-${c}`)}):C==="pptx"?jsxRuntimeExports.jsx("div",{className:"w-full h-full flex items-center justify-center p-2 bg-slate-900/5 max-w-[90vw] max-h-[82vh] aspect-video rounded-2xl overflow-hidden shadow-2xl border border-neutral-850",children:jsxRuntimeExports.jsx("div",{ref:Ne,className:"w-full h-full overflow-auto rounded-xl bg-white border border-slate-100 shadow-md flex items-center justify-center"})}):jsxRuntimeExports.jsx("div",{className:"flex-1 w-full flex items-center justify-center max-w-[90vw] min-h-0",children:jsxRuntimeExports.jsxs("div",{className:"w-full bg-white rounded-xl shadow-md border border-slate-100 flex flex-col overflow-y-auto p-6 md:p-8 aspect-video relative transition-all duration-300 hover:shadow-lg max-h-[82vh] max-w-none p-12 md:p-16 border-neutral-850 rounded-3xl shadow-2xl",children:[jsxRuntimeExports.jsxs("div",{className:"flex justify-between items-center text-[10px] font-semibold text-slate-400 border-b border-slate-100 pb-2 mb-4 shrink-0",children:[jsxRuntimeExports.jsx("span",{className:"tracking-wide uppercase text-indigo-650",children:"SMART CLASS SLIDE DECK"}),jsxRuntimeExports.jsxs("span",{className:"font-mono",children:["SLIDE ",c+1," / ",ie]})]}),jsxRuntimeExports.jsx("div",{className:"flex-1 min-h-0 overflow-y-auto pr-1",children:jsxRuntimeExports.jsx("div",{className:"markdown-body text-slate-800 leading-relaxed font-sans prose prose-neutral max-w-none text-xs",children:je[c]?jsxRuntimeExports.jsx(Markdown,{children:je[c]}):jsxRuntimeExports.jsx("div",{className:"text-center text-slate-400 italic py-8",children:"幻灯片没有内容,请在“编辑文档”中添加。"})})}),jsxRuntimeExports.jsxs("div",{className:"mt-4 pt-2 border-t border-slate-50 flex items-center justify-between text-[10px] text-slate-400 shrink-0 font-sans",children:[jsxRuntimeExports.jsx("span",{children:"智慧互动教室白板演示系统"}),jsxRuntimeExports.jsxs("span",{children:["Page ",c+1]})]})]})})}),!(p&&ee&&se)&&jsxRuntimeExports.jsxs("div",{className:"absolute bottom-6 bg-neutral-900/80 backdrop-blur-md px-6 py-2.5 rounded-full border border-neutral-800 shadow-2xl z-[100001]",children:[jsxRuntimeExports.jsx("button",{disabled:c===0||p,onClick:()=>be(c-1),className:`p-1.5 rounded-full border transition-colors cursor-pointer ${c===0||p?"border-neutral-800 text-neutral-600 bg-neutral-950/20 cursor-not-allowed":"border-neutral-700 text-neutral-300 hover:bg-neutral-800"}`,title:"上一张 (ArrowLeft)",children:jsxRuntimeExports.jsx(ChevronLeft,{size:18})}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5 px-1 font-mono text-xs text-neutral-200",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-white text-base",children:c+1}),jsxRuntimeExports.jsx("span",{className:"text-neutral-600",children:"/"}),jsxRuntimeExports.jsx("span",{children:ie})]}),jsxRuntimeExports.jsx("button",{disabled:c>=ie-1||p,onClick:()=>be(c+1),className:`p-1.5 rounded-full border transition-colors cursor-pointer ${c>=ie-1||p?"border-neutral-800 text-neutral-600 bg-neutral-950/20 cursor-not-allowed":"border-neutral-700 text-neutral-300 hover:bg-neutral-800"}`,title:"下一张 (ArrowRight)",children:jsxRuntimeExports.jsx(ChevronRight,{size:18})})]})]}),document.body)]});const me=H?"fixed inset-0 z-[99999] bg-neutral-950 flex flex-col items-center justify-center font-sans p-6":"flex-1 flex flex-col items-center justify-between p-4 bg-slate-900/5 relative min-w-0";return jsxRuntimeExports.jsxs("div",{className:"w-full h-full flex flex-col bg-slate-50 text-slate-800 overflow-hidden text-xs relative font-sans",children:[!H&&jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between px-3 py-1.5 bg-slate-100 border-b border-slate-200 shrink-0 select-none relative z-10",children:[jsxRuntimeExports.jsx("div",{className:"flex items-center gap-1",children:C==="md"?jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsxs("button",{onClick:()=>O("ppt"),className:`px-2 py-1 rounded flex items-center gap-1 font-medium transition-colors cursor-pointer ${E==="ppt"?"bg-indigo-600 text-white shadow-sm":"text-slate-600 hover:bg-slate-200"}`,title:"播放课件幻灯片 (PPT Mode)",children:[jsxRuntimeExports.jsx(Play,{size:11}),jsxRuntimeExports.jsx("span",{children:"PPT 播放"})]}),jsxRuntimeExports.jsxs("button",{onClick:()=>O("doc"),className:`px-2 py-1 rounded flex items-center gap-1 font-medium transition-colors cursor-pointer ${E==="doc"?"bg-indigo-600 text-white shadow-sm":"text-slate-600 hover:bg-slate-200"}`,title:"以精美文档形式阅读 (Markdown Document mode)",children:[jsxRuntimeExports.jsx(BookOpen,{size:11}),jsxRuntimeExports.jsx("span",{children:"文档阅读"})]}),jsxRuntimeExports.jsxs("button",{onClick:()=>O("edit"),className:`px-2 py-1 rounded flex items-center gap-1 font-medium transition-colors cursor-pointer ${E==="edit"?"bg-indigo-600 text-white shadow-sm":"text-slate-600 hover:bg-slate-200"}`,title:"在线编辑 Markdown 内容",children:[jsxRuntimeExports.jsx(PenLine,{size:11}),jsxRuntimeExports.jsx("span",{children:"编辑文档"})]})]}):jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1 bg-indigo-50 border border-indigo-200/50 text-indigo-700 px-2 py-0.5 rounded text-[10px] font-semibold",children:[jsxRuntimeExports.jsx(Presentation,{size:10}),jsxRuntimeExports.jsxs("span",{children:[C.toUpperCase()," 课件演示中"]})]})}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-3",children:[L&&jsxRuntimeExports.jsx("div",{className:"flex items-center gap-1.5 border-r border-slate-200 pr-3",children:pe?jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1 text-[10px] text-slate-500 font-medium",children:[jsxRuntimeExports.jsx(LoaderCircle,{size:10,className:"animate-spin"}),jsxRuntimeExports.jsx("span",{children:"上传解析中..."})]}):G?jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5 bg-slate-200/50 pl-2 pr-1.5 py-0.5 rounded border border-slate-300/30",children:[jsxRuntimeExports.jsx("span",{className:"text-[10px] font-medium text-slate-600 max-w-[120px] truncate font-mono",title:_,children:_}),jsxRuntimeExports.jsx("button",{onClick:He,className:"p-0.5 hover:bg-slate-300 rounded text-red-500 cursor-pointer border-0 bg-transparent",title:"清除并切换回 Markdown",children:jsxRuntimeExports.jsx(Trash2,{size:10})})]}):jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsxs("button",{onClick:()=>fe.current?.click(),className:"px-2 py-1 rounded bg-indigo-50 border border-indigo-200 text-indigo-700 hover:bg-indigo-100 flex items-center gap-1 font-semibold text-[10px] cursor-pointer",title:"上传 PPTX 或 PDF 课件",children:[jsxRuntimeExports.jsx(Upload,{size:10}),jsxRuntimeExports.jsx("span",{children:"上传课件"})]}),jsxRuntimeExports.jsx("input",{type:"file",ref:fe,onChange:Ie,accept:".pdf,.pptx",className:"hidden"})]})}),E==="ppt"&&C==="md"&&jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5",children:[jsxRuntimeExports.jsxs("button",{onClick:()=>J(h=>!h),className:`p-1 rounded flex items-center gap-1 font-semibold text-[10px] transition-colors border cursor-pointer ${k?"bg-emerald-50 border-emerald-300 text-emerald-700":"bg-white border-slate-200 text-slate-500 hover:bg-slate-50"}`,title:"开启/关闭幻灯片自动播放",children:[k?jsxRuntimeExports.jsx("span",{className:"w-1.5 h-1.5 rounded-full bg-emerald-500 animate-ping"}):null,jsxRuntimeExports.jsx("span",{children:k?"自动播放中":"自动播放"})]}),k&&jsxRuntimeExports.jsxs("select",{value:ce,onChange:h=>T(Number(h.target.value)),className:"bg-white border border-slate-200 rounded px-1 text-[10px] py-0.5 text-slate-700 font-medium",children:[jsxRuntimeExports.jsx("option",{value:2,children:"2秒"}),jsxRuntimeExports.jsx("option",{value:4,children:"4秒"}),jsxRuntimeExports.jsx("option",{value:6,children:"6秒"}),jsxRuntimeExports.jsx("option",{value:10,children:"10秒"})]})]}),L&&E==="ppt"&&jsxRuntimeExports.jsxs("label",{className:"flex items-center gap-1 text-[10px] text-slate-500 font-medium cursor-pointer",children:[jsxRuntimeExports.jsx("input",{type:"checkbox",checked:ee,onChange:h=>Te(h.target.checked),className:"rounded border-slate-300 text-indigo-650 focus:ring-0 focus:ring-offset-0 cursor-pointer"}),jsxRuntimeExports.jsx("span",{children:"同步学生全屏"})]}),E==="ppt"&&(!p||!(ee&&se))&&jsxRuntimeExports.jsx("button",{onClick:()=>ze(!0),className:"p-1 rounded-lg text-slate-655 hover:bg-slate-200 border border-slate-200 bg-white transition-colors cursor-pointer",title:"全屏放映",children:jsxRuntimeExports.jsx(Maximize2,{size:11})})]})]}),jsxRuntimeExports.jsxs("div",{className:"flex-1 min-h-0 relative flex flex-row overflow-hidden",children:[E==="ppt"&&jsxRuntimeExports.jsxs("div",{className:me,children:[H&&jsxRuntimeExports.jsxs("div",{className:"absolute top-4 left-4 right-4 flex items-center justify-between text-white/80 select-none z-[100001] px-4 py-2 bg-neutral-900/60 backdrop-blur-md rounded-xl border border-neutral-800",children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("span",{className:"w-2.5 h-2.5 rounded-full bg-emerald-500 animate-pulse"}),jsxRuntimeExports.jsxs("span",{className:"font-bold text-xs tracking-wider uppercase",children:[C==="md"?"Markdown Slides":`${C.toUpperCase()} Presentation`," ",p&&"(Synced)"]})]}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-4",children:[jsxRuntimeExports.jsxs("span",{className:"text-xs font-mono text-white/50",children:["Slide ",c+1," / ",ie]}),L&&jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[C==="md"&&jsxRuntimeExports.jsx("button",{onClick:()=>J(h=>!h),className:`px-2.5 py-1 rounded-md text-[10px] uppercase font-bold tracking-wider transition-colors border cursor-pointer ${k?"bg-emerald-50 border-emerald-400 text-white animate-pulse":"bg-transparent border-neutral-700 text-neutral-400 hover:bg-neutral-850"}`,children:k?"Autoplay Live":"Autoplay"}),jsxRuntimeExports.jsxs("label",{className:"flex items-center gap-1.5 text-xs text-white/70 cursor-pointer",children:[jsxRuntimeExports.jsx("input",{type:"checkbox",checked:ee,onChange:h=>Te(h.target.checked),className:"rounded border-neutral-700 bg-neutral-800 text-indigo-500 focus:ring-0 focus:ring-offset-0 cursor-pointer"}),jsxRuntimeExports.jsx("span",{children:"同步学生全屏"})]}),jsxRuntimeExports.jsx("button",{onClick:()=>ze(!1),className:"p-1 px-2.5 bg-red-655 text-white text-xs font-bold rounded-md transition-colors cursor-pointer border-0",title:"退出放映",children:"退出放映 (Esc)"})]})]})]}),jsxRuntimeExports.jsx("div",{className:"w-full flex-1 min-h-0 flex items-center justify-center relative",children:C==="pdf"?jsxRuntimeExports.jsx("div",{className:`w-full h-full flex items-center justify-center p-2 bg-slate-100 ${H?"max-w-5xl aspect-video rounded-2xl overflow-hidden shadow-2xl border border-neutral-850":""}`,children:jsxRuntimeExports.jsx("iframe",{src:`${z}#page=${c+1}&toolbar=0&navpanes=0`,className:"w-full h-full border-0 rounded-xl"},`${z}-${H?"fs":"card"}-${c}`)}):C==="pptx"?jsxRuntimeExports.jsx("div",{className:`w-full h-full flex items-center justify-center p-2 bg-slate-900/5 ${H?"max-w-5xl aspect-video rounded-2xl overflow-hidden shadow-2xl border border-neutral-850":""}`,children:jsxRuntimeExports.jsx("div",{ref:Ne,className:"w-full h-full overflow-auto rounded-xl bg-white border border-slate-100 shadow-md flex items-center justify-center"})}):jsxRuntimeExports.jsx("div",{className:"flex-1 w-full flex items-center justify-center max-w-2xl min-h-0",children:jsxRuntimeExports.jsxs("div",{className:`w-full bg-white rounded-xl shadow-md border border-slate-100 flex flex-col overflow-y-auto p-6 md:p-8 aspect-video relative transition-all duration-300 hover:shadow-lg max-h-full ${H?"max-w-4xl p-12 md:p-16 border-neutral-850 rounded-3xl shadow-2xl":""}`,children:[jsxRuntimeExports.jsxs("div",{className:"flex justify-between items-center text-[10px] font-semibold text-slate-400 border-b border-slate-100 pb-2 mb-4 shrink-0",children:[jsxRuntimeExports.jsx("span",{className:"tracking-wide uppercase text-indigo-650",children:"SMART CLASS SLIDE DECK"}),jsxRuntimeExports.jsxs("span",{className:"font-mono",children:["SLIDE ",c+1," / ",ie]})]}),jsxRuntimeExports.jsx("div",{className:"flex-1 min-h-0 overflow-y-auto pr-1",children:jsxRuntimeExports.jsx("div",{className:"markdown-body text-slate-800 leading-relaxed font-sans prose prose-neutral max-w-none text-xs",children:je[c]?jsxRuntimeExports.jsx(Markdown,{children:je[c]}):jsxRuntimeExports.jsx("div",{className:"text-center text-slate-400 italic py-8",children:"幻灯片没有内容,请在“编辑文档”中添加。"})})}),jsxRuntimeExports.jsxs("div",{className:"mt-4 pt-2 border-t border-slate-50 flex items-center justify-between text-[10px] text-slate-400 shrink-0 font-sans",children:[jsxRuntimeExports.jsx("span",{children:"智慧互动教室白板演示系统"}),jsxRuntimeExports.jsxs("span",{children:["Page ",c+1]})]})]})})}),!(p&&ee&&se)&&jsxRuntimeExports.jsxs("div",{className:`mt-4 flex items-center justify-center gap-3 select-none shrink-0 ${H?"absolute bottom-6 bg-neutral-900/80 backdrop-blur-md px-6 py-2.5 rounded-full border border-neutral-800 shadow-2xl z-[100001]":"bg-white px-4 py-2 rounded-full border border-slate-200/80 shadow-md relative z-10"}`,children:[jsxRuntimeExports.jsx("button",{disabled:c===0||p&&ee&&se,onClick:()=>be(c-1),className:`p-1.5 rounded-full border transition-colors cursor-pointer ${c===0||p&&ee&&se?H?"border-neutral-800 text-neutral-600 bg-neutral-950/20 cursor-not-allowed":"border-slate-100 bg-slate-50 text-slate-300 cursor-not-allowed":H?"border-neutral-700 text-neutral-300 hover:bg-neutral-800":"border-slate-205 text-slate-655 hover:bg-slate-50"}`,title:"上一张 (ArrowLeft)",children:jsxRuntimeExports.jsx(ChevronLeft,{size:H?18:14})}),jsxRuntimeExports.jsxs("div",{className:`flex items-center gap-1.5 px-1 font-mono text-xs ${H?"text-neutral-200":"text-slate-700"}`,children:[jsxRuntimeExports.jsx("span",{className:`font-bold ${H?"text-white text-base":"text-slate-900"}`,children:c+1}),jsxRuntimeExports.jsx("span",{className:H?"text-neutral-600":"text-slate-350",children:"/"}),jsxRuntimeExports.jsx("span",{children:ie})]}),jsxRuntimeExports.jsx("button",{disabled:c>=ie-1||p&&ee&&se,onClick:()=>be(c+1),className:`p-1.5 rounded-full border transition-colors cursor-pointer ${c>=ie-1||p&&ee&&se?H?"border-neutral-800 text-neutral-600 bg-neutral-950/20 cursor-not-allowed":"border-slate-100 bg-slate-50 text-slate-300 cursor-not-allowed":H?"border-neutral-700 text-neutral-300 hover:bg-neutral-800":"border-slate-205 text-slate-655 hover:bg-slate-50"}`,title:"下一张 (ArrowRight)",children:jsxRuntimeExports.jsx(ChevronRight,{size:H?18:14})})]})]}),E==="doc"&&C==="md"&&jsxRuntimeExports.jsxs("div",{className:"flex-1 flex flex-row min-h-0 bg-white",children:[Y.length>0&&jsxRuntimeExports.jsxs("div",{className:"w-1/4 min-w-[120px] max-w-[200px] border-r border-slate-200 bg-slate-50/50 flex flex-col py-3 px-2 overflow-y-auto shrink-0 select-none",children:[jsxRuntimeExports.jsxs("span",{className:"text-[10px] font-bold text-slate-400 uppercase tracking-widest px-2 mb-2 flex items-center gap-1",children:[jsxRuntimeExports.jsx(FileText,{size:10}),"文档大纲"]}),jsxRuntimeExports.jsx("div",{className:"flex flex-col gap-0.5",children:Y.map((h,v)=>jsxRuntimeExports.jsx("button",{onClick:()=>{const A=de.current?.querySelector(`[data-line-index="${h.lineIndex}"]`);A&&A.scrollIntoView({behavior:"smooth",block:"start"})},className:"text-left text-[11px] py-1 px-2 rounded hover:bg-slate-100 text-slate-600 hover:text-slate-900 truncate cursor-pointer font-medium whitespace-nowrap border-0 bg-transparent",style:{paddingLeft:`${Math.max(8,h.level*6)}px`},title:h.text,children:h.text},v))})]}),jsxRuntimeExports.jsx("div",{className:"flex-1 min-h-0 overflow-y-auto p-6 md:p-8",ref:de,children:jsxRuntimeExports.jsx("div",{className:"markdown-body prose prose-neutral max-w-none text-xs leading-relaxed text-slate-700",children:f.split(`
|
|
49
|
+
`).map((h,v)=>{const A=h.match(/^(#{1,3})\s+(.*)$/);if(A){const K=A[1].length,ge=A[2].trim(),I=K===1?"h1":K===2?"h2":"h3",ye=K===1?"text-lg font-bold text-indigo-900 border-b pb-1 mt-4 mb-2":K===2?"text-base font-bold text-slate-800 mt-3 mb-1.5":"text-sm font-semibold text-slate-700 mt-2 mb-1";return jsxRuntimeExports.jsx(I,{"data-line-index":v,className:ye,children:ge},v)}return h.trim()==="---"?jsxRuntimeExports.jsx("hr",{className:"my-4 border-slate-200"},v):jsxRuntimeExports.jsx("p",{className:"my-1.5 text-slate-600 antialiased leading-relaxed",children:h},v)})})})]}),E==="edit"&&C==="md"&&jsxRuntimeExports.jsxs("div",{className:"flex-1 flex flex-col md:flex-row min-h-0 bg-white",children:[jsxRuntimeExports.jsxs("div",{className:"w-full md:w-1/3 border-b md:border-b-0 md:border-r border-slate-100 bg-slate-50/40 p-3 flex flex-col overflow-y-auto shrink-0 select-none",children:[jsxRuntimeExports.jsxs("span",{className:"text-[10px] font-bold text-slate-400 tracking-wider uppercase mb-2 flex items-center gap-1",children:[jsxRuntimeExports.jsx(WandSparkles,{size:10,className:"text-indigo-650"}),"推荐课件及文档模板"]}),jsxRuntimeExports.jsx("div",{className:"flex flex-col gap-2",children:Ye.map((h,v)=>jsxRuntimeExports.jsxs("button",{type:"button",onClick:()=>{window.confirm(`确定要加载模板 “${h.name}” 吗?这将会覆盖当前白板课件中的所有编辑内容。`)&&(Ee(h.content),S(0))},className:"w-full text-left p-2.5 rounded-lg border border-slate-200 bg-white hover:border-indigo-300 hover:shadow-sm transition-all focus:outline-none cursor-pointer group",children:[jsxRuntimeExports.jsx("div",{className:"font-bold text-[11px] text-slate-800 group-hover:text-indigo-700 whitespace-nowrap overflow-hidden text-ellipsis",children:h.name}),jsxRuntimeExports.jsx("div",{className:"text-[9px] text-slate-400 mt-0.5",children:h.desc})]},v))}),jsxRuntimeExports.jsxs("div",{className:"mt-4 p-2 bg-amber-50 rounded border border-amber-100 text-[10px] text-amber-700 font-sans leading-relaxed",children:[jsxRuntimeExports.jsx("strong",{children:"💡 使用提示"}),jsxRuntimeExports.jsx("br",{}),"在任意位置插入一行 ",jsxRuntimeExports.jsx("code",{children:"---"})," 即可分割出一个新的幻灯片(PPT)页面。"]})]}),jsxRuntimeExports.jsxs("div",{className:"flex-1 flex flex-col p-3 min-h-[200px]",children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between mb-1.5 px-1",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-slate-500 text-[10px] uppercase",children:"Markdown Source Code"}),jsxRuntimeExports.jsx("span",{className:"text-[9px] text-slate-400",children:"实时自动同步到所有协同终端"})]}),jsxRuntimeExports.jsx("textarea",{value:f,onChange:h=>Ee(h.target.value),placeholder:"在此输入 Markdown 文档。使用 '---' 来作为 PPT 页面分页符...",className:"flex-1 w-full p-3 font-mono text-xs bg-slate-50 border border-slate-200 rounded-lg focus:outline-none focus:ring-1 focus:ring-indigo-500 focus:bg-white transition-all resize-none leading-relaxed text-slate-800"})]})]})]})]})}let _srcDocAttemptCounter=0;function wrapSrcDocWithBridge(s,l){const d={student_id:"teacher_preview",student_name:"Teacher (Preview)",class_id:"",attempt_id:`att_srcdoc_${l}_${Date.now()}_${++_srcDocAttemptCounter}`},E={uuid:l,name:"Whiteboard HTML Applet"};return`<!DOCTYPE html>
|
|
50
50
|
<html><head>
|
|
51
51
|
<script>
|
|
52
52
|
window.__LMS_STUDENT__ = ${JSON.stringify(d)};
|
|
53
|
-
window.__LMS_COURSEWARE__ = ${JSON.stringify(
|
|
53
|
+
window.__LMS_COURSEWARE__ = ${JSON.stringify(E)};
|
|
54
54
|
(function() {
|
|
55
55
|
try {
|
|
56
56
|
// Override window.postMessage (self-targeting, always works)
|
|
@@ -86,17 +86,17 @@ The teacher used the virtual whiteboard to ___ classroom active learning slides.
|
|
|
86
86
|
<script src="/bridge.js"><\/script>
|
|
87
87
|
</head><body>
|
|
88
88
|
${s||""}
|
|
89
|
-
</body></html>`}const WhiteboardToolbar=({tool:s,setTool:
|
|
89
|
+
</body></html>`}const WhiteboardToolbar=({tool:s,setTool:l,setSelectedShapeId:g,highlighterColor:d,setHighlighterColor:E,onElementAdd:O,currentPage:f,activeSegmentId:N,lessonId:c,safeElements:S,selectedShapeId:k,showGrid:J,setShowGrid:ce,userRole:T="teacher",isSyncing:R,setIsSyncing:P,handleClearBoard:de,handleResetBoard:L,handleElementDelete:p,setDialog:z,setDialogInput:C,onRefresh:_})=>jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-start gap-1.5 px-3 py-1.5 bg-white border-b border-slate-200 shrink-0 font-sans select-none",children:[jsxRuntimeExports.jsx("button",{onClick:()=>{l("cursor"),g(null)},className:`p-1.5 rounded-xl transition-all cursor-pointer ${s==="cursor"?"bg-indigo-600 text-white shadow-2xs":"text-slate-600 hover:bg-slate-100"}`,title:"选择工具 (Pointer / Selector)",children:jsxRuntimeExports.jsx(MousePointer2,{size:16})}),jsxRuntimeExports.jsx("div",{className:"w-px h-4 bg-slate-200/80 mx-0.5"}),jsxRuntimeExports.jsx("button",{onClick:()=>l("pen"),className:`p-1.5 rounded-xl transition-all cursor-pointer ${s==="pen"?"bg-indigo-600 text-white shadow-2xs":"text-slate-600 hover:bg-slate-100"}`,title:"画笔工具 (Pen)",children:jsxRuntimeExports.jsx(PenTool,{size:16})}),jsxRuntimeExports.jsx("button",{onClick:()=>l("highlighter"),className:`p-1.5 rounded-xl transition-all cursor-pointer ${s==="highlighter"?"bg-amber-500 text-white shadow-2xs":"text-slate-600 hover:bg-slate-100"}`,title:"荧光高亮笔 (Highlighter)",children:jsxRuntimeExports.jsx(Highlighter,{size:16})}),s==="highlighter"&&jsxRuntimeExports.jsx("div",{className:"flex items-center gap-1 bg-slate-100 p-1 rounded-xl border border-slate-200 animate-in zoom-in-95 duration-150",children:[{hex:"#facc15",label:"Yellow"},{hex:"#4ade80",label:"Green"},{hex:"#f472b6",label:"Pink"},{hex:"#60a5fa",label:"Blue"}].map(G=>jsxRuntimeExports.jsx("button",{onClick:()=>E(G.hex),className:`w-3.5 h-3.5 rounded-full border transition-all ${d===G.hex?"ring-2 ring-indigo-500 scale-110 border-white":"border-transparent"}`,style:{backgroundColor:G.hex},title:G.label},G.hex))}),jsxRuntimeExports.jsx("div",{className:"w-px h-4 bg-slate-200/80 mx-0.5"}),jsxRuntimeExports.jsx("button",{onClick:()=>l("rect"),className:`p-1.5 rounded-xl transition-all cursor-pointer ${s==="rect"?"bg-indigo-600 text-white shadow-2xs":"text-slate-600 hover:bg-slate-100"}`,title:"矩形工具 (Rectangle)",children:jsxRuntimeExports.jsx(Square,{size:16})}),jsxRuntimeExports.jsx("button",{onClick:()=>l("circle"),className:`p-1.5 rounded-xl transition-all cursor-pointer ${s==="circle"?"bg-indigo-600 text-white shadow-2xs":"text-slate-600 hover:bg-slate-100"}`,title:"圆形工具 (Circle)",children:jsxRuntimeExports.jsx(Circle,{size:16})}),jsxRuntimeExports.jsx("button",{onClick:()=>l("text"),className:`p-1.5 rounded-xl transition-all cursor-pointer ${s==="text"?"bg-indigo-600 text-white shadow-2xs":"text-slate-600 hover:bg-slate-100"}`,title:"文本工具 (Text)",children:jsxRuntimeExports.jsx(Type,{size:16})}),jsxRuntimeExports.jsx("div",{className:"w-px h-4 bg-slate-200/80 mx-0.5"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:presentation",placement:"before"}),jsxRuntimeExports.jsx("button",{onClick:()=>{C(`# Title Slide
|
|
90
90
|
---
|
|
91
91
|
## Slide 2`),z({type:"prompt",title:"添加演示文稿",message:"请输入演示文稿的 Markdown 内容 (使用 --- 拆分新幻灯片):",placeholder:`# Title Slide
|
|
92
92
|
---
|
|
93
93
|
## Slide 2`,onConfirm:async G=>{const pe=G||`# Title Slide
|
|
94
94
|
---
|
|
95
|
-
## Slide 2`;
|
|
95
|
+
## Slide 2`;P(!0);try{await O("presentation",{markdown:pe,x:50,y:50,width:600,height:400,slideX:0,slideY:0,page:f,segmentId:N}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:c},timestamp:Date.now(),correlationId:c})}finally{P(!1),z(null)}}})},className:"p-1.5 rounded-xl text-slate-600 hover:bg-slate-100 transition-all cursor-pointer",title:"插入演示幻灯片 (Presentation)",children:jsxRuntimeExports.jsx(Presentation,{size:16})}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:presentation",placement:"after"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:code-sandbox",placement:"before"}),jsxRuntimeExports.jsx("button",{onClick:async()=>{P(!0);try{await O("code-sandbox",{code:"console.log('Hello Sandbox!');",x:100,y:100,page:f,segmentId:N}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:c},timestamp:Date.now(),correlationId:c})}finally{P(!1)}},className:"p-1.5 rounded-xl text-slate-600 hover:bg-slate-100 transition-all cursor-pointer",title:"插入代码沙箱 (Code Sandbox)",children:jsxRuntimeExports.jsx(Terminal,{size:16})}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:code-sandbox",placement:"after"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:math-graph",placement:"before"}),jsxRuntimeExports.jsx("button",{onClick:async()=>{P(!0);try{await O("math-graph",{equation:"Math.sin(x)",x:100,y:150,page:f,segmentId:N}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:c},timestamp:Date.now(),correlationId:c})}finally{P(!1)}},className:"p-1.5 rounded-xl text-slate-600 hover:bg-slate-100 transition-all cursor-pointer",title:"插入数学函数图表 (Math Graph)",children:jsxRuntimeExports.jsx(Activity,{size:16})}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:math-graph",placement:"after"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:courseware",placement:"before"}),jsxRuntimeExports.jsx("button",{onClick:async()=>{P(!0);try{await O("html-applet",{code:`<!-- Interactive Web Courseware -->
|
|
96
96
|
<div style='padding:20px; text-align:center;'>
|
|
97
97
|
<h2>Interactive Web Courseware</h2>
|
|
98
98
|
<p>可在右侧属性栏中选择本地 ZIP/HTML 部署包。</p>
|
|
99
|
-
</div>`,x:100,y:150,page:j,segmentId:w}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:c},timestamp:Date.now(),correlationId:c})}finally{S(!1)}},className:"p-1.5 rounded-xl text-slate-600 hover:bg-slate-100 transition-all cursor-pointer",title:"插入交互网页课件 (Interactive Courseware)",children:jsxRuntimeExports.jsx(Globe,{size:16})}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:courseware",placement:"after"}),jsxRuntimeExports.jsx("div",{className:"w-px h-4 bg-slate-200/80 mx-0.5"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:rollcall",placement:"before"}),jsxRuntimeExports.jsx("button",{onClick:async()=>{S(!0);try{await M("rollcall",{title:"随机点名助手",x:120,y:120,page:j,segmentId:w}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:c},timestamp:Date.now(),correlationId:c})}finally{S(!1)}},className:"p-1.5 rounded-xl text-indigo-600 hover:bg-indigo-50 transition-all cursor-pointer flex items-center gap-1 text-xs font-semibold",title:"插入随机点名组件 (Roll Call)",children:jsxRuntimeExports.jsx(UserCheck,{size:15})}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:rollcall",placement:"after"}),jsxRuntimeExports.jsx("div",{className:"w-px h-4 bg-slate-200/80 mx-0.5"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"classroom.tool"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:ai-tutor",placement:"before"}),jsxRuntimeExports.jsx("button",{onClick:async()=>{S(!0);try{(await fetch(`/api/lessons/${c}/ai-tutor`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({elements:P.map(pe=>({type:pe.type,data:JSON.parse(pe.data)}))})})).ok?(frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:c},timestamp:Date.now(),correlationId:c}),A&&A()):z({type:"alert",title:"AI 辅导提示",message:"无法获取 AI 授课助手的帮助,请稍后再试。",onConfirm:()=>z(null)})}finally{S(!1)}},className:"p-1.5 rounded-xl text-purple-600 hover:bg-purple-50 transition-all cursor-pointer",title:"请求 AI 助教建议 (Ask AI Tutor)",children:jsxRuntimeExports.jsx(WandSparkles,{size:16})}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:ai-tutor",placement:"after"}),jsxRuntimeExports.jsx("div",{className:"w-px h-4 bg-slate-200/80 mx-0.5"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:grid",placement:"before"}),jsxRuntimeExports.jsx("button",{onClick:()=>ce(G=>!G),className:`p-1.5 rounded-xl transition-all cursor-pointer ${_?"text-indigo-600 bg-indigo-50/80":"text-slate-400 hover:bg-slate-100"}`,title:_?"关闭网格背景":"开启网格背景",children:jsxRuntimeExports.jsx(Grid3x3,{size:16})}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:grid",placement:"after"}),R&&jsxRuntimeExports.jsxs("button",{onClick:()=>{p(R),h(null)},className:"px-2 py-1 rounded-xl text-rose-600 bg-rose-50 hover:bg-rose-100 border border-rose-200/80 shadow-2xs font-semibold flex items-center gap-1 text-xs transition-all cursor-pointer",title:"删除选中图形",children:[jsxRuntimeExports.jsx(Trash2,{size:13})," 删除"]}),$!=="student"?jsxRuntimeExports.jsx("button",{onClick:de,className:"p-1.5 rounded-xl text-slate-500 hover:text-rose-600 hover:bg-rose-50 transition-all cursor-pointer",title:"清空白板 (Clear Board)",children:jsxRuntimeExports.jsx(Eraser,{size:16})}):jsxRuntimeExports.jsx("button",{onClick:L,className:"p-1.5 rounded-xl text-slate-500 hover:text-amber-600 hover:bg-amber-50 transition-all cursor-pointer",title:"重置白板 (Reset Board)",children:jsxRuntimeExports.jsx(RotateCcw,{size:16})}),N&&jsxRuntimeExports.jsx(LoaderCircle,{size:15,className:"text-indigo-500 animate-spin ml-1"})]}),WhiteboardPageBar=({pages:s,currentPage:i,showPageDrawer:h,setShowPageDrawer:d,editingPageIdx:g,setEditingPageIdx:M,editingPageTitle:j,setEditingPageTitle:w,activeMenuPageIdx:c,setActiveMenuPageIdx:P,safeElements:R,handleSwitchPage:_,handleRenamePage:ce,handleDuplicatePage:$,handleMovePage:N,handleDeletePage:S,handleAddPage:de})=>jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsxs("div",{className:"absolute bottom-3 left-1/2 -translate-x-1/2 z-20 flex items-center gap-1.5 bg-white/95 backdrop-blur-md px-3 py-1.5 rounded-full shadow-lg border border-slate-200/80 font-sans select-none",children:[jsxRuntimeExports.jsxs("button",{onClick:()=>d(!h),className:`p-1.5 rounded-full transition-colors cursor-pointer flex items-center gap-1 text-xs font-medium ${h?"bg-indigo-100 text-indigo-700":"text-slate-600 hover:bg-slate-100"}`,title:"页面大纲与预览 (Pages Outline)",children:[jsxRuntimeExports.jsx(LayoutGrid,{size:15}),jsxRuntimeExports.jsxs("span",{className:"hidden sm:inline text-[11px] font-semibold",children:["大纲 (",s.length,")"]})]}),jsxRuntimeExports.jsx("div",{className:"h-4 w-px bg-slate-200 mx-0.5"}),jsxRuntimeExports.jsx("button",{onClick:()=>_(Math.max(0,i-1)),className:"p-1 hover:bg-slate-100 rounded-full text-slate-600 disabled:opacity-30 disabled:hover:bg-transparent transition-colors cursor-pointer",disabled:i===0,title:"上一页",children:jsxRuntimeExports.jsx(ChevronLeft,{size:16})}),jsxRuntimeExports.jsx("div",{className:"flex items-center gap-1 max-w-[500px] overflow-x-auto no-scrollbar py-0.5",children:s.map((L,p)=>{const z=p===i,C=g===p;return jsxRuntimeExports.jsxs("div",{className:"relative group flex items-center",children:[C?jsxRuntimeExports.jsx("input",{type:"text",autoFocus:!0,value:j,onChange:A=>w(A.target.value),onKeyDown:A=>{A.key==="Enter"&&ce(p,j),A.key==="Escape"&&M(null)},onBlur:()=>ce(p,j),className:"px-2 py-0.5 text-xs font-bold bg-white border border-indigo-500 rounded-full outline-none w-28 text-slate-800 shadow-2xs"}):jsxRuntimeExports.jsx("button",{onClick:()=>_(p),onDoubleClick:()=>{M(p),w(L.title)},className:`px-3 py-1 rounded-full text-xs font-bold transition-all cursor-pointer flex items-center gap-1 border ${z?"bg-indigo-600 text-white border-indigo-600 shadow-2xs":"text-slate-600 hover:bg-slate-100 hover:text-slate-900 border-transparent"}`,title:"双击重命名",children:jsxRuntimeExports.jsx("span",{className:"truncate max-w-[120px]",children:L.title})}),jsxRuntimeExports.jsx("button",{onClick:A=>{A.stopPropagation(),P(c===p?null:p)},className:`p-0.5 rounded-full hover:bg-black/10 transition-colors ml-[-4px] z-10 ${z?"text-white/80 hover:text-white":"text-slate-400 hover:text-slate-600"}`,title:"页面选项",children:jsxRuntimeExports.jsx(ChevronDown,{size:12})}),c===p&&jsxRuntimeExports.jsxs("div",{className:"absolute bottom-full mb-2 left-1/2 -translate-x-1/2 bg-white rounded-xl shadow-xl border border-slate-100 py-1 w-36 z-50 text-xs font-normal",onClick:A=>A.stopPropagation(),children:[jsxRuntimeExports.jsxs("button",{onClick:()=>{M(p),w(L.title),P(null)},className:"w-full px-3 py-1.5 text-left text-slate-700 hover:bg-indigo-50 hover:text-indigo-600 flex items-center gap-2 cursor-pointer",children:[jsxRuntimeExports.jsx(PenLine,{size:13})," 重命名"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{$(p),P(null)},className:"w-full px-3 py-1.5 text-left text-slate-700 hover:bg-indigo-50 hover:text-indigo-600 flex items-center gap-2 cursor-pointer",children:[jsxRuntimeExports.jsx(Copy,{size:13})," 复制页面"]}),p>0&&jsxRuntimeExports.jsxs("button",{onClick:()=>{N(p,"left"),P(null)},className:"w-full px-3 py-1.5 text-left text-slate-700 hover:bg-indigo-50 hover:text-indigo-600 flex items-center gap-2 cursor-pointer",children:[jsxRuntimeExports.jsx(ChevronLeft,{size:13})," 向左移动"]}),p<s.length-1&&jsxRuntimeExports.jsxs("button",{onClick:()=>{N(p,"right"),P(null)},className:"w-full px-3 py-1.5 text-left text-slate-700 hover:bg-indigo-50 hover:text-indigo-600 flex items-center gap-2 cursor-pointer",children:[jsxRuntimeExports.jsx(ChevronRight,{size:13})," 向右移动"]}),jsxRuntimeExports.jsx("div",{className:"my-1 border-t border-slate-100"}),jsxRuntimeExports.jsxs("button",{onClick:()=>{S(p),P(null)},className:"w-full px-3 py-1.5 text-left text-red-600 hover:bg-red-50 flex items-center gap-2 cursor-pointer disabled:opacity-30",disabled:s.length<=1,children:[jsxRuntimeExports.jsx(Trash2,{size:13})," 删除页面"]})]})]},L.id||p)})}),jsxRuntimeExports.jsx("button",{onClick:()=>de(),className:"p-1 hover:bg-indigo-50 hover:text-indigo-600 text-slate-400 rounded-full transition-colors cursor-pointer ml-0.5",title:"新建白板页面",children:jsxRuntimeExports.jsx(Plus,{size:16})}),jsxRuntimeExports.jsx("button",{onClick:()=>_(Math.min(s.length-1,i+1)),className:"p-1 hover:bg-slate-100 rounded-full text-slate-600 disabled:opacity-30 disabled:hover:bg-transparent transition-colors cursor-pointer",disabled:i>=s.length-1,title:"下一页",children:jsxRuntimeExports.jsx(ChevronRight,{size:16})})]}),h&&jsxRuntimeExports.jsx("div",{className:"absolute inset-0 bg-slate-900/30 backdrop-blur-xs z-30 flex flex-col justify-end pointer-events-auto font-sans",onClick:()=>d(!1),children:jsxRuntimeExports.jsxs("div",{className:"bg-white/95 backdrop-blur-xl border-t border-slate-200 rounded-t-2xl shadow-2xl p-4 max-h-[70vh] flex flex-col w-full max-w-5xl mx-auto animate-in slide-in-from-bottom duration-200",onClick:L=>L.stopPropagation(),children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between pb-3 border-b border-slate-100 shrink-0",children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx(LayoutGrid,{className:"w-5 h-5 text-indigo-600"}),jsxRuntimeExports.jsx("h3",{className:"font-bold text-slate-800 text-sm",children:"白板页面大纲与预览"}),jsxRuntimeExports.jsxs("span",{className:"px-2 py-0.5 bg-indigo-50 text-indigo-600 text-xs rounded-full font-semibold",children:["共 ",s.length," 页"]})]}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsxs("button",{onClick:()=>de(),className:"px-3 py-1.5 bg-indigo-600 hover:bg-indigo-700 text-white rounded-lg text-xs font-semibold flex items-center gap-1.5 transition-colors cursor-pointer shadow-xs",children:[jsxRuntimeExports.jsx(Plus,{size:14})," 新建页面"]}),jsxRuntimeExports.jsx("button",{onClick:()=>d(!1),className:"p-1.5 hover:bg-slate-100 rounded-full text-slate-400 hover:text-slate-600 transition-colors cursor-pointer",children:jsxRuntimeExports.jsx(X,{size:16})})]})]}),jsxRuntimeExports.jsx("div",{className:"grid grid-cols-2 sm:grid-cols-3 md:grid-cols-4 lg:grid-cols-5 gap-3 py-4 overflow-y-auto max-h-[50vh]",children:s.map((L,p)=>{const z=p===i,C=R.filter(A=>A.type!=="page_meta"&&(()=>{try{const G=JSON.parse(A.data);return(G.page??0)===p||G.pageId===L.id}catch{return p===0}})()).length;return jsxRuntimeExports.jsxs("div",{onClick:()=>{_(p),d(!1)},className:`relative flex flex-col p-3 rounded-xl border-2 transition-all cursor-pointer group bg-white ${z?"border-indigo-600 bg-indigo-50/20 shadow-md ring-2 ring-indigo-500/20":"border-slate-200/80 hover:border-indigo-300 hover:shadow-sm"}`,children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between mb-2",children:[jsxRuntimeExports.jsxs("span",{className:`text-[11px] font-extrabold px-2 py-0.5 rounded-md ${z?"bg-indigo-600 text-white":"bg-slate-100 text-slate-600"}`,children:["P",p+1]}),z&&jsxRuntimeExports.jsx("span",{className:"text-[10px] font-bold text-indigo-600 bg-indigo-50 px-1.5 py-0.5 rounded",children:"当前激活"})]}),jsxRuntimeExports.jsxs("div",{className:"h-20 bg-slate-50 border border-slate-100 rounded-lg flex flex-col items-center justify-center mb-2 overflow-hidden relative",children:[jsxRuntimeExports.jsx(FileText,{size:24,className:z?"text-indigo-400":"text-slate-300"}),jsxRuntimeExports.jsxs("span",{className:"text-[10px] text-slate-400 font-medium mt-1",children:[C," 个组件/笔画"]})]}),jsxRuntimeExports.jsx("div",{className:"font-bold text-xs text-slate-800 truncate mb-1",title:L.title,children:L.title}),jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between pt-2 border-t border-slate-100 text-slate-400 text-[11px]",onClick:A=>A.stopPropagation(),children:[jsxRuntimeExports.jsx("button",{onClick:()=>{M(p),w(L.title)},className:"hover:text-indigo-600 p-1 rounded hover:bg-slate-100 transition-colors",title:"重命名",children:jsxRuntimeExports.jsx(PenLine,{size:13})}),jsxRuntimeExports.jsx("button",{onClick:()=>$(p),className:"hover:text-indigo-600 p-1 rounded hover:bg-slate-100 transition-colors",title:"复制页面",children:jsxRuntimeExports.jsx(Copy,{size:13})}),p>0&&jsxRuntimeExports.jsx("button",{onClick:()=>N(p,"left"),className:"hover:text-indigo-600 p-1 rounded hover:bg-slate-100 transition-colors",title:"向左移",children:jsxRuntimeExports.jsx(ChevronLeft,{size:13})}),p<s.length-1&&jsxRuntimeExports.jsx("button",{onClick:()=>N(p,"right"),className:"hover:text-indigo-600 p-1 rounded hover:bg-slate-100 transition-colors",title:"向右移",children:jsxRuntimeExports.jsx(ChevronRight,{size:13})}),jsxRuntimeExports.jsx("button",{onClick:()=>S(p),className:"hover:text-red-600 p-1 rounded hover:bg-red-50 transition-colors disabled:opacity-30",disabled:s.length<=1,title:"删除页面",children:jsxRuntimeExports.jsx(Trash2,{size:13})})]})]},L.id||p)})})]})})]}),WhiteboardDialog=({dialog:s,dialogInput:i,setDialogInput:h,setDialog:d})=>s?jsxRuntimeExports.jsx("div",{className:"absolute inset-0 bg-neutral-900/40 backdrop-blur-[2px] flex items-center justify-center z-[9999] p-4 font-sans",children:jsxRuntimeExports.jsxs("div",{className:"bg-white rounded-xl shadow-2xl overflow-hidden max-w-sm w-full border border-gray-100 flex flex-col scale-100 pointer-events-auto",children:[jsxRuntimeExports.jsxs("div",{className:"px-5 py-4 border-b border-gray-150/60 bg-gray-50 flex justify-between items-center shrink-0",children:[jsxRuntimeExports.jsx("h3",{className:"font-bold text-gray-800 text-sm",children:s.title}),jsxRuntimeExports.jsx("button",{onClick:()=>d(null),className:"text-gray-400 hover:text-gray-650 transition-colors text-xl font-light cursor-pointer",children:"×"})]}),jsxRuntimeExports.jsxs("div",{className:"p-5 flex-1 min-h-0",children:[jsxRuntimeExports.jsx("p",{className:"text-xs text-gray-600 leading-relaxed whitespace-pre-wrap mb-4 font-medium",children:s.message}),s.type==="prompt"&&jsxRuntimeExports.jsx("textarea",{value:i,onChange:g=>h(g.target.value),placeholder:s.placeholder,className:"w-full h-32 p-3 border border-gray-300 rounded-lg text-xs font-mono focus:outline-none focus:ring-2 focus:ring-indigo-500 bg-gray-50 focus:bg-white transition-all resize-none font-medium",onPointerDown:g=>g.stopPropagation()})]}),jsxRuntimeExports.jsxs("div",{className:"px-5 py-3 border-t border-gray-100 bg-gray-50 flex justify-end gap-2 text-xs shrink-0",children:[s.type!=="alert"&&jsxRuntimeExports.jsx("button",{onClick:()=>d(null),className:"px-4 py-2 text-gray-500 hover:bg-gray-100 rounded-lg transition-colors font-medium border border-gray-200 cursor-pointer",children:"取消"}),jsxRuntimeExports.jsx("button",{onClick:async()=>{try{await s.onConfirm(i)}catch(g){console.error("Dialog action error:",g)}},className:"px-4 py-2 bg-indigo-600 hover:bg-indigo-700 text-white rounded-lg font-semibold transition-all shadow-sm cursor-pointer",children:"确定"})]})]})}):null,CoursewareEntrySelectorModal=({showEntrySelector:s,setShowEntrySelector:i,zipUploadInfo:h,zipCandidates:d,handlePropsUpdate:g,fetchCoursewares:M})=>!s||!h?null:jsxRuntimeExports.jsx("div",{className:"absolute inset-0 bg-neutral-900/40 backdrop-blur-[2px] flex items-center justify-center z-[9999] p-4 font-sans",children:jsxRuntimeExports.jsxs("div",{className:"bg-white rounded-xl shadow-2xl overflow-hidden max-w-sm w-full border border-gray-100 flex flex-col scale-100 pointer-events-auto",children:[jsxRuntimeExports.jsxs("div",{className:"px-5 py-4 border-b border-gray-150/60 bg-gray-50 flex justify-between items-center shrink-0",children:[jsxRuntimeExports.jsx("h3",{className:"font-bold text-gray-800 text-sm",children:"选择课件入口页面"}),jsxRuntimeExports.jsx("button",{onClick:()=>i(!1),className:"text-gray-400 hover:text-gray-650 transition-colors text-xl font-light cursor-pointer",children:"×"})]}),jsxRuntimeExports.jsxs("div",{className:"p-5 flex-1 min-h-0 space-y-3",children:[jsxRuntimeExports.jsx("p",{className:"text-xs text-gray-600 leading-relaxed font-medium",children:"ZIP压缩包中含有多个HTML文件,请选择一个作为课件入口:"}),jsxRuntimeExports.jsx("div",{className:"max-h-60 overflow-y-auto border border-gray-200 rounded-lg p-2 bg-gray-50 space-y-1",children:d.map(j=>jsxRuntimeExports.jsxs("button",{onClick:async()=>{try{const w=await fetch("/api/courseware/confirm",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({uuid:h.uuid,name:h.name,entry:j})});if(w.ok){const c=await w.json();g({coursewareUuid:c.uuid,resourceId:""}),i(!1),M()}}catch(w){console.error("Failed to confirm entry point:",w)}},className:"w-full text-left p-2 rounded hover:bg-indigo-50 hover:text-indigo-700 text-xs font-semibold font-mono truncate transition-all cursor-pointer",children:["📄 ",j]},j))})]}),jsxRuntimeExports.jsx("div",{className:"px-5 py-3 border-t border-gray-100 bg-gray-50 flex justify-end gap-2 text-xs shrink-0",children:jsxRuntimeExports.jsx("button",{onClick:()=>i(!1),className:"px-4 py-2 text-gray-500 hover:bg-gray-100 rounded-lg transition-colors font-medium border border-gray-200 cursor-pointer",children:"取消"})})]})});class FullscreenRendererRegistry{constructor(){this.renderers=new Map}register(i,h){this.renderers.set(i,h)}get(i){return this.renderers.get(i)}has(i){return this.renderers.has(i)}}const fullscreenRendererRegistry=new FullscreenRendererRegistry,FullscreenOverlay=({type:s,title:i,data:h,containerSize:d,onClose:g,lessonId:M})=>{React.useEffect(()=>{const R=_=>{_.key==="Escape"&&g()};return window.addEventListener("keydown",R),()=>window.removeEventListener("keydown",R)},[g]);const j=fullscreenRendererRegistry.get(s),[w,c]=reactExports.useState({width:window.innerWidth,height:window.innerHeight});reactExports.useEffect(()=>{const R=()=>c({width:window.innerWidth,height:window.innerHeight});return window.addEventListener("resize",R),()=>window.removeEventListener("resize",R)},[]);const P=jsxRuntimeExports.jsx("div",{className:"fixed inset-0 z-[99999] bg-black/60 flex items-center justify-center",style:{pointerEvents:"auto"},children:jsxRuntimeExports.jsxs("div",{className:"relative bg-white rounded-xl shadow-2xl overflow-hidden flex flex-col",style:{width:Math.max(400,w.width-32),height:Math.max(300,w.height-32)},children:[jsxRuntimeExports.jsxs("div",{className:"bg-indigo-50 text-indigo-700 px-4 py-2 flex justify-between items-center text-sm font-semibold border-b border-indigo-100 shrink-0",children:[jsxRuntimeExports.jsx("span",{className:"truncate",children:i}),jsxRuntimeExports.jsxs("button",{onClick:g,className:"p-1.5 hover:bg-indigo-200/50 rounded-lg text-indigo-600 hover:text-indigo-900 transition-colors cursor-pointer flex items-center gap-1 text-xs",children:[jsxRuntimeExports.jsx(Minimize2,{size:14})," 退出全屏"]})]}),jsxRuntimeExports.jsx("div",{className:"absolute top-3 right-3 z-10",children:jsxRuntimeExports.jsx("button",{onClick:g,className:"w-8 h-8 flex items-center justify-center rounded-full bg-black/20 hover:bg-black/40 text-white transition-colors cursor-pointer",title:"关闭 (ESC)",children:jsxRuntimeExports.jsx(X,{size:16})})}),jsxRuntimeExports.jsx("div",{className:"flex-1 overflow-auto p-6",children:j?jsxRuntimeExports.jsx(j,{elementType:s,data:h,onClose:g,containerSize:w,lessonId:M}):jsxRuntimeExports.jsx(DefaultFullscreenRenderer,{elementType:s,data:h,onClose:g,containerSize:w,lessonId:M})})]})});return reactDomExports.createPortal(P,document.body)},PRIORITY_FIELDS=[{field:"text",icon:"📝",label:"文本"},{field:"markdown",icon:"📄",label:"Markdown"},{field:"code",icon:"💻",label:"代码"},{field:"question",icon:"❓",label:"测验",extra:["options"]},{field:"equation",icon:"📐",label:"公式"},{field:"url",icon:"🔗",label:"链接"},{field:"src",icon:"🖼",label:"图片"},{field:"coursewareUuid",icon:"📚",label:"课件"}];function DefaultFullscreenRenderer({data:s}){const i=PRIORITY_FIELDS.find(j=>s[j.field]!==void 0&&s[j.field]!==null&&s[j.field]!=="");if(!i)return jsxRuntimeExports.jsxs("div",{className:"flex flex-col items-center justify-center h-full gap-4 text-gray-500",children:[jsxRuntimeExports.jsx(BookOpen,{size:48,className:"opacity-30"}),jsxRuntimeExports.jsx("div",{className:"text-sm font-medium",children:"自动识别渲染"}),jsxRuntimeExports.jsx("pre",{className:"text-xs text-left bg-gray-50 border rounded-lg p-4 max-w-full max-h-80 overflow-auto font-mono",children:JSON.stringify(s,null,2)})]});const{field:h,icon:d,label:g,extra:M}=i;if(h==="markdown")return jsxRuntimeExports.jsx("div",{className:"prose prose-sm max-w-none",children:jsxRuntimeExports.jsx(Markdown,{children:String(s.markdown)})});if(h==="code")return jsxRuntimeExports.jsx("textarea",{value:String(s.code),readOnly:!0,className:"w-full h-full p-4 bg-gray-900 text-green-400 font-mono text-sm rounded-xl resize-none"});if(h==="text")return jsxRuntimeExports.jsx("div",{className:"flex items-start h-full",children:jsxRuntimeExports.jsx("div",{className:"text-lg whitespace-pre-wrap leading-relaxed",children:String(s.text)})});if(h==="question"){const j=Array.isArray(s.options)?s.options:[];return jsxRuntimeExports.jsxs("div",{className:"max-w-2xl mx-auto space-y-6",children:[jsxRuntimeExports.jsx("h3",{className:"text-xl font-bold text-gray-800",children:s.question}),jsxRuntimeExports.jsx("div",{className:"flex flex-col gap-3",children:j.map((w,c)=>jsxRuntimeExports.jsxs("div",{className:"px-5 py-4 text-left bg-gray-50 border-2 border-gray-200 rounded-xl text-base",children:[jsxRuntimeExports.jsxs("span",{className:"font-bold text-indigo-600 mr-3",children:["ABCDEFGHIJKLMNOPQRSTUVWXYZ"[c],"."]}),w]},c))})]})}return h==="url"?jsxRuntimeExports.jsx("div",{className:"flex items-center justify-center h-full",children:jsxRuntimeExports.jsx("a",{href:String(s.url),target:"_blank",rel:"noopener noreferrer",className:"text-indigo-600 underline text-lg",children:String(s.url)})}):h==="src"?jsxRuntimeExports.jsx("div",{className:"flex items-center justify-center h-full",children:jsxRuntimeExports.jsx("img",{src:String(s.src),alt:"",className:"max-w-full max-h-full object-contain rounded-lg"})}):h==="coursewareUuid"?jsxRuntimeExports.jsx("iframe",{src:`/runtime/${s.coursewareUuid}/`,sandbox:"allow-scripts allow-forms allow-downloads",className:"w-full h-full rounded-xl border"}):h==="equation"?jsxRuntimeExports.jsx("div",{className:"flex items-center justify-center h-full",children:jsxRuntimeExports.jsx("div",{className:"text-2xl font-mono text-gray-800 bg-gray-50 px-8 py-4 rounded-xl border",children:String(s.equation)})}):jsxRuntimeExports.jsx("div",{className:"flex items-center justify-center h-full",children:jsxRuntimeExports.jsxs("div",{className:"text-center",children:[jsxRuntimeExports.jsx("div",{className:"text-4xl mb-2",children:d}),jsxRuntimeExports.jsx("div",{className:"text-lg font-semibold text-gray-800",children:g}),jsxRuntimeExports.jsx("pre",{className:"mt-4 text-xs text-gray-500 max-w-md overflow-auto",children:JSON.stringify(s,null,2)})]})})}class PropertyEditorRegistry{constructor(){this.editors=new Map}register(i,h){this.editors.set(i,h)}get(i){return this.editors.get(i)}has(i){return this.editors.has(i)}}const propertyEditorRegistry=new PropertyEditorRegistry;fullscreenRendererRegistry.register("quiz",({data:s})=>jsxRuntimeExports.jsxs("div",{className:"max-w-2xl mx-auto space-y-6",children:[jsxRuntimeExports.jsx("h3",{className:"text-xl font-bold text-gray-800",children:s.question}),jsxRuntimeExports.jsx("div",{className:"flex flex-col gap-3",children:(s.options||[]).map((i,h)=>jsxRuntimeExports.jsxs("button",{className:"px-5 py-4 text-left bg-gray-50 border-2 border-gray-200 rounded-xl text-base hover:bg-gray-100 transition-colors",children:[jsxRuntimeExports.jsxs("span",{className:"font-bold text-indigo-600 mr-3",children:["ABCDEFGHIJKLMNOPQRSTUVWXYZ"[h],"."]}),i]},h))}),s.submissions&&Object.keys(s.submissions).length>0&&jsxRuntimeExports.jsx("div",{className:"mt-4 p-4 bg-gray-50 rounded-xl",children:jsxRuntimeExports.jsxs("p",{className:"text-sm font-semibold text-gray-600",children:["提交统计: ",Object.keys(s.submissions).length," 人已作答"]})})]}));fullscreenRendererRegistry.register("timer",({data:s})=>jsxRuntimeExports.jsx("div",{className:"flex items-center justify-center h-full",children:jsxRuntimeExports.jsxs("div",{className:"text-center",children:[jsxRuntimeExports.jsxs("div",{className:"text-8xl font-mono font-bold text-orange-600 mb-4",children:[String(Math.floor((s.remaining??s.duration??60)/60)).padStart(2,"0"),":",String((s.remaining??s.duration??60)%60).padStart(2,"0")]}),jsxRuntimeExports.jsx("p",{className:"text-lg text-gray-500",children:s.label||"计时器"})]})}));fullscreenRendererRegistry.register("assignment",({data:s})=>jsxRuntimeExports.jsxs("div",{className:"max-w-2xl mx-auto space-y-6",children:[jsxRuntimeExports.jsx("h3",{className:"text-xl font-bold text-gray-800",children:s.title}),jsxRuntimeExports.jsx("p",{className:"text-gray-600 text-base whitespace-pre-wrap",children:s.description}),jsxRuntimeExports.jsx("button",{className:"w-full bg-orange-600 hover:bg-orange-700 text-white font-medium py-3 rounded-xl transition-colors text-base shadow-sm cursor-pointer",children:"Upload File"})]}));fullscreenRendererRegistry.register("rollcall",({data:s})=>jsxRuntimeExports.jsx("div",{className:"flex items-center justify-center h-full",children:jsxRuntimeExports.jsxs("div",{className:"text-center",children:[jsxRuntimeExports.jsx("div",{className:"text-6xl font-bold text-indigo-600 mb-4",children:s.selectedStudent||"点击点名"}),jsxRuntimeExports.jsx("p",{className:"text-lg text-gray-500",children:"随机点名"})]})}));fullscreenRendererRegistry.register("html-applet",({data:s,lessonId:i})=>s.coursewareUuid?jsxRuntimeExports.jsx("iframe",{src:`/runtime/${s.coursewareUuid}/`,sandbox:"allow-scripts allow-forms allow-downloads",className:"w-full h-full rounded-xl border"}):s.resourceId?jsxRuntimeExports.jsx("iframe",{src:`/api/resources/${s.resourceId}/`,sandbox:"allow-scripts allow-forms allow-downloads",className:"w-full h-full rounded-xl border"}):jsxRuntimeExports.jsx("iframe",{srcDoc:wrapSrcDocWithBridge(s.code||"",i),sandbox:"allow-scripts allow-forms allow-downloads",className:"w-full h-full rounded-xl border"}));const DEFAULT_WHITEBOARD_PAGES=[{id:"page-0",title:"P1 · 引入导入",order:0},{id:"page-1",title:"P2 · 核心讲解",order:1},{id:"page-2",title:"P3 · 互动练习",order:2}],InteractiveWhiteboard=reactExports.forwardRef(({lessonId:s,elements:i,onElementAdd:h,onElementUpdate:d,onElementDelete:g,onClearBoard:M,onRefresh:j,enableAutoAI:w,activeSegmentId:c,onSegmentSync:P,userRole:R="teacher",isEditMode:_=!0},ce)=>{const $=Array.isArray(i)?i:[],[N,S]=reactExports.useState("cursor"),[de,L]=reactExports.useState("#facc15"),[p,z]=reactExports.useState(0),[C,A]=reactExports.useState(!0),[G,pe]=reactExports.useState(!1),[Z,fe]=reactExports.useState(DEFAULT_WHITEBOARD_PAGES),[Ne,oe]=reactExports.useState(!1),[ee,se]=reactExports.useState(null),[Y,je]=reactExports.useState(""),[ie,be]=reactExports.useState(null);reactExports.useEffect(()=>{const t=$.find(e=>e.type==="page_meta");if(t)try{const e=JSON.parse(t.data);Array.isArray(e.pages)&&e.pages.length>0&&fe(e.pages)}catch(e){console.error("Failed to parse whiteboard page_meta:",e)}},[i]);const Ee=t=>{const e=$.find(r=>r.type==="page_meta");e&&d?d(e.id,{pages:t}):h&&h("page_meta",{pages:t}),U.current&&U.current.emit("whiteboard-update",{roomId:s,type:"page-meta-update",payload:{pages:t}})},Ie=t=>{z(t),be(null),U.current&&U.current.emit("whiteboard-update",{roomId:s,type:"page-change",payload:{page:t}})},He=t=>{const e=Z.length,r={id:`page-${Date.now()}-${e}`,title:t||`P${e+1} · 备课页面`,order:e},o=[...Z,r];fe(o),z(e),Ee(o),U.current&&U.current.emit("whiteboard-update",{roomId:s,type:"page-change",payload:{page:e}})},ze=(t,e)=>{if(!e.trim()){se(null);return}const r=Z.map((o,l)=>l===t?{...o,title:e.trim()}:o);fe(r),Ee(r),se(null),je("")},Te=t=>{const e=Z[t];if(!e)return;const r=t+1,o={id:`page-${Date.now()}-${r}`,title:`${e.title} (副本)`,order:r},l=[...Z.slice(0,r),o,...Z.slice(r).map(u=>({...u,order:u.order+1}))];fe(l),z(r),Ee(l),$.filter(u=>u.type!=="page_meta"&&(()=>{try{const b=JSON.parse(u.data);return(b.page??0)===t||b.pageId===e.id}catch{return t===0}})()).forEach(u=>{try{const b=JSON.parse(u.data);h&&h(u.type,{...b,page:r,pageId:o.id,x:(b.x??100)+20,y:(b.y??100)+20})}catch(b){console.error("Failed duplicating page element:",b)}})},Ye=t=>{if(Z.length<=1){ue({title:"无法删除",message:"至少需要保留一个白板页面!",type:"alert"});return}const e=Z[t],r=$.filter(l=>l.type!=="page_meta"&&(()=>{try{const a=JSON.parse(l.data);return(a.page??0)===t||a.pageId===e.id}catch{return t===0}})()),o=()=>{g&&r.forEach(u=>g(u.id));const l=Z.filter((u,b)=>b!==t).map((u,b)=>({...u,order:b}));fe(l);const a=Math.min(p,l.length-1);z(a),Ee(l)};r.length>0?ue({title:"确认删除白板页面",message:`页面 [${e.title}] 包含 ${r.length} 个组件,删除页面将同时清理该页面的组件,是否确定删除?`,type:"confirm",onConfirm:o}):o()},st=(t,e)=>{const r=e==="left"?t-1:t+1;if(r<0||r>=Z.length)return;const o=[...Z],l=o[t];o[t]=o[r],o[r]=l,o.forEach((a,u)=>{a.order=u}),fe(o),p===t?z(r):p===r&&z(t),Ee(o)},[q,me]=reactExports.useState(null),[f,k]=reactExports.useState(!1),I=reactExports.useRef(null),[K,ge]=reactExports.useState({width:0,height:0}),H=reactExports.useRef(null),[we,T]=reactExports.useState(!1),U=reactExports.useRef(null),[ft,rt]=reactExports.useState({}),[qt,Jt]=reactExports.useState({}),[Ut,Gt]=reactExports.useState({}),[Kt,Qt]=reactExports.useState({}),[qe,De]=reactExports.useState(null),[$e,Je]=reactExports.useState(null),ne=reactExports.useRef(null),F=reactExports.useRef(null),ke=reactExports.useRef(null),[E,nt]=reactExports.useState(null),D=t=>{R==="teacher"&&nt(t)},[Be,jt]=reactExports.useState(null),V=t=>{R==="teacher"&&jt(t)},[ot,it]=reactExports.useState(null),[Ce,Ue]=reactExports.useState(null),Oe=reactExports.useRef(null),[gt,ue]=reactExports.useState(null),[bt,at]=reactExports.useState(""),[v,he]=reactExports.useState(null),[Le,Ge]=reactExports.useState({}),[Fe,Ke]=reactExports.useState({}),[Et,wt]=reactExports.useState([]),[Zt,lt]=reactExports.useState(!1),[yt,Rt]=reactExports.useState([]),[vt,Nt]=reactExports.useState([]),[kt,Ct]=reactExports.useState(null),[Pt,xt]=reactExports.useState(!1),Qe=async()=>{try{const t=await fetch("/api/courseware");if(t.ok){const e=await t.json();Rt(e)}}catch(t){console.error("Error fetching coursewares:",t)}},Ze=async()=>{try{lt(!0);const t=await fetch("/api/resources");if(t.ok){const e=await t.json();wt(e)}}catch(t){console.error("Error fetching system resources:",t)}finally{lt(!1)}};reactExports.useEffect(()=>{if(E){const t=$.find(e=>e.id===E);if(t){t.type==="html-applet"&&(Ze(),Qe());try{he(JSON.parse(t.data))}catch{he({})}}else he(null)}else he(null)},[E,i]);const Pe=async t=>{const e=$.find(u=>u.id===E);if(!e)return;let r={};try{r=JSON.parse(e.data)}catch{}const o={...r,...t},l=e.data,a=JSON.stringify(o);if(l!==a&&(Ge(u=>{const b=u[e.id]?[...u[e.id]]:[];return b.length>=30&&b.shift(),b.push(l),{...u,[e.id]:b}}),Ke(u=>({...u,[e.id]:[]}))),d){T(!0);try{await d(e.id,o),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),j&&j()}catch(u){console.error("更新属性失败:",u)}finally{T(!1)}}},St=async()=>{if(!E)return;const t=$.find(a=>a.id===E);if(!t)return;const e=Le[E]||[];if(e.length===0)return;const r=e[e.length-1],o=e.slice(0,e.length-1),l=t.data;if(Ke(a=>{const u=a[E]?[...a[E]]:[];return u.push(l),{...a,[E]:u}}),Ge(a=>({...a,[E]:o})),d){T(!0);try{const a=JSON.parse(r);he(a),await d(E,a),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),j&&j()}catch(a){console.error("撤销修改失败:",a)}finally{T(!1)}}},zt=async()=>{if(!E)return;const t=$.find(a=>a.id===E);if(!t)return;const e=Fe[E]||[];if(e.length===0)return;const r=e[e.length-1],o=e.slice(0,e.length-1),l=t.data;if(Ge(a=>{const u=a[E]?[...a[E]]:[];return u.push(l),{...a,[E]:u}}),Ke(a=>({...a,[E]:o})),d){T(!0);try{const a=JSON.parse(r);he(a),await d(E,a),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),j&&j()}catch(a){console.error("重做修改失败:",a)}finally{T(!1)}}},Q=(t,e)=>{he(r=>r&&{...r,[t]:e})},ae=(t,e)=>{Pe({[t]:e})},Se=t=>{he(e=>e&&{...e,...t}),Pe(t)},Me=(t,e)=>{const r=parseFloat(e);isNaN(r)||Pe({[t]:r})},Dt=(t,e)=>{he(r=>{if(!r)return r;const o=[...r.options||[]];return o[t]=e,{...r,options:o}})},Mt=(t,e)=>{if(!v)return;const r=[...v.options||[]];r[t]=e,Pe({options:r})},Tt=()=>{if(!v)return;const t=v.options||[],r="ABCDEFGHIJKLMNOPQRSTUVWXYZ"[t.length]||`Option ${t.length+1}`,o=[...t,`选项 ${r}`];he(l=>l&&{...l,options:o}),Pe({options:o})},$t=t=>{if(!v)return;const e=(v.options||[]).filter((r,o)=>o!==t);he(r=>r&&{...r,options:e}),Pe({options:e})};reactExports.useEffect(()=>{const t=()=>{V(null)};return window.addEventListener("click",t),()=>window.removeEventListener("click",t)},[]);const Bt=t=>{try{const e=JSON.parse(t.data);if(t.type==="pen"&&e.points){let r=1/0,o=-1/0,l=1/0;for(let a=0;a<e.points.length;a+=2){const u=e.points[a],b=e.points[a+1];u<r&&(r=u),u>o&&(o=u),b<l&&(l=b)}return{x:(r+o)/2,y:l-36}}else if(t.type==="rectangle"||t.type==="shape"&&e.shape==="rect"){const r=e.x??0,o=e.y??0,l=e.width??0,a=e.height??0;return{x:r+l/2,y:(a<0?o+a:o)-36}}else if(t.type==="circle"||t.type==="shape"&&e.shape==="circle"){const r=e.x??0,o=e.y??0,l=e.radius??0;return{x:r,y:o-l-36}}else if(t.type==="text"){const r=e.x??0,o=e.y??0;return{x:r+40,y:o-36}}else if(e.x!==void 0&&e.y!==void 0)return{x:e.x+(e.width?e.width/2:150),y:e.y-36}}catch(e){console.error(e)}return null},ye=(t,e,r)=>{if(R!=="teacher")return;t.preventDefault();const o=r.x??0,l=r.y??0,a={id:e,currentX:o,currentY:l,startPointerX:t.clientX,startPointerY:t.clientY,data:r};ne.current=a,Je(a)},Re=t=>{},ve=async t=>{},_e=(t,e,r,o,l,a,u)=>{if(R!=="teacher")return;t.preventDefault(),t.stopPropagation();const b={id:e,corner:r,startX:t.clientX,startY:t.clientY,initialX:o,initialY:l,initialWidth:a,initialHeight:u},B={id:e,x:o,y:l,width:a,height:u};F.current=b,ke.current=B,it(b),Ue(B)},Ae=t=>{},Xe=async t=>{};reactExports.useEffect(()=>{if(!$e)return;const t=r=>{if(!ne.current)return;const o=r.clientX-ne.current.startPointerX,l=r.clientY-ne.current.startPointerY,a=ne.current.data.x??0,u=ne.current.data.y??0;ne.current.currentX=a+o,ne.current.currentY=u+l,Je({...ne.current})},e=async r=>{if(!ne.current)return;const o=ne.current.currentX,l=ne.current.currentY,a=ne.current.id,u=ne.current.data;if(ne.current=null,Je(null),d){T(!0);try{await d(a,{...u,x:o,y:l}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}catch(b){console.error("Drag end update error:",b)}finally{T(!1)}}};return window.addEventListener("pointermove",t),window.addEventListener("pointerup",e),()=>{window.removeEventListener("pointermove",t),window.removeEventListener("pointerup",e)}},[$e,d,s]),reactExports.useEffect(()=>{if(!ot||!Ce)return;const t=r=>{if(!F.current||!ke.current)return;const o=r.clientX-F.current.startX,l=r.clientY-F.current.startY;let a=F.current.initialX,u=F.current.initialY,b=F.current.initialWidth,B=F.current.initialHeight;const W=150,re=100,{corner:te}=F.current;if(te==="bottom-right")b=Math.max(W,F.current.initialWidth+o),B=Math.max(re,F.current.initialHeight+l);else if(te==="bottom-left"){const n=F.current.initialWidth-o;n>=W&&(b=n,a=F.current.initialX+o),B=Math.max(re,F.current.initialHeight+l)}else if(te==="top-right"){b=Math.max(W,F.current.initialWidth+o);const n=F.current.initialHeight-l;n>=re&&(B=n,u=F.current.initialY+l)}else if(te==="top-left"){const n=F.current.initialWidth-o;n>=W&&(b=n,a=F.current.initialX+o);const m=F.current.initialHeight-l;m>=re&&(B=m,u=F.current.initialY+l)}ke.current={id:F.current.id,x:a,y:u,width:b,height:B},Ue({...ke.current})},e=async r=>{if(!F.current||!ke.current)return;const{id:o}=F.current,{x:l,y:a,width:u,height:b}=ke.current;F.current=null,ke.current=null,it(null),Ue(null);const B=$.find(W=>W.id===o);if(B&&d)try{const W=JSON.parse(B.data);T(!0),await d(o,{...W,x:l,y:a,width:u,height:b}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}catch(W){console.error("Resize end update error:",W)}finally{T(!1)}};return window.addEventListener("pointermove",t),window.addEventListener("pointerup",e),()=>{window.removeEventListener("pointermove",t),window.removeEventListener("pointerup",e)}},[ot,Ce,i,d,s]);const le=t=>{ue({type:"confirm",title:"删除组件",message:"您确定要从白板中删除这个组件或图形吗?该操作不可撤销。",onConfirm:async()=>{T(!0);try{g?await g(t):await fetch(`/api/lessons/${s}/whiteboard/${t}`,{method:"DELETE"}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),j&&j(),D(null)}catch(e){console.error("Delete element failed:",e)}finally{T(!1),ue(null)}}})},Ot=()=>{ue({type:"confirm",title:"清空白板",message:"您确定要清空画布上的所有组件、图形和线条吗?此操作将永久清空白板且不可逆!",onConfirm:async()=>{T(!0);try{M?await M():await fetch(`/api/lessons/${s}/whiteboard`,{method:"DELETE"}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),j&&j(),D(null)}catch(t){console.error("Clear board failed:",t)}finally{T(!1),ue(null)}}})},Lt=()=>{ue({type:"confirm",title:"重置白板",message:"您确定要将白板重置为开始上课的状态吗?您在白板上做的所有临时修改都将被重置。",onConfirm:async()=>{T(!0);try{await fetch(`/api/lessons/${s}/whiteboard/reset`,{method:"POST"}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),j&&j(),D(null)}catch(t){console.error("Reset board failed:",t)}finally{T(!1),ue(null)}}})};reactExports.useEffect(()=>{const t=e=>{if((e.key==="Delete"||e.key==="Backspace")&&E){const r=e.target;r.tagName!=="INPUT"&&r.tagName!=="TEXTAREA"&&(le(E),D(null))}};return window.addEventListener("keydown",t),()=>window.removeEventListener("keydown",t)},[E]);const ct=()=>{Oe.current&&clearTimeout(Oe.current),w&&(Oe.current=setTimeout(async()=>{T(!0);try{(await fetch(`/api/lessons/${s}/ai-tutor`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({elements:$.map(e=>({type:e.type,data:JSON.parse(e.data)}))})})).ok&&(frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),j&&j())}catch(t){console.error(t)}finally{T(!1)}},6e4))};reactExports.useEffect(()=>(ct(),()=>{Oe.current&&clearTimeout(Oe.current)}),[i]),reactExports.useEffect(()=>{const t=getSocketInstance();U.current=t,t.emit("join-room",s);const e=r=>{r.type==="temp-draw"?rt(o=>({...o,[r.userId]:r.payload})):r.type==="temp-end"?rt(o=>{const l={...o};return delete l[r.userId],l}):r.type==="refresh"?j&&j():r.type==="segment-change"?P&&r.payload?.segmentId&&P(r.payload.segmentId):r.type==="page-change"?typeof r.payload?.page=="number"&&z(r.payload.page):r.type==="page-meta-update"&&Array.isArray(r.payload?.pages)&&fe(r.payload.pages)};return U.current.on("whiteboard-sync",e),()=>{U.current?.off("whiteboard-sync",e)}},[s,j,P]),reactExports.useEffect(()=>{if(!H.current)return;const t=new ResizeObserver(r=>{for(let o of r)H.current&&ge({width:H.current.offsetWidth,height:H.current.offsetHeight})});t.observe(H.current);const e=()=>{H.current&&ge({width:H.current.offsetWidth,height:H.current.offsetHeight})};return e(),window.addEventListener("resize",e),()=>{t.disconnect(),window.removeEventListener("resize",e)}},[]);const Ft=t=>{if(ct(),V(null),N==="cursor"){t.target===t.target.getStage()&&D(null);return}if(we)return;k(!0);const e=t.target.getStage().getPointerPosition();N==="pen"?me({type:"pen",points:[e.x,e.y],color:"black"}):N==="highlighter"?me({type:"highlighter",points:[e.x,e.y],color:de}):N==="rect"?me({type:"rectangle",x:e.x,y:e.y,width:0,height:0,stroke:"blue"}):N==="circle"?me({type:"circle",x:e.x,y:e.y,radius:0,stroke:"green"}):N==="text"&&me({type:"text",x:e.x,y:e.y,text:"Click to edit...",fontSize:16,color:"black"})},Wt=t=>{if(!f||!q)return;const e=t.target.getStage().getPointerPosition();if(q.type==="pen"||q.type==="highlighter")me({...q,points:q.points.concat([e.x,e.y])});else if(q.type==="rectangle")me({...q,width:e.x-q.x,height:e.y-q.y});else if(q.type==="circle"){const r=Math.sqrt(Math.pow(e.x-q.x,2)+Math.pow(e.y-q.y,2));me({...q,radius:r})}},_t=async()=>{if(!f||!q)return;k(!1);const t={...q,page:p,segmentId:c};me(null),T(!0);try{await h(t.type,t),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}finally{T(!1)}};reactExports.useEffect(()=>{!U.current||!U.current.id||(q?U.current.emit("whiteboard-update",{roomId:s,type:"temp-draw",userId:U.current.id,payload:{...q,page:p,segmentId:c}}):U.current.emit("whiteboard-update",{roomId:s,type:"temp-end",userId:U.current.id}))},[q,s,p,c]),reactExports.useEffect(()=>{c&&U.current&&U.current.emit("whiteboard-update",{roomId:s,type:"segment-change",payload:{segmentId:c}})},[c,s]);const dt=t=>{if(!t)return null;const e=t.page??0,r=Z[p];return!(t.pageId&&r?.id?t.pageId===r.id:e===p)||c&&t.segmentId&&t.segmentId!==c?null:t.type==="pen"?jsxRuntimeExports.jsx(Line,{points:t.points,stroke:t.color,strokeWidth:4,tension:.5,lineCap:"round",lineJoin:"round"}):t.type==="highlighter"?jsxRuntimeExports.jsx(Line,{points:t.points,stroke:t.color||"#facc15",strokeWidth:18,tension:.5,lineCap:"round",lineJoin:"round",opacity:.5}):t.type==="rectangle"?jsxRuntimeExports.jsx(Rect,{x:t.x,y:t.y,width:t.width,height:t.height,stroke:t.stroke}):t.type==="circle"?jsxRuntimeExports.jsx(Circle$1,{x:t.x,y:t.y,radius:t.radius,stroke:t.stroke}):t.type==="text"?jsxRuntimeExports.jsx(Text,{x:t.x,y:t.y,text:t.text,fontSize:t.fontSize,fill:t.color}):null},At=()=>dt(q?{...q,page:p,segmentId:c}:null),Xt=()=>Object.values(ft).map((t,e)=>jsxRuntimeExports.jsx(React.Fragment,{children:dt(t)},e)),It=t=>{try{const e=JSON.parse(t.data),r=$e?.id===t.id,o=Ce?.id===t.id,l=o?Ce.x:r?$e.currentX:e.x??0,a=o?Ce.y:r?$e.currentY:e.y??0,u=n=>n==="plugin"?e.width||500:n==="hello-world"?160:n==="quiz"?300:n==="rollcall"?320:n==="assignment"?310:n==="html-applet"||n==="code-sandbox"||n==="math-graph"?400:n==="presentation"?600:300,b=n=>n==="plugin"?e.height||400:n==="hello-world"?64:n==="quiz"?280:n==="rollcall"?310:n==="assignment"?250:n==="html-applet"?300:n==="code-sandbox"?320:n==="math-graph"?350:n==="presentation"?400:300,B=o?Ce.width:e.width??u(t.type),W=o?Ce.height:e.isMinimized?32:e.height??b(t.type),re=E===t.id,te=()=>re?jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx("div",{className:"absolute -inset-1 border-2 border-indigo-500 rounded-lg pointer-events-none z-50 shadow-md animate-pulse duration-1000 animate-in fade-in"}),jsxRuntimeExports.jsx("div",{className:"absolute -top-1.5 -left-1.5 w-3.5 h-3.5 bg-white border-2 border-indigo-600 rounded-full cursor-nwse-resize z-50 hover:bg-indigo-50 hover:scale-110 transition-transform shadow",onPointerDown:n=>_e(n,t.id,"top-left",l,a,B,W),onPointerMove:Ae,onPointerUp:Xe}),jsxRuntimeExports.jsx("div",{className:"absolute -top-1.5 -right-1.5 w-3.5 h-3.5 bg-white border-2 border-indigo-600 rounded-full cursor-nesw-resize z-50 hover:bg-indigo-50 hover:scale-110 transition-transform shadow",onPointerDown:n=>_e(n,t.id,"top-right",l,a,B,W),onPointerMove:Ae,onPointerUp:Xe}),jsxRuntimeExports.jsx("div",{className:"absolute -bottom-1.5 -left-1.5 w-3.5 h-3.5 bg-white border-2 border-indigo-600 rounded-full cursor-nesw-resize z-50 hover:bg-indigo-50 hover:scale-110 transition-transform shadow",onPointerDown:n=>_e(n,t.id,"bottom-left",l,a,B,W),onPointerMove:Ae,onPointerUp:Xe}),jsxRuntimeExports.jsx("div",{className:"absolute -bottom-1.5 -right-1.5 w-3.5 h-3.5 bg-white border-2 border-indigo-600 rounded-full cursor-nwse-resize z-50 hover:bg-indigo-50 hover:scale-110 transition-transform shadow",onPointerDown:n=>_e(n,t.id,"bottom-right",l,a,B,W),onPointerMove:Ae,onPointerUp:Xe})]}):null;if(t.type==="plugin"){const n=R==="teacher",m=n?e.teacherWidgetId:e.studentWidgetId,O=n?"teacher.dashboard.widget":"student.view";return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${a}px`,left:`${l}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:J=>{D(t.id),J.stopPropagation()},onContextMenu:J=>{J.preventDefault(),J.stopPropagation();const xe=H.current?.getBoundingClientRect();xe&&V({x:J.clientX-xe.left,y:J.clientY-xe.top,elementId:t.id})},className:"bg-white border border-gray-300 rounded-lg shadow-xl overflow-hidden flex flex-col font-sans text-sm relative",style:{pointerEvents:"auto",width:`${B}px`,height:`${W}px`},children:[jsxRuntimeExports.jsxs("div",{className:"bg-indigo-50 text-indigo-750 px-3 py-1.5 flex justify-between items-center text-xs font-semibold border-b border-indigo-150 cursor-move select-none shrink-0",onPointerDown:J=>ye(J,t.id,e),onPointerMove:Re,onPointerUp:ve,children:[jsxRuntimeExports.jsx("span",{children:e.title||"Plugin Component"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1",children:[jsxRuntimeExports.jsx("button",{onClick:()=>De(t.id),onPointerDown:J=>J.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-indigo-650 hover:text-indigo-900 transition-colors cursor-pointer flex items-center justify-center",title:"全屏",children:jsxRuntimeExports.jsx(Maximize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:()=>le(t.id),onPointerDown:J=>J.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-indigo-600 hover:text-red-500 transition-colors cursor-pointer flex items-center justify-center",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:11})})]})]}),!e.isMinimized&&jsxRuntimeExports.jsx("div",{className:"flex-grow bg-white overflow-auto relative min-h-0 p-2",children:jsxRuntimeExports.jsx(PluginCardRenderer,{pluginId:e.pluginId,slot:O,widgetId:m,elementId:t.id,lessonId:s})}),!e.isMinimized&&te()]})})},t.id)}if(t.type==="hello-world")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${a}px`,left:`${l}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},className:"bg-transparent",style:{pointerEvents:"auto",width:`${B}px`,height:`${W}px`},children:[jsxRuntimeExports.jsx(HelloWorldWrapper,{elementId:t.id,data:e,onPointerDown:n=>ye(n,t.id,e),onPointerMove:Re,onPointerUp:ve,onDelete:()=>le(t.id),onElementUpdate:d,lessonId:s}),te()]})})},t.id);if(t.type==="rollcall")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${a}px`,left:`${l}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=H.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"bg-transparent",style:{pointerEvents:"auto",width:`${B}px`,height:`${W}px`},children:[jsxRuntimeExports.jsx(RollCallWrapper,{elementId:t.id,data:e,onElementUpdate:d,onPointerDown:n=>ye(n,t.id,e),onPointerMove:Re,onPointerUp:ve,onDelete:()=>le(t.id)}),te()]})})},t.id);if(t.type==="quiz")return null;if(t.type==="assignment")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${a}px`,left:`${l}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=H.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"bg-white border border-gray-300 rounded-lg shadow-xl overflow-hidden flex flex-col font-sans text-sm relative select-none",style:{pointerEvents:"auto",width:`${B}px`,height:`${W}px`},children:[jsxRuntimeExports.jsxs("div",{className:"bg-orange-50 text-orange-700 px-3 py-1.5 flex justify-between items-center text-xs font-semibold border-b border-orange-100 cursor-move select-none shrink-0",onPointerDown:n=>ye(n,t.id,e),onPointerMove:Re,onPointerUp:ve,children:[jsxRuntimeExports.jsx("span",{children:"Assignment Upload Task"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1",children:[jsxRuntimeExports.jsx("button",{onClick:()=>De(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-orange-600 hover:text-orange-900 transition-colors cursor-pointer flex items-center justify-center",title:"全屏",children:jsxRuntimeExports.jsx(Maximize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:async()=>{d&&(await d(t.id,{...e,isMinimized:!e.isMinimized}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))},onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-orange-655 hover:text-orange-900 transition-colors cursor-pointer flex items-center justify-center",title:e.isMinimized?"展开组件":"收起组件",children:e.isMinimized?jsxRuntimeExports.jsx(Maximize2,{size:11}):jsxRuntimeExports.jsx(Minimize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:()=>le(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-orange-600 hover:text-red-500 transition-colors cursor-pointer flex items-center justify-center",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:11})})]})]}),!e.isMinimized&&jsxRuntimeExports.jsxs("div",{className:"p-4 text-center flex-1 overflow-y-auto flex flex-col justify-center min-h-0",children:[jsxRuntimeExports.jsx("p",{className:"font-semibold text-gray-800 mb-1 text-xs",children:e.title}),jsxRuntimeExports.jsx("p",{className:"text-xs text-gray-500 mb-3 line-clamp-3",children:e.description}),jsxRuntimeExports.jsx("button",{className:"w-full bg-orange-600 hover:bg-orange-700 text-white font-medium py-1.5 rounded transition-colors text-xs shadow-sm cursor-pointer",onClick:()=>{ue({type:"alert",title:"作业文件上传",message:`系统已经成功模拟拉起本地文件选择和上传流程!
|
|
100
|
-
已准备上传作业: ${e.title??"白板作业"}`,onConfirm:()=>ue(null)})},children:"Upload File"})]}),!e.isMinimized&&te()]})})},t.id);if(t.type==="html-applet")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${a}px`,left:`${l}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=H.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"bg-white border border-gray-300 rounded-lg shadow-xl overflow-hidden flex flex-col font-sans text-sm relative",style:{pointerEvents:"auto",width:`${B}px`,height:`${W}px`},children:[jsxRuntimeExports.jsxs("div",{className:"bg-gray-100 text-gray-700 px-3 py-1.5 flex justify-between items-center text-xs font-semibold border-b border-gray-200 cursor-move select-none shrink-0",onPointerDown:n=>ye(n,t.id,e),onPointerMove:Re,onPointerUp:ve,children:[jsxRuntimeExports.jsx("span",{children:"Interactive Courseware"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1",children:[jsxRuntimeExports.jsx("button",{onClick:()=>De(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-gray-600 hover:text-gray-900 transition-colors cursor-pointer flex items-center justify-center",title:"全屏",children:jsxRuntimeExports.jsx(Maximize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:async()=>{d&&(await d(t.id,{...e,isMinimized:!e.isMinimized}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))},onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-gray-650 hover:text-gray-900 transition-colors cursor-pointer flex items-center justify-center",title:e.isMinimized?"展开组件":"收起组件",children:e.isMinimized?jsxRuntimeExports.jsx(Maximize2,{size:11}):jsxRuntimeExports.jsx(Minimize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:()=>le(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-gray-650 hover:text-red-500 transition-colors cursor-pointer flex items-center justify-center",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:11})})]})]}),!e.isMinimized&&jsxRuntimeExports.jsx("div",{className:"flex-1 bg-white overflow-hidden relative min-h-0",children:jsxRuntimeExports.jsx("iframe",{className:"w-full h-full border-none",src:e.coursewareUuid?`/runtime/${e.coursewareUuid}/`:e.resourceId?`/api/resources/${e.resourceId}/`:void 0,srcDoc:e.coursewareUuid||e.resourceId?void 0:wrapSrcDocWithBridge(e.code,s),sandbox:"allow-scripts allow-forms allow-downloads"})}),!e.isMinimized&&te()]})})},t.id);if(t.type==="pen"){const n=E===t.id;return jsxRuntimeExports.jsx(Line,{id:t.id,points:e.points,stroke:n?"#3b82f6":e.color||"black",strokeWidth:n?6:4,tension:.5,lineCap:"round",lineJoin:"round",draggable:R==="teacher"&&N==="cursor",onClick:m=>{N==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onTap:m=>{N==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onDragEnd:async m=>{const O=m.target,J=O.x(),xe=O.y();O.x(0),O.y(0);const Ve=e.points.map((We,et)=>et%2===0?We+J:We+xe);d&&(await d(t.id,{...e,points:Ve}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))}},t.id)}if(t.type==="highlighter"){const n=E===t.id;return jsxRuntimeExports.jsx(Line,{id:t.id,points:e.points,stroke:n?"#3b82f6":e.color||"#facc15",strokeWidth:n?24:18,tension:.5,lineCap:"round",lineJoin:"round",opacity:.5,draggable:R==="teacher"&&N==="cursor",onClick:m=>{N==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onTap:m=>{N==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onDragEnd:async m=>{const O=m.target,J=O.x(),xe=O.y();O.x(0),O.y(0);const Ve=e.points.map((We,et)=>et%2===0?We+J:We+xe);d&&(await d(t.id,{...e,points:Ve}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))}},t.id)}if(t.type==="rectangle"||t.type==="shape"&&e.shape==="rect"){const n=E===t.id;return jsxRuntimeExports.jsx(Rect,{id:t.id,x:e.x,y:e.y,width:e.width,height:e.height,fill:e.fill||"transparent",stroke:n?"#3b82f6":e.stroke||"blue",strokeWidth:n?3:1,draggable:R==="teacher"&&N==="cursor",onClick:m=>{N==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onTap:m=>{N==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onDragEnd:async m=>{const O=m.target,J=O.x(),xe=O.y();O.x(0),O.y(0),d&&(await d(t.id,{...e,x:e.x+J,y:e.y+xe}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))}},t.id)}if(t.type==="circle"||t.type==="shape"&&e.shape==="circle"){const n=E===t.id;return jsxRuntimeExports.jsx(Circle$1,{id:t.id,x:e.x,y:e.y,radius:e.radius,fill:e.fill||"transparent",stroke:n?"#3b82f6":e.stroke||"green",strokeWidth:n?3:1,draggable:R==="teacher"&&N==="cursor",onClick:m=>{N==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onTap:m=>{N==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onDragEnd:async m=>{const O=m.target,J=O.x(),xe=O.y();O.x(0),O.y(0),d&&(await d(t.id,{...e,x:e.x+J,y:e.y+xe}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))}},t.id)}if(t.type==="text"){const n=E===t.id;return jsxRuntimeExports.jsx(Text,{id:t.id,x:e.x,y:e.y,text:e.text,fontSize:e.fontSize||16,fill:n?"#3b82f6":e.color||"black",fontStyle:n?"bold":"normal",draggable:R==="teacher"&&N==="cursor",onClick:m=>{N==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onTap:m=>{N==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onDragEnd:async m=>{const O=m.target,J=O.x(),xe=O.y();O.x(0),O.y(0),d&&(await d(t.id,{...e,x:e.x+J,y:e.y+xe}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))}},t.id)}if(t.type==="code-sandbox")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${a}px`,left:`${l}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=H.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"relative rounded-lg shadow-xl",style:{pointerEvents:"auto",width:`${B}px`,height:`${W}px`},children:[jsxRuntimeExports.jsx(CodeSandboxWrapper,{elementId:t.id,data:e,onElementUpdate:d?async(n,m)=>{await d(n,m),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}:void 0,onPointerDown:n=>ye(n,t.id,e),onPointerMove:Re,onPointerUp:ve,onDelete:()=>le(t.id)}),te()]})})},t.id);if(t.type==="math-graph")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${a}px`,left:`${l}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=H.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"relative rounded-lg shadow-xl",style:{pointerEvents:"auto",width:`${B}px`,height:`${W}px`},children:[jsxRuntimeExports.jsx(MathGraphWrapper,{elementId:t.id,data:e,onElementUpdate:d?async(n,m)=>{await d(n,m),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}:void 0,onPointerDown:n=>ye(n,t.id,e),onPointerMove:Re,onPointerUp:ve,onDelete:()=>le(t.id)}),te()]})})},t.id);if(t.type==="presentation")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${a}px`,left:`${l}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=H.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"bg-white border border-gray-305 rounded-lg shadow-xl overflow-hidden flex flex-col font-sans text-sm relative select-none",style:{pointerEvents:"auto",width:`${B}px`,height:`${W}px`},children:[jsxRuntimeExports.jsxs("div",{className:"bg-purple-100 text-purple-700 px-3 py-1.5 flex justify-between items-center text-xs font-semibold border-b border-purple-200 cursor-move shrink-0",onPointerDown:n=>ye(n,t.id,e),onPointerMove:Re,onPointerUp:ve,children:[jsxRuntimeExports.jsx("span",{children:"Interactive Presentation"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1",children:[jsxRuntimeExports.jsx("button",{onClick:()=>De(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-purple-600 hover:text-purple-900 transition-colors cursor-pointer flex items-center justify-center",title:"全屏",children:jsxRuntimeExports.jsx(Maximize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:async()=>{d&&(await d(t.id,{...e,isMinimized:!e.isMinimized}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))},onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-purple-650 hover:text-purple-900 transition-colors cursor-pointer flex items-center justify-center",title:e.isMinimized?"展开组件":"收起组件",children:e.isMinimized?jsxRuntimeExports.jsx(Maximize2,{size:11}):jsxRuntimeExports.jsx(Minimize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:()=>le(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-purple-600 hover:text-red-500 transition-colors cursor-pointer flex items-center justify-center",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:11})})]})]}),!e.isMinimized&&jsxRuntimeExports.jsx("div",{className:"flex-1 min-h-0 relative bg-white",style:{pointerEvents:"auto"},children:jsxRuntimeExports.jsx(RevealPresentationWrapper,{elementId:t.id,data:e,userRole:R,onElementUpdate:d?async(n,m)=>{await d(n,m),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}:void 0})}),!e.isMinimized&&te()]})})},t.id)}catch(e){console.error(e)}return null},ut=t=>{t.preventDefault(),t.dataTransfer.dropEffect="copy",G||pe(!0)},pt=t=>{t.preventDefault(),t.dataTransfer.dropEffect="copy",pe(!0)},Ht=t=>{t.preventDefault(),t.currentTarget.contains(t.relatedTarget)||pe(!1)},mt=(t,e,r,o)=>{const l={x:r,y:o,page:p,segmentId:c};switch(t){case"code-sandbox":return{...l,code:e.code??"console.log('Hello Sandbox!');"};case"math-graph":return{...l,equation:e.equation??"Math.sin(x)"};case"presentation":return{...l,markdown:e.markdown??`# Title Slide
|
|
99
|
+
</div>`,x:100,y:150,page:f,segmentId:N}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:c},timestamp:Date.now(),correlationId:c})}finally{P(!1)}},className:"p-1.5 rounded-xl text-slate-600 hover:bg-slate-100 transition-all cursor-pointer",title:"插入交互网页课件 (Interactive Courseware)",children:jsxRuntimeExports.jsx(Globe,{size:16})}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:courseware",placement:"after"}),jsxRuntimeExports.jsx("div",{className:"w-px h-4 bg-slate-200/80 mx-0.5"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:rollcall",placement:"before"}),jsxRuntimeExports.jsx("button",{onClick:async()=>{P(!0);try{await O("rollcall",{title:"随机点名助手",x:120,y:120,page:f,segmentId:N}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:c},timestamp:Date.now(),correlationId:c})}finally{P(!1)}},className:"p-1.5 rounded-xl text-indigo-600 hover:bg-indigo-50 transition-all cursor-pointer flex items-center gap-1 text-xs font-semibold",title:"插入随机点名组件 (Roll Call)",children:jsxRuntimeExports.jsx(UserCheck,{size:15})}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:rollcall",placement:"after"}),jsxRuntimeExports.jsx("div",{className:"w-px h-4 bg-slate-200/80 mx-0.5"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"classroom.tool"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:ai-tutor",placement:"before"}),jsxRuntimeExports.jsx("button",{onClick:async()=>{P(!0);try{(await fetch(`/api/lessons/${c}/ai-tutor`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({elements:S.map(pe=>({type:pe.type,data:JSON.parse(pe.data)}))})})).ok?(frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:c},timestamp:Date.now(),correlationId:c}),_&&_()):z({type:"alert",title:"AI 辅导提示",message:"无法获取 AI 授课助手的帮助,请稍后再试。",onConfirm:()=>z(null)})}finally{P(!1)}},className:"p-1.5 rounded-xl text-purple-600 hover:bg-purple-50 transition-all cursor-pointer",title:"请求 AI 助教建议 (Ask AI Tutor)",children:jsxRuntimeExports.jsx(WandSparkles,{size:16})}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:ai-tutor",placement:"after"}),jsxRuntimeExports.jsx("div",{className:"w-px h-4 bg-slate-200/80 mx-0.5"}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:grid",placement:"before"}),jsxRuntimeExports.jsx("button",{onClick:()=>ce(G=>!G),className:`p-1.5 rounded-xl transition-all cursor-pointer ${J?"text-indigo-600 bg-indigo-50/80":"text-slate-400 hover:bg-slate-100"}`,title:J?"关闭网格背景":"开启网格背景",children:jsxRuntimeExports.jsx(Grid3x3,{size:16})}),jsxRuntimeExports.jsx(ExtensionPointRenderer,{slot:"anchor:whiteboard-toolbar:grid",placement:"after"}),k&&jsxRuntimeExports.jsxs("button",{onClick:()=>{p(k),g(null)},className:"px-2 py-1 rounded-xl text-rose-600 bg-rose-50 hover:bg-rose-100 border border-rose-200/80 shadow-2xs font-semibold flex items-center gap-1 text-xs transition-all cursor-pointer",title:"删除选中图形",children:[jsxRuntimeExports.jsx(Trash2,{size:13})," 删除"]}),T!=="student"?jsxRuntimeExports.jsx("button",{onClick:de,className:"p-1.5 rounded-xl text-slate-500 hover:text-rose-600 hover:bg-rose-50 transition-all cursor-pointer",title:"清空白板 (Clear Board)",children:jsxRuntimeExports.jsx(Eraser,{size:16})}):jsxRuntimeExports.jsx("button",{onClick:L,className:"p-1.5 rounded-xl text-slate-500 hover:text-amber-600 hover:bg-amber-50 transition-all cursor-pointer",title:"重置白板 (Reset Board)",children:jsxRuntimeExports.jsx(RotateCcw,{size:16})}),R&&jsxRuntimeExports.jsx(LoaderCircle,{size:15,className:"text-indigo-500 animate-spin ml-1"})]}),WhiteboardPageBar=({pages:s,currentPage:l,showPageDrawer:g,setShowPageDrawer:d,editingPageIdx:E,setEditingPageIdx:O,editingPageTitle:f,setEditingPageTitle:N,activeMenuPageIdx:c,setActiveMenuPageIdx:S,safeElements:k,handleSwitchPage:J,handleRenamePage:ce,handleDuplicatePage:T,handleMovePage:R,handleDeletePage:P,handleAddPage:de})=>jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsxs("div",{className:"absolute bottom-3 left-1/2 -translate-x-1/2 z-20 flex items-center gap-1.5 bg-white/95 backdrop-blur-md px-3 py-1.5 rounded-full shadow-lg border border-slate-200/80 font-sans select-none",children:[jsxRuntimeExports.jsxs("button",{onClick:()=>d(!g),className:`p-1.5 rounded-full transition-colors cursor-pointer flex items-center gap-1 text-xs font-medium ${g?"bg-indigo-100 text-indigo-700":"text-slate-600 hover:bg-slate-100"}`,title:"页面大纲与预览 (Pages Outline)",children:[jsxRuntimeExports.jsx(LayoutGrid,{size:15}),jsxRuntimeExports.jsxs("span",{className:"hidden sm:inline text-[11px] font-semibold",children:["大纲 (",s.length,")"]})]}),jsxRuntimeExports.jsx("div",{className:"h-4 w-px bg-slate-200 mx-0.5"}),jsxRuntimeExports.jsx("button",{onClick:()=>J(Math.max(0,l-1)),className:"p-1 hover:bg-slate-100 rounded-full text-slate-600 disabled:opacity-30 disabled:hover:bg-transparent transition-colors cursor-pointer",disabled:l===0,title:"上一页",children:jsxRuntimeExports.jsx(ChevronLeft,{size:16})}),jsxRuntimeExports.jsx("div",{className:"flex items-center gap-1 max-w-[500px] overflow-x-auto no-scrollbar py-0.5",children:s.map((L,p)=>{const z=p===l,C=E===p;return jsxRuntimeExports.jsxs("div",{className:"relative group flex items-center",children:[C?jsxRuntimeExports.jsx("input",{type:"text",autoFocus:!0,value:f,onChange:_=>N(_.target.value),onKeyDown:_=>{_.key==="Enter"&&ce(p,f),_.key==="Escape"&&O(null)},onBlur:()=>ce(p,f),className:"px-2 py-0.5 text-xs font-bold bg-white border border-indigo-500 rounded-full outline-none w-28 text-slate-800 shadow-2xs"}):jsxRuntimeExports.jsx("button",{onClick:()=>J(p),onDoubleClick:()=>{O(p),N(L.title)},className:`px-3 py-1 rounded-full text-xs font-bold transition-all cursor-pointer flex items-center gap-1 border ${z?"bg-indigo-600 text-white border-indigo-600 shadow-2xs":"text-slate-600 hover:bg-slate-100 hover:text-slate-900 border-transparent"}`,title:"双击重命名",children:jsxRuntimeExports.jsx("span",{className:"truncate max-w-[120px]",children:L.title})}),jsxRuntimeExports.jsx("button",{onClick:_=>{_.stopPropagation(),S(c===p?null:p)},className:`p-0.5 rounded-full hover:bg-black/10 transition-colors ml-[-4px] z-10 ${z?"text-white/80 hover:text-white":"text-slate-400 hover:text-slate-600"}`,title:"页面选项",children:jsxRuntimeExports.jsx(ChevronDown,{size:12})}),c===p&&jsxRuntimeExports.jsxs("div",{className:"absolute bottom-full mb-2 left-1/2 -translate-x-1/2 bg-white rounded-xl shadow-xl border border-slate-100 py-1 w-36 z-50 text-xs font-normal",onClick:_=>_.stopPropagation(),children:[jsxRuntimeExports.jsxs("button",{onClick:()=>{O(p),N(L.title),S(null)},className:"w-full px-3 py-1.5 text-left text-slate-700 hover:bg-indigo-50 hover:text-indigo-600 flex items-center gap-2 cursor-pointer",children:[jsxRuntimeExports.jsx(PenLine,{size:13})," 重命名"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{T(p),S(null)},className:"w-full px-3 py-1.5 text-left text-slate-700 hover:bg-indigo-50 hover:text-indigo-600 flex items-center gap-2 cursor-pointer",children:[jsxRuntimeExports.jsx(Copy,{size:13})," 复制页面"]}),p>0&&jsxRuntimeExports.jsxs("button",{onClick:()=>{R(p,"left"),S(null)},className:"w-full px-3 py-1.5 text-left text-slate-700 hover:bg-indigo-50 hover:text-indigo-600 flex items-center gap-2 cursor-pointer",children:[jsxRuntimeExports.jsx(ChevronLeft,{size:13})," 向左移动"]}),p<s.length-1&&jsxRuntimeExports.jsxs("button",{onClick:()=>{R(p,"right"),S(null)},className:"w-full px-3 py-1.5 text-left text-slate-700 hover:bg-indigo-50 hover:text-indigo-600 flex items-center gap-2 cursor-pointer",children:[jsxRuntimeExports.jsx(ChevronRight,{size:13})," 向右移动"]}),jsxRuntimeExports.jsx("div",{className:"my-1 border-t border-slate-100"}),jsxRuntimeExports.jsxs("button",{onClick:()=>{P(p),S(null)},className:"w-full px-3 py-1.5 text-left text-red-600 hover:bg-red-50 flex items-center gap-2 cursor-pointer disabled:opacity-30",disabled:s.length<=1,children:[jsxRuntimeExports.jsx(Trash2,{size:13})," 删除页面"]})]})]},L.id||p)})}),jsxRuntimeExports.jsx("button",{onClick:()=>de(),className:"p-1 hover:bg-indigo-50 hover:text-indigo-600 text-slate-400 rounded-full transition-colors cursor-pointer ml-0.5",title:"新建白板页面",children:jsxRuntimeExports.jsx(Plus,{size:16})}),jsxRuntimeExports.jsx("button",{onClick:()=>J(Math.min(s.length-1,l+1)),className:"p-1 hover:bg-slate-100 rounded-full text-slate-600 disabled:opacity-30 disabled:hover:bg-transparent transition-colors cursor-pointer",disabled:l>=s.length-1,title:"下一页",children:jsxRuntimeExports.jsx(ChevronRight,{size:16})})]}),g&&jsxRuntimeExports.jsx("div",{className:"absolute inset-0 bg-slate-900/30 backdrop-blur-xs z-30 flex flex-col justify-end pointer-events-auto font-sans",onClick:()=>d(!1),children:jsxRuntimeExports.jsxs("div",{className:"bg-white/95 backdrop-blur-xl border-t border-slate-200 rounded-t-2xl shadow-2xl p-4 max-h-[70vh] flex flex-col w-full max-w-5xl mx-auto animate-in slide-in-from-bottom duration-200",onClick:L=>L.stopPropagation(),children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between pb-3 border-b border-slate-100 shrink-0",children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx(LayoutGrid,{className:"w-5 h-5 text-indigo-600"}),jsxRuntimeExports.jsx("h3",{className:"font-bold text-slate-800 text-sm",children:"白板页面大纲与预览"}),jsxRuntimeExports.jsxs("span",{className:"px-2 py-0.5 bg-indigo-50 text-indigo-600 text-xs rounded-full font-semibold",children:["共 ",s.length," 页"]})]}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsxs("button",{onClick:()=>de(),className:"px-3 py-1.5 bg-indigo-600 hover:bg-indigo-700 text-white rounded-lg text-xs font-semibold flex items-center gap-1.5 transition-colors cursor-pointer shadow-xs",children:[jsxRuntimeExports.jsx(Plus,{size:14})," 新建页面"]}),jsxRuntimeExports.jsx("button",{onClick:()=>d(!1),className:"p-1.5 hover:bg-slate-100 rounded-full text-slate-400 hover:text-slate-600 transition-colors cursor-pointer",children:jsxRuntimeExports.jsx(X,{size:16})})]})]}),jsxRuntimeExports.jsx("div",{className:"grid grid-cols-2 sm:grid-cols-3 md:grid-cols-4 lg:grid-cols-5 gap-3 py-4 overflow-y-auto max-h-[50vh]",children:s.map((L,p)=>{const z=p===l,C=k.filter(_=>_.type!=="page_meta"&&(()=>{try{const G=JSON.parse(_.data);return(G.page??0)===p||G.pageId===L.id}catch{return p===0}})()).length;return jsxRuntimeExports.jsxs("div",{onClick:()=>{J(p),d(!1)},className:`relative flex flex-col p-3 rounded-xl border-2 transition-all cursor-pointer group bg-white ${z?"border-indigo-600 bg-indigo-50/20 shadow-md ring-2 ring-indigo-500/20":"border-slate-200/80 hover:border-indigo-300 hover:shadow-sm"}`,children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between mb-2",children:[jsxRuntimeExports.jsxs("span",{className:`text-[11px] font-extrabold px-2 py-0.5 rounded-md ${z?"bg-indigo-600 text-white":"bg-slate-100 text-slate-600"}`,children:["P",p+1]}),z&&jsxRuntimeExports.jsx("span",{className:"text-[10px] font-bold text-indigo-600 bg-indigo-50 px-1.5 py-0.5 rounded",children:"当前激活"})]}),jsxRuntimeExports.jsxs("div",{className:"h-20 bg-slate-50 border border-slate-100 rounded-lg flex flex-col items-center justify-center mb-2 overflow-hidden relative",children:[jsxRuntimeExports.jsx(FileText,{size:24,className:z?"text-indigo-400":"text-slate-300"}),jsxRuntimeExports.jsxs("span",{className:"text-[10px] text-slate-400 font-medium mt-1",children:[C," 个组件/笔画"]})]}),jsxRuntimeExports.jsx("div",{className:"font-bold text-xs text-slate-800 truncate mb-1",title:L.title,children:L.title}),jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between pt-2 border-t border-slate-100 text-slate-400 text-[11px]",onClick:_=>_.stopPropagation(),children:[jsxRuntimeExports.jsx("button",{onClick:()=>{O(p),N(L.title)},className:"hover:text-indigo-600 p-1 rounded hover:bg-slate-100 transition-colors",title:"重命名",children:jsxRuntimeExports.jsx(PenLine,{size:13})}),jsxRuntimeExports.jsx("button",{onClick:()=>T(p),className:"hover:text-indigo-600 p-1 rounded hover:bg-slate-100 transition-colors",title:"复制页面",children:jsxRuntimeExports.jsx(Copy,{size:13})}),p>0&&jsxRuntimeExports.jsx("button",{onClick:()=>R(p,"left"),className:"hover:text-indigo-600 p-1 rounded hover:bg-slate-100 transition-colors",title:"向左移",children:jsxRuntimeExports.jsx(ChevronLeft,{size:13})}),p<s.length-1&&jsxRuntimeExports.jsx("button",{onClick:()=>R(p,"right"),className:"hover:text-indigo-600 p-1 rounded hover:bg-slate-100 transition-colors",title:"向右移",children:jsxRuntimeExports.jsx(ChevronRight,{size:13})}),jsxRuntimeExports.jsx("button",{onClick:()=>P(p),className:"hover:text-red-600 p-1 rounded hover:bg-red-50 transition-colors disabled:opacity-30",disabled:s.length<=1,title:"删除页面",children:jsxRuntimeExports.jsx(Trash2,{size:13})})]})]},L.id||p)})})]})})]}),WhiteboardDialog=({dialog:s,dialogInput:l,setDialogInput:g,setDialog:d})=>s?jsxRuntimeExports.jsx("div",{className:"absolute inset-0 bg-neutral-900/40 backdrop-blur-[2px] flex items-center justify-center z-[9999] p-4 font-sans",children:jsxRuntimeExports.jsxs("div",{className:"bg-white rounded-xl shadow-2xl overflow-hidden max-w-sm w-full border border-gray-100 flex flex-col scale-100 pointer-events-auto",children:[jsxRuntimeExports.jsxs("div",{className:"px-5 py-4 border-b border-gray-150/60 bg-gray-50 flex justify-between items-center shrink-0",children:[jsxRuntimeExports.jsx("h3",{className:"font-bold text-gray-800 text-sm",children:s.title}),jsxRuntimeExports.jsx("button",{onClick:()=>d(null),className:"text-gray-400 hover:text-gray-650 transition-colors text-xl font-light cursor-pointer",children:"×"})]}),jsxRuntimeExports.jsxs("div",{className:"p-5 flex-1 min-h-0",children:[jsxRuntimeExports.jsx("p",{className:"text-xs text-gray-600 leading-relaxed whitespace-pre-wrap mb-4 font-medium",children:s.message}),s.type==="prompt"&&jsxRuntimeExports.jsx("textarea",{value:l,onChange:E=>g(E.target.value),placeholder:s.placeholder,className:"w-full h-32 p-3 border border-gray-300 rounded-lg text-xs font-mono focus:outline-none focus:ring-2 focus:ring-indigo-500 bg-gray-50 focus:bg-white transition-all resize-none font-medium",onPointerDown:E=>E.stopPropagation()})]}),jsxRuntimeExports.jsxs("div",{className:"px-5 py-3 border-t border-gray-100 bg-gray-50 flex justify-end gap-2 text-xs shrink-0",children:[s.type!=="alert"&&jsxRuntimeExports.jsx("button",{onClick:()=>d(null),className:"px-4 py-2 text-gray-500 hover:bg-gray-100 rounded-lg transition-colors font-medium border border-gray-200 cursor-pointer",children:"取消"}),jsxRuntimeExports.jsx("button",{onClick:async()=>{try{await s.onConfirm(l)}catch(E){console.error("Dialog action error:",E)}},className:"px-4 py-2 bg-indigo-600 hover:bg-indigo-700 text-white rounded-lg font-semibold transition-all shadow-sm cursor-pointer",children:"确定"})]})]})}):null,CoursewareEntrySelectorModal=({showEntrySelector:s,setShowEntrySelector:l,zipUploadInfo:g,zipCandidates:d,handlePropsUpdate:E,fetchCoursewares:O})=>!s||!g?null:jsxRuntimeExports.jsx("div",{className:"absolute inset-0 bg-neutral-900/40 backdrop-blur-[2px] flex items-center justify-center z-[9999] p-4 font-sans",children:jsxRuntimeExports.jsxs("div",{className:"bg-white rounded-xl shadow-2xl overflow-hidden max-w-sm w-full border border-gray-100 flex flex-col scale-100 pointer-events-auto",children:[jsxRuntimeExports.jsxs("div",{className:"px-5 py-4 border-b border-gray-150/60 bg-gray-50 flex justify-between items-center shrink-0",children:[jsxRuntimeExports.jsx("h3",{className:"font-bold text-gray-800 text-sm",children:"选择课件入口页面"}),jsxRuntimeExports.jsx("button",{onClick:()=>l(!1),className:"text-gray-400 hover:text-gray-650 transition-colors text-xl font-light cursor-pointer",children:"×"})]}),jsxRuntimeExports.jsxs("div",{className:"p-5 flex-1 min-h-0 space-y-3",children:[jsxRuntimeExports.jsx("p",{className:"text-xs text-gray-600 leading-relaxed font-medium",children:"ZIP压缩包中含有多个HTML文件,请选择一个作为课件入口:"}),jsxRuntimeExports.jsx("div",{className:"max-h-60 overflow-y-auto border border-gray-200 rounded-lg p-2 bg-gray-50 space-y-1",children:d.map(f=>jsxRuntimeExports.jsxs("button",{onClick:async()=>{try{const N=await fetch("/api/courseware/confirm",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({uuid:g.uuid,name:g.name,entry:f})});if(N.ok){const c=await N.json();E({coursewareUuid:c.uuid,resourceId:""}),l(!1),O()}}catch(N){console.error("Failed to confirm entry point:",N)}},className:"w-full text-left p-2 rounded hover:bg-indigo-50 hover:text-indigo-700 text-xs font-semibold font-mono truncate transition-all cursor-pointer",children:["📄 ",f]},f))})]}),jsxRuntimeExports.jsx("div",{className:"px-5 py-3 border-t border-gray-100 bg-gray-50 flex justify-end gap-2 text-xs shrink-0",children:jsxRuntimeExports.jsx("button",{onClick:()=>l(!1),className:"px-4 py-2 text-gray-500 hover:bg-gray-100 rounded-lg transition-colors font-medium border border-gray-200 cursor-pointer",children:"取消"})})]})});fullscreenRendererRegistry.register("quiz",({data:s})=>jsxRuntimeExports.jsxs("div",{className:"max-w-2xl mx-auto space-y-6",children:[jsxRuntimeExports.jsx("h3",{className:"text-xl font-bold text-gray-800",children:s.question}),jsxRuntimeExports.jsx("div",{className:"flex flex-col gap-3",children:(s.options||[]).map((l,g)=>jsxRuntimeExports.jsxs("button",{className:"px-5 py-4 text-left bg-gray-50 border-2 border-gray-200 rounded-xl text-base hover:bg-gray-100 transition-colors",children:[jsxRuntimeExports.jsxs("span",{className:"font-bold text-indigo-600 mr-3",children:["ABCDEFGHIJKLMNOPQRSTUVWXYZ"[g],"."]}),l]},g))}),s.submissions&&Object.keys(s.submissions).length>0&&jsxRuntimeExports.jsx("div",{className:"mt-4 p-4 bg-gray-50 rounded-xl",children:jsxRuntimeExports.jsxs("p",{className:"text-sm font-semibold text-gray-600",children:["提交统计: ",Object.keys(s.submissions).length," 人已作答"]})})]}));fullscreenRendererRegistry.register("timer",({data:s})=>jsxRuntimeExports.jsx("div",{className:"flex items-center justify-center h-full",children:jsxRuntimeExports.jsxs("div",{className:"text-center",children:[jsxRuntimeExports.jsxs("div",{className:"text-8xl font-mono font-bold text-orange-600 mb-4",children:[String(Math.floor((s.remaining??s.duration??60)/60)).padStart(2,"0"),":",String((s.remaining??s.duration??60)%60).padStart(2,"0")]}),jsxRuntimeExports.jsx("p",{className:"text-lg text-gray-500",children:s.label||"计时器"})]})}));fullscreenRendererRegistry.register("assignment",({data:s})=>jsxRuntimeExports.jsxs("div",{className:"max-w-2xl mx-auto space-y-6",children:[jsxRuntimeExports.jsx("h3",{className:"text-xl font-bold text-gray-800",children:s.title}),jsxRuntimeExports.jsx("p",{className:"text-gray-600 text-base whitespace-pre-wrap",children:s.description}),jsxRuntimeExports.jsx("button",{className:"w-full bg-orange-600 hover:bg-orange-700 text-white font-medium py-3 rounded-xl transition-colors text-base shadow-sm cursor-pointer",children:"Upload File"})]}));fullscreenRendererRegistry.register("rollcall",({data:s})=>jsxRuntimeExports.jsx("div",{className:"flex items-center justify-center h-full",children:jsxRuntimeExports.jsxs("div",{className:"text-center",children:[jsxRuntimeExports.jsx("div",{className:"text-6xl font-bold text-indigo-600 mb-4",children:s.selectedStudent||"点击点名"}),jsxRuntimeExports.jsx("p",{className:"text-lg text-gray-500",children:"随机点名"})]})}));fullscreenRendererRegistry.register("html-applet",({data:s,lessonId:l})=>s.coursewareUuid?jsxRuntimeExports.jsx("iframe",{src:`/runtime/${s.coursewareUuid}/`,sandbox:"allow-scripts allow-forms allow-downloads",className:"w-full h-full rounded-xl border"}):s.resourceId?jsxRuntimeExports.jsx("iframe",{src:`/api/resources/${s.resourceId}/`,sandbox:"allow-scripts allow-forms allow-downloads",className:"w-full h-full rounded-xl border"}):jsxRuntimeExports.jsx("iframe",{srcDoc:wrapSrcDocWithBridge(s.code||"",l),sandbox:"allow-scripts allow-forms allow-downloads",className:"w-full h-full rounded-xl border"}));const DEFAULT_WHITEBOARD_PAGES=[{id:"page-0",title:"P1 · 引入导入",order:0},{id:"page-1",title:"P2 · 核心讲解",order:1},{id:"page-2",title:"P3 · 互动练习",order:2}],InteractiveWhiteboard=reactExports.forwardRef(({lessonId:s,elements:l,onElementAdd:g,onElementUpdate:d,onElementDelete:E,onClearBoard:O,onRefresh:f,enableAutoAI:N,activeSegmentId:c,onSegmentSync:S,userRole:k="teacher",isEditMode:J=!0},ce)=>{const T=Array.isArray(l)?l:[],[R,P]=reactExports.useState("cursor"),[de,L]=reactExports.useState("#facc15"),[p,z]=reactExports.useState(0),[C,_]=reactExports.useState(!0),[G,pe]=reactExports.useState(!1),[Z,fe]=reactExports.useState(DEFAULT_WHITEBOARD_PAGES),[Ne,oe]=reactExports.useState(!1),[ee,se]=reactExports.useState(null),[H,je]=reactExports.useState(""),[ie,be]=reactExports.useState(null);reactExports.useEffect(()=>{const t=T.find(e=>e.type==="page_meta");if(t)try{const e=JSON.parse(t.data);Array.isArray(e.pages)&&e.pages.length>0&&fe(e.pages)}catch(e){console.error("Failed to parse whiteboard page_meta:",e)}},[l]);const Ee=t=>{const e=T.find(r=>r.type==="page_meta");e&&d?d(e.id,{pages:t}):g&&g("page_meta",{pages:t}),U.current&&U.current.emit("whiteboard-update",{roomId:s,type:"page-meta-update",payload:{pages:t}})},Ie=t=>{z(t),be(null),U.current&&U.current.emit("whiteboard-update",{roomId:s,type:"page-change",payload:{page:t}})},He=t=>{const e=Z.length,r={id:`page-${Date.now()}-${e}`,title:t||`P${e+1} · 备课页面`,order:e},o=[...Z,r];fe(o),z(e),Ee(o),U.current&&U.current.emit("whiteboard-update",{roomId:s,type:"page-change",payload:{page:e}})},ze=(t,e)=>{if(!e.trim()){se(null);return}const r=Z.map((o,a)=>a===t?{...o,title:e.trim()}:o);fe(r),Ee(r),se(null),je("")},Te=t=>{const e=Z[t];if(!e)return;const r=t+1,o={id:`page-${Date.now()}-${r}`,title:`${e.title} (副本)`,order:r},a=[...Z.slice(0,r),o,...Z.slice(r).map(u=>({...u,order:u.order+1}))];fe(a),z(r),Ee(a),T.filter(u=>u.type!=="page_meta"&&(()=>{try{const j=JSON.parse(u.data);return(j.page??0)===t||j.pageId===e.id}catch{return t===0}})()).forEach(u=>{try{const j=JSON.parse(u.data);g&&g(u.type,{...j,page:r,pageId:o.id,x:(j.x??100)+20,y:(j.y??100)+20})}catch(j){console.error("Failed duplicating page element:",j)}})},Ye=t=>{if(Z.length<=1){ue({title:"无法删除",message:"至少需要保留一个白板页面!",type:"alert"});return}const e=Z[t],r=T.filter(a=>a.type!=="page_meta"&&(()=>{try{const i=JSON.parse(a.data);return(i.page??0)===t||i.pageId===e.id}catch{return t===0}})()),o=()=>{E&&r.forEach(u=>E(u.id));const a=Z.filter((u,j)=>j!==t).map((u,j)=>({...u,order:j}));fe(a);const i=Math.min(p,a.length-1);z(i),Ee(a)};r.length>0?ue({title:"确认删除白板页面",message:`页面 [${e.title}] 包含 ${r.length} 个组件,删除页面将同时清理该页面的组件,是否确定删除?`,type:"confirm",onConfirm:o}):o()},st=(t,e)=>{const r=e==="left"?t-1:t+1;if(r<0||r>=Z.length)return;const o=[...Z],a=o[t];o[t]=o[r],o[r]=a,o.forEach((i,u)=>{i.order=u}),fe(o),p===t?z(r):p===r&&z(t),Ee(o)},[Y,me]=reactExports.useState(null),[h,v]=reactExports.useState(!1),A=reactExports.useRef(null),[K,ge]=reactExports.useState({width:0,height:0}),I=reactExports.useRef(null),[ye,M]=reactExports.useState(!1),U=reactExports.useRef(null),[ft,rt]=reactExports.useState({}),[Jt,qt]=reactExports.useState({}),[Ut,Gt]=reactExports.useState({}),[Kt,Qt]=reactExports.useState({}),[Je,De]=reactExports.useState(null),[$e,qe]=reactExports.useState(null),ne=reactExports.useRef(null),F=reactExports.useRef(null),ke=reactExports.useRef(null),[b,nt]=reactExports.useState(null),D=t=>{k==="teacher"&&nt(t)},[Be,jt]=reactExports.useState(null),V=t=>{k==="teacher"&&jt(t)},[ot,it]=reactExports.useState(null),[Ce,Ue]=reactExports.useState(null),Oe=reactExports.useRef(null),[gt,ue]=reactExports.useState(null),[bt,at]=reactExports.useState(""),[w,he]=reactExports.useState(null),[Le,Ge]=reactExports.useState({}),[Fe,Ke]=reactExports.useState({}),[Et,yt]=reactExports.useState([]),[Zt,lt]=reactExports.useState(!1),[wt,Rt]=reactExports.useState([]),[vt,Nt]=reactExports.useState([]),[kt,Ct]=reactExports.useState(null),[Pt,xt]=reactExports.useState(!1),Qe=async()=>{try{const t=await fetch("/api/courseware");if(t.ok){const e=await t.json();Rt(e)}}catch(t){console.error("Error fetching coursewares:",t)}},Ze=async()=>{try{lt(!0);const t=await fetch("/api/resources");if(t.ok){const e=await t.json();yt(e)}}catch(t){console.error("Error fetching system resources:",t)}finally{lt(!1)}};reactExports.useEffect(()=>{if(b){const t=T.find(e=>e.id===b);if(t){t.type==="html-applet"&&(Ze(),Qe());try{he(JSON.parse(t.data))}catch{he({})}}else he(null)}else he(null)},[b,l]);const Pe=async t=>{const e=T.find(u=>u.id===b);if(!e)return;let r={};try{r=JSON.parse(e.data)}catch{}const o={...r,...t},a=e.data,i=JSON.stringify(o);if(a!==i&&(Ge(u=>{const j=u[e.id]?[...u[e.id]]:[];return j.length>=30&&j.shift(),j.push(a),{...u,[e.id]:j}}),Ke(u=>({...u,[e.id]:[]}))),d){M(!0);try{await d(e.id,o),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),f&&f()}catch(u){console.error("更新属性失败:",u)}finally{M(!1)}}},St=async()=>{if(!b)return;const t=T.find(i=>i.id===b);if(!t)return;const e=Le[b]||[];if(e.length===0)return;const r=e[e.length-1],o=e.slice(0,e.length-1),a=t.data;if(Ke(i=>{const u=i[b]?[...i[b]]:[];return u.push(a),{...i,[b]:u}}),Ge(i=>({...i,[b]:o})),d){M(!0);try{const i=JSON.parse(r);he(i),await d(b,i),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),f&&f()}catch(i){console.error("撤销修改失败:",i)}finally{M(!1)}}},zt=async()=>{if(!b)return;const t=T.find(i=>i.id===b);if(!t)return;const e=Fe[b]||[];if(e.length===0)return;const r=e[e.length-1],o=e.slice(0,e.length-1),a=t.data;if(Ge(i=>{const u=i[b]?[...i[b]]:[];return u.push(a),{...i,[b]:u}}),Ke(i=>({...i,[b]:o})),d){M(!0);try{const i=JSON.parse(r);he(i),await d(b,i),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),f&&f()}catch(i){console.error("重做修改失败:",i)}finally{M(!1)}}},Q=(t,e)=>{he(r=>r&&{...r,[t]:e})},ae=(t,e)=>{Pe({[t]:e})},Se=t=>{he(e=>e&&{...e,...t}),Pe(t)},Me=(t,e)=>{const r=parseFloat(e);isNaN(r)||Pe({[t]:r})},Dt=(t,e)=>{he(r=>{if(!r)return r;const o=[...r.options||[]];return o[t]=e,{...r,options:o}})},Mt=(t,e)=>{if(!w)return;const r=[...w.options||[]];r[t]=e,Pe({options:r})},Tt=()=>{if(!w)return;const t=w.options||[],r="ABCDEFGHIJKLMNOPQRSTUVWXYZ"[t.length]||`Option ${t.length+1}`,o=[...t,`选项 ${r}`];he(a=>a&&{...a,options:o}),Pe({options:o})},$t=t=>{if(!w)return;const e=(w.options||[]).filter((r,o)=>o!==t);he(r=>r&&{...r,options:e}),Pe({options:e})};reactExports.useEffect(()=>{const t=()=>{V(null)};return window.addEventListener("click",t),()=>window.removeEventListener("click",t)},[]);const Bt=t=>{try{const e=JSON.parse(t.data);if(t.type==="pen"&&e.points){let r=1/0,o=-1/0,a=1/0;for(let i=0;i<e.points.length;i+=2){const u=e.points[i],j=e.points[i+1];u<r&&(r=u),u>o&&(o=u),j<a&&(a=j)}return{x:(r+o)/2,y:a-36}}else if(t.type==="rectangle"||t.type==="shape"&&e.shape==="rect"){const r=e.x??0,o=e.y??0,a=e.width??0,i=e.height??0;return{x:r+a/2,y:(i<0?o+i:o)-36}}else if(t.type==="circle"||t.type==="shape"&&e.shape==="circle"){const r=e.x??0,o=e.y??0,a=e.radius??0;return{x:r,y:o-a-36}}else if(t.type==="text"){const r=e.x??0,o=e.y??0;return{x:r+40,y:o-36}}else if(e.x!==void 0&&e.y!==void 0)return{x:e.x+(e.width?e.width/2:150),y:e.y-36}}catch(e){console.error(e)}return null},we=(t,e,r)=>{if(k!=="teacher")return;t.preventDefault();const o=r.x??0,a=r.y??0,i={id:e,currentX:o,currentY:a,startPointerX:t.clientX,startPointerY:t.clientY,data:r};ne.current=i,qe(i)},Re=t=>{},ve=async t=>{},_e=(t,e,r,o,a,i,u)=>{if(k!=="teacher")return;t.preventDefault(),t.stopPropagation();const j={id:e,corner:r,startX:t.clientX,startY:t.clientY,initialX:o,initialY:a,initialWidth:i,initialHeight:u},$={id:e,x:o,y:a,width:i,height:u};F.current=j,ke.current=$,it(j),Ue($)},Ae=t=>{},Xe=async t=>{};reactExports.useEffect(()=>{if(!$e)return;const t=r=>{if(!ne.current)return;const o=r.clientX-ne.current.startPointerX,a=r.clientY-ne.current.startPointerY,i=ne.current.data.x??0,u=ne.current.data.y??0;ne.current.currentX=i+o,ne.current.currentY=u+a,qe({...ne.current})},e=async r=>{if(!ne.current)return;const o=ne.current.currentX,a=ne.current.currentY,i=ne.current.id,u=ne.current.data;if(ne.current=null,qe(null),d){M(!0);try{await d(i,{...u,x:o,y:a}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}catch(j){console.error("Drag end update error:",j)}finally{M(!1)}}};return window.addEventListener("pointermove",t),window.addEventListener("pointerup",e),()=>{window.removeEventListener("pointermove",t),window.removeEventListener("pointerup",e)}},[$e,d,s]),reactExports.useEffect(()=>{if(!ot||!Ce)return;const t=r=>{if(!F.current||!ke.current)return;const o=r.clientX-F.current.startX,a=r.clientY-F.current.startY;let i=F.current.initialX,u=F.current.initialY,j=F.current.initialWidth,$=F.current.initialHeight;const W=150,re=100,{corner:te}=F.current;if(te==="bottom-right")j=Math.max(W,F.current.initialWidth+o),$=Math.max(re,F.current.initialHeight+a);else if(te==="bottom-left"){const n=F.current.initialWidth-o;n>=W&&(j=n,i=F.current.initialX+o),$=Math.max(re,F.current.initialHeight+a)}else if(te==="top-right"){j=Math.max(W,F.current.initialWidth+o);const n=F.current.initialHeight-a;n>=re&&($=n,u=F.current.initialY+a)}else if(te==="top-left"){const n=F.current.initialWidth-o;n>=W&&(j=n,i=F.current.initialX+o);const m=F.current.initialHeight-a;m>=re&&($=m,u=F.current.initialY+a)}ke.current={id:F.current.id,x:i,y:u,width:j,height:$},Ue({...ke.current})},e=async r=>{if(!F.current||!ke.current)return;const{id:o}=F.current,{x:a,y:i,width:u,height:j}=ke.current;F.current=null,ke.current=null,it(null),Ue(null);const $=T.find(W=>W.id===o);if($&&d)try{const W=JSON.parse($.data);M(!0),await d(o,{...W,x:a,y:i,width:u,height:j}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}catch(W){console.error("Resize end update error:",W)}finally{M(!1)}};return window.addEventListener("pointermove",t),window.addEventListener("pointerup",e),()=>{window.removeEventListener("pointermove",t),window.removeEventListener("pointerup",e)}},[ot,Ce,l,d,s]);const le=t=>{ue({type:"confirm",title:"删除组件",message:"您确定要从白板中删除这个组件或图形吗?该操作不可撤销。",onConfirm:async()=>{M(!0);try{E?await E(t):await fetch(`/api/lessons/${s}/whiteboard/${t}`,{method:"DELETE"}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),f&&f(),D(null)}catch(e){console.error("Delete element failed:",e)}finally{M(!1),ue(null)}}})},Ot=()=>{ue({type:"confirm",title:"清空白板",message:"您确定要清空画布上的所有组件、图形和线条吗?此操作将永久清空白板且不可逆!",onConfirm:async()=>{M(!0);try{O?await O():await fetch(`/api/lessons/${s}/whiteboard`,{method:"DELETE"}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),f&&f(),D(null)}catch(t){console.error("Clear board failed:",t)}finally{M(!1),ue(null)}}})},Lt=()=>{ue({type:"confirm",title:"重置白板",message:"您确定要将白板重置为开始上课的状态吗?您在白板上做的所有临时修改都将被重置。",onConfirm:async()=>{M(!0);try{await fetch(`/api/lessons/${s}/whiteboard/reset`,{method:"POST"}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),f&&f(),D(null)}catch(t){console.error("Reset board failed:",t)}finally{M(!1),ue(null)}}})};reactExports.useEffect(()=>{const t=e=>{if((e.key==="Delete"||e.key==="Backspace")&&b){const r=e.target;r.tagName!=="INPUT"&&r.tagName!=="TEXTAREA"&&(le(b),D(null))}};return window.addEventListener("keydown",t),()=>window.removeEventListener("keydown",t)},[b]);const ct=()=>{Oe.current&&clearTimeout(Oe.current),N&&(Oe.current=setTimeout(async()=>{M(!0);try{(await fetch(`/api/lessons/${s}/ai-tutor`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({elements:T.map(e=>({type:e.type,data:JSON.parse(e.data)}))})})).ok&&(frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),f&&f())}catch(t){console.error(t)}finally{M(!1)}},6e4))};reactExports.useEffect(()=>(ct(),()=>{Oe.current&&clearTimeout(Oe.current)}),[l]),reactExports.useEffect(()=>{const t=getSocketInstance();U.current=t,t.emit("join-room",s);const e=r=>{r.type==="temp-draw"?rt(o=>({...o,[r.userId]:r.payload})):r.type==="temp-end"?rt(o=>{const a={...o};return delete a[r.userId],a}):r.type==="refresh"?f&&f():r.type==="segment-change"?S&&r.payload?.segmentId&&S(r.payload.segmentId):r.type==="page-change"?typeof r.payload?.page=="number"&&z(r.payload.page):r.type==="page-meta-update"&&Array.isArray(r.payload?.pages)&&fe(r.payload.pages)};return U.current.on("whiteboard-sync",e),()=>{U.current?.off("whiteboard-sync",e)}},[s,f,S]),reactExports.useEffect(()=>{if(!I.current)return;const t=new ResizeObserver(r=>{for(let o of r)I.current&&ge({width:I.current.offsetWidth,height:I.current.offsetHeight})});t.observe(I.current);const e=()=>{I.current&&ge({width:I.current.offsetWidth,height:I.current.offsetHeight})};return e(),window.addEventListener("resize",e),()=>{t.disconnect(),window.removeEventListener("resize",e)}},[]);const Ft=t=>{if(ct(),V(null),R==="cursor"){t.target===t.target.getStage()&&D(null);return}if(ye)return;v(!0);const e=t.target.getStage().getPointerPosition();R==="pen"?me({type:"pen",points:[e.x,e.y],color:"black"}):R==="highlighter"?me({type:"highlighter",points:[e.x,e.y],color:de}):R==="rect"?me({type:"rectangle",x:e.x,y:e.y,width:0,height:0,stroke:"blue"}):R==="circle"?me({type:"circle",x:e.x,y:e.y,radius:0,stroke:"green"}):R==="text"&&me({type:"text",x:e.x,y:e.y,text:"Click to edit...",fontSize:16,color:"black"})},Wt=t=>{if(!h||!Y)return;const e=t.target.getStage().getPointerPosition();if(Y.type==="pen"||Y.type==="highlighter")me({...Y,points:Y.points.concat([e.x,e.y])});else if(Y.type==="rectangle")me({...Y,width:e.x-Y.x,height:e.y-Y.y});else if(Y.type==="circle"){const r=Math.sqrt(Math.pow(e.x-Y.x,2)+Math.pow(e.y-Y.y,2));me({...Y,radius:r})}},_t=async()=>{if(!h||!Y)return;v(!1);const t={...Y,page:p,segmentId:c};me(null),M(!0);try{await g(t.type,t),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}finally{M(!1)}};reactExports.useEffect(()=>{!U.current||!U.current.id||(Y?U.current.emit("whiteboard-update",{roomId:s,type:"temp-draw",userId:U.current.id,payload:{...Y,page:p,segmentId:c}}):U.current.emit("whiteboard-update",{roomId:s,type:"temp-end",userId:U.current.id}))},[Y,s,p,c]),reactExports.useEffect(()=>{c&&U.current&&U.current.emit("whiteboard-update",{roomId:s,type:"segment-change",payload:{segmentId:c}})},[c,s]);const dt=t=>{if(!t)return null;const e=t.page??0,r=Z[p];return!(t.pageId&&r?.id?t.pageId===r.id:e===p)||c&&t.segmentId&&t.segmentId!==c?null:t.type==="pen"?jsxRuntimeExports.jsx(Line,{points:t.points,stroke:t.color,strokeWidth:4,tension:.5,lineCap:"round",lineJoin:"round"}):t.type==="highlighter"?jsxRuntimeExports.jsx(Line,{points:t.points,stroke:t.color||"#facc15",strokeWidth:18,tension:.5,lineCap:"round",lineJoin:"round",opacity:.5}):t.type==="rectangle"?jsxRuntimeExports.jsx(Rect,{x:t.x,y:t.y,width:t.width,height:t.height,stroke:t.stroke}):t.type==="circle"?jsxRuntimeExports.jsx(Circle$1,{x:t.x,y:t.y,radius:t.radius,stroke:t.stroke}):t.type==="text"?jsxRuntimeExports.jsx(Text,{x:t.x,y:t.y,text:t.text,fontSize:t.fontSize,fill:t.color}):null},At=()=>dt(Y?{...Y,page:p,segmentId:c}:null),Xt=()=>Object.values(ft).map((t,e)=>jsxRuntimeExports.jsx(React.Fragment,{children:dt(t)},e)),It=t=>{try{const e=JSON.parse(t.data),r=$e?.id===t.id,o=Ce?.id===t.id,a=o?Ce.x:r?$e.currentX:e.x??0,i=o?Ce.y:r?$e.currentY:e.y??0,u=n=>n==="plugin"?e.width||500:n==="hello-world"?160:n==="quiz"?300:n==="rollcall"?320:n==="assignment"?310:n==="html-applet"||n==="code-sandbox"||n==="math-graph"?400:n==="presentation"?600:300,j=n=>n==="plugin"?e.height||400:n==="hello-world"?64:n==="quiz"?280:n==="rollcall"?310:n==="assignment"?250:n==="html-applet"?300:n==="code-sandbox"?320:n==="math-graph"?350:n==="presentation"?400:300,$=o?Ce.width:e.width??u(t.type),W=o?Ce.height:e.isMinimized?32:e.height??j(t.type),re=b===t.id,te=()=>re?jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx("div",{className:"absolute -inset-1 border-2 border-indigo-500 rounded-lg pointer-events-none z-50 shadow-md animate-pulse duration-1000 animate-in fade-in"}),jsxRuntimeExports.jsx("div",{className:"absolute -top-1.5 -left-1.5 w-3.5 h-3.5 bg-white border-2 border-indigo-600 rounded-full cursor-nwse-resize z-50 hover:bg-indigo-50 hover:scale-110 transition-transform shadow",onPointerDown:n=>_e(n,t.id,"top-left",a,i,$,W),onPointerMove:Ae,onPointerUp:Xe}),jsxRuntimeExports.jsx("div",{className:"absolute -top-1.5 -right-1.5 w-3.5 h-3.5 bg-white border-2 border-indigo-600 rounded-full cursor-nesw-resize z-50 hover:bg-indigo-50 hover:scale-110 transition-transform shadow",onPointerDown:n=>_e(n,t.id,"top-right",a,i,$,W),onPointerMove:Ae,onPointerUp:Xe}),jsxRuntimeExports.jsx("div",{className:"absolute -bottom-1.5 -left-1.5 w-3.5 h-3.5 bg-white border-2 border-indigo-600 rounded-full cursor-nesw-resize z-50 hover:bg-indigo-50 hover:scale-110 transition-transform shadow",onPointerDown:n=>_e(n,t.id,"bottom-left",a,i,$,W),onPointerMove:Ae,onPointerUp:Xe}),jsxRuntimeExports.jsx("div",{className:"absolute -bottom-1.5 -right-1.5 w-3.5 h-3.5 bg-white border-2 border-indigo-600 rounded-full cursor-nwse-resize z-50 hover:bg-indigo-50 hover:scale-110 transition-transform shadow",onPointerDown:n=>_e(n,t.id,"bottom-right",a,i,$,W),onPointerMove:Ae,onPointerUp:Xe})]}):null;if(t.type==="plugin"){const n=k==="teacher",m=n?e.teacherWidgetId:e.studentWidgetId,B=n?"teacher.dashboard.widget":"student.view";return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${i}px`,left:`${a}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:q=>{D(t.id),q.stopPropagation()},onContextMenu:q=>{q.preventDefault(),q.stopPropagation();const xe=I.current?.getBoundingClientRect();xe&&V({x:q.clientX-xe.left,y:q.clientY-xe.top,elementId:t.id})},className:"bg-white border border-gray-300 rounded-lg shadow-xl overflow-hidden flex flex-col font-sans text-sm relative",style:{pointerEvents:"auto",width:`${$}px`,height:`${W}px`},children:[jsxRuntimeExports.jsxs("div",{className:"bg-indigo-50 text-indigo-750 px-3 py-1.5 flex justify-between items-center text-xs font-semibold border-b border-indigo-150 cursor-move select-none shrink-0",onPointerDown:q=>we(q,t.id,e),onPointerMove:Re,onPointerUp:ve,children:[jsxRuntimeExports.jsx("span",{children:e.title||"Plugin Component"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1",children:[jsxRuntimeExports.jsx("button",{onClick:()=>De(t.id),onPointerDown:q=>q.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-indigo-650 hover:text-indigo-900 transition-colors cursor-pointer flex items-center justify-center",title:"全屏",children:jsxRuntimeExports.jsx(Maximize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:()=>le(t.id),onPointerDown:q=>q.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-indigo-600 hover:text-red-500 transition-colors cursor-pointer flex items-center justify-center",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:11})})]})]}),!e.isMinimized&&jsxRuntimeExports.jsx("div",{className:"flex-grow bg-white overflow-auto relative min-h-0 p-2",children:jsxRuntimeExports.jsx(PluginCardRenderer,{pluginId:e.pluginId,slot:B,widgetId:m,elementId:t.id,lessonId:s})}),!e.isMinimized&&te()]})})},t.id)}if(t.type==="hello-world")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${i}px`,left:`${a}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},className:"bg-transparent",style:{pointerEvents:"auto",width:`${$}px`,height:`${W}px`},children:[jsxRuntimeExports.jsx(HelloWorldWrapper,{elementId:t.id,data:e,onPointerDown:n=>we(n,t.id,e),onPointerMove:Re,onPointerUp:ve,onDelete:()=>le(t.id),onElementUpdate:d,lessonId:s}),te()]})})},t.id);if(t.type==="rollcall")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${i}px`,left:`${a}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=I.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"bg-transparent",style:{pointerEvents:"auto",width:`${$}px`,height:`${W}px`},children:[jsxRuntimeExports.jsx(RollCallWrapper,{elementId:t.id,data:e,onElementUpdate:d,onPointerDown:n=>we(n,t.id,e),onPointerMove:Re,onPointerUp:ve,onDelete:()=>le(t.id)}),te()]})})},t.id);if(t.type==="quiz")return null;if(t.type==="assignment")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${i}px`,left:`${a}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=I.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"bg-white border border-gray-300 rounded-lg shadow-xl overflow-hidden flex flex-col font-sans text-sm relative select-none",style:{pointerEvents:"auto",width:`${$}px`,height:`${W}px`},children:[jsxRuntimeExports.jsxs("div",{className:"bg-orange-50 text-orange-700 px-3 py-1.5 flex justify-between items-center text-xs font-semibold border-b border-orange-100 cursor-move select-none shrink-0",onPointerDown:n=>we(n,t.id,e),onPointerMove:Re,onPointerUp:ve,children:[jsxRuntimeExports.jsx("span",{children:"Assignment Upload Task"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1",children:[jsxRuntimeExports.jsx("button",{onClick:()=>De(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-orange-600 hover:text-orange-900 transition-colors cursor-pointer flex items-center justify-center",title:"全屏",children:jsxRuntimeExports.jsx(Maximize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:async()=>{d&&(await d(t.id,{...e,isMinimized:!e.isMinimized}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))},onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-orange-655 hover:text-orange-900 transition-colors cursor-pointer flex items-center justify-center",title:e.isMinimized?"展开组件":"收起组件",children:e.isMinimized?jsxRuntimeExports.jsx(Maximize2,{size:11}):jsxRuntimeExports.jsx(Minimize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:()=>le(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-orange-600 hover:text-red-500 transition-colors cursor-pointer flex items-center justify-center",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:11})})]})]}),!e.isMinimized&&jsxRuntimeExports.jsxs("div",{className:"p-4 text-center flex-1 overflow-y-auto flex flex-col justify-center min-h-0",children:[jsxRuntimeExports.jsx("p",{className:"font-semibold text-gray-800 mb-1 text-xs",children:e.title}),jsxRuntimeExports.jsx("p",{className:"text-xs text-gray-500 mb-3 line-clamp-3",children:e.description}),jsxRuntimeExports.jsx("button",{className:"w-full bg-orange-600 hover:bg-orange-700 text-white font-medium py-1.5 rounded transition-colors text-xs shadow-sm cursor-pointer",onClick:()=>{ue({type:"alert",title:"作业文件上传",message:`系统已经成功模拟拉起本地文件选择和上传流程!
|
|
100
|
+
已准备上传作业: ${e.title??"白板作业"}`,onConfirm:()=>ue(null)})},children:"Upload File"})]}),!e.isMinimized&&te()]})})},t.id);if(t.type==="html-applet")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${i}px`,left:`${a}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=I.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"bg-white border border-gray-300 rounded-lg shadow-xl overflow-hidden flex flex-col font-sans text-sm relative",style:{pointerEvents:"auto",width:`${$}px`,height:`${W}px`},children:[jsxRuntimeExports.jsxs("div",{className:"bg-gray-100 text-gray-700 px-3 py-1.5 flex justify-between items-center text-xs font-semibold border-b border-gray-200 cursor-move select-none shrink-0",onPointerDown:n=>we(n,t.id,e),onPointerMove:Re,onPointerUp:ve,children:[jsxRuntimeExports.jsx("span",{children:"Interactive Courseware"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1",children:[jsxRuntimeExports.jsx("button",{onClick:()=>De(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-gray-600 hover:text-gray-900 transition-colors cursor-pointer flex items-center justify-center",title:"全屏",children:jsxRuntimeExports.jsx(Maximize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:async()=>{d&&(await d(t.id,{...e,isMinimized:!e.isMinimized}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))},onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-gray-650 hover:text-gray-900 transition-colors cursor-pointer flex items-center justify-center",title:e.isMinimized?"展开组件":"收起组件",children:e.isMinimized?jsxRuntimeExports.jsx(Maximize2,{size:11}):jsxRuntimeExports.jsx(Minimize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:()=>le(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-gray-650 hover:text-red-500 transition-colors cursor-pointer flex items-center justify-center",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:11})})]})]}),!e.isMinimized&&jsxRuntimeExports.jsx("div",{className:"flex-1 bg-white overflow-hidden relative min-h-0",children:jsxRuntimeExports.jsx("iframe",{className:"w-full h-full border-none",src:e.coursewareUuid?`/runtime/${e.coursewareUuid}/`:e.resourceId?`/api/resources/${e.resourceId}/`:void 0,srcDoc:e.coursewareUuid||e.resourceId?void 0:wrapSrcDocWithBridge(e.code,s),sandbox:"allow-scripts allow-forms allow-downloads"})}),!e.isMinimized&&te()]})})},t.id);if(t.type==="pen"){const n=b===t.id;return jsxRuntimeExports.jsx(Line,{id:t.id,points:e.points,stroke:n?"#3b82f6":e.color||"black",strokeWidth:n?6:4,tension:.5,lineCap:"round",lineJoin:"round",draggable:k==="teacher"&&R==="cursor",onClick:m=>{R==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onTap:m=>{R==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onDragEnd:async m=>{const B=m.target,q=B.x(),xe=B.y();B.x(0),B.y(0);const Ve=e.points.map((We,et)=>et%2===0?We+q:We+xe);d&&(await d(t.id,{...e,points:Ve}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))}},t.id)}if(t.type==="highlighter"){const n=b===t.id;return jsxRuntimeExports.jsx(Line,{id:t.id,points:e.points,stroke:n?"#3b82f6":e.color||"#facc15",strokeWidth:n?24:18,tension:.5,lineCap:"round",lineJoin:"round",opacity:.5,draggable:k==="teacher"&&R==="cursor",onClick:m=>{R==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onTap:m=>{R==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onDragEnd:async m=>{const B=m.target,q=B.x(),xe=B.y();B.x(0),B.y(0);const Ve=e.points.map((We,et)=>et%2===0?We+q:We+xe);d&&(await d(t.id,{...e,points:Ve}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))}},t.id)}if(t.type==="rectangle"||t.type==="shape"&&e.shape==="rect"){const n=b===t.id;return jsxRuntimeExports.jsx(Rect,{id:t.id,x:e.x,y:e.y,width:e.width,height:e.height,fill:e.fill||"transparent",stroke:n?"#3b82f6":e.stroke||"blue",strokeWidth:n?3:1,draggable:k==="teacher"&&R==="cursor",onClick:m=>{R==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onTap:m=>{R==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onDragEnd:async m=>{const B=m.target,q=B.x(),xe=B.y();B.x(0),B.y(0),d&&(await d(t.id,{...e,x:e.x+q,y:e.y+xe}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))}},t.id)}if(t.type==="circle"||t.type==="shape"&&e.shape==="circle"){const n=b===t.id;return jsxRuntimeExports.jsx(Circle$1,{id:t.id,x:e.x,y:e.y,radius:e.radius,fill:e.fill||"transparent",stroke:n?"#3b82f6":e.stroke||"green",strokeWidth:n?3:1,draggable:k==="teacher"&&R==="cursor",onClick:m=>{R==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onTap:m=>{R==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onDragEnd:async m=>{const B=m.target,q=B.x(),xe=B.y();B.x(0),B.y(0),d&&(await d(t.id,{...e,x:e.x+q,y:e.y+xe}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))}},t.id)}if(t.type==="text"){const n=b===t.id;return jsxRuntimeExports.jsx(Text,{id:t.id,x:e.x,y:e.y,text:e.text,fontSize:e.fontSize||16,fill:n?"#3b82f6":e.color||"black",fontStyle:n?"bold":"normal",draggable:k==="teacher"&&R==="cursor",onClick:m=>{R==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onTap:m=>{R==="cursor"&&(m.cancelBubble=!0,D(n?null:t.id))},onDragEnd:async m=>{const B=m.target,q=B.x(),xe=B.y();B.x(0),B.y(0),d&&(await d(t.id,{...e,x:e.x+q,y:e.y+xe}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))}},t.id)}if(t.type==="code-sandbox")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${i}px`,left:`${a}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=I.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"relative rounded-lg shadow-xl",style:{pointerEvents:"auto",width:`${$}px`,height:`${W}px`},children:[jsxRuntimeExports.jsx(CodeSandboxWrapper,{elementId:t.id,data:e,onElementUpdate:d?async(n,m)=>{await d(n,m),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}:void 0,onPointerDown:n=>we(n,t.id,e),onPointerMove:Re,onPointerUp:ve,onDelete:()=>le(t.id)}),te()]})})},t.id);if(t.type==="math-graph")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${i}px`,left:`${a}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=I.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"relative rounded-lg shadow-xl",style:{pointerEvents:"auto",width:`${$}px`,height:`${W}px`},children:[jsxRuntimeExports.jsx(MathGraphWrapper,{elementId:t.id,data:e,onElementUpdate:d?async(n,m)=>{await d(n,m),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}:void 0,onPointerDown:n=>we(n,t.id,e),onPointerMove:Re,onPointerUp:ve,onDelete:()=>le(t.id)}),te()]})})},t.id);if(t.type==="presentation")return jsxRuntimeExports.jsx(Group,{children:jsxRuntimeExports.jsx(Html,{divProps:{style:{position:"absolute",top:`${i}px`,left:`${a}px`,pointerEvents:"none",zIndex:re?20:10}},children:jsxRuntimeExports.jsxs("div",{onPointerDown:n=>{D(t.id),n.stopPropagation()},onContextMenu:n=>{n.preventDefault(),n.stopPropagation();const m=I.current?.getBoundingClientRect();m&&V({x:n.clientX-m.left,y:n.clientY-m.top,elementId:t.id})},className:"bg-white border border-gray-305 rounded-lg shadow-xl overflow-hidden flex flex-col font-sans text-sm relative select-none",style:{pointerEvents:"auto",width:`${$}px`,height:`${W}px`},children:[jsxRuntimeExports.jsxs("div",{className:"bg-purple-100 text-purple-700 px-3 py-1.5 flex justify-between items-center text-xs font-semibold border-b border-purple-200 cursor-move shrink-0",onPointerDown:n=>we(n,t.id,e),onPointerMove:Re,onPointerUp:ve,children:[jsxRuntimeExports.jsx("span",{children:"Interactive Presentation"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1",children:[jsxRuntimeExports.jsx("button",{onClick:()=>De(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-purple-600 hover:text-purple-900 transition-colors cursor-pointer flex items-center justify-center",title:"全屏",children:jsxRuntimeExports.jsx(Maximize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:async()=>{d&&(await d(t.id,{...e,isMinimized:!e.isMinimized}),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}))},onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-purple-650 hover:text-purple-900 transition-colors cursor-pointer flex items-center justify-center",title:e.isMinimized?"展开组件":"收起组件",children:e.isMinimized?jsxRuntimeExports.jsx(Maximize2,{size:11}):jsxRuntimeExports.jsx(Minimize2,{size:11})}),jsxRuntimeExports.jsx("button",{onClick:()=>le(t.id),onPointerDown:n=>n.stopPropagation(),className:"p-1 hover:bg-slate-200/50 rounded-full text-purple-600 hover:text-red-500 transition-colors cursor-pointer flex items-center justify-center",title:"删除组件",children:jsxRuntimeExports.jsx(Trash2,{size:11})})]})]}),!e.isMinimized&&jsxRuntimeExports.jsx("div",{className:"flex-1 min-h-0 relative bg-white",style:{pointerEvents:"auto"},children:jsxRuntimeExports.jsx(RevealPresentationWrapper,{elementId:t.id,data:e,userRole:k,onElementUpdate:d?async(n,m)=>{await d(n,m),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s})}:void 0})}),!e.isMinimized&&te()]})})},t.id)}catch(e){console.error(e)}return null},ut=t=>{t.preventDefault(),t.dataTransfer.dropEffect="copy",G||pe(!0)},pt=t=>{t.preventDefault(),t.dataTransfer.dropEffect="copy",pe(!0)},Ht=t=>{t.preventDefault(),t.currentTarget.contains(t.relatedTarget)||pe(!1)},mt=(t,e,r,o)=>{const a={x:r,y:o,page:p,segmentId:c};switch(t){case"code-sandbox":return{...a,code:e.code??"console.log('Hello Sandbox!');"};case"math-graph":return{...a,equation:e.equation??"Math.sin(x)"};case"presentation":return{...a,markdown:e.markdown??`# Title Slide
|
|
101
101
|
---
|
|
102
|
-
## Slide 2`,width:600,height:400,slideX:0,slideY:0};case"quiz":return{...l,question:e.question??"New Quiz",options:Array.isArray(e.options)?e.options:["A","B","C","D"]};case"html-applet":return{...l,code:e.code??""};case"assignment":return{...l,title:e.title??"New Assignment",description:e.description??""};case"hello-world":return l;case"rollcall":return{...l,allStudents:[]};default:return{...l,...e}}},Yt=async(t,e)=>{if(!H.current)return;const r=H.current.getBoundingClientRect(),o=Math.round(r.width/2),l=Math.round(r.height/2);T(!0);try{await h(t,mt(t,e,o,l)),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),j&&j()}catch(a){console.error("addElementAtCenter error",a)}finally{T(!1)}};reactExports.useImperativeHandle(ce,()=>({addElementAtCenter:Yt}));const ht=async t=>{t.preventDefault(),t.stopPropagation();try{let e=t.dataTransfer.getData("application/json");if(e||(e=t.dataTransfer.getData("text/plain")),e||(e=t.dataTransfer.getData("text")),e||(e=t.dataTransfer.getData("Text")),console.log("Whiteboard drop triggered. Payload:",e),!e)return;let r;try{r=JSON.parse(e)}catch(u){console.error("Failed to parse drop JSON payload:",u);return}if(typeof r!="object"||!r)return;if(!H.current){console.warn("containerRef.current is not loaded on drop");return}const o=H.current.getBoundingClientRect();let l=t.clientX-o.left,a=t.clientY-o.top;console.log(`Adding whiteboard element of type ${r.type} at (${l}, ${a})`),T(!0);try{await h(r.type,mt(r.type,r,l,a)),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),j&&j()}finally{T(!1)}}catch(e){console.error("Drop error",e)}};return jsxRuntimeExports.jsxs("div",{className:"flex-1 flex flex-row min-h-0 overflow-hidden bg-white",children:[jsxRuntimeExports.jsxs("div",{className:"flex-1 flex flex-col min-h-0 bg-white relative min-w-0",onDragOver:ut,onDragEnter:pt,onDrop:ht,children:[jsxRuntimeExports.jsx(WhiteboardToolbar,{tool:N,setTool:S,setSelectedShapeId:D,highlighterColor:de,setHighlighterColor:L,onElementAdd:h,currentPage:p,activeSegmentId:c,lessonId:s,safeElements:$,selectedShapeId:E,showGrid:C,setShowGrid:A,userRole:R,isSyncing:we,setIsSyncing:T,handleClearBoard:Ot,handleResetBoard:Lt,handleElementDelete:le,setDialog:ue,setDialogInput:at,onRefresh:j}),jsxRuntimeExports.jsxs("div",{ref:H,className:"flex-1 bg-slate-50/70 rounded-2xl border border-slate-200/80 relative overflow-hidden w-full mb-14 shadow-inner transition-all",style:{backgroundImage:C?"radial-gradient(#cbd5e1 1.2px, transparent 1.2px)":"none",backgroundSize:"24px 24px",backgroundColor:"#f8fafc"},onDragOver:ut,onDragEnter:pt,onDragLeave:Ht,onDrop:async t=>{pe(!1),await ht(t)},children:[G&&jsxRuntimeExports.jsxs("div",{className:"absolute inset-0 border-2 border-dashed border-indigo-500 bg-indigo-500/10 backdrop-blur-[2px] rounded-2xl flex flex-col items-center justify-center text-indigo-600 font-bold text-sm z-30 animate-in fade-in pointer-events-none",children:[jsxRuntimeExports.jsx(Plus,{size:32,className:"mb-2 text-indigo-600 animate-bounce"}),jsxRuntimeExports.jsx("span",{children:"释放鼠标将组件放入当前白板页面"})]}),$.filter(t=>{if(t.type==="page_meta")return!1;try{const e=JSON.parse(t.data),r=e.page??0,o=Z[p];return!(!(e.pageId&&o?.id?e.pageId===o.id:r===p)||c&&e.segmentId&&e.segmentId!==c)}catch{return p===0}}).length===0&&!qe&&jsxRuntimeExports.jsxs("div",{className:"absolute inset-0 flex flex-col items-center justify-center pointer-events-none select-none text-slate-400 p-6 z-0",children:[jsxRuntimeExports.jsx("div",{className:"w-16 h-16 rounded-2xl bg-indigo-50/80 border border-indigo-100/80 flex items-center justify-center mb-3 shadow-2xs",children:jsxRuntimeExports.jsx(Sparkles,{className:"w-7 h-7 text-indigo-500 animate-pulse"})}),jsxRuntimeExports.jsx("p",{className:"font-bold text-sm text-slate-700 mb-1",children:"交互式备课白板"}),jsxRuntimeExports.jsx("p",{className:"text-xs text-slate-400 max-w-sm text-center",children:"从左侧组件库拖拽组件至此处,或使用顶部工具栏插入画笔、几何图形与 AI 助教"})]}),jsxRuntimeExports.jsxs("div",{className:"absolute inset-0 w-full h-full overflow-hidden",style:{pointerEvents:G?"none":"auto"},children:[K.width>0&&K.height>0&&(qe?(()=>{const t=$.find(o=>o.id===qe);if(!t)return De(null),null;let e={};try{e=JSON.parse(t.data)}catch{}const r={quiz:"📝 随堂测验",timer:"⏱ 计时器",assignment:"📋 作业","code-sandbox":"💻 代码沙箱","html-applet":"🌐 交互课件",rollcall:"🎲 随机点名",presentation:"📽 演示文稿","math-graph":"📐 数学图形",text:"📝 文本"};return jsxRuntimeExports.jsx(FullscreenOverlay,{type:t.type,title:r[t.type]||t.type,data:e,containerSize:K,onClose:()=>De(null),lessonId:s})})():jsxRuntimeExports.jsx(Stage,{width:K.width,height:K.height,onMouseDown:Ft,onMousemove:Wt,onMouseup:_t,onContextMenu:t=>{t.evt.preventDefault();const e=H.current?.getBoundingClientRect();if(e){const r=t.evt.clientX-e.left,o=t.evt.clientY-e.top,a=t.target.id();a?(D(a),V({x:r,y:o,elementId:a})):V({x:r,y:o})}},ref:I,className:"w-full h-full cursor-crosshair",children:jsxRuntimeExports.jsxs(Layer,{children:[$.filter(t=>{if(t.type==="page_meta")return!1;try{const e=JSON.parse(t.data),r=e.page??0,o=Z[p];return!(!(e.pageId&&o?.id?e.pageId===o.id:r===p)||c&&e.segmentId&&e.segmentId!==c)}catch{return p===0}}).map(It),At(),Xt()]})})),E&&(()=>{const t=$.find(l=>l.id===E);if(!t)return null;const e=Bt(t);if(!e)return null;const r=Math.max(10,Math.min(K.width-150,e.x-60)),o=Math.max(10,Math.min(K.height-50,e.y));return jsxRuntimeExports.jsxs("div",{style:{left:`${r}px`,top:`${o}px`,pointerEvents:"auto"},className:"absolute bg-white text-gray-800 shadow-xl border border-red-200 rounded-lg py-1 px-2 flex items-center gap-1.5 z-30 animate-in fade-in slide-in-from-bottom-2 duration-150 animate-out fade-out duration-100",children:[jsxRuntimeExports.jsx("span",{className:"text-xs font-semibold px-1 text-gray-500 capitalize select-none",children:t.type}),jsxRuntimeExports.jsx("div",{className:"w-[1px] h-3 bg-gray-200"}),jsxRuntimeExports.jsxs("button",{onClick:()=>{le(E),D(null)},className:"flex items-center gap-1 text-xs text-red-600 hover:text-white hover:bg-red-600 px-2 py-0.5 rounded transition-all font-medium cursor-pointer",children:[jsxRuntimeExports.jsx(Trash2,{size:12}),"删除"]})]})})(),Be&&jsxRuntimeExports.jsx("div",{style:{left:`${Be.x}px`,top:`${Be.y}px`,pointerEvents:"auto"},className:"absolute bg-white rounded-lg shadow-2xl border border-gray-200 py-1.5 w-44 z-40 font-sans text-sm animate-in fade-in zoom-in-95 duration-100",onClick:t=>t.stopPropagation(),onContextMenu:t=>t.preventDefault(),children:Be.elementId?jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx("div",{className:"px-3 py-1 text-[11px] text-gray-500 font-bold uppercase tracking-wider select-none",children:"组件选项"}),jsxRuntimeExports.jsxs("button",{onClick:()=>{const t=Be.elementId;t&&(le(t),E===t&&D(null)),V(null)},className:"w-full px-3 py-1.5 flex items-center gap-2 text-left text-red-600 hover:bg-red-50 transition-colors text-xs font-semibold",children:[jsxRuntimeExports.jsx(Trash2,{size:14}),"删除此组件"]})]}):jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx("div",{className:"px-3 py-1 text-[11px] text-gray-400 font-bold uppercase tracking-wider select-none",children:"白板操作"}),jsxRuntimeExports.jsxs("button",{onClick:()=>{S("cursor"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${N==="cursor"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(MousePointer2,{size:14}),"选择工具 (Cursor)"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{S("pen"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${N==="pen"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(PenTool,{size:14}),"画笔工具 (Pen)"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{S("highlighter"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${N==="highlighter"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(Highlighter,{size:14}),"高亮荧光笔 (Highlighter)"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{S("rect"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${N==="rect"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(Square,{size:14}),"矩形工具 (Rectangle)"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{S("circle"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${N==="circle"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(Circle,{size:14}),"圆形工具 (Circle)"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{S("text"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${N==="text"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(Type,{size:14}),"文本工具 (Text)"]})]})})]})]}),jsxRuntimeExports.jsx(WhiteboardPageBar,{pages:Z,currentPage:p,showPageDrawer:Ne,setShowPageDrawer:oe,editingPageIdx:ee,setEditingPageIdx:se,editingPageTitle:Y,setEditingPageTitle:je,activeMenuPageIdx:ie,setActiveMenuPageIdx:be,safeElements:$,handleSwitchPage:Ie,handleRenamePage:ze,handleDuplicatePage:Te,handleMovePage:st,handleDeletePage:Ye,handleAddPage:He}),jsxRuntimeExports.jsx(WhiteboardDialog,{dialog:gt,dialogInput:bt,setDialogInput:at,setDialog:ue}),jsxRuntimeExports.jsx(CoursewareEntrySelectorModal,{showEntrySelector:Pt,setShowEntrySelector:xt,zipUploadInfo:kt,zipCandidates:vt,handlePropsUpdate:Se,fetchCoursewares:Qe})]}),_&&E&&v&&(()=>{const t=$.find(e=>e.id===E);return t?jsxRuntimeExports.jsxs("div",{className:"w-80 h-full max-h-full bg-slate-50 border-l border-slate-200 flex flex-col font-sans text-xs select-none shadow-xl shrink-0 z-20 animate-in slide-in-from-right duration-200",onPointerDown:e=>e.stopPropagation(),children:[jsxRuntimeExports.jsxs("div",{className:"px-4 py-3 border-b border-slate-200 bg-white flex justify-between items-center shrink-0",children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx(Settings,{size:15,className:"text-slate-500 animate-spin",style:{animationDuration:"6s"}}),jsxRuntimeExports.jsx("span",{className:"font-bold text-slate-800 text-sm",children:"属性编辑器"})]}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5 font-sans",children:[jsxRuntimeExports.jsxs("button",{onClick:St,disabled:(Le[E]||[]).length===0,className:`p-1 rounded-lg transition-all flex items-center justify-center gap-1 border border-transparent select-none cursor-pointer ${(Le[E]||[]).length===0?"text-slate-350 bg-transparent border-transparent opacity-40 cursor-not-allowed":"text-slate-700 bg-slate-50 hover:bg-slate-100 hover:border-slate-200 active:bg-slate-150"}`,title:"撤销属性修改",children:[jsxRuntimeExports.jsx(Undo2,{size:13}),(Le[E]||[]).length>0&&jsxRuntimeExports.jsx("span",{className:"text-[10px] font-bold text-slate-500",children:(Le[E]||[]).length})]}),jsxRuntimeExports.jsxs("button",{onClick:zt,disabled:(Fe[E]||[]).length===0,className:`p-1 rounded-lg transition-all flex items-center justify-center gap-1 border border-transparent select-none cursor-pointer ${(Fe[E]||[]).length===0?"text-slate-350 bg-transparent border-transparent opacity-40 cursor-not-allowed":"text-slate-700 bg-slate-50 hover:bg-slate-100 hover:border-slate-200 active:bg-slate-150"}`,title:"重做属性修改",children:[jsxRuntimeExports.jsx(Redo2,{size:13}),(Fe[E]||[]).length>0&&jsxRuntimeExports.jsx("span",{className:"text-[10px] font-bold text-slate-500",children:(Fe[E]||[]).length})]}),jsxRuntimeExports.jsx("div",{className:"h-4 w-px bg-slate-200 mx-0.5 shrink-0"}),jsxRuntimeExports.jsx("button",{onClick:()=>D(null),className:"text-slate-400 hover:text-slate-650 hover:bg-slate-100 p-1 rounded-full transition-all cursor-pointer",title:"关闭属性编辑器",children:jsxRuntimeExports.jsx(X,{size:15})})]})]}),jsxRuntimeExports.jsxs("div",{className:"flex-1 overflow-y-auto p-4 space-y-4",children:[jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-2",children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between",children:[jsxRuntimeExports.jsx("span",{className:"text-slate-400 text-[10px] font-bold uppercase tracking-wider",children:"组件类型"}),jsxRuntimeExports.jsx("span",{className:"px-2 py-0.5 bg-indigo-50 text-indigo-650 rounded text-[10px] font-bold uppercase tracking-wider",children:t.type})]}),jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between",children:[jsxRuntimeExports.jsx("span",{className:"text-slate-400 text-[10px] font-bold uppercase tracking-wider",children:"组件标识"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-slate-500 text-[10px] truncate max-w-[155px]",title:t.id,children:t.id})]})]}),jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5 flex items-center gap-1.5",children:"物理定位 & 尺寸"}),jsxRuntimeExports.jsxs("div",{className:"grid grid-cols-2 gap-2",children:[jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"X 坐标"}),jsxRuntimeExports.jsx("input",{type:"number",value:Math.round(v.x??0),onChange:e=>Q("x",parseFloat(e.target.value)||0),onBlur:e=>Me("x",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500"})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"Y 坐标"}),jsxRuntimeExports.jsx("input",{type:"number",value:Math.round(v.y??0),onChange:e=>Q("y",parseFloat(e.target.value)||0),onBlur:e=>Me("y",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500"})]})]}),t.type!=="pen"&&t.type!=="circle"&&jsxRuntimeExports.jsxs("div",{className:"grid grid-cols-2 gap-2 mt-2",children:[jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"宽度 (Width)"}),jsxRuntimeExports.jsx("input",{type:"number",min:"50",value:Math.round(v.width??300),onChange:e=>Q("width",parseFloat(e.target.value)||50),onBlur:e=>Me("width",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500"})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"高度 (Height)"}),jsxRuntimeExports.jsx("input",{type:"number",min:"50",value:Math.round(v.height??300),onChange:e=>Q("height",parseFloat(e.target.value)||50),onBlur:e=>Me("height",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500"})]})]}),t.type==="circle"&&jsxRuntimeExports.jsxs("div",{className:"mt-2",children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"半径 (Radius)"}),jsxRuntimeExports.jsx("input",{type:"number",min:"5",value:Math.round(v.radius??50),onChange:e=>Q("radius",parseFloat(e.target.value)||5),onBlur:e=>Me("radius",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500"})]})]}),(()=>{const e=propertyEditorRegistry.get(t.type);return e?jsxRuntimeExports.jsx(e,{elementId:t.id,elementType:t.type,data:v,updateData:Se,lessonId:s,onClose:()=>D(null)}):null})(),t.type==="quiz"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"随堂测验配置"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"测验题目 (Question)"}),jsxRuntimeExports.jsx("textarea",{value:v.question||"",onChange:e=>Q("question",e.target.value),onBlur:e=>ae("question",e.target.value),className:"w-full h-20 p-2 border border-slate-200 rounded-lg text-xs focus:outline-none focus:ring-1 focus:ring-indigo-500 resize-none font-medium leading-relaxed",placeholder:"编写问题描述..."})]}),(v.options||[]).length>0&&jsxRuntimeExports.jsxs("div",{className:"bg-amber-50 border border-amber-200 rounded-lg p-2.5",children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-amber-700 font-bold mb-1.5",children:"⚠️ 正确答案 (Correct Answer)"}),jsxRuntimeExports.jsxs("select",{value:v.correctAnswer||"",onChange:e=>{Q("correctAnswer",e.target.value),ae("correctAnswer",e.target.value)},className:`w-full px-2 py-1.5 border rounded-lg text-xs font-medium focus:outline-none focus:ring-1 focus:ring-amber-500 cursor-pointer ${v.correctAnswer?"border-green-300 bg-green-50 text-green-800":"border-amber-300 bg-white text-amber-800"}`,children:[jsxRuntimeExports.jsx("option",{value:"",children:"-- 请选择正确答案 --"}),(v.options||[]).map((e,r)=>jsxRuntimeExports.jsx("option",{value:e,children:e},r))]}),!v.correctAnswer&&jsxRuntimeExports.jsx("p",{className:"text-[9px] text-amber-600 mt-1",children:"未设置正确答案将无法自动判分"})]}),jsxRuntimeExports.jsxs("div",{className:"space-y-2",children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold",children:"选项列表 (Options)"}),jsxRuntimeExports.jsx("div",{className:"space-y-1.5 max-h-48 overflow-y-auto pr-1",children:(v.options||[]).map((e,r)=>{const l="ABCDEFGHIJKLMNOPQRSTUVWXYZ"[r]||r+1;return jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-slate-700 bg-slate-100 rounded px-1.5 py-1 text-center shrink-0 min-w-[22px]",children:l}),jsxRuntimeExports.jsx("input",{type:"text",value:e||"",onChange:a=>Dt(r,a.target.value),onBlur:a=>Mt(r,a.target.value),className:"flex-1 px-2 py-1 border border-slate-200 rounded-lg text-xs font-medium"}),jsxRuntimeExports.jsx("button",{onClick:()=>$t(r),title:"删除选项",className:"text-slate-400 hover:text-red-500 hover:bg-red-50 p-1 rounded-md shrink-0 transition-colors cursor-pointer",children:jsxRuntimeExports.jsx(Trash2,{size:13})})]},r)})}),jsxRuntimeExports.jsxs("button",{onClick:Tt,className:"w-full mt-2 py-1 bg-slate-100 hover:bg-slate-200 text-slate-600 font-bold border border-slate-200/80 rounded-lg flex items-center justify-center gap-1 hover:text-slate-700 transition-all text-[11px] cursor-pointer",children:[jsxRuntimeExports.jsx(Plus,{size:12})," 添加选项"]})]})]}),t.type==="assignment"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"作业选项配置"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"作业任务标题 (Title)"}),jsxRuntimeExports.jsx("input",{type:"text",value:v.title||"",onChange:e=>Q("title",e.target.value),onBlur:e=>ae("title",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-semibold focus:outline-none focus:ring-1 focus:ring-indigo-500",placeholder:"作业名..."})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"详细作业要求描述"}),jsxRuntimeExports.jsx("textarea",{value:v.description||"",onChange:e=>Q("description",e.target.value),onBlur:e=>ae("description",e.target.value),className:"w-full h-24 p-2 border border-slate-200 rounded-lg text-xs focus:outline-none focus:ring-1 focus:ring-indigo-500 resize-none font-medium leading-relaxed",placeholder:"请输入详细的作业指南..."})]})]}),(t.type==="code-sandbox"||t.type==="html-applet")&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsxs("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5 flex justify-between items-center",children:[jsxRuntimeExports.jsx("span",{children:"动态运行代码定制"}),t.type==="html-applet"&&jsxRuntimeExports.jsx("span",{className:"text-[10px] bg-indigo-50 text-indigo-700 px-1.5 py-0.5 rounded-full font-bold",children:"HTML Applet"})]}),t.type==="html-applet"&&jsxRuntimeExports.jsxs("div",{className:"space-y-3 border-b border-slate-100 pb-3",children:[jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-indigo-600 font-bold mb-1",children:"选择 AI 互动课件 (ZIP/HTML):"}),jsxRuntimeExports.jsxs("select",{value:v.coursewareUuid||"",onChange:e=>{const r=e.target.value;Se({coursewareUuid:r,resourceId:""})},className:"w-full text-xs p-2 bg-slate-50 border border-indigo-200 hover:border-indigo-300 rounded-lg text-slate-750 focus:outline-none focus:ring-1 focus:ring-indigo-500 transition-all font-semibold",children:[jsxRuntimeExports.jsx("option",{value:"",children:"-- 使用系统资源或自定义代码 --"}),yt.map(e=>jsxRuntimeExports.jsxs("option",{value:e.uuid,children:["📁 [互动课件] ",e.name]},e.id))]})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-500 font-bold mb-1",children:"选择已有的系统资源:"}),jsxRuntimeExports.jsxs("select",{value:v.resourceId||"",onChange:e=>{const r=e.target.value;Se({resourceId:r,coursewareUuid:""})},className:"w-full text-xs p-2 bg-slate-50 border border-slate-200 hover:border-slate-300 rounded-lg text-slate-750 focus:outline-none focus:ring-1 focus:ring-indigo-500 transition-all font-semibold",children:[jsxRuntimeExports.jsx("option",{value:"",children:"-- 使用互动课件或自定义代码 --"}),Et.map(e=>jsxRuntimeExports.jsxs("option",{value:e.id,children:["[",e.type==="folder"?"文件夹":"单HTML","] ",e.name]},e.id))]})]}),jsxRuntimeExports.jsxs("div",{className:"bg-slate-50 p-2.5 rounded-xl border border-slate-100 text-[10px] text-slate-500 space-y-2",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-slate-600 block",children:"上传资源 (会自动保存到对应库):"}),jsxRuntimeExports.jsxs("div",{className:"grid grid-cols-2 gap-2",children:[jsxRuntimeExports.jsxs("label",{className:"col-span-2 flex flex-col items-center justify-center p-2 bg-indigo-50 hover:bg-indigo-100 border border-indigo-200 hover:border-indigo-300 rounded-lg cursor-pointer text-center transition-all",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-indigo-700 text-[10px]",children:"✨ 上传 AI 互动课件 (.zip/.html)"}),jsxRuntimeExports.jsx("input",{type:"file",accept:".zip,.html,.htm",className:"hidden",onChange:async e=>{const r=e.target.files?.[0];if(!r)return;const o=new FileReader;o.onload=async l=>{const a=l.target?.result;try{const u=await fetch("/api/courseware/upload",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({name:r.name.replace(/\.[^/.]+$/,""),filename:r.name,base64Data:a})});if(u.ok){const b=await u.json();b.need_select_entry?(Nt(b.candidates),Ct({uuid:b.uuid,name:b.name}),xt(!0)):(Se({coursewareUuid:b.uuid,resourceId:""}),Qe())}else{const b=await u.json();alert("上传失败: "+(b.error||u.statusText))}}catch(u){console.error("Courseware upload failed:",u)}},o.readAsDataURL(r)}})]}),jsxRuntimeExports.jsxs("label",{className:"flex flex-col items-center justify-center p-2 bg-white hover:bg-slate-100 border border-slate-200 hover:border-slate-300 rounded-lg cursor-pointer text-center transition-all",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-slate-600 text-[10px]",children:"📄 上传系统HTML文件"}),jsxRuntimeExports.jsx("input",{type:"file",accept:".html,.htm",className:"hidden",onChange:async e=>{const r=e.target.files?.[0];if(!r)return;const o=new FileReader;o.onload=async l=>{const a=l.target?.result;try{const u=await fetch("/api/resources",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({name:r.name,type:"html",content:a})});if(u.ok){const b=await u.json();Se({resourceId:b.id,coursewareUuid:""}),Ze()}}catch(u){console.error("Upload failed:",u)}},o.readAsText(r)}})]}),jsxRuntimeExports.jsxs("label",{className:"flex flex-col items-center justify-center p-2 bg-white hover:bg-slate-100 border border-slate-200 hover:border-slate-300 rounded-lg cursor-pointer text-center transition-all",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-slate-600 text-[10px]",children:"📁 上传系统文件夹"}),jsxRuntimeExports.jsx("input",{type:"file",webkitdirectory:"",directory:"",multiple:!0,className:"hidden",onChange:async e=>{const r=e.target.files;if(!r||r.length===0)return;const o=[];let l="";for(let a=0;a<r.length;a++){const u=r[a],b=u.webkitRelativePath||u.name;l||(l=b.split("/")[0]||"uploaded_resource");const B=u.name.split(".").pop()?.toLowerCase(),W=["png","jpg","jpeg","gif","webp","ico"].includes(B||"");await new Promise(re=>{const te=new FileReader;te.onload=n=>{const m=n.target?.result;o.push({path:b,content:m}),re()},W?te.readAsDataURL(u):te.readAsText(u)})}try{const a=await fetch("/api/resources",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({name:l,type:"folder",content:JSON.stringify(o)})});if(a.ok){const u=await a.json();Se({resourceId:u.id,coursewareUuid:""}),Ze()}}catch(a){console.error("Folder upload failed:",a)}}})]})]})]})]}),(!v.resourceId&&!v.coursewareUuid||t.type==="code-sandbox")&&jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"沙箱程序代码 (Source Code)"}),jsxRuntimeExports.jsx("textarea",{value:v.code||"",onChange:e=>Q("code",e.target.value),onBlur:e=>ae("code",e.target.value),className:"w-full h-48 p-3 border border-slate-300 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500 bg-slate-900 text-slate-100 resize-none leading-relaxed",placeholder:"// 编写交互沙箱代码..."})]})]}),t.type==="math-graph"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"函数解析拟合"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"函数表达式 y = f(x)"}),jsxRuntimeExports.jsx("input",{type:"text",value:v.equation||"",onChange:e=>Q("equation",e.target.value),onBlur:e=>ae("equation",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-100"}),jsxRuntimeExports.jsxs("p",{className:"text-[10px] text-slate-400 mt-1 leading-snug",children:["支持标准 JS 表达式。 示例:",jsxRuntimeExports.jsx("br",{}),"• ",jsxRuntimeExports.jsx("code",{className:"bg-slate-100 px-1 rounded",children:"Math.sin(x)"})," 正负弦波形",jsxRuntimeExports.jsx("br",{}),"• ",jsxRuntimeExports.jsx("code",{className:"bg-slate-100 px-1 rounded",children:"Math.cos(x) * x"})," 振幅衰减"]})]})]}),t.type==="presentation"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"幻灯片 Markdown 文案"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"Markdown 源代码"}),jsxRuntimeExports.jsx("textarea",{value:v.markdown||"",onChange:e=>Q("markdown",e.target.value),onBlur:e=>ae("markdown",e.target.value),className:"w-full h-64 p-2.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-100 resize-none font-medium leading-relaxed bg-slate-50",placeholder:"修改 Markdown 内容..."})]})]}),t.type==="text"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"文字属性管理"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"文本内容"}),jsxRuntimeExports.jsx("input",{type:"text",value:v.text||"",onChange:e=>Q("text",e.target.value),onBlur:e=>ae("text",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-medium focus:outline-none focus:ring-1 focus:ring-indigo-500"})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"文字大小 (FontSize)"}),jsxRuntimeExports.jsx("input",{type:"number",min:"10",max:"100",value:v.fontSize||16,onChange:e=>Q("fontSize",parseInt(e.target.value)||10),onBlur:e=>Me("fontSize",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none"})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"文字填充颜色"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("input",{type:"color",value:v.color||"#000000",onChange:e=>Q("color",e.target.value),onBlur:e=>ae("color",e.target.value),className:"w-8 h-8 rounded border border-slate-200 cursor-pointer shrink-0"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-[11px] text-slate-500",children:v.color||"#000000"})]})]})]}),(t.type==="rectangle"||t.type==="shape")&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"矩形样式配置"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"外边框颜色"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("input",{type:"color",value:v.stroke||"#000000",onChange:e=>Q("stroke",e.target.value),onBlur:e=>ae("stroke",e.target.value),className:"w-8 h-8 rounded border border-slate-200 cursor-pointer shrink-0"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-[11px] text-slate-500",children:v.stroke||"#000000"})]})]})]}),t.type==="circle"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"圆形样式配置"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"外边框颜色"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("input",{type:"color",value:v.stroke||"#000000",onChange:e=>Q("stroke",e.target.value),onBlur:e=>ae("stroke",e.target.value),className:"w-8 h-8 rounded border border-slate-200 cursor-pointer shrink-0"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-[11px] text-slate-500",children:v.stroke||"#000000"})]})]})]}),t.type==="pen"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"线条样式配置"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"折线颜色"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("input",{type:"color",value:v.color||"#000000",onChange:e=>Q("color",e.target.value),onBlur:e=>ae("color",e.target.value),className:"w-8 h-8 rounded border border-slate-200 cursor-pointer shrink-0"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-[11px] text-slate-500",children:v.color||"#000000"})]})]})]}),t.type==="highlighter"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"高亮荧光标记 (Highlighter)"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"荧光笔颜色"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("input",{type:"color",value:v.color||"#facc15",onChange:e=>Q("color",e.target.value),onBlur:e=>ae("color",e.target.value),className:"w-8 h-8 rounded border border-slate-200 cursor-pointer shrink-0"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-[11px] text-slate-500",children:v.color||"#facc15"})]})]})]}),jsxRuntimeExports.jsx("div",{className:"text-[10px] text-slate-400 text-center select-none pt-2 font-medium",children:"提示:属性在失焦或修改时自动同步,多端可见。"})]}),jsxRuntimeExports.jsxs("div",{className:"p-3 border-t border-slate-200 bg-white flex flex-col gap-2 shrink-0",children:[jsxRuntimeExports.jsx("button",{onClick:()=>Pe(v),disabled:we,className:"w-full py-2 bg-indigo-600 hover:bg-indigo-700 text-white rounded-lg font-bold transition-all shadow-sm hover:shadow active:scale-[0.98] cursor-pointer flex items-center justify-center gap-1.5 text-xs",children:we?jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx(LoaderCircle,{size:13,className:"animate-spin"}),"正在广播同步..."]}):jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx(Paintbrush,{size:13}),"应用修改并强制同步"]})}),jsxRuntimeExports.jsxs("button",{onClick:()=>{le(E),D(null)},className:"w-full py-2 bg-red-50 hover:bg-red-105 text-red-650 rounded-lg font-semibold transition-all flex items-center justify-center gap-1.5 border border-red-200 cursor-pointer text-xs",children:[jsxRuntimeExports.jsx(Trash2,{size:13}),"删除当前组件"]})]})]}):null})()]})});export{DEFAULT_WHITEBOARD_PAGES,InteractiveWhiteboard};
|
|
102
|
+
## Slide 2`,width:600,height:400,slideX:0,slideY:0};case"quiz":return{...a,question:e.question??"New Quiz",options:Array.isArray(e.options)?e.options:["A","B","C","D"]};case"html-applet":return{...a,code:e.code??""};case"assignment":return{...a,title:e.title??"New Assignment",description:e.description??""};case"hello-world":return a;case"rollcall":return{...a,allStudents:[]};default:return{...a,...e}}},Yt=async(t,e)=>{if(!I.current)return;const r=I.current.getBoundingClientRect(),o=Math.round(r.width/2),a=Math.round(r.height/2);M(!0);try{await g(t,mt(t,e,o,a)),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),f&&f()}catch(i){console.error("addElementAtCenter error",i)}finally{M(!1)}};reactExports.useImperativeHandle(ce,()=>({addElementAtCenter:Yt}));const ht=async t=>{t.preventDefault(),t.stopPropagation();try{let e=t.dataTransfer.getData("application/json");if(e||(e=t.dataTransfer.getData("text/plain")),e||(e=t.dataTransfer.getData("text")),e||(e=t.dataTransfer.getData("Text")),console.log("Whiteboard drop triggered. Payload:",e),!e)return;let r;try{r=JSON.parse(e)}catch(u){console.error("Failed to parse drop JSON payload:",u);return}if(typeof r!="object"||!r)return;if(!I.current){console.warn("containerRef.current is not loaded on drop");return}const o=I.current.getBoundingClientRect();let a=t.clientX-o.left,i=t.clientY-o.top;console.log(`Adding whiteboard element of type ${r.type} at (${a}, ${i})`),M(!0);try{await g(r.type,mt(r.type,r,a,i)),frontendEventBus.publish({id:v7(),type:"whiteboard.element_updated",source:"whiteboard",payload:{lessonId:s},timestamp:Date.now(),correlationId:s}),f&&f()}finally{M(!1)}}catch(e){console.error("Drop error",e)}};return jsxRuntimeExports.jsxs("div",{className:"flex-1 flex flex-row min-h-0 overflow-hidden bg-white",children:[jsxRuntimeExports.jsxs("div",{className:"flex-1 flex flex-col min-h-0 bg-white relative min-w-0",onDragOver:ut,onDragEnter:pt,onDrop:ht,children:[jsxRuntimeExports.jsx(WhiteboardToolbar,{tool:R,setTool:P,setSelectedShapeId:D,highlighterColor:de,setHighlighterColor:L,onElementAdd:g,currentPage:p,activeSegmentId:c,lessonId:s,safeElements:T,selectedShapeId:b,showGrid:C,setShowGrid:_,userRole:k,isSyncing:ye,setIsSyncing:M,handleClearBoard:Ot,handleResetBoard:Lt,handleElementDelete:le,setDialog:ue,setDialogInput:at,onRefresh:f}),jsxRuntimeExports.jsxs("div",{ref:I,className:"flex-1 bg-slate-50/70 rounded-2xl border border-slate-200/80 relative overflow-hidden w-full mb-14 shadow-inner transition-all",style:{backgroundImage:C?"radial-gradient(#cbd5e1 1.2px, transparent 1.2px)":"none",backgroundSize:"24px 24px",backgroundColor:"#f8fafc"},onDragOver:ut,onDragEnter:pt,onDragLeave:Ht,onDrop:async t=>{pe(!1),await ht(t)},children:[G&&jsxRuntimeExports.jsxs("div",{className:"absolute inset-0 border-2 border-dashed border-indigo-500 bg-indigo-500/10 backdrop-blur-[2px] rounded-2xl flex flex-col items-center justify-center text-indigo-600 font-bold text-sm z-30 animate-in fade-in pointer-events-none",children:[jsxRuntimeExports.jsx(Plus,{size:32,className:"mb-2 text-indigo-600 animate-bounce"}),jsxRuntimeExports.jsx("span",{children:"释放鼠标将组件放入当前白板页面"})]}),T.filter(t=>{if(t.type==="page_meta")return!1;try{const e=JSON.parse(t.data),r=e.page??0,o=Z[p];return!(!(e.pageId&&o?.id?e.pageId===o.id:r===p)||c&&e.segmentId&&e.segmentId!==c)}catch{return p===0}}).length===0&&!Je&&jsxRuntimeExports.jsxs("div",{className:"absolute inset-0 flex flex-col items-center justify-center pointer-events-none select-none text-slate-400 p-6 z-0",children:[jsxRuntimeExports.jsx("div",{className:"w-16 h-16 rounded-2xl bg-indigo-50/80 border border-indigo-100/80 flex items-center justify-center mb-3 shadow-2xs",children:jsxRuntimeExports.jsx(Sparkles,{className:"w-7 h-7 text-indigo-500 animate-pulse"})}),jsxRuntimeExports.jsx("p",{className:"font-bold text-sm text-slate-700 mb-1",children:"交互式备课白板"}),jsxRuntimeExports.jsx("p",{className:"text-xs text-slate-400 max-w-sm text-center",children:"从左侧组件库拖拽组件至此处,或使用顶部工具栏插入画笔、几何图形与 AI 助教"})]}),jsxRuntimeExports.jsxs("div",{className:"absolute inset-0 w-full h-full overflow-hidden",style:{pointerEvents:G?"none":"auto"},children:[K.width>0&&K.height>0&&(Je?(()=>{const t=T.find(o=>o.id===Je);if(!t)return De(null),null;let e={};try{e=JSON.parse(t.data)}catch{}const r={quiz:"📝 随堂测验",timer:"⏱ 计时器",assignment:"📋 作业","code-sandbox":"💻 代码沙箱","html-applet":"🌐 交互课件",rollcall:"🎲 随机点名",presentation:"📽 演示文稿","math-graph":"📐 数学图形",text:"📝 文本"};return jsxRuntimeExports.jsx(FullscreenOverlay,{type:t.type,title:r[t.type]||t.type,data:e,containerSize:K,onClose:()=>De(null),lessonId:s})})():jsxRuntimeExports.jsx(Stage,{width:K.width,height:K.height,onMouseDown:Ft,onMousemove:Wt,onMouseup:_t,onContextMenu:t=>{t.evt.preventDefault();const e=I.current?.getBoundingClientRect();if(e){const r=t.evt.clientX-e.left,o=t.evt.clientY-e.top,i=t.target.id();i?(D(i),V({x:r,y:o,elementId:i})):V({x:r,y:o})}},ref:A,className:"w-full h-full cursor-crosshair",children:jsxRuntimeExports.jsxs(Layer,{children:[T.filter(t=>{if(t.type==="page_meta")return!1;try{const e=JSON.parse(t.data),r=e.page??0,o=Z[p];return!(!(e.pageId&&o?.id?e.pageId===o.id:r===p)||c&&e.segmentId&&e.segmentId!==c)}catch{return p===0}}).map(It),At(),Xt()]})})),b&&(()=>{const t=T.find(a=>a.id===b);if(!t)return null;const e=Bt(t);if(!e)return null;const r=Math.max(10,Math.min(K.width-150,e.x-60)),o=Math.max(10,Math.min(K.height-50,e.y));return jsxRuntimeExports.jsxs("div",{style:{left:`${r}px`,top:`${o}px`,pointerEvents:"auto"},className:"absolute bg-white text-gray-800 shadow-xl border border-red-200 rounded-lg py-1 px-2 flex items-center gap-1.5 z-30 animate-in fade-in slide-in-from-bottom-2 duration-150 animate-out fade-out duration-100",children:[jsxRuntimeExports.jsx("span",{className:"text-xs font-semibold px-1 text-gray-500 capitalize select-none",children:t.type}),jsxRuntimeExports.jsx("div",{className:"w-[1px] h-3 bg-gray-200"}),jsxRuntimeExports.jsxs("button",{onClick:()=>{le(b),D(null)},className:"flex items-center gap-1 text-xs text-red-600 hover:text-white hover:bg-red-600 px-2 py-0.5 rounded transition-all font-medium cursor-pointer",children:[jsxRuntimeExports.jsx(Trash2,{size:12}),"删除"]})]})})(),Be&&jsxRuntimeExports.jsx("div",{style:{left:`${Be.x}px`,top:`${Be.y}px`,pointerEvents:"auto"},className:"absolute bg-white rounded-lg shadow-2xl border border-gray-200 py-1.5 w-44 z-40 font-sans text-sm animate-in fade-in zoom-in-95 duration-100",onClick:t=>t.stopPropagation(),onContextMenu:t=>t.preventDefault(),children:Be.elementId?jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx("div",{className:"px-3 py-1 text-[11px] text-gray-500 font-bold uppercase tracking-wider select-none",children:"组件选项"}),jsxRuntimeExports.jsxs("button",{onClick:()=>{const t=Be.elementId;t&&(le(t),b===t&&D(null)),V(null)},className:"w-full px-3 py-1.5 flex items-center gap-2 text-left text-red-600 hover:bg-red-50 transition-colors text-xs font-semibold",children:[jsxRuntimeExports.jsx(Trash2,{size:14}),"删除此组件"]})]}):jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx("div",{className:"px-3 py-1 text-[11px] text-gray-400 font-bold uppercase tracking-wider select-none",children:"白板操作"}),jsxRuntimeExports.jsxs("button",{onClick:()=>{P("cursor"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${R==="cursor"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(MousePointer2,{size:14}),"选择工具 (Cursor)"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{P("pen"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${R==="pen"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(PenTool,{size:14}),"画笔工具 (Pen)"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{P("highlighter"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${R==="highlighter"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(Highlighter,{size:14}),"高亮荧光笔 (Highlighter)"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{P("rect"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${R==="rect"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(Square,{size:14}),"矩形工具 (Rectangle)"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{P("circle"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${R==="circle"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(Circle,{size:14}),"圆形工具 (Circle)"]}),jsxRuntimeExports.jsxs("button",{onClick:()=>{P("text"),V(null)},className:`w-full px-3 py-1.5 flex items-center gap-2 text-left text-xs font-medium hover:bg-gray-50 transition-colors ${R==="text"?"text-indigo-600":"text-gray-750"}`,children:[jsxRuntimeExports.jsx(Type,{size:14}),"文本工具 (Text)"]})]})})]})]}),jsxRuntimeExports.jsx(WhiteboardPageBar,{pages:Z,currentPage:p,showPageDrawer:Ne,setShowPageDrawer:oe,editingPageIdx:ee,setEditingPageIdx:se,editingPageTitle:H,setEditingPageTitle:je,activeMenuPageIdx:ie,setActiveMenuPageIdx:be,safeElements:T,handleSwitchPage:Ie,handleRenamePage:ze,handleDuplicatePage:Te,handleMovePage:st,handleDeletePage:Ye,handleAddPage:He}),jsxRuntimeExports.jsx(WhiteboardDialog,{dialog:gt,dialogInput:bt,setDialogInput:at,setDialog:ue}),jsxRuntimeExports.jsx(CoursewareEntrySelectorModal,{showEntrySelector:Pt,setShowEntrySelector:xt,zipUploadInfo:kt,zipCandidates:vt,handlePropsUpdate:Se,fetchCoursewares:Qe})]}),J&&b&&w&&(()=>{const t=T.find(e=>e.id===b);return t?jsxRuntimeExports.jsxs("div",{className:"w-80 h-full max-h-full bg-slate-50 border-l border-slate-200 flex flex-col font-sans text-xs select-none shadow-xl shrink-0 z-20 animate-in slide-in-from-right duration-200",onPointerDown:e=>e.stopPropagation(),children:[jsxRuntimeExports.jsxs("div",{className:"px-4 py-3 border-b border-slate-200 bg-white flex justify-between items-center shrink-0",children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx(Settings,{size:15,className:"text-slate-500 animate-spin",style:{animationDuration:"6s"}}),jsxRuntimeExports.jsx("span",{className:"font-bold text-slate-800 text-sm",children:"属性编辑器"})]}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5 font-sans",children:[jsxRuntimeExports.jsxs("button",{onClick:St,disabled:(Le[b]||[]).length===0,className:`p-1 rounded-lg transition-all flex items-center justify-center gap-1 border border-transparent select-none cursor-pointer ${(Le[b]||[]).length===0?"text-slate-350 bg-transparent border-transparent opacity-40 cursor-not-allowed":"text-slate-700 bg-slate-50 hover:bg-slate-100 hover:border-slate-200 active:bg-slate-150"}`,title:"撤销属性修改",children:[jsxRuntimeExports.jsx(Undo2,{size:13}),(Le[b]||[]).length>0&&jsxRuntimeExports.jsx("span",{className:"text-[10px] font-bold text-slate-500",children:(Le[b]||[]).length})]}),jsxRuntimeExports.jsxs("button",{onClick:zt,disabled:(Fe[b]||[]).length===0,className:`p-1 rounded-lg transition-all flex items-center justify-center gap-1 border border-transparent select-none cursor-pointer ${(Fe[b]||[]).length===0?"text-slate-350 bg-transparent border-transparent opacity-40 cursor-not-allowed":"text-slate-700 bg-slate-50 hover:bg-slate-100 hover:border-slate-200 active:bg-slate-150"}`,title:"重做属性修改",children:[jsxRuntimeExports.jsx(Redo2,{size:13}),(Fe[b]||[]).length>0&&jsxRuntimeExports.jsx("span",{className:"text-[10px] font-bold text-slate-500",children:(Fe[b]||[]).length})]}),jsxRuntimeExports.jsx("div",{className:"h-4 w-px bg-slate-200 mx-0.5 shrink-0"}),jsxRuntimeExports.jsx("button",{onClick:()=>D(null),className:"text-slate-400 hover:text-slate-650 hover:bg-slate-100 p-1 rounded-full transition-all cursor-pointer",title:"关闭属性编辑器",children:jsxRuntimeExports.jsx(X,{size:15})})]})]}),jsxRuntimeExports.jsxs("div",{className:"flex-1 overflow-y-auto p-4 space-y-4",children:[jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-2",children:[jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between",children:[jsxRuntimeExports.jsx("span",{className:"text-slate-400 text-[10px] font-bold uppercase tracking-wider",children:"组件类型"}),jsxRuntimeExports.jsx("span",{className:"px-2 py-0.5 bg-indigo-50 text-indigo-650 rounded text-[10px] font-bold uppercase tracking-wider",children:t.type})]}),jsxRuntimeExports.jsxs("div",{className:"flex items-center justify-between",children:[jsxRuntimeExports.jsx("span",{className:"text-slate-400 text-[10px] font-bold uppercase tracking-wider",children:"组件标识"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-slate-500 text-[10px] truncate max-w-[155px]",title:t.id,children:t.id})]})]}),jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5 flex items-center gap-1.5",children:"物理定位 & 尺寸"}),jsxRuntimeExports.jsxs("div",{className:"grid grid-cols-2 gap-2",children:[jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"X 坐标"}),jsxRuntimeExports.jsx("input",{type:"number",value:Math.round(w.x??0),onChange:e=>Q("x",parseFloat(e.target.value)||0),onBlur:e=>Me("x",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500"})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"Y 坐标"}),jsxRuntimeExports.jsx("input",{type:"number",value:Math.round(w.y??0),onChange:e=>Q("y",parseFloat(e.target.value)||0),onBlur:e=>Me("y",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500"})]})]}),t.type!=="pen"&&t.type!=="circle"&&jsxRuntimeExports.jsxs("div",{className:"grid grid-cols-2 gap-2 mt-2",children:[jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"宽度 (Width)"}),jsxRuntimeExports.jsx("input",{type:"number",min:"50",value:Math.round(w.width??300),onChange:e=>Q("width",parseFloat(e.target.value)||50),onBlur:e=>Me("width",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500"})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"高度 (Height)"}),jsxRuntimeExports.jsx("input",{type:"number",min:"50",value:Math.round(w.height??300),onChange:e=>Q("height",parseFloat(e.target.value)||50),onBlur:e=>Me("height",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500"})]})]}),t.type==="circle"&&jsxRuntimeExports.jsxs("div",{className:"mt-2",children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"半径 (Radius)"}),jsxRuntimeExports.jsx("input",{type:"number",min:"5",value:Math.round(w.radius??50),onChange:e=>Q("radius",parseFloat(e.target.value)||5),onBlur:e=>Me("radius",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500"})]})]}),(()=>{const e=propertyEditorRegistry.get(t.type);return e?jsxRuntimeExports.jsx(e,{elementId:t.id,elementType:t.type,data:w,updateData:Se,lessonId:s,onClose:()=>D(null)}):null})(),t.type==="quiz"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"随堂测验配置"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"测验题目 (Question)"}),jsxRuntimeExports.jsx("textarea",{value:w.question||"",onChange:e=>Q("question",e.target.value),onBlur:e=>ae("question",e.target.value),className:"w-full h-20 p-2 border border-slate-200 rounded-lg text-xs focus:outline-none focus:ring-1 focus:ring-indigo-500 resize-none font-medium leading-relaxed",placeholder:"编写问题描述..."})]}),(w.options||[]).length>0&&jsxRuntimeExports.jsxs("div",{className:"bg-amber-50 border border-amber-200 rounded-lg p-2.5",children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-amber-700 font-bold mb-1.5",children:"⚠️ 正确答案 (Correct Answer)"}),jsxRuntimeExports.jsxs("select",{value:w.correctAnswer||"",onChange:e=>{Q("correctAnswer",e.target.value),ae("correctAnswer",e.target.value)},className:`w-full px-2 py-1.5 border rounded-lg text-xs font-medium focus:outline-none focus:ring-1 focus:ring-amber-500 cursor-pointer ${w.correctAnswer?"border-green-300 bg-green-50 text-green-800":"border-amber-300 bg-white text-amber-800"}`,children:[jsxRuntimeExports.jsx("option",{value:"",children:"-- 请选择正确答案 --"}),(w.options||[]).map((e,r)=>jsxRuntimeExports.jsx("option",{value:e,children:e},r))]}),!w.correctAnswer&&jsxRuntimeExports.jsx("p",{className:"text-[9px] text-amber-600 mt-1",children:"未设置正确答案将无法自动判分"})]}),jsxRuntimeExports.jsxs("div",{className:"space-y-2",children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold",children:"选项列表 (Options)"}),jsxRuntimeExports.jsx("div",{className:"space-y-1.5 max-h-48 overflow-y-auto pr-1",children:(w.options||[]).map((e,r)=>{const a="ABCDEFGHIJKLMNOPQRSTUVWXYZ"[r]||r+1;return jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-1.5",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-slate-700 bg-slate-100 rounded px-1.5 py-1 text-center shrink-0 min-w-[22px]",children:a}),jsxRuntimeExports.jsx("input",{type:"text",value:e||"",onChange:i=>Dt(r,i.target.value),onBlur:i=>Mt(r,i.target.value),className:"flex-1 px-2 py-1 border border-slate-200 rounded-lg text-xs font-medium"}),jsxRuntimeExports.jsx("button",{onClick:()=>$t(r),title:"删除选项",className:"text-slate-400 hover:text-red-500 hover:bg-red-50 p-1 rounded-md shrink-0 transition-colors cursor-pointer",children:jsxRuntimeExports.jsx(Trash2,{size:13})})]},r)})}),jsxRuntimeExports.jsxs("button",{onClick:Tt,className:"w-full mt-2 py-1 bg-slate-100 hover:bg-slate-200 text-slate-600 font-bold border border-slate-200/80 rounded-lg flex items-center justify-center gap-1 hover:text-slate-700 transition-all text-[11px] cursor-pointer",children:[jsxRuntimeExports.jsx(Plus,{size:12})," 添加选项"]})]})]}),t.type==="assignment"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"作业选项配置"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"作业任务标题 (Title)"}),jsxRuntimeExports.jsx("input",{type:"text",value:w.title||"",onChange:e=>Q("title",e.target.value),onBlur:e=>ae("title",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-semibold focus:outline-none focus:ring-1 focus:ring-indigo-500",placeholder:"作业名..."})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"详细作业要求描述"}),jsxRuntimeExports.jsx("textarea",{value:w.description||"",onChange:e=>Q("description",e.target.value),onBlur:e=>ae("description",e.target.value),className:"w-full h-24 p-2 border border-slate-200 rounded-lg text-xs focus:outline-none focus:ring-1 focus:ring-indigo-500 resize-none font-medium leading-relaxed",placeholder:"请输入详细的作业指南..."})]})]}),(t.type==="code-sandbox"||t.type==="html-applet")&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsxs("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5 flex justify-between items-center",children:[jsxRuntimeExports.jsx("span",{children:"动态运行代码定制"}),t.type==="html-applet"&&jsxRuntimeExports.jsx("span",{className:"text-[10px] bg-indigo-50 text-indigo-700 px-1.5 py-0.5 rounded-full font-bold",children:"HTML Applet"})]}),t.type==="html-applet"&&jsxRuntimeExports.jsxs("div",{className:"space-y-3 border-b border-slate-100 pb-3",children:[jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-indigo-600 font-bold mb-1",children:"选择 AI 互动课件 (ZIP/HTML):"}),jsxRuntimeExports.jsxs("select",{value:w.coursewareUuid||"",onChange:e=>{const r=e.target.value;Se({coursewareUuid:r,resourceId:""})},className:"w-full text-xs p-2 bg-slate-50 border border-indigo-200 hover:border-indigo-300 rounded-lg text-slate-750 focus:outline-none focus:ring-1 focus:ring-indigo-500 transition-all font-semibold",children:[jsxRuntimeExports.jsx("option",{value:"",children:"-- 使用系统资源或自定义代码 --"}),wt.map(e=>jsxRuntimeExports.jsxs("option",{value:e.uuid,children:["📁 [互动课件] ",e.name]},e.id))]})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-500 font-bold mb-1",children:"选择已有的系统资源:"}),jsxRuntimeExports.jsxs("select",{value:w.resourceId||"",onChange:e=>{const r=e.target.value;Se({resourceId:r,coursewareUuid:""})},className:"w-full text-xs p-2 bg-slate-50 border border-slate-200 hover:border-slate-300 rounded-lg text-slate-750 focus:outline-none focus:ring-1 focus:ring-indigo-500 transition-all font-semibold",children:[jsxRuntimeExports.jsx("option",{value:"",children:"-- 使用互动课件或自定义代码 --"}),Et.map(e=>jsxRuntimeExports.jsxs("option",{value:e.id,children:["[",e.type==="folder"?"文件夹":"单HTML","] ",e.name]},e.id))]})]}),jsxRuntimeExports.jsxs("div",{className:"bg-slate-50 p-2.5 rounded-xl border border-slate-100 text-[10px] text-slate-500 space-y-2",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-slate-600 block",children:"上传资源 (会自动保存到对应库):"}),jsxRuntimeExports.jsxs("div",{className:"grid grid-cols-2 gap-2",children:[jsxRuntimeExports.jsxs("label",{className:"col-span-2 flex flex-col items-center justify-center p-2 bg-indigo-50 hover:bg-indigo-100 border border-indigo-200 hover:border-indigo-300 rounded-lg cursor-pointer text-center transition-all",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-indigo-700 text-[10px]",children:"✨ 上传 AI 互动课件 (.zip/.html)"}),jsxRuntimeExports.jsx("input",{type:"file",accept:".zip,.html,.htm",className:"hidden",onChange:async e=>{const r=e.target.files?.[0];if(!r)return;const o=new FileReader;o.onload=async a=>{const i=a.target?.result;try{const u=await fetch("/api/courseware/upload",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({name:r.name.replace(/\.[^/.]+$/,""),filename:r.name,base64Data:i})});if(u.ok){const j=await u.json();j.need_select_entry?(Nt(j.candidates),Ct({uuid:j.uuid,name:j.name}),xt(!0)):(Se({coursewareUuid:j.uuid,resourceId:""}),Qe())}else{const j=await u.json();alert("上传失败: "+(j.error||u.statusText))}}catch(u){console.error("Courseware upload failed:",u)}},o.readAsDataURL(r)}})]}),jsxRuntimeExports.jsxs("label",{className:"flex flex-col items-center justify-center p-2 bg-white hover:bg-slate-100 border border-slate-200 hover:border-slate-300 rounded-lg cursor-pointer text-center transition-all",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-slate-600 text-[10px]",children:"📄 上传系统HTML文件"}),jsxRuntimeExports.jsx("input",{type:"file",accept:".html,.htm",className:"hidden",onChange:async e=>{const r=e.target.files?.[0];if(!r)return;const o=new FileReader;o.onload=async a=>{const i=a.target?.result;try{const u=await fetch("/api/resources",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({name:r.name,type:"html",content:i})});if(u.ok){const j=await u.json();Se({resourceId:j.id,coursewareUuid:""}),Ze()}}catch(u){console.error("Upload failed:",u)}},o.readAsText(r)}})]}),jsxRuntimeExports.jsxs("label",{className:"flex flex-col items-center justify-center p-2 bg-white hover:bg-slate-100 border border-slate-200 hover:border-slate-300 rounded-lg cursor-pointer text-center transition-all",children:[jsxRuntimeExports.jsx("span",{className:"font-bold text-slate-600 text-[10px]",children:"📁 上传系统文件夹"}),jsxRuntimeExports.jsx("input",{type:"file",webkitdirectory:"",directory:"",multiple:!0,className:"hidden",onChange:async e=>{const r=e.target.files;if(!r||r.length===0)return;const o=[];let a="";for(let i=0;i<r.length;i++){const u=r[i],j=u.webkitRelativePath||u.name;a||(a=j.split("/")[0]||"uploaded_resource");const $=u.name.split(".").pop()?.toLowerCase(),W=["png","jpg","jpeg","gif","webp","ico"].includes($||"");await new Promise(re=>{const te=new FileReader;te.onload=n=>{const m=n.target?.result;o.push({path:j,content:m}),re()},W?te.readAsDataURL(u):te.readAsText(u)})}try{const i=await fetch("/api/resources",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({name:a,type:"folder",content:JSON.stringify(o)})});if(i.ok){const u=await i.json();Se({resourceId:u.id,coursewareUuid:""}),Ze()}}catch(i){console.error("Folder upload failed:",i)}}})]})]})]})]}),(!w.resourceId&&!w.coursewareUuid||t.type==="code-sandbox")&&jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"沙箱程序代码 (Source Code)"}),jsxRuntimeExports.jsx("textarea",{value:w.code||"",onChange:e=>Q("code",e.target.value),onBlur:e=>ae("code",e.target.value),className:"w-full h-48 p-3 border border-slate-300 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-500 bg-slate-900 text-slate-100 resize-none leading-relaxed",placeholder:"// 编写交互沙箱代码..."})]})]}),t.type==="math-graph"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"函数解析拟合"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"函数表达式 y = f(x)"}),jsxRuntimeExports.jsx("input",{type:"text",value:w.equation||"",onChange:e=>Q("equation",e.target.value),onBlur:e=>ae("equation",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-100"}),jsxRuntimeExports.jsxs("p",{className:"text-[10px] text-slate-400 mt-1 leading-snug",children:["支持标准 JS 表达式。 示例:",jsxRuntimeExports.jsx("br",{}),"• ",jsxRuntimeExports.jsx("code",{className:"bg-slate-100 px-1 rounded",children:"Math.sin(x)"})," 正负弦波形",jsxRuntimeExports.jsx("br",{}),"• ",jsxRuntimeExports.jsx("code",{className:"bg-slate-100 px-1 rounded",children:"Math.cos(x) * x"})," 振幅衰减"]})]})]}),t.type==="presentation"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"幻灯片 Markdown 文案"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"Markdown 源代码"}),jsxRuntimeExports.jsx("textarea",{value:w.markdown||"",onChange:e=>Q("markdown",e.target.value),onBlur:e=>ae("markdown",e.target.value),className:"w-full h-64 p-2.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none focus:ring-1 focus:ring-indigo-100 resize-none font-medium leading-relaxed bg-slate-50",placeholder:"修改 Markdown 内容..."})]})]}),t.type==="text"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"文字属性管理"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"文本内容"}),jsxRuntimeExports.jsx("input",{type:"text",value:w.text||"",onChange:e=>Q("text",e.target.value),onBlur:e=>ae("text",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-medium focus:outline-none focus:ring-1 focus:ring-indigo-500"})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"文字大小 (FontSize)"}),jsxRuntimeExports.jsx("input",{type:"number",min:"10",max:"100",value:w.fontSize||16,onChange:e=>Q("fontSize",parseInt(e.target.value)||10),onBlur:e=>Me("fontSize",e.target.value),className:"w-full px-2 py-1.5 border border-slate-200 rounded-lg text-xs font-mono focus:outline-none"})]}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"文字填充颜色"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("input",{type:"color",value:w.color||"#000000",onChange:e=>Q("color",e.target.value),onBlur:e=>ae("color",e.target.value),className:"w-8 h-8 rounded border border-slate-200 cursor-pointer shrink-0"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-[11px] text-slate-500",children:w.color||"#000000"})]})]})]}),(t.type==="rectangle"||t.type==="shape")&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"矩形样式配置"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"外边框颜色"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("input",{type:"color",value:w.stroke||"#000000",onChange:e=>Q("stroke",e.target.value),onBlur:e=>ae("stroke",e.target.value),className:"w-8 h-8 rounded border border-slate-200 cursor-pointer shrink-0"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-[11px] text-slate-500",children:w.stroke||"#000000"})]})]})]}),t.type==="circle"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"圆形样式配置"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"外边框颜色"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("input",{type:"color",value:w.stroke||"#000000",onChange:e=>Q("stroke",e.target.value),onBlur:e=>ae("stroke",e.target.value),className:"w-8 h-8 rounded border border-slate-200 cursor-pointer shrink-0"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-[11px] text-slate-500",children:w.stroke||"#000000"})]})]})]}),t.type==="pen"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"线条样式配置"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"折线颜色"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("input",{type:"color",value:w.color||"#000000",onChange:e=>Q("color",e.target.value),onBlur:e=>ae("color",e.target.value),className:"w-8 h-8 rounded border border-slate-200 cursor-pointer shrink-0"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-[11px] text-slate-500",children:w.color||"#000000"})]})]})]}),t.type==="highlighter"&&jsxRuntimeExports.jsxs("div",{className:"bg-white p-3 rounded-xl border border-slate-200 shadow-sm space-y-3",children:[jsxRuntimeExports.jsx("h4",{className:"font-bold text-slate-700 text-xs border-b border-slate-100 pb-1.5",children:"高亮荧光标记 (Highlighter)"}),jsxRuntimeExports.jsxs("div",{children:[jsxRuntimeExports.jsx("label",{className:"block text-[10px] text-slate-400 font-semibold mb-1",children:"荧光笔颜色"}),jsxRuntimeExports.jsxs("div",{className:"flex items-center gap-2",children:[jsxRuntimeExports.jsx("input",{type:"color",value:w.color||"#facc15",onChange:e=>Q("color",e.target.value),onBlur:e=>ae("color",e.target.value),className:"w-8 h-8 rounded border border-slate-200 cursor-pointer shrink-0"}),jsxRuntimeExports.jsx("span",{className:"font-mono text-[11px] text-slate-500",children:w.color||"#facc15"})]})]})]}),jsxRuntimeExports.jsx("div",{className:"text-[10px] text-slate-400 text-center select-none pt-2 font-medium",children:"提示:属性在失焦或修改时自动同步,多端可见。"})]}),jsxRuntimeExports.jsxs("div",{className:"p-3 border-t border-slate-200 bg-white flex flex-col gap-2 shrink-0",children:[jsxRuntimeExports.jsx("button",{onClick:()=>Pe(w),disabled:ye,className:"w-full py-2 bg-indigo-600 hover:bg-indigo-700 text-white rounded-lg font-bold transition-all shadow-sm hover:shadow active:scale-[0.98] cursor-pointer flex items-center justify-center gap-1.5 text-xs",children:ye?jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx(LoaderCircle,{size:13,className:"animate-spin"}),"正在广播同步..."]}):jsxRuntimeExports.jsxs(jsxRuntimeExports.Fragment,{children:[jsxRuntimeExports.jsx(Paintbrush,{size:13}),"应用修改并强制同步"]})}),jsxRuntimeExports.jsxs("button",{onClick:()=>{le(b),D(null)},className:"w-full py-2 bg-red-50 hover:bg-red-105 text-red-650 rounded-lg font-semibold transition-all flex items-center justify-center gap-1.5 border border-red-200 cursor-pointer text-xs",children:[jsxRuntimeExports.jsx(Trash2,{size:13}),"删除当前组件"]})]})]}):null})()]})});export{DEFAULT_WHITEBOARD_PAGES,InteractiveWhiteboard};
|