MozillaZine

JavaScript question

Discuss how to use and promote Web standards with the Mozilla Gecko engine.
Bethrezen
 
Posts: 390
Joined: September 13th, 2003, 11:56 am

Post Posted May 1st, 2018, 6:33 pm

Hi all

Ok so quick question, I have the following sample html

Code: Select all
<div id="left">

  <img id="icon1" src="path to icon" alt="icon name">
  <img id="icon2" src="path to icon" alt="icon name">
  <img id="icon3" src="path to icon" alt="icon name">

</div>

<div id="right">

  <table>
    <tr>
      <td>Icon name</td>
      <td>Icon name</td>
      <td>Icon name</td>
    </tr>
  </table>

</div>


Now what I want to do is to hover over one of the items on the right and have that highlight the corresponding icon on the left, here is a screen shot to demonstrate

Image

now when I do

Code: Select all
function hoveron(id)
{
  var id = document.getElementById(id);

  id.style.cssText = "border:1px dashed red;";
}

function hoveroff(id)
{
  var id = document.getElementById(id);

  id.style.cssText = "border:none;";
}

<table>
  <tr>
    <td onmouseover="hoveron('icon1')" onmouseout="hoveroff('icon1')">Icon name</td>
    <td onmouseover="hoveron('icon2')" onmouseout="hoveroff('icon2')">Icon name</td>
    <td onmouseover="hoveron('icon3')" onmouseout="hoveroff('icon3')">Icon name</td>
  </tr>
</table>


Everything seems to work correctly however I'm looking for a better way that doesn't involve me having to add

onmouseover="hoveron(' ')"
onmouseout="hoveroff(' ')"

To every td

So I rewrote the function like this

Code: Select all
function highlight(id)
{
  var id = document.getElementById(id);

  id.onmouseover = function(id)
  {
    id.style.cssText = "border:1px dashed red";
  };

  id.onmouseout = function(id)
  {
    id.style.cssText = "border:none;";
  };
}


The issue however is that I don’t seem to be able to get this working and I'm not sure why so I'm wondering if anyone can spot where I'm going wrong.

how do i get all the td's and then attach the highlight function to those td's so that when I mouse over them the function is run ?

jscher2000

User avatar
 
Posts: 10308
Joined: December 19th, 2004, 12:26 am
Location: Silicon Valley, CA USA

Post Posted May 2nd, 2018, 8:43 am

You have a working example... how do they do it?

I can't test this without creating a document, but as a general idea:

Assume a table ID of "hoverzone"

Code: Select all
document.getElementById('hoverzone').addEventListener('mouseover', function(evt){
  var tgt = evt.target || event.srcElement;
  if (tgt.nodeName != 'TD') return; // parts of tables other than cells are not interesting
  // get relevant information from the cell such as tgt.id or tgt.getAttribute('iconid') and use that
}, false);


mouseout would be similar.

Bethrezen
 
Posts: 390
Joined: September 13th, 2003, 11:56 am

Post Posted May 2nd, 2018, 7:36 pm

Sure, now obviously this is going to look a little different to the screen shot I posted above but that’s because this is simply a template which I'm using to actually build each page plus it's missing some images but otherwise the html and the css is the same.

To account for the missing images I added a few extra lines of css to fix the display issues you can find that at the bottom of the style section under /* testing */

If you decide to use place holder images the background for the #left box should be 513px by 513px and the icons should be 30px by 30px you will also need to remove the css under /* testing */ but it shouldn't matter if there are images or not since the alt text will just show in place of the icon and then allow you to see if the script is working.

Code: Select all
<!DOCTYPE html>
<html>
<head>
<title>Sector Map - sector name</title>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<style>

*
{
box-sizing: border-box;
}

html, body
{
margin:0;
padding:0;
}

body
{
background-color:#172331;
}

#flex_container
{
display:flex;
justify-content: center;
align-items:center;
min-height:100vh;
}

div#outer
{
white-space:nowrap;
}

#left,
#right
{
height:540px;
}

#left p,
#right p
{
background-image: url("../images/bordertop.jpg");
height:25px;
margin:0;
padding-left: 10px;
color: #fff;
font-weight:bold;
border-left:1px solid #9aabc5;
border-right:1px solid #9aabc5;
line-height:21px;
}

#left
{
display:inline-block;
vertical-align: top;
margin: 20px 7px 20px 18px
}

#left img
{
color:white;
}

#left img#map
{
border-left:1px solid #9aabc5;
border-right:1px solid #9aabc5;
border-bottom:1px solid #9aabc5;
}

#right
{
display:inline-block;
vertical-align: top;
margin: 20px 18px 20px 7px
}

#right #inner
{
overflow-y:auto;
height:calc(100% - 26px);
padding-right:32px;
border-left:1px solid #9aabc5;
border-right:1px solid #9aabc5;
border-bottom:1px solid #9aabc5;
}

#right #inner table
{
border-spacing: 0;
width:100%;
white-space:nowrap;
margin:16px;
padding-top:3px;
padding-bottom:3px;
color:#bfc6e5;
background-color:#0b111a;
border:2px solid #000001;
border-radius: 6px;
font-family: Arial;
font-size:0.90em;
}

#right #inner table tr th,
#right #inner table tr td
{
text-align:left;
padding: 3px 6px;
}

#right #inner table tr:hover:not(:nth-of-type(1))
{
background-color:#4f5d84;
}

/* Position Icons */

#left
{
position:relative;
}

img.icon
{
position:absolute;
z-index:10;
}

img#icon1
{
top:40px;
left:20px;
}

/* testing */

#left img#map
{
display:block;
height:513px;
width:513px;
}

#left,
#right
{
border-top:1px solid #9aabc5;
}

#left p,
#right p
{
border-bottom:1px solid #9aabc5;
}
</style>

<script>

function hoveron(id)
{
  var id = document.getElementById(id);

  id.style.cssText = "border:1px dashed red;";
}

function hoveroff(id)
{
  var id = document.getElementById(id);

  id.style.cssText = "border:none;";
}

</script>

</head>

<body>

<div id="flex_container">

  <div id="outer">

    <div id="left">
      <p>Sectormap - Sector Name</p>
      <img src="path to image" id="map">

      <img class="icon" id="icon1" src="path to image" alt="icon name">
    </div>

    <div id="right">
      <p>Information</p>

      <div id="inner">

        <table>
         
          <tr>
            <th>Station</th>
            <th colspan="3">Coordinates (x, y, z)</th>
          </tr>

          <tr onmouseover="hoveron('icon1')" onmouseout="hoveroff('icon1')">
            <td>Station</td>
            <td>X</td>
            <td>Y</td>
            <td>Z</td>
          </tr>

          </table>

          <table>

          <tr>
            <th>Type</th>
            <th>Yield</th>
            <th colspan="3">Coordinates (x, y, z)</th>
          </tr>

          <tr onmouseover="hoveron('icon1')" onmouseout="hoveroff('icon1')">
            <td>Type</td>
            <td>Yield</td>
            <td>X</td>
            <td>Y</td>
            <td>Z</td>
          </tr>

          </table>

          <table>

          <tr>
            <th>Gates</th>
            <th>Destination</th>
            <th colspan="3">Coordinates (x, y, z)</th>
          </tr>

          <tr onmouseover="hoveron('icon1')" onmouseout="hoveroff('icon1')">
            <td>Gate</td>
            <td>Destination</td>
            <td>X</td>
            <td>Y</td>
            <td>Z</td>
          </tr>

        </table>

      </div>
     
    </div>

  </div>

</div>

</body>
</html>


now as you will see when you copy and past this and create a new html document, stuff works correctly when i do

Code: Select all
function hoveron(id)
{
  var id = document.getElementById(id);

  id.style.cssText = "border:1px dashed red;";
}

function hoveroff(id)
{
  var id = document.getElementById(id);

  id.style.cssText = "border:none;";
}

<table>
         
  <tr>
    <th>Station</th>
    <th colspan="3">Coordinates (x, y, z)</th>
  </tr>

  <tr onmouseover="hoveron('icon1')" onmouseout="hoveroff('icon1')">
    <td>Station</td>
    <td>X</td>
    <td>Y</td>
    <td>Z</td>
  </tr>

</table>


but as i already mentioned I'd much rather not have to put

onmouseover="hoveron('icon1')" onmouseout="hoveroff('icon1')"
onmouseover="hoveron('icon2')" onmouseout="hoveroff('icon2')"
onmouseover="hoveron('icon3')" onmouseout="hoveroff('icon3')"

etc on every row I'd much prefair to just write the onmouseover="" onmouseout="" once put that in a function and then just attach that function to each row dynamically, which is why i tried rewriting the function to

Code: Select all
function highlight(id)
{
  var id = document.getElementById(id);

  id.onmouseover = function(id)
  {
    id.style.cssText = "border:1px dashed red";
  };

  id.onmouseout = function(id)
  {
    id.style.cssText = "border:none;";
  };
}


trouble is I'm a bit of a rookie when it comes to JavaScript so I'm not really sure how to get this working i tried a number of things to try and pass the id to the function so that it will know which row in the list I'm hovering over and which icon to find and highlight as this should work by matching pairs so i pass an id as a parameter to the function it then gets the image with the same id and highlights it but nothing i have tried works and i have no idea why.

Now I had assumed that it would be as simple as doing

Code: Select all
<table>
         
  <tr>
    <th>Station</th>
    <th colspan="3">Coordinates (x, y, z)</th>
  </tr>

  <tr highlight('icon1')>
    <td>Station</td>
    <td>X</td>
    <td>Y</td>
    <td>Z</td>
  </tr>

</table>


to call the function and pass it the id of the row I'm hovering over so that it knows which icon to find and highlight but clearly this is not the case as this simply doesn't work.

Frenzie

User avatar
 
Posts: 2134
Joined: May 5th, 2004, 10:40 am
Location: Belgium

Post Posted May 4th, 2018, 6:29 am

I don't know if it's related to your issue but this is a bad pattern:

Code: Select all
function highlight(id)
{
  var id = document.getElementById(id); //id is already defined!


I suspect you might get an explicit error about it if you use 'use strict';

https://developer.mozilla.org/en-US/doc ... trict_mode

As another aside, you should use addEventListener('mouseover', etc) so that you can attach multiple event listeners without overwriting any potential previous ones.

https://developer.mozilla.org/en-US/doc ... ntListener

If you want to get all the TDs, since it's 2018 you can just use querySelectorAll('td'). But for this particular example good old getElementsByTagName('td') would also work perfectly fine.

https://developer.mozilla.org/en-US/doc ... electorAll
https://developer.mozilla.org/en-US/doc ... sByTagName
Intelligent alien life does exist, otherwise they would have contacted us.

Frenzie

User avatar
 
Posts: 2134
Joined: May 5th, 2004, 10:40 am
Location: Belgium

Post Posted May 4th, 2018, 6:31 am

Now I had assumed that it would be as simple as doing
[…]
to call the function and pass it the id of the row I'm hovering over so that it knows which icon to find and highlight but clearly this is not the case as this simply doesn't work.

But there are no IDs anywhere in anything you posted?
Intelligent alien life does exist, otherwise they would have contacted us.

Bethrezen
 
Posts: 390
Joined: September 13th, 2003, 11:56 am

Post Posted May 4th, 2018, 10:09 am

Frenzie wrote:
Now I had assumed that it would be as simple as doing
[…]
to call the function and pass it the id of the row I'm hovering over so that it knows which icon to find and highlight but clearly this is not the case as this simply doesn't work.

But there are no IDs anywhere in anything you posted?


Actually strictly speaking that's not true the id is on the image, but there in lies the problem see I want to hover on the table in the #right box but I want the script to affect the associated image in the #left box as you can see in this screen shot that I posted earlier.

Image

This is of course where things get tricky because I don't want to add onmousover, onmouseout to every row of the table because doing inline code like that is messy and bad practice plus its a whole bunch more work to implement because I have to alter the html for every page, this is of course where I run in to problems because currently this beyond my level of knowledge the problem however is there is no way to do this with css because the general sibling selector only works when elements share the same parent so the following works fine

Code: Select all
img:hover ~ span#tooltip
{
Do stuff
}

<div>
<img src="path to image">
<span id="tooltip">tooltip text</span>
</div>


however this

Code: Select all
img:hover ~ div#left span#tooltip
{
Do stuff
}

<div id="right">
<img src="path to image">
</div>

<div id="left">
<span id="tooltip">tooltip text</span>
</div>


does not because they don't share the same parent and unfortunately to the best of my knowledge css doesn't have an equivalent to document.getElementById which will ignore the dom and simply get the specified target regardless of where in the page it is

so in a case like this

Code: Select all
<div id="right">
<img src="path to image">
</div>

<div id="left">
<span id="tooltip">tooltip text</span>
</div>


where the hover event is taking place on on the image but the target of that event is the span and they have different parents you have to use JavaScript, unless there is some advanced css to handle cases like this that i just don't know about or haven't found when i went searching.

Bethrezen
 
Posts: 390
Joined: September 13th, 2003, 11:56 am

Post Posted May 4th, 2018, 1:44 pm

ok so i been tinkering with this some more but I'm still having difficulties getting this working so here is some really simple example code.

Code: Select all
<!DOCTYPE html>
<html>
<head>
<title></title>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
</head>
<body>

<table>
  <tr>
    <td>TD 1</td>
  </tr>

  <tr>
    <td>TD 2</td>
  </tr>
</table>

<br>
<br>

<img id="icon1" src="path to image" alt="Image 1">
<img id="icon2" src="path to image" alt="Image 2">

<script>
function hoveron()
{
  var id = document.getElementById("icon1");
  id.style.cssText = "border:1px dashed red;";
}

function hoveroff()
{
  var id = document.getElementById("icon1");
  id.style.cssText = "border:none;";
}

// get all table rows
var rows = document.querySelectorAll("td");

// iterate through the node list and add event listeners.
// (i = 0;) start the loop at the first value in the node list.
// (i < rows.length;) while the index is less than the number of items in the node list keep Iterating through the node list.
// (i++) with each iteration add one to the index.

for (i = 0; i < rows.length; i++)
{
  rows[i].addEventListener("mouseover", hoveron);
  rows[i].addEventListener("mouseout", hoveroff);
}
</script>
</body>
</html>


now what should happen is if i hover on TD 1 then Image 1 should be highlighted and if i hover on TD 2 then image 2 should be highlighted, however this is not what happens now obviously that's because

Code: Select all
var id = document.getElementById("icon1");


is set to a static id so what i need to know is how do i make that dynamic so that the id will change depending on which item in the table I'm hovering on because right now the following

Code: Select all
<table>
  <tr>
    <td>TD 1</td>
  </tr>

  <tr>
    <td>TD 2</td>
  </tr>
</table>

<br>
<br>

<img id="icon1" src="path to image" alt="Image 1">
<img id="icon2" src="path to image" alt="Image 2">

function hoveron(id)
{
  var id = document.getElementById(id);
  id.style.cssText = "border:1px dashed red;";
}

function hoveroff(id)
{
  var id = document.getElementById(id);
  id.style.cssText = "";
}

var rows = document.querySelectorAll("td");

for (i = 0; i < rows.length; i++)
{
  rows[i].addEventListener("mouseover", hoveron);
  rows[i].addEventListener("mouseout", hoveroff);
}


keeps saying id is null, now presumable that's because there is no id on the table td's which was previously being set by

Code: Select all
<td onmouseover="hoveron('icon1')" onmouseout="hoveroff('icon1')"></td>
<td onmouseover="hoveron('icon2')" onmouseout="hoveroff('icon2')"></td>


question is how do i set that via addEventListener, i had a look around and saw a topic on stack overflow about this, but to be honest i really didn't understand it.

How to pass parameter to function using in addEventListener?

Frenzie

User avatar
 
Posts: 2134
Joined: May 5th, 2004, 10:40 am
Location: Belgium

Post Posted May 5th, 2018, 4:27 am

Actually strictly speaking that's not true the id is on the image

D'oh, it was hidden from me by the forum styles and I overlooked it. :)

question is how do i set that via addEventListener, i had a look around and saw a topic on stack overflow about this, but to be honest i really didn't understand it.

You could using an anonymous function, but the proper answer is almost certainly that you don't "set" anything yourself. The event does it for you.

Code: Select all
target.addEventListener('mouseover', hoverOff);

function hoveroff(event) { // or whatever you want to call it, but something other than e or event is probably confusing
  event.target.style.border = 'none'; // although for separation of concerns using classes is generally preferred
}

PS That's pseudo-code, even though it might look a little like JS. ;)
Intelligent alien life does exist, otherwise they would have contacted us.

Bethrezen
 
Posts: 390
Joined: September 13th, 2003, 11:56 am

Post Posted May 5th, 2018, 8:19 pm

Frenzie wrote:You could using an anonymous function, but the proper answer is almost certainly that you don't "set" anything yourself. The event does it for you.

Code: Select all
target.addEventListener('mouseover', hoverOff);

function hoveroff(event) { // or whatever you want to call it, but something other than e or event is probably confusing
  event.target.style.border = 'none'; // although for separation of concerns using classes is generally preferred
}

PS That's pseudo-code, even though it might look a little like JS. ;)


errr ok so I'm not really following, Now i know this might sound like a really stupid question but am i supposed to change.

Code: Select all
function hoveron(id)
{
  var id = document.getElementById(id);
  id.style.cssText = "border:1px dashed red;";
}

function hoveroff(id)
{
  var id = document.getElementById(id);
  id.style.cssText = "border:none;";
}


to

Code: Select all
function hoveron(event)
{
  event.target.style.cssText = "border:1px dashed red;";
}

function hoveroff(event)
{
  event.target.style.cssText = "border:none;";
}


Or am I supposed write a new function? The reason I ask is because it doesn't seem to work correctly when I do that, what happens is I hover on TD1 but instead of highlighting image 1 as expected it highlights TD 1 and this is incorrect.

when I hover on TD 1 it should highlight Image 1 when I hover on TD 2 it should highlight Image 2.

its why i was passing the name of the images id as a parameter via

Code: Select all
<td onmouseover="hoveron('icon1')" onmouseout="hoveroff('icon1')"></td>
<td onmouseover="hoveron('icon2')" onmouseout="hoveroff('icon2')"></td>


that way when i hover over one or other of the td's the id of

Code: Select all
document.getElementById(id)


would be set by the function so if i hover on

Code: Select all
<td onmouseover="hoveron('icon1')" onmouseout="hoveroff('icon1')"></td>


then

Code: Select all
function hoveron(id)

becomes

function hoveron("icon1")


which in turn sets

Code: Select all
document.getElementById(id)

to

document.getElementById("icon1")


which then causes

Code: Select all
<img id="icon1" src="path to image" alt="Image 1">


to be highlighted when i hover on TD1

Hopefully that's clear enough.

Frenzie

User avatar
 
Posts: 2134
Joined: May 5th, 2004, 10:40 am
Location: Belgium

Post Posted May 6th, 2018, 4:31 am

Sorry, I guess I was unclear.
Code: Select all
function hoveron(event)
{
  var target = event.target; // this is the target of the event, e.g. the TD
  // do something with target, for example read the `data-img-id` attribute
  result_of_something.style.cssText = "border:1px dashed red;";
}


You could also use an anonymous function like I already said, but you don't really want to pollute your script with all that data which should come from the markup.
Intelligent alien life does exist, otherwise they would have contacted us.

Bethrezen
 
Posts: 390
Joined: September 13th, 2003, 11:56 am

Post Posted May 6th, 2018, 7:51 am

Frenzie wrote:Sorry, I guess I was unclear.
Code: Select all
function hoveron(event)
{
  var target = event.target; // this is the target of the event, e.g. the TD
  // do something with target, for example read the `data-img-id` attribute
  result_of_something.style.cssText = "border:1px dashed red;";
}


You could also use an anonymous function like I already said, but you don't really want to pollute your script with all that data which should come from the markup.


Unfortunately that’s still not making a lot of sense to me, because I just tried doing

Code: Select all
function hoveron(event)
{
  var target = event.target;
  document.getElementById(target).style.cssText = "border:1px dashed red;";
}


But that doesn't work, it's still keeps saying id is null, and even putting id="icon1" on the td doesn't work, not to mention the fact that doing that is invalid anyway since each id is supposed to be unique and appear only once, I've tried various permutations of the code you posted and none of them work so clearly I'm still missing something ?!?

Bethrezen
 
Posts: 390
Joined: September 13th, 2003, 11:56 am

Post Posted May 8th, 2018, 9:02 am

deleted.
Last edited by Bethrezen on May 13th, 2018, 11:38 am, edited 1 time in total.

Bethrezen
 
Posts: 390
Joined: September 13th, 2003, 11:56 am

Post Posted May 8th, 2018, 11:02 am

ok so now that I have the simple example working as expected it's time for me to apply this to my real word page, however since on my real world page each row has 4 TDs I need to move things up a level and instead of applying this to the TDs I need to apply it to the TRs however this is where I have ran into another snag

While things work as expected when I hover over the table row as soon as the curser moves over any of the TDs I get the error "document.getElementById(…) is null" and the highlighting effect brakes.

Now I could probably fix that by just adding the appropriate data-attribute'…' to each TD but this is messy and probably not the best way to handle the problem, so I'm wondering since I already have the data-attribute'…' set on the table row is there some way I can make that percolate down to all of that rows children ?

now while this probably wont look quite right becaue the images are missing, you can just copy this into a new html document and open it in your browser to see the problem.

When you hover over the pink bit the table row everything is fine, but when you hover over to the green bit the TD the highlighting brakes and the console give the error "document.getElementById(…) is null"

so my question is what is the best way for me to make the data-name'...' attribute percolate down from the table row to that rows children, assuming that's actually possible that is.

Code: Select all
<!DOCTYPE html>
<html>
<head>
<title>Sector Map - Kingdom end</title>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">

<style>

*
{
box-sizing: border-box;
}

html, body
{
margin:0;
padding:0;
}

body
{
background-color:#172331;
}

#flex_container
{
display:flex;
justify-content: center;
align-items:center;

min-height:100vh;
}

div#outer
{
white-space:nowrap;
}

#left,
#right
{
height:540px;
}

#left p,
#right p
{
background-image: url("images/bordertop.jpg");
height:25px;

margin:0;
padding-left: 10px;

color: #fff;
font-weight:bold;

border-left:1px solid #9aabc5;
border-right:1px solid #9aabc5;

line-height:21px;
}

#left
{
display:inline-block;
vertical-align: top;
margin: 20px 7px 20px 18px
}

#left img
{
color:white;
}

#left img#map
{
border-left:1px solid #9aabc5;
border-right:1px solid #9aabc5;
border-bottom:1px solid #9aabc5;
}

#right
{
display:inline-block;
vertical-align: top;
margin: 20px 18px 20px 7px
}

#right #inner
{
overflow-y:auto;
height:calc(100% - 26px);

padding-right:32px;

border-left:1px solid #9aabc5;
border-right:1px solid #9aabc5;
border-bottom:1px solid #9aabc5;
}

#right #inner table
{
border-spacing: 0;
width:100%;

white-space:nowrap;

margin:16px;

padding-top:3px;
padding-bottom:3px;

color:#bfc6e5;
background-color:#0b111a;

border:2px solid #000001;
border-radius: 6px;

font-family: Arial;
font-size:0.90em;
}

#right #inner table tr th,
#right #inner table tr td
{
text-align:left;
padding: 3px 6px;
}

#right #inner table tr:hover:not(:nth-of-type(1))
{
background-color:#4f5d84;
}

/* Position Icons */

#left
{
position:relative;
}

img.icon
{
position:absolute;
z-index:10;
}

img#shipyard
{
top:360px;
left:248px;
}

img#equipdock
{
top:250px;
left:247px;
}

img#military_outpost
{
top:320px;
left:270px;
}

img#trading_station
{
top:275px;
left:277px;
}

img#quantum_tube_fab
{
top:164px;
left:273px;
}

img#weapon_component_factory
{
top:178px;
left:338px;
}

img#chip_plant
{
top:248px;
left:303px;
}

img#crystal_fab
{
top:238px;
left:367px;
}

img#satellite_factory
{
top:414px;
left:221px;
}

img#computer_plant
{
top:293px;
left:143px;
}

img#bio_gas_factory
{
top:221px;
left:175px;
}

img#plankton_farm
{
top:340px;
left:117px;
}

img#south_gate
{
top:390px;
left:302px;
}

img#east_gate
{
top:347px;
left:367px;
}

img#asteroid1
{
top:361px;
left:350px;
}

img#asteroid2
{
top:315px;
left:336px;
}

img#asteroid3
{
top:281px;
left:330px;
}

img#asteroid4
{
top:325px;
left:233px;
}

/* testing */

#left img#map
{
display:block;
height:513px;
width:513px;
}

#left,
#right
{
border-top:1px solid #9aabc5;
}

#left p,
#right p
{
border-bottom:1px solid #9aabc5;
}

tr
{
display:block;
padding:10px;
background-color:pink;
}

td
{
background-color:green
}

</style>

</head>

<body>

<div id="flex_container">

  <div id="outer">

    <div id="left">
      <p>Sectormap - Kingdom End</p>
      <img src="images/grid.png" id="map" alt="Sector Map Background ">

      <img class="icon" id="shipyard" src="images/shipyard.gif" alt="Shipyard Icon">
      <img class="icon" id="equipdock" src="images/equipdock.gif" alt="Equipment dock Icon">
      <img class="icon" id="trading_station" src="images/trading.gif" alt="Stock Exchange Icon">
      <img class="icon" id="military_outpost" src="images/equipdock.gif" alt="Military Outpost Icon">
      <img class="icon" id="bio_gas_factory" src="images/bio.gif" alt="Bio Gas Factory Icon">
      <img class="icon" id="chip_plant" src="images/quantum.gif" alt="Chip Plant Icon">
      <img class="icon" id="computer_plant" src="images/quantum.gif" alt="Computer Plant Icon">
      <img class="icon" id="crystal_fab" src="images/quantum.gif" alt="Crystal Fab Icon">
      <img class="icon" id="plankton_farm" src="images/farm.gif" alt="Plankton Farm">
      <img class="icon" id="quantum_tube_fab" src="images/quantum.gif" alt="Quantum Tube Fab">
      <img class="icon" id="satellite_factory" src="images/quantum.gif" alt="Satellite Factory">
      <img class="icon" id="weapon_component_factory" src="images/quantum.gif" alt="Weapon Component Factory">

      <img class="icon" id="south_gate" src="images/south_gate.png" alt="Gate Icon">
      <img class="icon" id="east_gate" src="images/east_gate.png" alt="Gate Icon">

      <img class="icon" id="asteroid1" src="images/asteroid.png" alt="Asteroid Icon">
      <img class="icon" id="asteroid2" src="images/asteroid.png" alt="Asteroid Icon">
      <img class="icon" id="asteroid3" src="images/asteroid.png" alt="Asteroid Icon">
      <img class="icon" id="asteroid4" src="images/asteroid.png" alt="Asteroid Icon">
    </div>

    <div id="right">
      <p>Information</p>

      <div id="inner">
        <table>
         
          <tr>
            <th>Station</th>
            <th colspan="3">Coordinates (x, y, z)</th>
          </tr>

          <tr data-name='shipyard'>
            <td>Royal Boron Shipyard</td>
            <td>406m</td>
            <td>4.97km</td>
            <td>-22.5km</td>
          </tr>

          <tr data-name='equipdock'>
            <td>Boron Equipment Dock</td>
            <td>994m</td>
            <td>6.75km</td>
            <td>4.78km</td>
          </tr>

          <tr data-name='trading_station'>
            <td>Boron Stock Exchange</td>
            <td>8.28km</td>
            <td>1.05km</td>
            <td>-1.55km</td>
          </tr>

          <tr data-name='military_outpost'>
            <td>Military Outpost</td>
            <td>6.65km</td>
            <td>3.50km</td>
            <td>-12.6km</td>
          </tr>

          <tr data-name='bio_gas_factory'>
            <td>Bio Gas Factory M Alpha</td>
            <td>-17.1km</td>
            <td>4.26km</td>
            <td>11.7km</td>
          </tr>

          <tr data-name='chip_plant'>
            <td>Chip Plant Alpha</td>
            <td>14.5km</td>
            <td>-4.68km</td>
            <td>5.17km</td>
          </tr>

          <tr data-name='computer_plant'>
            <td>Computer Plant</td>
            <td>-25.0km</td>
            <td>-893m</td>
            <td>-6.01km</td>
          </tr>

          <tr data-name='crystal_fab'>
            <td>Crystal Fab M Alpha</td>
            <td>30.2km</td>
            <td>5.81m</td>
            <td>7.85km</td>
          </tr>

          <tr data-name='plankton_farm'>
            <td>Plankton Farm M Alpha</td>
            <td>-31.1km</td>
            <td>-11.6km</td>
            <td>-17.8km</td>
          </tr>

          <tr data-name='quantum_tube_fab'>
            <td>Quantum Tube Fab Alpha</td>
            <td>7.09km</td>
            <td>-8.36km</td>
            <td>25.8km</td>
          </tr>

          <tr data-name='satellite_factory'>
            <td>Satellite Factory</td>
            <td>-5.80km</td>
            <td>-3.46km</td>
            <td>-35.7km</td>
          </tr>

          <tr data-name='weapon_component_factory'>
            <td>Weapon Component Factory</td>
            <td>32.2km</td>
            <td>1.55km</td>
            <td>22.5km</td>
          </tr>

          </table>

          <table>

          <tr>
            <th>Type</th>
            <th>Yield</th>
            <th colspan="3">Coordinates (x, y, z)</th>
          </tr>

          <tr data-name='asteroid1'>
            <td>Ore</td>
            <td>1</td>
            <td>23.7km</td>
            <td>3.32km</td>
            <td>-20.0km</td>
          </tr>

          <tr data-name='asteroid2'>
            <td>Ore</td>
            <td>2</td>
            <td>-5.11km</td>
            <td>1.38km</td>
            <td>-10.9km</td>
          </tr>

          <tr data-name='asteroid3'>
            <td>Ore</td>
            <td>7</td>
            <td>20.4km</td>
            <td>-1.92km</td>
            <td>-8.49km</td>
          </tr>

          <tr data-name='asteroid4'>
            <td>Ore</td>
            <td>2</td>
            <td>19.0km</td>
            <td>-2.58km</td>
            <td>-181m</td>
          </tr>

          </table>

          <table>

          <tr>
            <th>Gates</th>
            <th>Destination</th>
            <th colspan="3">Coordinates (x, y, z)</th>
          </tr>

          <tr data-name='east_gate'>
            <td>East</td>
            <td>Rolk's Drift</td>
            <td>27.2km</td>
            <td>-4.55km</td>
            <td>-16.4km</td>
          </tr>

          <tr data-name='south_gate'>
            <td>South</td>
            <td>Three Worlds</td>
            <td>11.9km</td>
            <td>0m</td>
            <td>-27.0km</td>
          </tr>

        </table>

      </div>

    </div>

  </div>

</div>

<script>

function hoveron(event)
{
  var target = event.target;
  var attribute = target.getAttribute('data-name');

  document.getElementById(attribute).style.cssText = "border:1px dashed red;";
}

function hoveroff(event)
{
  var target = event.target;
  var attribute = target.getAttribute('data-name');

  document.getElementById(attribute).style.cssText = "border:none;";
}

// get all table rows
var rows = document.querySelectorAll("tr");

for (i = 0; i < rows.length; i++)
{
  rows[i].addEventListener("mouseover", hoveron);
  rows[i].addEventListener("mouseout", hoveroff);
}

</script>

</body>
</html>

Frenzie

User avatar
 
Posts: 2134
Joined: May 5th, 2004, 10:40 am
Location: Belgium

Post Posted May 8th, 2018, 12:47 pm

I'd argue that I gave you the tools to figure it out by putting a description of what you could do in a comment. What I didn't do is spell it out. ;)

so my question is what is the best way for me to make the data-name'...' attribute percolate down from the table row to that rows children, assuming that's actually possible that is.

You could do that, but personally I'd be more inclined to turn it around for simplicity.

The easiest but not necessarily best way to get your example to work is this:
Code: Select all
var attribute = target.getAttribute('data-name') ? target.getAttribute('data-name') : target.parentNode.getAttribute('data-name');

[Edit: look up ternary operator if you don't know that notation yet. See here. It's just an alternative way of writing if/else.]

If you don't know the specific markup you'll encounter you could just keep on going up the tree, e.g. like this.

You could also do the reverse in the script init step (i.e. take the data-* attribute from the TR and stick it in child TDs), but in that case I'd say you should just do it while generating the markup.
Intelligent alien life does exist, otherwise they would have contacted us.

Frenzie

User avatar
 
Posts: 2134
Joined: May 5th, 2004, 10:40 am
Location: Belgium

Post Posted May 8th, 2018, 12:54 pm

Oh, also, an anonymous function looks like this in case you hadn't found it in the docs:

Code: Select all
target.addEventListener('hypermicefrommarshover', function(){
  aFunctionCall('parameter_not_executed_before_event');
});


It's listed on the function overview but doesn't sensibly show up in the search results. It's also not really explained.
https://developer.mozilla.org/en-US/doc ... y/Function

My apologies there; I assumed it would. That is, I gave you the right terms to search for and the MDN docs to search in.
Intelligent alien life does exist, otherwise they would have contacted us.

Return to Web Development / Standards Evangelism


Who is online

Users browsing this forum: No registered users and 1 guest