/** * A CMMN 1.1 diagram editing component. * * @param {Object} options */ function CmmnEditor(options) { ensureOpts([ 'layout', 'config', 'metaData' ], options); DiagramEditor.call(this, options); this.name = 'cmmn'; // set current modeler version and name to the diagram this.on('save', () => { var definitions = this.getModeler().definitions; if (definitions) { definitions.exporter = options.metaData.name; definitions.exporterVersion = options.metaData.version; } }); // elements to insert modeler and properties panel into this.$propertiesEl = domify('<div class="properties-parent"></div>'); // let canvas know that the window has been resized this.on('window:resized', this.compose('resizeCanvas')); // trigger the palette resizal whenever we focus a tab or the layout is updated this.on('focus', debounce(this.resizeCanvas, 50)); this.on('layout:update', debounce(this.resizeCanvas, 50)); }
fastdom.write(function () { /** * Set the item styles before creating the Sly instance */ this.updateItemStyles(); /** * Magic! */ this.sly = new Sly(this.$frame, this.config.options); /** * Set up callbacks for Sly * Note: The throttle count can be high because if the event is touch or drag based, the event * can fire lots of times consecutively */ this.sly.on('change', debounce(this.slideChanged, 250).bind(this)); this.sly.on('moveStart', throttle(this.lockCarousel, 250).bind(this)); this.sly.on('moveEnd', throttle(this.unlockCarousel, 250).bind(this)); this.sly.init(); /** * Set the state of the navigation buttons */ if (this.config.pageNav) { this.setPageNavigationStates(); } }.bind(this));
/** * A general purpose snapping component for diagram elements. * * @param {EventBus} eventBus * @param {Canvas} canvas */ function Snapping(eventBus, canvas) { this._canvas = canvas; var self = this; eventBus.on([ 'shape.move.start', 'create.start' ], function(event) { self.initSnap(event); }); eventBus.on([ 'shape.move.move', 'shape.move.end', 'create.move', 'create.end' ], HIGHER_PRIORITY, function(event) { if (event.originalEvent && event.originalEvent.ctrlKey) { return; } if (isSnapped(event)) { return; } self.snap(event); }); eventBus.on([ 'shape.move.cleanup', 'create.cleanup' ], function(event) { self.hide(); }); // delay hide by 1000 seconds since last match this._asyncHide = debounce(this.hide, 1000); }
/** * Scales text to fit within a given area * * In order to scale the text, a `span` is wrapped around the `$el`'s text; this * allows for the width of the text to be calculated. The width of the `$el` is * also calculated and those two widths are used to create a ratio in which to * divide the `minFontSize` by. * * Options * * fontSizes {Array} An array of font sizes that the text uses; if the font size * changes at different breakpoints, each font size should be * added to the array; the values are used to recalculate * the text width at each font size; each font size should * be a {Number} * minFontSize {Number} The minimum font size desired; this value is used to * create the `compressor`, or ratio for sizing; the * default is 30 * * @param {jQuery Object} $el The element where the text will be scaled * @param {Object} options An array of options * @example * fitText(this.$el.find(".js-masthead-title"), { * fontSizes: [40, 56, 80, 120], * minFontSize: 56 * }); * */ export default function fitText($el, options) { let wordCount = getWordCount($el.text()); let settings = { fontSizes: [], minFontSize: 30 }; $.extend(settings, options); if (wordCount === 1) { if (!$el.find("span").length) { $el.wrapInner("<span />"); } let textWidth = $el.find("span").width(); // Call once to set resizeFont($el, textWidth, settings); // Call on resize $(window).on("resize.fitText orientationchange.fitText", debounce(() => { if(settings.fontSizes.indexOf(parseInt($el.css("fontSize").replace("px", ""), 10)) !== -1) { textWidth = $el.find("span").width(); } resizeFont($el, textWidth, settings); }, 10)); } };
export async function buildSass({ log, kibanaDir, watch }) { log.info('running plugin discovery in', kibanaDir); const scanDirs = [resolve(kibanaDir, 'src/legacy/core_plugins')]; const paths = [resolve(kibanaDir, 'x-pack')]; const { spec$ } = findPluginSpecs({ plugins: { scanDirs, paths } }); const enabledPlugins = await spec$.pipe(toArray()).toPromise(); const uiExports = collectUiExports(enabledPlugins); const { styleSheetPaths } = uiExports; log.info('%s %d styleSheetPaths', watch ? 'watching' : 'found', styleSheetPaths.length); log.verbose(styleSheetPaths); if (watch) { const debouncedBuild = debounce(async path => { let buildPaths = styleSheetPaths; if (path) { buildPaths = styleSheetPaths.filter(styleSheetPath => path.includes(styleSheetPath.urlImports.publicDir) ); } await build({ log, kibanaDir, styleSheetPaths: buildPaths, watch }); }); const watchPaths = styleSheetPaths.map(styleSheetPath => styleSheetPath.urlImports.publicDir); await build({ log, kibanaDir, styleSheetPaths }); chokidar.watch(watchPaths, { ignoreInitial: true }).on('all', (_, path) => { debouncedBuild(path); }); } else { await build({ log, kibanaDir, styleSheetPaths }); } }
initialize() { if (!$("html").hasClass("ie9")) { this._clampText(); $(window).resize(debounce(this._reclamp.bind(this), 100)); } }
// _temporarilyIgnoreMouseSelection is used to ignore mouse selections. See // _mouseSelectItem. _temporarilyIgnoreMouseSelection() { if (!this._debouncedUnignoreMouseSelection) { this._debouncedUnignoreMouseSelection = debounce(() => { this._ignoreMouseSelection = false; }, 200, {leading: false, trailing: true}); } this._debouncedUnignoreMouseSelection(); this._ignoreMouseSelection = true; }
module.exports = function (viewModel) { var subject = $('.ec-subject'); var teaser = $('.ec-teaser'); var body = $('.ec-body'); var topic = $('.ec-topic'); var previewSubject = $('.ec-preview-subject'); var previewTeaser = $('.ec-preview-teaser'); var previewBody = $('.ec-preview-body'); var sendButton = $('.ec-send'); subject.on('keypress keydown paste', raf.bind(null, debounce(updatePreviewSubject, 200))); teaser.on('keypress keydown paste', raf.bind(null, debounce(updatePreviewTeaser, 200))); body.on('keypress keydown paste input', raf.bind(null, debounce(updatePreviewBody, 200))); sendButton.on('click', send); function updatePreviewSubject () { previewSubject.text(subject.value().trim() || 'Email Preview'); } function updatePreviewTeaser () { previewTeaser.text(teaser.value() || 'Teaser about email contents'); } function updatePreviewBody () { previewBody.html(getHtml(body).trim().replace(rparagraph, '') || 'Main body of your email'); } function getHtml (el) { return markdownService.compile(el.value()); } function send () { var model = { json: { topic: topic.value(), subject: subject.value(), teaser: teaser.value(), body: body.value() } }; viewModel.measly.post('/api/email', model).on('data', leave); } function leave () { taunus.navigate('/'); } };
init: function() { this.emitter = new EventEmitter(); this.express = this.express || require('express'); this.http = this.http || require('http'); var serverRestartDelayTime = this.serverRestartDelayTime || 100; this.scheduleServerRestart = debounce(function(){ this.restartHttpServer(); }, serverRestartDelayTime); },
function uiFrameworkWatch() { const debouncedCompile = debounce(uiFrameworkCompile, 400, { leading: true }); return new Promise((resolve, reject) => { debouncedCompile(); chokidar.watch('ui_framework/components', { ignoreInitial: true }).on('all', (event, path) => { grunt.log.writeln(event, path); debouncedCompile(); }); }); }
function scheduleSync(reactor) { if (!isSyncing(reactor)) { return; } if (!(reactor.hassId in SCHEDULED_SYNCS)) { /* eslint-disable no-use-before-define */ SCHEDULED_SYNCS[reactor.hassId] = debounce(fetchAll.bind(null, reactor), SYNC_INTERVAL); /* eslint-enable no-use-before-define */ } SCHEDULED_SYNCS[reactor.hassId](); }
$(document).on('ready', function() { $('#js-show-hide').click(function(){ $('#js-properties-panel').toggle(); }); $('#js-create-diagram').click(function(e) { e.stopPropagation(); e.preventDefault(); createNewDiagram(); }); var downloadLink = $('#js-download-diagram'); var downloadSvgLink = $('#js-download-svg'); $('.buttons a').click(function(e) { if (!$(this).is('.active')) { e.preventDefault(); e.stopPropagation(); } }); function setEncoded(link, name, data) { var encodedData = encodeURIComponent(data); if (data) { link.addClass('active').attr({ 'href': 'data:application/bpmn20-xml;charset=UTF-8,' + encodedData, 'download': name }); } else { link.removeClass('active'); } } var debounce = require('lodash/function/debounce'); var exportArtifacts = debounce(function() { saveSVG(function(err, svg) { setEncoded(downloadSvgLink, 'diagram.svg', err ? null : svg); }); saveDiagram(function(err, xml) { setEncoded(downloadLink, 'diagram.bpmn', err ? null : xml); }); }, 500); bpmnModeler.on('commandStack.changed', exportArtifacts); });
constructor(props) { super(props); this.state = { query: "", matchingDefs: {Defs: []}, selectionIndex: 0, focused: false, }; this._queryInput = null; this._handleKeyDown = this._handleKeyDown.bind(this); this._scrollToVisibleSelection = this._scrollToVisibleSelection.bind(this); this._setSelectedItem = this._setSelectedItem.bind(this); this._handleInput = this._handleInput.bind(this); this._onSelection = debounce(this._onSelection.bind(this), 100, {leading: false, trailing: true}); // Prevent rapid repeated selections this._onChangeQuery = this._onChangeQuery.bind(this); this._debouncedSetQuery = debounce((query) => { if (query !== this.state.query) { this._onChangeQuery(query); } }, 200, {leading: false, trailing: true}); }
constructor(props) { super(props); this.state = { open: false, }; this._closeDropdown = this._closeDropdown.bind(this); this._onToggleDropdown = this._onToggleDropdown.bind(this); this._onChangeQuery = this._onChangeQuery.bind(this); this._onClickOutside = this._onClickOutside.bind(this); this._onKeydown = this._onKeydown.bind(this); this._debouncedSetQuery = debounce((query) => { this.setState({query: query}); }, 150, {leading: true, trailing: true}); }
getInitialState: function getInitialState() { var preferredCountries = this.props.preferredCountries.map(function (iso2) { return allCountriesIso2Lookup.hasOwnProperty(iso2) ? allCountries[allCountriesIso2Lookup[iso2]] : null; }).filter(function (val) { return val !== null; }); return assign({}, { preferredCountries: preferredCountries, queryString: '', freezeSelection: false, debouncedQueryStingSearcher: debounce(this.searchCountry, 100) }, this._mapPropsToState(this.props)); },
Amygdala.prototype._emitChange = function(type) { // TODO: Add tests for debounced events if (!this._changeEvents[type]) { this._changeEvents[type] = debounce(partial(function(type) { // emit changes events this.emit('change', type); // change:<type> this.emit('change:' + type); // TODO: compare the previous object and trigger change events }.bind(this), type), 150); } this._changeEvents[type](); }
constructor(props, context) { super(props, context); this.state = {}; // needed for ReactComponentWithPureRenderMixin::shouldComponentUpdate() this.shouldComponentUpdate = shouldComponentUpdate.bind(this); this.hasEntityAndView = hasEntityAndView.bind(this); this.getView = getView.bind(this); this.onLoadFailure = onLoadFailure.bind(this); this.onSendFailure = onSendFailure.bind(this); this.updateField = debounce(this.updateField.bind(this), 300); this.viewName = 'EditView'; this.isValidEntityAndView = this.hasEntityAndView(context.router.getCurrentParams().entity); }
componentDidMount() { this.ah = new AH(this.refs.loading, this.refs.poptip); this.query(this.state.tab); LoadMore.init(() => { this.query(this.state.tab); }); let winH = $.height(window); EventListener.listen(window, 'scroll', debounce(() => { let t = $.scrollTop(window); let on = t > 1.5 * winH; this.setState({ hasGoTop: on }); })); }
this.handleMouseDown = (e) => { e.preventDefault(); this.setState({dragging: true}); $(document).off(`mousemove.${this.props.eventScope}`).on(`mousemove.${this.props.eventScope}`, debounce((event) => { const $resizer = $(this.refs.resizer); const offset = event.pageX - $resizer.offset().left - $resizer.width() / 2; let leftWidth = this.props.leftWidth + offset; let rightWidth = this.props.rightWidth - offset; if (leftWidth < this.props.minLeftWidth) { leftWidth = this.props.minLeftWidth; rightWidth = this.props.rightWidth + (this.props.leftWidth - this.props.minLeftWidth); } if (leftWidth > this.props.maxLeftWidth) { leftWidth = this.props.maxLeftWidth; rightWidth = this.props.rightWidth + (this.props.leftWidth - this.props.maxLeftWidth); } this.props.onResize(leftWidth, rightWidth); }, 10)); };
$(function(){ $('#'+componentId+' .buttons a').click(function(e) { if (!$(this).is('.active')) { e.preventDefault(); e.stopPropagation(); } }); var debounce = require('lodash/function/debounce'); var exportArtifacts = debounce(function() { saveDiagram(function(err, xml) { $('#' + xmlComponentId).val(xml); }); }, 500); bpmnModeler.on('commandStack.changed', exportArtifacts); openDiagram($('#' + xmlComponentId).val()); });
loadScript('/js/rome.js', function loaded () { var updateSlugSlowly = raf.bind(null, debounce(updateSlug, 100)); rome(presented, { time: false, inputFormat: 'DD-MM-YYYY' }); slugUpdates('on'); slug.once('keypress keydown paste input', unbindSlug); addResource.on('click', addResourceElements); function slugUpdates (direction) { title[direction]('keypress keydown paste input', updateSlugSlowly); } function unbindSlug () { slugUpdates('off'); } function updateSlug () { slug.value(sluggish(title.value())); } function addResourceElements () { resources.clone().beforeOf(actions); } });
initialize() { this.state = NavigationState.getState(); this.search = new SearchComponent(); this.navigation = new NavigationComponent({ el: $(".navigation") }); this.events = { "click .js-lp-global-header-search": "onSearchClick", "click .js-lp-global-header-search .navigation__link": "onSearchClick", "click .js-menu": "onMobileMenuClick" }; this.$search = this.$el.find(".js-lp-global-header-search"); this.$inner = this.$el.find(".js-lp-global-header-inner"); $(window).resize(debounce(this.render.bind(this), 100)); this.render(); this.$mobileNotificationBadge = require("./mobile_notification_badge.hbs"); this.appendMenuIcon(); }
// add listeners for various DOM events - scrolling, mutation and navigation // and use these to trigger checks for visible placeholders (and, in the case of mutations, // to record new placeholders and remove nodes that are no longer placeholders) function observeDomChanges( MutationObserver ) { // if anything scrolls, check if any of our placeholder elements are in view, // but not more than a few times a second window.addEventListener('scroll', debounce(checkForVisiblePlaceholders.bind(null, 'scroll'), 200), true); // if the user navigates, stop the current event and proceed to the next one page( function( context, next ) { // send "placeholder-wait-navigated" event checkForVisiblePlaceholders( 'navigate' ); next(); } ); // this is fired for matching mutations (childList and class attr changes) var observer = new MutationObserver(function(mutations, observer) { // record all the nodes that match our placeholder classes in the "activePlaceholders" array mutations.forEach( recordPlaceholders ); // remove any nodes from activePlaceholders that are no longer placeholders // check each node for: // a. whether it's still in the DOM at all, and if so: // b. whether it still has a placeholder class var removed = remove( activePlaceholders, function( node ) { return !OBSERVE_ROOT.contains( node ) || !isPlaceholder( node ); } ); checkForVisiblePlaceholders( 'mutation' ); } ); observer.observe( OBSERVE_ROOT, { subtree: true, attributes: true, childList: true, attributeFilter: ['class'] } ); }
getInitialState: function getInitialState() { var inputNumber = this.props.value || ''; var selectedCountryGuess = this.guessSelectedCountry(inputNumber.replace(/\D/g, '')); var selectedCountryGuessIndex = findIndex(allCountries, selectedCountryGuess); var formattedNumber = this.formatNumber(inputNumber.replace(/\D/g, ''), selectedCountryGuess ? selectedCountryGuess.format : null); var preferredCountries = []; preferredCountries = filter(allCountries, function (country) { return any(this.props.preferredCountries, function (preferredCountry) { return preferredCountry === country.iso2; }); }, this); return { preferredCountries: preferredCountries, selectedCountry: selectedCountryGuess, highlightCountryIndex: selectedCountryGuessIndex, formattedNumber: formattedNumber, showDropDown: false, queryString: '', freezeSelection: false, debouncedQueryStingSearcher: debounce(this.searchCountry, 100) }; },
getInitialState: function getInitialState() { var inputNumber = this.props.initialValue || this.props.value || ''; var selectedCountryGuess = this.guessSelectedCountry(inputNumber.replace(/\D/g, '')); var selectedCountryGuessIndex = findIndex(allCountries, selectedCountryGuess); var formattedNumber = this.formatNumber(inputNumber.replace(/\D/g, ''), selectedCountryGuess ? selectedCountryGuess.format : null); var preferredCountries = []; preferredCountries = this.props.preferredCountries.map(function (iso2) { return allCountriesIso2Lookup.hasOwnProperty(iso2) ? allCountries[allCountriesIso2Lookup[iso2]] : null; }).filter(function (val) { return val !== null; }); return { preferredCountries: preferredCountries, selectedCountry: selectedCountryGuess, highlightCountryIndex: selectedCountryGuessIndex, formattedNumber: formattedNumber, showDropDown: false, queryString: '', freezeSelection: false, debouncedQueryStingSearcher: debounce(this.searchCountry, 100) }; },
constructor(...args) { super(...args); this.onClickLogin = this.onClickLogin.bind(this); this.onSearch = debounce(this.onSearch.bind(this), 400); }
/** * Create the browserify bundle */ function createBundle(config) { var bopts = config.browserify || {}, bundleDelay = bopts.bundleDelay || DEFAULT_BUNDLE_DELAY; function warn(key) { log.warn('Invalid config option: "' + key + 's" should be "' + key + '"'); } forEach([ 'transform', 'plugin' ], function(key) { if (bopts[key + 's']) { warn(key); } }); var browserifyOptions = assign({ basedir: path.resolve(config.basePath), // watchify.args cache: {}, packageCache: {} }, omit(bopts, [ 'transform', 'plugin', 'configure', 'bundleDelay' ])); if ('prebundle' in browserifyOptions) { log.warn('The prebundle hook got removed in favor of configure'); } if ('watchify' in browserifyOptions) { log.warn('Configure watchify via config.watchify'); } var w = browserify(browserifyOptions); w.setMaxListeners(Infinity); forEach(bopts.plugin, function(p) { // ensure we can pass plugin options as // the first parameter if (!Array.isArray(p)) { p = [ p ]; } w.plugin.apply(w, p); }); forEach(bopts.transform, function(t) { // ensure we can pass transform options as // the first parameter if (!Array.isArray(t)) { t = [ t ]; } w.transform.apply(w, t); }); // test if we have a configure function if (bopts.configure && typeof bopts.configure === 'function') { bopts.configure(w); } // register rebuild bundle on change if (config.autoWatch) { if (!watchify) { log.error('watchify not found; install it via npm install --save-dev watchify'); log.error('cannot perform incremental rebuild'); throw new Error('watchify not found'); } w = watchify(w, config.watchify); log.info('registering rebuild (autoWatch=true)'); w.on('update', function(updated) { // we perform an update, karma will trigger one, too // because the bundling is deferred only one change will // be triggered. Anything else is the result of a // raise condition or a problem of watchify firing file // changes to late log.debug('files changed'); deferredBundle(); }); w.on('log', function(msg) { log.info(msg); }); // update bundle file w.on('bundled', function(err, content) { if (w._builtOnce) { bundleFile.update(err ? BUNDLE_ERROR_TPL : content.toString('utf-8')); log.info('bundle updated'); } }); } function deferredBundle(cb) { if (cb) { w.once('bundled', cb); } rebuild(); } var rebuild = debounce(function rebuild() { if (w._bundled) { log.debug('resetting bundle'); var recorded = w._recorded; w.reset(); recorded.forEach(function(e) { // we remove missing files on the fly // to cope with bundle internals missing if (e.file && !fs.existsSync(path.resolve(config.basePath, e.file))) { log.debug('removing missing file', e.file); } else { w.pipeline.write(e); } }); } w.emit('prebundle', w); log.debug('bundling'); w.bundle(function(err, content) { if (err) { log.error('bundle error'); log.error(String(err)); } w.emit('bundled', err, content); }); }, bundleDelay); w.bundleFile = function(file, done) { var absolutePath = path.resolve(file.path), relativePath = path.relative(config.basePath, absolutePath); // add file log.debug('updating %s in bundle', relativePath); // add the file during next prebundle step w.once('prebundle', function() { w.require('./' + relativePath, { expose: absolutePath }); }); deferredBundle(function(err) { var stub = 'typeof require === "function" && require("' + escape(absolutePath) + '");'; done(err, stub); }); }; /** * Wait for the bundle creation to have stabilized (no more additions) and invoke a callback. * * @param {Function} [callback] invoked with (err, content) */ w.deferredBundle = deferredBundle; return w; }
function ready (viewModel, container, route) { var weeklyCompiler = global.weeklyCompiler; var weeklyIssue = viewModel.issue; var editing = viewModel.editing; var released = editing && weeklyIssue.status === 'released'; var editor = $.findOne('.wa-editor', container); var toolbox = $.findOne('.wa-toolbox', container); var tools = $('.wa-tool', toolbox); var slug = $('.wa-slug'); var status = $('.wa-status'); var summaryEditor = $.findOne('.wa-summary-editor', container); var summary = $('.wa-summary'); var email = $('#wa-campaign-email'); var tweet = $('#wa-campaign-tweet'); var fb = $('#wa-campaign-fb'); var echojs = $('#wa-campaign-echojs'); var hn = $('#wa-campaign-hn'); var lobsters = $('#wa-campaign-lobsters'); var toggleSectionsButton = $('.wa-toggle-sections'); var discardButton = $('.wa-discard'); var saveButton = $('.wa-save'); var preview = $('.wa-preview'); var previewHtml = $('.wy-content', preview); var drakeTools = dragula([editor, toolbox], { moves: toolMoves, copy: true }); var drakeSort = dragula([editor], { moves: editorSectionMoves }); var updatePreviewSlowly = raf.bind(null, debounce(updatePreview, 100)); var scrapeLinkSlowly = debounce(scrapeLink, 500); var scraping = true; $(document.documentElement).on('keyup', cancellations); $(editor) .on('click', '.wa-section-remove', removeSection) .on('click', '.wa-section-toggle', toggleSection) .on('click', '.wa-section-clone', cloneSection) .on('change', '.wa-color-picker', pickedColor) .on('change', '.wa-header-background', updateLinkColors) .on('change keypress keydown paste input', '.wa-link-href', function (e) { scrapeLinkSlowly(e.target); }) .on('click', '.wa-link-toggle-tags', toggleTags) .and(summaryEditor) .on('change keypress keydown paste input', 'input,textarea,select', updatePreviewSlowly); drakeSort.on('drop', updatePreviewSlowly); drakeTools .on('cloned', clonedTool) .on('drop', droppedTool); status.on('change', updatePublication); tools.on('click', pickedTool); discardButton.on('click', discard); saveButton.on('click', save); toggleSectionsButton.on('click', toggleSections); $('.wa-scraper').on('click', toggleScraping); updatePublication(); updatePreview(); function toggleSections () { var sections = $('.wa-section', editor).but('[data-tool="header"]'); var contents = sections.find('.wa-section-contents'); var hidden = contents.where('.uv-hidden'); if (hidden.length === contents.length) { contents.removeClass('uv-hidden'); } else { contents.addClass('uv-hidden'); } } function updatePublication () { if (released) { saveButton.find('.bt-text').text('Save Changes'); saveButton.parent().attr('aria-label', 'Make your modifications immediately accessible!'); discardButton.text('Delete Issue'); discardButton.attr('aria-label', 'Permanently delete this weekly issue'); return; } var state = status.where(':checked').text(); if (state === 'draft') { saveButton.find('.bt-text').text('Save Draft'); saveButton.parent().attr('aria-label', 'You can access your drafts at any time'); return; } if (state === 'ready') { saveButton.find('.bt-text').text('Save & Mark Ready'); saveButton.parent().attr('aria-label', 'Schedule this weekly issue for publication next thursday!'); } } function updatePreview () { weeklyCompiler.compile(getModel().sections, { markdown: markdownService }, compiled); function compiled (err, html) { if (err) { html = textService.format('<pre class="wa-error">%s</pre>', err); } previewHtml.html(html); var previewSummary = $('.wy-section-summary', preview); var summaryHtml = markdownService.compile(summary.value()); previewSummary.html(summaryHtml); updateLinkSections(); } } function updateLinkSections () { $('.wa-section').where('[data-tool="link"]').forEach(function (el) { var $linkPreview = $('.wa-link-preview', el); var $title = $('.wa-link-title', el); var $image = $('.wa-link-image', el); var $imagePreview = $('.wa-link-image-preview', el); var title = markdownService.compile($title.value()).replace(rparagraph, ''); var summary = summaryService.summarize(title, 30).html.trim(); var postfix = summary ? ' – ' + summary : ''; var imageValue = $image.value().trim(); $linkPreview.html(postfix); $imagePreview.attr('src', imageValue); if (imageValue.length) { $imagePreview.removeClass('uv-hidden'); } else { $imagePreview.addClass('uv-hidden'); } }); } function updateLinkColors (e) { var $el = $(e.target); var $header = $el.parents('.wa-section'); var color = $el.value(); var $link = $header; do { $link = $link.next('[data-tool="link"]'); $link.find('.wa-link-foreground').value(color); } while ($link.length); updatePreview(); } function toolMoves (el, source) { return source === toolbox; } function editorSectionMoves (el, source, handle) { var $handle = $(handle); return ( $handle.hasClass('wa-section-header') || $handle.hasClass('wa-section-heading') || $handle.parents('.wa-section-heading').length > 0 ); } function removeSection (e) { $(e.target).parents('.wa-section').remove(); updatePreviewSlowly(); } function toggleSection (e) { var toggler = $(e.target); var content = toggler.parents('.wa-section').find('.wa-section-contents'); toggleUsingButton(content, toggler, ['fa-compress', 'fa-expand']); } function toggleTags (e) { var toggler = $(e.target); var content = toggler.parents('.wa-section').find('.wa-link-tag-list'); toggleUsingButton(content, toggler, ['fa-flip-horizontal', 'fa-rotate-90']); } function toggleUsingButton (content, button, classes) { if (content.hasClass('uv-hidden')) { content.removeClass('uv-hidden'); button.removeClass(classes[1]); button.addClass(classes[0]); } else { content.addClass('uv-hidden'); button.addClass(classes[1]); button.removeClass(classes[0]); } } function clonedTool (clone) { $(clone).addClass('wa-section-header'); } function cancellations (e) { if (e.which === 27) { drakeTools.cancel(true); drakeSort.cancel(true); } } function pickedColor (e) { var select = $(e.target); var color = select.value(); select .parents('.wa-color-picker') .find(select.attr('data-target')) .css('color', color); } function droppedTool (el, target) { if (target !== editor) { return; } var tool = $(el); var toolName = tool.attr('data-tool'); var action = 'author/weeklies/tool-' + toolName; insertingPartial(taunus.partial.replace(el, action, { knownTags: viewModel.knownTags, section: getDefaultSectionModel(toolName) })); } function pickedTool (e) { var tool = $(e.target); var toolName = tool.attr('data-tool'); var action = 'author/weeklies/tool-' + toolName; insertingPartial(taunus.partial.appendTo(editor, action, { knownTags: viewModel.knownTags, section: getDefaultSectionModel(toolName) })); e.preventDefault(); e.stopPropagation(); } function getDefaultSectionModel (toolName) { if (toolName === 'link') { return { sourceHref: 'https://twitter.com/' }; } return {}; } function cloneSection (e) { var section = $(e.target).parents('.wa-section'); var toolName = section.attr('data-tool'); var action = 'author/weeklies/tool-' + toolName; var model = getSectionModel(section); insertingPartial(taunus.partial.afterOf(section[0], action, { knownTags: viewModel.knownTags, section: model })); } function insertingPartial (partial) { partial .on('render', displayDetails) .on('render', updatePreviewSlowly); function displayDetails (html, container) { displayLinkDetails(container); } } function displayLinkDetails (container) { $('.wa-section-contents', container).removeClass('uv-hidden'); } function getSectionModel (section) { var mappers = { header: getHeaderSectionModel, markdown: getMarkdownSectionModel, link: getLinkSectionModel, styles: getStylesSectionModel }; var type = $(section).attr('data-tool'); return mappers[type](section); } function getHeaderSectionModel (section) { return { type: 'header', size: parseInt($('.wa-header-size', section).value(), 10), text: $('.wa-header-text', section).value(), foreground: $('.wa-header-foreground', section).value(), background: $('.wa-header-background', section).value() }; } function getMarkdownSectionModel (section) { return { type: 'markdown', text: $('.wa-markdown-text', section).value() }; } function getLinkSectionModel (section) { var unknownTags = textService.splitTags($('.wa-link-tags', section).value()); var knownTags = $('.wa-link-tag', section).filter(byChecked).map(toValue).filter(unique); return { type: 'link', title: $('.wa-link-title', section).value(), href: $('.wa-link-href', section).value(), foreground: $('.wa-link-foreground', section).value(), background: $('.wa-link-background', section).value(), source: $('.wa-link-source', section).value(), sourceHref: $('.wa-link-source-href', section).value(), image: $('.wa-link-image', section).value(), sponsored: $('.wa-link-sponsored', section).value(), tags: unknownTags.concat(knownTags), description: $('.wa-link-description', section).value() }; function byChecked (el) { return $(el).value(); } function toValue (el) { return $(el).text(); } function unique (tag) { return unknownTags.indexOf(tag) === -1; } } function getStylesSectionModel (section) { return { type: 'styles', styles: $('.wa-styles-text', section).value() }; } function getModel () { var state = released ? weeklyIssue.status : status.where(':checked').text(); var data = { slug: sluggish(slug.value()), sections: $('.wa-section', editor).map(getSectionModel), status: state, summary: summary.value(), email: email.value(), tweet: tweet.value(), fb: fb.value(), echojs: echojs.value(), hn: hn.value(), lobsters: lobsters.value() }; return data; } function toggleScraping (e) { scraping = !scraping; if (scraping) { $(e.target).removeClass('wa-toggler-off'); } else { $(e.target).addClass('wa-toggler-off'); } } function scrapeLink (el) { if (scraping === false) { return; } var $el = $(el); var $parent = $el.parent('.wa-section-contents'); var old = $el.attr('data-value'); var url = $el.value().trim(); $el.attr('data-value', url); if (url.length === 0 || url === old) { return; } var options = { url: '/api/metadata/scrape?url=' + url, json: true }; taunus.xhr(options, scraped); function scraped (err, data) { if (err) { return; } var firstImage = data.images[0] || ''; var description = (data.description || '').trim(); var sourceHref = 'https://twitter.com/' + (data.twitter ? data.twitter.slice(1) : ''); var imageInput = $('.wa-link-image', $parent); var imageInputContainer = $('.wa-link-image-container', $parent); updateInputs(); updateImageSwapper(); updatePreview(); function updateInputs () { $('.wa-link-title', $parent).value(data.title || ''); $('.wa-link-description', $parent).value(description); $('.wa-link-source', $parent).value(data.source || ''); $('.wa-link-source-href', $parent).value(sourceHref); $('.wa-link-image', $parent).value(firstImage); $('.wa-link-tags', $parent).value(''); $('.wa-link-tag', $parent).value(false); $('.wa-link-sponsored', $parent).value(false); } function updateImageSwapper () { var swapper = data.images.length > 1; if (swapper) { swapperOn(); } else { swapperOff(); } } function swapperOff () { $('.wa-toggler', imageInputContainer) .addClass('uv-hidden') .off('click'); } function swapperOn () { var togglerLeft = $('.wa-link-image-left', imageInputContainer); var togglerRight = $('.wa-link-image-right', imageInputContainer); var index = 0; togglerLeft.addClass('wa-toggler-off'); togglerRight.removeClass('wa-toggler-off'); $('.wa-toggler', imageInputContainer) .removeClass('uv-hidden') .on('click', swap); function swap (e) { var $el = $(e.target); if ($el.hasClass('wa-toggler-off')) { return; } var left = e.target === togglerLeft[0]; index += left ? -1 : 1; imageInput.value(data.images[index] || ''); invalidate(-1, togglerLeft); invalidate(1, togglerRight); updatePreview(); } function invalidate (offset, $el) { var on = typeof data.images[index + offset] === 'string'; var op = on ? 'removeClass' : 'addClass'; $el[op]('wa-toggler-off'); } } } } function save () { send({ json: getModel() }); } function send (data) { var req; if (editing) { req = viewModel.measly.patch('/api/weeklies/' + route.params.slug, data); } else { req = viewModel.measly.put('/api/weeklies', data); } req.on('data', leave); } function discard () { var name = route.params.slug ? '/weeklies/' + route.params.slug : 'draft'; var confirmation = confirm('About to discard ' + name + ', are you sure?'); if (!confirmation) { return; } if (editing) { viewModel.measly.delete('/api/weeklies/' + route.params.slug).on('data', leave); } else { leave(); } } function leave () { taunus.navigate('/author/weeklies'); } }
'use strict'; var debounce = require('lodash/function/debounce'); var contra = require('contra'); var feedService = require('./feed'); var weeklyFeedService = require('./weeklyFeed'); var articleFeedService = require('./articleFeed'); var fullFeed = feedService.from({ id: 'all', href: '/all/feed', title: 'Pony Foo', description: 'Latest feed items published on Pony Foo', getFeed: getFeed }); var rebuildSlowly = debounce(fullFeed.rebuild, 4000); weeklyFeedService.on('built', rebuildSlowly); articleFeedService.on('built', rebuildSlowly); function getFeed (done) { contra.concurrent({ weekly: contra.curry(weeklyFeedService.getFeed), articles: contra.curry(articleFeedService.getFeed) }, merge); function merge (err, result) { if (err) { done(err); return; } done(null, result.weekly.concat(result.articles)); } }
function main(){ var graphics = doc.graphics; var width = 180; var height = 100; var dotRadius = 2; var partyLabel = { width: 38, height: 10 }; var margin = { top: partyLabel.height, left: dotRadius, bottom: partyLabel.height / 2, right: partyLabel.width }; var slopeHeight = height - (margin.top + margin.bottom); var slopeWidth = width - (margin.left + margin.right); var slopeScale = d3.scale.linear() .domain([0,76]) .range([slopeHeight,0]); var layout = graphics.slope.layout() .start(function(d){ return d.resultnow; }) .end(function(d){ return d.resultprediction; }); var SVGSlope = graphics.slope.svg() .width(slopeWidth) .radius(dotRadius) .endClass(function(d){ return ' end-point ' + parties.className(d.data.party); }) .startClass(function(d){ return parties.className(d.data.party) + ' start-point'; }) .slopeClass(function(d){ return parties.className(d.data.party) + ' slope'; }) .labelClass(function(d){ return parties.className(d.data.party) + ' slope-label'; }) .label(function(d,i){ if( d.data.winner ){ return parties.shortName(d.data.party); } }) .scale(slopeScale); var slopeContainers = d3.selectAll('.constituency-group__slope-graphic').datum( function(){ var datum = doc.data.constituencyLookup[this.dataset.constituency]; datum.axes = (Number(this.dataset.order) === 0); return datum; }); slopeContainers.append('svg').attr({ class: 'slope-chart', 'data-constituency': function(d) { return d.id; }, width: width, height: height }) .append('g').attr({ transform: 'translate(' + margin.left + ',' + margin.top + ')' }) .each(function(d,i){ if(d.axes){ var axis = d3.select(this).append('g') .attr({ class:'slope-axes' }).selectAll('g').data(['Last vote','Polling']) .enter() .append('g') .attr({ 'transform':function(d,i){ return 'translate('+(i*width)+',0)'; }, 'class':'slope-axis' }); axis.append('line').attr({ class:'axis-line', x1:0, y1:3, x2:0, y2:height }); axis.append('text') .attr({ 'class':'axis-label' }) .text(function(d){ return d; }); } d3.select(this).selectAll('g.slope') .data( layout(d.parties) ) .call(SVGSlope, d.axes); }); redrawSlopes(); var resize = debounce(function(e) { redrawSlopes(); }, 200); window.addEventListener('resize', resize, false); function redrawSlopes(){ //Resize the SVG var el = d3.select('.constituency-group__slope-graphic').node(); var size = el.getBoundingClientRect(); var overhang = 12; slopeWidth = size.width + overhang - (margin.left + margin.right); slopeHeight = size.height - (margin.top + margin.bottom); slopeScale.range([slopeHeight,0]); SVGSlope .width(slopeWidth) .scale(slopeScale); d3.selectAll('svg.slope-chart').each(function(d, i) { var w = slopeWidth + margin.left + margin.right; var h = slopeHeight + margin.top + margin.bottom; var svg = d3.select(this); svg.selectAll('g.slope-axis') .attr('transform',function(d,i){ return 'translate('+(i*slopeWidth)+',0)'; }); svg.selectAll('g.slope').call(SVGSlope.reposition); svg.attr({ width: w, height: h }); }); } //decorate the results table d3.select('.result-table') .call(doc.graphics.resultTableDecorator); //decorate the coalition table d3.select('.coalition-table') .call(doc.graphics.coalitionsTableDecorator); //load and draw the map d3.json(mapData,function(map){ d3.selectAll('.constituency-group__locator-map-ratio').datum( function(){ return battlegrounds[this.dataset.group]; }).each(function(g,i){ var locator = graphics.constituencyLocator() .width(this.offsetWidth) .height(this.offsetHeight) .map(map) .locations(g.constituencies); d3.select(this).call(locator); }); }); }