45 lines
34 KiB
JavaScript
45 lines
34 KiB
JavaScript
import{c as L,d as we,f as se,r as T,j as e,B as R,ag as Ce,ae as D,H as B,S as ne,ac as de,P as $,F as Se,a8 as _e,T as ie,I as V,af as ze,v as Re}from"./index-T-NGjlrZ.js";import{C as ae,a as le,b as re}from"./card-C5ifMTlY.js";import{R as Pe}from"./refresh-cw-DXuKsZdS.js";/**
|
||
* @license lucide-react v0.475.0 - ISC
|
||
*
|
||
* This source code is licensed under the ISC license.
|
||
* See the LICENSE file in the root directory of this source tree.
|
||
*/const Ee=[["path",{d:"M12 5v14",key:"s699le"}],["path",{d:"m19 12-7 7-7-7",key:"1idqje"}]],me=L("ArrowDown",Ee);/**
|
||
* @license lucide-react v0.475.0 - ISC
|
||
*
|
||
* This source code is licensed under the ISC license.
|
||
* See the LICENSE file in the root directory of this source tree.
|
||
*/const Te=[["path",{d:"m5 12 7-7 7 7",key:"hav0vg"}],["path",{d:"M12 19V5",key:"x0mq9r"}]],xe=L("ArrowUp",Te);/**
|
||
* @license lucide-react v0.475.0 - ISC
|
||
*
|
||
* This source code is licensed under the ISC license.
|
||
* See the LICENSE file in the root directory of this source tree.
|
||
*/const Oe=[["path",{d:"m9 18 6-6-6-6",key:"mthhwq"}]],Fe=L("ChevronRight",Oe);/**
|
||
* @license lucide-react v0.475.0 - ISC
|
||
*
|
||
* This source code is licensed under the ISC license.
|
||
* See the LICENSE file in the root directory of this source tree.
|
||
*/const Ie=[["circle",{cx:"9",cy:"12",r:"1",key:"1vctgf"}],["circle",{cx:"9",cy:"5",r:"1",key:"hp0tcf"}],["circle",{cx:"9",cy:"19",r:"1",key:"fkjjf6"}],["circle",{cx:"15",cy:"12",r:"1",key:"1tmaij"}],["circle",{cx:"15",cy:"5",r:"1",key:"19l28e"}],["circle",{cx:"15",cy:"19",r:"1",key:"f4zoj3"}]],Le=L("GripVertical",Ie);/**
|
||
* @license lucide-react v0.475.0 - ISC
|
||
*
|
||
* This source code is licensed under the ISC license.
|
||
* See the LICENSE file in the root directory of this source tree.
|
||
*/const Me=[["rect",{width:"18",height:"18",x:"3",y:"3",rx:"2",key:"afitv7"}],["path",{d:"M15 3v18",key:"14nvp0"}],["path",{d:"m8 9 3 3-3 3",key:"12hl5m"}]],De=L("PanelRightClose",Me);/**
|
||
* @license lucide-react v0.475.0 - ISC
|
||
*
|
||
* This source code is licensed under the ISC license.
|
||
* See the LICENSE file in the root directory of this source tree.
|
||
*/const Ae=[["rect",{width:"18",height:"18",x:"3",y:"3",rx:"2",key:"afitv7"}],["path",{d:"M15 3v18",key:"14nvp0"}],["path",{d:"m10 15-3-3 3-3",key:"1pgupc"}]],Ke=L("PanelRightOpen",Ae);/**
|
||
* @license lucide-react v0.475.0 - ISC
|
||
*
|
||
* This source code is licensed under the ISC license.
|
||
* See the LICENSE file in the root directory of this source tree.
|
||
*/const Ue=[["path",{d:"M6 18H4a2 2 0 0 1-2-2v-5a2 2 0 0 1 2-2h16a2 2 0 0 1 2 2v5a2 2 0 0 1-2 2h-2",key:"143wyd"}],["path",{d:"M6 9V3a1 1 0 0 1 1-1h10a1 1 0 0 1 1 1v6",key:"1itne7"}],["rect",{x:"6",y:"14",width:"12",height:"8",rx:"1",key:"1ue0tg"}]],Be=L("Printer",Ue);/**
|
||
* @license lucide-react v0.475.0 - ISC
|
||
*
|
||
* This source code is licensed under the ISC license.
|
||
* See the LICENSE file in the root directory of this source tree.
|
||
*/const He=[["path",{d:"M3 12a9 9 0 1 0 9-9 9.75 9.75 0 0 0-6.74 2.74L3 8",key:"1357e3"}],["path",{d:"M3 3v5h5",key:"1xhq8a"}]],oe=L("RotateCcw",He),K=[{key:"info",defaultTitle:"基本信息",kind:"info",fixed:!0},{key:"education",defaultTitle:"教育经历",kind:"edu",fixed:!0},{key:"skills",defaultTitle:"核心技能",kind:"text"},{key:"projects",defaultTitle:"项目经历",kind:"list",types:["竞赛","科研","实习实践"]},{key:"certs",defaultTitle:"证书与荣誉",kind:"list",types:["荣誉惩处","证书技能"]},{key:"campus",defaultTitle:"在校经历",kind:"list",types:["学生工作","志愿公益"]},{key:"activity",defaultTitle:"文体活动",kind:"list",types:["文体活动"]},{key:"other",defaultTitle:"其他经历",kind:"list"},{key:"self",defaultTitle:"自我评价",kind:"text",fixed:!0}],A={skills:{text:`程序设计:熟悉 Python 与 C/C++,掌握常用数据结构与算法,能独立完成中小型工具与脚本开发。
|
||
网络安全:熟悉常见 Web 漏洞原理(SQL 注入、XSS、CSRF 等)与防护方案,掌握 Burp Suite、Nmap、Wireshark 等常用工具。
|
||
网络基础:熟悉 TCP/IP 协议栈与交换路由基础配置,理解 VLAN、NAT、ACL 等核心技术。
|
||
运维基础:熟悉 Linux 常用操作与 Shell 脚本,了解 Docker 容器化部署与 Nginx 服务配置。`},campus:{items:[{title:"校图书馆学生助理",subtitle:"读者服务岗",date:"2024.9 - 2025.6",desc:"负责书库整理与借阅服务,协助开展入馆培训与阅读推广活动,累计服务读者千余人次。培养了责任意识与服务意识,锻炼了多任务时间管理能力。"},{title:"院学生会宣传部干事",subtitle:"平面设计与文案",date:"2023.9 - 2024.6",desc:"参与学院活动的海报设计与推文撰写,负责活动现场的后勤与设备保障。锻炼了审美表达、协作沟通与临场应变能力。"}]},self:{text:"性格沉稳踏实,做事有计划性,习惯提前预判风险并准备预案;学习能力强,能快速上手新技术与工具;责任心强,注重细节与条理,凡事有始有终,能独立推进任务并在压力下保持稳定输出。"}};function H(){return{version:2,template:"tech",accent:"#3056d3",fontScale:1,density:"normal",onePage:!1,sections:K.map(i=>({key:i.key,title:i.defaultTitle,enabled:!0,kind:i.kind,types:i.types,...i.key==="skills"?{text:A.skills.text}:{},...i.key==="campus"?{items:A.campus.items}:{},...i.key==="self"?{text:A.self.text}:{}}))}}function q(i){const h=H();if(!i||typeof i!="object")return h;const u=i,C=Array.isArray(u.sections)?u.sections:[],g=h.sections.map(r=>{var w;const a=C.find(P=>P.key===r.key),_=K.find(P=>P.key===r.key),j={...r,...a??{},enabled:(a==null?void 0:a.enabled)??!0,title:(a==null?void 0:a.title)??(_==null?void 0:_.defaultTitle)??r.title,kind:_?r.kind:(a==null?void 0:a.kind)??r.kind,types:(_==null?void 0:_.types)??(a==null?void 0:a.types)};return r.key==="skills"&&j.text==null&&(j.text=A.skills.text),r.key==="campus"&&!((w=j.items)!=null&&w.length)&&(j.items=A.campus.items),r.key==="self"&&j.text==null&&(j.text=A.self.text),j}),c=new Set(["awards","competition","practice","research"]);for(const r of C)c.has(r.key)||g.some(a=>a.key===r.key)||g.push({key:r.key,title:r.title||r.key,enabled:r.enabled??!0,kind:"text",text:""});return{version:2,template:u.template??"tech",accent:u.accent??"#3056d3",fontScale:Math.min(1.2,Math.max(.8,u.fontScale??1)),density:u.density??"normal",onePage:u.onePage??!1,sections:g}}function We(){return K.filter(i=>i.types).flatMap(i=>i.types)}function qe(i){const h=[i.organizer,i.level,i.award_grade].filter(C=>C!=null&&C!=="").map(String).join(" · "),u=[i.result,i.description].filter(C=>C!=null&&C!=="").map(String).join(" — ");return{title:i.title,subtitle:h||void 0,date:i.start_date??i.created_at.slice(0,10),desc:u||void 0,fromRecord:i.id}}function pe(i,h){var c;const u=[],C=We(),g=new Set;for(const r of h.sections){if(!r.enabled)continue;const a=K.find(m=>m.key===r.key);if(r.key==="info"){u.push({key:r.key,title:r.title,kind:"info",hiddenFields:r.hiddenFields??[]});continue}if(r.key==="self"||r.kind==="text"){const m=r.text??"";if(!m.trim())continue;u.push({key:r.key,title:r.title,kind:"text",text:m});continue}const _=new Set(r.excluded??[]);let j=[];const w=a==null?void 0:a.types;w?j=i.filter(m=>w.includes(m.type_name)&&m.status!=="draft"&&!_.has(m.id)&&!g.has(m.id)):j=i.filter(m=>m.status!=="draft"&&!_.has(m.id)&&!g.has(m.id)&&!C.includes(m.type_name));const P=new Map((r.itemOrder??[]).map((m,v)=>[m,v])),k=[];for(const m of j){const v={itemKey:"r"+m.id,...qe(m),...((c=r.overrides)==null?void 0:c[String(m.id)])??{}};k.push({...v,_ord:P.get(v.itemKey)??9999}),g.add(m.id)}for(const m of r.items??[]){const v=m.id??"c"+(r.items??[]).indexOf(m);k.push({itemKey:v,...m,_ord:P.get(v)??9999})}k.sort((m,v)=>m._ord-v._ord||(v.date??"").localeCompare(m.date??"")),k.length&&u.push({key:r.key,title:r.title,kind:"list",items:k.map(m=>{const{_ord:v,...d}=m;return d})})}return u}const he=[{key:"tech",name:"互联网技术风",desc:"品牌色标题 + 左侧色条,紧凑现代"},{key:"minimal",name:"极简风",desc:"灰色大写字距标题,大量留白"},{key:"classic",name:"经典风",desc:"黑色衬线标题 + 通栏分隔线,正式通用"}],ue=["#3056d3","#0f766e","#7c3aed","#c2410c","#0e7490","#1f2937"],z=i=>String(i??"").replace(/&/g,"&").replace(/</g,"<").replace(/>/g,">");function Ve(i,h,u,C){var F,s,x;const g=u.fontScale,c=o=>(o*g).toFixed(1)+"pt",r=u.accent,a=h,_={classic:"font-size:"+c(14)+";color:#111;border-bottom:1.5pt solid #333;padding-bottom:3pt;margin:14pt 0 7pt",tech:"font-size:"+c(14)+";color:"+r+";border-bottom:1pt solid "+r+";padding-bottom:3pt;margin:14pt 0 7pt",minimal:"font-size:"+c(11.5)+";color:#555;letter-spacing:1.5pt;text-transform:uppercase;border-bottom:0.75pt solid #e0e0e0;padding-bottom:3pt;margin:14pt 0 7pt"},j=u.template==="tech"?r:"#111",w=[a.school,a.college,a.major,a.degree].filter(o=>o!=="").map(o=>z(o)).join(" · "),P=[a.phone,a.email,a.homepage].filter(o=>o!=="").map(o=>z(o)).join(" · "),k=(((F=u.header)==null?void 0:F.showPhoto)??!0)&&C&&a.photoUrl?'<td style="width:'+(120*g).toFixed(0)+'px;text-align:right;vertical-align:top"><img src="'+z(a.photoUrl)+'" alt="证件照" width="'+Math.round(120*g)+'" height="'+Math.round(160*g)+'" style="width:'+Math.round(120*g)+"px;height:"+Math.round(160*g)+'px" /></td>':"",m='<table style="width:100%;border-collapse:collapse"><tr><td style="vertical-align:top"><div style="font-size:'+c(20)+";font-weight:bold;color:"+j+'">'+z(a.name||"个人简历")+"</div>"+((((s=u.header)==null?void 0:s.showSchool)??!0)&&w?'<div style="color:#555;font-size:'+c(11)+';margin-top:3pt">'+w+"</div>":"")+((((x=u.header)==null?void 0:x.showContact)??!0)&&P?'<div style="color:#555;font-size:'+c(11)+';margin-top:2pt">'+P+"</div>":"")+"</td>"+k+"</tr></table>",v=o=>'<table style="width:100%;border-collapse:collapse;margin-top:'+(u.density==="compact"?4:7)+'pt"><tr><td style="font-weight:bold;font-size:'+c(12)+'">'+z(o.title)+'</td><td style="text-align:right;color:#666;font-size:'+c(10.5)+';white-space:nowrap">'+z(o.date??"")+"</td></tr></table>"+(o.subtitle?'<div style="color:#666;font-size:'+c(10.5)+'">'+z(o.subtitle)+"</div>":"")+(o.desc?'<div style="color:#444;font-size:'+c(11)+';line-height:1.55;margin-top:2pt">'+z(o.desc)+"</div>":""),d=i.map(o=>{let S="";if(o.kind==="edu"){const M=[["学校",a.school??""],["专业",a.major??""],["学制",a.eduLength??""],["学历",a.degree??""],["入学",a.eduStart??""],["毕业",a.eduEnd??""]].filter(b=>b[1]!=="");S='<table style="width:100%;border-collapse:collapse;font-size:'+c(12)+'">'+M.map(b=>'<tr><td style="width:80px;padding:3px 6px;color:#555">'+z(b[0])+'</td><td style="padding:3px 6px">'+z(b[1])+"</td></tr>").join("")+"</table>"+(a.majorCourses?'<div style="margin-top:6pt;font-size:'+c(11.5)+';line-height:1.6"><b>主修课程:</b>'+z(a.majorCourses)+"</div>":"")}else if(o.kind==="info"){const M=[["name","姓名",a.name??""],["gender","性别",a.gender??""],["birth","出生年月",a.birth??""],["nation","民族",a.nation??""],["native","籍贯",a.native??""],["political","政治面貌",a.political??""],["className","班级",a.className??""],["studentId","学号",a.studentId??""],["degree","学历",a.degree??""],["phone","手机",a.phone??""],["email","邮箱",a.email??""]].filter(b=>b[2]!==""&&!(o.hiddenFields??[]).includes(b[0]));S='<table style="width:100%;border-collapse:collapse;font-size:'+c(12)+'">'+M.map((b,I)=>(I%2===0?"<tr>":"")+'<td style="width:80px;padding:3px 6px;color:#555">'+z(b[1])+'</td><td style="padding:3px 6px">'+z(b[2])+"</td>"+(I%2===1?"</tr>":"")).join("")+"</table>"}else o.kind==="list"?S="<div>"+(o.items??[]).map(v).join("")+"</div>":S='<p style="font-size:'+c(12)+';line-height:1.7;margin:0;text-align:justify">'+z(o.text??"").replace(/\n/g,"<br/>")+"</p>";return'<div style="'+_[u.template]+'">'+z(o.title)+"</div>"+S}).join("");return'<html xmlns:o="urn:schemas-microsoft-com:office:office" xmlns:w="urn:schemas-microsoft-com:office:word"><head><meta charset="utf-8"><title>'+z(a.name||"个人简历")+'</title><!--[if gte mso 9]><xml><w:WordDocument><w:View>Print</w:View></w:WordDocument></xml><![endif]--></head><body style="font-family:Calibri,SimSun,sans-serif;margin:36pt;color:#222">'+m+d+"</body></html>"}const $e=Object.freeze(Object.defineProperty({__proto__:null,ACCENT_CHOICES:ue,RESUME_SECTION_DEFS:K,TEMPLATES:he,assembleSections:pe,defaultResumeConfig:H,migrateResumeConfig:q,resumeToWordHtml:Ve},Symbol.toStringTag,{value:"Module"})),Ge={姓名:"name",性别:"gender",���生年月:"birth",民族:"nation",籍贯:"native",政治面貌:"political",班级:"className",学号:"studentId",手机:"phone",邮箱:"email"},Qe=[["name","姓名"],["gender","性别"],["birth","出生年月"],["nation","民族"],["native","籍贯"],["political","政治面貌"],["className","班级"],["studentId","学号"],["phone","手机"],["email","邮箱"]];function ce(i){const h=/^(\d{4})-(\d{1,2})/.exec(i??"");return h?h[1]+"."+Number(h[2]):i??""}function O({html:i,onCommit:h,className:u}){const C=i.replace(/&/g,"&").replace(/</g,"<").replace(/>/g,">");return e.jsx("span",{contentEditable:!0,suppressContentEditableWarning:!0,spellCheck:!1,className:"outline-none break-words rounded-sm transition-shadow focus:shadow-[0_0_0_1.5px_rgba(48,86,211,0.5)] cursor-text "+(u??""),dangerouslySetInnerHTML:{__html:C},onBlur:g=>{const c=(g.currentTarget.textContent??"").trim();c!==i&&h(c)}})}function et(){var J,Y,Z,X,ee,te;const i=we(),h=se({queryKey:["profile"],queryFn:ze}),u=se({queryKey:["resume-records"],queryFn:()=>Re({page:1,page_size:500})}),[C,g]=T.useState(null),[c,r]=T.useState(""),[a,_]=T.useState(!0),[j,w]=T.useState(new Set),[P,k]=T.useState(1),m=T.useRef(null),v=T.useRef(null);T.useEffect(()=>{var l,n;const t=(l=h.data)==null?void 0:l.content;t&&(g(q(t.resume)),r(((n=t.info)==null?void 0:n.selfIntro)??""))},[h.data]);const d={...((Y=(J=h.data)==null?void 0:J.content)==null?void 0:Y.info)??{}},F=((Z=u.data)==null?void 0:Z.items)??[],s=C??H(),x={...d,selfIntro:c},o=[ce(d.eduStart),ce(d.eduEnd)].filter(Boolean).join("-"),S=T.useMemo(()=>pe(F,s),[F,s]),M=(t,l)=>g(n=>{if(!n)return n;const f=[...n.sections],N=t+l;return N<0||N>=f.length?n:([f[t],f[N]]=[f[N],f[t]],{...n,sections:f})}),b=t=>{g(t),D({info:{...d,selfIntro:c},resume:t}).catch(l=>i("error",l.message))},I=t=>{g(l=>{const n=l??s,f=n.sections.map(p=>{var y;if(p.key!==t.secKey)return p;if(t.field==="text")return{...p,text:t.value};if(t.fromRecord!=null){const E={...((y=p.overrides)==null?void 0:y[t.fromRecord])??{},[t.field]:t.value};return{...p,overrides:{...p.overrides??{},[t.fromRecord]:E}}}if(t.itemIdx!=null&&p.items){const E=[...p.items];return E[t.itemIdx]={...E[t.itemIdx],[t.field]:t.value},{...p,items:E}}return p}),N={...n,sections:f};return D({info:{...d,selfIntro:c},resume:N}).catch(p=>i("error",p.message)),N})},W=(t,l)=>{D({info:{...x,[t]:l}}).then(()=>h.refetch()).catch(n=>i("error",n.message))};T.useEffect(()=>{if(!s.onePage){k(1);return}const t=m.current;if(!t)return;const l=1043,n=t.scrollHeight;k(n>l?Math.max(.7,l/n):1)},[s.onePage,s.fontScale,s.density,S]);const G=s.fontScale*(s.onePage?P:1),fe=()=>{_e(()=>Promise.resolve().then(()=>$e),void 0).then(function(t){const l=t.resumeToWordHtml(S,x,s,d.photoUrl),n=new Blob(["\uFEFF"+l],{type:"application/msword"}),f=URL.createObjectURL(n),N=document.createElement("a");N.href=f,N.download=(d.name||"个人简历")+".doc",N.click(),setTimeout(()=>URL.revokeObjectURL(f),6e4),i("success","Word 文档已导出")})},Q=t=>{const l="custom_"+Date.now();b({...s,sections:[...s.sections,t==="text"?{key:l,title:"自定义板块",enabled:!0,kind:"text",text:""}:{key:l,title:"自定义经历",enabled:!0,kind:"list",items:[]}]}),w(n=>new Set(n).add(l))},ge=t=>{var l,n;return((n=(l=K.find(f=>f.key===t))==null?void 0:l.types)==null?void 0:n.join(" / "))??"固定板块"},[ye,U]=T.useState(!1),be=()=>{const t=H();g(t),w(new Set),D({info:{...d,selfIntro:c},resume:t}).then(()=>h.refetch()).then(()=>{U(!1),i("success","简历已初始化为默认模板")}).catch(l=>i("error",l.message))},je=()=>{const t=H();t.sections=t.sections.map(l=>({...l,text:l.kind==="text"?"":l.text,items:l.kind==="list"?[]:l.items,overrides:{},excluded:[],itemOrder:[],hiddenFields:[]})),g(t),w(new Set),D({info:{...d,selfIntro:c},resume:t}).then(()=>h.refetch()).then(()=>{U(!1),i("success","简历数据已彻底清空")}).catch(l=>i("error",l.message))},ke=async()=>{var t,l;try{const[n]=await Promise.all([h.refetch(),u.refetch()]),f=(t=n.data)==null?void 0:t.content;f&&(g(q(f.resume)),r(((l=f.info)==null?void 0:l.selfIntro)??"")),i("success","已重新载入最新数据")}catch(n){i("error",n.message)}},ve=()=>{const t=new Blob([JSON.stringify(s,null,2)],{type:"application/json"}),l=URL.createObjectURL(t),n=document.createElement("a");n.href=l,n.download="简历配置.json",n.click(),setTimeout(()=>URL.revokeObjectURL(l),6e4),i("success","简历配置已导出")},Ne=t=>{t&&t.text().then(l=>{try{const n=q(JSON.parse(l));b(n),i("success","配置已导入")}catch{i("error","配置文件格式不正确")}})};return e.jsxs("div",{className:"mx-auto max-w-[1280px] px-3 py-4 sm:px-6 sm:py-5",children:[e.jsxs("div",{className:"no-print mb-4 flex flex-wrap items-center justify-between gap-2",children:[e.jsx("h2",{className:"text-[15px] font-semibold text-ink-1",children:"我的简历"}),e.jsxs("div",{className:"flex flex-wrap gap-2",children:[e.jsxs(R,{variant:"secondary",onClick:()=>_(t=>!t),children:[a?e.jsx(De,{size:13}):e.jsx(Ke,{size:13}),a?"收起设置":"展开设置"]}),e.jsxs(R,{variant:"secondary",onClick:()=>void ke(),children:[e.jsx(Pe,{size:13})," 重新载入"]}),e.jsxs(R,{variant:"ghost",className:"text-danger hover:bg-danger-subtle",onClick:()=>U(!0),children:[e.jsx(oe,{size:13})," 初始化简历"]}),e.jsxs(R,{variant:"secondary",onClick:fe,children:[e.jsx(Ce,{size:13})," 导出 Word"]}),e.jsxs(R,{variant:"primary",onClick:()=>window.print(),children:[e.jsx(Be,{size:13})," 打印 / PDF"]})]})]}),e.jsxs("div",{className:"grid gap-4 "+(a?"lg:grid-cols-[1fr_340px]":"grid-cols-1"),children:[e.jsxs("div",{children:[e.jsx("div",{className:"print-sheet mx-auto w-full max-w-[794px] rounded-lg border border-line bg-white shadow-card",style:{minHeight:s.onePage?1123:void 0},children:e.jsxs("div",{ref:m,className:"min-w-0 overflow-x-hidden p-5 sm:p-10 resume-tpl-"+s.template,style:{zoom:G,"--accent":s.accent},children:[e.jsxs("div",{className:"mb-6 flex items-start justify-between gap-4 sm:gap-6",children:[e.jsxs("div",{className:"min-w-0 flex-1",children:[e.jsx("h1",{className:"text-[26px] font-bold leading-tight "+(s.template==="tech"?"text-[var(--accent)]":"text-neutral-900"),children:d.name||"姓名"}),(((X=s.header)==null?void 0:X.showSchool)??!0)&&e.jsx("div",{className:"mt-1.5 text-[12.5px] text-neutral-500",children:[d.school,d.college,d.major,d.degree].filter(Boolean).join(" · ")||"完善个人信息后自动展示"}),(((ee=s.header)==null?void 0:ee.showContact)??!0)&&e.jsx("div",{className:"mt-1 text-[12px] text-neutral-500",children:[d.phone,d.email,d.homepage].filter(Boolean).join(" · ")})]}),(((te=s.header)==null?void 0:te.showPhoto)??!0)&&d.photoUrl&&e.jsx("img",{src:d.photoUrl,alt:"证件照",className:"h-[110px] w-[82px] rounded border border-neutral-200 object-cover"})]}),S.map(t=>{var l;return e.jsxs("div",{className:"mb-5 r-sec",children:[e.jsx("div",{className:"r-sec-title mb-2.5 text-[14px] font-bold text-neutral-900",children:e.jsx(O,{html:t.title,onCommit:n=>I({secKey:t.key,field:"title",value:n})})}),t.kind==="edu"?e.jsxs("div",{children:[e.jsxs("div",{className:"flex flex-wrap items-baseline justify-between gap-x-4 gap-y-0.5 text-[13px]",children:[e.jsx("span",{className:"num shrink-0 text-neutral-500",children:e.jsx(O,{html:o,onCommit:n=>{const f=/(\d{4})\.(\d{1,2})\s*[-—~至]\s*(\d{4})\.(\d{1,2})/.exec(n);if(!f){i("error","时间格式:2023.9-2027.6");return}D({info:{...x,eduStart:f[1]+"-"+f[2].padStart(2,"0"),eduEnd:f[3]+"-"+f[4].padStart(2,"0")}}).then(()=>h.refetch()).catch(N=>i("error",N.message))}})}),e.jsx("span",{className:"min-w-0 font-semibold text-neutral-900",children:e.jsx(O,{html:d.school??"",onCommit:n=>W("school",n)})}),e.jsxs("span",{className:"shrink-0 text-neutral-600",children:[e.jsx(O,{html:d.major??"",onCommit:n=>W("major",n)}),d.degree?e.jsxs("span",{children:[" | ",e.jsx(O,{html:d.degree,onCommit:n=>W("degree",n)})]}):null]})]}),d.majorCourses&&e.jsxs("p",{className:"mt-1.5 text-[12px] leading-relaxed text-justify text-neutral-700",children:[e.jsx("b",{children:"主修课程:"}),e.jsx(O,{html:d.majorCourses,onCommit:n=>W("majorCourses",n)})]})]}):t.kind==="info"?e.jsx("div",{className:"grid grid-cols-1 gap-x-8 gap-y-1 text-[12.5px] sm:grid-cols-2",children:[["姓名",d.name],["性别",d.gender],["出生年月",d.birth],["民族",d.nation],["籍贯",d.native],["政治面貌",d.political],["班级",d.className],["学号",d.studentId],["手机",d.phone],["邮箱",d.email]].filter(n=>n[1]&&!(t.hiddenFields??[]).includes(Ge[n[0]])).map(n=>e.jsxs("div",{className:"flex gap-2",children:[e.jsx("span",{className:"w-16 shrink-0 text-neutral-500",children:n[0]}),e.jsx("span",{children:n[1]})]},n[0]))}):t.kind==="text"?e.jsx("p",{className:"whitespace-pre-wrap text-justify text-neutral-700 "+(s.density==="compact"?"":"leading-relaxed"),children:e.jsx(O,{html:t.text??"",onCommit:n=>I({secKey:t.key,field:"text",value:n})})}):e.jsx("div",{className:s.density==="compact"?"flex flex-col gap-1.5":"flex flex-col gap-3",children:(l=t.items)==null?void 0:l.map((n,f)=>e.jsxs("div",{children:[e.jsxs("div",{className:"flex items-baseline justify-between gap-3",children:[e.jsx("span",{className:"text-[13px] font-semibold text-neutral-900 r-item-title",children:e.jsx(O,{html:n.title,onCommit:N=>I({secKey:t.key,field:"title",value:N,itemIdx:f,fromRecord:n.fromRecord})})}),e.jsx("span",{className:"num shrink-0 text-[11.5px] text-neutral-500",children:e.jsx(O,{html:n.date??"",onCommit:N=>I({secKey:t.key,field:"date",value:N,itemIdx:f,fromRecord:n.fromRecord})})})]}),n.subtitle&&e.jsx("div",{className:"text-[12px] text-neutral-600",children:n.subtitle}),n.desc&&e.jsx("p",{className:"text-justify text-[12px] text-neutral-500 "+(s.density==="compact"?"":"mt-0.5"),children:e.jsx(O,{html:n.desc,onCommit:N=>I({secKey:t.key,field:"desc",value:N,itemIdx:f,fromRecord:n.fromRecord})})})]},n.itemKey??(n.title??"")+f))})]},t.key)})]})}),s.onePage&&e.jsxs("div",{className:"no-print mt-2 text-center text-[11.5px] text-ink-3",children:["一页限定已启用:内容自动缩放 ",Math.round(G*100),"% 以适配单页 A4"]})]}),a&&e.jsxs("div",{className:"no-print flex flex-col gap-4 lg:sticky lg:top-4 lg:max-h-[calc(100vh-2rem)] lg:self-start lg:overflow-y-auto lg:pr-1",children:[e.jsxs(ae,{children:[e.jsx(le,{title:"模板与风格"}),e.jsxs(re,{className:"flex flex-col gap-3",children:[e.jsx("div",{className:"grid grid-cols-1 gap-2",children:he.map(t=>e.jsxs("button",{className:"rounded-md border px-3 py-2 text-left transition-all "+(s.template===t.key?"border-brand bg-brand-subtle":"border-line bg-surface hover:border-line-strong"),onClick:()=>b({...s,template:t.key}),children:[e.jsx("div",{className:"text-[12.5px] font-semibold "+(s.template===t.key?"text-brand-text":"text-ink-1"),children:t.name}),e.jsx("div",{className:"text-[11px] text-ink-3",children:t.desc})]},t.key))}),e.jsxs("div",{className:"grid grid-cols-2 gap-2",children:[e.jsx(B,{label:"主题色",children:e.jsx("div",{className:"flex flex-wrap gap-1.5 pt-1",children:ue.map(t=>e.jsx("button",{"aria-label":"主题色 "+t,className:"size-5 rounded-full border-2 transition-transform "+(s.accent===t?"scale-110 border-ink-1":"border-transparent"),style:{backgroundColor:t},onClick:()=>b({...s,accent:t})},t))})}),e.jsx(B,{label:"字号",children:e.jsx(ne,{value:String(s.fontScale),onChange:t=>b({...s,fontScale:Number(t.target.value)}),options:[{value:"0.9",label:"小"},{value:"1",label:"标准"},{value:"1.1",label:"大"}]})})]}),e.jsx(B,{label:"头部布局",children:e.jsx("div",{className:"flex flex-wrap gap-1.5 pt-1",children:[["showPhoto","证件照"],["showContact","联系行"],["showSchool","学校行"]].map(t=>{var n;const l=((n=s.header)==null?void 0:n[t[0]])??!0;return e.jsx("button",{className:"rounded-md border px-2.5 py-1 text-[11.5px] transition-colors "+(l?"border-brand bg-brand-subtle text-brand-text":"border-line bg-surface text-ink-3"),onClick:()=>b({...s,header:{...s.header,[t[0]]:!l}}),children:t[1]},t[0])})})}),e.jsxs("div",{className:"grid grid-cols-2 gap-2",children:[e.jsx(B,{label:"间距",children:e.jsx(ne,{value:s.density,onChange:t=>b({...s,density:t.target.value}),options:[{value:"compact",label:"紧凑"},{value:"normal",label:"标准"},{value:"relaxed",label:"宽松"}]})}),e.jsx(B,{label:"单页限定",children:e.jsx("button",{className:"flex h-9 w-full items-center justify-center gap-1.5 rounded-md border text-[12px] transition-colors "+(s.onePage?"border-brand bg-brand-subtle text-brand-text":"border-line bg-surface text-ink-2"),onClick:()=>b({...s,onePage:!s.onePage}),children:s.onePage?"已开启":"已关闭"})})]}),e.jsxs("div",{className:"grid grid-cols-2 gap-2 border-t border-line pt-3",children:[e.jsx(R,{size:"sm",variant:"secondary",onClick:ve,children:"导出配置"}),e.jsxs("label",{className:"flex h-8 cursor-pointer items-center justify-center rounded-md border border-line bg-surface text-[12px] text-ink-2 transition-colors hover:border-line-strong",children:["导入配置",e.jsx("input",{type:"file",accept:"application/json",className:"hidden",onChange:t=>{var l;Ne((l=t.target.files)==null?void 0:l[0]),t.target.value=""}})]})]})]})]}),e.jsxs(ae,{children:[e.jsx(le,{title:"板块布局",extra:e.jsx("span",{className:"text-[11px] text-ink-3",children:"拖动排序 · 点击预览可改内容"})}),e.jsx(re,{className:"p-0",children:e.jsxs("div",{className:"flex flex-col divide-y divide-line",children:[s.sections.map((t,l)=>{var N;const n=j.has(t.key),f=t.kind==="info"?"固定":t.kind==="text"?"文本":t.kind==="edu"?"教育":"记录";return e.jsxs("div",{draggable:!0,onDragStart:()=>{v.current=t.key},onDragOver:p=>p.preventDefault(),onDrop:()=>{const p=s.sections.findIndex(y=>y.key===v.current);if(p>=0&&p!==l){const y=[...s.sections],E=y.splice(p,1)[0];y.splice(l,0,E),b({...s,sections:y})}v.current=null},className:"bg-surface "+(v.current===t.key?"opacity-40":""),children:[e.jsxs("div",{className:"flex items-center gap-1 px-3 py-2",children:[e.jsx(Le,{size:13,className:"shrink-0 cursor-grab text-ink-3"}),e.jsx("input",{className:"min-w-0 flex-1 rounded-sm border border-transparent bg-transparent px-1 py-0.5 text-[12.5px] font-medium text-ink-1 hover:border-line focus:border-brand focus:outline-none",value:t.title,onChange:p=>b({...s,sections:s.sections.map(y=>y.key===t.key?{...y,title:p.target.value}:y)})}),e.jsx("button",{className:"rounded p-1 text-ink-3 hover:text-ink-1 disabled:opacity-30","aria-label":"上移",disabled:l===0,onClick:()=>M(l,-1),children:e.jsx(xe,{size:12})}),e.jsx("button",{className:"rounded p-1 text-ink-3 hover:text-ink-1 disabled:opacity-30","aria-label":"下移",disabled:l===s.sections.length-1,onClick:()=>M(l,1),children:e.jsx(me,{size:12})}),e.jsx("button",{className:"ml-0.5 rounded-sm border px-1.5 py-0.5 text-[11px] transition-colors "+(t.enabled?"border-brand/40 bg-brand-subtle text-brand-text":"border-line bg-surface-2 text-ink-3"),onClick:()=>b({...s,sections:s.sections.map(p=>p.key===t.key?{...p,enabled:!p.enabled}:p)}),children:t.enabled?"显示":"隐藏"}),e.jsx("button",{className:"rounded p-1 text-ink-3 hover:text-ink-1","aria-label":"展开编辑",onClick:()=>w(p=>{const y=new Set(p);return y.has(t.key)?y.delete(t.key):y.add(t.key),y}),children:e.jsx(Fe,{size:13,className:"transition-transform "+(n?"rotate-90":"")})})]}),n&&e.jsx("div",{className:"border-t border-line bg-surface-2 px-3 py-2.5",children:t.kind==="text"?e.jsx(de,{rows:4,value:t.text??"",placeholder:"输入该板块内容…",onChange:p=>b({...s,sections:s.sections.map(y=>y.key===t.key?{...y,text:p.target.value}:y)})}):t.kind==="info"?e.jsxs("div",{className:"flex flex-col gap-1",children:[e.jsx("div",{className:"mb-0.5 text-[11px] text-ink-3",children:"勾选 = 在基本信息中显示"}),Qe.map(p=>e.jsxs("label",{className:"flex cursor-pointer items-center gap-2 text-[12px]",children:[e.jsx("input",{type:"checkbox",className:"size-3.5",checked:!(t.hiddenFields??[]).includes(p[0]),onChange:()=>b({...s,sections:s.sections.map(y=>{if(y.key!==t.key)return y;const E=new Set(y.hiddenFields??[]);return E.has(p[0])?E.delete(p[0]):E.add(p[0]),{...y,hiddenFields:[...E]}})})}),p[1]]},p[0]))]}):t.kind==="list"?e.jsx(Je,{cfg:s,section:t,records:F,persist:b,sectionTypes:ge(t.key)}):e.jsx("p",{className:"text-[11.5px] text-ink-3",children:"该板块内容来自「个人信息」页与记录数据。"})}),e.jsxs("div",{className:"px-3 pb-1.5 text-[10.5px] text-ink-3",children:[f,(N=t.types)!=null&&N.length?" · "+t.types.join("/"):""]})]},t.key)}),e.jsxs("div",{className:"grid grid-cols-2 gap-2 p-3",children:[e.jsxs(R,{size:"sm",variant:"secondary",onClick:()=>Q("text"),children:[e.jsx($,{size:13})," 文本板块"]}),e.jsxs(R,{size:"sm",variant:"secondary",onClick:()=>Q("list"),children:[e.jsx($,{size:13})," 列表板块"]})]})]})})]})]})]}),e.jsx(Se,{open:ye,onClose:()=>U(!1),width:440,title:"初始化简历",footer:e.jsxs(e.Fragment,{children:[e.jsx(R,{variant:"ghost",onClick:()=>U(!1),children:"取消"}),e.jsx(R,{variant:"secondary",onClick:je,children:"彻底清空"}),e.jsxs(R,{variant:"primary",onClick:be,children:[e.jsx(oe,{size:13})," 恢复默认模板"]})]}),children:e.jsxs("div",{className:"text-[12.5px] leading-relaxed text-ink-2",children:[e.jsx("b",{children:"恢复默认模板"}),":清除个性化修改,恢复默认板块与示例内容。",e.jsxs("div",{className:"mt-1",children:[e.jsx("b",{children:"彻底清空"}),":保留板块结构,内容全部置空,从零开始。"]}),e.jsx("div",{className:"mt-2 text-ink-3",children:"两种操作都不影响记录数据与个人信息。"}),e.jsx("div",{className:"mt-2 text-ink-3",children:"记录数据与个人信息不受影响,随时可重新修改。"})]})})]})}function Je({cfg:i,section:h,records:u,persist:C,sectionTypes:g}){const[c,r]=T.useState(null),a=new Set(h.excluded??[]),_=u.filter(s=>(h.types??[]).includes(s.type_name)&&s.status!=="draft").sort((s,x)=>(x.start_date??x.created_at).localeCompare(s.start_date??s.created_at)),j=h.items??[],w=s=>C({...i,sections:i.sections.map(x=>x.key===h.key?{...x,...s}:x)}),P=s=>{const x=new Set(h.excluded??[]);x.has(s)?x.delete(s):x.add(s),w({excluded:[...x]})},k=[...h.itemOrder??[]],m=new Set(k),v=new Map;_.forEach(s=>{const x="r"+s.id;v.set(x,{type:"record",r:s}),m.has(x)||(k.push(x),m.add(x))}),j.forEach((s,x)=>{const o=s.id??"c"+x;v.set(o,{type:"custom",c:s,idx:x}),m.has(o)||(k.push(o),m.add(o))});const d=(s,x)=>{const o=k.indexOf(s),S=o+x;o<0||S<0||S>=k.length||([k[o],k[S]]=[k[S],k[o]],w({itemOrder:k}))},F=({k:s})=>e.jsxs("span",{className:"flex shrink-0 flex-col",children:[e.jsx("button",{className:"text-ink-3 hover:text-ink-1","aria-label":"上移",onClick:()=>d(s,-1),children:e.jsx(xe,{size:11})}),e.jsx("button",{className:"text-ink-3 hover:text-ink-1","aria-label":"下移",onClick:()=>d(s,1),children:e.jsx(me,{size:11})})]});return e.jsxs("div",{className:"flex flex-col gap-2.5",children:[e.jsx("div",{className:"text-[11px] text-ink-3",children:"条目排序(↑↓)· 记录勾选显隐 · 自定义条目可增删"}),k.map(s=>{const x=v.get(s);if(!x)return null;if(x.type==="record"){const o=x.r;return e.jsxs("div",{className:"flex items-center gap-2 text-[12px]",children:[e.jsx(F,{k:s}),e.jsxs("label",{className:"flex min-w-0 flex-1 cursor-pointer items-center gap-2",children:[e.jsx("input",{type:"checkbox",className:"size-3.5",checked:!a.has(o.id),onChange:()=>P(o.id)}),e.jsx("span",{className:"min-w-0 flex-1 truncate text-ink-1",children:o.title})]}),e.jsx("span",{className:"num shrink-0 text-[11px] text-ink-3",children:(o.start_date??"").slice(0,7)})]},s)}return e.jsxs("div",{className:"flex items-center gap-2 rounded-md border border-line bg-surface p-1.5 text-[12px]",children:[e.jsx(F,{k:s}),e.jsxs("span",{className:"min-w-0 flex-1 truncate text-ink-1",children:[x.c.title,e.jsxs("span",{className:"text-ink-3",children:[" · ",x.c.date??""]})]}),e.jsx("button",{className:"text-ink-3 hover:text-danger","aria-label":"删除条目",onClick:()=>w({items:j.filter((o,S)=>S!==x.idx)}),children:e.jsx(ie,{size:12})})]},s)}),e.jsxs("div",{className:"mt-1 border-t border-line pt-2",children:[e.jsxs("div",{className:"mb-1.5 flex items-center justify-between",children:[e.jsxs("span",{className:"text-[11.5px] font-medium text-ink-2",children:["自定义条目(",j.length,")"]}),e.jsxs(R,{size:"sm",variant:"ghost",onClick:()=>r({title:""}),children:[e.jsx($,{size:12})," 添加"]})]}),c&&e.jsxs("div",{className:"mb-2 rounded-md border border-line bg-surface p-2",children:[e.jsx(V,{className:"mb-1.5",placeholder:"标题",value:c.title,onChange:s=>r({...c,title:s.target.value})}),e.jsxs("div",{className:"mb-1.5 grid grid-cols-2 gap-1.5",children:[e.jsx(V,{placeholder:"副标题(单位/角色)",value:c.subtitle??"",onChange:s=>r({...c,subtitle:s.target.value})}),e.jsx(V,{placeholder:"日期(2025.9)",value:c.date??"",onChange:s=>r({...c,date:s.target.value})})]}),e.jsx(de,{rows:2,placeholder:"描述:做了什么、负责什么、学会什么",value:c.desc??"",onChange:s=>r({...c,desc:s.target.value})}),e.jsxs("div",{className:"mt-1.5 flex gap-1.5",children:[e.jsx(R,{size:"sm",variant:"primary",disabled:!c.title.trim(),onClick:()=>{c.title.trim()&&(w({items:[...j,{...c,id:"c"+Date.now()}]}),r(null))},children:"添加"}),e.jsx(R,{size:"sm",variant:"ghost",onClick:()=>r(null),children:"取消"})]})]}),j.map((s,x)=>e.jsxs("div",{className:"flex items-center gap-2 rounded-md border border-line bg-surface p-1.5 text-[12px]",children:[e.jsxs("span",{className:"min-w-0 flex-1 truncate text-ink-1",children:[s.title,e.jsxs("span",{className:"text-ink-3",children:[" · ",s.date??""]})]}),e.jsx("button",{className:"text-ink-3 hover:text-danger","aria-label":"删除条目",onClick:()=>w({items:j.filter((o,S)=>S!==x)}),children:e.jsx(ie,{size:12})})]},x)),!j.length&&!c&&e.jsx("p",{className:"text-[11.5px] text-ink-3",children:"暂无自定义条目"})]}),e.jsxs("p",{className:"text-[11px] text-ink-3",children:["「",g,"」相关条目来自你的记录数据,此处可隐藏不需要展示的条目;描述可在预览中点击直接修改。"]})]})}export{et as ResumePage};
|