/*
* @(#)DataSource.java 1.15 02/08/21
*
* Copyright (c) 1996-2002 Sun Microsystems, Inc. All rights reserved.
*/
package com.sun.media.protocol.rtp;
import java.io.*;
import javax.media.protocol.*;
import com.sun.media.*;
import com.sun.media.protocol.*;
import javax.media.*;
import javax.media.rtp.*;
import com.sun.media.rtp.RTPSessionMgr;
import com.sun.media.rtp.RTPControlImpl;
import com.sun.media.rtp.SSRCInfo;
import com.sun.media.rtp.RTPSourceStream;
import com.sun.media.protocol.BufferListener;
public class DataSource extends BasicPushBufferDataSource
implements Streamable, RTPSource
{
static int SSRC_UNDEFINED = 0; // RTPMediaLocator.SSRC_UNDEFINED
private RTPSourceStream[] srcStreams = null;
private boolean stopped = true;
Player streamplayer = null;
RTPSessionMgr mgr = null;
RTPControl rtpcontrol = null;
DataSource childsrc = null;
int ssrc = SSRC_UNDEFINED;
public void setMgr(RTPSessionMgr mgr){
//System.out.println("manager being set to " + mgr);
this.mgr = mgr;
}
public RTPSessionMgr getMgr(){
return mgr;
}
public void setChild(DataSource source){
childsrc = source;
}
public DataSource()
{
srcStreams = new RTPSourceStream[1];
rtpcontrol = new MyRTPControl();
//setContentType(ContentDescriptor.RAW);
setContentType("rtp");
}
/**
* Obtain the collection of streams that this source
* manages. The collection of streams is entirely
* content dependent. The mime-type of this
* DataSource provides the only indication of
* what streams can be available on this connection.
*
* @return collection of streams for this source.
*/
public PushBufferStream[] getStreams() {
if (!connected)
return null;
return srcStreams;
}
public void setPlayer(Player player){
streamplayer = player;
}
public Player getPlayer(){
return streamplayer;
}
public void setSourceStream(RTPSourceStream stream){
if (srcStreams != null)
srcStreams[0] = stream;
}
public void setBufferListener(BufferListener listener) {
srcStreams[0].setBufferListener(listener);
}
public void setLocator(MediaLocator mrl){
super.setLocator(mrl);
}
public void setBufferWhenStopped(boolean flag) {
srcStreams[0].setBufferWhenStopped(flag);
}
public void prebuffer() {
started = true;
srcStreams[0].prebuffer();
}
/**
* A method to flush the data buffers int the DataSource.
*/
public void flush() {
srcStreams[0].reset();
}
public void setSSRC(int ssrc) {
this.ssrc = ssrc;
}
public int getSSRC() {
return ssrc;
}
public String getCNAME() {
if (mgr == null)
return null;
SSRCInfo info = mgr.getSSRCInfo(ssrc);
if (info != null)
return info.getCNAME();
return null;
}
/**
* Initiates data-transfer. Start must be called before
* data is available. Connect must be called before start.
* @exception IOException thrown if the source has IO trouble
* at startup time.
*/
public void start() throws IOException {
super.start();
if (childsrc != null)
childsrc.start();
if (srcStreams != null){
for (int i = 0; i < srcStreams.length; i++)
((com.sun.media.rtp.RTPSourceStream)srcStreams[i]).start();
}
}
/**
* Stops data-transfer.
* If the source has not already been connected and started,
* stop does nothing.
*/
public void stop() throws IOException {
super.stop();
// stop your child source as well
if (childsrc != null)
childsrc.stop();
if (srcStreams != null){
for (int i = 0; i < srcStreams.length; i++)
((com.sun.media.rtp.RTPSourceStream)srcStreams[i]).stop();
}
}
public void setContentType(String contentType){
this.contentType = contentType;
}
public boolean isStarted(){
return started;
}
/**
* Opens a connection to the source described by
* the URL.<p>
* Connect initiates communmication with the source.
*
* @exception IOException thrown if the connect has IO trouble.
*/
public void connect() throws IOException {
// start the RTPSessionManager by calling startSession()
// this will throw an IOException if there is any problem
/*
if (mgr != null){
mgr.startSession();
}
*/
if (srcStreams != null){
for (int i = 0; i < srcStreams.length; i++){
if (srcStreams[i] != null)
((com.sun.media.rtp.RTPSourceStream)srcStreams[i]).connect();
}
}
connected = true;
}
/**
* Close the connection to the source described by the URL. <p>
* Disconnect frees resources used to maintain a connection
* to the source. If no resources are in use, disconnect
* is ignored.
* Implies a stop, if stop hasn't already been called.
*/
public void disconnect() {
// once we have disconnected, set boolean to false
// If this datasource was created by using the RTPAPI and not
// via Manager, we dont want to disconnect this source i.e. we
// dont want to closeSession() on RTPSM. In this case, the
// datasource will not have a manager set to it. In this case,
// the datasource cannot really be disconnected until the
// session manager is closed by using the RTPAPI
if (srcStreams != null){
for (int i = 0; i < srcStreams.length; i++)
((com.sun.media.rtp.RTPSourceStream)srcStreams[i]).close();
}
/*
if (mgr != null){
// close the RTPSourceStream
mgr.removeDataSource(this);
mgr.closeSession();
mgr = null;
// to fix bug 4174773, multiple stream problem 9/18/98
started = false;
connected = false;
return;
}
*/
}
/**
* Returns an zero length array because no controls
* are supported.
*
* @return a zero length <code>Object</code> array.
*/
public Object[] getControls() {
// return a one element array of rtpcontrol object
RTPControl[] controls = new RTPControl[1];
controls[0] = rtpcontrol;
return controls;
}
public void setControl(Object control){
rtpcontrol = (RTPControl)control;
}
/**
* Returns <code>null</code> because no controls are implemented.
*
* @return <code>null</code>.
*/
public Object getControl(String type) {
Class cls;
try {
cls = Class.forName(type);
} catch (ClassNotFoundException e) {
return null;
}
Object cs[] = getControls();
for (int i = 0; i < cs.length; i++) {
if (cls.isInstance(cs[i]))
return cs[i];
}
return null;
}
public boolean isPrefetchable() {
return false;
}
class MyRTPControl extends RTPControlImpl {
public int getSSRC() {
return ssrc;
}
public String getCNAME() {
if (mgr == null)
return null;
SSRCInfo info = mgr.getSSRCInfo(ssrc);
if (info != null)
return info.getCNAME();
return null;
}
}
}
|