Yunowork
Yunowork

Reputation: 345

Changing text in table with Javascript

I've been working on something for the last hours but can't seem to get it working properly. When a user clicks on a table column (Rn) it should become highlighted and the text should change (player names and race information) in some other TD elements, the same principle as for the previous and next buttons, where everything works fine.

Anyone knows what I'm doing wrong here?

Code: http://jsfiddle.net/yunowork/4UGre/8/

Upvotes: 1

Views: 181

Answers (5)

Sushanth --
Sushanth --

Reputation: 55750

You need to select the td with which you want to replace the text.. If that is found then the function seems to be working fine..

rows.children().not('.emptyrace, .race, .not').on('click', function(e) {
    rows.children().removeClass('highlighted');
    var id=e.target.id ;
    $('.showtext').html($('#'+id).find('.hiddentext').html());
    $('.showplayerone').html($('#'+id).find('.hiddenplayerone').html());
    $('.showplayertwo').html($('#'+id).find('.hiddenplayertwo').html());
    $('.showplayerthree').html($('#'+id).find('.hiddenplayerthree').html());
    var index = $(this).prevAll().length;  
    rows.find(':nth-child(' + (index + 1) + ')').addClass('highlighted');
  });

FIDDLE

UPDATED FIDDLE

Upvotes: 1

Stphane
Stphane

Reputation: 3476

Here is my full working solution

jsFiddle Here

I want to say 'enjoy' ... Notice : only one handler is attached to the DOM (the table element)

$(function(){
  var $t = $('table');
  $t.on('click', function(e){
    var $table = $(this),
        $target = $(e.target),
        $tdParent = $target.closest('td'),
        $alltr = $table.find('> tr, > tbody > tr');
    // Prev, next and td actions
    if( $target.is('.race > a') || ! $tdParent.is('.highlighted, .emptyrace, .race, .not')  ){
        // if a 'prev' or 'next' has been clicked
        if( $target.is('a') ){
            $tdParent = $('.highlighted', $alltr.filter(':gt(0)'))[($target.hasClass('next')? 'next':'prev')]('td:not(.not)');
            if( ! $tdParent.length){
                return false;
            } else if ($tdParent.hasClass('invisible')) {
                var $one = $tdParent.eq(0), $other = $one.parent().children(':not(.not)'), index = $other.index($one);
                $tdParent.parent().each( function(i,el){
                    $(this)
                        .children(':not(.not)')
                        .filter(':eq('+(index + (6*($target.hasClass('next')? -1:1)))+')')
                            .removeClass('visible').addClass('invisible')
                });
                $tdParent.removeClass('invisible').addClass('visible');

            }
        }
        // Common actions ...
        var tdIndex = ':nth-child(' + ($tdParent.eq(0).parent().children().index($tdParent.eq(0)) + 1) + ')';
        $alltr.eq(0).find('.showtext').html($alltr.eq(1).find(tdIndex + ' > .hiddentext').html());
        $alltr.filter(':gt(0)')
                .find(' > td.highlighted').removeClass('highlighted').end()
                .find(tdIndex).addClass('highlighted').end()
                .not(':eq(0)').each(function(){
                    var $this = $(this),
                        css = $this.find('> td.not > span').attr('class').replace(/^.*(player[^ ]+).*$/, '$1');
                    $this.find('.show'+css).html($alltr.eq(1).find(tdIndex + ' .hidden'+css).html());
                });
        return false;
    }
  });
});

Upvotes: 1

Bubbles
Bubbles

Reputation: 3815

At a glance, it would appear your problem is that you use "$prevCall" and "$nextCall" to determine what players to display when previous or next is clicked. Nothing like this is done when a column is clicked - if you do something like this:

var $thisCol = $(this);
rows.children().removeClass('highlighted');
$('.showtext').html($thisCol.find('.hiddentext').html());
$('.showplayerone').html($thisCol.find('.hiddenplayerone').html());
$('.showplayertwo').html($thisCol.find('.hiddenplayertwo').html());
$('.showplayerthree').html($thisCol.find('.hiddenplayerthree').html());

it should be fine. However, you might look into creating a single "select_colum" function which previous, next and clicking all rely on, it would make the code more compact and reduce duplicate code, which makes for easier debugging and troubleshooting.

To elaborate a bit on this: let's say you wanted to add a name to the table. In order to properly update them all, you'd need to add the line

$('.showplayerfour').html($thisCol.find('.hiddenplayerfour').html());

in three different places. What you can instead do is create a function like this:

function update_names($col) {
    $('.showtext').html($col.find('.hiddentext').html());
    $('.showplayerone').html($col.find('.hiddenplayerone').html());
    $('.showplayertwo').html($col.find('.hiddenplayertwo').html());
    $('.showplayerthree').html($col.find('.hiddenplayerthree').html());
}

You can then add player four just to this function, and each display option would work with it. There's a lot more you can do with this technique (if you're motivated, you can probably get it to the point where you wouldn't even need to specify each individual player).

Upvotes: 1

Timm
Timm

Reputation: 12753

The code

$('.showplayerone').html($('.hiddenplayerone').html());
$('.showplayertwo').html($('.hiddenplayertwo').html());
$('.showplayerthree').html($('.hiddenplayerthree').html());

is putting the value of the first element with class of hiddenplayerone two etc into the shown data, which will always be John, Fred and Jason. You need to select only the correct element by supplying the selector with the ID of the correct data, something like this:

thisRow = $(this).prop('id');
rows.children().removeClass('highlighted');
$('.showtext').html($('.hiddentext').html());
$('.showplayerone').html($('#'+thisRow+' .hiddenplayerone').html());
$('.showplayertwo').html($('#'+thisRow+' .hiddenplayertwo').html());
$('.showplayerthree').html($('#'+thisRow+' .hiddenplayerthree').html());

This works if you click on any of rows in the race column, not just the title row.

Working Example: http://jsfiddle.net/4UGre/13/

You appear to be using the same ID in several places though (R1, R2 etc), which is bad practice, consider changing this.

Upvotes: 1

Pete
Pete

Reputation: 2558

You're not being specific enough in your search for ".hidden_____" information. So it's just selecting the first one it finds. I corrected the issue by narrowing the search to only decedents of the ancestor <td> of the clicked element:

$('.showtext').html($(this).closest("td").find('.hiddentext').html());
$('.showplayerone').html($(this).closest("td").find('.hiddenplayerone').html());
$('.showplayertwo').html($(this).closest("td").find('.hiddenplayertwo').html());
$('.showplayerthree').html($(this).closest("td").find('.hiddenplayerthree').html()); 

I forked your code with the fix here:

http://jsfiddle.net/4pu9Q/

Upvotes: 1

Related Questions