记录工作中的一些疑问,疑难杂症,简单的细节。
随着工作时间越来越长遇到的问题也会越来越多,踩到的坑越来越多,
好的习惯是将它们一一记录,以便下次快速翻查。
好奇疑问
- 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'}))
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
}
}
});
需求实现
1.写一个白板支持撤销
2.写一个爬网页素材的爬虫