Jump to content
Search Community

GSAP and React is it possible to pass a dynamic reference URL to a clipPath?

Gilbert test
Moderator Tag

Warning: Please note

This thread was started before GSAP 3 was released. Some information, especially the syntax, may be out of date for GSAP 3. Please see the GSAP 3 migration guide and release notes for more information about how to update the code to GSAP 3's syntax. 

Recommended Posts

I am trying to use GSAP with React. 

In React I am creating a component with some text animations,  for which I would I would like to create several instances at runtime.

 

The main component should look like this:

import React, { Component } from 'react';
import './App.css';
import { TimelineMax, Bounce} from 'gsap';

import Title from './Title.js';

let mainTimeline;

class App extends Component {
  componentDidMount() {
    setTimeout(this.animate, 1000);
  }

  componentWillUnmount() {
    mainTimeline.kill();
  }

  animate = () => {
    mainTimeline = new TimelineMax({ id: 'Everything' });
    const titleTimeLine = new TimelineMax({ id: 'Title' });
    const titleTimeLine2 = new TimelineMax({ id: 'Title2' });

    mainTimeline.addLabel('start');

    // get external timelines
    titleTimeLine.add(this.title.timelineEnter);
    titleTimeLine2.add(this.title2.timelineEnter)

    mainTimeline
      .add(titleTimeLine, 'start')
      .addLabel("title2")
      .add(titleTimeLine2, 'title2')
  }

  render() {
    return (
      <div className="App">
        <Title text="The benefits are:" clipPathId="clipPath1" ref={(el) => { this.title = el; }}/>
        <Title text="This should work" clipPathId="clipPath2" ref={(el) => { this.title2 = el; }}/>
      </div>
    );
  }
}

export default App;


And the Tile component is:

import React, { Component } from 'react';
import { TimelineMax, Power4, SlowMo} from 'gsap';
import './Title.css'

class Title extends Component {
  constructor(props) {
    super(props);
    const { text, clipPathId } = this.props;
  }

  get timelineEnter() {
    const tl = new TimelineMax();
    const duration = 1;

    tl.to(this.line, duration, {attr:{x1:120, x2:880}, ease:Power4.easeInOut})
    .to([this.reveal, this.line], duration, {y:"+=120",  ease:Power4.easeInOut})
    .to(this.line, duration, {attr:{x1:500, x2:500}, ease:Power4.easeInOut})
    .to(this.clipPathReveal, duration, {y: -180, scale: .3, transformOrigin:"50% 50%", ease:SlowMo.ease.config(0.7, 0.7, false)})
  return tl;
}

render() {
  return (
    <svg className="demo" viewBox="0 0 1000 500">
      <defs>
        <clipPath id={this.props.clipPathId} ref={(el) => { this.theClipPath = el; }}>
          <rect ref={(el) => { this.reveal = el; }} x="0" y="-100" width="1000" height="250" fill="#000" />
        </clipPath>
      </defs>
      <line ref={(el) => { this.line = el; }} x1="500" y1="150" x2="500" y2="150" strokeWidth="20" stroke="red"/>
      <g ref={(el) => { this.clipPathReveal = el; }} clipPath="url(#clipPath1)">
        <text transform="translate(500 250)" fill="#3088Ef" textAnchor="middle" fontSize="80">{this.props.text}</text>
      </g>
    </svg>
    );
  }
}

export default Title;

The problem is that in the code:
 

<g ref={(el) => { this.clipPathReveal = el; }} clipPath="url(#clipPath1)">
    <text transform="translate(500 250)" fill="#3088Ef" textAnchor="middle" fontSize="80">{this.props.text}</text>
</g>

for the clipPath attribute, I need to pass a dynamic URL. Otherwise, it doesn't work correctly.

 

Is there a way to pass a dynamic id to the URL in clipPath="url(#clipPath1)".

Something like clipPath="url({dynamicURL})" or something?

 

In the first instance of <Title>, it should produce clipPath="url(#clipPath1)", while in the second it should be clipPath="url(#clipPath2)" and so on.

Link to comment
Share on other sites

Hi Gilbert,

 

I'll assume that the clipPathId passed in the components props is the url you want to add, right?

 

If that's the case you can use template literals a feature from ES2015:

 

<g ref={(el) => { this.clipPathReveal = el; }} clipPath={`url#${this.props.clipPathId}`}>

 

If this is not what you're after, please let us know how the specific clip url is being passed.

 

Happy Tweening!!!

  • Like 2
Link to comment
Share on other sites

13 hours ago, PointC said:

My apologies. When I see React in the thread title I just assume the Rodrigo React Signal has been fired up and my services will not be necessary.

 

The signal is only visible at night, so it might be awhile before he actually sees it.

 

Maybe you should fill that void. I hereby promote you to the role of Senior Daytime React Answering Manager, so you should start learning it. I think the basics are pretty easy to pickup, and being able to combine JavaScript with HTML/SVG is a joy.

https://reactjs.org/

https://reactjs.org/tutorial/tutorial.html

 

 

 

  • Like 6
Link to comment
Share on other sites

19 minutes ago, OSUblake said:

Maybe you should fill that void. I hereby promote you to the role of Senior Daytime React Answering Manager, so you should start learning it.

 

Sounds good. It's officially item 1,437 on my 'to-do' list so I may not get to it until the year 2029.

 

Unless you're gonna let me use your Blaketrix headjack so I can learn it in a few seconds. 

 

r0RjYUz.jpg

  • Like 3
  • Haha 3
Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...