Search code examples
javascriptonclickhtml-tableappendchild

JavaScript table onclick


I'm working on creating a game where a proverb is displayed in a table. When you click on one of the letters (or td) then it displays the letter.

I used Javascript to create the table, after removing spaces/author/etc. Here is the code I used to create the table.

function createRow(tableRowId, startIndex, endIndex) {
    var row = document.getElementById(tableRowId);
    var index = startIndex;

    while(index <= endIndex){
        //hints array contains the letters to be displayed
        if(hints[index] != undefined){
            var newCell = row.insertCell(-1);
            var newText = document.createTextNode(hints[index]);
            newCell.appendChild(newText);
        }
        else{
            break;
        }
        index++;
}

The problem I have is that onclick wont work with the td that were just created.

var cells = document.getElementsByTagName("td");
cells.onclick = function (){
    cells.style.backgroundColor = "white";
}

I must be missing a step or something, maybe some small error in my code. Maybe there is a better way of doing this. All the source can be found here. http://wikisend.com/download/831324/lab4.zip


Solution

  • I'll update with a method to toggle the highlight to only one cell.

    EDIT

    Ok, here is a method to remove the blue class and add it to the one which was clicked:

    // Remember el.attachEvent('onclick', ...) for IE8 and lower
    base.addEventListener('click', function delegate(e){
        var cells = tbody.getElementsByClassName('blue'),
            i = 0,
            cell;
    
        while (cell = cells[i++]) {
            cell.className = cell.className.replace(/\bblue\b/g, '');
        }
    
        e.target.className += ' blue';
    });
    

    http://jsfiddle.net/xwgyK/1/

    This uses el.getElementsByClassName(), which is supported by most modern browsers and IE9 and greater. An alternative, of course, could be to do another tbody.getElementsByTagName('td'), which is universally supported.

    EDIT 2

    Note, I noticed sometimes it's possible not to click a TD, so we should first check for that and ignore the click on table if it's not a td:

    base.addEventListener('click', function delegate(e){
        var cells = tbody.getElementsByClassName('blue'),
            i = 0,
            cell;
    
        if (e.target.nodeName.toLowerCase() == 'td') {
            while (cell = cells[i++]) {
                cell.className = cell.className.replace(/\bblue\b/g, '');
            }
    
            e.target.className += ' blue';
        }
    });
    

    http://jsfiddle.net/xwgyK/2/

    HTML

    <table id="base">
        <tbody></tbody>
    </table>
    

    Javascript

    var base = document.getElementById('base'),
        tbody = base.getElementsByTagName('tbody')[0],
        numrows = 30,
        numcols = 10,
        col = 0,
        row = "<tr>{row}</tr>",
        rows = "",
        cell = "<td>{cell}</td>",
        cells = "";
    
    // Remember el.attachEvent('onclick', ...) for IE8 and lower
    base.addEventListener('click', function delegate(e){
        e.target.style.backgroundColor = 'blue';
    });
    
    while (numrows--) {
        cells = "";
        col = 0;
    
        while (col++ < numcols) {
            cells += cell.replace('{cell}', col);
        }
    
        rows += row.replace('{row}', cells);
    }
    
    tbody.innerHTML = rows;
    

    http://jsfiddle.net/xwgyK/