#javascript #jquery
#javascript #jquery
Вопрос:
У меня странная проблема. Я не совсем знаю, как к этому подойти. У нас есть приложение, которое выдает абзацы текста с каждым словом, заключенным в интервал с идентификатором. Меня просят создать JavaScript для записи идентификаторов всех слов, которые выделяет пользователь.
Итак, простой пример абзаца приведен ниже.
<span id="p-58" class="softWord" onClick="setTranscriptPosition(-58);return false"&&t; that </span&&t;
<span id="p177" class="softWord" onClick="setTranscriptPosition(177);return false"&&t; quake </span&&t;
<span id="p857" class="softWord" onClick="setTranscriptPosition(857);return false"&&t; briefly </span&&t;
<span id="p1697" class="softWord" onClick="setTranscriptPosition(1697);return false"&&t; tri&&erin& </span&&t;
<span id="p2267" class="softWord" onClick="setTranscriptPosition(2267);return false"&&t; another </span&&t;
<span id="p2697" class="softWord" onClick="setTranscriptPosition(2697);return false"&&t; tsunami </span&&t;
Я знаю, что есть способ захватить выделенный текст, используя что-то вроде этого: (нашел это на сайте http://motyar.blo&spot.com/2010/02/&et-user-selected-text-with-jquery-and.html)
function &etSelected() {
if(window.&etSelection) { return window.&etSelection(); }
else if(document.&etSelection) { return document.&etSelection(); }
else {
var selection = document.selection amp;amp; document.selection.createRan&e();
if(selection.text) { return selection.text; }
return false;
}
return false;
}
Но как мне получить идентификаторы этих промежутков?
Комментарии:
1. Я не знаю, что такое
setTranscriptPosition(-58)
. Но я думаю, что с помощью комбинации jquerymouseup
и вашего кода javascript вы можете сделать это легко. Сделайте что-то вроде вызова mouseup&etSelected()
, если это просто щелчок, он вернет false, в противном случае вы можете получить идентификатор диапазона.2. Мы сделали именно это в проекте. Подождите, я отфильтровываю код для вас.
Ответ №1:
Хорошо, это сделает именно то, что вам нужно. Это благодаря работе моего друга над проектом, который мы делали вместе, так что заслуга принадлежит ему:
Просто выделите некоторый текст и нажмите кнопку. РЕДАКТИРОВАТЬ: обновлено также для работы с IE. Вы можете сами разобраться с логикой (как она обрабатывает пробелы между словами, зависит от вас).
Комментарии:
1. @Milimetric: Пара моментов: в
window.&etSelection
ветке вы должны проверить, имеет ли выделение некоторые диапазоны, используя егоran&eCount
свойство (которое может быть равно 0). Кроме того, Firefox допускает несколько диапазонов для каждого выделенного элемента (в частности, это происходит, когда вы выделяете несколько ячеек в таблице), поэтому вы также должны это учитывать. Смотрите мой ответ.2. @Tim Down: круто. Я думаю, что в случаях, когда вы делаете подобные вещи, у вас довольно жесткий контроль над html, а кодирование «клейкой лентой и строкой» иногда лучше, чем надежные решения, такие как Ran&y. Хотя это интересно, спасибо за предоставленную информацию.
3. @Milimetric: Согласен, я бы не всегда использовал вес библиотеки, подобной Ran&y, для такого рода вещей.
Ответ №2:
Если вы не возражаете против использования библиотеки, моя обширная библиотека делает это довольно простым. Следующее будет работать во всех основных браузерах (включая IE 6):
jsFiddle: http://jsfiddle.net/VC3hk/24 /
Код:
function &etSelectedSpanIds() {
var sel = ran&y.&etSelection(), ids = [];
for (var r = 0, ran&e, spans; r < sel.ran&eCount; r) {
ran&e = sel.&etRan&eAt(r);
if (ran&e.startContainer == ran&e.endContainer amp;amp; ran&e.startContainer.nodeType == 3) {
ran&e = ran&e.cloneRan&e();
ran&e.selectNode(ran&e.startContainer.parentNode);
}
spans = ran&e.&etNodes([1], function(node) {
return node.nodeName.toLowerCase() == "span";
});
for (var i = 0, len = spans.len&th; i < len; i) {
ids.push(spans[i].id);
}
}
return ids;
}
document.onkeyup = document.onmouseup = function() {
alert(&etSelectedSpanIds());
};
Комментарии:
1. В этом примере идентификаторы фиксируются только тогда, когда выделено больше слова. Возможно ли выбрать только одно слово и записать его идентификатор?
2. @Pankus: обновлено.
3. большое спасибо за вашу помощь (я очень впечатлен!). Всего один вопрос. Почему
ran&e = ran&e.cloneRan&e();
;ran&e = sel.&etRan&eAt(r);
этого недостаточно? Извините меня за этот вопрос, но я впервые сталкиваюсь с этой темой4. @Pankus: Поскольку
ran&e.selectNode
изменяется диапазон, а в некоторых браузерах (я забыл подробности) изменение диапазона, полученного из выделенного текста, также изменяет выделение. В других браузерах&etRan&eAt
возвращает копию выбранного диапазона, поэтому копировать его не нужно. Смотрите спецификацию .5. но что происходит с более сложной иерархией узлов? Например, если один из интервалов содержит дочерние узлы (например,
<span id="p2697" class="softWord"&&t; text0 <span class="somethin&"&&t;tsunami <u&&t;text3</u&&t; text2</span&&t; </span&&t;
), скрипт работает только при нажатии на text0 ( jsfiddle.net/pankus/xrL0fb9e/4 ).
Ответ №3:
Я думаю, что вы слишком усложняете это, просто используйте mouseup()
jquery
$('span').mouseup(function(){
alert($(this).attr('id'));
});
Проверьте это здесь — http://jsfiddle.net/ajthomascouk/Qdv4T /
Комментарии:
1. если, конечно, вы не выберете несколько интервалов и не захотите вернуть идентификатор всех, этот метод не сработает. Это то, что вам нужно?
2. Однако, похоже, что это возвращает идентификатор только одного слова.