wc/r18865/#8604/ contributed by Mitz Pettel <mitz@webkit.org>
[kdelibs.git] / phonon / bytestream.h
blob5f6cd1373a2b38c8b399fb57bce37edbde7c0c2c
1 /* This file is part of the KDE project
2 Copyright (C) 2005-2006 Matthias Kretz <kretz@kde.org>
4 This library is free software; you can redistribute it and/or
5 modify it under the terms of the GNU Library General Public
6 License version 2 as published by the Free Software Foundation.
8 This library is distributed in the hope that it will be useful,
9 but WITHOUT ANY WARRANTY; without even the implied warranty of
10 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 Library General Public License for more details.
13 You should have received a copy of the GNU Library General Public License
14 along with this library; see the file COPYING.LIB. If not, write to
15 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
16 Boston, MA 02110-1301, USA.
19 #ifndef PHONON_BYTESTREAM_H
20 #define PHONON_BYTESTREAM_H
22 #include "abstractmediaproducer.h"
23 #include <kdelibs_export.h>
24 #include "phonondefs.h"
26 class QString;
27 class QStringList;
29 namespace Phonon
31 class ByteStreamPrivate;
34 * loud thinking about async parts of this interface
35 * =============================
37 * Let us go over all the methods to make sure we will not get in trouble
38 * (i.e. deadlocks or necessary processEvents calls)
40 * The following functions are safe because they don't have anything to do
41 * with the stream data
42 * - stop
43 * - pause
44 * - state
45 * - currentTime
46 * - videoPaths/audioPaths
47 * - streamSize/setStreamSize
48 * - tickInterval/setTickInterval
49 * - streamSeekable/setStreamSeekable
50 * - aboutToFinishTime/setAboutToFinishTime
51 * - selectAudioStream/selectVideoStream/selectSubtitleStream
52 * - selectedAudioStream/selectedVideoStream/selectedSubtitleStream
54 * - metaDataKeys/metaDataItem/metaDataItems
55 * Safe because the meta data is sent to the frontend async (calls don't
56 * call any functions on the backend object)
58 * - addVideoPath/addAudioPath
59 * flow graph setup calls, sometimes depend on stream data:
60 * With xine you need to create a new xine_stream which might need to do
61 * seeks and reads. In this case the backend should go into LoadingState
62 * or BufferingState (or ErrorState if the stream is not seekable).
64 * - hasVideo
65 * - isSeekable
66 * - availableAudioStreams/availableVideoStreams/availableSubtitleStreams
67 * Needs the stream data to know the "correct answer".
68 * Returns false if not enough data has been sent. TODO: might need a
69 * Q_SIGNAL to make it work async.
71 * - totalTime/remainingTime
72 * Needs the stream data to know the "correct answer".
73 * Returns -1 if not enough data has been sent. Has the length signal for
74 * async notification.
76 * - play
77 * - seek
78 * if not enough data is available to start playback the backend goes into
79 * BufferingState
82 /**
83 * \short Send media data to be decoded and played back.
85 * This class allows you to send arbitrary media data (well, any media data
86 * format that the backend can decode) to the mediaframework used by the
87 * backend. MediaObject uses the facilities of this class internally when
88 * the mediaframework cannot handle an URL using KIO to fetch the data and
89 * ByteStream to stream it to the backend.
91 * To use it you need to provide a constant (fast enough) datastream via
92 * writeData. The signals needData and enoughData tell when the stream is
93 * about to drop out or when the internal buffer is sufficently filled. The
94 * backend should be able to buffer whatever you throw at it (of course,
95 * depending on the available memory of the computer).
97 * This allows your data provider to use a push method (calling writeData
98 * and waiting when enoughData is emitted) or a pull method (call writeData
99 * whenever needData is emitted).
101 * If your datastream is seekable you can tell the ByteStream object via
102 * setStreamSeekable. When a seek is called and the ByteStream needs data at
103 * a different position it will tell you with the seekStream signal. This
104 * signal passes the offset from the beginning of the datastream where the
105 * next array of data passed to writeData should start from.
107 * When the datastream is complete written you need to call endOfData, else
108 * ByteStream will not emit the finished signal, but go into the
109 * BufferingState.
111 * As soon as you know the size of the stream (in bytes) you should call
112 * setStreamSize. This could be useful for the ByteStream object to
113 * correctly emit the aboutToFinish signal. If the size is not known the
114 * aboutToFinish signal will still work, but you should not depend on it
115 * being emitted at the correct time.
117 * \author Matthias Kretz <kretz@kde.org>
119 class PHONONCORE_EXPORT ByteStream : public AbstractMediaProducer
121 Q_OBJECT
122 K_DECLARE_PRIVATE( ByteStream )
123 PHONON_HEIR( ByteStream )
124 Q_PROPERTY( qint32 aboutToFinishTime READ aboutToFinishTime WRITE setAboutToFinishTime )
125 Q_PROPERTY( qint64 streamSize READ streamSize WRITE setStreamSize )
126 Q_PROPERTY( bool streamSeekable READ streamSeekable WRITE setStreamSeekable )
127 public:
129 * \copydoc MediaObject::totalTime()
131 qint64 totalTime() const;
134 * \copydoc MediaObject::remainingTime()
136 qint64 remainingTime() const;
139 * \copydoc MediaObject::aboutToFinishTime()
141 qint32 aboutToFinishTime() const;
144 * Returns the size of the stream in bytes. If the size is unknown
145 * \c -1 is returned.
147 * \return \c -1 if the size is unknown, otherwise the size in bytes
149 * \see setStreamSize
151 qint64 streamSize() const;
154 * Returns whether you need to react on the seekStream signal when
155 * it is emitted.
157 * \return \c true You have to seek in the datastream when
158 * seekStream is emitted.
159 * \return \c false You only have to write the stream to writeData
160 * in one sequence.
162 * \see setStreamSeekable
164 bool streamSeekable() const;
166 public Q_SLOTS:
168 * Tell the object whether you will support seeking in the
169 * datastream. If you do, you have to react to the seekStream
170 * signal. If you don't you can safely ignore that signal.
172 * \param seekable Whether you are able to seek in the datastream
173 * and provide the writeData method with the data at arbitrary
174 * positions.
176 * \see streamSeekable
177 * \see seekStream
179 void setStreamSeekable( bool seekable );
182 * Passes media data to the mediaframework used by the backend. The
183 * data should be written in chunks of at least 512 bytes to not
184 * become too inefficient.
186 * \todo Actually I have no idea what array size should be used.
187 * Some tests would be good.
189 * \param data A QByteArray holding the data. After this call you are free
190 * to dispose of the array.
192 * \see needData
193 * \see enoughData
194 * \see seekStream
196 void writeData( const QByteArray& data );
199 * Sets how many bytes the complete datastream has. The Size is
200 * counted from the start of the stream until the end and not from
201 * the point in time when the slot is called.
203 * \param streamSize The size of the stream in bytes. The special
204 * value \c -1 is used for "unknown size".
206 * \see streamSize
207 * \see endOfData
209 void setStreamSize( qint64 streamSize );
212 * Call this slot after your last call to writeData. This is needed
213 * for the ByteStream to properly emit the finished and
214 * aboutToFinish signals. If the internal buffer is too small to
215 * cover the aboutToFinishTime the streamSize is used for the
216 * aboutToFinish signal. If the streamSize is unknown and the buffer
217 * is too small to emit the aboutToFinish signal in time it is
218 * emitted as soon as possible.
220 * \see setStreamSize
222 void endOfData();
225 * \copydoc MediaObject::setAboutToFinishTime( qint32 )
227 void setAboutToFinishTime( qint32 newAboutToFinishTime );
229 Q_SIGNALS:
231 * \copydoc MediaObject::finished()
233 void finished();
236 * Emitted when the stream is about to finish. The aboutToFinishTime
237 * is not guaranteed to be correct as sometimes the stream time
238 * until the end is not known early enough. Never rely on the
239 * aboutToFinishTime you set, but use the \p msec parameter instead.
241 * \warning Sometimes the media framework has no idea when the
242 * stream will end and only knows it when it has finished. For
243 * example, for an Ogg Vorbis stream which is not seekable the
244 * backend can only estimate the length of the stream by looking at
245 * the average bitrate and size of the stream, which can make a big
246 * difference some times. So especially when the stream is not
247 * seekable you cannot expect this signal to be of any use.
249 * \param msec The time in milliseconds until the stream finishes.
251 void aboutToFinish( qint32 msec );
254 * \copydoc MediaObject::length()
256 void length( qint64 length );
259 * Emitted when the ByteStream object needs more data to process.
260 * Your slot should not take too long to call writeData because otherwise
261 * the stream might drop.
263 void needData();
266 * Emitted when the ByteStream object has enough data to process.
267 * This means you do not need to call writeData anymore until
268 * needData is emitted.
270 void enoughData();
273 * Emitted when the ByteStream needs you to continue streaming data
274 * at a different position in the stream. This happens when seek(
275 * qint64 ) is called and the needed data is not in the internal
276 * buffer.
278 * \param age The number of bytes since the start of the stream.
279 * Your next call to writeData is expected to contain the
280 * data from this position on.
282 * \see setStreamSeekable
284 void seekStream( qint64 age );
286 } //namespace Phonon
288 // vim: sw=4 ts=4 tw=80
289 #endif // PHONON_BYTESTREAM_H