Kevin Bryan
Kevin Bryan

Reputation: 1858

Select class from component with multiple instances

I have two instances of a component on my page and I need to select it's class to do a css transform, it works but the problem is that the first instance is the only one that is being triggered.

const carousel = document.querySelector(".carousel-slide");
carousel.style.transform = `translateX(-100%)`;

When I click a button my carousel should go next, but I'm always selecting the first .carousel-slide so even if I click the next button on the second instance of my component, the first instance is the one that is being affected

Upvotes: 0

Views: 131

Answers (1)

T.J. Crowder
T.J. Crowder

Reputation: 1074385

Two answers for you:

  1. You may not need to do this at the DOM level.

  2. If you do, you use "refs"

You may not need to do this at the DOM level

From Style and CSS - React:

React can be used to power animations. See React Transition Group and React Motion or React Spring, for example.

Here's an example of adding a class to trigger a (very boring) transform:

class Example extends React.Component {
    constructor(props) {
        super(props);
        this.state = {
            transformed: false
        };
        this.triggerTransform = this.triggerTransform.bind(this);
    }

    triggerTransform() {
        this.setState({transformed: true});
    }

    render() {
        const {transformed} = this.state;
        return <div className={transformed ? "transformed" : undefined} onClick={this.triggerTransform}>Click me</div>;
    }
}

ReactDOM.render(<Example/>, document.getElementById("root"));
.transformed {
    transform: translateX(+10%);
}
<div id="root"></div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.11.0/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.11.0/umd/react-dom.production.min.js"></script>

But if you do (or want to)...

...you use refs for those occasions where you need to cross the React/DOM boundary like that.

  1. Create a ref
  2. Use it on the JSX defining the element you want to target
  3. Use the ref's current property when you need to do something on the actual DOM element

Rough example:

class Example extends React.Component {
    constructor(props) {
        super(props);
        this.myRef = React.createRef();
        this.triggerTransform = this.triggerTransform.bind(this);
    }

    triggerTransform() {
        if (this.myRef.current) {
            this.myRef.current.style.transform = `translateX(+10%)`
        }
    }

    render() {
        return <div ref={this.myRef} onClick={this.triggerTransform}>Click me</div>;
    }
}

ReactDOM.render(<Example/>, document.getElementById("root"));
<div id="root"></div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.11.0/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.11.0/umd/react-dom.production.min.js"></script>


Both of the above can be done with hooks as well, you don't need to be using class components. For some reason I had the impression the OP was using class components, but...I think I invented that.

Upvotes: 1

Related Questions