Выделите текст DIV как пользовательский тип символов в поле ввода

Я видел много сообщений, касающихся выделения текста в DIV с помощью javascript, но никто не делает то, что я ищу.

То, что мне нужно сделать, – выделить текст в пределах определенного DIV, символ по символу, когда пользователь вводит поисковый запрос. И наоборот, по мере того, как пользователь обращает или удаляет символы, мне нужно «удалить выделение» текста того же DIV.

Я предполагаю, что это уже что-то было сделано кем-то, но я еще не нашел сообщение здесь или из Google, который ведет себя точно так, как мне нужно.

Любые отзывы приветствуются.

этот код выполняет как пользовательские типы символов в поле ввода. Проблема в том, что в некоторых случаях она вставляет строку «» в таблицу по мере ввода, и я не знаю, почему, поэтому я ищу другое решение.

Спасибо за ваш отзыв!

function filterTable(Stxt, table) { dehighlight(document.getElementById(table)); if (Stxt.value.length > 0) highlight(Stxt.value.toLowerCase(), document.getElementById(table)); } function dehighlight(container) { for (var i = 0; i < container.childNodes.length; i++) { var node = container.childNodes[i]; if (node.attributes && node.attributes['class'] && node.attributes['class'].value == 'highlighted') { node.parentNode.parentNode.replaceChild( document.createTextNode(node.parentNode.innerHTML.replace(/]+>/g, "")),node.parentNode); return; } else if (node.nodeType != 3) { dehighlight(node); } } } function highlight(Stxt, container) { for (var i = 0; i = 0) { var new_node = document.createElement('span'); node.parentNode.replaceChild(new_node, node); var result; while ((result = data_low.indexOf(Stxt)) != -1) { new_node.appendChild(document.createTextNode(data.substr(0, result))); new_node.appendChild(create_node( document.createTextNode(data.substr(result, Stxt.length)))); data = data.substr(result + Stxt.length); data_low = data_low.substr(result + Stxt.length); } new_node.appendChild(document.createTextNode(data)); } } else { highlight(Stxt, node); } } } function create_node(child) { var node = document.createElement('span'); node.setAttribute('class', 'highlighted'); node.attributes['class'].value = 'highlighted'; node.appendChild(child); return node; } 

Это можно легко сделать с помощью регулярного выражения для изменения содержимого div. Вот простая реализация:

 var s = document.getElementById('s'); // your input var div = document.getElementById('a'); // the div to change var t = a.textContent || a.innerText; s.onkeyup = function(){ div.innerHTML = this.value ? t.replace(new RegExp('('+this.value+')','ig'), '$1') : t; }; 

Демонстрация (нажмите «Запустить с помощью JS»)


РЕДАКТИРОВАТЬ :

Эта более сложная версия работает, даже если у вас есть таблицы и прочее:

 var s = document.getElementById('s'); var div = document.getElementById('a'); function changeNode(n, r, f) { f=n.childNodes; for(c in f) changeNode(f[c], r); if (n.data) { f = document.createElement('span'); f.innerHTML = n.data.replace(r, '$1'); n.parentNode.insertBefore(f, n); n.parentNode.removeChild(n); } } s.onkeyup = function(){ var spans = document.getElementsByClassName('found'); while (spans.length) { var p = spans[0].parentNode; p.innerHTML = p.textContent || p.innerText; } if (this.value) changeNode( div, new RegExp('('+this.value+')','gi') ); }; 

Демонстрация (нажмите «Запустить с помощью JS»)

У моей библиотеки Rangy есть поддержка для этого, хотя я признаю, что это довольно большой скрипт для этого использования.

Демо: http://rangy.googlecode.com/svn/trunk/demos/textrange.html

Я сделал демоверсию, которая использует регулярное выражение.

 // Input element var input = document.getElementById("highlighter"), // Text container element divText = document.getElementById("text"), // using textContent property if it exists textProp = ("textContent" in divText) ? "textContent" : "innerText", // Getting text to discard html tags (delete line 6 and use divText.innerHTML if you want to keep the HTML tags) originalText = divText[textProp]; function handler(){ // if Input.value is empty clear the highlights if(!this.value){ divText.innerHTML = originalText; return true; } // Regex to group the matches, with tags 'global' and 'case insensitive' var regex = new RegExp("("+this.value+")", "ig"); // replace text with the new one ($1 refers to first group matched by regex) divText.innerHTML = originalText.replace(regex, "$1"); }; // adding listener to input.. IE uses attachEvent method input.addEventListener("keyup", handler, false); 

JSFiddle DEMO