Jump to content


  • Posts

  • Joined

  • Last visited


2 Newbie
  1. Thanks so much for the detailed explanation. I am still quite new to the JS world so it takes me some time to realize this. After posting I realized that it has to do with async/await. I will look further into it as I think it will be needed in the future. Thanks again and have a great weekend. Happy Tweening!!
  2. Hi Rodrigo, thank you very much for clarifying everything. I was expecting its an issue with the ref, however I am new to both React and GSAP so debugging was a little nightmare. I have now managed to make it work. To add to the answer, I don't understand why, but it was an issue when I was trying to create the TweenMax before making a `fetch()` inside `componenetDidMount()`. Only once I moved the Tween inside `.then()` I it started working again. Thanks again for the help. Greetings, Nikolay "Donkoko"
  3. Hello everyone, since recently I started using React with GSAP. I have little experience in both, so the struggle is real. I am trying to create something very simple, a full screen menu that you can show/hide. When i am trying to debug this, i can see the state changing, and if I try to print within the `toggleMenu()`, method, i can see the state is changing however `timeline.play()`, simply doesn't do anything. I tried also removing the if case for play and reverse but still no effect. Its just atht my timeline doesnt want to play. I also tried using `componentDidUpdate()` but still no success. in that case my code looked like this: toggleMenu() { this.setState({ visible: !this.state.visible }); } componentDidUpdate(prevProps, prevState){ const {visible: preVisible} = prevState; const { visible } = this.state; if (visible && visible !== preVisible) { this.timeline.play(); } } componentDidMount(){ this.timeline = new TimelineLite({ paused: true }) .to(this.menuRef.current, 0.5, {autoAlpha: 1}); // .staggerTo(this.listNodes, 0.3, { opacity: 1,y: 0}, 0.2, "-=0.3"); } This is my container, where the magic is supposed to happen: import React, { Component } from "react"; import Hamburger from "./hamburger.jsx"; import Menu from "./menu.jsx"; import Logo from "./misc/Logo.jsx"; import { TweenMax, TimelineLite, CSSPlugin } from "gsap/all"; import { Transition } from "react-transition-group"; class MenuContainer extends Component { constructor(props) { super(props); this.state = { visible: false }; this.toggleMenu = this.toggleMenu.bind(this); this.timeline = null; this.menuRef = React.createRef(); } toggleMenu() { console.log(this.state.visible) this.state.visible ? this.timeline.reverse() : this.timeline.play(); this.setState({ visible: !this.state.visible }); } componentDidMount(){ this.timeline = new TimelineLite({ paused: true }) .to(this.menuRef.current, 0.5, {autoAlpha: 1}); // .staggerTo(this.listNodes, 0.3, { opacity: 1,y: 0}, 0.2, "-=0.3"); } render() { const { visible } = this.state; let logoColor = "#3e444e"; //blue if (visible) logoColor = "#ffffff"; //White return ( <div className="nav-wrapper"> <div className="top-bar"> <div className="top-bar-left"> <Logo logocolor={logoColor} /> </div> <div className="top-bar-right"> <div> <Hamburger handleMouseDown={this.toggleMenu} menuVisibility={visible} /> </div> </div> </div> <div> <Menu visible={visible} menuRef={this.menuRef} /> </div> </div> ); } } export default MenuContainer; This is the menu element where I am setting the `ref`: import React, { Component } from "react"; import { apiUrl } from './../../methods'; class Menu extends Component { constructor(props) { super(props); this.state = { links: [], isLoading: false, error: null }; } componentDidMount() { const targetUrl = apiUrl("/sapi/main_menu_items.json"); this.setState({ isLoading: true }); fetch(targetUrl) .then(response => { if (response.ok) { return response.json(); } else { throw new Error("Something went wrong...."); } }) .then(data => this.setState({ links: data.links, isLoading: false })) .catch(error => this.setState({ error, isLoading: false })); //Passing the data to state.links and changing isLoading to false } render() { const { links, isLoading, error } = this.state; const listItems = links.map((link, index) => ( <li className="menu-link v-link" key={link.slug} // ref={li => (this.listNodes[index] = li)} > <a href={link.slug}>{link.title}</a> </li> )); if (error) return <p>{error.message}</p>; if (isLoading) return <p>Loading....</p>; return ( <div className="full-screen-menu" ref={this.props.menuRef}> <div className="grid-y grid-frame align-middle"> <div className="cell auto links-wrapper"> <div className="grid-container full-height"> <div className="grid-x align-middle full-height"> <div className="cell small-12"> <ul className="links">{listItems}</ul> </div> </div> </div> </div> <div className="cell shrink"> <div className="grid-container"> <div className="grid-x"> <div className="cell small-12 text-right text-white"> <ul> <li> <a className="text-white">+31 638 501 270</a> </li> <li> <a className="text-white">hello@whale-agency.com</a> </li> </ul> </div> </div> </div> </div> </div> </div> ); } } export default Menu; And here is the hamburger, that is being clicked: import React, { Component } from "react"; import MenuOpener from "./misc/menuOpener.jsx"; import MenuCloser from "./misc/menuCloser.jsx"; class Hamburger extends Component { render() { if (!this.props.menuVisibility) { return ( <MenuOpener className="menu-button" onMouseDown={this.props.handleMouseDown} /> ); } else { return ( <MenuCloser className="menu-button" onMouseDown={this.props.handleMouseDown} /> ); } } } export default Hamburger; Last but not least, the important css: .full-screen-menu { position: absolute; opacity: 0; visibility: hidden; width: 100vw; height: 100vh; bottom: 0; left: 0; background: url(/images/menu-background.jpg); background-size: cover; background-position: center; background-repeat: no-repeat; z-index: 999; } Hopefully someone can help me go in the right direction. Greetings, Nikolay