WordPress.org

Make WordPress Core

Ticket #19815: 19815.8.diff

File 19815.8.diff, 7.3 KB (added by mikeschroder, 10 years ago)

Renamed class to ThemeScroller, caching more JQuery selectors, throttling scroll, using Deferred for AJAX calls, and general cleanup. Does not include 19815.7.diff [edit - get rid of stray propset]

  • wp-admin/js/theme.dev.js

     
    4545                        init: init
    4646                };
    4747
    48         return api;
     48        return api;
    4949        }
    5050})(jQuery);
    5151
     
    5454        theme_viewer.init();
    5555});
    5656
    57 var wpThemes;
     57var ThemeScroller;
    5858
    5959(function($){
    60         var inputs = {}, Query;
     60        ThemeScroller = {
     61                // Inputs
     62                nonce: '',
     63                search: '',
     64                tab: '',
     65                type: '',
     66                nextPage: 2,
     67                features: {},
    6168
    62         wpThemes = {
    63                 timeToTriggerQuery: 150,
    64                 minQueryAJAXDuration: 200,
     69                // Preferences
     70                scrollThrottleDelay: 250,
     71                failedRetryDelay: 4000,
    6572                outListBottomThreshold: 200,
     73
     74                // Flags
    6675                noMoreResults: false,
    67                
     76                scrolling: false,
     77                querying: false,
     78
    6879                init : function() {
     80                        var self = this,
     81                                startPage,
     82                                queryArray = {},
     83                                queryString = window.location.search;
     84
     85                        // We're using infinite scrolling, so hide all pagination.
    6986                        $('.pagination-links').hide();
    7087
    71                         inputs.nonce = $('#_ajax_fetch_list_nonce').val();
    72        
    73                         // Parse Query
    74                         inputs.queryString = window.location.search;                   
    75                         inputs.queryArray = wpThemes.parseQuery( inputs.queryString.substring( 1 ) );
     88                        // Parse GET query string
     89                        queryArray = this.parseQuery( queryString.substring( 1 ) );
    7690
    77                         // Handle Inputs from Query
    78                         inputs.search = inputs.queryArray['s'];
    79                         inputs.features = inputs.queryArray['features'];
    80                         inputs.startPage = parseInt( inputs.queryArray['paged'] );     
    81                         inputs.tab = inputs.queryArray['tab'];
    82                         inputs.type = inputs.queryArray['type'];
     91                        // Handle inputs
     92                        this.nonce = $('#_ajax_fetch_list_nonce').val();
     93                        this.search = queryArray['s'];
     94                        this.features = queryArray['features'];
     95                        this.tab = queryArray['tab'];
     96                        this.type = queryArray['type'];
    8397
    84                         if ( isNaN( inputs.startPage ) )
    85                                 inputs.startPage = 2;
    86                         else
    87                                 inputs.startPage++;
     98                        startPage = parseInt( queryArray['paged'] );
     99                        if ( !isNaN( startPage ) )
     100                                this.nextPage++;
    88101
    89                         // Cache jQuery objects
    90                         inputs.outList = $('#availablethemes');
    91                         inputs.waiting = $('div.tablenav.bottom').children( 'img.ajax-loading' );
    92                         inputs.window = $(window);
     102                        // Cache jQuery selectors
     103                        this.$outList = $('#availablethemes');
     104                        this.$spinner = $('div.tablenav.bottom').children( 'img.ajax-loading' );
     105                        this.$window = $(window);
     106                        this.$document = $(document);
    93107
    94                         // Generate Query
    95                         wpThemes.query = new Query();
    96 
    97108                        // Start Polling
    98                         inputs.window.scroll( function(){ wpThemes.maybeLoad(); } );
     109                        this.$window.scroll( function(){ self.scrolling = true; });
     110                        setInterval( function() {
     111                                if ( self.scrolling ) {
     112                                        self.scrolling = false;
     113                                        self.maybeLoad();
     114                                }
     115                        }, this.scrollThrottleDelay );
    99116                },
    100                 delayedCallback : function( func, delay ) {
    101                         var timeoutTriggered, funcTriggered, funcArgs, funcContext;
    102 
    103                         if ( ! delay )
    104                                 return func;
    105 
    106                         setTimeout( function() {
    107                                 if ( funcTriggered )
    108                                         return func.apply( funcContext, funcArgs );
    109                                 // Otherwise, wait.
    110                                 timeoutTriggered = true;
    111                         }, delay);
    112 
    113                         return function() {
    114                                 if ( timeoutTriggered )
    115                                         return func.apply( this, arguments );
    116                                 // Otherwise, wait.
    117                                 funcArgs = arguments;
    118                                 funcContext = this;
    119                                 funcTriggered = true;
    120                         };
    121                 },
    122                 ajax: function( callback ) {
    123                         var self = this,
    124                                 response = wpThemes.delayedCallback( function( results, params ) {
    125                                         self.process( results, params );
    126                                         if ( callback )
    127                                                 callback( results, params );
    128                                 }, wpThemes.minQueryAJAXDuration );
    129 
    130                         this.query.ajax( response );
    131                 },
    132                 process: function( results, params ) {
    133                         // If no Results, for now, mark as no Matches, and bail.
    134                         // Alternately: inputs.outList.append(wpThemesL10n.noMatchesFound);
     117                process: function( results ) {
    135118                        if ( ( results === undefined ) ||
    136                                  ( results.rows.indexOf( "no-items" ) != -1 ) ) {
     119                                ( results.rows.indexOf( "no-items" ) != -1 ) ) {
    137120                                this.noMoreResults = true;
    138121                        } else {
    139                                 inputs.outList.append( results.rows );
     122                                this.$outList.append( results.rows );
    140123                        }
    141124                },
    142125                maybeLoad: function() {
    143126                        var self = this,
    144                                 el = $(document),
    145                                 bottom = el.scrollTop() + inputs.window.innerHeight();
    146                                
     127                                bottom = this.$document.scrollTop() + this.$window.innerHeight();
     128
    147129                        if ( this.noMoreResults ||
    148                                  !this.query.ready() ||
    149                                  ( bottom < inputs.outList.height() - wpThemes.outListBottomThreshold ) )
     130                                this.querying ||
     131                                ( bottom < this.$outList.height() - this.outListBottomThreshold ) )
    150132                                return;
    151133
    152                         setTimeout( function() {
    153                                 var newTop = el.scrollTop(),
    154                                         newBottom = newTop + inputs.window.innerHeight();
     134                        this.querying = true;
     135                        var query = {
     136                                action: 'fetch-list',
     137                                tab: this.tab,
     138                                paged: this.nextPage,
     139                                s: this.search,
     140                                type: this.type,
     141                                _ajax_fetch_list_nonce: this.nonce,
     142                                'features[]': this.features,
     143                                'list_args': list_args
     144                        };
    155145
    156                                 if ( !self.query.ready() ||
    157                                          ( newBottom < inputs.outList.height() - wpThemes.outListBottomThreshold ) )
    158                                         return;
    159 
    160                                 inputs.waiting.css( 'visibility', 'visible' ); // Show Spinner
    161                                 self.ajax( function() { inputs.waiting.css( 'visibility', 'hidden' ) } ); // Hide Spinner
    162                                
    163                         }, wpThemes.timeToTriggerQuery );
     146                        this.$spinner.css( 'visibility', 'visible' );
     147                        $.getJSON( ajaxurl, query )
     148                                .done( function( response ) {
     149                                        self.nextPage++;
     150                                        self.process( response );
     151                                        self.$spinner.css( 'visibility', 'hidden' );
     152                                        self.querying = false;
     153                                })
     154                                .fail( function() {
     155                                        self.$spinner.css( 'visibility', 'hidden' );
     156                                        self.querying = false;
     157                                        setTimeout( function() { self.maybeLoad(); }, self.failedRetryDelay)
     158                                });
    164159                },
    165160                parseQuery: function( query ) {
    166161                        var Params = {};
    167                         if ( ! query ) {return Params;}// return empty object
     162                        if ( !query ) { return Params; }
    168163                        var Pairs = query.split(/[;&]/);
    169164                        for ( var i = 0; i < Pairs.length; i++ ) {
    170165                                var KeyVal = Pairs[i].split('=');
    171                                 if ( ! KeyVal || KeyVal.length != 2 ) {continue;}
     166                                if ( ! KeyVal || KeyVal.length != 2 ) { continue; }
    172167                                var key = unescape( KeyVal[0] );
    173168                                var val = unescape( KeyVal[1] );
    174169                                val = val.replace(/\+/g, ' ');
    175170                                key = key.replace(/\[.*\]$/g, '');
    176        
     171
    177172                                if ( Params[key] === undefined ) {
    178173                                        Params[key] = val;
    179174                                } else {
    180175                                        var oldVal = Params[key];
    181                                         if ( ! jQuery.isArray( Params[key] ) )
     176                                        if ( !jQuery.isArray( Params[key] ) )
    182177                                                Params[key] = new Array( oldVal, val );
    183178                                        else
    184179                                                Params[key].push( val );
     
    188183                }
    189184        }
    190185
    191         Query = function() {
    192                 this.failedRequest = false;
    193                 this.querying = false;
    194                 this.page = inputs.startPage;
    195         }
    196        
    197         $.extend( Query.prototype, {
    198                 ready: function() {
    199                         return !( this.querying || this.failedRequest );
    200                 },
    201                 ajax: function( callback ) {
    202                         var self = this,
    203                         query = {
    204                                 action: 'fetch-list',
    205                                 tab: inputs.tab,
    206                                 paged: this.page,
    207                                 s: inputs.search,
    208                                 type: inputs.type,
    209                                 _ajax_fetch_list_nonce: inputs.nonce,
    210                                 'features[]': inputs.features,
    211                                 'list_args': list_args
    212                         };
     186        $(document).ready( function($) { ThemeScroller.init(); });
    213187
    214                         this.querying = true;
    215                         $.get( ajaxurl, query, function(r) {
    216                                 self.page++;
    217                                 self.querying = false;
    218                                 self.failedRequest = !r;
    219                                 callback( r, query );
    220                         }, "json" );
    221                 }
    222         });
    223 
    224         $(document).ready( wpThemes.init );
    225 
    226188})(jQuery);