Javascript-форум (https://javascript.ru/forum/)
-   Events/DOM/Window (https://javascript.ru/forum/events/)
-   -   Помогите написать текстовый редактор (https://javascript.ru/forum/events/72942-pomogite-napisat-tekstovyjj-redaktor.html)

Devil198711 08.03.2018 22:46

Помогите написать текстовый редактор
 
Есть необходимость создать простой текстовый редактор на чистом js под chrome. При этом реализовать его надо без iframe а на div contenteditable.
потратил уже целый день на поиск решение как вернуть каретку в прежнее положение если кликаю по кнопке (ну к примеру bold)
Помогите ПЛИЗ!!!

j0hnik 09.03.2018 02:26

<!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8">
	<title>Document</title>
	<style>
		#area{
			border: 1px solid gray;
			width: 500px;
			height: 100px;
			font-weight: 
		}

	</style>
</head>
<body>
	<div contenteditable id="area"></div>
	font-weight: <button>bold</button>
	<script>
		document.querySelector('button').addEventListener('mouseup', function(){
			document.querySelector('#area').focus();
		});

	</script>

рони 09.03.2018 08:53

j0hnik,
условно 5 слов, выделено третье, по клику на кнопку bold, это слово стало "жирным", а курсор встал после него.

Devil198711 09.03.2018 13:18

Цитата:

Сообщение от j0hnik (Сообщение 480093)
<!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8">
	<title>Document</title>
	<style>
		#area{
			border: 1px solid gray;
			width: 500px;
			height: 100px;
			font-weight: 
		}

	</style>
</head>
<body>
	<div contenteditable id="area"></div>
	font-weight: <button>bold</button>
	<script>
		document.querySelector('button').addEventListener('mouseup', function(){
			document.querySelector('#area').focus();
		});

	</script>


Спасибо частично помогло:)

j0hnik 09.03.2018 16:14

Цитата:

Сообщение от рони (Сообщение 480096)
j0hnik,
условно 5 слов, выделено третье, по клику на кнопку bold, это слово стало "жирным", а курсор встал после него.

Рони, это неудобно, а если вам нужен и жирный и курсив?
Можете редактор открыть (word например) и посмотреть как там.

рони 09.03.2018 16:34

Цитата:

Сообщение от j0hnik
Можете редактор открыть (word например)

есть куча плагинов текстовых редакторов, тут изобретается велосипед.

j0hnik 09.03.2018 18:47

Цитата:

Сообщение от рони (Сообщение 480096)
j0hnik,
условно 5 слов, выделено третье, по клику на кнопку bold, это слово стало "жирным", а курсор встал после него.

Значит это как доп. задание?

рони 09.03.2018 21:06

Цитата:

Сообщение от j0hnik
Значит это как доп. задание?

это было моё предположение.

рони 09.03.2018 21:07

Devil198711,
на всякй случай 10 Best jQuery and HTML5 WYSIWYG Plugins

Devil198711 09.03.2018 23:38

У меня стоит задача написать редактор на чистом js, многое уже сделано, но вот вот при вызове модального окна для ввода данных о ссылкке происходит потеря фокуса выделенного текста. Вот мне и нужно после ввода данных вернуть фокус в прежнее место, как это работало с iframe

рони 09.03.2018 23:51

Devil198711,
редакторы по ссылке выше, содержат все необходимые вам решения, в том числе и на js, нужно только читать их код.

рони 10.03.2018 01:02

contenteditable возвращение курсора в конец выделения
 
Devil198711,
возможно есть проще варианты
<!DOCTYPE html>

<html>
<head>
  <title>Untitled</title>
  <meta charset="utf-8">
  <style type="text/css">
  </style>

  <script>
    window.addEventListener('DOMContentLoaded', function() {
       var myTextArea = document.querySelector('#myTextArea'),
       but = document.querySelector('#but');
       but.addEventListener('click', function() {
       if(!window.getSelection().anchorNode) return;

       var selection = window.getSelection().getRangeAt(0);
            var selectedText = selection.extractContents();
            var tagname = document.createElement('b');
            tagname.appendChild(selectedText);

          if(tagname.textContent.length) {
          selection.insertNode(tagname);
          var range = document.createRange();
          range.setStart(tagname.childNodes[0], tagname.textContent.length);
          range.collapse(true);
          var sel = window.getSelection();
          sel.removeAllRanges();
          sel.addRange(range);
          }
          else   myTextArea.focus()


       });
         });
  </script>
</head>

<body>
 <div  id="myTextArea" style="background: #ccc" contenteditable="true">
 текст <br />ещё текст<br />и ещё
</div>
<br />
<input type="button" value="Вставить тег b" id="but">

</body>
</html>

Devil198711 10.03.2018 14:43

Цитата:

Сообщение от рони (Сообщение 480163)
Devil198711,
возможно есть проще варианты
<!DOCTYPE html>

<html>
<head>
  <title>Untitled</title>
  <meta charset="utf-8">
  <style type="text/css">
  </style>

  <script>
    window.addEventListener('DOMContentLoaded', function() {
       var myTextArea = document.querySelector('#myTextArea'),
       but = document.querySelector('#but');
       but.addEventListener('click', function() {
       if(!window.getSelection().anchorNode) return;

       var selection = window.getSelection().getRangeAt(0);
            var selectedText = selection.extractContents();
            var tagname = document.createElement('b');
            tagname.appendChild(selectedText);

          if(tagname.textContent.length) {
          selection.insertNode(tagname);
          var range = document.createRange();
          range.setStart(tagname.childNodes[0], tagname.textContent.length);
          range.collapse(true);
          var sel = window.getSelection();
          sel.removeAllRanges();
          sel.addRange(range);
          }
          else   myTextArea.focus()


       });
         });
  </script>
</head>

<body>
 <div  id="myTextArea" style="background: #ccc" contenteditable="true">
 текст <br />ещё текст<br />и ещё
</div>
<br />
<input type="button" value="Вставить тег b" id="but">

</body>
</html>



Спасибо, но проблемы с вставкой тегов я решил уже, единственное что мне никак не поддается это вернуть выделение в прежнее положение при потере фокуса редактора. То есть когда я нажимаю на кнопку вставки ссылки появляется модальное окно с тремя полями форм (урл, текст ссылки, тайтл), и при установке курсора в любое поле редактор теряет фокус и ответственно забывает выделенный текст, вот я и не могу понять как при нажатии кнопки "вставить ссылку" заменить выделенный текст или вставить там где была каретка

рони 10.03.2018 14:54

Devil198711,
не понимаю, разве код выше не решает ваши проблемы?
что мешает сохранить выделение и вернуть обратно? код перед вами

рони 10.03.2018 14:59

Devil198711,
медитировать здесь https://learn.javascript.ru/range-textrange-selection

Devil198711 10.03.2018 15:11

Цитата:

Сообщение от рони (Сообщение 480205)
Devil198711,
не понимаю, разве код выше не решает ваши проблемы?
что мешает сохранить выделение и вернуть обратно? код перед вами

И беда что я не могу понять как это сделать (Слишком туп наверное)

Devil198711 10.03.2018 20:04

Всем спасибо за помощь, вот что у меня получилось
<!DOCTYPE HTML>
<html>

<head>
  <meta charset="utf-8">
</head>

<body>
  <div id="editor" style="border:1px dashed #999; color:#666; background:#EEE; padding:2px 5px; margin:10px 0;" contenteditable>
    какой-то текст
  </div>
  <div>
    <input onclick="setSelection()" type="button" value="Выделить">
    <input onclick="saveSelection()" type="button" value="Сохранить выделение">
  </div>
  <script>
    var wsEditor = document.getElementById('editor');
    var wsSelection;
    function setSelection() {
        if (wsSelection) {
            var sel = window.getSelection();
            var rng = document.createRange();
            rng.selectNode(wsEditor);
            rng.setStart(wsSelection.startContainer, wsSelection.startOffset);
            rng.setEnd(wsSelection.endContainer, wsSelection.endOffset);
            sel.removeAllRanges();
            sel.addRange(rng);
        }                    
    }
    function saveSelection() {
        wsEditor.focus()
        var sel = window.getSelection();
        if (sel.anchorNode) {
            wsSelection = sel.getRangeAt(0);
        }
    }
  </script>


</body>

рони 10.03.2018 20:29

Devil198711,
добавьте run в пост №17
[HTML  run][/HTML]

Devil198711 14.03.2018 16:01

Подскажите как получить картинку которая в данный момент выделена

j0hnik 14.03.2018 19:22

смотря как выделена.
event.target ссылка на объект вызвавший событие.

Devil198711 16.03.2018 01:13

Цитата:

Сообщение от j0hnik (Сообщение 480530)
смотря как выделена.
event.target ссылка на объект вызвавший событие.

Выделена обычным выделением курсором мыши

j0hnik 16.03.2018 01:41

Devil198711,
window.getSelection().anchorNode.querySelector('img')

Devil198711 16.03.2018 12:33

Цитата:

Сообщение от j0hnik (Сообщение 480649)
Devil198711,
window.getSelection().anchorNode.querySelector('img')

Проблема в этом способе в том, что если стоит рядом несколько картинок то выбирается не выделенная а первая в div

j0hnik 16.03.2018 12:51

Devil198711,
window.getSelection().anchorNode.querySelectorAll('img')[укажите номер нужной]

Devil198711 16.03.2018 14:09

Цитата:

Сообщение от j0hnik (Сообщение 480686)
Devil198711,
window.getSelection().anchorNode.querySelectorAll('img')[укажите номер нужной]

Так втомто и дело что я не знаю какую в данный момент выделил пользователь


Часовой пояс GMT +3, время: 13:37.