基于Arduino的智能温控风扇:从传感器到PWM控制的完整实践
2026/6/3 18:39:21
大家好,我是江西某高校计算机专业大三的"代码狂魔",正在给我的CMS新闻管理系统做一次"整容手术"——添加Word一键转存功能!每次看到编辑部的妹子们手动复制Word内容到后台,图片还要一张张上传,我就心疼(主要是心疼她们的加班费都拿去喝奶茶了)
// 测试代码片段importmammothfrom"mammoth";mammoth.extractRawText({arrayBuffer:fileArrayBuffer}).then(function(result){console.log(result.value);// 纯文本内容}).done();✔️ 优点:免费、轻量
❌ 缺点:只能提取文本,丢失格式和图片
💰 价格:$199 → 超预算!PASS!
// PHP后端处理逻辑usePhpOffice\PhpWord\IOFactory;$phpWord=IOFactory::load($tempFilePath);$writer=IOFactory::createWriter($phpWord,'HTML');$writer->save('converted.html');✔️ 优点:格式保留较好
❌ 缺点:PPT/PDF支持有限
import E from 'wangeditor' import 'wangeditor/release/wangEditor.min.css' export default { data() { return { editor: null } }, mounted() { this.initEditor() }, methods: { initEditor() { this.editor = new E(this.$refs.editor) // 自定义菜单 this.editor.config.menus = [ 'head', 'bold', 'italic', 'underline', 'strikeThrough', 'foreColor', 'backColor', 'link', 'list', 'justify', 'quote', 'table', 'code', 'undo', 'redo', 'importWord' // 自定义按钮 ] // 注册自定义按钮 this.editor.config.customAlert = (s) => { console.log(s) } this.editor.config.customMenu = { importWord: { text: '导入Office', className: 'icon-import-word', callback: () => { document.getElementById('word-upload').click() } } } this.editor.create() }, async handleFileUpload(e) { const file = e.target.files[0] if (!file) return try { const formData = new FormData() formData.append('file', file) const res = await this.$http.post('/api/office/upload', formData, { headers: { 'Content-Type': 'multipart/form-data' } }) this.editor.txt.html(res.data.htmlContent) } catch (error) { console.error('文件上传失败:', error) } } } }ossClient=newOSS\OssClient(getenv('OSS_ACCESS_KEY_ID'),getenv('OSS_ACCESS_KEY_SECRET'),getenv('OSS_ENDPOINT'));$this->bucketName=getenv('OSS_BUCKET');}publicfunctionhandleUpload($file){$fileExt=strtolower(pathinfo($file['name'],PATHINFO_EXTENSION));$tempPath=$file['tmp_name'];switch($fileExt){case'doc':case'docx':return$this->processWord($tempPath);case'xls':case'xlsx':return$this->processExcel($tempPath);case'ppt':case'pptx':return$this->processPpt($tempPath);case'pdf':return$this->processPdf($tempPath);default:thrownewException("不支持的格式:$fileExt");}}privatefunctionprocessWord($filePath){$phpWord=\PhpOffice\PhpWord\IOFactory::load($filePath);$htmlWriter=new\PhpOffice\PhpWord\Writer\HTML($phpWord);// 处理图片$mediaElements=$phpWord->getMediaElements();foreach($mediaElementsas$element){$imagePath=$this->uploadImageToOSS($element['source'],$element['imageExtension']);// 替换HTML中的图片路径$htmlWriter->replaceImagePath($element['mediaIndex'],$imagePath);}$htmlContent=$htmlWriter->getContent();return['htmlContent'=>$htmlContent];}privatefunctionuploadImageToOSS($binaryData,$extension){$filename='uploads/'.uniqid().'.'.$extension;$this->ossClient->putObject($this->bucketName,$filename,$binaryData);return$this->ossClient->generatePresignedUrl($this->bucketName,$filename,3600);}// 其他格式处理方法类似...}?>文件处理流程:
前端上传 → 后端识别格式 → 调用对应解析器 → 提取内容+图片 → 图片上传OSS → 生成HTML → 返回编辑器成本控制技巧:
兼容性hack:
// 处理Mac系统差异constisMac=navigator.platform.toUpperCase().indexOf('MAC')>=0;if(isMac){// 调整某些API调用方式}这个项目让我深刻体会到——“程序员的时间都去哪了?全花在找免费替代方案上了!” 欢迎加入QQ群223813913一起交流,群里不定期分享:
(注:因篇幅限制,部分代码已简化,完整实现需要处理更多边界情况。需要详细代码可以进群@我)
安装jquery
npm install jqueryimportEfrom'wangeditor'const{$,BtnMenu,DropListMenu,PanelMenu,DropList,Panel,Tooltip}=Eimport{WordPaster}from'../../static/WordPaster/js/w'import{zyCapture}from'../../static/zyCapture/z'import{zyOffice}from'../../static/zyOffice/js/o'//zyCapture ButtonclasszyCaptureBtnextendsBtnMenu{constructor(editor){const$elem=E.$(`<div class="w-e-menu">`)super($elem,editor)}clickHandler(){window.zyCapture.setEditor(this.editor).Capture();}tryChangeActive(){this.active()}}//zyOffice ButtonclassimportWordBtnextendsBtnMenu{constructor(editor){const$elem=E.$(`<div class="w-e-menu">`)super($elem,editor)}clickHandler(){window.zyOffice.SetEditor(this.editor).api.openDoc();}tryChangeActive(){this.active()}}//zyOffice ButtonclassexportWordBtnextendsBtnMenu{constructor(editor){const$elem=E.$(`<div class="w-e-menu">`)super($elem,editor)}clickHandler(){window.zyOffice.SetEditor(this.editor).api.exportWord();}tryChangeActive(){this.active()}}//zyOffice ButtonclassimportPdfBtnextendsBtnMenu{constructor(editor){const$elem=E.$(`<div class="w-e-menu">`)super($elem,editor)}clickHandler(){window.zyOffice.SetEditor(this.editor).api.openPdf();}tryChangeActive(){this.active()}}//WordPaster ButtonclassWordPasterBtnextendsBtnMenu{constructor(editor){const$elem=E.$(`<div class="w-e-menu">`)super($elem,editor)}clickHandler(){WordPaster.getInstance().SetEditor(this.editor).Paste();}tryChangeActive(){this.active()}}//wordImport ButtonclassWordImportBtnextendsBtnMenu{constructor(editor){const$elem=E.$(`<div class="w-e-menu">`)super($elem,editor)}clickHandler(){WordPaster.getInstance().SetEditor(this.editor).importWord();}tryChangeActive(){this.active()}}//excelImport ButtonclassExcelImportBtnextendsBtnMenu{constructor(editor){const$elem=E.$(`<div class="w-e-menu">`)super($elem,editor)}clickHandler(){WordPaster.getInstance().SetEditor(this.editor).importExcel();}tryChangeActive(){this.active()}}//ppt paster ButtonclassPPTImportBtnextendsBtnMenu{constructor(editor){const$elem=E.$(`<div class="w-e-menu">`)super($elem,editor)}clickHandler(){WordPaster.getInstance().SetEditor(this.editor).importPPT();}tryChangeActive(){this.active()}}//pdf paster ButtonclassPDFImportBtnextendsBtnMenu{constructor(editor){const$elem=E.$(`<div class="w-e-menu">`)super($elem,editor)}clickHandler(){WordPaster.getInstance().SetEditor(this.editor);WordPaster.getInstance().ImportPDF();}tryChangeActive(){this.active()}}//importWordToImg ButtonclassImportWordToImgBtnextendsBtnMenu{constructor(editor){const$elem=E.$(`<div class="w-e-menu">`)super($elem,editor)}clickHandler(){WordPaster.getInstance().SetEditor(this.editor).importWordToImg();}tryChangeActive(){this.active()}}//network paster ButtonclassNetImportBtnextendsBtnMenu{constructor(editor){const$elem=E.$(`<div class="w-e-menu">`)super($elem,editor)}clickHandler(){WordPaster.getInstance().SetEditor(this.editor);WordPaster.getInstance().UploadNetImg();}tryChangeActive(){this.active()}}exportdefault{name:'HelloWorld',data(){return{msg:'Welcome to Your Vue.js App'}},mounted(){vareditor=newE('#editor');WordPaster.getInstance({//上传接口:http://www.ncmem.com/doc/view.aspx?id=d88b60a2b0204af1ba62fa66288203edPostUrl:"http://localhost:8891/upload.aspx",License2:"",//为图片地址增加域名:http://www.ncmem.com/doc/view.aspx?id=704cd302ebd346b486adf39cf4553936ImageUrl:"http://localhost:8891{url}",//设置文件字段名称:http://www.ncmem.com/doc/view.aspx?id=c3ad06c2ae31454cb418ceb2b8da7c45FileFieldName:"file",//提取图片地址:http://www.ncmem.com/doc/view.aspx?id=07e3f323d22d4571ad213441ab8530d1ImageMatch:''});zyCapture.getInstance({config:{PostUrl:"http://localhost:8891/upload.aspx",License2:'',FileFieldName:"file",Fields:{uname:"test"},ImageUrl:'http://localhost:8891{url}'}})// zyoffice,// 使用前请在服务端部署zyoffice,// http://www.ncmem.com/doc/view.aspx?id=82170058de824b5c86e2e666e5be319czyOffice.getInstance({word:'http://localhost:13710/zyoffice/word/convert',wordExport:'http://localhost:13710/zyoffice/word/export',pdf:'http://localhost:13710/zyoffice/pdf/upload'})// 注册菜单E.registerMenu("zyCaptureBtn",zyCaptureBtn)E.registerMenu("WordPasterBtn",WordPasterBtn)E.registerMenu("ImportWordToImgBtn",ImportWordToImgBtn)E.registerMenu("NetImportBtn",NetImportBtn)E.registerMenu("WordImportBtn",WordImportBtn)E.registerMenu("ExcelImportBtn",ExcelImportBtn)E.registerMenu("PPTImportBtn",PPTImportBtn)E.registerMenu("PDFImportBtn",PDFImportBtn)E.registerMenu("importWordBtn",importWordBtn)E.registerMenu("exportWordBtn",exportWordBtn)E.registerMenu("importPdfBtn",importPdfBtn)//挂载粘贴事件editor.txt.eventHooks.pasteEvents.length=0;editor.txt.eventHooks.pasteEvents.push(function(){WordPaster.getInstance().SetEditor(editor).Paste();e.preventDefault();});editor.create();varedt2=newE('#editor2');//挂载粘贴事件edt2.txt.eventHooks.pasteEvents.length=0;edt2.txt.eventHooks.pasteEvents.push(function(){WordPaster.getInstance().SetEditor(edt2).Paste();e.preventDefault();return;});edt2.create();}}h1,h2{font-weight:normal;}ul{list-style-type:none;padding:0;}li{display:inline-block;margin:010px;}a{color:#42b983;}测试前请配置图片上传接口并测试成功
接口测试
接口返回JSON格式参考
components:{Editor,Toolbar},data(){return{editor:null,html:'dd',toolbarConfig:{insertKeys:{index:0,keys:['zycapture','wordpaster','pptimport','pdfimport','netimg','importword','exportword','importpdf']}},editorConfig:{placeholder:''},mode:'default'// or 'simple'}},一键粘贴Word内容,自动上传Word中的图片,保留文字样式。
一键导入Word文件,并将Word文件转换成图片上传到服务器中。
一键导入PDF文件,并将PDF转换成图片上传到服务器中。
一键导入PPT文件,并将PPT转换成图片上传到服务器中。
一键自动上传网络图片,自动下载远程服务器图片,自动上传远程服务器图片
点击下载完整示例