React: workaround for CSS pointer-events: none in IE9

1.5k views Asked by At

I would appreciate some help in implementing a workaround for pointer-events: none to my React button component in IE9. I use this button to submit a form. I pass down a prop to the button and, based on the value of this prop, the button will have different styling.

I use componentWillReceiveProps to change the state and the styling of my button when it receives the new prop value.

What I am trying to achieve here: submitState is '' then clicks are allowed. submitState is 'loading' or 'success' then disable click on the button.

The issue I have is that I end up trying to query selectors that don’t exist when the component mounts. What am I doing wrong here? How can I make my code below work?

class Button extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      submitState: this.props.buttonState,
      text: 'Click',
      textLoad: 'Loading',
      textSuccess: 'Success'
    }
    this.noclickLoad = this.noclickLoad.bind(this);
    this.noclickSuccess = this.noclickSuccess.bind(this);
  }

  loading () {
    this.setState({
      submitState: 'loading'
    });
  }
  success() {
    this.setState({
      submitState: 'success'
    });
  }
  disabled() {
    this.setState({
      submitState: 'disabled'
    });
  }
  nothing() {
    this.setState({
      submitState: ''
    })
  }

  noclickLoad() {
    document.querySelector('.myButtonContainer.loading .myButton').style.cursor = 'default';   
    document.querySelector('.myButtonContainer.loading .myButton').disabled = 'true';
  }
  noclickSuccess() {
    document.querySelector('.myButtonContainer.success .myButton').style.cursor = 'default';   
    document.querySelector('.myButtonContainer.success .myButton').disabled = 'true';
  }

  componentWillReceiveProps(nextProps) {
    if(nextProps.submitState === this.props.submitState) {
      return
    } 
    switch (nextProps.submitState) {
      case 'loading':
        this.loading();
        break;
      case 'success':
        this.success();
        break;
      case '': 
        this.nothing();
        break;
      default: 
        return
    }
  }
  componentDidMount () {
    window.addEventListener('load', this.noclickLoad);
    window.addEventListener('load', this.noclickSuccess);
  }

  render() {
    return (
      <div>
        <div className={`myButtonContainer ${this.state.submitState}`}>
          <button className="myButton">
            <div className="buttonText">{this.state.text}</div>
            <div className="buttonTextLoad">{this.state.textLoad}</div>
            <div className="buttonTextSuccess">{this.state.textSuccess}</div>
          </button>
        </div>
      </div>
    );
  }
}

And the css

.myButtonContainer .myButton {
    background-color: red;
}
.myButtonContainer .myButton .buttonTextLoad, .myButtonContainer .myButton .buttonTextSuccess {
    display: none;
}

.myButtonContainer.loading .myButton {
    background-color: yellow;
}
.myButtonContainer.loading .myButton .buttonTextLoad {
    display: block;
}
.myButtonContainer.loading .myButton .buttonText, .myButtonContainer.loading .myButton .buttonTextSuccess {
    display: none;
}
.myButtonContainer.success .myButton {
    background-color: chartreuse;
}
.myButtonContainer.success .myButton .buttonTextSuccess {
    display: block;
}
.myButtonContainer.success .myButton .buttonText, .myButtonContainer.success .myButton .buttonTextLoading {
    display: none;
}
2

There are 2 answers

0
leaf On

It seems that .loading and .success of button container won't coexist at the same time. Use if statement to make sure that the selector's element exists before change it.

// Same to .success
let button = document.querySelector('.myButtonContainer.loading .myButton');
if (button) {
    button.style.cursor = 'default';   
    button.disabled = 'true';
}
0
Sagar Mistry On
const [loading, setLoading] = useState(false);

<div id='inputArea' className={`input-area${loading ? ' pointerEventNone' : ''}`} aria-disabled={loading}>
    //code..
</div>

<button className="myButton" onClick={()=>setLoading(!loading)}>Toggle Button for Disable</button>

css:

.pointerEventNone {
    pointer-events: none;
}