X-Git-Url: https://scripts.mit.edu/gitweb/autoinstalls/wordpress.git/blobdiff_plain/177fd6fefd2e3d5a0ea6591c71d660cabdb3c1a4..607b7e02d77e7326161e8ec15639052d2040f745:/wp-admin/js/common.js diff --git a/wp-admin/js/common.js b/wp-admin/js/common.js index 6559d7d2..200d3e47 100644 --- a/wp-admin/js/common.js +++ b/wp-admin/js/common.js @@ -1,45 +1,946 @@ -jQuery(document).ready( function() { - // pulse - jQuery('.fade').animate( { backgroundColor: '#ffffe0' }, 300).animate( { backgroundColor: '#fffbcc' }, 300).animate( { backgroundColor: '#ffffe0' }, 300).animate( { backgroundColor: '#fffbcc' }, 300); +/* global setUserSetting, ajaxurl, commonL10n, alert, confirm, pagenow */ +var showNotice, adminMenu, columns, validateForm, screenMeta; +( function( $, window, undefined ) { + var $document = $( document ), + $window = $( window ), + $body = $( document.body ); - // Reveal - jQuery('.wp-no-js-hidden').removeClass( 'wp-no-js-hidden' ); +// Removed in 3.3. +// (perhaps) needed for back-compat +adminMenu = { + init : function() {}, + fold : function() {}, + restoreMenuState : function() {}, + toggle : function() {}, + favorites : function() {} +}; - // Basic form validation - if ( ( 'undefined' != typeof wpAjax ) && jQuery.isFunction( wpAjax.validateForm ) ) { - jQuery('form.validate').submit( function() { return wpAjax.validateForm( jQuery(this) ); } ); +// show/hide/save table columns +columns = { + init : function() { + var that = this; + $('.hide-column-tog', '#adv-settings').click( function() { + var $t = $(this), column = $t.val(); + if ( $t.prop('checked') ) + that.checked(column); + else + that.unchecked(column); + + columns.saveManageColumnsState(); + }); + }, + + saveManageColumnsState : function() { + var hidden = this.hidden(); + $.post(ajaxurl, { + action: 'hidden-columns', + hidden: hidden, + screenoptionnonce: $('#screenoptionnonce').val(), + page: pagenow + }); + }, + + checked : function(column) { + $('.column-' + column).removeClass( 'hidden' ); + this.colSpanChange(+1); + }, + + unchecked : function(column) { + $('.column-' + column).addClass( 'hidden' ); + this.colSpanChange(-1); + }, + + hidden : function() { + return $( '.manage-column[id]' ).filter( ':hidden' ).map(function() { + return this.id; + }).get().join( ',' ); + }, + + useCheckboxesForHidden : function() { + this.hidden = function(){ + return $('.hide-column-tog').not(':checked').map(function() { + var id = this.id; + return id.substring( id, id.length - 5 ); + }).get().join(','); + }; + }, + + colSpanChange : function(diff) { + var $t = $('table').find('.colspanchange'), n; + if ( !$t.length ) + return; + n = parseInt( $t.attr('colspan'), 10 ) + diff; + $t.attr('colspan', n.toString()); } +}; + +$document.ready(function(){columns.init();}); + +validateForm = function( form ) { + return !$( form ) + .find( '.form-required' ) + .filter( function() { return $( 'input:visible', this ).val() === ''; } ) + .addClass( 'form-invalid' ) + .find( 'input:visible' ) + .change( function() { $( this ).closest( '.form-invalid' ).removeClass( 'form-invalid' ); } ) + .length; +}; + +// stub for doing better warnings +showNotice = { + warn : function() { + var msg = commonL10n.warnDelete || ''; + if ( confirm(msg) ) { + return true; + } + + return false; + }, + + note : function(text) { + alert(text); + } +}; + +screenMeta = { + element: null, // #screen-meta + toggles: null, // .screen-meta-toggle + page: null, // #wpcontent + + init: function() { + this.element = $('#screen-meta'); + this.toggles = $( '#screen-meta-links' ).find( '.show-settings' ); + this.page = $('#wpcontent'); + + this.toggles.click( this.toggleEvent ); + }, + + toggleEvent: function() { + var panel = $( '#' + $( this ).attr( 'aria-controls' ) ); + + if ( !panel.length ) + return; + + if ( panel.is(':visible') ) + screenMeta.close( panel, $(this) ); + else + screenMeta.open( panel, $(this) ); + }, + + open: function( panel, button ) { + + $( '#screen-meta-links' ).find( '.screen-meta-toggle' ).not( button.parent() ).css( 'visibility', 'hidden' ); + + panel.parent().show(); + panel.slideDown( 'fast', function() { + panel.focus(); + button.addClass( 'screen-meta-active' ).attr( 'aria-expanded', true ); + }); + + $document.trigger( 'screen:options:open' ); + }, + + close: function( panel, button ) { + panel.slideUp( 'fast', function() { + button.removeClass( 'screen-meta-active' ).attr( 'aria-expanded', false ); + $('.screen-meta-toggle').css('visibility', ''); + panel.parent().hide(); + }); + + $document.trigger( 'screen:options:close' ); + } +}; + +/** + * Help tabs. + */ +$('.contextual-help-tabs').delegate('a', 'click', function(e) { + var link = $(this), + panel; + + e.preventDefault(); + + // Don't do anything if the click is for the tab already showing. + if ( link.is('.active a') ) + return false; + + // Links + $('.contextual-help-tabs .active').removeClass('active'); + link.parent('li').addClass('active'); + + panel = $( link.attr('href') ); + + // Panels + $('.help-tab-content').not( panel ).removeClass('active').hide(); + panel.addClass('active').show(); }); -(function(JQ) { - JQ.fn.tTips = function() { +$document.ready( function() { + var checks, first, last, checked, sliced, mobileEvent, transitionTimeout, focusedRowActions, + lastClicked = false, + pageInput = $('input.current-page'), + currentPage = pageInput.val(), + isIOS = /iPhone|iPad|iPod/.test( navigator.userAgent ), + isAndroid = navigator.userAgent.indexOf( 'Android' ) !== -1, + isIE8 = $( document.documentElement ).hasClass( 'ie8' ), + $adminMenuWrap = $( '#adminmenuwrap' ), + $wpwrap = $( '#wpwrap' ), + $adminmenu = $( '#adminmenu' ), + $overlay = $( '#wp-responsive-overlay' ), + $toolbar = $( '#wp-toolbar' ), + $toolbarPopups = $toolbar.find( 'a[aria-haspopup="true"]' ), + $sortables = $('.meta-box-sortables'), + wpResponsiveActive = false, + $adminbar = $( '#wpadminbar' ), + lastScrollPosition = 0, + pinnedMenuTop = false, + pinnedMenuBottom = false, + menuTop = 0, + menuIsPinned = false, + height = { + window: $window.height(), + wpwrap: $wpwrap.height(), + adminbar: $adminbar.height(), + menu: $adminMenuWrap.height() + }; + + + // when the menu is folded, make the fly-out submenu header clickable + $adminmenu.on('click.wp-submenu-head', '.wp-submenu-head', function(e){ + $(e.target).parent().siblings('a').get(0).click(); + }); + + $('#collapse-menu').on('click.collapse-menu', function() { + var respWidth, state; + + // reset any compensation for submenus near the bottom of the screen + $('#adminmenu div.wp-submenu').css('margin-top', ''); + + if ( window.innerWidth ) { + // window.innerWidth is affected by zooming on phones + respWidth = Math.max( window.innerWidth, document.documentElement.clientWidth ); + } else { + // IE < 9 doesn't support @media CSS rules + respWidth = 961; + } + + if ( respWidth && respWidth < 960 ) { + if ( $body.hasClass('auto-fold') ) { + $body.removeClass('auto-fold').removeClass('folded'); + setUserSetting('unfold', 1); + setUserSetting('mfold', 'o'); + state = 'open'; + } else { + $body.addClass('auto-fold'); + setUserSetting('unfold', 0); + state = 'folded'; + } + } else { + if ( $body.hasClass('folded') ) { + $body.removeClass('folded'); + setUserSetting('mfold', 'o'); + state = 'open'; + } else { + $body.addClass('folded'); + setUserSetting('mfold', 'f'); + state = 'folded'; + } + } + + currentMenuItemHasPopup(); + $document.trigger( 'wp-collapse-menu', { state: state } ); + }); + + // Handle the `aria-haspopup` attribute on the current menu item when it has a sub-menu. + function currentMenuItemHasPopup() { + var respWidth, + $current = $( 'a.wp-has-current-submenu' ); + + if ( window.innerWidth ) { + respWidth = Math.max( window.innerWidth, document.documentElement.clientWidth ); + } else { + respWidth = 961; + } + + if ( $body.hasClass( 'folded' ) || ( $body.hasClass( 'auto-fold' ) && respWidth && respWidth <= 960 && respWidth > 782 ) ) { + // When folded or auto-folded and not responsive view, the current menu item does have a fly-out sub-menu. + $current.attr( 'aria-haspopup', 'true' ); + } else { + // When expanded or in responsive view, reset aria-haspopup. + $current.attr( 'aria-haspopup', 'false' ); + } + } + + $document.on( 'wp-window-resized wp-responsive-activate wp-responsive-deactivate', currentMenuItemHasPopup ); + + /** + * Ensure an admin submenu is within the visual viewport. + * + * @since 4.1.0 + * + * @param {jQuery} $menuItem The parent menu item containing the submenu. + */ + function adjustSubmenu( $menuItem ) { + var bottomOffset, pageHeight, adjustment, theFold, menutop, wintop, maxtop, + $submenu = $menuItem.find( '.wp-submenu' ); + + menutop = $menuItem.offset().top; + wintop = $window.scrollTop(); + maxtop = menutop - wintop - 30; // max = make the top of the sub almost touch admin bar + + bottomOffset = menutop + $submenu.height() + 1; // Bottom offset of the menu + pageHeight = $wpwrap.height(); // Height of the entire page + adjustment = 60 + bottomOffset - pageHeight; + theFold = $window.height() + wintop - 50; // The fold + + if ( theFold < ( bottomOffset - adjustment ) ) { + adjustment = bottomOffset - theFold; + } + + if ( adjustment > maxtop ) { + adjustment = maxtop; + } + + if ( adjustment > 1 ) { + $submenu.css( 'margin-top', '-' + adjustment + 'px' ); + } else { + $submenu.css( 'margin-top', '' ); + } + } + + if ( 'ontouchstart' in window || /IEMobile\/[1-9]/.test(navigator.userAgent) ) { // touch screen device + // iOS Safari works with touchstart, the rest work with click + mobileEvent = isIOS ? 'touchstart' : 'click'; + + // close any open submenus when touch/click is not on the menu + $body.on( mobileEvent+'.wp-mobile-hover', function(e) { + if ( $adminmenu.data('wp-responsive') ) { + return; + } + + if ( ! $( e.target ).closest( '#adminmenu' ).length ) { + $adminmenu.find( 'li.opensub' ).removeClass( 'opensub' ); + } + }); + + $adminmenu.find( 'a.wp-has-submenu' ).on( mobileEvent + '.wp-mobile-hover', function( event ) { + var $menuItem = $(this).parent(); + + if ( $adminmenu.data( 'wp-responsive' ) ) { + return; + } + + // Show the sub instead of following the link if: + // - the submenu is not open + // - the submenu is not shown inline or the menu is not folded + if ( ! $menuItem.hasClass( 'opensub' ) && ( ! $menuItem.hasClass( 'wp-menu-open' ) || $menuItem.width() < 40 ) ) { + event.preventDefault(); + adjustSubmenu( $menuItem ); + $adminmenu.find( 'li.opensub' ).removeClass( 'opensub' ); + $menuItem.addClass('opensub'); + } + }); + } + + if ( ! isIOS && ! isAndroid ) { + $adminmenu.find( 'li.wp-has-submenu' ).hoverIntent({ + over: function() { + var $menuItem = $( this ), + $submenu = $menuItem.find( '.wp-submenu' ), + top = parseInt( $submenu.css( 'top' ), 10 ); + + if ( isNaN( top ) || top > -5 ) { // the submenu is visible + return; + } + + if ( $adminmenu.data( 'wp-responsive' ) ) { + // The menu is in responsive mode, bail + return; + } + + adjustSubmenu( $menuItem ); + $adminmenu.find( 'li.opensub' ).removeClass( 'opensub' ); + $menuItem.addClass( 'opensub' ); + }, + out: function(){ + if ( $adminmenu.data( 'wp-responsive' ) ) { + // The menu is in responsive mode, bail + return; + } + + $( this ).removeClass( 'opensub' ).find( '.wp-submenu' ).css( 'margin-top', '' ); + }, + timeout: 200, + sensitivity: 7, + interval: 90 + }); + + $adminmenu.on( 'focus.adminmenu', '.wp-submenu a', function( event ) { + if ( $adminmenu.data( 'wp-responsive' ) ) { + // The menu is in responsive mode, bail + return; + } + + $( event.target ).closest( 'li.menu-top' ).addClass( 'opensub' ); + }).on( 'blur.adminmenu', '.wp-submenu a', function( event ) { + if ( $adminmenu.data( 'wp-responsive' ) ) { + return; + } + + $( event.target ).closest( 'li.menu-top' ).removeClass( 'opensub' ); + }).find( 'li.wp-has-submenu.wp-not-current-submenu' ).on( 'focusin.adminmenu', function() { + adjustSubmenu( $( this ) ); + }); + } + + /* + * The `.below-h2` class is here just for backward compatibility with plugins + * that are (incorrectly) using it. Do not use. Use `.inline` instead. See #34570. + */ + $( 'div.updated, div.error, div.notice' ).not( '.inline, .below-h2' ).insertAfter( $( '.wrap h1, .wrap h2' ).first() ); + + // Make notices dismissible + function makeNoticesDismissible() { + $( '.notice.is-dismissible' ).each( function() { + var $el = $( this ), + $button = $( '' ), + btnText = commonL10n.dismiss || ''; + + // Ensure plain text + $button.find( '.screen-reader-text' ).text( btnText ); + $button.on( 'click.wp-dismiss-notice', function( event ) { + event.preventDefault(); + $el.fadeTo( 100, 0, function() { + $el.slideUp( 100, function() { + $el.remove(); + }); + }); + }); + + $el.append( $button ); + }); + } + + $document.on( 'wp-updates-notice-added wp-plugin-install-error wp-plugin-update-error wp-plugin-delete-error wp-theme-install-error wp-theme-delete-error', makeNoticesDismissible ); + + // Init screen meta + screenMeta.init(); + + // check all checkboxes + $('tbody').children().children('.check-column').find(':checkbox').click( function(e) { + if ( 'undefined' == e.shiftKey ) { return true; } + if ( e.shiftKey ) { + if ( !lastClicked ) { return true; } + checks = $( lastClicked ).closest( 'form' ).find( ':checkbox' ).filter( ':visible:enabled' ); + first = checks.index( lastClicked ); + last = checks.index( this ); + checked = $(this).prop('checked'); + if ( 0 < first && 0 < last && first != last ) { + sliced = ( last > first ) ? checks.slice( first, last ) : checks.slice( last, first ); + sliced.prop( 'checked', function() { + if ( $(this).closest('tr').is(':visible') ) + return checked; + + return false; + }); + } + } + lastClicked = this; + + // toggle "check all" checkboxes + var unchecked = $(this).closest('tbody').find(':checkbox').filter(':visible:enabled').not(':checked'); + $(this).closest('table').children('thead, tfoot').find(':checkbox').prop('checked', function() { + return ( 0 === unchecked.length ); + }); + + return true; + }); + + $('thead, tfoot').find('.check-column :checkbox').on( 'click.wp-toggle-checkboxes', function( event ) { + var $this = $(this), + $table = $this.closest( 'table' ), + controlChecked = $this.prop('checked'), + toggle = event.shiftKey || $this.data('wp-toggle'); - JQ('body').append('