javascripthtmlcursor-positionvirtual-keyboard

How to write a character where the cursor is with a virtual keyboard?


I'm working on a live HTML editor. It's basically for mobile users. So I've made a virtual keyboard that has the HTML tags. However, I'm facing a problem: the keyboard only prints the tags at the end of another tag. So it isn't working as I want it to be.

Here is the code.

(function() {
  'use strict';
  var i, c, t, delay = 5000,
    kb = document.getElementById('keyboard');
  /* get all the input elements within the div whose id is "keyboard */
  i = kb.getElementsByTagName('input');
  /* loop through all the elements */

  for (c = 0; c < i.length; c++) {
    /* find all the the input type="button" elements */
    if (i[c].type === 'button') {
      /* add an onclick handler to each of them  and set the function to call */
      i[c].addEventListener('onclick', makeClickHandler(c));
    }
  }

  /* this is the type="reset" input */
  document.getElementById('clear').addEventListener('click',
    function() {
      /* remove all the characters from the input type="text" element */
      document.getElementById('text').value = '';
    }, false);

  function makeClickHandler(c) {
    i[c].onclick = function() {
      /* find the non-text button  which has an id */
      if (i[c].id === 'back') {
        /* remove last character from the input the type="text" element using regular expression */
        document.getElementById('text').value =
          document.getElementById('text').value.replace(/.$/, '');
      }
      /* find the text buttons */
      else {
        /* add characters to the input type="text" element */
        document.getElementById('text').value += this.value.toLowerCase();
      }
    };
  }
  document.onmousemove = resetTimer;
  document.onkeypress = resetTimer;

  function logout() {
    kb.classList.remove('show');
    kb.classList.add('hide');
  }

  function resetTimer() {
    clearTimeout(t);
    t = setTimeout(logout, delay)
  }
  resetTimer();
})();
<div id="keyboard" class="show">

  <div>
    <input type="button" value="Q">
    <input type="button" value="W"> .........
    <input type="button" value="V">
    <input type="button" value="B">
    <input type="button" value="N">
    <input type="button" value="M">
  </div>
  <div>
    <input id="back" type="button" value="&#8592;">
    <input id="space" type="button" value=" ">
    <input id="clear" type="reset" value="clear">
  </div>
  <div>
    <label>Track Search</label> - <input id="text" type="text">
  </div>

  <!-- #keyboard -->
</div>

With this code, I can only print after the last printed character. But I want it like so (| means the cursor position),

An|ant

Here I wrote An before ant.

But it prints it like this:

ant An|

What can I do to solve the problem?


Solution

  • I guess what you search for is selectionStart You can use it in major browsers
    so you get the start point(and not simply append to the end of the string) of where to add in your

    .value += this.value.toLowerCase();
    

    you can simply use it like this:

    var input = document.getElementById('text');
    var caretPosition = input.selectionStart;
    
    // Check if there is a Selection in your input
    if (input.selectionStart != input.selectionEnd)
    {
       var selectionValue =
       input.value.substring(input.selectionStart, input.selectionEnd);
    }