I was inspired by the screencast on EndUserSharePoint.com called 5 Minute Screencast: Create a Multimedia Center in SharePoint. I decided to create a solution along these lines for our company intranet. However, in looking further into the solution I found that many things were probably included in the workshop on this topic that I was missing by just watching the screencast.
Being one to try to find my own solutions to these sort of things I set out to create my own solution.
Criteria:
- The Media Library would be built within a SharePoint site
- The Media Library was to use Lytebox to display the videos
- The Media Library needed to be dynamic enough that an end user could use it by only uploading new videos to a SharePoint document library
- The end user would not need to create any code
- The end user would not need to create any new pages (more on this later)
Steps:
Using the method of embedding HTML coding in a list column based on the Calculated Column, I could recreate the call to Lytebox and create the URL necessary to refer to video files in the "Video Library" document library of my site.
Using SharePoint Designer, I put the Lytebox javascript and associated .css and images in a new folder called "javascript".
I inserted a new Content Editor Web Part (CEWP) on the page of the library view above the list web part. In that I inserted the script call to the Lytebox scripts in the javascript folder.
I inserted another CEWP below the list web part and inserted Christophe Humbourg's Text to HTML script (read about that here: http://pathtosharepoint.wordpress.com/).
I uploaded a button graphic to the site's image library.
I had everything in place so that I could create my calculated column.
But, when I attempted to add the name of the file to the calculation, I found that the field that holds the file name in a SharePoint list is not available in a calculated column (or a lookup column for that matter).
So, I created a new list column called "File Name". Then I opened the site in SharePoint Designer and created a short workflow that fired "On New" to set the value of "File Name" to "Name (for use in forms)". If you just use "Name" you won't get the file extension.
Now I had a column I could use in my calculation. Mine is very much like Mark's at EUSP.com.
=CONCATENATE("<DIV><a href='../",[File Name],"' rel='lyteframe' title='SharePoint Info'rev='width",":","850px",";","height",":","650px",";","'><img src='../../images/playbutton24x24.png' border='0' width='24' height='24' alt='Click to View the Screencast' /></a></DIV>")
I did find that it was important to do the following:
- Use CONCATENATE as SharePoint may not recognize the formula without it.
- Capitalize the "DIV" tags.
- You must include characters like colons and semicolons in quotes so they are interpreted as text and not special coding characters.
This, however, had the following undesired effect: Lytebox opened, but so did Windows Media Player and the video played in WMP. Not, what I wanted.
So, after a lot of searching I finally sent a message to Mark and after a quick phone call he filled in the necessary blank – Lytebox renders a web page, not a file. So to get this to work I would need to call a page in my calculation in which the code to play the video was embedded.
Embedding code to play a media file is easy enough – standard HTML. I created an aspx page (called viewvideo.aspx) and inserted the proper code to embed the video just for proof of concept. Here is the new calculation for that:
=CONCATENATE("<DIV><a href='../Pages/viewvideo.aspx,"' rel='lyteframe' title='SharePoint Info'rev='width",":","850px",";","height",":","650px",";","'><img src='../../images/playbutton24x24.png' border='0' width='24' height='24' alt='Click to View the Screencast' /></a></DIV>")
It worked just fine. But had two issues:
- I didn't want the user to have to create a new page with this code every time they uploaded a new video, and then have to hard-code the URL to the page somewhere.
- I learned that this should be a regular .aspx page with no Master Page attached (the entire rendered page is displayed in Lytebox which includes the master page, not just the layout page.)
So….I needed to be able to pass a value from the video library list to the viewvideo.aspx page and insert it into the embed HTML code. I decided to do this with a little javascript. I'd already used it for Lytebox, so why not add a bit more?
I changed my calculated column in the video library to the following:
=CONCATENATE("<DIV><a href='../Pages/viewvideo.aspx?name=",[File Name],"' rel='lyteframe' title='SharePoint Info'rev='width",":","850px",";","height",":","650px",";","'><img src='../../images/playbutton24x24.png' border='0' width='24' height='24' alt='Click to View the Screencast' /></a></DIV>")
You will notice that I am hard-coding a bit of what I might be able to do by altering the form code (such as: <FORM METHOD="LINK" ACTION="viewvideo.aspx">, to be able to pass a value into the URL of the targeted page. But I didn't see how I could do that effectively in SharePoint. So I hard-coded the "?name=,[File Name]," part of what I would get programmatically outside SharePoint.
This would produce a URL such as:
http://domain.com/pages/viewvideo.aspx?name=videoname.wmv
Now, with a bit of javascript I could capture that parameter in the viewvideo.aspx embed code.
To the viewvideo.aspx page I decided to add a web part zone and inserted a CEWP into the zone. Into this I put the following code:
<SCRIPT LANGUAGE="javascript">
var locate = window.location.toString();
function delineate(str)
{
point = str.lastIndexOf("=");
return(str.substring(point+1, str.length));
}
document.write('<embed src="../Video%20Library/'+delineate(locate)+'" WIDTH=800 HEIGHT=600 Align=center>');
</SCRIPT>
Window.location pulls the entire address of the page into and the .toString() part converts it from a parameter to a text string. I assigned it to the 'locate' variable.
Then the function called delineate with a data type of str (text) does the following:
- It finds the "=" character
- It then returns all the characters after that to the end of the string
- It then assigns that new string to a variable called point (don't actually use this variable, but we need a place to store the value)
Then the document.write creates the HTML code for embedding the video into the page, using the value returned from the function to name the actual file name.
Now I go back to the video library and click on the button … and the viewvideo.aspx page loads into Lytebox and plays the appropriate video file.
All done except for a bit of tweaking to make the Lytebox window large enough to just hold the media player window. So, make the Lytebox parameters a few pixels larger than you set in your embed coding.
That's it. A fully functional media center that can now be used for any media file uploaded to the video library document library. The user just has to upload the file and click on the button. All is good.