jump to navigation

Getting Strarted with Open Source Media Framework (OSMF) formerly Strobe July 22, 2010

Posted by Tournas Dimitrios in Frameworks.
trackback

Open Source Media Framework (OSMF) simplifies the development of media players by allowing developers to assemble components to create high-quality, full-featured video playback experiences. This open framework enables development focused on web-based video monetization, with lower costs and faster turnaround.Follow these 6-part video screen cast to get started with this excellent framework and create your custom video player

Part 1: Overview of Adobe OSMF :

Part 2: Getting Started with OSMF in Adobe Flash :

download the files to accompany this video

Part 3: Dynamic Streaming with Adobe OSMF :

download the files to accompany this video

Part 4: Composite Elements in Adobe OSMF :

download the files to accompany this video

Part 5: Subclipping :

download the files to accompany this video


Part 6: Key MediaPlayer Properties And Events in OSMF :

download the files to accompany this video

This is the code for the Full basic Media player :


package
{
//flash imports
import flash.display.Sprite;
import flash.events.MouseEvent ;
import flash.events.Event ;
//Flash component imports
import fl.controls.Button;
import fl.controls.Slider;
//osmf imports
import org.osmf.containers.MediaContainer;
import org.osmf.layout.LayoutMetadata;
import org.osmf.media.MediaPlayer;
import org.osmf.media.MediaElement;
import org.osmf.media.MediaFactory;
import org.osmf.media.DefaultMediaFactory;
import org.osmf.media.URLResource;
import org.osmf.net.NetStreamCodes;
//osmf event imports
import org.osmf.events.MediaPlayerCapabilityChangeEvent;
import org.osmf.events.MediaErrorEvent;
import org.osmf.events.MediaPlayerStateChangeEvent;
import org.osmf.events.TimeEvent;
import org.osmf.events.MediaElementEvent;

public class MyPlayer extends Sprite
{

//--------------------------------------
// Group: Constants
//--------------------------------------
private static const MEDIA_URL_1 :String  = "../../MEDIA/kennedy.flv";
private static const MEDIA_URL_2 :String  = "../../MEDIA/1920s.flv";

//--------------------------------------
//  Group: Constructor
//--------------------------------------
public function MyPlayer()
{
_init ( ) ;
_setupGUI ( ) ;
}

//--------------------------------------
//  Group: Private Variables
//--------------------------------------
private var _mediaFactory:MediaFactory;
private var _mediaElement:MediaElement;
private var _mediaPlayer:MediaPlayer;
private var _mediaContainer:MediaContainer;
private var _layout:LayoutMetadata ;

//--------------------------------------
//  Group: Event Handlers
//--------------------------------------
//**STANDARD EVENT CALLBACK FUNCTIONS
/*
onPlaylistBtnClick is called when one of our playlist buttons
(labeled 'Kennedy' and 'The 1920's') is clicked by the user
*/
private function _onPlaylistBtnClick( evt : MouseEvent ):void {
//if the instance name of the clicked button is 'btn_media1'
if (evt.target.name=="btn_media1") {
//call playVideo with the path to the kennedy video
_playVideo( MEDIA_URL_1 );
//if the instance name of the clicked button is 'btn_media2'
} else if ( evt.target.name == "btn_media2" ) {
//call playVideo with the path to the Apollo 11 video
_playVideo( MEDIA_URL_2 );
}
}

/*
onBtnPauseClick is called when the user clicks the pause button
*/
private function _onBtnPauseClick( evt : MouseEvent ):void {
/*			trace ( "_onBtnPauseClick()" ) ;*/
_togglePause ( ) ;
}

/*
onProgressBarMouseDown is called when the user mouses down on the progress bar
*/
private function _onProgressBarMouseDown( evt : MouseEvent ):void {
/*			trace ( "_onProgressBarMouseDown ( )" ) ;*/
//calculate the percentage into our video the user wishes to seek
//based on where in the progressbar they clicked
var seekTo : Number = ( evt.localX / mc_progressBar.mc_bg.width );
//call seek video with that percentage
_seekVideo( seekTo );
}

/*
onVolumeSliderChange is called when the current value of the
volume slider changes (when the user clicks, moves the slider, and releases)
*/
private function _onVolumeSliderChange( evt : Event ):void {
//update the volume of the video to the selected value of the slider
_mediaPlayer.volume=evt.target.value;
}

//**************************************
//**OSMF EVENT CALLBACK FUNCTIONS
//**************************************
private function _onCurrentTimeChange ( evt : TimeEvent ) : void
{
/*			trace ( "_onCurrentTimeChange () , evt.time : " + evt.time ) ;*/
_updateProgressBar ( evt.time / _mediaPlayer.duration ) ;
}

private function _onCanLoadChange ( evt : MediaPlayerCapabilityChangeEvent ) : void
{
trace ( "_onCanLoadChange () , evt.enabled : " + evt.enabled ) ;
}

private function _onCanPlayChange ( evt : MediaPlayerCapabilityChangeEvent ) : void
{
trace ( "_onCanPlayChange () , evt.enabled : " + evt.enabled ) ;
if ( evt.enabled )
{
_enableControls ( ) ;
}
}

private function _onCanSeekChange ( evt : MediaPlayerCapabilityChangeEvent ) : void
{
trace ( "_onCanSeekChange () , evt.enabled : " + evt.enabled ) ;
if ( evt.enabled )
{
_enableProgressBar ( ) ;
}
}

private function _onMediaError ( evt : MediaErrorEvent ) : void
{
trace ( "_onMediaError () , evt.error : " + evt.error ) ;
}

private function _onMediaPlayerStateChange ( evt : MediaPlayerStateChangeEvent ) : void
{
trace ( "_onMediaPlayerStateChange () , evt.state : " + evt.state ) ;
switch ( evt.state )
{
case "playing":
break ;
case "loading":
_disableControls ( ) ;
break;
case "buffering":
break;
case "uninitialized":
_disableControls ( ) ;
break;
case "ready":
_disableControls ( ) ;
_cleanUpVideo ( ) ;
break;
default :
break;
}

}

//--------------------------------------
//  Group: Private and Protected Methods
//--------------------------------------
private function _init ( ) : void
{
//disable all controls on the stage, because no video has yet loaded
_disableControls( );
_setupGUI ( ) ;
_setupOSMF ( ) ;
}

private function _setupOSMF ( ) : void
{
_mediaPlayer = new MediaPlayer();
_mediaPlayer.autoRewind = false ;
_mediaPlayer.addEventListener ( TimeEvent.CURRENT_TIME_CHANGE , _onCurrentTimeChange , false , 0 , true ) ;
_mediaPlayer.addEventListener ( MediaPlayerCapabilityChangeEvent.CAN_LOAD_CHANGE , _onCanLoadChange , false , 0 , true ) ;
_mediaPlayer.addEventListener ( MediaPlayerCapabilityChangeEvent.CAN_PLAY_CHANGE , _onCanPlayChange , false , 0 , true ) ;
_mediaPlayer.addEventListener ( MediaPlayerCapabilityChangeEvent.CAN_SEEK_CHANGE , _onCanSeekChange , false , 0 , true ) ;
_mediaPlayer.addEventListener ( MediaErrorEvent.MEDIA_ERROR , _onMediaError , false , 0 , true ) ;
_mediaPlayer.addEventListener ( MediaPlayerStateChangeEvent.MEDIA_PLAYER_STATE_CHANGE , _onMediaPlayerStateChange , false , 0 , true ) ;
/*			_mediaPlayer.autoPlay = false; */
_mediaFactory = new DefaultMediaFactory();
_layout = new LayoutMetadata();
_layout.width = mc_videoDisplay.width-2;
_layout.height = mc_videoDisplay.height-2;
_layout.x = mc_videoDisplay.x+1;
_layout.y = mc_videoDisplay.y+1;
_mediaContainer = new MediaContainer();
addChild(_mediaContainer);
}

/*
playVideo is called with a specific video to play
This function
*/
private function _playVideo( videoToPlay : String ):void {
//call cleanUpVideo to clear out the video, in case one
//is currently loaded, and to reset the navigation to a disabled state
_cleanUpVideo( );
_mediaElement = _mediaFactory.createMediaElement(new URLResource(videoToPlay));
_mediaElement.addMetadata(LayoutMetadata.LAYOUT_NAMESPACE, _layout);
_mediaPlayer.media = _mediaElement;
_mediaContainer.addMediaElement(_mediaElement);
}

private function _togglePause ( ) : void
{
/*			trace ( "_togglePause() " ) ;*/
//if the video is currently paused
if (!_mediaPlayer.playing) {
//play the video
_mediaPlayer.play( );
//change the label on the play/pause button to 'Pause'
btn_pause.label="Pause";
} else {
//pause the video
_mediaPlayer.pause( );
//change the label on the play/pause button to 'Play'
btn_pause.label="Play";
}
}

/*
seekVideo is called to jump to another part of our video
with a percentage into the video to seek (e.g., 50% for half way)
*/
private function _seekVideo( seekTo : Number ):void {
//if the player can see to the specified point
if (_mediaPlayer.canSeekTo(seekTo*_mediaPlayer.duration))
//tell the MediaPlayer instance to seek to the specified seconds into the video
//by multiplying the seek percentage times the duration of the currently-loaded video
_mediaPlayer.seek( seekTo * _mediaPlayer.duration );
}

/*
updateProgressBar is called to update the visual status of the progress bar
so the nub and current position indicators remain accurate as the video plays
*/
private function _updateProgressBar( percentIn : Number ):void {
//set the x position of the progress nub
//and the width of the current position indicator
//to the product of the progress bar background
//and the percentIn (passed in when this function is called)
mc_progressBar.mc_nub.x = mc_progressBar.mc_currentPosition.width = Math.floor(percentIn*mc_progressBar.mc_bg.width);
}

/*
cleanUpVideo is called to 'clean up' after a video
when the currently-loaded video has completed
*/
private function _cleanUpVideo( ):void {
/*			trace ( "_cleanUpVideo ()" ) ;*/
//disable the GUI controls
_disableControls( );
if ( _mediaElement )
{
if ( _mediaContainer && _mediaContainer.containsMediaElement ( _mediaElement ) )
{
_mediaContainer.removeMediaElement ( _mediaElement ) ;
}
_mediaElement = undefined ;
}
}

/*
disableControls is called to disable all GUI video controls
*/
private function _disableControls( ):void {
/*			trace ( "_disableControls ( ) " ) ;*/
//disable the pause button
btn_pause.enabled=false;
btn_pause.mouseEnabled=false;
//disable the volume slider
sl_volume.enabled=false;
sl_volume.mouseEnabled=false;
//disable the progress bar from hearing mouse events
mc_progressBar.mouseEnabled=false;
//make the progress bar look disabled, by appearing at 50% alpha
mc_progressBar.alpha=.5;
}

private function _enableControls ( ) : void
{
/*			trace ( "_enableControls ()" );*/
//set the pause button label to 'pause'
btn_pause.label="Pause";
//enable the pause button
btn_pause.enabled=true;
btn_pause.mouseEnabled=true;
//enable the volume slider
sl_volume.enabled=true;
sl_volume.mouseEnabled=true;
//reset the x position of the nub, and the width of the current position indicator, to 0
mc_progressBar.mc_nub.x = mc_progressBar.mc_currentPosition.width = 0;
}

private function _enableProgressBar ( ) : void
{
//enable the progress bar from hearing mouse events
mc_progressBar.mouseEnabled=true;
//make the progress bar look enabled
mc_progressBar.alpha=1;
}

private function _setupGUI ( ) : void
{
//listen for the change event on the volume slider and call onVolumeSliderChange
sl_volume.addEventListener( Event.CHANGE , _onVolumeSliderChange );
//listen for the mouse down event on the progress bar and call onProgressBarMouseDown
mc_progressBar.addEventListener( MouseEvent.MOUSE_DOWN , _onProgressBarMouseDown );
//listen for the mouse click event on the pause button and call onBtnPauseClick
btn_pause.addEventListener( MouseEvent.CLICK , _onBtnPauseClick );
//set the progress bar to have a hand-cursor so it looks like it can be clicked on
mc_progressBar.buttonMode = true ;
//listen for the mouse click on both 'kennedy' and 'The 1920s' buttons
//and call onPlaylistBtnClick for both buttons
btn_media1.addEventListener( MouseEvent.CLICK , _onPlaylistBtnClick );
btn_media2.addEventListener( MouseEvent.CLICK , _onPlaylistBtnClick );
}

}
}

Building progressive video players in Flash with the Adobe Open Source Media Framework

These 8-screen cast made by Adobe cover all the basic functionality and concepts required to build progressive video players in Flash CS4 Professional using the Open Source Media Framework

Further reading :

Comments»

No comments yet — be the first.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s