Javascript: Trying to build an onscreen keyboard with a loop but I get an "allocated size overflow" message

StackOverflow https://stackoverflow.com/questions/20056604

Pregunta

<html>
<head>
    <script type = "text/javascript">
        var fst_row = ["q","w","e","r","t","y","u","i","o","p"];
        var snd_row = ["a","s","d","f","g","h","j","k","l"];
        var thd_row = ["z","x","c","v","b","n","m"];

        function insert_fst_row(){
            document.getElementById("my_key").innerHTML = keyboard(snd_row);  
        } //inserts first row of letters of the keyboard when user clicks button.

        function keyboard(array){
            var key = "";
            key += "<table>";
            for (var row = 1; row = 1; row++){
                key +=      "<tr>";
                for (var col = 1; col <= array.length; col++){
                    key +=      "<td><input type = 'button' value = 'array[i]'/></td>"; ** //Error here.
                    }
                key +=      "</tr>";
                }

            key += "</table>";
            return key;
        }

    </script>
</head>

<body>
    <input type = "text" name = "text" id = "text"/>
    <input type = "button" value = "insert key" onclick = "insert_fst_row()"/>
    <p id = "my_key"></p>
</body>

I'm trying to make an onscreen keyboard using a loop, so I put each row of letters in a separate array. However I'm having trouble making the keyboard appear when I click the button. Instead when it runs, it prints out an error stating "allocation size overflow" and it refers to the line indicated in the code with **. What does this mean and how can it be resolved?

¿Fue útil?

Solución

The problem is here:

// ---------------vvvvvvv
for (var row = 1; row = 1; row++) {

On every loop iteration row = 1 will always be non false (i.e. 1), hence your loop will never stop executing. This infinite loop leads to stack memory overflow. In ordinary cases the second section of for loop carries a clause that will stop iterations, e.g. row < number_of_rows.

Otros consejos

I would do something like this.

The following code doesn't use rigid table elements or static html with hard-coded event listeners. It also accepts any number of keyboard rows with any number of keys in each.

This code intends to help solve some of your issues as well as give you some ideas to make improvements upon your own.

Watch the console as you click the keys to see the output.

jsfiddle demo here

var Keyboard = function(elem) {
  this.elem = elem;
  this.elem.className = "keyboard";

  Keyboard.rows.map(function(row) {
    this.elem.appendChild(this.createRow(row));
  }.bind(this));
};

Keyboard.rows = [
  ["`", "1", "2", "3", "4", "5", "6", "7", "8", "9", "0", "-", "=", "delete"],
  ["tab", "q", "w", "e", "r", "t", "y", "u", "i", "o", "p", "[", "]", "\\"],
  ["caps", "a", "s", "d", "f", "g", "h", "j", "k", "l", ";", "'", "return"],
  ["shift", "z", "x", "c", "v", "b", "n", "m", ",", ".", "/", "shift"],
];

Keyboard.prototype.createRow = function(row) {
  var div = document.createElement("div");

  row.map(function(key) {
    div.appendChild(this.createKey(key));
  }.bind(this));

  return div;
};

Keyboard.prototype.createKey = function(key) {
  var button = document.createElement("button");
  button.innerHTML = key;
  button.addEventListener("click", this.onKeypress.bind(this, key));
  return button;
};

Keyboard.prototype.onKeypress = function(key, event) {
  var keypressEvent = new Event("keypress");
  keypressEvent.key = key;
  this.elem.dispatchEvent(keypressEvent);
  event.preventDefault();
};

Usage

var div = document.getElementsByTagName("div")[0];
new Keyboard(div);

div.addEventListener("keypress", function(event) {
  console.log(event.key + " was pressed", event);
});
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top