第四式:让汪峰轻松走上百度热搜
“汪峰上头条”一直是娱乐界里的一个梗,每次在微博热搜榜看到汪峰,以为能登顶榜首,不想都会有其他的爆点压制住,不管粉丝怎么努力,汪峰还是迟迟上不了头条!
最后“帮汪峰上头条”反而成了热搜,甚至被收录入百度百科[7]🐶。
蒽 🤔,如果汪峰是个前端工程师,那热搜的事儿不是分分钟搞定吗?就算不懂 HTML,只要知道 HTML5 的contenteditable
属性,控制台输入一个document.body.contentEditable='true';
,热搜还不是随便改,想要多少有多少 😄。
蒽 🤔,学了这招,甚至你可以轻松通过热搜向对象告白了...不过作为专业的 web 应用和网站开发人员,我们怎能满足于此呢?
同理,也是利用了 HTML5 中的contenteditable
属性,巧妙的在 body 增加一个可编辑的 style 标签,那这个样式,我们在页面上都可以修改了,想想就...没有太多卵用,哈哈哈 😂,不过话说回来,这个属性在部分富文本编辑器上还是很有用处的。很多富文本编辑器就是基于contenteditable
实现的,具体可以参考深入浅出 contenteditable 富文本编辑器[8]。
<style style="display:block; height:50px;" contenteditable> body { background: red; } </style>
效果图(图片来自下面的参考文章):
你以为contenteditable
只有true
和false
?其实它的可选值包括:
- contenteditable=""
- contenteditable="events"
- contenteditable="caret"
- contenteditable="plaintext-only"
- contenteditable="true"
- contenteditable="false"
除了 HTML5 的contenteditable
属性,其实还有一个不常用的 css 属性 —— user-modify
可以实现类似的效果,user-modify
可取值为以下四个:
read-only
read-write
write-only
read-write-plaintext-only
其中,write-only
不用在意,当下这个年代,基本上没有浏览器支持,以后估计也不会有。read-only
表示只读,就是普通元素的默认状态。然后,read-write
和read-write-plaintext-only
会让元素表现得像个文本域一样,可以 focus 以及输入内容,前者可以输入富文本,而后者只能输入纯文本。
具体效果你可以通过审查元素,给元素添加 CSS 样式查看,也可以直接看张鑫旭大佬的CSS user-modify 属性行为表现测试实例页面[9]demo。
- 这些鲜为人知的前端冷知识,你都 GET 了吗?
- 小 tip: 如何让 contenteditable 元素只能输入纯文本[10]
第五式:鼠标消失术
这个一个隐藏页面上鼠标的技巧,其实不值一提,也没有什么卵用。可以直接复制以下代码到控制台试试(此时如果在页面上吊起右键菜单,还是可以看见鼠标的):
var style = document.createElement('style'); document.head.appendChild(style); style.type = 'text/css'; style.styleSheet ? (style.styleSheet.cssText = '* { cursor: none;!important; }') : style.appendChild( document.createTextNode('* { cursor: none;!important; }') );
原理非常简单,设置cursor
属性为none
即可:
* { cursor: none !important; }
或者在浏览器地址栏输入以下内容:
IE 和 Chrome 会自动隐去前面的
javascript:
然后把后面的部分当做查询字段。你需要复制以下代码黏贴后手动在前面加上javascript:
, 然后回车效果就出来了。
javascript:function play(){var style = document.createElement('style');document.head.appendChild(style);style.type = 'text/css';style.styleSheet ? (style.styleSheet.cssText = '* { cursor: none !important; }') : style.appendChild(document.createTextNode('* { cursor: none !important; }'));}play();
第六式:让你的网站模糊不清
也许你经常碰到这样的页面,当没有登录的时候,只能看到下面的效果:
当然,这里的模糊不清效果是通过背景图占位来做的,其实如果不考虑安全性、被破解等因素,我们也完全可以使用 css 来实现类似的效果。
javascript:function play(){var style = document.createElement('style');document.head.appendChild(style);style.type = 'text/css';style.styleSheet ? (style.styleSheet.cssText = '* { color: transparent !important; text-shadow: #333 0 0 10px !important; }') : style.appendChild(document.createTextNode('* { color: transparent !important; text-shadow: #333 0 0 10px !important; }'));}play();
显而易见,这里主要是使用了以下两个 CSS 属性:
color: transparent !important; text-shadow: #333 0 0 10px !important;
第七式:让网站屏蔽开发者工具
浏览器开发者工具是给我们这些专业的 web 应用和网站开发人员使用的工具(当然,到底专不专业,自己心里都会有点 B 数 😄),它的作用在于,帮助开发人员审查元素、对网页进行布局、帮助前端工程师更好的断点调试等,还可以使用工具查看网页加载过程,进行性能分析和优化,获取网页请求等(这个过程也叫做抓包)。笔者可以豪不违心的说,离开了开发者工具,火热而有趣的的前端开发将变得索然无味,因为我感受不到有比浏览器自带开发者工具更趁手的利器。当然,据说真正的大神写出的 JS 和 CSS 都是不需要进行调试的,那我们另当别论,显然我和真正的大神不是一类人。
既然开发者工具这么可爱、这么好用,那我们为什么要屏蔽它呢?—— 可能是因为我们用过了、完成了开发工作,不想让别人有机会发现那些我们自己也看不懂的代码以及其中蕴含的商业机密吧,哼哼,果然是渣男~
那么,到底该如何做一个有能力可以屏蔽开发者工具的渣男呢?
也许依据打开控制台的几种方式,你自然就想到了:
- 监听 F12;
- 监听和禁止右键菜单(因为右键菜单里有“检查”选项可以打开控制台);
但是这样真的就行了吗?不,我们依然可以通过浏览器右上角的三个点,找到更多工具中的开发者工具,然后点击打开。
那我们该以什么思路解决这一问题呢?网上解法有很多,有些非主流,有些由于浏览器的升级已失效,相关思路及链接会在本小节末尾给出,这里只说两个我觉得还不错的方法:
const im = new Image(); Object.defineProperty(im, 'id', { get: function () { // 在这里放入你的代码,比如我这里会让他跳到百度 console.log('Console is opened'); window.location.href = 'http://www.baidu.com'; }, }); console.log(im); //谷歌最新版失效 let num = 0; //谷歌最新版有效 const devtools = new Date(); devtools.toString = function () { num++; if (num > 1) { // 在这里放入你的代码,比如我这里会让他跳到百度 console.log('Console is opened'); // window.location.href = "http://www.baidu.com"; return Date.prototype.toString.call(devtools); // 返回devtools结果(这一步不是必须的) } }; console.log(devtools);
以上方法的核心原理在于一点:只有打开控制台,才会执行 console 方法,而使用console
打印Date
,会调用Date
的toString
方法,我们对toString
方法做了改写。如果直接注入代码,如console = 1
,以上代码将失效。
其他几种思路包括:
- 监听 F12 或者 shift+ctrl+i 调起开发者工具(无法防止先打开开发者工具,然后在地址栏输入网址的访问);
- 监听和禁止右键菜单(因为右键菜单里有“检查”选项可以打开控制台);
- 监视窗口大小(适用于未将开发工具设置成独立窗口的情况);
- 监视 DOM 修改(适用于水印保护等场景);
- 利用 debugger 的特性,无限递归。
除了以上方法,也有诸如devtools-detector[13]一类的插件,用来对开发者工具打开的监测问题,在此不过多赘述。
第八式:代码性能大pk
性能、各种写法的优劣是我们在日常开发、技术讨论中最常提及和关注的。在写一段代码的时候,很多同学可能都会想要知道它的性能到底如何,和其他写法比起来哪个更快,但却苦于没有好用的工具,只能手动测试运行时间,这样一个是不方便,二是因为样本数太少误差较大。那么,除了对原理解析这种理论性的东西之外,我们可以怎样简洁、清晰、高效的对比各种不同 JS 写法的执行速度和性能呢?这就涉及到 JS性能测试工具了。
JS 性能测试工具原理一般是将给定的测试用例循环在指定环境下运行许多次,然后输出比对结果。JSBench.Me[19]就是这样一款在线代码性能测试利器。
同时也有一款 npm 插件 —— 强大的基准测试库Benchmark.js[20]官方说:
Benchmark.js 是一个强大的**基准测试**[21]库,支持高分辨率计时器并返回具有统计意义的结果。正如在 jsPerf 上看到的那样。
上文提到的jsPerf[22]本来是我想要介绍的一个工具,奈何这款工具无情的拒绝了我 😭。
所以,我们还是看看Benchmark.js
这个库的使用吧:
var suite = new Benchmark.Suite(); // add tests suite .add('RegExp#test', function () { /o/.test('Hello World!'); }) .add('String#indexOf', function () { 'Hello World!'.indexOf('o') > -1; }) // add listeners .on('cycle', function (event) { console.log(String(event.target)); }) .on('complete', function () { console.log('Fastest is ' + this.filter('fastest').map('name')); }) // run async .run({ async: true }); // logs: // => RegExp#test x 4,161,532 +-0.99% (59 cycles) // => String#indexOf x 6,139,623 +-1.00% (131 cycles) // => Fastest is String#indexOf