ãã®ç« ã§ã¯ããã¥ã¡ã³ãã§ã®é¸æã¨ã<input> ãªã©ã®ãã©ã¼ã ãã£ã¼ã«ãã§ã®é¸æã«ã¤ãã¦èª¬æãã¾ãã
JavaScript ãå©ç¨ãã¦é¸æç¶æ ãåå¾ããããå ¨ä½ãããã¯ä¸é¨åã®é¸æ/é¸æè§£é¤ãããã¥ã¡ã³ããã鏿ããé¨åãåé¤ãã¿ã°ã¸ã®ã©ãããªã©ãè¡ããã¨ãã§ãã¾ãã
æ«å°¾ã® âãµããªâ ã»ã¯ã·ã§ã³ã«ã¬ã·ãããããããã§ç¾æç¹ã§å¿ è¦ãªãã¨ã¯ã«ãã¼ããã¦ããããããã¾ããããã ãç« å ¨ä½ãèªããã¨ã§ããå¤ãã®ãã¨ãç¥ããã¨ãã§ãã¾ãã
åºç¤ã¨ãªã Range 㨠Selection ãªãã¸ã§ã¯ãã®ææ¡ã¯é£ããã¯ãªãã®ã§ãå¿
è¦ãªãã¨ãããããã®ã¬ã·ãã¯å¿
è¦ããã¾ããã
ç¯å²(Range)
鏿ã®åºæ¬çãªæ¦å¿µã¯ ç¯å²(Range) ã§ãåºæ¬çã«ã¯ âå¢çç¹â(ç¯å²ã®éå§ã¨çµäº) ã®ãã¢ã§ãã
Range ãªãã¸ã§ã¯ãã¯ãã©ã¡ã¼ã¿ãªãã§ä½æã§ãã¾ã:
let range = new Range();
次ã«ãrange.setStart(node, offset) 㨠range.setEnd(node, offset) ã使ç¨ãã¦é¸æã®å¢çãè¨å®ãã¾ãã
ãæ³åã®ã¨ãããããã«é¸æããã¦ããããã« Range ãªãã¸ã§ã¯ãã使ç¨ãã¾ãããæåã«ãã®ãããªãªãã¸ã§ã¯ããããã¤ã使ãã¾ãããã
ããã¹ããé¨åçã«é¸æ
è峿·±ããã¨ã¯ã両æ¹ã®ã¡ã½ããã®æåã®å¼æ° node ã¯ããã¹ããã¼ãããããã¯è¦ç´ ãã¼ãã§ã2ã¤ç®ã®å¼æ°ã®æå³ã¯ãã®ç¨®é¡ã«ããã¾ãã
node ãããã¹ããã¼ãã®å ´åãoffset ã¯ãã®ããã¹ãã§ã®ä½ç½®ã«ãªãã¾ãã
ä¾ãã°ãè¦ç´ <p>Hello</p> ãããå ´åãæ¬¡ã®ããã«ãã¦æå âllâ ãå«ãç¯å²ã使ã§ãã¾ãã:
<p id="p">Hello</p>
<script>
let range = new Range();
range.setStart(p.firstChild, 2);
range.setEnd(p.firstChild, 4);
// range ã® toString ã¯ããã¹ãã¨ãã¦ã³ã³ãã³ããè¿ãã¾ã
console.log(range); // ll
</script>
ããã§ã¯ <p> ã®æåã®åï¼ããã¹ããã¼ãï¼ãåãããã®ä¸ã®ããã¹ãä½ç½®ãæå®ãã¦ãã¾ãã:
è¦ç´ ãã¼ãã®é¸æ
䏿¹ãnode ãè¦ç´ ãã¼ãã§ããã°ãoffset ã¯åä¾ã®çªå·ã«ãªãã¾ãã
ããã¯ãããã¹ãå ã®ã©ããã§åæ¢ããã®ã§ã¯ãªãããã¼ãå ¨ä½ãå«ãç¯å²ã使ããå ´åã«ä¾¿å©ã§ãã
ä¾ã¨ãã¦ããã® HTML ã®ä¸é¨ãèãã¾ã:
<p id="p">Example: <i>italic</i> and <b>bold</b></p>
DOMæ§é ã¯æ¬¡ã®éãã§ããããã§ã¯ããã¹ããã¼ããéè¦ã§ãã:
"Example: <i>italic</i>" ã®ç¯å²ã使ãã¾ãããã
ã覧ã®éããããã¯ã¤ã³ããã¯ã¹ 0 㨠1 ãæã¤ <p> ã®å
é ãã2ã¤ã®åã§ã:
-
éå§ä½ç½®ã¯è¦ªã®
nodeã¨ãã¦<p>ãããªãã»ããã¯0ãæã¡ã¾ãããªã®ã§ã
range.setStart(p, 0)ã¨è¨å®ã§ãã¾ãã -
çµäºä½ç½®ã親ãã¼ãã¨ãã¦
<p>ãæã¡ã¾ããããªãã»ããã¨ãã¦ã¯2ã«ãªãã¾ãï¼ããã¾ã§ãã¨ããç¯å²ãæå®ãã¾ãããoffsetã®å«ã¿ã¾ããï¼ããã®ããã
range.setEnd(p, 2)ã¨è¨å®ã§ãã¾ãã
ããã¯ãã¢ã§ããå®è¡ããã¨ããã¹ãã鏿ãããã®ãåããã¾ã:
<p id="p">Example: <i>italic</i> and <b>bold</b></p>
<script>
let range = new Range();
range.setStart(p, 0);
range.setEnd(p, 2);
// range ã® toString ã¯ãã®ã³ã³ãã³ããããã¹ãã¨ãã¦(ã¿ã°ãªã)è¿ãã¾ã
alert(range); // Example: italic
// ãã® range ãããã¥ã¡ã³ã鏿ã«é©ç¨ãã¾ãï¼å¾ã§èª¬æãã¾ãï¼
document.getSelection().addRange(range);
</script>
ããã¯ããæè»ãªä¾ã§å¤ãã®ãã¿ã¼ã³ã試ãã¾ãã:
<p id="p">Example: <i>italic</i> and <b>bold</b></p>
From <input id="start" type="number" value=1> â To <input id="end" type="number" value=4>
<button id="button">Click to select</button>
<script>
button.onclick = () => {
let range = new Range();
range.setStart(p, start.value);
range.setEnd(p, end.value);
// apply the selection, explained later
document.getSelection().removeAllRanges();
document.getSelection().addRange(range);
};
</script>
ä¾. 1 ãã 4 ã鏿ããå ´åã®ç¯å²ã¯ <i>italic</i> and <b>bold</b> ã§ãã
setStart 㨠setEnd ã§åããã¼ããæå®ããå¿
è¦ã¯ããã¾ãããç¯å²ï¼rangeï¼ã¯å¤æ°ã®ç¡é¢ä¿ãªãã¼ãã«ã¾ãããå ´åãããã¾ããææ¸å
ã§çµäºãéå§ã®å¾ã«ãããã¨ã ããéè¦ã§ãã
ãã大ããªãã©ã°ã¡ã³ãã®é¸æ
次ã®ããã«ãä¾ã®ä¸ã§ãã大ããªé¸æã使ãã¦ã¿ã¾ããã:
ãã§ã«ããæ¹ã¯ç¥ã£ã¦ãã¾ããéå§ã¨çµäºãããã¹ããã¼ãã§ç¸å¯¾ãªãã»ããã¨ãã¦ã»ããããã ãã§ãã
次ã®ãããªç¯å²ã使ãã¾ã:
<p>ã®æåã®åã®ä½ç½® 2 ããéå§("Example: " ã®æåã®2æåãé¤ããã¹ã¦)<b>ã®æåã®åã®ä½ç½® 3 ã§çµäº(âboldâ ã®æåã®3æå):
<p id="p">Example: <i>italic</i> and <b>bold</b></p>
<script>
let range = new Range();
range.setStart(p.firstChild, 2);
range.setEnd(p.querySelector('b').firstChild, 3);
alert(range); // ample: italic and bol
// 鏿ã«ãã®ç¯å²ã使ç¨ãã¾ã(å¾ã»ã©èª¬æãã¾ã)
window.getSelection().addRange(range);
</script>
ã覧ã®éããå¿ è¦ã¨ããç¯å²ï¼rangeï¼ã使ããã®ã¯é常ã«ç°¡åã§ãã
ãããã¼ãå
¨ä½ãããªããå ´åãsetStart/setEnd ã§è¦ç´ ãæ¸¡ããã¨ãã§ãã¾ãããã以å¤ã®å ´åã¯ããã¹ãã¬ãã«ã§ä½æ¥ã§ãã¾ãã
ç¯å²ï¼rangeï¼ããããã£
ä¸ã®ä¾ã§ä½æããç¯å²ï¼rangeï¼ãªãã¸ã§ã¯ãã¯æ¬¡ã®ããããã£ãæã¡ã¾ã:
startContainer,startOffsetâ éå§ç¹ã®ãã¼ãã¨ãªãã»ãã- ä¸ã®ä¾ã§ã¯ã
på ã®æåã®ããã¹ããã¼ãã¨2ã§ãã
- ä¸ã®ä¾ã§ã¯ã
endContainer,endOffsetâ çµäºç¹ã®ãã¼ãã¨ãªãã»ãã- ä¸ã®ä¾ã§ã¯ã
<b>å ã®æåã®ããã¹ããã¼ãã¨3ã§ãã
- ä¸ã®ä¾ã§ã¯ã
collapsedâ çå½å¤, range ã®éå§/çµäºç¹ãåã(ã¤ã¾ã range å ã«ã³ã³ãã³ãããªã)å ´åã¯trueã§ãã- ä¸ã®ä¾ã§ã¯
falseãã§ãã
- ä¸ã®ä¾ã§ã¯
commonAncestorContainerâ range å ã®ãã¹ã¦ã®ãã¼ãã®æãè¿ãå ±éã®ç¥å - ä¸ã®ä¾ã§ã¯
<p>ã§ãã
- ä¸ã®ä¾ã§ã¯
ç¯å²(range) 鏿ã¡ã½ãã
ç¯å²ãæä½ããããã®ä¾¿å©ãªã¡ã½ãããããããããã¾ãã
ãã§ã« setStart 㨠setEnd ã¯è¦ã¦ãã¾ããããããã«ã¯ä»ã®é¡ä¼¼ã¡ã½ãããããã¾ãã
ç¯å²ã®éå§ãè¨å®:
setStart(node, offset)ã¯nodeå ã®offsetã®ä½ç½®ã«éå§ç¹ãè¨å®ãã¾ããsetStartBefore(node)ã¯nodeã®ç´åãéå§ç¹ã«è¨å®ãã¾ããsetStartAfter(node)ã¯nodeã®ç´å¾ãéå§ç¹ã«è¨å®ãã¾ãã
ç¯å²ã®çµäºãè¨å®(åæ§ã®ã¡ã½ããã§ã):
setEnd(node, offset)ã¯nodeå ã®offsetã®ä½ç½®ã«çµäºç¹ãè¨å®ãã¾ããsetEndBefore(node)nodeã®ç´åãçµäºç¹ã«è¨å®ãã¾ããsetEndAfter(node)ã¯nodeã®ç´å¾ãçµäºç¹ã«è¨å®ãã¾ãã
æè¡çã«ã¯ãsetStart/setEnd ã¯ä½ã§ãã§ãã¾ãããããå¤ãã®ã¡ã½ããã§ããã«ä¾¿å©ã«ãªãã¾ãã
ãããã®ã¡ã½ããã¯ãã¹ã¦ãnode ã¯ããã¹ããããã¯è¦ç´ ãã¼ã両æ¹ã«ãªãã¾ããããã¹ããã¼ãã®å ´å offset ã¯æåãã¹ããããã䏿¹ã§ãè¦ç´ ãã¼ãã¯åãã¼ããã¹ããããã¾ãã
ç¯å²ï¼rangeï¼ã使ããããã®ã¡ã½ãããä»ã«ãããã¾ã:
selectNode(node)ã¯nodeå ¨ä½ã鏿ãããããªç¯å²ãè¨å®ãã¾ããselectNodeContents(node)ã¯nodeã®ã³ã³ãã³ãå ¨ä½ã鏿ãããããªç¯å²ãè¨å®ãã¾ãcollapse(toStart)ã¯ãtoStart=trueã®å ´å end=start ãããã§ãªããã° start=end ãè¨å®ãã¾ããç¯å²ãæãããã¿ã¾ããcloneRange()ã¯åãéå§/çµäºç¹ããã¤æ°ããç¯å²ã使ãã¾ãã
ç¯å²ï¼rangeï¼ç·¨éã¡ã½ãã
ä¸åº¦ç¯å²(range)ã使ããæ¬¡ã®ãããªã¡ã½ããã使ç¨ãããã¨ã§ã³ã³ãã³ããæä½ãããã¨ãã§ãã¾ã:
deleteContents()â ããã¥ã¡ã³ãããç¯å²ã®ã³ã³ãã³ããåé¤ãã¾ãextractContents()â ããã¥ã¡ã³ãããç¯å²ã®ã³ã³ãã³ããåé¤ããDocumentFragment ã¨ãã¦è¿å´ãã¾ããcloneContents()â ç¯å²ã®ã³ã³ãã³ããã¯ãã¼ã³ããDocumentFragment ã¨ãã¦è¿å´ãã¾ããinsertNode(node)â ããã¥ã¡ã³ãã®ç¯å²ã®å é ã«nodeãæ¿å ¥ãã¾ããsurroundContents(node)ânodeã§ç¯å²ã³ã³ãã³ããã©ãããã¾ãããããæ©è½ããã«ã¯ãç¯å²å ã«ãã¹ã¦ã®è¦ç´ ã®éå§ã¨çµäºã¿ã°ãå«ã¾ãã¦ããå¿ è¦ãããã¾ãã<i>abcã®ãããªé¨åçãªç¯å²ã§ã¯æ©è½ãã¾ããã
ãããã®ã¡ã½ããã使ç¨ããã¨ã鏿ãããã¼ãã«å¯¾ãåºæ¬çã«ä½ã§ãã§ãã¾ãã
ããã¯å®éã®åä½ã確èªã§ããä¾ã§ãã:
ãã¿ã³ã¯ãªãã¯ã§é¸æç¯å²ã«å¯¾ãã¡ã½ãããå®è¡ãã"resetExample" ã§ãªã»ãããã¾ãã
<p id="p">Example: <i>italic</i> and <b>bold</b></p>
<p id="result"></p>
<script>
let range = new Range();
// Each demonstrated method is represented here:
let methods = {
deleteContents() {
range.deleteContents()
},
extractContents() {
let content = range.extractContents();
result.innerHTML = "";
result.append("extracted: ", content);
},
cloneContents() {
let content = range.cloneContents();
result.innerHTML = "";
result.append("cloned: ", content);
},
insertNode() {
let newNode = document.createElement('u');
newNode.innerHTML = "NEW NODE";
range.insertNode(newNode);
},
surroundContents() {
let newNode = document.createElement('u');
try {
range.surroundContents(newNode);
} catch(e) { alert(e) }
},
resetExample() {
p.innerHTML = `Example: <i>italic</i> and <b>bold</b>`;
result.innerHTML = "";
range.setStart(p.firstChild, 2);
range.setEnd(p.querySelector('b').firstChild, 3);
window.getSelection().removeAllRanges();
window.getSelection().addRange(range);
}
};
for(let method in methods) {
document.write(`<div><button onclick="methods.${method}()">${method}</button></div>`);
}
methods.resetExample();
</script>
ç¯å²ãæ¯è¼ããã¡ã½ãããåå¨ãã¾ããããã£ãã«ä½¿ããããã¨ã¯ããã¾ãããå¿ è¦ã«ãªã£ããã仿§ ã MDN ããã¥ã¢ã«ãåç §ãã¦ãã ããã
鏿(Selection)
Range ã¯é¸æç¯å²ã管çããããã®æ±ç¨ãªãã¸ã§ã¯ãã§ãããã®ãããªãªãã¸ã§ã¯ãã使ãå©ç¨ãã¾ãã-- ãããã¯èªèº«ã§ã¯è¦è¦çã«ã¯ä½ã鏿ãã¾ããã
ããã¥ã¡ã³ãã®é¸æã¯ Selection ãªãã¸ã§ã¯ãã§è¡¨ç¾ãããwindow.getSelection() ããã㯠document.getSelection() ã§åå¾ãããã¨ãã§ãã¾ãã
é¸æã¯ 0 å以ä¸ã®ç¯å²ãå«ãããã¨ãã§ãã¾ãããããªãã¨ã Selection API 仿§ ã§ã¯ãã®ããã«è¿°ã¹ã¦ãã¾ããã§ãããå®éã«ã¯ Firefox ã®ã¿ã Ctrl+click (Mac ã®å ´å㯠Cmd+click)ã使ç¨ãã¦ããã¥ã¡ã³ãå ã®è¤æ°ã®ç¯å²ã鏿ãããã¨ãã§ãã¾ãã
ãã㯠Firefox ã§ 3ã¤ã®ç¯å²ã鏿ãã¦ããã¹ã¯ãªã¼ã³ã·ã§ããã§ãã:
ä»ã®ãã©ã¦ã¶ã¯æå¤§1ã¤ã®ç¯å²ã ããµãã¼ããã¦ãã¾ããå¾ã§è¦ã¦ããã¾ãããSelection ã¡ã½ããã«ãã£ã¦ã¯è¤æ°ã®ç¯å²ãåå¨ããå¯è½æ§ããããã¨ã示åãã¦ãããã®ãããã¾ããããç¹°ãè¿ãã«ãªãã¾ãã Firefox 以å¤ã®ãã©ã¦ã¶ã¯æå¤§ã§ 1 ã§ãã
ããã¯å°ããªãã¢ã§ãç¾å¨ã®é¸æï¼ä½ãã鏿ãã¦ã¯ãªãã¯ï¼ãããã¹ãã¨ãã¦è¡¨ç¤ºãã¾ãã
Selection ããããã£
åè¿°ããããã«ãçè«ä¸ã鏿ã«ã¯è¤æ°ã®ç¯å²ãå«ã¾ããå ´åãããã¾ãããããã®ç¯å²ãªãã¸ã§ã¯ãã¯ã次ã®ã¡ã½ããã使ç¨ãã¦åå¾ã§ãã¾ãã
getRangeAt(i)â0ããå§ã¾ã i çªç®ã®ç¯å²ãåå¾ãã¾ããFirefox ãé¤ããã¹ã¦ã®ãã©ã¦ã¶ã§ã¯ã0ã®ã¿ã使ç¨ããã¾ãã
ã¾ããå¤ãã®å ´åãå©ä¾¿æ§ãåä¸ããããããã£ãåå¨ãã¾ãã
ç¯å²(range)ã¨åæ§ã鏿ã«ã¯å§ç¹ã¨çµç¹ãããããããã âanchor(ã¢ã³ã«ã¼)âãâfocus(ãã©ã¼ã«ã¹)â ã¨å¼ã°ãã¾ãã
主㪠selection ããããã£ã¯æ¬¡ã®ãã®ã§ã:
anchorNodeâ selection ã®å§ç¹ã®ãã node ã§ããanchorOffsetâ selection ã®å§ç¹ã®anchorNodeã§ã®ãªãã»ããã§ããfocusNodeâ selection ã®çµç¹ã®ãã node ã§ããfocusOffsetâ selection ã®çµç¹ã®focusNodeã§ã®ãªãã»ããã§ããisCollapsedâ selection ãæªé¸æ(空ã®ç¯å²) ãããã¯åå¨ããªãå ´åtrueã«ãªãã¾ããrangeCountâ selection ã«å«ã¾ãã range ã®æ°ã§ãã
鏿(selection)ã® ã¢ã³ã«ã¼/ãã©ã¼ã«ã¹ 㯠Range ã® éå§/çµäº ã¨æ¯è¼ãã¦éè¦ãªéããããã¾ãã
ãåç¥ã®éããRange ãªãã¸ã§ã¯ãã¯å¸¸ã« çµäºã®åã«éå§ãããã¾ãã
鏿ã®å ´åã常ã«ããã§ããããã§ã¯ããã¾ããã
ãã¦ã¹ã§ä½ãã鏿ãããã¨ã¯ããå·¦ããå³ãã¾ãã¯ãå³ããå·¦ãã®ä¸¡æ¹åã§è¡ããã¨ãã§ãã¾ãã
ã¤ã¾ãããã¦ã¹ ãã¿ã³ãæ¼ãã¦ããã¥ã¡ã³ãå ãåã«ç§»åããã¨ããã®çµäºç¹ (ãã©ã¼ã«ã¹) ã¯éå§ç¹ (ã¢ã³ã«ã¼) ã®å¾ã«æ¥ã¾ãã
E.g. ã¦ã¼ã¶ããã¦ã¹ã§é¸æãéå§ããâExampleâ ãã âitalicâ ã¾ã§æä½ããå ´å:
â¦ããããåã鏿ãéæ¹åã«è¡ããã¨ãã§ãã¾ããâitalicâ ãã âExampleâ ã¾ã§éå§ãã㨠(éæ¹å)ããã®çµäº (ãã©ã¼ã«ã¹) ãéå§ (ã¢ã³ã«ã¼) ã®åã«ãªãã¾ãã
Selection ã¤ãã³ã
鏿ç¯å²ã追跡ããããã®ã¤ãã³ããããã¾ã:
elem.onselectstartâelem(ã¾ãã¯ãã®å é¨)ã§é¸æã éå§ ãããã¨ããä¾ãã°ãã¦ã¼ã¶ããã¿ã³ãæ¼ããªãããã¦ã¹ãåããå§ããã¨ãã- ããã©ã«ãã¢ã¯ã·ã§ã³ãé²ãã å ´åã鏿ã¯éå§ããã¾ããããããã£ã¦ããã®è¦ç´ ãã鏿ãéå§ãããã¨ã¯ä¸å¯è½ã«ãªãã¾ãããè¦ç´ ã¯å¼ãç¶ã鏿å¯è½ã§ãã訪åè ã¯ä»ã®å ´æãã鏿ãéå§ããã ãã§æ¸ã¿ã¾ãã
document.onselectionchangeâ 鏿ç¯å²ã夿´ãããã¨ãã- 注æ: ãã®ãã³ãã©ã¯
documentã«å¯¾ãã¦ã®ã¿è¨å®å¯è½ã§ãã
- 注æ: ãã®ãã³ãã©ã¯
鏿ç¯å²ã®è¿½è·¡ãã¢
ããã¯é¸æå¢çã®å¤æ´ã«å¿ãã¦åçã«é¸æå¢çã表示ããå°ããªãã¢ã§ã:
<p id="p">Select me: <i>italic</i> and <b>bold</b></p>
From <input id="from" disabled> â To <input id="to" disabled>
<script>
document.onselectionchange = function() {
let selection = document.getSelection();
let {anchorNode, anchorOffset, focusNode, focusOffset} = selection;
// anchorNode 㨠focusNode ã¯é常ããã¹ããã¼ãã§ã
from.value = `${anchorNode?.data}, offset ${anchorOffset}`;
to.value = `${focusNode?.data}, offset ${focusOffset}`;
};
</script>
鏿(selection)ã®ã³ãã¼ãã¢
鏿ãããã³ã³ãã³ããã³ãã¼ããã2ã¤ã®ã¢ããã¼ããããã¾ã:
document.getSelection().toString()ã使ç¨ãã¦ããã¹ãã¨ãã¦åå¾ã§ãã¾ãã- DOM ãã¼ãã¨ãã¦: åºåºã¨ãªãç¯å²ãåå¾ãããããã®
cloneContents()ãå¼ã³åºãã¾ã(Firefox ã®ãã«ã鏿ããµãã¼ããã¦ãªãå ´åã¯æåã®1ã¤ã® range ã«å¯¾ãã¦ã®ã¿)ã
ããã¦ãããã¯ããã¹ãã¨DOM ãã¼ã両æ¹ã§é¸æç¯å²ãåå¾ãããã¢ã§ã:
<p id="p">Select me: <i>italic</i> and <b>bold</b></p>
Cloned: <span id="cloned"></span>
<br>
As text: <span id="astext"></span>
<script>
document.onselectionchange = function() {
let selection = document.getSelection();
cloned.innerHTML = astext.innerHTML = "";
// range ãã DOM ãã¼ããã¯ãã¼ã³ãã¾ã(ããã§ã¯ multiselect ããµãã¼ããã¦ãã¾ã)
for (let i = 0; i < selection.rangeCount; i++) {
cloned.append(selection.getRangeAt(i).cloneContents());
}
// ããã¹ãã¨ãã¦åå¾
astext.innerHTML += selection;
};
</script>
Selection ã¡ã½ãã
range ã®è¿½å /åé¤ãããããã® Selection ã¡ã½ãã:
getRangeAt(i)â0ããå§ã¾ã i çªç®ã® range ãåå¾ãã¾ããfirefox 以å¤ã®ãã©ã¦ã¶ã¯0ã ãã使ç¨ããã¾ããaddRange(range)â 鏿ç¯å²ã«rangeã追å ãã¾ãããã§ã« range ãé¢é£ä»ãããã¦ããå ´åãfirefox 以å¤ã®ãã©ã¦ã¶ã¯å¼ã³åºããç¡è¦ãã¾ããremoveRange(range)â selection ããrangeãåé¤ãã¾ããremoveAllRanges()â ãã¹ã¦ã® range ãåé¤ãã¾ããempty()âremoveAllRangesã®ã¨ã¤ãªã¢ã¹ã§ãã
ã¾ããRange ãªãã§é¸æç¯å²ããç´æ¥æä½ããããã®ä¾¿å©ãªã¡ã½ãããããã¾ã:
collapse(node, offset)â 鏿ããã range ããæå®ãããnodeã®ä½ç½®offsetã§éå§åã³çµäºããæ°ãã range ã«ç½®ãæãã¾ããsetPosition(node, offset)âcollapseã®ã¨ã¤ãªã¢ã¹ã§ããcollapseToStart()â 鏿ç¯å²ã®å§ç¹ã«æãããã¿ã¾ã(空㮠range ã«ç½®ãæãã¾ã)collapseToEnd()â 鏿ç¯å²ã®çµç¹ã«æãããã¿ã¾ãextend(node, offset)â 鏿ç¯å²ã® focus ãæå®ãããnodeã®ä½ç½®offsetã«ç§»åãã¾ããsetBaseAndExtent(anchorNode, anchorOffset, focusNode, focusOffset)â 鏿ç¯å²ã® range ããæå®ãããå§ç¹anchorNode/anchorOffsetã¨çµç¹focusNode/focusOffsetã«ç½®ãæãã¾ãããããã®éã«ãããã¹ã¦ã®ã³ã³ãã³ãã鏿ããã¾ããselectAllChildren(node)ânodeã®ãã¹ã¦ã®åã鏿ãã¾ããdeleteFromDocument()â ããã¥ã¡ã³ããã鏿ãããã³ã³ãã³ããåé¤ãã¾ããcontainsNode(node, allowPartialContainment = false)â 鏿ç¯å²ãnodeãå«ãããã§ãã¯ãã¾ã(2çªãã®å¼æ°ãtrueã®å ´åã¯é¨åçã«å«ããã許å¯ãã)ã
ãããã£ã¦ãå¤ãã®ã¿ã¹ã¯ã§ Selection ã¡ã½ãããå¼ã³åºããã¨ãã§ããåºç¤ã¨ãªã Range ãªãã¸ã§ã¯ãã«ã¢ã¯ã»ã¹ããå¿
è¦ã¯ããã¾ããã
ä¾ãã°ãæ®µè½ <p> ã®ã³ã³ãã³ãå
¨ä½ã鏿ããã«ã¯æ¬¡ã®ããã«ãã¾ã:
<p id="p">Select me: <i>italic</i> and <b>bold</b></p>
<script>
// <p> ã® 0 çªç®ã®åããæå¾ã®åã¾ã§ã鏿
document.getSelection().setBaseAndExtent(p, 0, p, p.childNodes.length);
</script>
The same thing using ranges:
<p id="p">Select me: <i>italic</i> and <b>bold</b></p>
<script>
let range = new Range();
range.selectNodeContents(p); // or selectNode(p) ã§ <p> ã¿ã°ã鏿ãã¾ã
document.getSelection().removeAllRanges(); // åå¨ãã鏿ç¯å²ãã¯ãªã¢ãã¾ã
document.getSelection().addRange(range);
</script>
鏿ç¯å²ããã§ã«åå¨ããå ´åãremoveAllRanges() ã§æåã«ç©ºã«ãããã®å¾ range ã追å ãã¦ãã ãããããã§ãªãå ´åãFirefox 以å¤ã®ãã©ã¦ã¶ã¯æ°ãã range ãç¡è¦ãã¾ãã
setBaseAndExtent ãªã©ã®ããã¤ãã® selection ã¡ã½ããã¯ä¾å¤ã§ãæ¢åã®é¸æç¯å²ãç½®ãæãã¾ãã
ãã©ã¼ã ã³ã³ããã¼ã«ã§ã®é¸æ
input ã textarea ã¨è¡ã£ããã©ã¼ã è¦ç´ 㯠Selection ã Range ãªãã¸ã§ã¯ããªãã§ã鏿ã®ããã®ç¹å¥ãªAPI ãæä¾ãã¾ããå
¥åå¤ã¯ HTML ã§ã¯ãªãç´ç²ãªããã¹ããªã®ã§ããã®ãããªãªãã¸ã§ã¯ãã¯å¿
è¦ãªãããã¹ã¦ãããã·ã³ãã«ã§ãã
ããããã£:
input.selectionStartâ 鏿éå§ä½ç½®ï¼æ¸ãè¾¼ã¿å¯è½ï¼input.selectionEndâ 鏿çµäºä½ç½®ï¼æ¸ãè¾¼ã¿å¯è½ï¼input.selectionDirectionâ 鏿æ¹åãæ¬¡ã®ããããã§ã: âforwardâ, âbackwardâ ããã㯠ânoneâ (ä¾ ãã¦ã¹ã®ããã«ã¯ãªãã¯ã§é¸æããå ´å ) ã§ãã
ã¤ãã³ã:
input.onselectâ ä½ãã鏿ãããã¨ãã«çºçãã¾ãã
ã¡ã½ãã:
-
input.select()â ããã¹ãã³ã³ããã¼ã«å ã®ãã¹ã¦ã鏿ãã¾ãï¼inputã®ä»£ããã«textareaã OK ã§ãï¼ã -
input.setSelectionRange(start, end, [direction])â 鏿ç¯å²ããstartä½ç½®ããendä½ç½®ã¾ã§ãæå®ãããæ¹å(ä»»æ)ã«åºãã¾ãã -
input.setRangeText(replacement, [start], [end], [selectionMode])â ããã¹ãã®ç¯å²ãæ°ããããã¹ãã«ç½®ãæãã¾ããä»»æã®å¼æ°
startã¨endãæå®ãããå ´åã¯éå§/çµäºã®ç¯å²ãè¨å®ãã¾ããããã§ãªãå ´åã¯ã¦ã¼ã¶ã®é¸æã使ç¨ããã¾ããæå¾ã®å¼æ°
selectionModeã¯ããã¹ããç½®æããããã¨ã®é¸ææ¹æ³ã決å®ãã¾ããæ¬¡ã®å¤ãæå®ã§ãã¾ã:"select"â æ°ãã«æ¿å ¥ãããããã¹ãã鏿ããã¾ãã"start"â 鏿ç¯å²ã¯æ¿å ¥ãããããã¹ãã®ç´åã«æãããã¾ãã¾ã(ã«ã¼ã½ã«ã¯ãã®ç´åã«ãªãã¾ã)ã"end"â 鏿ç¯å²ã¯æ¿å ¥ãããããã¹ãã®ç´å¾ã«æãããã¾ãã¾ã(ã«ã¼ã½ã«ã¯ãã®ç´å¾ã«ãªãã¾ã)ã"preserve"â 鏿ç¯å²ãä¿ã¨ãã¨ãã¾ããããã©ã«ãã¯ãã®åä½ã«ãªãã¾ãã
ããã§ã¯ããããã®ã¡ã½ããã®åä½ãè¦ã¦ã¿ã¾ãããã
ä¾: 鏿ã®è¿½è·¡
ä¾ãã°ããã®ã³ã¼ã㯠onselect ã¤ãã³ãã使ç¨ãã¦é¸æã追跡ãã¾ã:
<textarea id="area" style="width:80%;height:60px">
Selecting in this text updates values below.
</textarea>
<br>
From <input id="from" disabled> â To <input id="to" disabled>
<script>
area.onselect = function() {
from.value = area.selectionStart;
to.value = area.selectionEnd;
};
</script>
注æãã¦ãã ãã:
onselectã¯ãªã«ãã鏿ãããã¨ãã«çºçãã¾ããã鏿ãé¤å»ãããã¨ãã«ã¯çºçãã¾ãããdocument.onselectionchangeã¤ãã³ãã¯ã仿§ã«ããã¨documentã®é¸æãç¯å²ã¨ã¯é¢ä¿ãªãããããã©ã¼ã ã³ã³ããã¼ã«å ã®é¸æã§ã¯çºçãã¹ãã§ã¯ããã¾ãããä¸é¨ã®ãã©ã¦ã¶ã«ã¯ã¤ãã³ããçæãã¾ãããããã«é ¼ãã¹ãã§ã¯ããã¾ããã
ä¾: ã«ã¼ã½ã«ã®ç§»å
鏿ç¯å²ãè¨å®ãã selectionStart 㨠selectionEnd ã夿´ãããã¨ãã§ãã¾ãã
éè¦ãªã¨ãã¸ã±ã¼ã¹ã¯ selectionStart 㨠selectionEnd ãäºãã«çããå ´åã§ãããã®ã¨ããããã¯ã¾ãã«ã«ã¼ã½ã«ä½ç½®ã«ãªãã¾ãããããã¯ä½ã鏿ããã¦ããªãå ´åã¯ã鏿ã¯ã«ã¼ã½ã«ä½ç½®ã§æãããã¾ãã¾ãã
ãããã£ã¦ãselectionStart 㨠selectionEnd ãåãå¤ã«è¨å®ãããã¨ã§ã«ã¼ã½ã«ãç§»åããããã¨ãã§ãã¾ãã
ä¾:
<textarea id="area" style="width:80%;height:60px">
Focus on me, the cursor will be at position 10.
</textarea>
<script>
area.onfocus = () => {
// ãã©ã¦ã¶ã® "focus" ã¢ã¯ã·ã§ã³ãçµäºãããã¨ã«å®è¡ãããããã®ã¼ãé
å»¶ã® setTimeout
setTimeout(() => {
// ä»»æã®é¸æãè¨å®ã§ãã¾ã
// éå§ = çµäº ã®å ´åãã«ã¼ã½ã«ã¯ã¾ãã«ãã®å ´æã§ã
area.selectionStart = area.selectionEnd = 10;
});
};
</script>
ä¾: 鏿ã®å¤æ´
鏿å
容ã夿´ããã«ã¯ãinput.setRangeText() ã¡ã½ãããå©ç¨ã§ãã¾ãããã¡ãããselectionStart/End ãèªã¿åãã鏿ã«é¢ããç¥èãããã° value ã®å¯¾å¿ããé¨åæååã夿´ãããã¨ã¯ã§ãã¾ãããsetRangeText ã¯ããå¼·åã§ãå¤ãã®å ´åãã便å©ã§ãã
ããã¯ããããè¤éãªã¡ã½ããã§ããæãã·ã³ãã«ãªåä¸å¼æ°ã®ãã©ã¼ã ã§ã¯ãã¦ã¼ã¶ã®é¸æããç¯å²ãç½®ãæãã鏿ãåé¤ãã¾ãã
ä¾ãã°ãããã§ã¯ã¦ã¼ã¶ã®é¸æã¯ *...* ã§å²ã¾ãã¾ã:
<input id="input" style="width:200px" value="Select here and click the button">
<button id="button">Wrap selection in stars *...*</button>
<script>
button.onclick = () => {
if (input.selectionStart == input.selectionEnd) {
return; // ä½ã鏿ããã¦ããªã
}
let selected = input.value.slice(input.selectionStart, input.selectionEnd);
input.setRangeText(`*${selected}*`);
};
</script>
弿°ãå¢ãããã¨ã§ãç¯å²ã® start 㨠end ãè¨å®ãããã¨ãã§ãã¾ãã
ãã®ä¾ã§ã¯ãå
¥åããã¹ããã "THIS" ãè¦ã¤ãããããç½®ãæããç½®æããã鏿ç¯å²ãç¶æãã¾ã:
<input id="input" style="width:200px" value="Replace THIS in text">
<button id="button">Replace THIS</button>
<script>
button.onclick = () => {
let pos = input.value.indexOf("THIS");
if (pos >= 0) {
input.setRangeText("*THIS*", pos, pos + 4, "select");
input.focus(); // 鏿ãè¦ããããã«ããããã® focus
}
};
</script>
ä¾: ã«ã¼ã½ã«ä½ç½®ã«æ¿å ¥
ä½ã鏿ããã¦ããªãå ´åãããã㯠setRangeText ã§ start 㨠end ãçããããå ´åãæ°ããããã¹ããåã«æ¿å
¥ãããã ãã§ä½ãåé¤ã¯ããã¾ããã
setRangeText ã使ç¨ã㦠âã«ã¼ã½ã«ä½ç½®â ã«æ¿å
¥ãããã¨ãã§ãã¾ãã
ããã¯ã«ã¼ã½ã«ä½ç½®ã« "HELLO" ãæ¿å
¥ãããã®ç´å¾ã«ã«ã¼ã½ã«ãç½®ããã¿ã³ã§ãã鏿ã空ã§ãªãå ´åã¯ç½®ãæãããã¾ã(selectionStart!=selectionEnd ãæ¯è¼ãããã¨ã§ãããæ¤ç¥ãã代ããã«ãªã«ããè¡ããã¨ãã§ãã¾ã):
<input id="input" style="width:200px" value="Text Text Text Text Text">
<button id="button">Insert "HELLO" at cursor</button>
<script>
button.onclick = () => {
input.setRangeText("HELLO", input.selectionStart, input.selectionEnd, "end");
input.focus();
};
</script>
鏿ä¸å¯ã«ãã
鏿ä¸å¯ã«ããããã®ï¼ã¤ã®æ¹æ³ãããã¾ã:
-
CSS ããããã£
user-select: noneã使ç¨ãã¾ã.<style> #elem { user-select: none; } </style> <div>Selectable <div id="elem">Unselectable</div> Selectable</div>ããã¯
elemããå§ã¾ã鏿ã許å¯ãã¾ãããã§ãããã¦ã¼ã¶ã¯å¥ã®å ´æãã鏿ãéå§ãã¦ããã®ä¸ã«elemãå«ãããããã¾ãããããã¨ã
elemã¯document.getSelection()ã®ä¸é¨ã«ãªãã®ã§ã鏿ã¯å®éã«ã¯èµ·ããã¾ãããããã®ä¸èº«ã¯é常ã³ãã¼/è²¼ãä»ãã§ã¯ç¡è¦ããã¾ãã -
onselectstartã¾ãã¯mousedownã¤ãã³ãã§ãããã©ã«ãåä½ã鲿¢ãã¾ãã<div>Selectable <div id="elem">Unselectable</div> Selectable</div> <script> elem.onselectstart = () => false; </script>ããã«ãã
elemãã鏿ãéå§ããã®ãã¨ã¯ã§ããªããªãã¾ããã訪åè ã¯å¥ã®è¦ç´ ã§é¸æãéå§ãã¦elemã¾ã§åºãããã¨ãã§ãã¾ããããã¯ã鏿ãããªã¬ã¼ããåãã¢ã¯ã·ã§ã³ã«å¥ã®ã¤ãã³ããã³ãã©ã¼ãããå ´åã«ä¾¿å©ã§ã(ä¾.
mousedown)ããã®ãããç«¶åãé¿ããããã«é¸æãç¡å¹ã«ãã¤ã¤ãä¾ç¶ã¨ãã¦elemã®å 容ã¯ã³ãã¼ã§ããããã«ãã¾ãã -
document.getSelection().empty()ãçºçãããã¨ãäºå¾ã®é¸æãã¯ãªã¢ãããã¨ãã§ãã¾ããããã¯é¸æã表示ããã¦æ¶ããã¨ãã«ä¸è¦ãªç¹æ» ãå¼ãèµ·ããããããã£ãã«ä½¿ããã¾ããã
ãªãã¡ã¬ã³ã¹
ãµããª
鏿ã®ããã®ï¼ã¤ã®ç°ãªã API ã«ã¤ãã¦èª¬æãã¾ãã:
- document ã«å¯¾ãã¦:
Selectionã¨Rangeãªãã¸ã§ã¯ã input,textareaã«å¯¾ãã¦: 追å ã®ã¡ã½ããã¨ããããã£
ï¼ã¤ç®ã®APIã¯ããã¹ãã«å¯¾ãã¦ã®ã¿åä½ããã®ã§ã¨ã¦ãã·ã³ãã«ã§ãã
æããã使ç¨ãããã¬ã·ãã¯ããããæ¬¡ã®ãã®ã§ã:
- 鏿ãåå¾ãã:
let selection = document.getSelection(); let cloned = /* 鏿ãããã¼ãã®ã¯ãã¼ã³ã使ããè¦ç´ */; // 次㫠selection.getRangeAt(0) ã«å¯¾ã㦠Range ã¡ã½ãããé©ç¨ãã¾ãã // ãããã¯ãããã®ããã«è¤æ°é¸æããµãã¼ãããããã«ãã¹ã¦ã®ç¯å²ã«é©ç¨ãã¾ãã for (let i = 0; i < selection.rangeCount; i++) { cloned.append(selection.getRangeAt(i).cloneContents()); } - 鏿ãè¨å®ãã:
let selection = document.getSelection(); // ç´æ¥: selection.setBaseAndExtent(...from...to...); // ããã㯠rangeãã使ãè¨å®ãã¾ã: selection.removeAllRanges(); selection.addRange(range);
ããã¦ãæå¾ã«ã«ã¼ã½ã«ã«ã¤ãã¦ã§ãã<textarea> ã®ãããªç·¨éå¯è½ãªè¦ç´ ã®ã«ã¼ã½ã«ä½ç½®ã¯å¸¸ã«é¸æç¯å²ã®å
é ãããã¯æ«å°¾ã«ãªãã¾ããããã使ç¨ãã¦ãelem.selectionStart ã elem.selectionEnd ãè¨å®ãããã¨ã§ã«ã¼ã½ã«ä½ç½®ãåå¾ãããã«ã¼ã½ã«ãç§»åããããã¨ãã§ãã¾ãã
ã³ã¡ã³ã
<code>ã¿ã°ã使ã£ã¦ãã ãããè¤æ°è¡ã®å ´åã¯<pre>ãã10è¡ãè¶ ããå ´åã«ã¯ãµã³ãããã¯ã¹ã使ã£ã¦ãã ãã(plnkr, JSBin, codepenâ¦)ã