简体   繁体   中英

JavaScript- Events: How To Trigger onClick of underlayed image?

I have two images one on top of another (using absolute position).

Only the underlayed image has an onClick event defined and I want to trigger onClick event of the underlayed image when I click the overlayed image.

I found that for multiple div tags, I can stop these behaviors using stopImmediatePropagation .

However, it seems that image elements do not propagate events by default. Is there any ways that I can turn on these behaviors with a plain javascript or react?

+) I know image absolute positioning is a bad practice. I am creating a board game, and there are some special places you can visit on top of a main board image. Any suggestion is appreciated.

<img className="map" src="map.jpg"></img>
<img className="mission" src="mission.jpg"
     style={{react.js part setting top and left}}></img>

.board {
  position: relative;
  height: auto;
  width: 100%;
  float: left;
}
.mission {
  position: absolute;
  height: 10%;
  width: auto;
}

Since the element that is in front is the one that the click event will be fired on, you can put the event handler on that element. Then, inside that event handler, you can select the DOM element of the image that is in the back and use JavaScript to trigger an event on it.

For Vanilla JavaScript:

One way is to use the.click() method on the DOM element.

https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/click

let imageInBack = document.getElementById('image-in-back')
let imageInFront = document.getElementById('image-in-front')

imageInFront.addEventListener('click', (e)=>{
    e.stopPropagation() //for general purposes, this won't affect theater image
    imageInBack.click() //programatically cause the other image to be clicked.
})

For a React JSX/ Class Component:

Since you appear to be using React, I am guessing that there is probably a better way to accomplish what you are trying to do, without triggering an event on another element. But as far as literally triggering a click event, here is one way:

class MyComponent extends React.Component {
  constructor(props) {
    super(props)
    this.imageInBack = React.CreateRef() //gets this variable ready to store a DOM element.  See the ref property in the JSX, where the DOM element actually gets assigned to this variable.
  }

  //the event handler will be assigned to the imageInFront, but it will trigger the DOM element of the image in back:

  handleClick(e) {
      this.imageInBack.click()
  }
  render() {
    return <div style={{position: 'relative'}}>
       <img 
            ref={(img)=> {this.imageInBack = img}}
            className="image-in-back"  
            style={{position: 'absolute', top: '0px', left: '0px'}}/>
       <img className="image-in-front" 
            style={{position: 'absolute', top: '0px', left: '0px'/>
     </div>;
     }
   }
}

You can re-assign the event handler from the back image to the front image. Make sure and cancel the handler on the back image as well:

let imageInBack = document.getElementById('image-in-back')
let imageInFront = document.getElementById('image-in-front')

let events = getEventListeners(imageInBack)
if(events["click"]){
  events["click"].forEach((event) => {
    imageInFront.addListener('click', event["listener"]);
    imageInBack.removeListener('click', event["listener"]);
  }
}

I agree with other commenters that if you are using React, then there is probably a better way to accomplish this.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM