diff options
author | André Fabian Silva Delgado <emulatorman@parabola.nu> | 2016-07-15 15:33:36 -0300 |
---|---|---|
committer | André Fabian Silva Delgado <emulatorman@parabola.nu> | 2016-07-15 15:33:36 -0300 |
commit | a5f917bbc55e295896b8084f6657eb8b6abaf8a8 (patch) | |
tree | 83dca14378e45b11fe6bbf1d17e64505dff43cbd /extensions/TimedMediaHandler/resources | |
parent | a1d705e541e0d10baa6bb03935ffd38d9478d0e6 (diff) |
Add TimedMediaHandler extension that allows display audio and video files in wiki pages, using the same syntax as for image files
Diffstat (limited to 'extensions/TimedMediaHandler/resources')
13 files changed, 693 insertions, 0 deletions
diff --git a/extensions/TimedMediaHandler/resources/PopUpThumbVideo.css b/extensions/TimedMediaHandler/resources/PopUpThumbVideo.css new file mode 100644 index 00000000..3ba0572a --- /dev/null +++ b/extensions/TimedMediaHandler/resources/PopUpThumbVideo.css @@ -0,0 +1,29 @@ +.PopUpMediaTransform a .play-btn-large{ + position : absolute; + top: 50%; + left : 50%; + width: 70px; + height: 53px; + margin-left: -35px; + margin-top: -25px; + /* @embed */ + background-image:url('player_big_play_button.png'); +} +.PopUpMediaTransform a .play-btn-large :hover{ + /* @embed */ + background-image:url('player_big_play_button_hover.png'); +} +.PopUpMediaTransform { + position : relative; + display: inline-block; +} +/* Should hopefully be only visible to screen readers */ +.mw-tmh-playtext { + display: block; + height: 0; + overflow: hidden; +} + +li.gallerybox div.thumb div.PopUpMediaTransform { + margin: 0 auto; +} diff --git a/extensions/TimedMediaHandler/resources/download_sprite.png b/extensions/TimedMediaHandler/resources/download_sprite.png Binary files differnew file mode 100644 index 00000000..541d4a99 --- /dev/null +++ b/extensions/TimedMediaHandler/resources/download_sprite.png diff --git a/extensions/TimedMediaHandler/resources/embedPlayerIframe.css b/extensions/TimedMediaHandler/resources/embedPlayerIframe.css new file mode 100644 index 00000000..eb6e9003 --- /dev/null +++ b/extensions/TimedMediaHandler/resources/embedPlayerIframe.css @@ -0,0 +1,7 @@ +body { + margin-left: 0px; + margin-top: 0px; + margin-right: 0px; + margin-bottom: 0px; + overflow: hidden; +} diff --git a/extensions/TimedMediaHandler/resources/ext.tmh.OgvJsSupport.js b/extensions/TimedMediaHandler/resources/ext.tmh.OgvJsSupport.js new file mode 100644 index 00000000..af3fd9f5 --- /dev/null +++ b/extensions/TimedMediaHandler/resources/ext.tmh.OgvJsSupport.js @@ -0,0 +1,67 @@ +( function( $, mw ) { + + var support = mw.OgvJsSupport = { + /** + * Ensure that the OGVPlayer class is loaded before continuing. + * + * @return jQuery.Deferred + */ + loadOgvJs: function() { + return $.Deferred( function( deferred ) { + if ( typeof OGVPlayer === 'undefined' ) { + mw.loader.using( 'ext.tmh.OgvJs', function() { + OGVLoader.base = support.basePath(); + deferred.resolve(); + } ); + } else { + deferred.resolve(); + } + }); + }, + + /** + * Get the base path of ogv.js and friends. + * + * @return string + */ + basePath: function() { + var ext = mw.config.get( 'wgExtensionAssetsPath' ), + binPlayers = ext + '/TimedMediaHandler/MwEmbedModules/EmbedPlayer/binPlayers'; + return binPlayers + '/ogv.js'; + }, + + /** + * Return a stub audio context + * + * This is used for iOS Safari to enable Web Audio by triggering an empty + * audio output channel during a user input event handler. Without that, + * audio is left disabled and won't work when we start things up after an + * asynchronous code load. + * + * @return AudioContext + */ + initAudioContext: function() { + var AudioContext = window.AudioContext || window.webkitAudioContext; + if ( AudioContext ) { + var context = new AudioContext(), + node; + if ( context.createScriptProcessor ) { + node = context.createScriptProcessor( 1024, 0, 2 ); + } else if ( context.createJavaScriptNode ) { + node = context.createJavaScriptNode( 1024, 0, 2 ); + } else { + throw new Error( 'Bad version of web audio API?' ); + } + + // Don't actually run any audio, just start & stop the node + node.connect( context.destination ); + node.disconnect(); + + return context; + } else { + return null; + } + } + }; + +} )( jQuery, mediaWiki ); diff --git a/extensions/TimedMediaHandler/resources/ext.tmh.TimedTextSelector.js b/extensions/TimedMediaHandler/resources/ext.tmh.TimedTextSelector.js new file mode 100644 index 00000000..b53bb6f8 --- /dev/null +++ b/extensions/TimedMediaHandler/resources/ext.tmh.TimedTextSelector.js @@ -0,0 +1,8 @@ +( function ( $, mw ) { + $( function () { + $( '#timedmedia-tt-go' ).click( function () { + window.location = mw.config.get( 'wgScript' ) + '?title=' + mw.util.wikiUrlencode( mw.config.get( 'wgPageName' ) ) + '.' + $( '#timedmedia-tt-input' ).val() + '.srt&action=edit'; + } ); + } ); + +} )( jQuery, mediaWiki ); diff --git a/extensions/TimedMediaHandler/resources/ext.tmh.transcodetable.js b/extensions/TimedMediaHandler/resources/ext.tmh.transcodetable.js new file mode 100644 index 00000000..a8c8f98d --- /dev/null +++ b/extensions/TimedMediaHandler/resources/ext.tmh.transcodetable.js @@ -0,0 +1,90 @@ +/** +* Javascript to support transcode table on image page +*/ +( function ( mw, $ ) { + $( document ).ready( function () { + var errorPopup, $errorLink; + + errorPopup = function () { + // pop up dialog + mw.addDialog( { + 'width': '640', + 'height': '480', + 'title': $(this).attr( 'title' ), + 'content': $('<textarea />') + .css( { + 'width':'99%', + 'height':'99%' + } ) + .text( $(this).attr('data-error') ) + } ) + .css( 'overflow', 'hidden' ); + return false; + }; + + // Old version. Need to keep for a little while in case of cached pages. + $( '.mw-filepage-transcodestatus .errorlink' ).click( errorPopup ); + // New version. + $errorLink = $( '.mw-filepage-transcodestatus .mw-tmh-pseudo-error-link' ); + $errorLink.wrapInner( function () { + var $this = $( this ); + return $( '<a />' ).attr( { + href: '#', + title: $this.text(), + 'data-error': $this.attr( 'data-error' ) + } ).click( errorPopup ); + } ); + + // Reset transcode action: + $( '.mw-filepage-transcodereset a' ).click( function () { + var tKey = $( this ).attr( 'data-transcodekey' ), + buttons = {}; + + buttons[ mw.msg( 'mwe-ok' ) ] = function () { + var api, + _thisDialog = this, + cancelBtn = {}; + + // Only show cancel button while loading: + cancelBtn[ mw.msg( 'mwe-cancel' ) ] = function () { + $(this).dialog( 'close' ); + }; + $( _thisDialog ).dialog( 'option', 'buttons', cancelBtn ); + + $( this ).loadingSpinner(); + + api = new mw.Api(); + api.postWithEditToken( { + 'action' : 'transcodereset', + 'transcodekey' : tKey, + 'title' : mw.config.get('wgPageName') + } ).done( function () { + // Refresh the page + location.reload(); + } ).fail( function ( code, data ) { + if( data.error && data.error.info ){ + $( _thisDialog ).text( data.error.info ); + } else { + $( _thisDialog ).text( mw.msg( 'timedmedia-reset-error' ) ); + } + var okBtn = {}; + okBtn[ mw.msg('mwe-ok') ] = function() { $(this).dialog( 'close' ); }; + $( _thisDialog ).dialog( 'option', 'buttons', okBtn ); + } ); + }; + buttons[ mw.msg( 'mwe-cancel' ) ] = function () { + $( this ).dialog( 'close' ); + }; + // pop up dialog + mw.addDialog( { + 'width': '400', + 'height': '200', + 'title': mw.msg( 'timedmedia-reset' ), + 'content': mw.msg( 'timedmedia-reset-confirm' ), + 'buttons': buttons + } ) + .css( 'overflow', 'hidden' ); + return false; + }); + }); +} )( mediaWiki, jQuery ); diff --git a/extensions/TimedMediaHandler/resources/mw.MediaWikiPlayer.loader.js b/extensions/TimedMediaHandler/resources/mw.MediaWikiPlayer.loader.js new file mode 100644 index 00000000..6167418b --- /dev/null +++ b/extensions/TimedMediaHandler/resources/mw.MediaWikiPlayer.loader.js @@ -0,0 +1,8 @@ +( function ( mw, $ ) { + // Add MediaWikiSupportPlayer dependency on players with a mediaWiki title + $( mw ).bind( 'EmbedPlayerUpdateDependencies', function ( event, embedPlayer, dependencySet ) { + if ( $( embedPlayer ).attr( 'data-mwtitle' ) ) { + $.merge( dependencySet, ['mw.MediaWikiPlayerSupport'] ); + } + } ); +} )( mediaWiki, jQuery ); diff --git a/extensions/TimedMediaHandler/resources/mw.MediaWikiPlayerSupport.js b/extensions/TimedMediaHandler/resources/mw.MediaWikiPlayerSupport.js new file mode 100644 index 00000000..16ce367c --- /dev/null +++ b/extensions/TimedMediaHandler/resources/mw.MediaWikiPlayerSupport.js @@ -0,0 +1,380 @@ +( function ( mw, $ ) { + /** + * Merge in the default video attributes supported by embedPlayer: + */ + mw.mergeConfig( 'EmbedPlayer.Attributes', { + // A apiTitleKey for looking up subtitles, credits and related videos + 'data-mwtitle': null, + + // The apiProvider where to lookup the title key + 'data-mwprovider': null + } ); + + // Add mediaWiki player support to target embedPlayer + $( mw ).bind( 'EmbedPlayerNewPlayer', function ( event, embedPlayer ) { + mw.addMediaWikiPlayerSupport( embedPlayer ); + }); + + /** + * Closure function wraps mediaWiki embedPlayer bindings + */ + mw.addMediaWikiPlayerSupport = function ( embedPlayer ) { + var apiTitleKey, apiProvider, $creditsCache = false; + // Set some local variables: + if ( !embedPlayer['data-mwtitle'] ) { + return false; + } else { + apiTitleKey = embedPlayer['data-mwtitle']; + // legacy support ( set as attribute ) + embedPlayer.apiTitleKey = apiTitleKey; + } + // Set local apiProvider via config if not defined + apiProvider = embedPlayer['data-mwprovider']; + if ( !apiProvider ) { + apiProvider = mw.config.get( 'EmbedPlayer.ApiProvider' ); + } + + /** + * Loads mediaWiki sources for a given embedPlayer + * @param {function} callback Function called once player sources have been added + */ + function loadPlayerSources( callback ) { + // Setup the request + var request = { + 'prop': 'imageinfo', + // In case the user added File: or Image: to the apiKey: + 'titles': 'File:' + decodeURIComponent( apiTitleKey ).replace( /^(File:|Image:)/, '' ), + 'iiprop': 'url|size|dimensions|metadata', + 'iiurlwidth': embedPlayer.getWidth(), + 'redirects': true // automatically resolve redirects + }; + + // Run the request: + mw.getJSON( mw.getApiProviderURL( apiProvider ), request, function ( data ) { + var i, page, imageinfo; + if ( data.query.pages ) { + for ( i in data.query.pages ) { + if ( i === '-1' ) { + callback( false ); + return ; + } + page = data.query.pages[i]; + } + } else { + callback( false ); + return ; + } + // Make sure we have imageinfo: + if ( !page.imageinfo || !page.imageinfo[0] ) { + callback( false ); + return ; + } + imageinfo = page.imageinfo[0]; + + // TODO these should call public methods rather than update internals: + + // Update the poster + embedPlayer.poster = imageinfo.thumburl; + + // Add the media src + embedPlayer.mediaElement.tryAddSource( + $( '<source />' ) + .attr( 'src', imageinfo.url ) + .get( 0 ) + ); + + // Set the duration + if ( imageinfo.metadata[2].name === 'length' ) { + embedPlayer.duration = imageinfo.metadata[2].value; + } + + // Set the width height + // Make sure we have an accurate aspect ratio + if ( imageinfo.height !== 0 && imageinfo.width !== 0 ) { + embedPlayer.height = Math.floor( embedPlayer.width * ( imageinfo.height / imageinfo.width ) ); + } + + // Update the css for the player interface + $( embedPlayer ).css( 'height', embedPlayer.height ); + + callback(); + }); + } + + /** + * Build a clip credit from the resource wikiText page + * + * TODO parse the resource page template + * + * @param {String} resourceHTML Resource wiki text page contents + */ + function doCreditLine( resourceHTML, articleUrl ) { + var authUrl, $page, $author, $authorText, $links, $date, $authorLink, + imgSize = {}, + // Get the title string ( again a "Title" like js object could help out here. ) + titleStr = embedPlayer.apiTitleKey.replace( /_/g, ' ' ), + // Setup the initial credits line: + $creditLine = $( '<div />' ); + + // Add the title: + $creditLine.append( + $( '<span>' ).html( + mw.msg( 'mwe-embedplayer-credit-title', + // get the link + $( '<div>' ).append( + $( '<a/>' ).attr( { + 'href': articleUrl, + 'title': titleStr + } ) + .text( titleStr ) + )[0].innerHTML + ) + ) + ); + + // Parse some data from the page info template if possible: + $page = $( resourceHTML ); + + // Look for author: + $author = $page.find( '#fileinfotpl_aut' ); + if ( $author.length ) { + // Get the real author sibling of fileinfotpl_aut + $authorText = $author.next(); + // Remove white space: + $authorText.find( 'br' ).remove(); + + // Update link to be absolute per page url context: + $links = $authorText.find( 'a' ); + if ( $links.length ) { + $links.each( function ( i, authorLink ) { + $authorLink = $( authorLink ); + authUrl = $authorLink.attr( 'href' ); + authUrl = mw.absoluteUrl( authUrl, articleUrl ); + $authorLink.attr( 'href', authUrl ); + }); + } + $creditLine.append( $( '<br />' ), + mw.msg( 'mwe-embedplayer-credit-author', $authorText.html() ) + ); + } + + // Look for date: + $date = $page.find( '#fileinfotpl_date' ); + if ( $date.length ) { + // Get the real date sibling of fileinfotpl_date + $date = $date.next(); + + // remove white space: + $date.find( 'br' ).remove(); + $creditLine.append( $( '<br />' ), + mw.msg( 'mwe-embedplayer-credit-date', $date.html() ) + ); + } + + // Build out the image and credit line + if ( embedPlayer.isAudio() ) { + imgSize.height = imgSize.width = ( embedPlayer.controlBuilder.getOverlayWidth() < 250 ) ? 45 : 80; + } else { + imgSize.width = ( embedPlayer.controlBuilder.getOverlayWidth() < 250 ) ? 45 : 120; + imgSize.height = Math.floor( imgSize.width * ( embedPlayer.getHeight() / embedPlayer.getWidth() ) ); + } + return $( '<div/>' ).addClass( 'creditline' ) + .append( + $( '<a/>' ).attr( { + 'href': articleUrl, + 'title': titleStr + } ).html( + $( '<img/>' ).attr( { + 'border': 0, + 'src': embedPlayer.poster + } ).css( imgSize ) + ) + ) + .append( + $creditLine + ); + } + + /** + * Issues a request to populate the credits box + */ + function showCredits( $target, callback ) { + var apiUrl, fileTitle, request; + if ( $creditsCache ) { + $target.html( $creditsCache ); + callback( true ); + return; + } + // Setup shortcuts: + apiUrl = mw.getApiProviderURL( apiProvider ); + fileTitle = 'File:' + decodeURIComponent( apiTitleKey ).replace( /^File:|^Image:/, ''); + + // Get the image page ( cache for 1 hour ) + request = { + 'action': 'parse', + 'page': fileTitle, + 'smaxage': 3600, + 'maxage': 3600 + }; + mw.getJSON( apiUrl, request, function ( data ) { + var descUrl = apiUrl.replace( 'api.php', 'index.php'); + descUrl += '?title=' + encodeURIComponent( fileTitle ); + if ( data && data.parse && data.parse.text && data.parse.text['*'] ) { + // TODO improve provider 'concept' to support page title link + $creditsCache = doCreditLine( data.parse.text['*'], descUrl ); + } else { + $creditsCache = doCreditLine( false, descUrl ); + } + $target.html( $creditsCache ); + callback( true ); + } ); + } + /** + * Adds embedPlayer Bindings + */ + + // Show credits when requested + $( embedPlayer ).bindQueueCallback( 'showCredits', function ( $target, callback ) { + if ( $target.data( 'playerId') !== embedPlayer.id ) { + // bad event trigger + return ; + } + // Only request the credits once: + showCredits( $target, callback ); + }); + + // Show credits on clip complete: + $( embedPlayer ).bind( 'onEndedDone', function ( event, id ) { + if ( embedPlayer.id !== id ) { + // possible event trigger error. ( skip ) + return ; + } + // dont show credits for audio elements, + // seek to begining instead + if ( embedPlayer.isAudio() ) { + embedPlayer.setCurrentTime( 0 ); + return ; + } + var cb = embedPlayer.controlBuilder; + cb.checkMenuOverlay(); + cb.showMenuOverlay(); + cb.showMenuItem( 'credits' ); + }); + + $( embedPlayer ).bind( 'showInlineDownloadLink', function () { + // Add recommend HTML5 player if we have non-native playback: + if ( embedPlayer.controlBuilder.checkNativeWarning( ) ) { + embedPlayer.controlBuilder.addWarningBinding( + 'EmbedPlayer.ShowNativeWarning', + mw.msg( 'mwe-embedplayer-for_best_experience', + $( '<div>' ).append( + $( '<a />' ).attr({ + 'href': 'http://www.mediawiki.org/wiki/Extension:TimedMediaHandler/Client_download', + 'target': '_new' + }) + )[0].innerHTML + ), + true + ); + } + }); + + $( embedPlayer ).bind( 'TimedText_BuildCCMenu', function ( event, $menu, id ) { + var _this, + pageTitle, + addTextPage, + $li; + if ( id !== embedPlayer.id ) { + _this = $( '#' + id )[0].timedText; + embedPlayer = _this.embedPlayer; + } + // Put in the "Make Transcript" link if config enabled and we have an api key + if ( embedPlayer.apiTitleKey ) { + // check if not already there: + if ( $menu.find( '.add-timed-text' ).length ) { + // add text link already present + return ; + } + + pageTitle = 'TimedText:' + + decodeURIComponent( embedPlayer.apiTitleKey ).replace( /^File:|^Image:/, '' ); + addTextPage = mw.getApiProviderURL( apiProvider ) + .replace( 'api.php', 'index.php') + + '?title=' + encodeURIComponent( pageTitle ); + + $li = $.getLineItem( mw.msg( 'mwe-timedtext-upload-timed-text'), 'script', function () { + window.location = addTextPage; + }); + + $li.addClass( 'add-timed-text') + .find( 'a' ) + .attr( { + 'href': addTextPage, + 'target': '_new' + } ); + $menu.append( + $li + ); + } + }); + + $( embedPlayer ).bindQueueCallback( 'checkPlayerSourcesEvent', function ( callback ) { + // Only load source if none are available: + if ( embedPlayer.mediaElement.sources.length === 0 ) { + loadPlayerSources( callback ); + } else { + // No source to load, issue callback directly + callback(); + } + } ); + $( mw ).bindQueueCallback( 'TimedText_LoadTextSource', function ( source, callback ) { + if ( !source.mwtitle || !source.mwprovider ) { + callback(); + return ; + } + // Load via api + var apiUrl = mw.getApiProviderURL( source.mwprovider ), + // Get the image page ( cache for 1 hour ) + request = { + 'action': 'parse', + 'page': source.mwtitle, + 'smaxage': 3600, + 'maxage': 3600 + }; + mw.getJSON( apiUrl, request, function ( data ) { + if ( data && data.parse && data.parse.text && data.parse.text['*'] ) { + source.loaded = true; + source.mimeType = 'text/mw-srt'; + source.captions = source.getCaptions( data.parse.text['*'] ); + callback(); + } else { + mw.log( 'Error: MediaWiki api error in getting timed text:', data ); + callback(); + } + }); + }); + + $( embedPlayer ).bind( 'getShareIframeSrc', function ( event, callback, id ) { + if ( id !== embedPlayer.id ) { + embedPlayer = $( '#' + id )[0]; + } + var iframeUrl = false; + // Do a special check for wikimediacommons provider as a known shared reop + if ( embedPlayer['data-mwprovider'] === 'wikimediacommons' ) { + iframeUrl = '//commons.wikimedia.org/wiki/File:' + decodeURIComponent( embedPlayer.apiTitleKey ).replace( /^(File:|Image:)/, '' ); + } else { + // use the local wiki: + if ( mw.config.get( 'wgServer' ) && mw.config.get( 'wgArticlePath' ) ) { + iframeUrl = mw.config.get( 'wgServer' ) + + mw.config.get( 'wgArticlePath' ).replace( /\$1/, 'File:' + + decodeURIComponent( embedPlayer.apiTitleKey ).replace( /^(File:|Image:)/, '' ) ); + } + } + if ( iframeUrl ) { + iframeUrl += '?embedplayer=yes'; + } + callback( iframeUrl ); + }); + }; + +} )( mediaWiki, jQuery ); diff --git a/extensions/TimedMediaHandler/resources/mw.PopUpThumbVideo.js b/extensions/TimedMediaHandler/resources/mw.PopUpThumbVideo.js new file mode 100644 index 00000000..c0aa30df --- /dev/null +++ b/extensions/TimedMediaHandler/resources/mw.PopUpThumbVideo.js @@ -0,0 +1,44 @@ +/** +* Simple script to add pop-up video dialog link support for video thumbnails +*/ +( function ( mw, $ ) { + $( document ).ready( function () { + $('.PopUpMediaTransform a').each( function () { + var link, title, + parent = $( this ).parent(); + if ( parent.attr( 'videopayload' ) ) { + $( this ).click( function ( /*event*/ ) { + var thisref = this; + + mw.loader.using( 'mw.MwEmbedSupport', function () { + var $videoContainer = $( $( thisref ).parent().attr( 'videopayload' ) ); + mw.addDialog({ + 'width': 'auto', + 'height': 'auto', + 'title': mw.html.escape( $videoContainer.find( 'video, audio' ).attr( 'data-mwtitle' ) ), + 'content': $videoContainer, + 'close': function(){ + // On close destroy the dialog rather than just hiding it, + // so it doesn't eat up resources or keep playing. + $( this ).remove(); + return true; + }, + 'open': function() { + $( this ).find( 'video, audio' ).embedPlayer(); + } + }) + .css( 'overflow', 'hidden' ); + } ); + // don't follow file link + return false; + } ); + } else if ( parent.attr( 'data-videopayload' ) ) { + link = $( this ).attr( 'href' ); + title = mw.Title.newFromImg( { src: link } ); + if ( title && title.getPrefixedDb() !== mw.config.get( 'wgPageName' ) ) { + $( this ).attr( 'href', title.getUrl() ); + } + } /* else fall back to linking directly to media file */ + } ); + } ); +} )( mediaWiki, jQuery ); diff --git a/extensions/TimedMediaHandler/resources/mw.TMHGalleryHook.js b/extensions/TimedMediaHandler/resources/mw.TMHGalleryHook.js new file mode 100644 index 00000000..fd23690e --- /dev/null +++ b/extensions/TimedMediaHandler/resources/mw.TMHGalleryHook.js @@ -0,0 +1,46 @@ +/** +* Simple script to add pop-up video dialog link support for video thumbnails +*/ +( function ( mw ) { + // Hook to allow dynamically resizing videos in image galleries + mw.hook( 'mediawiki.page.gallery.resize' ).add( function ( info ) { + var $mwPlayerContainer, + $popUp, + $tmhVideo, + $mwContainer = info.$imageDiv.find( '.mediaContainer' ); + if ( info.resolved ) { + // Everything is already done here. + return; + } + + $mwContainer = info.$imageDiv.find( '.mediaContainer' ); + if ( $mwContainer.length ) { + // Add some padding, so caption doesn't overlap video controls if + // we are overlaying the caption on top of the image. + if ( !info.$outerDiv.parent().hasClass( 'mw-gallery-packed' ) ) { + info.$outerDiv.find( 'div.gallerytext' ).css( 'padding-bottom', '20px' ); + } + + info.$imageDiv.width( info.imgWidth ); + $mwContainer.width( info.imgWidth ); + $mwPlayerContainer = $mwContainer.children( '.mwPlayerContainer' ); + if ( $mwPlayerContainer.length ) { + // Case 1: HTML5 player already loaded + $mwPlayerContainer.width( info.imgWidth ).height( info.imgHeight ); + $mwPlayerContainer.find( 'img.playerPoster' ).width( info.imgWidth ).height( info.imgHeight ); + } else { + // Case 2: Raw video element + $tmhVideo = info.$imageDiv.find( 'video' ); + $tmhVideo.width( info.imgWidth ).height( info.imgHeight ); + } + info.resolved = true; + return; + } + + $popUp = info.$imageDiv.find( '.PopUpMediaTransform' ); + if ( $popUp.length ) { + info.$imageDiv.width( info.imgWidth ); + $popUp.add( $popUp.find( 'img' ) ).width( info.imgWidth ).height( info.imgHeight ); + } + } ); +} )( mediaWiki ); diff --git a/extensions/TimedMediaHandler/resources/player_big_play_button.png b/extensions/TimedMediaHandler/resources/player_big_play_button.png Binary files differnew file mode 100644 index 00000000..041fea9c --- /dev/null +++ b/extensions/TimedMediaHandler/resources/player_big_play_button.png diff --git a/extensions/TimedMediaHandler/resources/player_big_play_button_hover.png b/extensions/TimedMediaHandler/resources/player_big_play_button_hover.png Binary files differnew file mode 100644 index 00000000..3517563e --- /dev/null +++ b/extensions/TimedMediaHandler/resources/player_big_play_button_hover.png diff --git a/extensions/TimedMediaHandler/resources/transcodeTable.css b/extensions/TimedMediaHandler/resources/transcodeTable.css new file mode 100644 index 00000000..795ce134 --- /dev/null +++ b/extensions/TimedMediaHandler/resources/transcodeTable.css @@ -0,0 +1,14 @@ +.mw-filepage-transcodestatus .download-btn { + background-image: url('download_sprite.png'); + width: 49px; + height: 36px; + background-repeat:no-repeat; + background-position: -50px; +} +.mw-filepage-transcodestatus .download-btn:hover { + background-position: 0 0; +} +.mw-filepage-transcodestatus .download-btn span { + /* Text hidden by the above image */ + display: none; +} |