skip to Main Content

I have a situation where I want to add two different parameters as I want to display image tag popups in different positions?

This function is to display popup on left side

 function openBubble() {
      var content = myData[this.id];
      bubbleContent.innerHTML = '<h3>' + content.title + '</h3>'
                              + '<img src="' + content.image + '" alt="" />'
                              + '<p>' + content.description + '</p>';
      bubble.style.top = (event.clientY - 20) + "px";                        
      bubble.style.left = (event.clientX - 200) + "px";                        
      bubble.className = 'shown';
    }

This function is to display popup on right side

function openBubble() {
  var content = myData[this.id];
  bubbleContent.innerHTML = '<h3>' + content.title + '</h3>'
                          + '<img src="' + content.image + '" alt="" />'
                          + '<p>' + content.description + '</p>';
  bubble.style.top = (event.clientY + 20) + "px";                        
  bubble.style.left = (event.clientX + 200) + "px";                        
  bubble
.className = 'shown';
}

Here is my HTML –

<map name="myMap" id="myMap">
  <area id="left-eye"  coords="118,36,148,80" shape="rect" href="javascript:void(0);">
  <area id="mouth"  coords="121,84,198,118" shape="rect" href="javascript:void(0);">
</map>

I want to associate area id="left-eye" with function on the left side.
I want to associate area id="mouth" with function on the right side.

Here is the jsfiddle to my code – https://jsfiddle.net/1u6n5rvw/

How can I do this? Thanks.

3

Answers


  1. make the positions properties of the objects …

    var myData = {
          "left-eye": {
              "title": "ggfhfhgh",
              "image":"",
              "description": "Lorem ipsum A dolor sin amet. .",
              "left": -200,
              "top": -20
          },
          "mouth": {
              "title": "",
              "description": "...",
              "left": 200,
              "top": 20
          }
       };
      ......
     bubble.style.top = (event.clientY + this.top) + "px";                        
     bubble.style.left = (event.clientX + this.left) + "px";
    

    Using a switch would be quick and dirty but this is more scaleable.

    Login or Signup to reply.
  2. Your case is a bit special, as you are already retreiving data based on the id of the element you cliked.

    As you are learning JavaScript, I will explain in case you are not sure: when you add an event listener like this areas[i].addEventListener('click', openBubble, false); (passing directly the function reference), JavaScript binds for you this to the HTML element you clicked, that allows you to use this.id inside the function.

    Now, the more flexible to you IMO will be to use this data so you can configure directly the window position inside the data. This way, you can keep using the function reference as the event handler without having to add more code to pass parameters to the function (it’s possible, but more complicated)

    Here is a first version if you only want to distinguish between "left" and "right", by adding a string property position to your data and testing against fixed values

    $(function() {
        $('.map').maphilight();
      });
    var myData = {
        "left-eye": {
            "title": "",
            "image":"",
            "description": "Lorem ipsum A dolor sin amet. .",
            "position": "left"
        },
        "mouth": {
            "title": "",
           
            "description": "Lorem ipsum B dolor sin amet. Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.vLorem ipsum B dolor sin amet.vLorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.</p>Lorem ipsum B dolor sin amet.",
            "position": "right"
        },
       
    };
    
    var areas         = document.getElementsByTagName('area'),
        bubble        = document.getElementById('myBubble'),
        bubbleContent = document.getElementById('myBubbleContent'),
        bubbleClose   = document.getElementById('myBubbleCloseButton');
    
    // On click of an area, open popup
    for(var i=0, l=areas.length; i<l; i++) {
      areas[i].addEventListener('click', openBubble, false);
    }
    
    // On click of close button, close popup
    bubbleClose.addEventListener('click', closeBubble, false);
    
    function openBubble() {
      var content = myData[this.id];
      bubbleContent.innerHTML = '<h3>' + content.title + '</h3>'
                              + '<img src="' + content.image + '" alt="" />'
                              + '<p>' + content.description + '</p>';
      if(content.position === 'left'){
        bubble.style.top = (event.clientY - 20) + "px";                        
        bubble.style.left = (event.clientX - 200) + "px";    
      }else if(content.position === 'right'){
        bubble.style.top = (event.clientY + 20) + "px";                        
        bubble.style.left = (event.clientX + 200) + "px";    
      }
      bubble.className = 'shown';
    }
    
    
    
    
    
    function closeBubble() {
      bubble.className = '';
    }
    
    // Make the image map responsive
    imageMapResize();
    
    $.fn.maphilight.defaults = {
    fill: true,
    fillColor: '1A8782',
    fillOpacity: 1,
    stroke: true,
    strokeColor: '#1A8782',
    strokeOpacity: 1,
    strokeWidth: 1,
    fade: true,
    alwaysOn: false,
    neverOn: false,
    groupBy: false,
    wrapClass: true,
    shadow: false,
    shadowX: 0,
    shadowY: 0,
    shadowRadius: 6,
    shadowColor: '000000',
    shadowOpacity: 0.8,
    shadowPosition: 'outside',
    shadowFrom: false
    }
    #myWrapper{ position: relative; font-family: Arial, Helvetica, sans-serif; }
    #myImage{ display: block; }
    #myBubble{  background: #fff; border: 1px solid #aaa; padding: .5rem 1rem; display: none; top: 1.5rem; left: 1.5rem; width: 40%;  }
    #myBubble.shown{position: fixed; display: block;cursor: pointer;font-size: 0.8rem;
        margin-top: 0.2rem; filter: drop-shadow(0 2px 4px rgba(0,0,0,0.5)); width:20%; }
        #myBubble.shown:before{
        content: "";
        position: absolute;
        top: 20px;
        left:-30px;
        z-index: 1;
        border: solid 15px transparent;
        border-right-color: #FFF;
        
    }
    #myBubble img{ display: block; width: 100%;
    }
    #myBubbleCloseButton{ position: absolute; top: 0; right: 0; padding: .5rem;  line-height: 1; cursor: pointer; color: #1A8782; }
    #myBubbleCloseButton:hover{  color: #1A8782;  }
    <script src="https://cdn.rawgit.com/davidjbradshaw/image-map-resizer/master/js/imageMapResizer.js"></script>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
    <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/maphilight/1.4.0/jquery.maphilight.min.js"></script>
    
    <div id="myWrapper">
    
       <img id="myImage" src="http://tinypic.com/images/goodbye.jpg" usemap="#myMap" alt="" class="map" />
    
    
     <map name="myMap" id="myMap">
      <area id="left-eye"  coords="118,36,148,80" shape="rect" href="javascript:void(0);">
      <area id="mouth"  coords="121,84,198,118" shape="rect">
    </map>
    
       <div id="myBubble">
          <div id="myBubbleContent"></div>
          <div id="myBubbleCloseButton">✕</div>
        </div>
    </div>

    Here is a more flexible version where you can directly set the x and y offsets by adding numeric properties yOffset and xOffset to your data and using them directly to set the window coordinates

    $(function() {
        $('.map').maphilight();
      });
    var myData = {
        "left-eye": {
            "title": "",
            "image":"",
            "description": "Lorem ipsum A dolor sin amet. .",
            "yOffset": -20,
            "xOffset": -200
        },
        "mouth": {
            "title": "",
           
            "description": "Lorem ipsum B dolor sin amet. Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.vLorem ipsum B dolor sin amet.vLorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.</p>Lorem ipsum B dolor sin amet.",
            "yOffset": +20,
            "xOffset": +200
        },
       
    };
    
    var areas         = document.getElementsByTagName('area'),
        bubble        = document.getElementById('myBubble'),
        bubbleContent = document.getElementById('myBubbleContent'),
        bubbleClose   = document.getElementById('myBubbleCloseButton');
    
    // On click of an area, open popup
    for(var i=0, l=areas.length; i<l; i++) {
      areas[i].addEventListener('click', openBubble, false);
    }
    
    // On click of close button, close popup
    bubbleClose.addEventListener('click', closeBubble, false);
    
    function openBubble() {
      var content = myData[this.id];
      bubbleContent.innerHTML = '<h3>' + content.title + '</h3>'
                              + '<img src="' + content.image + '" alt="" />'
                              + '<p>' + content.description + '</p>';
      bubble.style.top = (event.clientY + content.yOffset) + "px";                        
      bubble.style.left = (event.clientX + content.xOffset) + "px";    
      bubble.className = 'shown';
    }
    
    
    
    
    
    function closeBubble() {
      bubble.className = '';
    }
    
    // Make the image map responsive
    imageMapResize();
    
    $.fn.maphilight.defaults = {
    fill: true,
    fillColor: '1A8782',
    fillOpacity: 1,
    stroke: true,
    strokeColor: '#1A8782',
    strokeOpacity: 1,
    strokeWidth: 1,
    fade: true,
    alwaysOn: false,
    neverOn: false,
    groupBy: false,
    wrapClass: true,
    shadow: false,
    shadowX: 0,
    shadowY: 0,
    shadowRadius: 6,
    shadowColor: '000000',
    shadowOpacity: 0.8,
    shadowPosition: 'outside',
    shadowFrom: false
    }
    #myWrapper{ position: relative; font-family: Arial, Helvetica, sans-serif; }
    #myImage{ display: block; }
    #myBubble{  background: #fff; border: 1px solid #aaa; padding: .5rem 1rem; display: none; top: 1.5rem; left: 1.5rem; width: 40%;  }
    #myBubble.shown{position: fixed; display: block;cursor: pointer;font-size: 0.8rem;
        margin-top: 0.2rem; filter: drop-shadow(0 2px 4px rgba(0,0,0,0.5)); width:20%; }
        #myBubble.shown:before{
        content: "";
        position: absolute;
        top: 20px;
        left:-30px;
        z-index: 1;
        border: solid 15px transparent;
        border-right-color: #FFF;
        
    }
    #myBubble img{ display: block; width: 100%;
    }
    #myBubbleCloseButton{ position: absolute; top: 0; right: 0; padding: .5rem;  line-height: 1; cursor: pointer; color: #1A8782; }
    #myBubbleCloseButton:hover{  color: #1A8782;  }
    <script src="https://cdn.rawgit.com/davidjbradshaw/image-map-resizer/master/js/imageMapResizer.js"></script>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
    <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/maphilight/1.4.0/jquery.maphilight.min.js"></script>
    
    <div id="myWrapper">
    
       <img id="myImage" src="http://tinypic.com/images/goodbye.jpg" usemap="#myMap" alt="" class="map" />
    
    
     <map name="myMap" id="myMap">
      <area id="left-eye"  coords="118,36,148,80" shape="rect" href="javascript:void(0);">
      <area id="mouth"  coords="121,84,198,118" shape="rect">
    </map>
    
       <div id="myBubble">
          <div id="myBubbleContent"></div>
          <div id="myBubbleCloseButton">✕</div>
        </div>
    </div>
    Login or Signup to reply.
  3. Since you already have the object myData, you can store the top and left values in there. You can store the negatives with a minus and the positive without it. Then for the math just + those values.

    var myData = {
    "left-eye": {
            "top" : -20,
            "left" : -200,
            "title": "",
            "image":"",
            "description": "Lorem ipsum A dolor sin amet. ."
        },
        "mouth": {
            "top" : 20,
            "left" : 200,
            "title": "",       
            "description": "Lorem ipsum B dolor sin amet. Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.vLorem ipsum B dolor sin amet.vLorem ipsum B dolor sin amet.Lorem ipsum B dolor sin amet.</p>Lorem ipsum B dolor sin amet."
        },
       
    };
    
    const areas = document.querySelectorAll('area')
    areas.forEach((a) => a.addEventListener("click",openBubble,false))
    
    function openBubble(){
      const data = myData[this.id];
      const top = (event.clientY + data.top) + "px";                        
      const left = (event.clientX + data.left) + "px";   
      console.log(event.clientY, data.top,top)
      console.log(event.clientX, data.left,left)
    }
    <img id="myImage" src="http://tinypic.com/images/goodbye.jpg" usemap="#myMap" alt="" class="map" />
    <map name="myMap" id="myMap">
      <area id="left-eye"  coords="118,36,148,80" shape="rect" href="javascript:void(0);">
      <area id="mouth"  coords="121,84,198,118" shape="rect" href="javascript:void(0);">
    </map>
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search