Include particles.js into rails / webpack project - javascript

I have a project based on Rails 6.0.0.rc2 including webpack. I am trying to include simply the library particles.js
I am following the GitHub readme:
- Install the library with yarn
- Add a container with a specific id
- Try to initialize the function using particlesJS.load
Obviously, it is not working: particleJS is not defined
particle_js__webpack_imported_module_0___default.a.load is not a
function
After reading a lot of questions on this topic but nothing is really clear. here are some leads but I did not succeed:
https://stackoverflow.com/a/42457020/11027833
https://github.com/vigetlabs/blendid/issues/287
https://github.com/VincentGarreau/particles.js/issues/114
I understood that particleJS is linked to the window object. And indeed, when I try in the console particleJS, it works.
So could you tell me simply how to use particleJS with webpack? Or how to use a window function into webpack?
Thank you in advance for your efforts!

Welcome to the Rails+webpacker mayhem. In theory you would do something like:
let particlejs = require("particlejs");
That goes in your pack file. Then you have particlejs available in your window object.
You can also do:
// config/webpack/custom.js
module.exports = {
resolve: {
alias: {
jquery: 'jquery/src/jquery',
particle_js: 'particlejs'
}
}
}
Also try this:
import 'particles.js/particles';
const particlesJS = window.particlesJS;
particlesJS.load('particles-js', 'particles.json', null);

I ran into this exact same issue, here is what I did to get it working.
If you're using yarn to install/add packages then run the following command from the root of your application to add the particles.js to the node_modules folder:
yarn add particles.js
Now open up app/javascript/packs/application.js and add the following:
require("particles.js")
Now restart your rails server and it should work.

Related

Rails 7 failing to import yarn package (https://github.com/keisto/vanilla-rangeslider)

This is a non-jQuery version of IonRangeSlider (https://github.com/IonDen/ion.rangeSlider):
https://github.com/keisto/vanilla-rangeslider
I have used this before by trying to stick to pure JS and avoid adding another layer with JQ.
I installed this via yarn and it's in my node_modules folder.
I added this to my app/javascript/application.js file:
import IonRangeSlider from 'vanilla-rangeslider/js/rangeslider'
after also trying just:
import IonRangeSlider from 'vanilla-rangeslider'
In my compiled JS file in dev all it has is this:
// ../../node_modules/vanilla-rangeslider/js/rangeslider.js
var require_rangeslider = __commonJS({
"../../node_modules/vanilla-rangeslider/js/rangeslider.js"() {
}
});
and if I try and initialize a slider all I get is:
Uncaught ReferenceError: ionRangeSlider is not defined
Any ideas here as to what I am missing? I have added some other yarn based JS package with no issues.
The range slider has no exported functions, meaning you won't be able to import anything from it.
The only way to use its functions would be to add it in a script tag unfortunately.

How to require a js library with dependencies on webpack?

I'm working on a Symfony 3 project and trying to build a skeleton fỏ frontend development. I decided to use webpack encore.
This is my webpack entry file:
// assets/js/app.js
// loads the jquery package from node_modules
var $ = require('jquery');
require('node-waves');
require('popper.js');
require('bootstrap');
require('mdbootstrap');
require('slick-carousel');
require('jquery-validation');
require('jquery-validation-unobtrusive');
require('multi-step-form-js');
$(document).ready(function() {});
The things seem okay if I don't use the "multi-step-form-js". If I require it into the entry file. I will get an error like this in console of Google Chrome "Uncaught TypeError: Cannot read property 'prototype' of undefined". It locates me to this snippet of code inside the libary:
$.validator.prototype.subset = function(container) {
var ok = true;
var self = this;
$(container).find(':input').each(function() {
if (!self.element($(this))) ok = false;
});
return ok;
};
I think the problem is missing of dependence (the "jquery-validation"). I tried to require it with this line of code "require('jquery-validation');". The problem isn't be solved. I guess that webpack use requirejs by by default so I have to find a special way to require it. Unluckily, I'm still finding.
Are there any ideas about how to solve it?
Thanks in advance!
For missing dependencies, you can try installing it manually into your devDependencies with the following.
npm install -D jquery-validation or yarn add -D jquery-validation
Please ensure that the package name is correct. I am just using what you have spelt.

How to include 3rd party library that uses older import approach to Angular4.x?

What is the proper workflow to include the library to angular 4.0 and use it inside a component?
My steps:
yarn add mathjs
Then there should be a way to injects js libraries in one of the build lifecycles so the angular4 component can use it. JHipster utilizes Webpack and Yarn.
Then I tried to add to Component (docs):
import { mathjs } from "./mathjs";
and
var math = require('mathjs');
Those were not working. What am I missing?
UPDATE:
It seems like mathjs uses older approach suggesting var math = require('mathjs'). Maybe it is similar to JQuery question in some way...
UPDATE2
This is a great question and I'm glad you ask because I wish I had what I'm about to write the first time I encountered this little problem. This is a typescript/javascript and webpack issue before it is an angular issue. I definitely am planning a writeup on my blog soon as possible.
Your Scenario:
You run
npm install mathjs
Now you try to use math.js from a component:
Find math.js dist js file (node_modules/mathjs/dist/math.js) and reference like this
import {mathjs} from "../../node_modules/mathjs/dist/math";
But you get error message saying "set --allowJS". You do that like this:
Set --allowJS in config (tsconfig.json)
{ "compilerOptions": {
"allowJs": true, ...
Now you get:
ERROR in ../node_modules/mathjs/dist/math.js (12209,13): Unreachable
code detected.
Looking in the math.js source, you see that it is an old school module but there is no root wrapper function (one function to bring them all and in the darkness bind them..) (more on that later).
Solution: install a typings file for the target lib (#types/mathjs)
First, check to see if you can get #typings files for your module here
https://microsoft.github.io/TypeSearch/
Grab mathjs typings file from npm (https://www.npmjs.com/package/#types/mathjs) and Run npm install to add the typings .d.ts files to the target lib's node_modules directory
npm install --save #types/mathjs
Add your type ref correctly
import * as mjs from "mathjs"
Use it like this:
console.log("e was: " + mjs.e);
I have the complete solution for the math.js lib on my github here
https://github.com/res63661/importOldJSDemoWithTypings/
More:
For examples look no further than your own angular project. CLI creates node_modules folder each time you run npm install after creating a new project with ng new . Dig down into here and note the d.ts files for many of the .js files.
When messing with typings or defining your own (.d.ts files) be sure to restart your server between builds as the typings don't seem to update currently on the fly
Further reading:
http://www.typescriptlang.org/docs/handbook/declaration-files/consumption.html
https://angular.io/guide/typescript-configuration#typescript-typings
https://microsoft.github.io/TypeSearch/
Lastly:
If you are in a pinch and this is not working for you, I did have success creating a custom wrapper for a different (much smaller) module by wrapping it in a master export type
export var moduleNamer = (function(){
//module implementation
}());
then dumping the .js file local to my component and then referencing it as follows:
//reference like this from your component:
import {moduleNamer} from "./source"; //from source.js
--rich
I did this way and it worked for angular9.
First install npm package mathjs.
npm install mathjs
Then import in your component or directive.
import { round } from 'mathjs'
You may test with this.
console.log(round(math.pi, 3) )
Try to include the script into index.html:
<script src="./assets/math.js" type="text/javascript"></script>
Then add this into your component file:
declare const math;
You can then use math in your component:
ngOnInit(): void {
console.log(math.sqrt(-4););
}

How to import JavaScript file into angular2

I am having trouble figuring out how to import a javascript file into my angular2 project. It is a file that is not a module that is apart of npm and the only instructions I have been able to find is using npm which is not an option here.
I am using angular cli and in my angular-cli.json file I have:
{
"apps": [
"styles": [..],
"scripts": ["../pathtomyjs/file.js"]
]}
I ran ng build and ng serve and when I open up my app and look at the web console and try referencing the function that is in my js file, I am able to do so successfully.
Example in the console I type in:
var test = MyObject;
and I get test = {};
However, when I try do
let test = MyObject;
in my component .ts file I get :
home.component.ts (10,11): Cannot find name 'MyObject'.)
Not sure how to do this in Angular2.
Thanks!
Do:
declare var MyObject: any;
let test = MyObject;
Or:
let test = (<any> MyObject);
For jQuery:
declare var jQuery: any;
jQuery.ajax({ ... });
Is it a 3rd party library? you'll have to let the typescript compiler know where the type definition files are. Normally, it looks under node_modules/#types folder. For example, if you wanted to use jQuery, you would install the necessary type definition files by running:
npm install #types/jquery
I did a deep dive on this here:
This is a great question and I'm glad you ask because I wish I had what I'm about to write the first time I encountered this little problem. This is a typescript/javascript and webpack issue before it is an angular issue. I definitely am planning a writeup on my blog soon as possible.
Your Scenario:
You run
npm install mathjs
Now you try to use math.js from a component:
Find math.js dist js file (node_modules/mathjs/dist/math.js) and reference like this
import {mathjs} from "../../node_modules/mathjs/dist/math";
But you get error message saying "set --allowJS". You do that like this:
Set --allowJS in config (tsconfig.json)
{ "compilerOptions": {
"allowJs": true, ...
Now you get:
ERROR in ../node_modules/mathjs/dist/math.js (12209,13): Unreachable
code detected.
Looking in the math.js source, you see that it is an old school module but there is no root wrapper function (one function to bring them all and in the darkness bind them..) (more on that later).
Solution: install a typings file for the target lib (#types/mathjs)
read more...
I put my js files into app/assets/scripts and load them in index.html
<script src="assets/scripts/foobar.js"></script> . This is for a ionic2 / angular2 project.
In the module you have to define your functions like this in global scope of the module file
declare var myFancyFunction;

Local require() paths for React-Native

I am looking for a convenient way to access files in the root of my application while avoiding require() strings that look like:
require('../../../../myModule')
There are some good solutions out there for Node (https://gist.github.com/branneman/8048520) but I haven't seen a way to use global variables in React Native.
Does anyone have a clean solution to this problem?
From Marc Shilling's answer on https://github.com/facebook/react-native/issues/3099
You can use an absolute path on imports/requires:
import {ProximaNovaText} from 'MyApp/src/components';
require('MyApp/src/utils/moment-twitter');
where 'MyApp' is whatever name you registered in your index.ios.js file
Note for VS Code: This works, but be warned that you might lose intellisense and cmd/ctrl + click. Thanks Johan for the info about CS code
You can mark a directory as a package by adding a package.json within the root directory you want to resolve.
e.g:
- app
- package.json // ← Add this package.json file
- config
- components
- ... (etc)
package.json should look like this:
{ "name": "app" }
Restart your packager
react-native start --reset-cache
Now you can use the following in all of you project files:
import store from 'app/config/store';
import Button from 'app/components/Button';
You can use this same method across other directories in your project, I don't think this works via require, although image paths seemed work.
As noted in the comments, you may lose auto-complete in your editor (VSCode).
For Jetbrains IDE's there are some ongoing tickets here:
https://youtrack.jetbrains.com/issue/WEB-17254
https://youtrack.jetbrains.com/issue/WEB-20104#comment=27-1486526
https://intellij-support.jetbrains.com/hc/en-us/community/posts/205434510-Configure-custom-modules-resolve-folder
This might help with Jetbrains IDE's in the meantime.
// A slash may allow auto-complete to work in your IDE (but will fail to resolve)
import Button from '/app/components/Button'; // Cannot be resolved
Put code below on top of your myModule file:
/**
* #providesModule myModule
*/
Then you can use require('myModule') in any other files.
Complementing #Tiagojdferreira
You can use his solution with babel-plugin-module-resolver library.
Install with:
npm install --save-dev babel-plugin-module-resolver
Configure .babelrc adding plugins property like this:
{
"presets": ["react-native"],
"plugins": [
["module-resolver", {
"alias": {
"#src": "MyApp/src",
"#otherAlias": "MyApp/src/other/path",
}
}]
]
}
Usage:
require('#src/utils/moment-twitter');
Hope this helps!
You can use global variables in react native, same as node, properties defined on global are accessible globally.
e.g.
global.foo = "blah";
console.log(foo); //logs "blah"
Most of the node solutions in the gist above should work correctly.
One I've used in the past is defining a global function at the top directory level, usually on the first line like
global.rootRequire = function(path) { return require(path); }
Which simply allows deeply nested requires to be from the root, and avoids all of the ../../ business.
However the other comment is true, if this is really an issue, there is probably something structurally deficient with the project.

Categories

Resources