1

I'm struggling on how to style in the best way possible this kind of code:

<td><div data-source="lightstreamer" data-field="yellow-cards">-</div></td>

The data-source node will be dynamically deeded with content (i.e. 1, 2..) but I have to show an image, instead (a yellow card if node content is 1 or a red card if node content is 2). I cannot modify the markup as it will be provided by a third part.

If you have any tip on how to achieve that result in a clean way, it will be greatly appreciated, as I'm not sure how to do it, right now.

Thank you so much!

Teo

Matteo
  • 1,217
  • 1
  • 13
  • 17

3 Answers3

2

If you don't have to support older browsers (css selectors are required for this to work), you might improve your solution by exploiting the data-update option: that option tells the Lightstreamer client library to place the update value somewhere else instead of placing it as content for the html node. In this case we can tell the library to fill a custom property named "data-card".

The resulting html will look like this:

<div data-source="lightstreamer" data-field="yellowCards" data-update="data-card" data-card="0">-</div>

Now we tell the browser to colorize the element based on the value of such data-card property using a simple CSS:

div[data-card="0"] {background: white;display: none;}
div[data-card="1"] {background: yellow;}
div[data-card="2"] {background: red;}

this way you don't have to code any handler for the grid update.

HTH

Mone
  • 74
  • 3
0

You can use a CSS selector to target the 'yellow-cards' attribute.. text-indent will hide the innerHTML by offsetting it if you don't want to display that.

eg:

div[data-field='yellow-cards'] { background:url(<yellow card image>); text-indent:-5000px; }

If you can't rely on the data-field value, you'll have to use javascript to select all the div nodes and go through them checking the innerHTML.

var divarray = document.getElementById(<table id>).getElementsByTagName("DIV")
for (loop=0;loop<divarray.length;loop++) {
    switch(divarray[loop].innerHTML){
    case "-": divarray[loop].className="novalue";
              break;
    case "1": divarray[loop].className="yellowcard";
              break;
    case "2": divarray[loop].className="redcard";
              break;
    }
}

Then iterate through that checking the innerHTML and applying a class depending on the value. The first method is best as the second will visibly change the display on page load.

WindsorAndy
  • 237
  • 1
  • 11
  • Well, unfortunately I can't rely only on the data-field value but rather on the text node value... And it must be dynamic too... So if value is "-" I display nothing, if value is "1" I display a yellow card, if value is "2" I display red one... without reloading the page. – Matteo Nov 19 '13 at 10:30
  • You can't use CSS then, it'll have to be the Javascript solution.. I've edited it. You'll have to sanity check the results of the getElementsByTagName as it'll find all DIV nodes within your table. You'll obviously need to set us CSS styles for the 3 different possible states. – WindsorAndy Nov 19 '13 at 10:34
0

Ok, the solution I found is strictly based upon LightStreamer. Given a DynaGrid:

// Create Home Players Grid
    var homePlayersGrid = new DynaGrid("homePlayersGrid",true);
    var fieldList = ["key", "command", "jersey", "lastName", "sequence","substituted","yellowCards","redCards","autoGoals","goals"]; 
    var homePlayersSubscription = new Subscription("COMMAND","homePlayers",fieldList);
    homePlayersSubscription.addListener(homePlayersGrid);
    homePlayersGrid.setSort("sequence",false,true);
    client.subscribe(homePlayersSubscription);

chained to a HTML table:

<tr id="homePlayersGrid" data-source="lightstreamer">
        <td><div data-source="lightstreamer" data-field="sequence">-</div></td>
        <td><div data-source="lightstreamer" data-field="jersey">-</div></td>
        <td><div data-source="lightstreamer" data-field="lastName">-</div></td>
        <td><div data-source="lightstreamer" data-field="substituted">-</div></td>
        <td><div data-source="lightstreamer" data-field="yellowCards">-</div></td>
        <td><div data-source="lightstreamer" data-field="redCards">-</div></td>
        <td><div data-source="lightstreamer" data-field="autoGoals">-</div></td>
        <td><div data-source="lightstreamer" data-field="goals">-</div></td>
    </tr>

I add a listener to detect any update to the contents:

homePlayersGrid.addListener({
      onVisualUpdate: function(key,info,domNode) {
        if (info == null) {return;}
        formatYellowCards(domNode,info);
      }
    });

Where formatYellowCards() is a function that sets the right kind of class to the changed data-field:

function formatYellowCards(domNode, info) { //onChangingValues
       if (info == null) {return;}
       info.setCellStyle("yellowCards","transition","yellowCards-"+info.getCellValue("yellowCards"));
    }

Finally, the CSS is trivial:

.transition {background: green;text-indent: -5000px}
.yellowCards-0 {background: white;display: none;text-indent: -5000px}
.yellowCards-1 {background: yellow;text-indent: -5000px}
.yellowCards-1 {background: red;text-indent: -5000px}
Matteo
  • 1,217
  • 1
  • 13
  • 17