How to use addons method in storybook-root

Best JavaScript code snippet using storybook-root

Addons.ts

Source:Addons.ts Github

copy

Full Screen

1import fs from 'fs';2import originalFs from 'original-fs';3import Path from 'path';4import { app, ipcMain } from 'electron';5import { spawn, spawnSync } from 'child_process';6import compareVersions from 'compare-versions';7import winston from 'winston';8import TTVSTMain from '../TTVSTMain';9import { IAddon, AddonFlag } from './AddonsTypes';10import got from 'got';11import BroadcastMain from '../BroadcastMain';12declare var logger: winston.Logger;13declare var TTVST: TTVSTMain;14export default class Addons {15 installedAddons: Array<IAddon> = [];16 availableAddons: Array<IAddon> = [];17 static snippedIndex: number = 0;18 static batchLines: { [addonid: string] : Array<string> } = {};19 constructor() {20 this.checkForAddons(Path.join('.', 'addons'));21 this.checkForAddons(Path.join('.', 'resources'));22 this.loadAddons = this.loadAddons.bind(this);23 this.loadResporitory = this.loadResporitory.bind(this);24 this.loadError = this.loadError.bind(this);25 this.languageError = this.languageError.bind(this);26 this.onUpdate = this.onUpdate.bind(this);27 this.onUninstall = this.onUninstall.bind(this);28 this.onInstall = this.onInstall.bind(this);29 this.onRestart = this.onRestart.bind(this);30 ipcMain.on('Addons.loadInstalled', this.loadAddons);31 ipcMain.on('Addons.loadRepository', this.loadResporitory);32 ipcMain.on('Addons.loadError', this.loadError);33 ipcMain.on('Addons.languageError', this.languageError);34 ipcMain.on('Addons.update', this.onUpdate);35 ipcMain.on('Addons.uninstall', this.onUninstall);36 ipcMain.on('Addons.install', this.onInstall);37 ipcMain.on('Addons.restart', this.onRestart);38 let batchPath = Path.join(app.getPath('temp'), 'addons.bat');39 fs.access(batchPath, fs.constants.W_OK, (err) => {40 if(err) return;41 fs.unlink(batchPath, (err) => {42 if(err) {43 logger.error('[Addons]', err);44 }45 });46 })47 }48 checkForAddons(directory: string): Promise<void> {49 logger.info(`[Addons] Checking ${directory} for addons`);50 return new Promise((resolve) => {51 fs.readdir(directory, async (err: NodeJS.ErrnoException, files: string[]) => {52 if(err === null) {53 for(let i = 0; i < files.length; i++) {54 let p = Path.join(directory, files[i]);55 await new Promise((re) => {56 fs.stat(p, async (e: NodeJS.ErrnoException, stats: fs.Stats) => {57 if(e === null) {58 if(stats.isDirectory()) {59 await this.checkAddon(p);60 }61 }62 re(null);63 });64 });65 }66 } else {67 logger.info(`[Addons] Directory ${directory} could not be read`);68 logger.verbose(err);69 }70 resolve();71 })72 });73 }74 checkAddon(path: string): Promise<void> {75 const self = this;76 return new Promise((resolve) => {77 let packagePath = Path.join(path, 'package.json');78 fs.readFile(packagePath, { encoding: 'utf8' }, (err: NodeJS.ErrnoException, data: string) => {79 if(err === null) {80 try {81 let packageJson = JSON.parse(data);82 if(83 typeof(packageJson.addonid) === 'string' &&84 typeof(packageJson.name) === 'string' &&85 typeof(packageJson.version) === 'string' &&86 typeof(packageJson.description) === 'string' &&87 typeof(packageJson.author) === 'object' &&88 typeof(packageJson.toolversion) === 'string' &&89 (typeof(packageJson.main) === 'string' || typeof(packageJson.renderer) === 'string')90 ) {91 if(compareVersions.compare(packageJson.toolversion, app.getVersion(), '>=') && !this.addonInstalled(packageJson.addonid)) {92 self.installedAddons.push(Object.assign(packageJson, { path, flags: ['compatible'], loaderror: '', updateAvaiable: '' }));93 } else {94 self.installedAddons.push(Object.assign(packageJson, { path, flags: [], loaderror: 'Addon is not compatible with the current version of TTVStreamerTool', updateAvaiable: '' }));95 }96 } else {97 logger.debug(`[Addons] Addon package.json at ${packagePath} missing fields`);98 }99 } catch(e) {100 logger.debug(`[Addons] Addon package.json at ${packagePath} could not be loaded`);101 logger.debug(e);102 }103 } else {104 logger.debug(`[Addons] Could not read ${packagePath}`);105 logger.debug(err);106 }107 resolve();108 });109 });110 }111 addonInstalled(addonid: string): boolean {112 for(let i = 0; i < this.installedAddons.length; i++) {113 if(this.installedAddons[i].addonid === addonid) {114 return true;115 }116 }117 return false;118 }119 async loadAddons() {120 for(let i = 0; i < this.installedAddons.length; i++) {121 let addon = this.installedAddons[i];122 if(!this.hasFlag(addon, 'compatible')) {123 continue;124 }125 if(this.hasFlag(addon, 'loaded')) {126 this.checkForRendererStuff(addon);127 continue;128 }129 if(typeof(addon.path) === 'string') {130 if(typeof(addon.main) === 'string') {131 try {132 let modpath = Path.relative(__dirname, Path.join(process.cwd(), addon.path, addon.main.substring(0, addon.main.lastIndexOf('.')))).replace(new RegExp('\\'+Path.sep, 'g'), '/');133 logger.debug(`[Addons] Loading addon main module for ${addon.name} at ${modpath}`);134 require(modpath);135 this.setFlag(this.installedAddons[i].addonid, 'loaded');136 this.checkForRendererStuff(addon);137 this.checkForBroadcastStuff(addon);138 } catch(e) {139 logger.error(`[Addons] Addon (main) at ${addon.path} could not be loaded`);140 logger.error(e);141 this.removeFlag(this.installedAddons[i].addonid, 'compatible');142 this.installedAddons[i].loaderror = 'Addon loader on main thread failed';143 }144 } else if(typeof(addon.renderer) === 'string') {145 TTVST.mainWindow.ipcSend('Addons.load', addon.path, addon.renderer.substring(0, addon.renderer.lastIndexOf('.')));146 }147 }148 }149 let newAvailable: Array<IAddon> = [];150 for(let i = 0; i < this.availableAddons.length; i++) {151 if(!this.addonInstalled(this.availableAddons[i].addonid)) {152 newAvailable.push(this.availableAddons[i]);153 }154 }155 this.availableAddons = newAvailable;156 this.sendAddonUpdate();157 }158 checkForRendererStuff(addon: IAddon) {159 fs.access(Path.join(process.cwd(), addon.path, 'language.json'), fs.constants.R_OK, (err) => {160 if(!err && TTVST.mainWindow.window !== null && TTVST.mainWindow.window.isVisible()) {161 logger.debug(`[Addons] Remind renderer to load language file for ${addon.name}`);162 TTVST.mainWindow.ipcSend('Addons.language', addon.path);163 }164 if(typeof(addon.renderer) === 'string' && TTVST.mainWindow.window !== null && TTVST.mainWindow.window.isVisible()) {165 logger.debug(`[Addons] Remind renderer load renderer module for ${addon.name}`);166 TTVST.mainWindow.ipcSend('Addons.load', addon.path, addon.renderer.substring(0, addon.renderer.lastIndexOf('.')));167 }168 });169 }170 checkForBroadcastStuff(addon: IAddon) {171 fs.readFile(Path.join(process.cwd(), addon.path, 'broadcast.json'), { encoding: 'utf8' }, (err: NodeJS.ErrnoException, data: string) => {172 if(err) {173 return;174 }175 try {176 logger.debug(`[Addons] Adding broadcast information for ${addon.name}`);177 let broadcastData = JSON.parse(data);178 if(Array.isArray(broadcastData.triggers)) {179 for(let i = 0; i < broadcastData.triggers.length; i++) {180 BroadcastMain.registerTrigger(broadcastData.triggers[i]);181 }182 }183 if(Array.isArray(broadcastData.actions)) {184 for(let i = 0; i < broadcastData.actions.length; i++) {185 BroadcastMain.registerAction(broadcastData.actions[i]);186 }187 }188 } catch(e) {189 logger.error(e);190 }191 });192 }193 loadError(event: Electron.IpcMainEvent, addonpath: string, error: { code: string, message: string, stack: string }) {194 for(let i = 0; i < this.installedAddons.length; i++) {195 if(this.installedAddons[i].path === addonpath) {196 this.removeFlag(this.installedAddons[i].addonid, 'loaded');197 this.installedAddons[i].loaderror = 'Addon loader on renderer thread failed';198 this.setFlag(this.installedAddons[i].addonid, 'compatible');199 logger.error(`[Addons] Addon (renderer) at ${addonpath} could not be loaded`);200 logger.error(error);201 this.sendAddonUpdate();202 break;203 }204 }205 }206 languageError(event: Electron.IpcMainEvent, addonpath: string, error: { code: string, message: string, stack: string }) {207 logger.error(`[Addons] Addon language pack ${addonpath} could not be loaded`);208 logger.error(error);209 }210 async loadResporitory(event: Electron.IpcMainEvent, url: string) {211 for(let i = 0; i < TTVST.startpage.currentStatus.length; i++) {212 if(TTVST.startpage.currentStatus[i].key == 'app.ttvst.update') {213 if(TTVST.startpage.currentStatus[i].status == 'good') {214 return;215 }216 break;217 }218 }219 if(!url.startsWith('https://')) return;220 try {221 logger.info(`[Addons] Load addons at repository ${url}`);222 let response = await got(url, { responseType: 'json', timeout: 10000 });223 if(response.statusCode == 200) {224 let body = response.body;225 if(Array.isArray(body)) {226 for(let i = 0; i < body.length; i++) {227 let pack = body[i];228 if(229 typeof(pack.addonid) === 'string' &&230 typeof(pack.name) === 'string' &&231 typeof(pack.version) === 'string' &&232 typeof(pack.description) === 'string' &&233 typeof(pack.author) === 'object' &&234 typeof(pack.toolversion) === 'string' &&235 typeof(pack.download) === 'string'236 ) {237 let compatible: boolean = compareVersions(pack.toolversion, app.getVersion()) >= 0;238 Object.assign(pack, { flags: compatible ? ['compatible'] : [] });239 this.overwriteAddon(pack);240 } else {241 logger.debug(`[Addons] Addon description missing fields at repository ${url} (${i})`);242 }243 }244 } else {245 logger.error(`[Addons] Repository at ${url} responded with an invalid format`);246 }247 } else {248 logger.error(`[Addons] Repository at ${url} responded with a status code ${response.statusCode}`);249 }250 } catch(e) {251 logger.error(`[Addons] Something went wrong while loading repository at ${url}`);252 logger.error(e);253 }254 255 this.sendAddonUpdate();256 }257 overwriteAddon(addon: IAddon) {258 for(let i = 0; i < this.installedAddons.length; i++) {259 if(this.installedAddons[i].addonid === addon.addonid) {260 if(this.installedAddons[i].version !== addon.version && this.hasFlag(addon, 'compatible')) {261 this.installedAddons[i].updateAvaiable = addon.version;262 this.installedAddons[i].download = addon.download;263 this.setFlag(this.installedAddons[i].addonid, 'updateavailable');264 }265 return;266 }267 }268 for(let i = 0; i < this.availableAddons.length; i++) {269 if(this.availableAddons[i].addonid === addon.addonid) {270 this.availableAddons[i] = addon;271 return;272 }273 }274 this.availableAddons.push(addon);275 }276 sendAddonUpdate() {277 TTVST.mainWindow.ipcSend('Addons.update', this.installedAddons.concat(this.availableAddons));278 }279 static getRetryDeleteSnippet(file: string) {280 Addons.snippedIndex++281 let index = Addons.snippedIndex.toString()282 return ':LOOP' + index + '\r\ndel "' + file + '"\r\nIF EXIST "' + file + '" (\r\ntimeout /T 1 /Nobreak >nul\r\nGOTO LOOP' + index + '\r\n)'283 }284 async onUpdate(event: Electron.IpcMainEvent, addons: Array<IAddon>) {285 for(let i = 0; i < addons.length; i++) {286 let addon = addons[i];287 if(typeof(addon.download) !== 'string' || !addon.download.startsWith('https://')) {288 TTVST.mainWindow.ipcSend('Addons.updateFailed', addon);289 continue;290 }291 try {292 this.setFlag(addon.addonid, 'updating');293 let resp = await got(addon.download, { responseType: 'buffer', timeout: 20000 })294 if(resp.statusCode === 200) {295 let sanitizedAddonName = addon.addonid.replace(/[^a-z0-9\.\-]/ig, '');296 let addonDownload = Path.join(app.getPath('temp'), sanitizedAddonName + '.asar');297 await new Promise((res, rej) => {298 originalFs.writeFile(addonDownload, resp.body, (err) => {299 if(err === null) {300 res(null);301 } else {302 rej(err);303 }304 });305 });306 Addons.batchLines[addon.addonid] = [];307 Addons.batchLines[addon.addonid].push(Addons.getRetryDeleteSnippet(addon.path));308 Addons.batchLines[addon.addonid].push(`move "${addonDownload}" resources\\${sanitizedAddonName}.asar`);309 310 this.setFlag(addon.addonid, 'updateready');311 } else {312 this.setFlag(addon.addonid, 'updatefailed');313 logger.error(`[Addons] Addon download failed. Server responded with status code ${resp.statusCode}`);314 }315 } catch(e) {316 this.setFlag(addon.addonid, 'updatefailed');317 logger.error(`[Addons] Addon update failed`);318 logger.error(e);319 }320 }321 }322 async onUninstall(event: Electron.IpcMainEvent, addons: Array<IAddon>) {323 for(let i = 0; i < addons.length; i++) {324 let addon = addons[i];325 if(typeof(addon.path) !== 'string' || addon.path.length <= 0) continue;326 327 await new Promise((res) => {328 originalFs.stat(addon.path, (err: NodeJS.ErrnoException, stats: fs.Stats) => {329 if(err === null) {330 if(stats.isFile()) {331 Addons.batchLines[addon.addonid] = [Addons.getRetryDeleteSnippet(addon.path)];332 this.setFlag(addon.addonid, 'uninstallready');333 } else {334 this.setFlag(addon.addonid, 'uninstallfailed');335 }336 } else {337 this.setFlag(addon.addonid, 'uninstallfailed');338 logger.error(`[Addons] Addon uninstall failed`);339 logger.error(err);340 }341 res(null);342 });343 })344 }345 }346 isSomethingInstalling() {347 for(let i = 0; i < this.availableAddons.length; i++) {348 if(this.hasFlag(this.availableAddons[i], 'installing')) {349 return true;350 }351 }352 return false;353 }354 async onInstall(event: Electron.IpcMainEvent, addons: Array<IAddon>) {355 let installingRows: string[] = [];356 let addonFileNames: Array<string[]> = [];357 if(this.isSomethingInstalling()) {358 return;359 }360 let tempPath = app.getPath('temp');361 for(let i = 0; i < addons.length; i++) {362 let addon = addons[i];363 if(typeof(addon.download) !== 'string' || !addon.download.startsWith('https://')) {364 this.setFlag(addon.addonid, 'installfailed');365 continue;366 }367 try {368 this.setFlag(addon.addonid, 'installing');369 let resp = await got(addon.download, { responseType: 'buffer', timeout: 20000 })370 if(resp.statusCode === 200) {371 let sanitizedAddonName = addon.addonid.replace(/[^a-z0-9\.\-]/ig, '');372 await new Promise((res, rej) => {373 let addonDownload = Path.join(tempPath, sanitizedAddonName + '.asar');374 originalFs.writeFile(addonDownload, resp.body, (err) => {375 if(err === null) {376 installingRows.push('move "' + addonDownload + '" "resources\\' + sanitizedAddonName + '.asar"');377 addonFileNames.push([addon.addonid, sanitizedAddonName]);378 res(null);379 } else {380 rej(err);381 }382 });383 });384 } else {385 this.setFlag(addon.addonid, 'installfailed');386 logger.error(`[Addons] Addon download failed. Server responded with status code ${resp.statusCode}`);387 }388 } catch(e) {389 this.setFlag(addon.addonid, 'installfailed');390 logger.error(`[Addons] Addon install failed`);391 logger.error(e);392 }393 }394 let batch = '@echo off\r\n' + installingRows.join('\r\n');395 let batchPath = Path.join(tempPath, 'addons.bat');396 try {397 fs.writeFileSync(batchPath, batch);398 399 spawnSync('resources\\elevate -w -c "'+batchPath+'"', { cwd: process.cwd(), env: process.env, shell: true, windowsHide: true });400 for(let i = 0; i < addonFileNames.length; i++) {401 try {402 originalFs.accessSync(`resources\\${addonFileNames[i][1]}.asar`, fs.constants.R_OK);403 await this.checkAddon(`resources\\${addonFileNames[i][1]}.asar`);404 } catch(e) {405 this.setFlag(addonFileNames[i][0], 'installfailed');406 logger.error(`[Addons] Addon install failed`);407 logger.error(e);408 }409 }410 } catch(e) {}411 this.loadAddons();412 }413 onRestart() {414 let execArgv = process.execArgv.map(a => a.replace(/"/g, '""'));415 let batchLines: Array<string> = [];416 for(let addonid of Object.keys(Addons.batchLines)) {417 batchLines = batchLines.concat(Addons.batchLines[addonid]);418 }419 let batchPath = Path.join(app.getPath('temp'), 'addons.bat');420 let batch = '@echo off\r\n' + batchLines.join('\r\n') + '\r\nstart "" "' + process.execPath + '"' + (execArgv.length > 0 ? ' "' + execArgv.join('" "') + '"' : '') + '\r\nexit'421 fs.writeFile(batchPath, batch, (err: NodeJS.ErrnoException) => {422 if(err === null) {423 spawn('resources\\elevate -c "'+batchPath+'"', { cwd: process.cwd(), env: process.env, shell: true, detached: true, windowsHide: false });424 app.quit();425 } else {426 TTVST.mainWindow.ipcSend('Addons.batchFailed');427 logger.error(`[Addons] Addon batch creation failed`);428 logger.error(err);429 }430 });431 }432 setFlag(addonid: string, flag: AddonFlag, skipupdate?: boolean) {433 switch(flag) {434 case 'installing': this.removeFlag(addonid, 'installfailed', true); break;435 case 'installfailed': this.removeFlag(addonid, 'installing', true); break;436 437 case 'updating': this.removeFlag(addonid, ['updateready','updatefailed','uninstallready','uninstallfailed'], true); break;438 case 'updateready': this.removeFlag(addonid, ['updating','updatefailed','uninstallready','uninstallfailed'], true); break;439 case 'updatefailed': this.removeFlag(addonid, ['updateready','updating','uninstallready','uninstallfailed'], true); break;440 441 case 'uninstallready': this.removeFlag(addonid, ['uninstallfailed','updateready','updatefailed'], true); break;442 case 'uninstallfailed': this.removeFlag(addonid, ['uninstallready','updateready','updatefailed'], true); break;443 case 'loaded': this.removeFlag(addonid, ['installing','installfailed','updating','updateready','updatefailed','uninstallready','uninstallfailed'], true); break;444 }445 for(let i = 0; i < this.installedAddons.length; i++) {446 if(this.installedAddons[i].addonid === addonid) {447 if(typeof(this.installedAddons[i].flags) === 'undefined') {448 this.installedAddons[i].flags = [];449 }450 if(!this.hasFlag(this.installedAddons[i], flag)) {451 this.installedAddons[i].flags.push(flag);452 }453 break;454 }455 }456 for(let i = 0; i < this.availableAddons.length; i++) {457 if(this.availableAddons[i].addonid === addonid) {458 if(typeof(this.availableAddons[i].flags) === 'undefined') {459 this.availableAddons[i].flags = [];460 }461 if(!this.hasFlag(this.availableAddons[i], flag)) {462 this.availableAddons[i].flags.push(flag);463 }464 break;465 }466 }467 if(typeof(skipupdate) !== 'boolean' || !skipupdate) {468 this.sendAddonUpdate();469 }470 }471 removeFlag(addonid: string, flags: AddonFlag | Array<AddonFlag>, skipupdate?: boolean) {472 if(!Array.isArray(flags)) {473 flags = [flags];474 }475 for(let i = 0; i < this.installedAddons.length; i++) {476 if(this.installedAddons[i].addonid === addonid) {477 if(typeof(this.installedAddons[i].flags) === 'undefined') {478 break;479 }480 this.installedAddons[i].flags = this.installedAddons[i].flags.filter(f => flags.indexOf(f) < 0);481 break;482 }483 }484 for(let i = 0; i < this.availableAddons.length; i++) {485 if(this.availableAddons[i].addonid === addonid) {486 if(typeof(this.availableAddons[i].flags) === 'undefined') {487 break;488 }489 this.availableAddons[i].flags = this.availableAddons[i].flags.filter(f => flags.indexOf(f) < 0);490 break;491 }492 }493 if(typeof(skipupdate) !== 'boolean' || !skipupdate) {494 this.sendAddonUpdate();495 }496 }497 hasFlag(addon: IAddon, flag: AddonFlag) {498 if(typeof(addon.flags) === 'undefined') return false;499 if(addon.flags.indexOf(flag) >= 0) {500 return true;501 }502 return false;503 }...

Full Screen

Full Screen

elementor.js

Source:elementor.js Github

copy

Full Screen

1import { setButtonAtts } from '../modules/getButtonURL';2import { lazyImages } from '../modules/lazyImages';3import loadItems from '../modules/loadItems';4/**5 * Set up the instance on Elementor6 *7 * @param {object} alm8 * @since 5.3.09 */10export function elementorInit(alm) {11 if (!alm.addons.elementor || !alm.addons.elementor_type || !alm.addons.elementor_type === 'posts') {12 return false;13 }14 let target = alm.addons.elementor_element;15 if (target) {16 // Set button data attributes17 alm.button.dataset.page = alm.addons.elementor_paged;18 // Set button URL19 let nextPage = alm.addons.elementor_next_page_url;20 alm.button.dataset.url = nextPage ? nextPage : '';21 // Set a11y attributes22 target.setAttribute('aria-live', 'polite');23 target.setAttribute('aria-atomic', 'true');24 alm.listing.removeAttribute('aria-live');25 alm.listing.removeAttribute('aria-atomic');26 // Set data atts on 1st grid item27 let item = target.querySelector(`.${alm.addons.elementor_item_class}`); // Get first `.product` item28 if (item) {29 item.classList.add('alm-elementor');30 item.dataset.url = window.location;31 item.dataset.page = alm.addons.elementor_paged;32 item.dataset.pageTitle = document.title;33 }34 if (alm.addons.elementor_paged > 1) {35 // maybe soon36 //almElementorResultsTextInit(alm);37 }38 // Masonry Window Resize. Delay for masonry to be added via Elementor.39 if (alm.addons.elementor_masonry) {40 let resizeTimeout;41 setTimeout(function () {42 window.addEventListener('resize', function () {43 clearTimeout(resizeTimeout);44 resizeTimeout = setTimeout(function () {45 positionMasonryItems(alm, `.${alm.addons.elementor_container_class}`, `.${alm.addons.elementor_item_class}`);46 }, 100);47 });48 }, 250);49 }50 }51}52/**53 * Core ALM Elementor loader.54 *55 * @param {HTMLElement} content56 * @param {object} alm57 * @param {string} pageTitle58 * @since 5.3.059 */60export function elementor(content, alm, pageTitle = document.title) {61 if (!content || !alm) {62 return false;63 }64 return new Promise((resolve) => {65 let container = alm.addons.elementor_element.querySelector(`.${alm.addons.elementor_container_class}`); // Get post container66 let items = content.querySelectorAll(`.${alm.addons.elementor_item_class}`); // Get all items in container67 let url = alm.addons.elementor_current_url; // Current Page URL68 if (container && items && url) {69 // Convert NodeList to Array70 items = Array.prototype.slice.call(items);71 // Trigger almElementorLoaded callback.72 if (typeof almElementorLoaded === 'function') {73 window.almElementorLoaded(items);74 }75 // Load the items76 (async function () {77 await loadItems(container, items, alm, pageTitle, url, 'alm-elementor');78 if (alm.addons.elementor_masonry) {79 setTimeout(function () {80 positionMasonryItems(alm, `.${alm.addons.elementor_container_class}`, `.${alm.addons.elementor_item_class}`);81 }, 125);82 }83 resolve(true);84 })().catch((e) => {85 console.log(e, 'There was an error with Elementor');86 });87 } else {88 resolve(false);89 }90 });91}92/**93 * Handle Elementor loaded functionality and dispatch actions.94 *95 * @param {object} alm96 * @since 5.5.097 */98export function elementorLoaded(alm) {99 let nextPageNum = alm.page + 1;100 let nextPage = alm.addons.elementor_next_page_url; // Get URL.101 // Set button data attributes.102 setButtonAtts(alm.button, nextPageNum, nextPage);103 // Lazy load images if necessary.104 lazyImages(alm);105 // Trigger almComplete.106 if (typeof almComplete === 'function' && alm.transition !== 'masonry') {107 window.almComplete(alm);108 }109 // End transitions.110 alm.AjaxLoadMore.transitionEnd();111 // ALM Done112 if (!nextPage) {113 alm.AjaxLoadMore.triggerDone();114 }115}116/**117 * Get the content, title and results text from the Ajax response.118 *119 * @param {*} response120 * @param {object} alm121 * @since 5.4.0122 */123export function elementorGetContent(response, alm) {124 let data = {125 html: '',126 meta: {127 postcount: 1,128 totalposts: alm.localize.total_posts,129 debug: false,130 },131 };132 if (response.status === 200 && response.data) {133 let div = document.createElement('div');134 div.innerHTML = response.data;135 // Get Page Title136 let title = div.querySelector('title').innerHTML;137 data.pageTitle = title;138 // Get Elementor Items HTML139 let items = div.querySelector(`${alm.addons.elementor_target} .${alm.addons.elementor_container_class}`);140 data.html = items ? items.innerHTML : '';141 // Set Page URL Params142 alm.addons.elementor_current_url = alm.addons.elementor_next_page_url; // Set current to previous page URL143 alm.addons.elementor_next_page_url = elementorGetNextPage(div, alm.addons.elementor_pagination_class);144 // Results Text145 //almElementorResultsText(div, alm);146 }147 return data;148}149/**150 * Create Elementor Params for ALM.151 *152 * @param Object alm153 * @return alm154 */155export function elementorCreateParams(alm) {156 // Get Settings157 alm.addons.elementor_type = 'posts';158 alm.addons.elementor_settings = JSON.parse(alm.listing.dataset.elementorSettings);159 // Parse Container Settings160 alm.addons.elementor_target = alm.addons.elementor_settings.target;161 alm.addons.elementor_element = alm.addons.elementor_settings.target162 ? document.querySelector(`.elementor-widget-wrap ${alm.addons.elementor_settings.target}`)163 : '';164 alm.addons.elementor_widget = elementorGetWidgetType(alm.addons.elementor_element);165 // Masonry166 alm = setElementorClasses(alm, alm.addons.elementor_widget);167 // Pagination Element168 alm.addons.elementor_pagination =169 alm.addons.elementor_element.querySelector(alm.addons.elementor_pagination_class) ||170 alm.addons.elementor_element.querySelector(`.${alm.addons.elementor_settings.pagination_class}`);171 alm.addons.elementor_pagination = alm.addons.elementor_pagination ? alm.addons.elementor_pagination : false;172 alm.addons.elementor_controls = alm.addons.elementor_settings.controls;173 alm.addons.elementor_controls = alm.addons.elementor_controls === 'true' ? true : false;174 alm.addons.elementor_scrolltop = parseInt(alm.addons.elementor_settings.scrolltop);175 // Set Page & URL params176 alm.addons.elementor_current_url = window.location.href;177 alm.addons.elementor_next_page_url = elementorGetNextUrl(alm.addons.elementor_pagination);178 alm.addons.elementor_paged = alm.addons.elementor_settings.paged ? parseInt(alm.addons.elementor_settings.paged) : 1;179 alm.page = parseInt(alm.page) + alm.addons.elementor_paged;180 // Masonry181 alm = parseMasonryConfig(alm);182 if (!alm.addons.elementor_element) {183 console.warn("Ajax Load More: Unable to locate Elementor Widget. Are you sure you've set up your target parameter correctly?");184 }185 if (!alm.addons.elementor_pagination) {186 console.warn(187 'Ajax Load More: Unable to locate Elementor pagination. There are either no results or p Ajax Load More is unable to locate the pagination widget?'188 );189 }190 return alm;191}192/**193 * Set the required classnames for parsing data and injecting content into the Elementor listing194 *195 * @param {*} alm196 * @param {*} type197 */198function setElementorClasses(alm, type = 'posts') {199 // Container Class200 alm.addons.elementor_container_class =201 type === 'woocommerce' ? alm.addons.elementor_settings.woo_container_class : alm.addons.elementor_settings.posts_container_class;202 // Item Class203 alm.addons.elementor_item_class = type === 'woocommerce' ? alm.addons.elementor_settings.woo_item_class : alm.addons.elementor_settings.posts_item_class;204 // Pagination Class205 alm.addons.elementor_pagination_class =206 type === 'woocommerce' ? `.${alm.addons.elementor_settings.woo_pagination_class}` : `.${alm.addons.elementor_settings.posts_pagination_class}`;207 return alm;208}209/**210 * Parse Masonry Settings from Elementor Data atts211 *212 * @param {*} alm213 */214function parseMasonryConfig(alm) {215 if (!alm.addons.elementor_element) {216 return alm; // Exit if not found.217 }218 const target = alm.addons.elementor_element;219 const settings = target.dataset.settings ? JSON.parse(target.dataset.settings) : '';220 if (!settings) {221 return alm; // Exit if not found.222 }223 alm.addons.elementor_masonry = settings.hasOwnProperty('cards_masonry') || settings.hasOwnProperty('classic_masonry');224 if (alm.addons.elementor_masonry) {225 alm.addons.elementor_masonry_columns = parseInt(settings.cards_columns) || parseInt(settings.classic_columns);226 alm.addons.elementor_masonry_columns_mobile = parseInt(settings.cards_columns_mobile) || parseInt(settings.classic_columns_mobile);227 alm.addons.elementor_masonry_columns_tablet = parseInt(settings.cards_columns_tablet) || parseInt(settings.classic_columns_tablet);228 alm.addons.elementor_masonry_gap = parseInt(settings.cards_row_gap.size);229 }230 return alm;231}232/**233 * Position Elementor Masonry Items234 *235 * @param {*} alm236 * @param {*} container_class237 * @param {*} item_class238 */239function positionMasonryItems(alm, container_class, item_class) {240 let heights = [];241 // Get Elementor Settings242 const columnsCount = alm.addons.elementor_masonry_columns;243 const columnsCountTablet = alm.addons.elementor_masonry_columns_tablet;244 const columnsCountMobile = alm.addons.elementor_masonry_columns_mobile;245 const verticalSpaceBetween = alm.addons.elementor_masonry_gap;246 let columns = columnsCount;247 // Get Elementor Breakpoints248 const breakpoints = window.elementorFrontendConfig && window.elementorFrontendConfig.breakpoints ? window.elementorFrontendConfig.breakpoints : 0;249 const windowW = window.innerWidth;250 // Set Columns251 if (windowW > breakpoints.lg) {252 columns = columnsCount;253 } else if (windowW > breakpoints.md) {254 columns = columnsCountTablet;255 } else {256 columns = columnsCountMobile;257 }258 // Get Containers259 const container = document.querySelector(container_class);260 if (!container) {261 return false;262 }263 const items = container.querySelectorAll(item_class);264 if (!items) {265 return false;266 }267 // Loop items268 items.forEach((item, index) => {269 let row = Math.floor(index / columns);270 let itemHeight = item.getBoundingClientRect().height + verticalSpaceBetween;271 if (row) {272 let itemPosition = jQuery(item).position();273 let indexAtRow = index % columns;274 let pullHeight = Math.round(itemPosition.top) - heights[indexAtRow];275 pullHeight *= -1;276 item.style.marginTop = `${Math.round(pullHeight)}px`;277 heights[indexAtRow] += itemHeight;278 } else {279 heights.push(itemHeight);280 }281 });282}283/**284 * Determine the type of elementor widget (woocommerce || posts)285 *286 * @param {*} target287 * @param {*} classname288 */289function elementorGetWidgetType(target) {290 if (!target) {291 return false;292 }293 // If container contains the woocommerce elementor class294 const type = target.classList.contains('elementor-wc-products') ? 'woocommerce' : 'posts';295 return type;296}297/**298 * Get the upcoming URL from the a.next link from the HTML299 *300 * @param {HTMLElement} element301 * @param {String} classname302 * @return {string} href303 */304function elementorGetNextPage(element, classname) {305 const pagination = element.querySelector(classname);306 const href = pagination ? elementorGetNextUrl(pagination) : '';307 return href;308}309/**310 * Get the URL of the next page to load from the a.next href311 *312 * @param {HTMLElement} element313 * @return {String} url314 */315function elementorGetNextUrl(element) {316 if (!element) {317 return '';318 }319 return element.querySelector('a.next') ? element.querySelector('a.next').href : '';...

Full Screen

Full Screen

useSelectableInputs.js

Source:useSelectableInputs.js Github

copy

Full Screen

1// Copyright (C) 2017-2022 Smart code 2033585072const React = require('react');3const mapSelectableInputs = (installedAddons, remoteAddons) => {4 const catalogSelect = {5 title: 'Select catalog',6 options: remoteAddons.selectable.catalogs7 .concat(installedAddons.selectable.catalogs)8 .map(({ name, deepLinks }) => ({9 value: deepLinks.addons,10 label: name,11 title: name12 })),13 selected: remoteAddons.selectable.catalogs14 .concat(installedAddons.selectable.catalogs)15 .filter(({ selected }) => selected)16 .map(({ deepLinks }) => deepLinks.addons),17 renderLabelText: remoteAddons.selected !== null ?18 () => {19 const selectableCatalog = remoteAddons.selectable.catalogs20 .find(({ id }) => id === remoteAddons.selected.request.path.id);21 return selectableCatalog ? selectableCatalog.name : remoteAddons.selected.request.path.id;22 }23 :24 null,25 onSelect: (event) => {26 window.location = event.value;27 }28 };29 const typeSelect = {30 title: 'Select type',31 options: installedAddons.selected !== null ?32 installedAddons.selectable.types.map(({ type, deepLinks }) => ({33 value: deepLinks.addons,34 label: type !== null ? type : 'All'35 }))36 :37 remoteAddons.selectable.types.map(({ type, deepLinks }) => ({38 value: deepLinks.addons,39 label: type40 })),41 selected: installedAddons.selected !== null ?42 installedAddons.selectable.types43 .filter(({ selected }) => selected)44 .map(({ deepLinks }) => deepLinks.addons)45 :46 remoteAddons.selectable.types47 .filter(({ selected }) => selected)48 .map(({ deepLinks }) => deepLinks.addons),49 renderLabelText: () => {50 return installedAddons.selected !== null ?51 installedAddons.selected.request.type === null ?52 'All'53 :54 installedAddons.selected.request.type55 :56 remoteAddons.selected !== null ?57 remoteAddons.selected.request.path.type58 :59 typeSelect.title;60 },61 onSelect: (event) => {62 window.location = event.value;63 }64 };65 return [catalogSelect, typeSelect];66};67const useSelectableInputs = (installedAddons, remoteAddons) => {68 const selectableInputs = React.useMemo(() => {69 return mapSelectableInputs(installedAddons, remoteAddons);70 }, [installedAddons, remoteAddons]);71 return selectableInputs;72};...

Full Screen

Full Screen

Using AI Code Generation

copy

Full Screen

1import React from 'react';2import { Button } from '@storybook/react/demo';3import { withKnobs, text, boolean, number } from "@storybook/addon-knobs";4export default {5};6export const Text = () => <Button>{text("Label", "Hello Storybook")}</Button>;7export const Emoji = () => (8);9export const WithSomeEmojiAndAction = () => (10 <Button onClick={action('clicked')}>11);12export const WithSomeEmojiAndAction = () => (13 <Button onClick={action('clicked')}>14);15export const WithSomeEmojiAndAction = () => (16 <Button onClick={action('clicked')}>17);18export const WithSomeEmojiAndAction = () => (19 <Button onClick={action('clicked')}>20);21export const WithSomeEmojiAndAction = () => (22 <Button onClick={action('clicked')}>23);24export const WithSomeEmojiAndAction = () => (25 <Button onClick={action('clicked')}>26);27export const WithSomeEmojiAndAction = () => (28 <Button onClick={action('clicked')}>29);30export const WithSomeEmojiAndAction = () => (31 <Button onClick={action('

Full Screen

Using AI Code Generation

copy

Full Screen

1import { configure } from '@storybook/react'2const req = require.context('../src', true, /\.stories\.js$/)3function loadStories() {4 req.keys().forEach(filename => req(filename))5}6configure(loadStories, module)7import { configure } from '@storybook/react'8const req = require.context('../', true, /\.stories\.js$/)9function loadStories() {10 req.keys().forEach(filename => req(filename))11}12configure(loadStories, module)

Full Screen

Using AI Code Generation

copy

Full Screen

1import { addons } from '@storybook/addons';2import { create } from '@storybook/theming/create';3import { themes } from '@storybook/theming';4addons.setConfig({5 theme: create({6 }),7});8addons.setConfig({9});10addons.setConfig({11});12addons.setConfig({13});

Full Screen

Using AI Code Generation

copy

Full Screen

1module.exports = require('storybook-root-config').addons;2module.exports = {3 {4 options: {5 },6 },7};8import { addParameters } from '@storybook/react';9import { DocsPage, DocsContainer } from '@storybook/addon-docs/blocks';10addParameters({11 docs: {12 },13});14module.exports = ({ config }) => {15 config.module.rules.push({16 test: /\.(js|jsx)$/,17 include: path.resolve(__dirname, 'src'),18 {19 loader: require.resolve('babel-loader'),20 options: {21 },22 },23 });24 config.resolve.extensions.push('.js', '.jsx');25 return config;26};27import { addons } from '@storybook/addons';28import { themes } from '@storybook/theming';29addons.setConfig({30});31 window.STORYBOOK_REACT_CLASSES = {};32 window.STORYBOOK_REACT_CLASSES = {};33import { addParameters } from '@storybook/react';34import { DocsPage, DocsContainer } from '@storybook/addon-docs/blocks';35addParameters({36 docs: {37 },38});39import { addDecorator } from '@storybook/react';40import { withInfo } from '@storybook/addon-info';41addDecorator(withInfo);42import { addDecorator } from '@storybook/react';43import { withProvider } from 'storybook-addon-redux-decorator';44addDecorator(withProvider);45import { addDecorator } from '@storybook/react';46import { withRedux } from 'storybook-addon-redux-decorator';47addDecorator(withRedux);48import { addDecorator } from '@

Full Screen

Using AI Code Generation

copy

Full Screen

1import addons from '@storybook/addons';2import { withInfo } from '@storybook/addon-info';3import { withKnobs } from '@storybook/addon-knobs';4import { configure } from '@storybook/react';5addons.setConfig({6 theme: {},7 sidebar: {8 },9});10function loadStories() {11 require('../src/stories');12}13configure(loadStories, module);14addons.register('storybookjs/knobs', () => {15 addons.addPanel('storybookjs/knobs/panel', {16 render: () => <div>Knobs</div>,17 });18});19addons.register('storybookjs/info', () => {20 addons.addPanel('storybookjs/info/panel', {21 render: () => <div>Info</div>,22 });23});24addons.register('storybookjs/actions', () => {25 addons.addPanel('storybookjs/actions/panel', {26 render: () => <div>Actions</div>,27 });28});29addons.register('storybookjs/viewport', () => {30 addons.addPanel('storybookjs/viewport/panel', {31 render: () => <div>Viewport</div>,32 });33});34addons.register('storybookjs/source', () => {35 addons.addPanel('storybookjs/source/panel', {36 render: () => <div>Source</div>,37 });38});39addons.register('storybookjs/links', () => {

Full Screen

Using AI Code Generation

copy

Full Screen

1import addons from '@storybook/addons';2import { ADDON_ID, PANEL_ID } from './';3import { ADDON_ID as ADDON_ID_KNOBS } from '@storybook/addon-knobs';4addons.register(ADDON_ID, api => {5 addons.addPanel(PANEL_ID, {6 render: ({ active, key }) => (7 <MyPanel key={key} api={api} active={active} />8 });9});10import addons from '@storybook/addons';11import { ADDON_ID, PANEL_ID } from './';12import { ADDON_ID as ADDON_ID_KNOBS } from '@storybook/addon-knobs';13addons.register(ADDON_ID, api => {14 addons.addPanel(PANEL_ID, {15 render: ({ active, key }) => (16 <MyPanel key={key} api={api} active={active} />17 });18});19import React from 'react';20import { useParameter } from '@storybook/api';21import { PARAM_KEY } from './';22export const MyPanel = () => {23 const value = useParameter(PARAM_KEY, null);24 return <div>{value}</div>;25};

Full Screen

Using AI Code Generation

copy

Full Screen

1import addons from '@storybook/addons';2import { EVENT_ID } from './constants';3addons.getChannel().addListener(EVENT_ID, data => {4 console.log(`Received ${EVENT_ID} with data: ${data}`);5});6export const EVENT_ID = 'my-event';7import { EVENT_ID } from './constants';8addons.getChannel().emit(EVENT_ID, 'Hello from the preview');9import { EVENT_ID } from './constants';10addons.getChannel().emit(EVENT_ID, 'Hello from the manager');11import { EVENT_ID } from './constants';12addons.getChannel().emit(EVENT_ID, 'Hello from the preview');13import { EVENT_ID } from './constants';14addons.getChannel().emit(EVENT_ID, 'Hello from the manager');15import { EVENT_ID } from './constants';16addons.getChannel().emit(EVENT_ID, 'Hello from the preview');17import { EVENT_ID } from './constants';18addons.getChannel().emit(EVENT_ID, 'Hello from the manager');19import { EVENT_ID } from './constants';20addons.getChannel().emit(EVENT_ID, 'Hello from the preview');21import { EVENT_ID } from './constants';22addons.getChannel().emit(EVENT_ID, 'Hello from the manager');23import { EVENT_ID } from './constants';24addons.getChannel().emit(EVENT_ID, 'Hello from the preview');25import { EVENT_ID } from './constants';

Full Screen

Using AI Code Generation

copy

Full Screen

1import { addons } from '@storybook/addons';2import { withRootDecorator } from 'storybook-root-decorator';3addons.setConfig({4 decorator: withRootDecorator({5 style: {6 },7 bodyStyle: {8 },9 }),10});11import { withRootDecorator } from 'storybook-root-decorator';12 withRootDecorator({13 style: {14 },15 bodyStyle: {16 },17 }),18];19import React from 'react';20import { storiesOf } from '@storybook/react';21import MyComponent from './MyComponent';22storiesOf('MyComponent', module).add('default', () => <MyComponent />);23Default: {}24Default: {}

Full Screen

Using AI Code Generation

copy

Full Screen

1const rootConfig = require('storybook-root-config');2const addons = rootConfig.addons;3module.exports = {4};5module.exports = {6 stories: ['../src/**/*.stories.@(js|jsx|ts|tsx|mdx)'],7};

Full Screen

Automation Testing Tutorials

Learn to execute automation testing from scratch with LambdaTest Learning Hub. Right from setting up the prerequisites to run your first automation test, to following best practices and diving deeper into advanced test scenarios. LambdaTest Learning Hubs compile a list of step-by-step guides to help you be proficient with different test automation frameworks i.e. Selenium, Cypress, TestNG etc.

LambdaTest Learning Hubs:

YouTube

You could also refer to video tutorials over LambdaTest YouTube channel to get step by step demonstration from industry experts.

Run storybook-root automation tests on LambdaTest cloud grid

Perform automation testing on 3000+ real desktop and mobile devices online.

Try LambdaTest Now !!

Get 100 minutes of automation test minutes FREE!!

Next-Gen App & Browser Testing Cloud

Was this article helpful?

Helpful

NotHelpful