I think the title it's someway self-explaing: we know that when you add a video to a HTML field, SharePoint doesn't use HTML5 video tag, but it installs a web part which show the video itself using a player.
A video, in SharePoint, it's not simply a file, but a folder which contains that video file, maybe its renditions and other stuff i'm not interested in.
Video and assets generally are in a Asset Site which could be accessed from catalog, public site and many others.
If we want to simply use HTML5 video tag, we first need to find the correct video file, then we have to create a reusable content with these features:
Because i want the user to have a placeholder like this
Then include a JS (in master page or page layout: up to you) which:
A video, in SharePoint, it's not simply a file, but a folder which contains that video file, maybe its renditions and other stuff i'm not interested in.
Video and assets generally are in a Asset Site which could be accessed from catalog, public site and many others.
If we want to simply use HTML5 video tag, we first need to find the correct video file, then we have to create a reusable content with these features:
- User can select the video using the OOB AssetPicker
- Reusable content automatically finds the video file
- Reusable content automatically generates HTML5 video tag
Why in the world i'm using an img tag?
Because i want the user to have a placeholder like this
Then include a JS (in master page or page layout: up to you) which:
- Binds a click event to every asset_video class object
- On click opens OOB Asset Picker and let user choose an asset
- On Asset Picker close event, finds the video URL using REST
- Writes the HTML5 tag using the URL
jQuery(document).ready(function () { initAddVideoTemplate(); SP.SOD.executeOrDelayUntilScriptLoaded(function () { SP.SOD.executeOrDelayUntilScriptLoaded(function () { var ctx = SP.ClientContext.get_current(); var site = ctx.get_site(); ctx.load(site); }, "cui.js"); }, "sp.js"); }); // Adds a listener on every HTML element with class "asset_video" // You can add your own classes in this obj array, lister for all elements will be created // The listener will make asset picker to be opened when you click on a asset_video function initAddVideoTemplate() { var count = 0; var obj = { 'asset_video': '' } jQuery.each(obj, function (index, value) { jQuery('body').on('click', 'img[class="' + index + '"]', function () { var className = this.className; var idOldVideo = "reusableContentInsertVideo-" + rc_generateUUID(); this.setAttribute('id', idOldVideo); if (!count) { jQuery.getScript('/_layouts/15/AssetPickers.js', function () { insertVideo(idOldVideo, className, value); }); count += 1; } else insertVideo(idOldVideo, className, value); }); }); }; // Asset picker configuration function insertVideo(idOldVideo, className, value) { var assetPicker = new AssetPickerConfig(""); assetPicker.ClientID = ""; assetPicker.DefaultAssetLocation = ""; assetPicker.DefaultAssetImageLocation = ""; assetPicker.CurrentWebBaseUrl = ""; assetPicker.AllowExternalUrls = ""; assetPicker.ManageHyperlink = false; assetPicker.AssetUrlClientID = idOldVideo; assetPicker.AssetType = "Media"; assetPicker.ReturnItemFields = 'Title,Name,Label,SourceUrl,FileRef'; assetPicker.ReturnCallback = function () { // Self explaining variable names var video_AbsoluteUrl = arguments[0]; var video_FolderName = arguments[1]; var pathArray = video_AbsoluteUrl.split('/'); var assetSite_Url; var assetList_DocLib; if (pathArray.length >= 5) { assetSite_Url = pathArray[0] + "//" + pathArray[2]; assetList_DocLib = pathArray[3]; // Helps you to rebuild the folder relative URL for (i = 4; i < pathArray.length - 1; i++) { assetList_DocLib = assetList_DocLib + "/" + pathArray[i]; } // Finds the HTML img tag to substitute var idCalled = jQuery(this).attr('AssetUrlClientID'); if (undefined !== arguments && arguments.length > 3 && assetSite_Url !== undefined && assetList_DocLib !== undefined) { // REST url generation // Using URL and folder, you can request the first file of the video folder, which is the default video rendition restUrl = assetSite_Url + "/_api/Web/GetFolderByServerRelativeUrl('/" + assetList_DocLib + "/" + video_FolderName + "')/Files?$select=ServerRelativeUrl,Name&top=1"; jQuery.ajax({ url: restUrl, type: "GET", crossDomain: true, dataType: "json", headers: { "Accept": "application/json; odata=verbose" }, success: function (data) { // If success, generate che HTML var response = data.d.results; if (response.length > 0) { var videoUrl = assetSite_Url + response[0].ServerRelativeUrl; var fileName = response[0].Name; var extension = fileName.split('.').pop(); if (jQuery("#" + idCalled).length > 0) jQuery("#" + idCalled).first().replaceWith(""); } }, error: function (data) { alert('Error'); } }); } } else { alert("Error"); } }; var imageAsset = new LinkAsset(""); imageAsset.LaunchModalAssetPicker(assetPicker); }; // Generate a ID function rc_generateUUID() { var d = new Date().getTime(); var uuid = 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function (c) { var r = (d + Math.random() * 16) % 16 | 0; d = Math.floor(d / 16); return (c == 'x' ? r : (r & 0x7 | 0x8)).toString(16); }); return uuid; };