Search code examples
reactjsmaterialize

How to import JS library and script to React project?


I have a working project and imported a library (materialize.js), and a little script that works with sidenav, but it does'nt work.

The scripts makes an EventListener to an icon, and shows a sidenav. The icon and the sidenav are olaced in different components.

Here is the listing of Header component (I removed a lot of staff, that's not relevant to the script):

import React, { Component } from 'react';
import logo from '../img/logo.png';
import { Link } from 'react-router-dom';

class Header extends Component {
  render() {
    return (
      <div id="top" className="dark">
        <section id="top-section">
          <div className="container">
            <div className="flex-bet">
              <Link to="/"><div className="logo"><img src={logo} alt="" /></div></Link>
              <a href="#" data-target="mobile-demo" className="sidenav-trigger right hide-on-large-only">
                <i id="icon" className="material-icons">menu</i>
              </a>
            </div>
          </div>
        </section>
      </div>
    );
  }
}

export default Header;

The sidenav component:

import React, { Component } from 'react';

class Sidenav extends Component {
  render() {
    return (
      <ul className="sidenav" id="mobile">
        <li className="sidenav-close"><a href="">111</a></li>
        <li className="sidenav-close"><a href="">222</a></li>
        <li className="sidenav-close"><a href="">333</a></li>
        <li className="sidenav-close"><a href="">444</a></li>
        <li className="sidenav-close"><a href="">555</a></li>
      </ul>
    );
  }
}

export default Sidenav;

An index.html file, where the library and the script are imported:

<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="utf-8" />
  <link rel="shortcut icon" href="%PUBLIC_URL%/favicon.png" />
  <meta name="viewport" content="width=device-width, initial-scale=1" />
  <meta name="theme-color" content="#000000" />
  <title>Интер Сухум</title>
  <link href="https://fonts.googleapis.com/icon?family=Material+Icons" rel="stylesheet">
  <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css">
  <link href="https://fonts.googleapis.com/css?family=Alegreya|Alegreya+Sans|Alice|Anonymous+Pro|Andika|Arimo|Arsenal|Cousine|El+Messiri|Forum|Gabriela|Jura|Ledger|Literata|Lora|Merriweather|Montserrat+Alternates|Noto+Sans|Noto+Serif|Noto+Serif+SC|Noto+Serif+TC|PT+Mono|PT+Serif|PT+Serif+Caption|Play|Prata|Source+Sans+Pro|Spectral|Tenor+Sans|Tinos|Ubuntu+Condensed|Vollkorn&display=swap"
    rel="stylesheet">
  <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
  <link rel="stylesheet" type="text/css" charset="UTF-8" href="https://cdnjs.cloudflare.com/ajax/libs/slick-carousel/1.6.0/slick.min.css" />
  <link rel="stylesheet" type="text/css" href="https://cdnjs.cloudflare.com/ajax/libs/slick-carousel/1.6.0/slick-theme.min.css" />
</head>

<body>
  <noscript>You need to enable JavaScript to run this app.</noscript>
  <div id="root"></div>  
  <script>
    $(document).ready(function () {
      $('.sidenav').sidenav();
    }); 
  </script>
  <script src="https://snapwidget.com/js/snapwidget.js"></script>
  <script type="text/javascript" src="js/materialize.js"></script>
</body>

</html>

What is wrong with this approach? Thanks to everyone!


Solution

  • Is not ideal to manipulate the DOM directly when using React

     $(document).ready(function () {
          $('.sidenav').sidenav();
        }); 
    

    You can add onClick events to your sidenav items and call your sidenav func there.

    import React, { Component } from 'react';
    
    class Sidenav extends Component {
    
      sidenav = () => {
        // handle logic here
      }
      render() {
        return (
          <ul className="sidenav" id="mobile">
            <li className="sidenav-close" onClick={this.sidenav}><a href="">111</a></li>
            <li className="sidenav-close" onClick={this.sidenav}><a href="">222</a></li>
            <li className="sidenav-close" onClick={this.sidenav}><a href="">333</a></li>
            <li className="sidenav-close" onClick={this.sidenav}><a href="">444</a></li>
            <li className="sidenav-close" onClick={this.sidenav}><a href="">555</a></li>
          </ul>
        );
      }
    }
    
    export default Sidenav;
    

    I suggest using the React implementation of Materialize, it will make your life much easier.

    http://react-materialize.github.io/react-materialize/?path=/story/react-materialize--welcome