前言
由于很多人都提出了一些基础的问题,或者一些很常见的问题,我在此整理了一部分误区,方便大家查阅以及纠正
找不到元素的问题
一般可能有两个因素,一个是存在ifame,另外一个问题可能是页面加载的问题
页面加载与元素的那点破事
页面加载不等于元素已经出现,我们通常在f12控制台调试和查看的是现有的页面,并不代表页面加载完毕后就一定具备这个元素
尽管很多页面会在加载的时候就出现所有元素
但是也有很多页面,会在渲染完毕后,再根据xhr请求数据等方式,再在页面上绘制新的数据,这个时候如果我们在页面加载完毕和获取数据绘制之间进行获取元素
是获取不到的。
解决方法也很简单,
这里我提供两个常见的方法
1.使用Setinterval来进行循环判断,当获取元素不为空的时候继续执行,但需要注意不要创建过多的定时器,以及不使用的时候可以考虑销毁定时器
https://www.runoob.com/jsref/met-win-setinterval.html
2.通过DOM插入监控来判断
在bilibili的例子中我们已经搞过了,通过上层已经存在的元素对其进行dom监听,然后再插入的时候会触发这个函数,来进行一些操作
但是需要注意把握好下层元素的数量问题,如果绘制元素过多反复触发,会极大的延迟运行速度
let ops=document.querySelector('#arc_toolbar_report .ops');
//插入三连之后好像会重新生成,不添加就不会重新生成,暂时没弄清什么情况,先这样处理了.
//主要作用是监听ops的DOMNodeInserted事件,等它修改完成之后再插入我们的三连按钮,另外注意run-at是document-end,要等待ops生成之后再监听,不然query返回null会报错
//这个事件会多次调用,但是我们insertBefore插入如果元素存在,只是修改而不会新增
ops.addEventListener("DOMNodeInserted", function(event) {
let share=document.querySelector('.share');
share.parentElement.insertBefore(triple,share);
});
iframe的那点破事
可以参考https://music.163.com/#
我们可以获取到iframe元素后通过conetentWindow进入iframe的作用域来执行相应的函数
document.querySelector('#g_iframe').contentWindow.document.querySelector
在我的印象里好像是contentWindow内的document通常同域下才可以使用,而非同域是没有办法的
如果没法调用contentWindow下的document我们也有其他办法的
相信你一定想到了樱花动漫那一节课吧?
通过match匹配让脚本运行在iframe内就好了!
https://bbs.tampermonkey.net.cn/thread-274-1-1.html
queryselect的临时大培训!
很多人都说document.queryselect的时候经常不知道怎么找元素
我这里列几个例子
以这个小iframe拿捏,我们可以根据id来获取
document.querySelector('#g_iframe')
也可以感觉除了id和class的其他属性来获取,比如name='contentFrame'
像这种除了id和class的其他属性,可以加上中括号和等于来进行判断
document.querySelector('[name="contentFrame"]')
另外queryslector是按层级匹配,但是不需要把每层都写上,即使隔层也可以匹配到的
这里我们想获取updn
document.querySelector('.g-btmbar .updn')
就可以了,不需要填写btmbar和updn中间那层元素
html中的标签也可以作为queryselect的搜索因素的
比如
网页只有这一个iframe标签,那我们可以直接
document.querySelector('iframe')
来获取
如果存在大量的相同的class元素,并且没什么特征怎么办?
通过queryselectorall获取全部匹配的元素,然后通过for循环,根据每个元素的特征来判断是否是我们需要的元素,这个在百度去广告那节
我们有进行讨论过
https://bbs.tampermonkey.net.cn/thread-688-1-1.html
关于脚本作用域问题
一旦你开启了沙盒模式,你的沙盒中的函数与网页的函数是隔离的
如果你再写代码的过程中网页与沙盒之间产生了一些函数的交互或者调用,一定要注意这个问题
这时候可以考虑在沙盒对网页的元素进行监控或者挂载一些实践
关于这个问题在平时是不常见的,如果发生了这种问题,相信那时候的你是已经知道如何解决得了!