记录工作中的一些疑问,疑难杂症,简单的细节。
随着工作时间越来越长遇到的问题也会越来越多,踩到的坑越来越多,
好的习惯是将它们一一记录,以便下次快速翻查。
好奇疑问
markdown如何添加锚点
- [标题名](#给标题取得一个id,一般与标题同名即可) ### <a id="给标题取得一个id,一般与标题同名即可">标题名</a>
数组中去除对象, 根据对象中的某个key名重复的简单方法
const arr = [
{ name:’xiaoming’, age:11 },
{ name:’xiaohua’, age:18 },
{ name:’xiaoming’, age:10 }
]
现在需要把name重复的剔除。function unique({arr=[],key}){ if(!key){ return arr; } let hash = {}; arr = arr.reduce(function(item, next) { hash[next[key]] ? '' : hash[next[key]] = true && item.push(next); return item }, []) return arr; }
如何预览PDF文件(用单个闭合标签多个iframe会被渲染成一个iframe)
<iframe src="xxx.pdf"></iframe>
markdown文章章节如何 展开 & 收起
<!--details中添加open属性可展开内容--> <details> <summary>展开查看</summary> <pre> 展开内容 </pre> </details>
如何创建微信公众号并发布文章,并且可以查看历史文章
先申请一个微信公众号,然后创建
相对地址绝对地址转换方法(也可以用 new URL)
function relative2absolute(url, base) { let ele = document.createElement('a'); ele.href = (base || '') + url; return eleLink.href; }
微信公众号VUE页面缓存
location / { root /opt/static/xxxx; index index.html; autoindex on; directio 512; output_buffers 1 128k; open_file_cache max=1000 inactive=30s; open_file_cache_valid 30s; open_file_cache_min_uses 2; open_file_cache_errors on; #### 清除缓存 add_header Last-Modified $date_gmt; add_header Cache-Control 'no-store, no-cache, must-revalidate, proxy-revalidate, max-age=0'; if_modified_since off; expires off; etag off; }
node-sass安装失败
sudo npm install node-sass --unsafe-perm --save-dev
mac文件只有读功能
sudo chmod -R 777 '文件路径'
如何将本地项目(远端没有)推送到远端github上面
// 1.在远端仓库创建一个与本地同名的项目 // 2.git remote add origin https://github.com/MrRetro/element-form.git // 3.git push -u origin master
获取视频第一帧并展示
/** * 获取视频第一帧画面 * @param eleVideo 当前视频元素 * @param eleTarget 第一帧渲染到当前元素内 * @param imgWidth 图片渲染宽度 * @param imgHeight 图片渲染高度 * */ export function getVideoFirstImg ({ eleVideo, eleTarget, imgWidth = 400, imgHeight = 300 }) { const canvas = document.createElement('canvas') const img = document.createElement('img') eleVideo.setAttribute('crossOrigin', 'anonymous') canvas.width = eleVideo.clientWidth canvas.height = eleVideo.clientHeight eleVideo.onloadeddata = () => { canvas.getContext('2d').drawImage(eleVideo, 0, 0, canvas.width, canvas.height) const dataURL = canvas.toDataURL('image/png') img.src = dataURL img.width = imgWidth img.height = imgHeight eleTarget.appendChild(img) } }
服务端给到的一维数组转成树形结构
// 例如: // [ // {id: 1, name: '2-1', pid: 2}, // {id: 2, name: '2'} // ] // ==> [id:2, name: '2', children: [{id: 1, name: '2-1', pid: 2}]] function transData(arr, idStr, pidStr, chindrenStr) { let result = [], hash = {}, id = idStr, pid = pidStr, children = chindrenStr, i = 0, j = 0, len = arr.length; for (; i < len; i++) { hash[arr[i][id]] = arr[i]; } for (; j < len; j++) { let aVal = arr[j], hashVP = hash[aVal[pid]]; if (hashVP) { !hashVP[children] && (hashVP[children] = []); hashVP[children].push(aVal); } else { result.push(aVal); } } return result; }
金额数字(带小数点)转大写中文
function convertCurrency(money) { let cnNums = ['零', '壹', '贰', '叁', '肆', '伍', '陆', '柒', '捌', '玖'] let cnIntRadice = ['', '拾', '佰', '仟'] let cnIntUnits = ['', '万', '亿', '兆'] let cnDecUnits = ['角', '分', '毫', '厘'] let cnInteger = '整' let cnIntLast = '元' let maxNum = 999999999999999.9999 let integerNum let decimalNum let chineseStr = '' let parts if (money === '') { return '' } money = parseFloat(money) if (money >= maxNum) { return '' } if (money === 0) { chineseStr = cnNums[0] + cnIntLast + cnInteger return chineseStr } money = money.toString() if (money.indexOf('.') === -1) { integerNum = money decimalNum = '' } else { parts = money.split('.') integerNum = parts[0] decimalNum = parts[1].substr(0, 4) } if (parseInt(integerNum, 10) > 0) { let zeroCount = 0 let IntLen = integerNum.length for (let i = 0; i < IntLen; i++) { let n = integerNum.substr(i, 1) let p = IntLen - i - 1 let q = p / 4 let m = p % 4 if (n === '0') { zeroCount++ } else { if (zeroCount > 0) { chineseStr += cnNums[0] } zeroCount = 0 chineseStr += cnNums[parseInt(n)] + cnIntRadice[m] } if (m === 0 && zeroCount < 4) { chineseStr += cnIntUnits[q] } } chineseStr += cnIntLast } if (decimalNum !== '') { let decLen = decimalNum.length for (i = 0; i < decLen; i++) { n = decimalNum.substr(i, 1) if (n !== '0') { chineseStr += cnNums[Number(n)] + cnDecUnits[i] } } } if (chineseStr === '') { chineseStr += cnNums[0] + cnIntLast + cnInteger } else if (decimalNum === '') { chineseStr += cnInteger } return chineseStr }
通过id和数组找到它的所有父级
/** * 获取节点的所有父级节点 * @param data 整个树 * @param nodeId 某节点的id * @param idStr 自定义设置唯一标识名称 * @param childrenStr 自定义设置孩子节点名称 * */ function getParentNode({data, nodeId, idStr = 'id', childrenStr = 'children'}) { let arrRes = []; if (data.length === 0) { if (nodeId) { arrRes.unshift(data) } return arrRes; } let rev = (arr, nodeId, pareantId) => { for (let i = 0, length = arr.length; i < length; i++) { let node = arr[i]; node._pareantId = pareantId if (node[idStr] === nodeId) { arrRes.unshift(node) rev(data, node._pareantId); break; } else { if (node[childrenStr]) { rev(node[childrenStr], nodeId, node[idStr]); } } } return arrRes; }; arrRes = rev(data, nodeId); return arrRes; } // let data = [ // {value: 1, childrens: [{value: 2, childrens: [{value: 3}]}]}, // {value: 4, childrens: [{value: 5, childrens: [{value: 6}]}]}, // ] // console.log(getParentNode({data, nodeId: 6, idStr: 'value', childrenStr:'childrens'}))
新建一个shell脚本文件.bat,用于执行shell命令,用来启动全端所有微项目命令
// window start cmd /k "cd \work\system && npm run serve"
字符串对比输出相似度
// s 字符串1 // t 字符串2 // f 小数位数 function similar(s, t, f) { if (!s || !t) { return 0 } var l = s.length > t.length ? s.length : t.length var n = s.length var m = t.length var d = [] f = f || 3 var min = function(a, b, c) { return a < b ? (a < c ? a : c) : (b < c ? b : c) } var i, j, si, tj, cost if (n === 0) return m if (m === 0) return n for (i = 0; i <= n; i++) { d[i] = [] d[i][0] = i } for (j = 0; j <= m; j++) { d[0][j] = j } for (i = 1; i <= n; i++) { si = s.charAt(i - 1) for (j = 1; j <= m; j++) { tj = t.charAt(j - 1) if (si === tj) { cost = 0 } else { cost = 1 } d[i][j] = min(d[i - 1][j] + 1, d[i][j - 1] + 1, d[i - 1][j - 1] + cost) } } let res = (1 - d[n][m] / l) return res.toFixed(f) }
vue踩到的坑
输入框只能输入数字
<input v-model="value" @input="value=value.replace(/[^\d]/g, '')" />
vue-cli3.3+打包后路径找不到(空白)
重新配置vue.config.js文件module.exports = { publicPath: './', outputDir: 'dist', assetsDir: 'static' }
给elementui中的dialog加上拖拽功能
// v-dialogDrag: 弹窗拖拽 import Vue from 'vue'; let draging = false; let dragDom: HTMLElement | null; let dragpoint: { x: number, y: number }; Vue.directive('dialogDrag', { bind(el, binding, vnode, oldVnode) { let dialogHeaderEl = el.querySelector('.el-dialog__header') as HTMLElement; dialogHeaderEl.addEventListener('mousedown', (ev: MouseEvent) => { let target = ev.target as HTMLElement; //由于点击关闭按钮会事件冒泡,取消拖拽 if (target.classList.contains('el-dialog__close')) { return; } draging = true; dragDom = el.querySelector('.el-dialog'); //自定义样式,让弹窗在拖拽过程中鼠标指针变成十字移动 dragDom?.classList.add('draging'); dragpoint = { x: ev.clientX, y: ev.clientY } }); } }); document.addEventListener('mouseup', (ev: MouseEvent) => { draging = false; dragDom?.classList.remove('draging'); dragDom = null; }); document.addEventListener('mousemove', (ev: MouseEvent) => { if (draging) { let _dragdom = dragDom as HTMLElement; let sty = window.getComputedStyle(_dragdom, null); _dragdom.style.marginLeft = `${parseFloat(sty.marginLeft) + ev.clientX - dragpoint.x}px`; _dragdom.style.marginTop = `${parseFloat(sty.marginTop) + ev.clientY - dragpoint.y}px`; dragpoint = { x: ev.clientX, y: ev.clientY } } });
vue线上如何调试
1.控制台找到app.js打包后的主文件,打包后的文件一般会加上哈希码,例如:app.6d11e565.js 2.搜索 "$mount" 关键字 3.断点到 new Vue 位置 4.修改 new 后面的 Vue.config.devtools = true, 注意:这边的Vue以实际编译的为准 例如 new i.a({...})
vue生产环境开启vue-tools调试
(function openVueTool(){ //在方法中执行,避免污染全局变量 //开启vue2 production调试的方法 //1.找vue实例,可以说99%的应用是用的app.__vue__ //如果实在找不到,那么就到找到任意组件,用组件元素.__vue__.$root来获取 var vue = app.__vue__ //2.vue构造函数 var constructor = vue.__proto__.constructor //3.Vue有多级,要找到最顶级的 var Vue = constructor; while(Vue.super){ Vue = Vue.super } //4.找到config,并且把devtools设置成true Vue.config.devtools = true; //5.注册到Vue DevTool上 var hook = window.__VUE_DEVTOOLS_GLOBAL_HOOK__ hook.emit('init',Vue) //6.如果有vuex store if(vue.$store){ var store = vue.$store; store._devtoolHook = hook; hook.emit('vuex:init', store); hook.on('vuex:travel-to-state',function(targetState){ store.replaceState(targetState); }); store.subscribe(function(mutation, state){ hook.emit('vuex:mutation', mutation, state); }); } })()
需求实现
1.写一个白板支持撤销
http://www.htmleaf.com/ziliaoku/qianduanjiaocheng/201502151385.html
2.写一个爬网页素材的爬虫
- 本文作者: MrRetro博客
- 本文链接: http://mrretro.gitee.io/retroblog/retroblog/2020/01/16/工作中记录的点点滴滴问题/
- 版权声明: 本博客所有文章除特别声明外,均采用 MIT 许可协议。转载请注明出处!