选你所爱,爱你所选。
在浏览网站时,反白(或称反蓝)其实是一个非常常见的动作,不管是要强调目前的阅读区域或是想要复制某个段落,使用者都会透过游标进行反白,而 Selection API 就是针对反白的选取区块进行操作。
Selection 本身是一个物件,它代表的是目前使用者所选的文本范围,或是「输入游标」插入的位置,这文本范围可能会涵盖到多个元素,也可能会坍缩在一个点(也就是没有选取到任何文本),而这整个选取范围又包含了几个专有术语:
你该知道:
- anchor 有可能在 focus 前面也有可能在 focus 後面,这取决於你拖曳游标的方向。
- range 可能会横跨多个节点,但 anchor 和 focus 只会存在在最初与最後的节点当中。
如果想要取得目前选取范围的 Selection 物件,那只要呼叫这个 method 就可以了:
let selectionObj = window.getSelection();
console.log(selectionObj); // Selection 物件
取得了 Selection 物件後我们就可以读取它本身的一些属性了,而 anchorNode
就是其中之一,它会给我们当初反白时 anchor 位置所在的节点。
let selectionObj = window.getSelection();
console.log(selectionObj.anchorNode); // 一个文字节点
知道 anchor 所在节点後,还可以透过 anchorOffset
来知道 anchor 点下的位置距离节点开头相差了几个字:
let selectionObj = window.getSelection();
console.log(selectionObj.anchorOffset); // 一个 number,代表与节点开头相差了几个字
当然了,可以知道 anchor 的位置,自然也能知道 focus 的位置。
let selectionObj = window.getSelection();
console.log(selectionObj.focusNode); // 一个文字节点
以此类推,有 focusNode
就也会有 focusOffset
:
let selectionObj = window.getSelection();
console.log(selectionObj.focusOffset); // 一个 number,代表与节点开头相差了几个字
那除了一些唯读属性之外呢,Selection 物件有有一些自身的 methods 可以使用,其中最简单也最重要的自然就是取得所选范围的文本内容,这时候只要呼叫 toString
就可以了:
let selectionObj = window.getSelection();
console.log(selectionObj.toString()); // 所选范围的文本内容
collapse
是个比较特别的 method,它会让 Selection 坍缩到只剩下一个点,也就是从一个反白区块变成只剩下一个闪烁的输入游标在画面上。
而 collapse
有两个参数可以传入,第一个是你想坍缩 Selection 到哪一个节点上,第二个参数则是你要坍缩在该节点上的第几个位置。
<div contenteditable="true">这里的文字可以编辑</div>
<button>collapse</button>
<script>
const button = document.querySelector("button");
button.addEventListener("mousedown", function(e){
e.preventDefault();
})
button.addEventListener("click", function(){
const selection = window.getSelection();
// 将选取范围坍缩在 anchor 所在节点的第十个字
selection.collapse(selection.anchorNode, 10);
})
</script>
要注意,尽管你看不到闪烁的游标,但其实游标还是被放到了你 focus 或 collapse 的位置。而如果你将元素改为
contenteditable
,你就可以清楚看到游标了。
另一个和 collapse
很像的是 extend
,它会让 anchor 保持不变并移动 focus,也就是说你可以改变反白的区域。它的参数也和 collapse
一样,第一个是你要将 focus 移动到哪个节点,第二个则是要移动到该节点的第几个字。
<div contenteditable="true">这里的文字可以编辑</div>
<button>extend</button>
<script>
const button = document.querySelector("button");
button.addEventListener("mousedown", function(e){
e.preventDefault();
})
button.addEventListener("click", function(){
const selection = window.getSelection();
// 将 focus 移动到跟 anchor 一样的位置,此时 Selection 会是坍缩的
selection.extend(selection.anchorNode, selection.anchorOffset);
})
</script>
这个 method 算是非常好用的,它可以够传入一个元素节点来指定目前的选取范围。如果你传的是整个 document.body
那就相当於是全选整个网页。
<div>
Lorem ipsum dolor sit amet consectetur adipisicing elit.
</div>
<script>
const div = document.querySelector("div");
const selection = window.getSelection();
selection.selectAllChildren(div); // div 中的内容将整个被反白起来
</script>
deleteFromDocument
可以帮我们将目前选取的区块从整个文件中删除,当然,他指的是目前浏览的页面,并不会连同你的程序码一并删除。
<div>
Lorem ipsum dolor sit amet consectetur adipisicing elit.
</div>
<script>
const div = document.querySelector("div");
const selection = window.getSelection();
// 我们将 div 中的内容整个反白起来後删除了
selection.selectAllChildren(div);
selection.deleteFromDocument();
</script>
最後,除了主动针对 Selection 物件进行操作外,Document 本来还可以监听 selectionchange
的事件,当今天文件中的选取范围有了更动,该事件就会触发,并执行我们指定的 Callback。
document.addEventListener("selectionchange", () => {
// 讲选取起来的文本内容设定到指定的容器中
document.querySelector("#text").textContent = window.getSelection().toString();
});
相信看完今天的内容,你可能会觉得 Selection API 功能似乎蛮齐全的,但好像也不知道要拿来做什麽应用,但其实只要搭配昨天的 DesignMode,我们就可以制作一个简易的文章编辑器了,不过等到明天的 Clipboard 一并介绍完後,我们再来实际动手做,届时各位就会知道 Selection API 其实是蛮好玩的。
>>: [C 语言笔记--Day13] Pointers to Functions
用了多少时间 记录在变数的方式 declare @BTIME datetime declare @E...
出於书本 Chapter 1. Introduction to Ethical Hacking 骇客...
Interceptor 拦截器 在许多的Java Web 框架都有实现Interceptor 的方法...
来到了铁人赛的29天,扣除掉最後一集的心得,今天算是最後一个主题。 今天的影片和以往不太一样,我事...
● 这章来示范如何取得期货(Futures)的ticks 回顾上一章,我们学会如何取得股票的tick...