My project is being built with Webpack via Laravel Mix. I want to dynamically import an ES6 module that itself imports other modules and a stylesheet. Here is the dynamically imported module (loadJQueryTextillate.js):
import style from 'animate.css/animate.css';
import 'letteringjs';
import 'textillate';
style.use();
export default () => {
};
Here is the module that dynamically imports loadJQueryTextillate.js (animatedText.js):
import isInViewport from './isInViewport';
function maybeAnimateText( elem ) {
const $el = $( elem );
let bounding,
el_html,
el_lines,
in_viewport = $el.data( 'in-viewport' ) || false;
const viewport_height = window.innerHeight || document.documentElement.clientHeight;
if ( $el.hasClass( 'opaque' ) ) {
bounding = elem.getBoundingClientRect();
if ( in_viewport && !isInViewport( elem ) && ( bounding.top > viewport_height ) ) { // Element scrolled off screen
in_viewport = false;
$el.removeClass( 'opaque' ).find( 'ul.texts' ).remove().end().text( $.trim( $el.text() ) );
} else if ( isInViewport( elem ) ) {
in_viewport = true;
}
$el.data( 'in-viewport', in_viewport );
return;
} else if ( !isInViewport( elem ) ) {
return;
}
el_html = $el.html();
el_lines = el_html.split( /<br\s*\/?>/ );
$.each( el_lines, function( key, line ) {
el_lines[ key ] = $.trim( line );
} );
el_html = '<span class="line">' + el_lines.join( '</span><span class="line">' ) + '</span>';
import( /* webpackChunkName: "scripts/jQuery.textillate" */ './loadJQueryTextillate' ).then( () => {
$el.html( el_html ).addClass( 'opaque' ).children( '.line' ).textillate( {
in : {
effect : $el.data( 'in-effect' ) || 'fadeInLeft',
delay : $el.data( 'delay' ) || 12,
},
} );
} );
}
export default () => {
const $els = $( '.tlt' );
if ( 0 === $els.length ) {
return false;
}
$els.each( function( index, elem ) {
maybeAnimateText( elem );
} );
return true;
};
Here is the JS entry script (app.js):
window.$ = window.jQuery = require( 'jquery' );
import 'bootstrap';
import checkAnimatedText from './modules/animatedText';
$( window ).on( 'load', () => {
checkAnimatedText();
} );
Finally, here is the Laravel Mix config script (webpack.mix.js):
const mix = require( 'laravel-mix' );
require( 'laravel-mix-versionhash' );
// Public path helper
const publicPath = path => `${mix.config.publicPath}/${path}`;
// Source path helper
const src = path => `resources/assets/${path}`;
// Public Path
mix
.setPublicPath( './dist' )
.setResourceRoot( `/wp-content/themes/magnetar/${mix.config.publicPath}/` )
.webpackConfig( {
module : {
rules : [ {
test : /animate\.css$/,
use : [ {
loader : "style-loader/useable",
}, { loader : "css-loader" } ],
} ],
},
output : { publicPath : mix.config.resourceRoot },
} );
// Browsersync
mix.browserSync( 'magnetar.localhost' );
// Styles
mix.sass( src`styles/app.scss`, 'styles' );
// Assets
mix.copyDirectory( src`images`, publicPath`images` )
.copyDirectory( src`fonts`, publicPath`fonts` );
// JavaScript
mix.js( src`scripts/app.js`, 'scripts' );
//.extract();
// Autoload
/*mix.autoload( {
jquery : [ '$', 'window.jQuery' ],
} );*/
// Source maps when not in production.
mix.sourceMaps( false, 'source-map' );
// Hash and version files in production.
mix.versionHash( { length : 16 } );
Compiler output:
ERROR in ./node_modules/animate.css/animate.css (./node_modules/css-loader??ref--6-1!./node_modules/postcss-loader/src??ref--6-2!./node_modules/style-loader/useable.js!./node_modules/css-loader!./node_modules/animate.css/animate.css)
Module build failed (from ./node_modules/postcss-loader/src/index.js):
SyntaxError
(1:1) Unknown word
> 1 | var refs = 0;
| ^
2 | var dispose;
3 | var content = require("!!../css-loader/index.js!./animate.css");
EDIT: Updated contents of loadJQueryTextillate.js, webpack.mix.js and compiler output.
You can try style-loader/useable to dynamically load css file. In your script code, you should use style.use() to make style useable or use style.unuse() to make style disable.
The following code shows how you should do to use style-loader/useable.
webpack.config.js
{
module: {
rules: [
{
test: /\.css$/,
exclude: /\.useable\.css$/,
use: [
{ loader: "style-loader" },
{ loader: "css-loader" },
],
},
{
test: /\.useable\.css$/,
use: [
{
loader: "style-loader/useable"
},
{ loader: "css-loader" },
],
},
],
},
}
file you want to dynamically load animate.css
import style form './animate.css';
// make aniamte.css useable
style.use();
// make animate.css disable
style.unuse();
Related
I have a custom plugin in ckeditor5.
When user click on toolbar icon my plugin convert selected test to custom element with a custom attribute name comment-id.
this work properly.
Now I want to watch on click element and get comment-id on click and I don't know how can I do that.
this is the code of my custom plugin
import uploadIcon from './message.svg'
import ButtonView from '#ckeditor/ckeditor5-ui/src/button/buttonview'
import Plugin from '#ckeditor/ckeditor5-core/src/plugin'
import Command from '#ckeditor/ckeditor5-core/src/command'
import './comment.css'
export default class CustomFileExporerPlugin extends Plugin {
init() {
const editor = this.editor
const config = editor.config.get('comment')
console.log(editor.editing.view.document.isFocused)
editor.editing.view.document.on('click', a => {
console.log(a)
})
editor.model.schema.extend('$text', { allowAttributes: 'comment' })
editor.conversion.attributeToElement({
model: 'comment',
view: (commentId, writer) => {
debugger
if (writer) {
return writer.writer.createAttributeElement(
'comment',
{
'comment-id': commentId,
class: `ck-comment-marker`
},
{ priority: 5 }
)
}
}
})
editor.commands.add('comment', new CommentCommand(editor))
editor.ui.componentFactory.add('comment', locale => {
const view = new ButtonView(locale)
view.set({
label: 'add comment',
icon: uploadIcon,
tooltip: true
})
view.on('execute', async () => {
editor.editing.view.focus()
let id = await config.callback()
editor.execute('comment', { value: 'comment', id })
})
return view
})
}
}
class CommentCommand extends Command {
refresh() {
const model = this.editor.model
const doc = model.document
this.value = doc.selection.getAttribute('comment')
this.isEnabled = model.schema.checkAttributeInSelection(
doc.selection,
'comment'
)
}
execute(options = {}) {
const model = this.editor.model
const document = model.document
const selection = document.selection
const highlighter = options.value
model.change(writer => {
const ranges = model.schema.getValidRanges(
selection.getRanges(),
'comment'
)
if (selection.isCollapsed) {
const position = selection.getFirstPosition()
if (selection.hasAttribute('comment')) {
const isSameHighlight = value => {
return (
value.item.hasAttribute('comment') &&
value.item.getAttribute('comment') === this.value
)
}
const highlightStart = position.getLastMatchingPosition(
isSameHighlight,
{ direction: 'backward' }
)
const highlightEnd = position.getLastMatchingPosition(isSameHighlight)
const highlightRange = writer.createRange(
highlightStart,
highlightEnd
)
writer.removeAttribute('comment', highlightRange)
writer.removeSelectionAttribute('comment')
} else if (highlighter) {
writer.setSelectionAttribute('comment', highlighter)
}
} else {
for (const range of ranges) {
writer.setAttribute('comment', options, range)
}
}
})
}
}
When rendering editor, you can catch custom plugin click event using below code.
const command = editor.commands.get('comment')
command.on('execute', () => { catch click event in custom plugin})
I'm adding IE v11 support for web application. bitcoinjs-lib package contains arrow function causing IE v11 to break.
I have added babel-polyfill, react-app-polyfill/ie11, url-search-params-polyfill and react-app-polyfill/stable which makes up for most IE v11 support expect bitcoinjs-lib package.
Image in IE v11 browser
.bashrc
{
"plugins": [
["#babel/plugin-transform-arrow-functions"],
[
"module-resolver", {
"root": ["./"],
"alias": {
"~": "./"
}
}]
],
"presets": [
[
"next/babel",
{
"preset-env": {
"useBuiltIns": "usage"
}
}
]
]
}
source code inside package
'use strict';
Object.defineProperty(exports, '__esModule', { value: true });
const parser_1 = require('../parser');
function combine(psbts) {
const self = psbts[0];
const selfKeyVals = parser_1.psbtToKeyVals(self);
const others = psbts.slice(1);
if (others.length === 0) throw new Error('Combine: Nothing to combine');
const selfTx = getTx(self);
if (selfTx === undefined) {
throw new Error('Combine: Self missing transaction');
}
const selfGlobalSet = getKeySet(selfKeyVals.globalKeyVals);
const selfInputSets = selfKeyVals.inputKeyVals.map(input => getKeySet(input));
const selfOutputSets = selfKeyVals.outputKeyVals.map(output =>
getKeySet(output),
);
for (const other of others) {
const otherTx = getTx(other);
if (
otherTx === undefined ||
!otherTx.toBuffer().equals(selfTx.toBuffer())
) {
throw new Error(
'Combine: One of the Psbts does not have the same transaction.',
);
}
const otherKeyVals = parser_1.psbtToKeyVals(other);
const otherGlobalSet = getKeySet(otherKeyVals.globalKeyVals);
otherGlobalSet.forEach(
keyPusher(
selfGlobalSet,
selfKeyVals.globalKeyVals,
otherKeyVals.globalKeyVals,
),
);
const otherInputSets = otherKeyVals.inputKeyVals.map(input =>
getKeySet(input),
);
otherInputSets.forEach((inputSet, idx) =>
inputSet.forEach(
keyPusher(
selfInputSets[idx],
selfKeyVals.inputKeyVals[idx],
otherKeyVals.inputKeyVals[idx],
),
),
);
const otherOutputSets = otherKeyVals.outputKeyVals.map(output =>
getKeySet(output),
);
otherOutputSets.forEach((outputSet, idx) =>
outputSet.forEach(
keyPusher(
selfOutputSets[idx],
selfKeyVals.outputKeyVals[idx],
otherKeyVals.outputKeyVals[idx],
),
),
);
}
return parser_1.psbtFromKeyVals(selfTx, {
globalMapKeyVals: selfKeyVals.globalKeyVals,
inputKeyVals: selfKeyVals.inputKeyVals,
outputKeyVals: selfKeyVals.outputKeyVals,
});
}
exports.combine = combine;
function keyPusher(selfSet, selfKeyVals, otherKeyVals) {
return key => {
if (selfSet.has(key)) return;
const newKv = otherKeyVals.filter(kv => kv.key.toString('hex') === key)[0];
selfKeyVals.push(newKv);
selfSet.add(key);
};
}
function getTx(psbt) {
return psbt.globalMap.unsignedTx;
}
function getKeySet(keyVals) {
const set = new Set();
keyVals.forEach(keyVal => {
const hex = keyVal.key.toString('hex');
if (set.has(hex))
throw new Error('Combine: KeyValue Map keys should be unique');
set.add(hex);
});
return set;
}
.next.config.js
const fs = require('fs')
const dotenv = require('dotenv')
const webpack = require('webpack')
const withCSS = require('#zeit/next-css')
const withFonts = require('next-fonts')
const withImages = require('next-images')
const withPlugins = require("next-compose-plugins")
const withTM = require('next-transpile-modules');
const getEnvFile = () => {
const fileName = process.env.NODE_ENV == 'development' ? '.env' : `.env.${process.env.NODE_ENV}`
return fs.readFileSync(fileName)
}
const envConfig = dotenv.parse(getEnvFile())
const nextConfig = {
webpack(config) {
config.plugins.push(new webpack.EnvironmentPlugin(envConfig))
const originalEntry = config.entry;
config.entry = async () => {
const entries = await originalEntry();
if (entries['main.js'] && !entries['main.js'].includes('./polyfills.js')) {
entries['main.js'].unshift('./polyfills.js');
}
return entries;
};
config.module.rules.push({
test: /\.js$/,
include: [/node_modules\/bitcoinjs-lib/],
use: {
loader: "next/babel",
options: {
presets: ["#babel/presets-env", {modules: false}],
plugins: ["#babel/plugin-transform-arrow-functions"],
},
},
})
return config
},
exportPathMap: async function(defaultPathMap) {
return {
'/' : { page: '/people' },
'/dashboard' : { page: '/dashboard' },
'/tenant-investigator' : { page: '/tenant_investigator' },
'/pricing-history' : { page: '/pricingHistory' },
'/algorithm' : { page: '/algorithm' },
'/group' : { page: '/group' },
'/group-detail' : { page: '/group_detail' },
'/investigation' : { page: '/investigation' },
'/login' : { page: '/login' },
'/map' : { page: '/map' },
'/people' : { page: '/people' },
'/people-report' : { page: '/people_report' },
'/report' : { page: '/report' },
'/people-detail' : { page: '/people_detail' },
'/pricing-history' : { page: '/pricingHistory' },
'/settings' : { page: '/settings' },
'/tenant' : { page: '/tenant' },
'/wallets' : { page: '/wallets' },
'/transactions' : { page: '/transactions' },
'/taxable-event' : { page: '/taxable_event' },
'/subpoena-upload' : { page: '/subpoenaUpload' },
'/people-subpoena-upload': { page: '/peopleSubpoenaUpload' },
'/subpoena-transactions' : { page: '/subpoenaTransactions' },
'/event-detail' : { page: '/peopleEvent' },
'/grand-unified' : { page: '/grandUnified' },
'/blocks' : { page: '/blocks' },
'/person-edit' : { page: '/personEdit' },
'/addresses' : { page: '/addresses' },
'/exchanges' : { page: '/exchanges' }
}
}
}
console.log(nextConfig)
// module.exports = withPlugins([withCSS, withFonts, withImages], nextConfig)
module.exports = withPlugins(
[
[
withTM,
{
transpileModules: ['bitcoinjs-lib']
}
],
withCSS,
withFonts,
withImages
],
nextConfig
);
As we see use of arrow function causing error
I want node_module package to be converted to native javascript to IE v11 can read easily. When I look in to node_module source, arrow function and ES6 can be seen in package shipment.
I am not finding in the documentation how to access a local variable of method of the class from within a nested require blocks.
declare( "Clust", StrictIntHashMap,
{
constructor : function()
{
},
cust : function( custId )
{
return this.get( custId );
},
add : function( custObject )
{
this.set( custObject.custId, custObject );
},
reloadThecustses : function()
{
that = this;
require( [ 'inst/DataExtractor', 'inst/ClustTree' ], function ( de, theTree )
{
de.getPlainJSON( Commandz.COMMAND_GET_CUSTS,
function ( dataR )
{
that.add( new Customer( dataR.root[c] ) ); // not working
this.cust( 0 ); // not working
theTree.refreshTheData( dataR.root );
} );
} );
}
} );
return Clust;
How to access the method "add" of the class from within the require block ?
How to access the local variable "that" from within the require block ?
You should be able to access variables defined in the parent scope when using require, since it's equivalent to just having a child scope.
I'm not entirely sure what you are trying to access, but I assume it's the Clust instance.
Would this code work for you?
declare( "Clust", StrictIntHashMap, {
constructor : function() {
},
cust : function( custId ) {
return this.get( custId );
},
add : function( custObject ) {
this.set( custObject.custId, custObject );
},
reloadThecustses : function() {
var clustInstance = this;
require( [ 'inst/DataExtractor', 'inst/ClustTree' ],
function ( de, theTree ) {
de.getPlainJSON( Commandz.COMMAND_GET_CUSTS, function ( dataR ) {
clustInstance.add( new Customer( dataR.root[c] ) );
clustInstance.cust( 0 );
theTree.refreshTheData( dataR.root );
});
});
}
});
return Clust;
Perhaps the problem is caused by having the wrong context in the callback function to getPlainJSON. dojo.hitch() will fix this:
reloadThecustses : function()
{
require( [ 'inst/DataExtractor', 'inst/ClustTree', 'dojo/_base/lang' ], function ( de, theTree, lang )
{
de.getPlainJSON( Commandz.COMMAND_GET_CUSTS,
lang.hitch( function ( dataR )
{
this.add( new Customer( dataR.root[c] ) ); // not working
this.cust( 0 ); // not working
theTree.refreshTheData( dataR.root );
}, this )
} );
}
I am trying to add a field with auto complete functionality , I have used javascript for this
<link rel="stylesheet" href="http://code.jquery.com/ui/1.9.0/themes/base/jquery-ui.css " />
<script src="http://code.jquery.com/jquery-1.8.2.js "></script>
<script src="http://code.jquery.com/ui/1.9.0/jquery-ui.js "></script>
<script>
$(function() {
var availableTags = [
"ActionScript",
"AppleScript",
"Asp",
"BASIC",
"C",
"C++",
"Clojure",
"COBOL",
"ColdFusion",
"Erlang",
"Fortran",
"Groovy",
"Haskell",
"Java",
"JavaScript",
"Lisp",
"Perl",
"PHP",
"Python",
"Ruby",
"Scala",
"Scheme"
];
function split( val ) {
//document.write(val.length);
return val.split( /,\s*/ );
}
function extractLast( term ) {
//echo (term.length);
//document.write(term.length);
return split( term ).pop();
}
$( "#Tag_tag_name" )
// don't navigate away from the field on tab when selecting an item
.bind( "keydown", function( event ) {
var a=0;
// if (event.keyCode === $.ui.keyCode.TAB)
// {
// a=a+1;
// }
if ( event.keyCode === $.ui.keyCode.TAB &&
$( this ).data( "autocomplete" ).menu.active ) {
event.preventDefault();
}
// if (event.keyCode === $.ui.keyCode.P)
// {
// alert(a);
// }
})
.autocomplete({
minLength: 0,
source: function( request, response ) {
// delegate back to autocomplete, but extract the last term
response( $.ui.autocomplete.filter(
availableTags, extractLast( request.term ) ) );
},
focus: function() {
// prevent value inserted on focus
return false;
},
select: function( event, ui ) {
var terms = split( this.value );
// remove the current input
terms.pop();
// add the selected item
terms.push( ui.item.value );
// add placeholder to get the comma-and-space at the end
terms.push( "" );
this.value = terms.join( ", " );
return false;
}
});
});
</script>
Now What I want tot do is instead of this static values in AvaialbleTags variable I want values from database ? Plus I want to limit three values to be add by the user.
Can anyone help me with this ?
Here is what i am using multicomplete
$this->widget('ext.widgets.MultiComplete', array(
'model'=>$model,
'attribute'=>$attribute,
'splitter'=>',',
'sourceUrl'=>$this->createUrl($url),
// additional javascript options for the autocomplete plugin
'options'=>array(
'minLength'=>'1',
),
'htmlOptions'=>array(
'size'=>'60'
),
));
Any examples of using AMD with TypeScript and dojo AMD? Keep getting "3" instead of an object (tslab == 3):
require( ["TypeScriptLab"], function ( tslab )
{
new tslab.Tests().run();
} );
The TypeScript looks like this:
export class TypeScriptLab {
test() {
}
}
The generated JS looks like this:
define(["require", "exports"], function(require, exports) {
var TypeScriptLab = (function () {
function TypeScriptLab() { }
TypeScriptLab.prototype.test = function () {
};
return TypeScriptLab;
})();
exports.TypeScriptLab = TypeScriptLab;
})
I defined my packages:
<script>
dojoConfig = {
async: true,
packages: [
{ name: "TSLab", location: "/IPS" }
]
};
</script>
And added a namespace prefix:
require( ["TSLab/typeScriptLab"], function ( tslab )
{
new tslab.Tests().run();
} );
And the module now loads.