{"version":3,"sources":["webpack://mfModules.[name]/./src/mobile.categories.overlays/CategoryAddOverlay.js","webpack://mfModules.[name]/./src/mobile.categories.overlays/CategoryGateway.js","webpack://mfModules.[name]/./src/mobile.categories.overlays/CategoryLookupInputWidget.js","webpack://mfModules.[name]/./src/mobile.categories.overlays/CategoryTabs.js","webpack://mfModules.[name]/./src/mobile.categories.overlays/categoryOverlay.js","webpack://mfModules.[name]/./src/mobile.categories.overlays/mobile.categories.overlays.js"],"names":["Overlay","require","mfExtend","util","CategoryGateway","CategoryLookupInputWidget","icons","toast","router","mw","loader","CategoryAddOverlay","options","heading","msg","title","this","eventBus","call","extend","className","events","click .save","click .suggestion","defaults","prototype","waitMsg","waitIcon","spinner","toHtmlString","template","get","templatePartials","header","saveHeader","postRender","input","apply","$suggestions","$el","find","$saveButton","wgCategories","categories","gateway","api","suggestions","saveButton","append","$element","onCategoryClick","ev","target","closest","detach","length","prop","onSaveClick","newCategories","self","showHidden","each","data","show","type","save","then","navigate","notify","$safeButton","module","exports","actionParams","SearchGateway","parent","arguments","continueParams","canContinue","searchNamespace","postWithToken","action","appendtext","summary","getCategories","params","titles","clprop","cllimit","undefined","continue","OO","inheritClass","placeholder","ui","TextInputWidget","mixin","LookupElement","mixinClass","onLookupMenuItemChoose","button","ButtonWidget","icon","label","classes","flags","attr","getLookupRequest","search","value","getLookupCacheDataFromResponse","response","Title","results","unshift","toString","displayTitle","getNameText","getLookupMenuOptionsFromData","result","forEach","indexOf","push","MenuOptionWidget","View","ScrollEndEventEmitter","CategoryTabs","scrollEndEventEmitter","on","EVENT_SCROLL_END","_loadCategories","bind","click .catlink","isTemplateMode","normalcatlink","hiddencatlink","item","hideSpinner","hide","showSpinner","apiResult","$normalCatlist","$hiddenCatlist","setElement","disable","query","pages","page","category","newFromText","ns","hidden","render","url","getUrl","text","_changeView","enable","onCatlinkClick","preventDefault","hasClass","toggleClass","overlay","widget","headerButtons","isAnon","href","subheading","m","categoryOverlay","define"],"mappings":"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","file":"mobile.categories.overlays.js","sourcesContent":["var\n\tOverlay = require( '../mobile.startup/Overlay' ),\n\tmfExtend = require( '../mobile.startup/mfExtend' ),\n\tutil = require( '../mobile.startup/util' ),\n\tCategoryGateway = require( './CategoryGateway' ),\n\tCategoryLookupInputWidget = require( './CategoryLookupInputWidget' ),\n\ticons = require( '../mobile.startup/icons' ),\n\ttoast = require( '../mobile.startup/toast' ),\n\trouter = mw.loader.require( 'mediawiki.router' );\n\n/**\n * Displays the list of categories for a page\n * @class CategoryAddOverlay\n * @extends Overlay\n * @uses CategoryGateway\n * @param {Object} options Configuration options\n * @param {OO.EventEmitter} options.eventBus Object used to emit category-added events\n */\nfunction CategoryAddOverlay( options ) {\n\toptions.heading = mw.msg( 'mobile-frontend-categories-add-heading', options.title );\n\tthis.eventBus = options.eventBus;\n\tOverlay.call(\n\t\tthis,\n\t\tutil.extend(\n\t\t\ttrue,\n\t\t\t{\n\t\t\t\tclassName: 'category-overlay overlay',\n\t\t\t\tevents: {\n\t\t\t\t\t'click .save': 'onSaveClick',\n\t\t\t\t\t'click .suggestion': 'onCategoryClick'\n\t\t\t\t}\n\t\t\t},\n\t\t\toptions\n\t\t)\n\t);\n}\n\nmfExtend( CategoryAddOverlay, Overlay, {\n\t/**\n\t * @memberof CategoryAddOverlay\n\t * @instance\n\t * @mixes Overlay#defaults\n\t * @property {Object} defaults Default options hash.\n\t * @property {mw.Api} defaults.api to use to construct gateway\n\t * @property {string} defaults.waitMsg Text that displays while a page edit is being saved.\n\t * @property {string} defaults.waitIcon HTML of the icon that displays while a page edit\n\t * is being saved.\n\t */\n\tdefaults: util.extend( {}, Overlay.prototype.defaults, {\n\t\twaitMsg: mw.msg( 'mobile-frontend-categories-add-wait' ),\n\t\twaitIcon: icons.spinner().toHtmlString()\n\t} ),\n\t/**\n\t * @inheritdoc\n\t * @memberof CategoryAddOverlay\n\t * @instance\n\t */\n\ttemplate: mw.template.get( 'mobile.categories.overlays', 'CategoryAddOverlay.hogan' ),\n\t/**\n\t * @inheritdoc\n\t * @memberof CategoryAddOverlay\n\t * @instance\n\t */\n\ttemplatePartials: util.extend( {}, Overlay.prototype.templatePartials, {\n\t\theader: mw.template.get( 'mobile.categories.overlays', 'CategoryAddOverlayHeader.hogan' ),\n\t\tsaveHeader: mw.template.get( 'mobile.editor.overlay', 'saveHeader.hogan' )\n\t} ),\n\n\t/**\n\t * @inheritdoc\n\t * @memberof CategoryAddOverlay\n\t * @instance\n\t */\n\tpostRender: function () {\n\t\tvar input;\n\n\t\tOverlay.prototype.postRender.apply( this );\n\n\t\tthis.$suggestions = this.$el.find( '.category-suggestions' );\n\t\tthis.$saveButton = this.$el.find( '.save' );\n\t\tthis.wgCategories = this.options.categories;\n\t\tthis.title = this.options.title;\n\n\t\tthis.gateway = new CategoryGateway( this.options.api );\n\t\tinput = new CategoryLookupInputWidget( {\n\t\t\tgateway: this.gateway,\n\t\t\tsuggestions: this.$suggestions,\n\t\t\tcategories: this.wgCategories,\n\t\t\tsaveButton: this.$saveButton\n\t\t} );\n\t\tthis.$el.find( '.category-add-input' ).append(\n\t\t\tinput.$element\n\t\t);\n\t},\n\n\t/**\n\t * Handle a click on an added category\n\t * @memberof CategoryAddOverlay\n\t * @instance\n\t * @param {jQuery.Event} ev\n\t */\n\tonCategoryClick: function ( ev ) {\n\t\tthis.$el.find( ev.target ).closest( '.suggestion' ).detach();\n\t\tif ( this.$el.find( '.suggestion' ).length > 0 ) {\n\t\t\tthis.$saveButton.prop( 'disabled', false );\n\t\t} else {\n\t\t\tthis.$saveButton.prop( 'disabled', true );\n\t\t}\n\t},\n\n\t/**\n\t * Handle the click on the save button. Builds a string of new categories\n\t * and add it to the article.\n\t * @memberof CategoryAddOverlay\n\t * @instance\n\t */\n\tonSaveClick: function () {\n\t\tvar newCategories = '',\n\t\t\tself = this;\n\n\t\t// show the loading spinner and disable the safe button\n\t\tthis.showHidden( '.saving-header' );\n\n\t\t// add wikitext to add to the page\n\t\tthis.$el.find( '.suggestion' ).each( function () {\n\t\t\tvar data = self.$el.find( this ).data( 'title' );\n\n\t\t\tif ( data ) {\n\t\t\t\t// add the new categories in wikitext markup\n\t\t\t\tnewCategories += '\\n[[' + data + ']] ';\n\t\t\t}\n\t\t} );\n\n\t\t// if there are no categories added, don't do anything (the user shouldn't see the save\n\t\t// button)\n\t\tif ( newCategories.length === 0 ) {\n\t\t\ttoast.show( mw.msg( 'mobile-frontend-categories-nodata' ), { type: 'error' } );\n\t\t} else {\n\t\t\t// save the new categories\n\t\t\tthis.gateway.save( this.title, newCategories ).then( function () {\n\t\t\t\t// we're closing the overlay to show the user\n\t\t\t\t// that the action was completed successful\n\t\t\t\trouter.navigate( '#' );\n\t\t\t\tmw.notify( mw.msg( 'mobile-frontend-categories-notification' ) );\n\t\t\t}, function () {\n\t\t\t\tself.showHidden( '.initial-header' );\n\t\t\t\tself.$safeButton.prop( 'disabled', false );\n\t\t\t\t// FIXME: Should be a better error message\n\t\t\t\ttoast.show( mw.msg( 'mobile-frontend-categories-nodata' ), { type: 'error' } );\n\t\t\t} );\n\t\t}\n\t}\n} );\n\nmodule.exports = CategoryAddOverlay;\n","var\n\tprototype,\n\tactionParams = require( '../mobile.startup/actionParams' ),\n\tutil = require( '../mobile.startup/util' ),\n\tSearchGateway = require( '../mobile.startup/search/SearchGateway' );\n\n/**\n * Api for CategoryOverlay\n * @class CategoryGateway\n * @extends SearchGateway\n */\nfunction CategoryGateway() {\n\tCategoryGateway.parent.apply( this, arguments );\n}\nprototype = {\n\t/**\n\t * @memberof CategoryGateway\n\t * @instance\n\t */\n\tcontinueParams: {},\n\t/**\n\t * @memberof CategoryGateway\n\t * @instance\n\t */\n\tcanContinue: true,\n\t/**\n\t * @inheritdoc\n\t * @memberof CategoryGateway\n\t * @instance\n\t */\n\tsearchNamespace: 14,\n\t/**\n\t * Saves the categories passed to this function to the page\n\t * @memberof CategoryGateway\n\t * @instance\n\t * @param {string} title Title of the current page (to add the categories to)\n\t * @param {string} categories List of Categories to add\n\t * @return {jQuery.Deferred}\n\t */\n\tsave: function ( title, categories ) {\n\t\treturn this.api.postWithToken( 'csrf', {\n\t\t\taction: 'edit',\n\t\t\ttitle: title,\n\t\t\tappendtext: categories,\n\t\t\tsummary: mw.msg( 'mobile-frontend-categories-summary' )\n\t\t} );\n\t},\n\t/**\n\t * Returns the categories the title belongs to.\n\t * @memberof CategoryGateway\n\t * @instance\n\t * @param {string} title Title of the current page (to add the categories to)\n\t * @return {jQuery.Deferred|boolean} False, if no further continuation is possible,\n\t *                                   jQuery.Deferred otherwise.\n\t */\n\tgetCategories: function ( title ) {\n\t\tvar self = this, params;\n\n\t\tif ( this.canContinue === false ) {\n\t\t\treturn false;\n\t\t}\n\n\t\tparams = util.extend( {}, {\n\t\t\tprop: 'categories',\n\t\t\ttitles: title,\n\t\t\tclprop: 'hidden',\n\t\t\tcllimit: 50\n\t\t}, this.continueParams );\n\t\treturn this.api.get( actionParams( params ) ).then( function ( data ) {\n\t\t\tif ( data.continue !== undefined ) {\n\t\t\t\tself.continueParams = data.continue;\n\t\t\t} else {\n\t\t\t\tself.canContinue = false;\n\t\t\t}\n\n\t\t\treturn data;\n\t\t} );\n\t}\n};\n\nOO.inheritClass( CategoryGateway, SearchGateway );\nutil.extend( CategoryGateway.prototype, prototype );\n\nmodule.exports = CategoryGateway;\n","/**\n * @class CategoryLookupInputWidget\n * @extends OO.ui.mixin.LookupElement\n *\n * @param {Object} options Configuration options\n * @param {CategoryGateway} options.gateway to use to retrieve search results\n * @param {jQuery.Object} options.suggestions container element for search suggestions\n * @param {jQuery.Object} options.saveButton element. Will get disabled when suggested item\n *                                           clicked.\n */\nfunction CategoryLookupInputWidget( options ) {\n\t// Note: this.$element is set to $( '<div>' ) by OOUI.\n\tthis.gateway = options.gateway;\n\tthis.$suggestions = options.suggestions;\n\tthis.categories = options.categories || [];\n\tthis.$saveButton = options.saveButton;\n\toptions.placeholder = mw.msg( 'mobile-frontend-categories-search' );\n\tOO.ui.TextInputWidget.call( this, options );\n\tOO.ui.mixin.LookupElement.call( this, options );\n}\nOO.inheritClass( CategoryLookupInputWidget, OO.ui.TextInputWidget );\nOO.mixinClass( CategoryLookupInputWidget, OO.ui.mixin.LookupElement );\n\n/**\n * Handle a click on a suggested item. Add it to the list of added categories and show save\n * button.\n * @memberof CategoryLookupInputWidget\n * @instance\n * @param {Object} data Data of the clicked element\n */\nCategoryLookupInputWidget.prototype.onLookupMenuItemChoose = function ( data ) {\n\tvar button = new OO.ui.ButtonWidget( {\n\t\ticon: 'check',\n\t\tlabel: data.label,\n\t\tclasses: [ 'suggestion', 'suggested' ],\n\t\tflags: [ 'progressive', 'primary' ]\n\t} );\n\n\tbutton.$element.attr( 'data-title', data.data );\n\tthis.$suggestions.append( button.$element );\n\tthis.$saveButton.prop( 'disabled', false );\n};\n\n/**\n * Returns the result of the search request.\n * @memberof CategoryLookupInputWidget\n * @instance\n * @return {jQuery.Deferred}\n */\nCategoryLookupInputWidget.prototype.getLookupRequest = function () {\n\treturn this.gateway.search( this.value );\n};\n\n/**\n * Get lookup cache item from server response data.\n * @memberof CategoryLookupInputWidget\n * @instance\n * @param {Mixed} response Response from server\n * @return {Mixed} Cached result response\n */\nCategoryLookupInputWidget.prototype.getLookupCacheDataFromResponse = function ( response ) {\n\tvar title = new mw.Title( this.value, 14 );\n\n\t// add user input as a possible (actually not existing) category\n\tresponse.results.unshift( {\n\t\ttitle: title.toString(),\n\t\tdisplayTitle: title.getNameText()\n\t} );\n\n\treturn response;\n};\n\n/**\n * Get a list of menu item widgets from the data stored by the lookup request's done handler.\n * @memberof CategoryLookupInputWidget\n * @instance\n * @param {Mixed} data Cached result data, usually an array\n * @return {Array} Array of OO.ui.MenuOptionWidget\n */\nCategoryLookupInputWidget.prototype.getLookupMenuOptionsFromData = function ( data ) {\n\tvar result = [],\n\t\t$el = this.$element,\n\t\tself = this;\n\n\tdata.results.forEach( function ( value ) {\n\t\tif (\n\t\t\t!$el.find( 'div[data-title=\"' + value.title + '\"]' ).length &&\n\t\t\tself.categories.indexOf( value.displayTitle ) === -1\n\t\t) {\n\t\t\tresult.push(\n\t\t\t\tnew OO.ui.MenuOptionWidget( {\n\t\t\t\t\tdata: value.title,\n\t\t\t\t\tlabel: value.displayTitle\n\t\t\t\t} )\n\t\t\t);\n\t\t}\n\t} );\n\treturn result;\n};\n\nmodule.exports = CategoryLookupInputWidget;\n","var\n\tmfExtend = require( '../mobile.startup/mfExtend' ),\n\tutil = require( '../mobile.startup/util' ),\n\tView = require( '../mobile.startup/View' ),\n\tScrollEndEventEmitter = require( '../mobile.startup/ScrollEndEventEmitter' ),\n\tCategoryGateway = require( './CategoryGateway' );\n\n/**\n * Displays the list of categories for a page in two tabs\n * TODO: Break this into Tab and CategoryList components for better reuse.\n * @class CategoryTabs\n * @extends View\n * @uses CategoryGateway\n *\n * @param {Object} options Configuration options\n * @param {string} options.title of page to obtain categories for\n * @param {string} options.subheading for explaining the list of categories.\n * @param {mw.Api} options.api for use with CategoryGateway\n * @param {OO.EventEmitter} options.eventBus Object used to listen for category-added\n * and scroll:throttled events\n */\nfunction CategoryTabs( options ) {\n\tthis.scrollEndEventEmitter = new ScrollEndEventEmitter( options.eventBus );\n\tthis.scrollEndEventEmitter.on( ScrollEndEventEmitter.EVENT_SCROLL_END,\n\t\tthis._loadCategories.bind( this ) );\n\tthis.gateway = new CategoryGateway( options.api );\n\tView.call(\n\t\tthis,\n\t\tutil.extend(\n\t\t\ttrue,\n\t\t\t{ events: { 'click .catlink': 'onCatlinkClick' } },\n\t\t\toptions\n\t\t)\n\t);\n}\n\nmfExtend( CategoryTabs, View, {\n\tisTemplateMode: true,\n\t/**\n\t * @memberof CategoryTabs\n\t * @instance\n\t * @mixes View#defaults\n\t * @property {Object} defaults Default options hash.\n\t */\n\tdefaults: {\n\t\tnormalcatlink: mw.msg( 'mobile-frontend-categories-normal' ),\n\t\thiddencatlink: mw.msg( 'mobile-frontend-categories-hidden' )\n\t},\n\t/**\n\t * @inheritdoc\n\t * @memberof CategoryTabs\n\t * @instance\n\t */\n\ttemplate: mw.template.get( 'mobile.categories.overlays', 'CategoryTabs.hogan' ),\n\t/**\n\t * @inheritdoc\n\t * @memberof CategoryTabs\n\t * @instance\n\t */\n\ttemplatePartials: {\n\t\titem: mw.template.get( 'mobile.categories.overlays', 'CategoryTab.hogan' )\n\t},\n\t/**\n\t * @inheritdoc\n\t * @memberof CategoryTabs\n\t * @instance\n\t */\n\tpostRender: function () {\n\t\tView.prototype.postRender.apply( this );\n\t\tthis._loadCategories();\n\t},\n\n\t/**\n\t * @memberof CategoryTabs\n\t * @instance\n\t * @return {void}\n\t */\n\thideSpinner: function () {\n\t\tthis.$el.find( '.spinner' ).hide();\n\t},\n\t/**\n\t * @memberof CategoryTabs\n\t * @instance\n\t * @return {void}\n\t */\n\tshowSpinner: function () {\n\t\tthis.$el.find( '.spinner' ).show();\n\t},\n\t/**\n\t * Get a list of categories the page belongs to and re-renders the overlay content\n\t * FIXME: CategoryTabs should be dumb and solely focus on rendering. This should\n\t * be refactored out at the earliest opportunity.\n\t * @memberof CategoryTabs\n\t * @instance\n\t */\n\t_loadCategories: function () {\n\t\tvar self = this,\n\t\t\t$normalCatlist = this.$el.find( '.normal-catlist' ),\n\t\t\t$hiddenCatlist = this.$el.find( '.hidden-catlist' ),\n\t\t\tapiResult;\n\n\t\tthis.scrollEndEventEmitter.setElement( this.$el );\n\t\t// ScrollEndEventEmitter is enabled once it's created, but we want to wait, until at\n\t\t// least one element is in the list before we enable it. So disable it here and enable\n\t\t// once the elements are loaded.\n\t\tthis.scrollEndEventEmitter.disable();\n\t\tapiResult = this.gateway.getCategories( this.options.title );\n\t\tif ( apiResult === false ) {\n\t\t\tself.hideSpinner();\n\t\t\treturn;\n\t\t}\n\t\tapiResult.then( function ( data ) {\n\t\t\tif ( data.query && data.query.pages ) {\n\t\t\t\t// add categories to overlay\n\t\t\t\tdata.query.pages.forEach( function ( page ) {\n\t\t\t\t\tif ( page.categories ) {\n\t\t\t\t\t\tpage.categories.forEach( function ( category ) {\n\t\t\t\t\t\t\tvar title = mw.Title.newFromText( category.title, category.ns );\n\n\t\t\t\t\t\t\tif ( category.hidden ) {\n\t\t\t\t\t\t\t\t$hiddenCatlist.append( self.templatePartials.item.render( {\n\t\t\t\t\t\t\t\t\turl: title.getUrl(),\n\t\t\t\t\t\t\t\t\ttitle: title.getNameText()\n\t\t\t\t\t\t\t\t} ) );\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t$normalCatlist.append( self.templatePartials.item.render( {\n\t\t\t\t\t\t\t\t\turl: title.getUrl(),\n\t\t\t\t\t\t\t\t\ttitle: title.getNameText()\n\t\t\t\t\t\t\t\t} ) );\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} );\n\t\t\t\t\t}\n\t\t\t\t} );\n\n\t\t\t\tif ( $normalCatlist.length === 0 && $normalCatlist.length === 0 ) {\n\t\t\t\t\tself.$el.find( '.content-header' ).text( mw.msg( 'mobile-frontend-categories-nocat' ) );\n\t\t\t\t} else if ( $normalCatlist.length === 0 && $normalCatlist.length > 0 ) {\n\t\t\t\t\tthis._changeView();\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tself.$el.find( '.content-header' ).text( mw.msg( 'mobile-frontend-categories-nocat' ) );\n\t\t\t}\n\t\t\tself.hideSpinner();\n\t\t\tself.scrollEndEventEmitter.enable();\n\t\t} );\n\t},\n\n\t/**\n\t * Handles a click on one of the tabs to change the viewable categories\n\t * @memberof CategoryTabs\n\t * @instance\n\t * @param {jQuery.Event} ev The Event object triggered this handler\n\t */\n\tonCatlinkClick: function ( ev ) {\n\t\tev.preventDefault();\n\t\t// change view only, if the user clicked another view\n\t\tif ( !this.$el.find( ev.target ).parent().hasClass( 'selected' ) ) {\n\t\t\tthis._changeView();\n\t\t}\n\t},\n\n\t/**\n\t * Changes the view from hidden categories to content-based categories and vice-versa\n\t * @memberof CategoryTabs\n\t * @instance\n\t */\n\t_changeView: function () {\n\t\tthis.$el.find( '.category-header li' ).toggleClass( 'selected' );\n\t\tthis.$el.find( '.topic-title-list' ).toggleClass( 'hidden' );\n\t}\n} );\n\nmodule.exports = CategoryTabs;\n","var\n\tOverlay = require( '../mobile.startup/Overlay' ),\n\tCategoryTabs = require( './CategoryTabs' );\n\n/**\n * Gets an overlay for displaying categories\n *\n * @param {Object} options Configuration options\n * @param {string} options.title of page to obtain categories for\n * @param {mw.Api} options.api for usage in CategoryTabs\n * @param {string} options.subheading for usage in CategoryTabs\n * @param {OO.EventEmitter} options.eventBus Object used to listen for category-added\n * and scroll:throttled events\n * @return {Overlay}\n */\nfunction categoryOverlay( options ) {\n\tvar overlay, widget,\n\t\theaderButtons = options.isAnon ? [] :\n\t\t\t[ {\n\t\t\t\thref: '#/categories/add',\n\t\t\t\tclassName: 'add continue',\n\t\t\t\tmsg: mw.msg( 'mobile-frontend-categories-add' )\n\t\t\t} ];\n\toverlay = new Overlay( {\n\t\tclassName: 'category-overlay overlay',\n\t\theading: mw.msg( 'mobile-frontend-categories-heading' ),\n\t\theaderButtons: headerButtons\n\t} );\n\twidget = new CategoryTabs(\n\t\t{\n\t\t\teventBus: options.eventBus,\n\t\t\tapi: options.api,\n\t\t\ttitle: options.title,\n\t\t\tsubheading: mw.msg( 'mobile-frontend-categories-subheading' )\n\t\t}\n\t);\n\toverlay.$el.find( '.overlay-content' ).append( widget.$el );\n\treturn overlay;\n}\n\nmodule.exports = categoryOverlay;\n","var m = require( '../mobile.startup/moduleLoaderSingleton' ),\n\tCategoryAddOverlay = require( './CategoryAddOverlay' ),\n\tcategoryOverlay = require( './categoryOverlay' );\n\n// needed for minerva usages\nm.define( 'mobile.categories.overlays/CategoryAddOverlay', CategoryAddOverlay );\nm.define( 'mobile.categories.overlays/categoryOverlay', categoryOverlay );\n"],"sourceRoot":""}