Loading an asset within the app.js Symfony 4 file - javascript

I'm looking to mainstream a certain asset loading within app.js
My assets get built like such: public/build/images/icons/**.svg
Within my app.js file, I have the following:
/*
* Welcome to your app's main JavaScript file!
*
* We recommend including the built version of this JavaScript file
* (and its CSS file) in your base layout (base.html.twig).
*/
// any CSS you require will output into a single css file (app.css in this case)
import '../sass/standards.scss';
// Need jQuery? Install it with "yarn add jquery", then uncomment to require it.
const $ = require('jquery');
$(window).on("load", function() {
$(".icon").each(function(){
var $classes = $(this).prop("classList");
var className;
$.each($classes, function(){
if(this.match("^icon-"))
{
className = this;
return;
}
});
className = String(className);
var fileName = className.replace("icon-", "") + ".svg";
$(this).load("public/build/images/icons/" + fileName);
})
});
The idea is to find any .icon element and inject it with the appropriate SVG file that I have in the assets folder. But the problem is, there is also some caching happening so the file names change for version controlling. Is this the correct way to call an asset through the app.js file?
What's the proper way?

You need to require the file before using it. Docs.
// assets/js/app.js
// returns the final, public path to this file
// path is relative to this file - e.g. assets/images/logo.png
const logoPath = require('../images/logo.png');
var html = `<img src="${logoPath}">`;

Related

Vue DOM image won't show correctly

I'm using the Vue framework and creating an image using the DomUtil.Create function. In this image I want to dynamically write the source to this image. But the image won't show to the user.
I put a normal image on the page using the <img> tag and it works here. Only when creating the DOM element it doesn't work. I put the path hard coded in here so it is certain that the path is correct.
var img = L.DomUtil.create("img", "popUpImg", divImg);
img.src = '#/assets/pictures/1.png';
Use require()
When binding to a project path / filename, use require:
require('#/assets/pictures/1.png');
If you use project asset paths and filenames in Vue CLI, Webpack actually renames them while bundling. Vue CLI quietly takes care of this if you use a string path for img src in the template. But in any other situation, you need to manually use Webpack's require to give the correct path and filename at runtime.
- Note: You can npm run build and then check the dist > img folder to see the renaming for yourself. -
Can I use a variable with require()?
When using a variable path/filename, require needs some assistance. You must hard code at least the first portion of the path as a string.
For example, this works:
const filename = '1.png';
require('#/assets/pictures/' + filename); // <-- The string is needed
This works too:
const path = 'assets/pictures/1.png';
require('#/' + path); // <-- This is good enough too
But this would not work:
const fullpath = '#/assets/pictures/1.png';
require(fullpath); // <-- No. Can't infer the path from a variable only
Read more in the Vue Loader docs

Browserify: Uncaught error when requiring js file by path created from string concatenation

I am using browesify for client side app. I have files maps.js and directions.js sitting besides my index.js file, and inside my index.js, I have a function getPageName() which returns the name of the file that I should "require". When I try to do
var pageName = getPageName();
var page;
if (pageName === 'maps') {
page = require('./maps');
} else if (pageName === 'directions') {
page = require('./directions');
}
it works fine. But when I instead try to use following trick to minimize my code,
var pageName = getPageName();
var page = require('./' + pageName);
I get error Uncaught Error: Cannot find module './maps' in console log in Chrome. Why does it not work when I use string concatenation but works when I use pass the path explicitly?
That is a limitation of Browserify and similar type libraries. In order to do the require() the library has to examine the js code as a string, and determine file paths before the code is run. This means file paths have to be static in order for it to be picked up.
https://github.com/substack/node-browserify/issues/377
Browserify can only analyze static requires. It is not in the scope of
browserify to handle dynamic requires

Is it possible to require modules from outside of your project directory without relative paths?

I'm trying to build a local library of JS modules to use in Node projects.
If a new project lives in /Users/me/projects/path/to/new/project/ and my library files are located in /Users/me/projects/library/*.js is there a way to access those files without using a relative path?
In /Users/me/projects/path/to/new/project/app.js you can require foo.js like so:
var foo = require('../../../../../library/foo') and that will work but that's clunky and if files move you'd have to update your relative paths.
I've tried requireFrom and app-module-path with no luck as they are relative to a project root.
Any ideas for how to require files from outside of your project dir?
Thanks in advance!
var librarypath = '/Users/me/projects/library/';
// or if you prefer...
// var librarypath = '../../../../../library/';
var foo = require(librarypath + 'foo.js');
... or dressed up a bit more ...
function requirelib(lib){ return require('/Users/me/projects/library/'+lib+'.js'); }
var foo = requirelib('foo');
var bar = requirelib('bar');
I had the same problem many times. This can be solved by using the basetag npm package. It doesn't have to be required itself, only installed as it creates a symlink inside node_modules to your base path.
const localFile = require('$/local/file')
// instead of
const localFile = require('../../local/file')
Using the $/... prefix will always reference files relative to your apps root directory.
Disclaimer: I created basetag to solve this problem

Setting a path for require in node.js

I have a folder structure like this.
include/
index.js
plugin/
plugin.js
helper.js
Where:-
include/index.js
//Function for mapping the path of "require" statement in the plugin.js file.
var mapRequirePath = function(){
var plugins = require('./plugin/plugin');
return plugins;
}
//Now call the plugins..
var plugin = mapRequirePath();
include/plugin/plugin.js
/*
I want all four require statements to point to the same file location '/include/plugin/helper.js'
i.e search in the same folder location for module irrespective of the '../' or '../../' present in the require statement
*/
var helper1 = require('./helper');
var helper2 = require('helper');
var helper3 = require('../../helper');
var helper4 = require('../helper');
I want to map the path of require in plugin.js file so that all require call should search for its module in the same directory only.
You might be able to dynamically change the NODE_PATH environment variable:
// First take a backup:
var _NODE_PATH = process.env.NODE_PATH;
// Add /includes/plugin to the path, also note that we need to support
// `require('../hello.js')`. We can do that by adding /includes/plugin/a,
// /includes/plugin/a/b, etc.. to the list
process.env.NODE_PATH+=':/includes/plugin:/includes/plugin/a';
// Do your think...
require('./plugins/plugin');
// Restore NODE_PATH
process.env.NODE_PATH = _NODE_PATH;
Try changing the NODE_PATH variable via the command line:
exports NODE_PATH=directoryYouWant
If you don't want to have to change it for every other project, you could try just dynamically changing it in you .js file:
var currentNodePath = process.env.NODE_PATH;
process.env.NODE_PATH = directoryYouWant;
//do stuff then change it back
process.env.NODE_PATH = currentNodePath;
If your wanna add /foo/bar to require:
by editting process.env.NODE_PATH
then your js files should reside inside /foo/bar/node_modules/
process.env.NODE_PATH = '/foo/bar' + ':' + process.env.NODE_PATH;
by editting module.paths
then your js files should reside inside /foo/bar/
module.paths.push('/foo/bar');

How do I ignore a file using gulp?

I have the following folder and file structure:
Vendor
bootstrap
css
-bootstrap.css
js
-bootstrap.js
font-awesome
css
-font-awesome.css
nivo-slider
-nivo-slider.css
theme
-theme.css
-theme-animate.css
-theme-blog.css
-theme-responsive.css
-theme-shop.css
I am trying to make sure that the css files are added to the stream in this specific order:
1) The bootstrap.css file
src/vendor/bootstrap/css/bootstrap.css
2) All of the other css files inside the 'src/vendor/' sub-directories in no particular order (I will be adding more in the future so I don't want to make this too specific)
src/vendor/font-awesome/css/font-awesome.css
src/vendor/nivo-slider/nivo-slider.css
3) These specific css files inside the 'src/vendor/theme/' directory in no particular order
src/vendor/theme/theme.css
src/vendor/theme/theme-animate.css
src/vendor/theme/theme-blog.css
src/vendor/theme/theme-shop.css
4) And finally the theme-responsive.css file
src/vendor/theme/theme-responsive.css
Here is my attempt:
var gulp = require('gulp');
var streamqueue = require('streamqueue');
gulp.task('styles', function() {
var stream = streamqueue({ objectMode: true });
// file that needs to be at the beginning of the concatenated css file
stream.queue(
gulp.src('src/vendor/**/bootstrap.css')
);
//Now I want to add most of the remaining files, except for the bootstrap.css file that was already added as well as any files with the word theme at the beginning of it
stream.queue(
gulp.src('src/vendor/**/*.css', '!src/vendor/**/bootstrap.css', '!src/vendor/**/theme*.css')
);
//Now I would like to add the files that begin with the word theme at the beginning, except for theme-responsive.css
stream.queue(
gulp.src('src/vendor/theme/**/*.css', '!src/vendor/theme/theme-responsive.css')
);
//Now I would like to add the theme-responsive.css file
stream.queue(
gulp.src('src/vendor/theme/theme-responsive.css')
);
return stream.done()
.pipe(concat("app.css"))
.pipe(gulp.dest('public/css/'))
});
Unfortunately, when I currently run this script, the bootstrap.css and other files that it should be ignoring are being added multiple times. How do I ignore a file using gulp?
You are almost there, the exclamation character is for it '!', just need to pass it as array:
eg:
stream.queue(
gulp.src([
'src/vendor/theme/**/*.css',
'!src/vendor/theme/theme-responsive.css'
]);
);
For more information: http://jb.demonte.fr/blog/production-package-with-gulp-js/
Hope this helps.
Try using gulp-concat. Files will be concatenated in the order that they are specified in the gulp.src function. https://www.npmjs.org/package/gulp-concat
var concat = require('gulp-concat');
gulp.task('scripts', function() {
gulp.src(['src/vendor/bootstrap/**/*.css',
'src/vendor/font-awesome/**/*.css',
'src/vendor/nivo-slider/**/*.css',
'src/vendor/theme/theme.css',
'src/vendor/theme/theme-animate.css',
'src/vendor/theme/theme-blog.css',
'src/vendor/theme/theme-shop.css',
'src/vendor/theme/theme-responsive.css'])
.pipe(concat('app.css'))
.pipe(gulp.dest('public/css/'))
;
});

Categories

Resources