9.8 Java Media Framework (JMF)JMF, currently at version 2.1, is Sun's initiative to bring time-based media processing to Java [JMF]. The JMF API enables JavaTV Xlets (possibly embedded within XHTML pages) to:
Consider a scenario in which a stereo system player plays music from a CD. In this scenario, the CD provides the data encoding of the music. The signal generated from the decoded data is sent the speakers. The data stored on the music CD has been previously captured in a studio using microphones and other audio capture devices. The CD itself is a data source to the stereo system. The speakers serve as an output device. The JMF programming models for this scenario uses the object classes of DataSource , Capture Device , Format , DataSink , Player , Processor and Manager . 9.8.1 Data SourceA data source represents the media stream much like a music CD. In JMF, a DataSource object encapsulates the audio media, video media, DSM-CC data stream, or a combination of the two. A DataSource can be a file or an incoming stream; it encapsulates both the media location, e.g., file name or URL, the protocol, e.g., HTTP, and the software used to deliver the media, e.g., MP3 decoder. Once created, a DataSource can be fed into a Player to be rendered, with the Player unconcerned about where the DataSource originated or what its format was. Media data can be obtained from various sources, such as local or network files, or live broadcasts. As such, DataSource s can be classified according to how a data transfer initiates:
9.8.2 Capture DeviceA capture device represents the hardware used to capture data, such as a microphone or a camera. Capture devices can be categorized as either push or pull sources. For example, a still camera is a pull data source because it does not capture, record or otherwise consume the data until a shot is taken. In contrast, a microphone and a video camera transmits data continuously regardless of whether the data is recorded or otherwise consumed in any way. 9.8.3 PlayerA Player takes as input a data source and renders it to a speaker or a screen, much like a CD Player reads a CD and outputs music to the speaker. A Player can have states, which exist naturally because a Player has to prepare itself and its data source before it can start playing the media. When a CD is inserted into the Player , the CD player cannot instantly play the song. It first has to start spinning the CD, then search the track where the first song begins and perform some other preparations . After about a few seconds the music could be heard . Likewise, the JMF Player does some preparation. A Player steps through a sequence of states until it reaches the final state. The following six Player states are defined by JMF:
9.8.4 ProcessorA Processor is a type of Player which has control on the specific processing performed on the input media. In the JMF API, a Processor interface extends Player . As such, a Processor supports the same presentation controls as a Player , with the addition of some processing controls. In addition to rendering a DataSource , a Processor can generate output media data through a DataSource so it can be presented or otherwise consumed by another Player or Processor , or converted to some other format. This feature enables cascading Processor in a tree structure whose root is a single data source and leaves are the output media. In addition to the six aforementioned Player states, a Processor includes two additional states that occur before the Processor enters the realizing state but after the unrealized state:
As with a Player , a DataSource transitions to the Realizing state on invocation of the realize() method and subsequently transitions into the Realized state as soon as the initialization procedure. 9.8.5 DataSinkThe DataSink is a base interface for objects that read media content delivered by a DataSource and render the media to some destination. As an example consider a file-writer object that stores the media in a file could serve as a DataSink . Intuitively, a DataSink is a simplified Processor that is not performing complex rendering operations and is not required to maintain states. An object can implement both the Processor and DataSink classes, and determine dynamically whether to behave as a sophisticated Processor or a DataSink . 9.8.6 FormatA Format object represents an object's exact media format. The format itself carries no encoding-specific parameters or global-timing information; it describes the format's encoding name and the type of data the format requires. Format subclasses include AudioFormat and VideoFor mat . In turn , VideoFormat contains six direct subclasses: H261Format , H263Format , IndexedColorFormat , JPEGFormat , RGBFormat , YUVFormat . 9.8.7 ManagerA JMF Manager is an intermediary object integrating the implementations of key interfaces that can be used seamlessly with existing classes. No real-world equivalent exists in a home-entertainment system; it can be found in the HAVi specification described in the previous chapter. The role of such a manager is to automate the interfacing between various objects. For example, with Manager one can create a Player from a DataSource s. The four JMF managers are:
9.8.8 Player ConstructionWith JMF multimedia programming, one key operation is creating a Player . A Player is created by calling the Manager.createPlayer() method giving it a URL for the media (i.e., containing the protocol, domain and path ). The Manager uses the URL of the media or MediaLocator to create an appropriate Player . Once a Player is created, one can obtain the visual components where a Player renders a visual representation of its media. Those components could be added to an application's window. The following is required to display a Player object's visual component:
A Player may create and subsequently utilize a control panel with buttons to start, stop, and pause the media stream, as well as control the volume, just like the similar buttons on a CD player. Many of the Player methods can be called only when the Player is in the realized state. To guarantee that a Player has been realized, one can call Manager.createRealizedPlayer() method to create the Player . This method provides a convenient way to create and realize a Player in a single step. When it is called, it blocks (i.e., doesn't return) until the Player is realized. The start() method can be invoked after a Player is created but before it reaches the prefetched state. In this case, start() attempts to transition the Player to the started state from whatever state it's currently in. The start() method implicitly invokes all necessary methods to bring the Player into the started state. 9.8.9 Processing StreamsJMF enables controlling the transmission and reception of media streams, such as live radio and TV broadcasts. Processing media streams differs from processing data files in several ways:
9.8.9.1 Transport ProtocolsJMF supports both MPEG-based and IP-based media streaming. The JMF was originally specified with API supporting the RTP delivering media streams over UDP/IP. The MHP extended the JMF API to support MPEG-based streaming, As opposed to TCP-based protocols, RTP, which is UDP-based, does not guarantee that data packets arrive in the order in which they were sent, and further, there is no guarantee that all packets arrive to their destination. In fact, there's no guarantee they arrive at all. It's up to the receiver to reconstruct the sender's packet sequence and detect lost packets using the information provided in the packet header. The RTCP protocol addresses resource reservation and QoS guarantees for real-time services. RTCP also allows data delivery monitoring in a manner scalable to large multicast networks. JMF provides the APIs defined in the javax.media.rtp, javax.media.rtp.event, and javax.media.rtp.rtcp packages for RTP stream playback and transmission. JMF RTP APIs can work seamlessly with JMF's capture device, players, processors, and processing capabilities. There is a SessionManager that is dedicated to coordinating RTP sessions and managing the RTCP control channel. 9.8.9.2 Transmission of RTP Media StreamsThere are two ways to transmit RTP streams:
9.8.9.3 Receive and Play RTP Media StreamsA MediaLocator is used to create a Player using the Manager.createPlayer() method, passing a MediaLocator as the argument. As an alternative, when the media location is not available and the DataSource can be accessed directly, a Player object is constructed by retrieving the DataSource from the stream and passing it to the Manager.createPlayer() method. In both scenarios, the DataSource comes from the SessionManager controlling the retrieval of the media stream; for each stream a separate player is constructed. |