1 | /* This file is part of the KDE project |
2 | Copyright (C) 2007 Matthias Kretz <kretz@kde.org> |
3 | |
4 | This library is free software; you can redistribute it and/or |
5 | modify it under the terms of the GNU Lesser General Public |
6 | License as published by the Free Software Foundation; either |
7 | version 2.1 of the License, or (at your option) version 3, or any |
8 | later version accepted by the membership of KDE e.V. (or its |
9 | successor approved by the membership of KDE e.V.), Nokia Corporation |
10 | (or its successors, if any) and the KDE Free Qt Foundation, which shall |
11 | act as a proxy defined in Section 6 of version 3 of the license. |
12 | |
13 | This library is distributed in the hope that it will be useful, |
14 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
15 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
16 | Lesser General Public License for more details. |
17 | |
18 | You should have received a copy of the GNU Lesser General Public |
19 | License along with this library. If not, see <http://www.gnu.org/licenses/>. |
20 | |
21 | */ |
22 | |
23 | #ifndef PHONON_ABSTRACTMEDIASTREAM_H |
24 | #define PHONON_ABSTRACTMEDIASTREAM_H |
25 | |
26 | #include "phonon_export.h" |
27 | #include "phononnamespace.h" |
28 | #include <QtCore/QObject> |
29 | |
30 | QT_BEGIN_HEADER |
31 | QT_BEGIN_NAMESPACE |
32 | |
33 | class QByteArray; |
34 | |
35 | #ifndef QT_NO_PHONON_ABSTRACTMEDIASTREAM |
36 | |
37 | namespace Phonon |
38 | { |
39 | class MediaObject; |
40 | class AbstractMediaStreamPrivate; |
41 | |
42 | /** \class AbstractMediaStream abstractmediastream.h Phonon/AbstractMediaStream |
43 | * \brief Base class for custom media data streams. |
44 | * |
45 | * Implement this class to provide a custom data stream to the backend. The class supports both, the |
46 | * push and the pull model. |
47 | * |
48 | * Push: |
49 | * \code |
50 | * PushStream::PushStream(QObject *parent) |
51 | * : AbstractMediaStream(parent), m_timer(new QTimer(this)) |
52 | * { |
53 | * setStreamSize(getMediaStreamSize()); |
54 | * |
55 | * connect(m_timer, SIGNAL(timeout()), SLOT(moreData())); |
56 | * m_timer->setInterval(0); |
57 | * } |
58 | * |
59 | * void PushStream::moreData() |
60 | * { |
61 | * const QByteArray data = getMediaData(); |
62 | * if (data.isEmpty()) { |
63 | * endOfData(); |
64 | * } else { |
65 | * writeData(data); |
66 | * } |
67 | * } |
68 | * |
69 | * void PushStream::needData() |
70 | * { |
71 | * m_timer->start(); |
72 | * moreData(); |
73 | * } |
74 | * |
75 | * void PushStream::enoughData() |
76 | * { |
77 | * m_timer->stop(); |
78 | * } |
79 | * \endcode |
80 | * |
81 | * Pull: |
82 | * \code |
83 | * PullStream::PullStream(QObject *parent) |
84 | * : AbstractMediaStream(parent) |
85 | * { |
86 | * setStreamSize(getMediaStreamSize()); |
87 | * } |
88 | * |
89 | * void PullStream::needData() |
90 | * { |
91 | * const QByteArray data = getMediaData(); |
92 | * if (data.isEmpty()) { |
93 | * endOfData(); |
94 | * } else { |
95 | * writeData(data); |
96 | * } |
97 | * } |
98 | * \endcode |
99 | * |
100 | * \ingroup Playback |
101 | * \author Matthias Kretz <kretz@kde.org> |
102 | */ |
103 | class PHONON_EXPORT AbstractMediaStream : public QObject |
104 | { |
105 | Q_OBJECT |
106 | Q_DECLARE_PRIVATE(AbstractMediaStream) |
107 | friend class MediaObject; |
108 | friend class MediaObjectPrivate; |
109 | friend class StreamInterface; |
110 | public: |
111 | virtual ~AbstractMediaStream(); |
112 | |
113 | protected: |
114 | /** |
115 | * Constructs an AbstractMediaStream object with a \p parent. |
116 | */ |
117 | explicit AbstractMediaStream(QObject *parent = 0); |
118 | |
119 | /** |
120 | * Returns the stream size that was set with \ref setStreamSize. |
121 | * |
122 | * A negative value means that the length of the stream cannot be known. |
123 | * |
124 | * Defaults to \c 0. |
125 | */ |
126 | qint64 streamSize() const; |
127 | |
128 | /** |
129 | * Sets the size of the stream in number of bytes. |
130 | * |
131 | * A negative value means that the length of the stream cannot be known. |
132 | * |
133 | * Defaults to 0. |
134 | * |
135 | * This function has to be called. A backend will not call \ref needData() until the |
136 | * stream size is set. |
137 | */ |
138 | void setStreamSize(qint64); |
139 | |
140 | /** |
141 | * Returns whether your data stream is set as seekable. |
142 | * |
143 | * Defaults to \c false. |
144 | */ |
145 | bool streamSeekable() const; |
146 | |
147 | /** |
148 | * Sets whether your data stream is seekable. |
149 | * |
150 | * Defaults to \c false. |
151 | * |
152 | * If you set this to \c true you have to implement the \ref seekStream function. |
153 | */ |
154 | void setStreamSeekable(bool); |
155 | |
156 | /** |
157 | * Sends the media \p data to the backend for decoding. |
158 | * |
159 | * \warning Don't call this function before the first needData() is emitted. |
160 | */ |
161 | void writeData(const QByteArray &data); |
162 | |
163 | /** |
164 | * Tells the backend that the media data stream is at its end. |
165 | * |
166 | * \warning Don't call this function before the first needData() is emitted. |
167 | */ |
168 | void endOfData(); |
169 | |
170 | /** |
171 | * If an I/O error occurs you should call this function to make MediaObject go into |
172 | * ErrorState. |
173 | * |
174 | * \see MediaObject::errorType() |
175 | * \see MediaObject::errorString() |
176 | */ |
177 | void error(Phonon::ErrorType errorType, const QString &errorString); |
178 | |
179 | /** |
180 | * Reimplement this function to reset the stream. Subsequent calls to writeData should start |
181 | * from the first position of the data unless a seek is requested. |
182 | * |
183 | * The function is necessary for the case where a non-seekable MediaStream is |
184 | * played more than once. For a seekable stream the implementation can simply call |
185 | * \code |
186 | * seekStream(0); |
187 | * \endcode. |
188 | */ |
189 | virtual void reset() = 0; |
190 | |
191 | /** |
192 | * Reimplement this function to be notified when the backend needs data. |
193 | * |
194 | * When this function is called you should try to call writeData or endOfData before |
195 | * returning. |
196 | */ |
197 | virtual void needData() = 0; |
198 | |
199 | /** |
200 | * Reimplement this function to be notified when the backend has enough data and your stream |
201 | * object may take a break. This method is important for pushing data to the backend in |
202 | * order to not fill the backend buffer unnecessarily. |
203 | */ |
204 | virtual void enoughData(); |
205 | |
206 | /** |
207 | * Reimplement this function if your stream is seekable. |
208 | * |
209 | * When this function is called the next call to writeData has to be at the requested \p |
210 | * offset. |
211 | * |
212 | * \warning Do not call the parent implementation. |
213 | */ |
214 | virtual void seekStream(qint64 offset); |
215 | |
216 | AbstractMediaStream(AbstractMediaStreamPrivate &dd, QObject *parent); |
217 | QScopedPointer<AbstractMediaStreamPrivate> d_ptr; |
218 | }; |
219 | |
220 | } // namespace Phonon |
221 | |
222 | #endif //QT_NO_PHONON_ABSTRACTMEDIASTREAM |
223 | |
224 | QT_END_NAMESPACE |
225 | QT_END_HEADER |
226 | |
227 | #endif // PHONON_ABSTRACTMEDIASTREAM_H |
228 | |