How can I highlight the row of a TableView and unhighlight it when another row is selected?

I have a TableView in a tablet app, so it only covers a small part of the screen and I keep it resident there. When a user selects a row, data for that row appears on the rest of the screen, and I would like to be able to highlight that row to remind the user of which row they’re on.

I’ve tried a lot of different ideas, but so far all I get is a highlighted row that persists when another row is pressed, instead of being set back to the unhighlighted color. Here’s my latest attempt:

local function onRowTouch( event ) local phase = event.phase if "press" == phase then     for i=1,#list.\_view.\_rows do         if (i == event.target.index) then -- Set highlight color list.\_view.\_rows[i].\_view:setRowColor( { default = {160,92,92,128 }} )         else -- Set unhighlight color list.\_view.\_rows[i].\_view:setRowColor( { default = {92,92,92,128 }} )         end         list.\_view.\_rows[i].\_view.reRender = true         end     end     return true end

If I push the tableview up off screen and let it pop back, then the rows change to the colors I set in onRowTouch, so it seems like there’s a way to trigger a rerender. That’s all I really need for the behavior I’m looking for. How can I do that?

edit: Also, what’s up with IE10 formatting? This code looks fine on Chrome, but I tried many different ways of formatting and it still looks like crap on IE10.

This thread should help: http://forums.coronalabs.com/topic/36881-tableview-how-to-force-re-rendering/

You are close, but in addition to what you have already you need to check for selected or not in your onRowRender function. So add a property to the row, something like row.selected = true. Then in your onRowRender function you check for that property when rendering rows and add the highlight if found. 

Thanks, I like your looping and reference better than mine, but that still only highlights the row that was just selected and doesn’t unhighlight the previously selected row. What I need is a way to force all the rows to rerender. I could do something like delete all the rows and add them back, but that’s pretty sad when you have to do something like that.

When you highlight a row you need to loop through the visible rows and check if some other row is highlighted and then unhighlight it (and change the row.params.isHighlighted = false or however you are tracking what rows are highlighted so that it doesn’t become highlighted again if you scroll it off screen and on again.)

Sorry, I guess I haven’t made it clear what’s going on. The key is, my TableView always stays on the screen. The user clicks a row, it highlights, and the data for that row comes up, and the user edits it. Then if the user selects another row, the new row highlights, and the data for that row comes up, but the old row stays highlighted even if I unhighlight it programmatically in the onRowTouch function.

When there’s a “press” event in onRowTouch, I’m unhighlighting all the rows, and then highlighting the one that’s been selected. Or alternatively, I’m highlighting all the rows except the selected one, and unhighilighting all the rest. But the problem is, as long as the TableView stays on the screen, only the selected row will be highlighted, because it’s the only one getting a rerender event. None of the other rows get this event, and so the last row that was highlighted never rerenders, and stays highlighted. So now I have two rows highlighted, and so on until they’re all highlighted.

If I scroll a highlighted row up off screen, then that row gets the rerender message, and changes to unhighlighted, unless it’s the row that’s supposed to be highlighted, the most recently selected row. This means the default row color has been the unhighlighted row color all along, but that row was waiting for an event to cause it to rerender. That even was triggered when I scrolled that row off screen. What I want to do it trigger that event myself, and force the rows to rerender whether they want to or not.

I have not used the setRowColor function. Not sure how it behaves but seems you have limited control over it. You may have to  add your own background rect for each row if that funciton is the problem.

In rowRender function do row.background = display.newRect(etc)

Now you have full control over this background. 

[lua]

for k, row in ipairs(list._view._row) do

    if row._view then   – If this condition is met it means the row is rendered (visible)

          row.background : setFillColor(92,92,92,128)

          etc

    end

end

[/lua]

This thread should help: http://forums.coronalabs.com/topic/36881-tableview-how-to-force-re-rendering/

You are close, but in addition to what you have already you need to check for selected or not in your onRowRender function. So add a property to the row, something like row.selected = true. Then in your onRowRender function you check for that property when rendering rows and add the highlight if found. 

Thanks, I like your looping and reference better than mine, but that still only highlights the row that was just selected and doesn’t unhighlight the previously selected row. What I need is a way to force all the rows to rerender. I could do something like delete all the rows and add them back, but that’s pretty sad when you have to do something like that.

When you highlight a row you need to loop through the visible rows and check if some other row is highlighted and then unhighlight it (and change the row.params.isHighlighted = false or however you are tracking what rows are highlighted so that it doesn’t become highlighted again if you scroll it off screen and on again.)

Sorry, I guess I haven’t made it clear what’s going on. The key is, my TableView always stays on the screen. The user clicks a row, it highlights, and the data for that row comes up, and the user edits it. Then if the user selects another row, the new row highlights, and the data for that row comes up, but the old row stays highlighted even if I unhighlight it programmatically in the onRowTouch function.

When there’s a “press” event in onRowTouch, I’m unhighlighting all the rows, and then highlighting the one that’s been selected. Or alternatively, I’m highlighting all the rows except the selected one, and unhighilighting all the rest. But the problem is, as long as the TableView stays on the screen, only the selected row will be highlighted, because it’s the only one getting a rerender event. None of the other rows get this event, and so the last row that was highlighted never rerenders, and stays highlighted. So now I have two rows highlighted, and so on until they’re all highlighted.

If I scroll a highlighted row up off screen, then that row gets the rerender message, and changes to unhighlighted, unless it’s the row that’s supposed to be highlighted, the most recently selected row. This means the default row color has been the unhighlighted row color all along, but that row was waiting for an event to cause it to rerender. That even was triggered when I scrolled that row off screen. What I want to do it trigger that event myself, and force the rows to rerender whether they want to or not.

I have not used the setRowColor function. Not sure how it behaves but seems you have limited control over it. You may have to  add your own background rect for each row if that funciton is the problem.

In rowRender function do row.background = display.newRect(etc)

Now you have full control over this background. 

[lua]

for k, row in ipairs(list._view._row) do

    if row._view then   – If this condition is met it means the row is rendered (visible)

          row.background : setFillColor(92,92,92,128)

          etc

    end

end

[/lua]