How can I embed VaniilaJS into React?

Viewed 2196

I have open source library that I want to use. the library wrote in clean vanilla js: follow their docs, if I want to use the library:

<html>
    <head>
        <script src="./jquery-2.0.3.min.js"></script>
        <script src="./kinetic-v5.1.0.min.js"></script>
        <script src="./inchlib-1.2.0.js"></script>
        <script>
        $(document).ready(function() { //run when the whole page is loaded
            var inchlib = new InCHlib({"target": "inchlib",
                            "width": 800,
                            "height": 1200,
                            "column_metadata_colors": "RdLrBu",
                            "heatmap_colors": "RdBkGr",
                            "max_percentile": 90,
                            "middle_percentile": 60,
                            "min_percentile": 10,
                            "heatmap_font_color": "white",
                             text: 'biojs'});
        inchlib.read_data_from_file("/microarrays.json");
        inchlib.draw();

    inchlib.onAll(function(name){
        console.log(name + " event triggered");
    });

});
        </script>
    </head>

    <body>
        <div class="heatmaps" style="margin:auto; align-items: center; margin-left:25%;">
            <div id="inchlib"></div>
        </div>
        <div ></div>
    </body>
 </html>    

The file inchlib-1.2.0.js contains the main logic and js code. I want to build react project and use this library there. How can I achieve this goal?

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

export default class App extends Component {
  render () {
    return (
   <div>
      <div>
      </div>
   </div>
)
  }
}
5 Answers

You can create custom hook with useEffect. In useEffect you should paste your code. You can insert html elements, add event listeners and so on.

useLibrary.js

import { useEffect } from "react";

const useLibrary = () => {

  useEffect(() => {
    $.getScript("inchlib-1.2.0.js", function(){
       var inchlib = new InCHlib({"target": "inchlib",
                          "width": 800,
                          "height": 1200,
                          "column_metadata_colors": "RdLrBu",
                          "heatmap_colors": "RdBkGr",
                          "max_percentile": 90,
                          "middle_percentile": 60,
                          "min_percentile": 10,
                          "heatmap_font_color": "white",
                           text: 'biojs'});
      inchlib.read_data_from_file("/microarrays.json");
      inchlib.draw();
      inchlib.onAll(function(name){
          console.log(name + " event triggered");
      });
    });
  }, []);


};

export default useLibrary;


App.js

import useLibrary from ".useLibrary";
export default class App extends Component {
  useLibrary();
  render () {
    return (
   <div>
      <div class="heatmaps" style="margin:auto; align-items: center; margin-left:25%;">
        <div id="inchlib"></div>
      </div>
   </div>
)
  }
}

But I warn you that this is a big crutch.

Well If I were to do the same thing then I would paste the script tags as you've done in your html file

<head>
    <script src="./jquery-2.0.3.min.js"></script>
    <script src="./kinetic-v5.1.0.min.js"></script>
    <script src="./inchlib-1.2.0.js"></script>
    <script>
 </head>

For accessing an object into react app, Create a file named Inchlib.js in same directory as is your app.js

Contents of Inchlib.js should be

export default window.InCHlib;

Import the default export into your app.js

import InCHlib from "./inchlib";

function App() {
    console.log(InCHlib); // prints the InCHlib object
    return "hello";
}

Note: Although this should work, there might be a better way to do this. Also using global objects in react code is not usually a preferred option.

Hopefully this would help.

Depends on what you're gonna do with the library you want to integrate with. Checkout this as a base reference: Integrating with other libraries.

If you're gonna manipulate DOM elements you'll gonna need a reference to them. In this case checkout this: Refs and the DOM.

If the library provides some general logic, you have no problem using it anywhere throughout your code or more specifically in effects.

As inchlib is a visual element library, you'll need to go the first route and get a reference to a specific DOM element. As already noted, checkout Refs from react docs.

Alternative solution is to wrap the whole library usage in your own react component.

Just add the Libraries and Scripts you want in the public/index.html file in your react project.

create loadScript function:

 function loadScript(src, position, id) {
  if (!position) {
    return;
  }

  const script = document.createElement('script');
  script.setAttribute('async', '');
  script.setAttribute('id', id);
  script.src = src;
  position.appendChild(script);
}

in Component:

 export default function GoogleMaps() {

    const loaded = React.useRef(false);

     if (typeof window !== 'undefined' && !loaded.current) {
       if (!document.querySelector('#google-maps')) {
         loadScript(
           'https://maps.googleapis.com/maps/api/js?key=AIzaSyBwRp1e12ec1vOTtGiA4fcCt2sCUS78UYc&libraries=places',
           document.querySelector('head'),
           'google-maps',
         );
       }

       loaded.current = true;
     }
  }

now you can access window.google

here is a example

Related