1// AbstractFileInterfaceNode.h
2//
3// Andrew Bachmann, 2002
4//
5// The AbstractFileInterfaceNode class implements
6// the common functionality between MediaReader
7// and MediaWriter.
8
9#if !defined(_ABSTRACT_FILE_INTERFACE_NODE_H)
10#define _ABSTRACT_FILE_INTERFACE_NODE_H
11
12#include <BufferGroup.h>
13#include <Controllable.h>
14#include <Entry.h>
15#include <File.h>
16#include <FileInterface.h>
17#include <MediaAddOn.h>
18#include <MediaDefs.h>
19#include <MediaNode.h>
20#include <MediaEventLooper.h>
21
22class AbstractFileInterfaceNode :
23    public BFileInterface,
24    public BControllable,
25    public BMediaEventLooper
26{
27protected:
28virtual ~AbstractFileInterfaceNode(void);
29
30public:
31
32explicit AbstractFileInterfaceNode(
33				size_t defaultChunkSize = 8192, // chunk size = 8 KB
34				float defaultBitRate = 800000,  // bit rate = 100.000 KB/sec = 5.85 MB/minute
35				const flavor_info * info = 0,   // buffer period = 80 milliseconds
36				BMessage * config = 0,
37				BMediaAddOn * addOn = 0);
38
39virtual status_t InitCheck(void) const;
40
41// see BMediaAddOn::GetConfigurationFor
42virtual	status_t GetConfigurationFor(
43				BMessage * into_message);
44
45/*************************/
46/* begin from BMediaNode */
47public:
48//	/* this port is what a media node listens to for commands */
49// virtual port_id ControlPort(void) const;
50
51virtual	BMediaAddOn* AddOn(
52				int32 * internal_id) const;	/* Who instantiated you -- or NULL for app class */
53
54protected:
55		/* These don't return errors; instead, they use the global error condition reporter. */
56		/* A node is required to have a queue of at least one pending command (plus TimeWarp) */
57		/* and is recommended to allow for at least one pending command of each type. */
58		/* Allowing an arbitrary number of outstanding commands might be nice, but apps */
59		/* cannot depend on that happening. */
60virtual	void Start(
61				bigtime_t performance_time);
62virtual	void Stop(
63				bigtime_t performance_time,
64				bool immediate);
65virtual	void Seek(
66				bigtime_t media_time,
67				bigtime_t performance_time);
68virtual	void SetRunMode(
69				run_mode mode);
70virtual	void TimeWarp(
71				bigtime_t at_real_time,
72				bigtime_t to_performance_time);
73virtual	void Preroll(void);
74virtual	void SetTimeSource(
75				BTimeSource * time_source);
76
77public:
78virtual	status_t HandleMessage(
79				int32 message,
80				const void * data,
81				size_t size);
82
83protected:
84		/* Called when requests have completed, or failed. */
85virtual	status_t RequestCompleted(	/* reserved 0 */
86				const media_request_info & info);
87
88protected:
89virtual		status_t DeleteHook(BMediaNode * node);		/* reserved 1 */
90
91virtual		void NodeRegistered(void);	/* reserved 2 */
92
93public:
94
95		/* fill out your attributes in the provided array, returning however many you have. */
96virtual		status_t GetNodeAttributes(	/* reserved 3 */
97					media_node_attribute * outAttributes,
98					size_t inMaxCount);
99
100virtual		status_t AddTimer(
101					bigtime_t at_performance_time,
102					int32 cookie);
103
104/* end from BMediaNode */
105/***********************/
106
107protected:
108virtual BParameterWeb * MakeParameterWeb(void);
109
110/*****************************/
111/* begin from BFileInterface */
112protected:
113//included from BMediaNode
114//virtual	status_t HandleMessage(
115//                int32 message,
116//				const void * data,
117//				size_t size);
118
119virtual	status_t GetNextFileFormat(
120				int32 * cookie,
121				media_file_format * out_format);
122virtual	void DisposeFileFormatCookie(
123				int32 cookie);
124
125virtual	status_t GetDuration(
126				bigtime_t * out_time);
127
128virtual	status_t SniffRef(
129				const entry_ref & file,
130				char * out_mime_type,	/* 256 bytes */
131				float * out_quality);
132
133virtual	status_t SetRef(
134				const entry_ref & file,
135				bool create,
136				bigtime_t * out_time) = 0;
137
138virtual	status_t SetRef(
139				const entry_ref & file,
140				uint32 openMode,
141				bool create,
142				bigtime_t * out_time);
143
144virtual	status_t GetRef(
145				entry_ref * out_ref,
146				char * out_mime_type);
147
148/* end from BFileInterface */
149/***************************/
150
151// provided for BAbstractFileInterfaceNodeAddOn
152public:
153static status_t StaticSniffRef(
154				const entry_ref & file,
155				char * out_mime_type,	/* 256 bytes */
156				float * out_quality);
157
158/****************************/
159/* begin from BControllable */
160
161//included from BMediaNode
162//virtual	status_t HandleMessage(
163//                int32 message,
164//				const void * data,
165//				size_t size);
166public:
167		/* These are alternate methods of accomplishing the same thing as */
168		/* connecting to control information source/destinations would. */
169virtual	status_t GetParameterValue(
170				int32 id,
171				bigtime_t * last_change,
172				void * value,
173				size_t * ioSize);
174virtual	void SetParameterValue(
175				int32 id,
176				bigtime_t when,
177				const void * value,
178				size_t size);
179virtual	status_t StartControlPanel(
180				BMessenger * out_messenger);
181
182/* end from BControllable */
183/**************************/
184
185public:
186		// these three are related:
187		// DEFAULT_CHUNK_SIZE = (DEFAULT_BIT_RATE * 1024) * (DEFAULT_BUFFER_PERIOD / 8000000)
188		static const int32 DEFAULT_CHUNK_SIZE_PARAM;    // in bytes
189		static const int32 DEFAULT_BIT_RATE_PARAM;      // in 1000*kilobits/sec
190		static const int32 DEFAULT_BUFFER_PERIOD_PARAM; // milliseconds
191
192private:
193		size_t fDefaultChunkSizeParam;
194		bigtime_t fDefaultChunkSizeParamChangeTime;
195		float fDefaultBitRateParam;
196		bigtime_t fDefaultBitRateParamChangeTime;
197		int32 fDefaultBufferPeriodParam;
198		bigtime_t fDefaultBufferPeriodParamChangeTime;
199
200		// This is used to figure out which parameter to compute
201		// when enforcing the above constraint relating the three params
202		int32 fLastUpdatedParameter;
203		int32 fLeastRecentlyUpdatedParameter;
204
205/********************************/
206/* start from BMediaEventLooper */
207
208	protected:
209		/* you must override to handle your events! */
210		/* you should not call HandleEvent directly */
211		virtual void		HandleEvent(	const media_timed_event *event,
212											bigtime_t lateness,
213											bool realTimeEvent = false);
214
215		/* override to clean up custom events you have added to your queue */
216		virtual void		CleanUpEvent(const media_timed_event *event);
217
218		/* called from Offline mode to determine the current time of the node */
219		/* update your internal information whenever it changes */
220		virtual	bigtime_t	OfflineTime();
221
222		/* override only if you know what you are doing! */
223		/* otherwise much badness could occur */
224		/* the actual control loop function: */
225		/* 	waits for messages, Pops events off the queue and calls DispatchEvent */
226		virtual void		ControlLoop();
227
228/* end from BMediaEventLooper */
229/******************************/
230
231protected:
232
233virtual status_t HandleStart(
234						const media_timed_event *event,
235						bigtime_t lateness,
236						bool realTimeEvent = false);
237virtual status_t HandleSeek(
238						const media_timed_event *event,
239						bigtime_t lateness,
240						bool realTimeEvent = false);
241virtual status_t HandleWarp(
242						const media_timed_event *event,
243						bigtime_t lateness,
244						bool realTimeEvent = false);
245virtual status_t HandleStop(
246						const media_timed_event *event,
247						bigtime_t lateness,
248						bool realTimeEvent = false);
249virtual status_t HandleBuffer(
250						const media_timed_event *event,
251						bigtime_t lateness,
252						bool realTimeEvent = false) = 0;
253virtual status_t HandleDataStatus(
254						const media_timed_event *event,
255						bigtime_t lateness,
256						bool realTimeEvent = false) = 0;
257virtual status_t HandleParameter(
258						const media_timed_event *event,
259						bigtime_t lateness,
260						bool realTimeEvent = false);
261
262public:
263
264static void GetFlavor(flavor_info * outInfo, int32 id);
265static void GetFormat(media_format * outFormat);
266static void GetFileFormat(media_file_format * outFileFormat);
267
268protected:
269
270virtual status_t AddRequirements(media_format * format);
271virtual status_t ResolveWildcards(media_format * format);
272
273// accessors
274
275inline BFile * GetCurrentFile() { return fCurrentFile; }
276
277private:
278
279		AbstractFileInterfaceNode(	/* private unimplemented */
280				const AbstractFileInterfaceNode & clone);
281		AbstractFileInterfaceNode & operator=(
282				const AbstractFileInterfaceNode & clone);
283
284		status_t fInitCheckStatus;
285
286		BMediaAddOn * fAddOn;
287
288		BFile * fCurrentFile;
289		entry_ref f_current_ref;
290		char f_current_mime_type[B_MIME_TYPE_LENGTH+1];
291
292		/* Mmmh, stuffing! */
293virtual		status_t _Reserved_AbstractFileInterfaceNode_0(void *);
294virtual		status_t _Reserved_AbstractFileInterfaceNode_1(void *);
295virtual		status_t _Reserved_AbstractFileInterfaceNode_2(void *);
296virtual		status_t _Reserved_AbstractFileInterfaceNode_3(void *);
297virtual		status_t _Reserved_AbstractFileInterfaceNode_4(void *);
298virtual		status_t _Reserved_AbstractFileInterfaceNode_5(void *);
299virtual		status_t _Reserved_AbstractFileInterfaceNode_6(void *);
300virtual		status_t _Reserved_AbstractFileInterfaceNode_7(void *);
301virtual		status_t _Reserved_AbstractFileInterfaceNode_8(void *);
302virtual		status_t _Reserved_AbstractFileInterfaceNode_9(void *);
303virtual		status_t _Reserved_AbstractFileInterfaceNode_10(void *);
304virtual		status_t _Reserved_AbstractFileInterfaceNode_11(void *);
305virtual		status_t _Reserved_AbstractFileInterfaceNode_12(void *);
306virtual		status_t _Reserved_AbstractFileInterfaceNode_13(void *);
307virtual		status_t _Reserved_AbstractFileInterfaceNode_14(void *);
308virtual		status_t _Reserved_AbstractFileInterfaceNode_15(void *);
309
310		uint32 _reserved_abstract_file_interface_node_[16];
311
312};
313
314#endif /* _ABSTRACT_FILE_INTERFACE_NODE_H */
315