~ubuntu-branches/ubuntu/wily/sflphone/wily

« back to all changes in this revision

Viewing changes to daemon/libs/pjproject-2.2.1/third_party/BaseClasses/ctlutil.h

  • Committer: Package Import Robot
  • Author(s): Jonathan Riddell
  • Date: 2015-01-07 14:51:16 UTC
  • mfrom: (4.3.5 sid)
  • Revision ID: package-import@ubuntu.com-20150107145116-yxnafinf4lrdvrmx
Tags: 1.4.1-0.1ubuntu1
* Merge with Debian, remaining changes:
 - Drop soprano, nepomuk build-dep
* Drop ubuntu patches, now upstream

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
//------------------------------------------------------------------------------
 
2
// File: CtlUtil.h
 
3
//
 
4
// Desc: DirectShow base classes.
 
5
//
 
6
// Copyright (c) 1992-2001 Microsoft Corporation.  All rights reserved.
 
7
//------------------------------------------------------------------------------
 
8
 
 
9
 
 
10
// Base classes implementing IDispatch parsing for the basic control dual
 
11
// interfaces. Derive from these and implement just the custom method and
 
12
// property methods. We also implement CPosPassThru that can be used by
 
13
// renderers and transforms to pass by IMediaPosition and IMediaSeeking
 
14
 
 
15
#ifndef __CTLUTIL__
 
16
#define __CTLUTIL__
 
17
 
 
18
// OLE Automation has different ideas of TRUE and FALSE
 
19
 
 
20
#define OATRUE (-1)
 
21
#define OAFALSE (0)
 
22
 
 
23
 
 
24
// It's possible that we could replace this class with CreateStdDispatch
 
25
 
 
26
class CBaseDispatch
 
27
{
 
28
    ITypeInfo * m_pti;
 
29
 
 
30
public:
 
31
 
 
32
    CBaseDispatch() : m_pti(NULL) {}
 
33
    ~CBaseDispatch();
 
34
 
 
35
    /* IDispatch methods */
 
36
    STDMETHODIMP GetTypeInfoCount(__out UINT * pctinfo);
 
37
 
 
38
    STDMETHODIMP GetTypeInfo(
 
39
      REFIID riid,
 
40
      UINT itinfo,
 
41
      LCID lcid,
 
42
      __deref_out ITypeInfo ** pptinfo);
 
43
 
 
44
    STDMETHODIMP GetIDsOfNames(
 
45
      REFIID riid,
 
46
      __in_ecount(cNames) LPOLESTR * rgszNames,
 
47
      UINT cNames,
 
48
      LCID lcid,
 
49
      __out_ecount(cNames) DISPID * rgdispid);
 
50
};
 
51
 
 
52
 
 
53
class AM_NOVTABLE CMediaControl :
 
54
    public IMediaControl,
 
55
    public CUnknown
 
56
{
 
57
    CBaseDispatch m_basedisp;
 
58
 
 
59
public:
 
60
 
 
61
    CMediaControl(const TCHAR *, LPUNKNOWN);
 
62
 
 
63
    DECLARE_IUNKNOWN
 
64
 
 
65
    // override this to publicise our interfaces
 
66
    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, __deref_out void **ppv);
 
67
 
 
68
    /* IDispatch methods */
 
69
    STDMETHODIMP GetTypeInfoCount(__out UINT * pctinfo);
 
70
 
 
71
    STDMETHODIMP GetTypeInfo(
 
72
      UINT itinfo,
 
73
      LCID lcid,
 
74
      __deref_out ITypeInfo ** pptinfo);
 
75
 
 
76
    STDMETHODIMP GetIDsOfNames(
 
77
      REFIID riid,
 
78
      __in_ecount(cNames) LPOLESTR * rgszNames,
 
79
      UINT cNames,
 
80
      LCID lcid,
 
81
      __out_ecount(cNames) DISPID * rgdispid);
 
82
 
 
83
    STDMETHODIMP Invoke(
 
84
      DISPID dispidMember,
 
85
      REFIID riid,
 
86
      LCID lcid,
 
87
      WORD wFlags,
 
88
      __in DISPPARAMS * pdispparams,
 
89
      __out_opt VARIANT * pvarResult,
 
90
      __out_opt EXCEPINFO * pexcepinfo,
 
91
      __out_opt UINT * puArgErr);
 
92
};
 
93
 
 
94
 
 
95
class AM_NOVTABLE CMediaEvent :
 
96
    public IMediaEventEx,
 
97
    public CUnknown
 
98
{
 
99
    CBaseDispatch m_basedisp;
 
100
 
 
101
public:
 
102
 
 
103
    CMediaEvent(__in_opt LPCTSTR, __in_opt LPUNKNOWN);
 
104
 
 
105
    DECLARE_IUNKNOWN
 
106
 
 
107
    // override this to publicise our interfaces
 
108
    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, __deref_out void **ppv);
 
109
 
 
110
    /* IDispatch methods */
 
111
    STDMETHODIMP GetTypeInfoCount(__out UINT * pctinfo);
 
112
 
 
113
    STDMETHODIMP GetTypeInfo(
 
114
      UINT itinfo,
 
115
      LCID lcid,
 
116
      __deref_out ITypeInfo ** pptinfo);
 
117
 
 
118
    STDMETHODIMP GetIDsOfNames(
 
119
      REFIID riid,
 
120
      __in_ecount(cNames) LPOLESTR * rgszNames,
 
121
      UINT cNames,
 
122
      LCID lcid,
 
123
      __out_ecount(cNames) DISPID * rgdispid);
 
124
 
 
125
    STDMETHODIMP Invoke(
 
126
      DISPID dispidMember,
 
127
      REFIID riid,
 
128
      LCID lcid,
 
129
      WORD wFlags,
 
130
      __in DISPPARAMS * pdispparams,
 
131
      __out_opt VARIANT * pvarResult,
 
132
      __out_opt EXCEPINFO * pexcepinfo,
 
133
      __out_opt UINT * puArgErr);
 
134
};
 
135
 
 
136
 
 
137
class AM_NOVTABLE CMediaPosition :
 
138
    public IMediaPosition,
 
139
    public CUnknown
 
140
{
 
141
    CBaseDispatch m_basedisp;
 
142
 
 
143
 
 
144
public:
 
145
 
 
146
    CMediaPosition(__in_opt LPCTSTR, __in_opt LPUNKNOWN);
 
147
    CMediaPosition(__in_opt LPCTSTR, __in_opt LPUNKNOWN, __inout HRESULT *phr);
 
148
 
 
149
    DECLARE_IUNKNOWN
 
150
 
 
151
    // override this to publicise our interfaces
 
152
    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, __deref_out void **ppv);
 
153
 
 
154
    /* IDispatch methods */
 
155
    STDMETHODIMP GetTypeInfoCount(__out UINT * pctinfo);
 
156
 
 
157
    STDMETHODIMP GetTypeInfo(
 
158
      UINT itinfo,
 
159
      LCID lcid,
 
160
      __deref_out ITypeInfo ** pptinfo);
 
161
 
 
162
    STDMETHODIMP GetIDsOfNames(
 
163
      REFIID riid,
 
164
      __in_ecount(cNames) LPOLESTR * rgszNames,
 
165
      UINT cNames,
 
166
      LCID lcid,
 
167
      __out_ecount(cNames) DISPID * rgdispid);
 
168
 
 
169
    STDMETHODIMP Invoke(
 
170
      DISPID dispidMember,
 
171
      REFIID riid,
 
172
      LCID lcid,
 
173
      WORD wFlags,
 
174
      __in DISPPARAMS * pdispparams,
 
175
      __out_opt VARIANT * pvarResult,
 
176
      __out_opt EXCEPINFO * pexcepinfo,
 
177
      __out_opt UINT * puArgErr);
 
178
 
 
179
};
 
180
 
 
181
 
 
182
// OA-compatibility means that we must use double as the RefTime value,
 
183
// and REFERENCE_TIME (essentially a LONGLONG) within filters.
 
184
// this class converts between the two
 
185
 
 
186
class COARefTime : public CRefTime {
 
187
public:
 
188
 
 
189
    COARefTime() {
 
190
    };
 
191
 
 
192
    COARefTime(CRefTime t)
 
193
        : CRefTime(t)
 
194
    {
 
195
    };
 
196
 
 
197
    COARefTime(REFERENCE_TIME t)
 
198
        : CRefTime(t)
 
199
    {
 
200
    };
 
201
 
 
202
    COARefTime(double d) {
 
203
        m_time = (LONGLONG) (d * 10000000);
 
204
    };
 
205
 
 
206
    operator double() {
 
207
        return double(m_time) / 10000000;
 
208
    };
 
209
 
 
210
    operator REFERENCE_TIME() {
 
211
        return m_time;
 
212
    };
 
213
 
 
214
    COARefTime& operator=(const double& rd)  {
 
215
        m_time = (LONGLONG) (rd * 10000000);
 
216
        return *this;
 
217
    }
 
218
 
 
219
    COARefTime& operator=(const REFERENCE_TIME& rt)  {
 
220
        m_time = rt;
 
221
        return *this;
 
222
    }
 
223
 
 
224
    inline BOOL operator==(const COARefTime& rt)
 
225
    {
 
226
        return m_time == rt.m_time;
 
227
    };
 
228
 
 
229
    inline BOOL operator!=(const COARefTime& rt)
 
230
    {
 
231
        return m_time != rt.m_time;
 
232
    };
 
233
 
 
234
    inline BOOL operator < (const COARefTime& rt)
 
235
    {
 
236
        return m_time < rt.m_time;
 
237
    };
 
238
 
 
239
    inline BOOL operator > (const COARefTime& rt)
 
240
    {
 
241
        return m_time > rt.m_time;
 
242
    };
 
243
 
 
244
    inline BOOL operator >= (const COARefTime& rt)
 
245
    {
 
246
        return m_time >= rt.m_time;
 
247
    };
 
248
 
 
249
    inline BOOL operator <= (const COARefTime& rt)
 
250
    {
 
251
        return m_time <= rt.m_time;
 
252
    };
 
253
 
 
254
    inline COARefTime operator+(const COARefTime& rt)
 
255
    {
 
256
        return COARefTime(m_time + rt.m_time);
 
257
    };
 
258
 
 
259
    inline COARefTime operator-(const COARefTime& rt)
 
260
    {
 
261
        return COARefTime(m_time - rt.m_time);
 
262
    };
 
263
 
 
264
    inline COARefTime operator*(LONG l)
 
265
    {
 
266
        return COARefTime(m_time * l);
 
267
    };
 
268
 
 
269
    inline COARefTime operator/(LONG l)
 
270
    {
 
271
        return COARefTime(m_time / l);
 
272
    };
 
273
 
 
274
private:
 
275
    //  Prevent bugs from constructing from LONG (which gets
 
276
    //  converted to double and then multiplied by 10000000
 
277
    COARefTime(LONG);
 
278
    LONG operator=(LONG);
 
279
};
 
280
 
 
281
 
 
282
// A utility class that handles IMediaPosition and IMediaSeeking on behalf
 
283
// of single-input pin renderers, or transform filters.
 
284
//
 
285
// Renderers will expose this from the filter; transform filters will
 
286
// expose it from the output pin and not the renderer.
 
287
//
 
288
// Create one of these, giving it your IPin* for your input pin, and delegate
 
289
// all IMediaPosition methods to it. It will query the input pin for
 
290
// IMediaPosition and respond appropriately.
 
291
//
 
292
// Call ForceRefresh if the pin connection changes.
 
293
//
 
294
// This class no longer caches the upstream IMediaPosition or IMediaSeeking
 
295
// it acquires it on each method call. This means ForceRefresh is not needed.
 
296
// The method is kept for source compatibility and to minimise the changes
 
297
// if we need to put it back later for performance reasons.
 
298
 
 
299
class CPosPassThru : public IMediaSeeking, public CMediaPosition
 
300
{
 
301
    IPin *m_pPin;
 
302
 
 
303
    HRESULT GetPeer(__deref_out IMediaPosition **ppMP);
 
304
    HRESULT GetPeerSeeking(__deref_out IMediaSeeking **ppMS);
 
305
 
 
306
public:
 
307
 
 
308
    CPosPassThru(__in_opt LPCTSTR, __in_opt LPUNKNOWN, __inout HRESULT*, IPin *);
 
309
    DECLARE_IUNKNOWN
 
310
 
 
311
    HRESULT ForceRefresh() {
 
312
        return S_OK;
 
313
    };
 
314
 
 
315
    // override to return an accurate current position
 
316
    virtual HRESULT GetMediaTime(__out LONGLONG *pStartTime, __out_opt LONGLONG *pEndTime) {
 
317
        return E_FAIL;
 
318
    }
 
319
 
 
320
    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid,__deref_out void **ppv);
 
321
 
 
322
    // IMediaSeeking methods
 
323
    STDMETHODIMP GetCapabilities( __out DWORD * pCapabilities );
 
324
    STDMETHODIMP CheckCapabilities( __inout DWORD * pCapabilities );
 
325
    STDMETHODIMP SetTimeFormat(const GUID * pFormat);
 
326
    STDMETHODIMP GetTimeFormat(__out GUID *pFormat);
 
327
    STDMETHODIMP IsUsingTimeFormat(const GUID * pFormat);
 
328
    STDMETHODIMP IsFormatSupported( const GUID * pFormat);
 
329
    STDMETHODIMP QueryPreferredFormat( __out GUID *pFormat);
 
330
    STDMETHODIMP ConvertTimeFormat(__out LONGLONG * pTarget, 
 
331
                                   __in_opt const GUID * pTargetFormat,
 
332
                                   LONGLONG Source, 
 
333
                                   __in_opt const GUID * pSourceFormat );
 
334
    STDMETHODIMP SetPositions( __inout_opt LONGLONG * pCurrent, DWORD CurrentFlags
 
335
                             , __inout_opt LONGLONG * pStop, DWORD StopFlags );
 
336
 
 
337
    STDMETHODIMP GetPositions( __out_opt LONGLONG * pCurrent, __out_opt LONGLONG * pStop );
 
338
    STDMETHODIMP GetCurrentPosition( __out LONGLONG * pCurrent );
 
339
    STDMETHODIMP GetStopPosition( __out LONGLONG * pStop );
 
340
    STDMETHODIMP SetRate( double dRate);
 
341
    STDMETHODIMP GetRate( __out double * pdRate);
 
342
    STDMETHODIMP GetDuration( __out LONGLONG *pDuration);
 
343
    STDMETHODIMP GetAvailable( __out_opt LONGLONG *pEarliest, __out_opt LONGLONG *pLatest );
 
344
    STDMETHODIMP GetPreroll( __out LONGLONG *pllPreroll );
 
345
 
 
346
    // IMediaPosition properties
 
347
    STDMETHODIMP get_Duration(__out REFTIME * plength);
 
348
    STDMETHODIMP put_CurrentPosition(REFTIME llTime);
 
349
    STDMETHODIMP get_StopTime(__out REFTIME * pllTime);
 
350
    STDMETHODIMP put_StopTime(REFTIME llTime);
 
351
    STDMETHODIMP get_PrerollTime(__out REFTIME * pllTime);
 
352
    STDMETHODIMP put_PrerollTime(REFTIME llTime);
 
353
    STDMETHODIMP get_Rate(__out double * pdRate);
 
354
    STDMETHODIMP put_Rate(double dRate);
 
355
    STDMETHODIMP get_CurrentPosition(__out REFTIME * pllTime);
 
356
    STDMETHODIMP CanSeekForward(__out LONG *pCanSeekForward);
 
357
    STDMETHODIMP CanSeekBackward(__out LONG *pCanSeekBackward);
 
358
 
 
359
private:
 
360
    HRESULT GetSeekingLongLong( HRESULT (__stdcall IMediaSeeking::*pMethod)( LONGLONG * ),
 
361
                                __out LONGLONG * pll );
 
362
};
 
363
 
 
364
 
 
365
// Adds the ability to return a current position
 
366
 
 
367
class CRendererPosPassThru : public CPosPassThru
 
368
{
 
369
    CCritSec m_PositionLock;    // Locks access to our position
 
370
    LONGLONG m_StartMedia;      // Start media time last seen
 
371
    LONGLONG m_EndMedia;        // And likewise the end media
 
372
    BOOL m_bReset;              // Have media times been set
 
373
 
 
374
public:
 
375
 
 
376
    // Used to help with passing media times through graph
 
377
 
 
378
    CRendererPosPassThru(__in_opt LPCTSTR, __in_opt LPUNKNOWN, __inout HRESULT*, IPin *);
 
379
    HRESULT RegisterMediaTime(IMediaSample *pMediaSample);
 
380
    HRESULT RegisterMediaTime(LONGLONG StartTime,LONGLONG EndTime);
 
381
    HRESULT GetMediaTime(__out LONGLONG *pStartTime,__out_opt LONGLONG *pEndTime);
 
382
    HRESULT ResetMediaTime();
 
383
    HRESULT EOS();
 
384
};
 
385
 
 
386
STDAPI CreatePosPassThru(
 
387
    __in_opt LPUNKNOWN pAgg,
 
388
    BOOL bRenderer,
 
389
    IPin *pPin,
 
390
    __deref_out IUnknown **ppPassThru
 
391
);
 
392
 
 
393
// A class that handles the IDispatch part of IBasicAudio and leaves the
 
394
// properties and methods themselves pure virtual.
 
395
 
 
396
class AM_NOVTABLE CBasicAudio : public IBasicAudio, public CUnknown
 
397
{
 
398
    CBaseDispatch m_basedisp;
 
399
 
 
400
public:
 
401
 
 
402
    CBasicAudio(__in_opt LPCTSTR, __in_opt LPUNKNOWN);
 
403
 
 
404
    DECLARE_IUNKNOWN
 
405
 
 
406
    // override this to publicise our interfaces
 
407
    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, __deref_out void **ppv);
 
408
 
 
409
    /* IDispatch methods */
 
410
    STDMETHODIMP GetTypeInfoCount(__out UINT * pctinfo);
 
411
 
 
412
    STDMETHODIMP GetTypeInfo(
 
413
      UINT itinfo,
 
414
      LCID lcid,
 
415
      __deref_out ITypeInfo ** pptinfo);
 
416
 
 
417
    STDMETHODIMP GetIDsOfNames(
 
418
      REFIID riid,
 
419
      __in_ecount(cNames) LPOLESTR * rgszNames,
 
420
      UINT cNames,
 
421
      LCID lcid,
 
422
      __out_ecount(cNames) DISPID * rgdispid);
 
423
 
 
424
    STDMETHODIMP Invoke(
 
425
      DISPID dispidMember,
 
426
      REFIID riid,
 
427
      LCID lcid,
 
428
      WORD wFlags,
 
429
      __in DISPPARAMS * pdispparams,
 
430
      __out_opt VARIANT * pvarResult,
 
431
      __out_opt EXCEPINFO * pexcepinfo,
 
432
      __out_opt UINT * puArgErr);
 
433
};
 
434
 
 
435
 
 
436
// A class that handles the IDispatch part of IBasicVideo and leaves the
 
437
// properties and methods themselves pure virtual.
 
438
 
 
439
class AM_NOVTABLE CBaseBasicVideo : public IBasicVideo2, public CUnknown
 
440
{
 
441
    CBaseDispatch m_basedisp;
 
442
 
 
443
public:
 
444
 
 
445
    CBaseBasicVideo(__in_opt LPCTSTR, __in_opt LPUNKNOWN);
 
446
 
 
447
    DECLARE_IUNKNOWN
 
448
 
 
449
    // override this to publicise our interfaces
 
450
    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, __deref_out void **ppv);
 
451
 
 
452
    /* IDispatch methods */
 
453
    STDMETHODIMP GetTypeInfoCount(__out UINT * pctinfo);
 
454
 
 
455
    STDMETHODIMP GetTypeInfo(
 
456
      UINT itinfo,
 
457
      LCID lcid,
 
458
      __deref_out ITypeInfo ** pptinfo);
 
459
 
 
460
    STDMETHODIMP GetIDsOfNames(
 
461
      REFIID riid,
 
462
      __in_ecount(cNames) LPOLESTR * rgszNames,
 
463
      UINT cNames,
 
464
      LCID lcid,
 
465
      __out_ecount(cNames) DISPID * rgdispid);
 
466
 
 
467
    STDMETHODIMP Invoke(
 
468
      DISPID dispidMember,
 
469
      REFIID riid,
 
470
      LCID lcid,
 
471
      WORD wFlags,
 
472
      __in DISPPARAMS * pdispparams,
 
473
      __out_opt VARIANT * pvarResult,
 
474
      __out_opt EXCEPINFO * pexcepinfo,
 
475
      __out_opt UINT * puArgErr);
 
476
 
 
477
    STDMETHODIMP GetPreferredAspectRatio(
 
478
      __out long *plAspectX,
 
479
      __out long *plAspectY)
 
480
    {
 
481
        return E_NOTIMPL;
 
482
    }
 
483
};
 
484
 
 
485
 
 
486
// A class that handles the IDispatch part of IVideoWindow and leaves the
 
487
// properties and methods themselves pure virtual.
 
488
 
 
489
class AM_NOVTABLE CBaseVideoWindow : public IVideoWindow, public CUnknown
 
490
{
 
491
    CBaseDispatch m_basedisp;
 
492
 
 
493
public:
 
494
 
 
495
    CBaseVideoWindow(__in_opt LPCTSTR, __in_opt LPUNKNOWN);
 
496
 
 
497
    DECLARE_IUNKNOWN
 
498
 
 
499
    // override this to publicise our interfaces
 
500
    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, __deref_out void **ppv);
 
501
 
 
502
    /* IDispatch methods */
 
503
    STDMETHODIMP GetTypeInfoCount(__out UINT * pctinfo);
 
504
 
 
505
    STDMETHODIMP GetTypeInfo(
 
506
      UINT itinfo,
 
507
      LCID lcid,
 
508
      __deref_out ITypeInfo ** pptinfo);
 
509
 
 
510
    STDMETHODIMP GetIDsOfNames(
 
511
      REFIID riid,
 
512
      __in_ecount(cNames) LPOLESTR * rgszNames,
 
513
      UINT cNames,
 
514
      LCID lcid,
 
515
      __out_ecount(cNames) DISPID * rgdispid);
 
516
 
 
517
    STDMETHODIMP Invoke(
 
518
      DISPID dispidMember,
 
519
      REFIID riid,
 
520
      LCID lcid,
 
521
      WORD wFlags,
 
522
      __in DISPPARAMS * pdispparams,
 
523
      __out_opt VARIANT * pvarResult,
 
524
      __out_opt EXCEPINFO * pexcepinfo,
 
525
      __out_opt UINT * puArgErr);
 
526
};
 
527
 
 
528
 
 
529
// abstract class to help source filters with their implementation
 
530
// of IMediaPosition. Derive from this and set the duration (and stop
 
531
// position). Also override NotifyChange to do something when the properties
 
532
// change.
 
533
 
 
534
class AM_NOVTABLE CSourcePosition : public CMediaPosition
 
535
{
 
536
 
 
537
public:
 
538
    CSourcePosition(__in_opt LPCTSTR, __in_opt LPUNKNOWN, __inout HRESULT*, __in CCritSec *);
 
539
 
 
540
    // IMediaPosition methods
 
541
    STDMETHODIMP get_Duration(__out REFTIME * plength);
 
542
    STDMETHODIMP put_CurrentPosition(REFTIME llTime);
 
543
    STDMETHODIMP get_StopTime(__out REFTIME * pllTime);
 
544
    STDMETHODIMP put_StopTime(REFTIME llTime);
 
545
    STDMETHODIMP get_PrerollTime(__out REFTIME * pllTime);
 
546
    STDMETHODIMP put_PrerollTime(REFTIME llTime);
 
547
    STDMETHODIMP get_Rate(__out double * pdRate);
 
548
    STDMETHODIMP put_Rate(double dRate);
 
549
    STDMETHODIMP CanSeekForward(__out LONG *pCanSeekForward);
 
550
    STDMETHODIMP CanSeekBackward(__out LONG *pCanSeekBackward);
 
551
 
 
552
    // override if you can return the data you are actually working on
 
553
    STDMETHODIMP get_CurrentPosition(__out REFTIME * pllTime) {
 
554
        return E_NOTIMPL;
 
555
    };
 
556
 
 
557
protected:
 
558
 
 
559
    // we call this to notify changes. Override to handle them
 
560
    virtual HRESULT ChangeStart() PURE;
 
561
    virtual HRESULT ChangeStop() PURE;
 
562
    virtual HRESULT ChangeRate() PURE;
 
563
 
 
564
    COARefTime m_Duration;
 
565
    COARefTime m_Start;
 
566
    COARefTime m_Stop;
 
567
    double m_Rate;
 
568
 
 
569
    CCritSec * m_pLock;
 
570
};
 
571
 
 
572
class AM_NOVTABLE CSourceSeeking :
 
573
    public IMediaSeeking,
 
574
    public CUnknown
 
575
{
 
576
 
 
577
public:
 
578
 
 
579
    DECLARE_IUNKNOWN;
 
580
    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, __deref_out void **ppv);
 
581
 
 
582
    // IMediaSeeking methods
 
583
 
 
584
    STDMETHODIMP IsFormatSupported(const GUID * pFormat);
 
585
    STDMETHODIMP QueryPreferredFormat(__out GUID *pFormat);
 
586
    STDMETHODIMP SetTimeFormat(const GUID * pFormat);
 
587
    STDMETHODIMP IsUsingTimeFormat(const GUID * pFormat);
 
588
    STDMETHODIMP GetTimeFormat(__out GUID *pFormat);
 
589
    STDMETHODIMP GetDuration(__out LONGLONG *pDuration);
 
590
    STDMETHODIMP GetStopPosition(__out LONGLONG *pStop);
 
591
    STDMETHODIMP GetCurrentPosition(__out LONGLONG *pCurrent);
 
592
    STDMETHODIMP GetCapabilities( __out DWORD * pCapabilities );
 
593
    STDMETHODIMP CheckCapabilities( __inout DWORD * pCapabilities );
 
594
    STDMETHODIMP ConvertTimeFormat( __out LONGLONG * pTarget, 
 
595
                                    __in_opt const GUID * pTargetFormat,
 
596
                                    LONGLONG Source, 
 
597
                                    __in_opt const GUID * pSourceFormat );
 
598
 
 
599
    STDMETHODIMP SetPositions( __inout_opt LONGLONG * pCurrent,  DWORD CurrentFlags
 
600
                             , __inout_opt LONGLONG * pStop,  DWORD StopFlags );
 
601
 
 
602
    STDMETHODIMP GetPositions( __out_opt LONGLONG * pCurrent, __out_opt LONGLONG * pStop );
 
603
 
 
604
    STDMETHODIMP GetAvailable( __out_opt LONGLONG * pEarliest, __out_opt LONGLONG * pLatest );
 
605
    STDMETHODIMP SetRate( double dRate);
 
606
    STDMETHODIMP GetRate( __out double * pdRate);
 
607
    STDMETHODIMP GetPreroll(__out LONGLONG *pPreroll);
 
608
 
 
609
 
 
610
protected:
 
611
 
 
612
    // ctor
 
613
    CSourceSeeking(__in_opt LPCTSTR, __in_opt LPUNKNOWN, __inout HRESULT*, __in CCritSec *);
 
614
 
 
615
    // we call this to notify changes. Override to handle them
 
616
    virtual HRESULT ChangeStart() PURE;
 
617
    virtual HRESULT ChangeStop() PURE;
 
618
    virtual HRESULT ChangeRate() PURE;
 
619
 
 
620
    CRefTime m_rtDuration;      // length of stream
 
621
    CRefTime m_rtStart;         // source will start here
 
622
    CRefTime m_rtStop;          // source will stop here
 
623
    double m_dRateSeeking;
 
624
 
 
625
    // seeking capabilities
 
626
    DWORD m_dwSeekingCaps;
 
627
 
 
628
    CCritSec * m_pLock;
 
629
};
 
630
 
 
631
 
 
632
// Base classes supporting Deferred commands.
 
633
 
 
634
// Deferred commands are queued by calls to methods on the IQueueCommand
 
635
// interface, exposed by the filtergraph and by some filters. A successful
 
636
// call to one of these methods will return an IDeferredCommand interface
 
637
// representing the queued command.
 
638
//
 
639
// A CDeferredCommand object represents a single deferred command, and exposes
 
640
// the IDeferredCommand interface as well as other methods permitting time
 
641
// checks and actual execution. It contains a reference to the CCommandQueue
 
642
// object on which it is queued.
 
643
//
 
644
// CCommandQueue is a base class providing a queue of CDeferredCommand
 
645
// objects, and methods to add, remove, check status and invoke the queued
 
646
// commands. A CCommandQueue object would be part of an object that
 
647
// implemented IQueueCommand.
 
648
 
 
649
class CCmdQueue;
 
650
 
 
651
// take a copy of the params and store them. Release any allocated
 
652
// memory in destructor
 
653
 
 
654
class CDispParams : public DISPPARAMS
 
655
{
 
656
public:
 
657
    CDispParams(UINT nArgs, __in_ecount(nArgs) VARIANT* pArgs, __inout_opt HRESULT *phr = NULL);
 
658
    ~CDispParams();
 
659
};
 
660
 
 
661
 
 
662
// CDeferredCommand lifetime is controlled by refcounts. Caller of
 
663
// InvokeAt.. gets a refcounted interface pointer, and the CCmdQueue
 
664
// object also holds a refcount on us. Calling Cancel or Invoke takes
 
665
// us off the CCmdQueue and thus reduces the refcount by 1. Once taken
 
666
// off the queue we cannot be put back on the queue.
 
667
 
 
668
class CDeferredCommand
 
669
    : public CUnknown,
 
670
      public IDeferredCommand
 
671
{
 
672
public:
 
673
 
 
674
    CDeferredCommand(
 
675
        __inout CCmdQueue * pQ,
 
676
        __in_opt LPUNKNOWN   pUnk,               // aggregation outer unk
 
677
        __inout HRESULT *   phr,
 
678
        __in LPUNKNOWN   pUnkExecutor,       // object that will execute this cmd
 
679
        REFTIME     time,
 
680
        __in GUID*       iid,
 
681
        long        dispidMethod,
 
682
        short       wFlags,
 
683
        long        cArgs,
 
684
        __in_ecount(cArgs) VARIANT*    pDispParams,
 
685
        __out VARIANT*    pvarResult,
 
686
        __out short*      puArgErr,
 
687
        BOOL        bStream
 
688
        );
 
689
 
 
690
    DECLARE_IUNKNOWN
 
691
 
 
692
    // override this to publicise our interfaces
 
693
    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, __out void **ppv);
 
694
 
 
695
    // IDeferredCommand methods
 
696
    STDMETHODIMP Cancel();
 
697
    STDMETHODIMP Confidence(
 
698
                    __out LONG* pConfidence);
 
699
    STDMETHODIMP Postpone(
 
700
                    REFTIME newtime);
 
701
    STDMETHODIMP GetHResult(
 
702
                    __out HRESULT* phrResult);
 
703
 
 
704
    // other public methods
 
705
 
 
706
    HRESULT Invoke();
 
707
 
 
708
    // access methods
 
709
 
 
710
    // returns TRUE if streamtime, FALSE if presentation time
 
711
    BOOL IsStreamTime() {
 
712
       return m_bStream;
 
713
    };
 
714
 
 
715
    CRefTime GetTime() {
 
716
        return m_time;
 
717
    };
 
718
 
 
719
    REFIID GetIID() {
 
720
        return *m_iid;
 
721
    };
 
722
 
 
723
    long GetMethod() {
 
724
        return m_dispidMethod;
 
725
    };
 
726
 
 
727
    short GetFlags() {
 
728
        return m_wFlags;
 
729
    };
 
730
 
 
731
    DISPPARAMS* GetParams() {
 
732
        return &m_DispParams;
 
733
    };
 
734
 
 
735
    VARIANT* GetResult() {
 
736
        return m_pvarResult;
 
737
    };
 
738
 
 
739
protected:
 
740
 
 
741
    CCmdQueue* m_pQueue;
 
742
 
 
743
    // pUnk for the interface that we will execute the command on
 
744
    LPUNKNOWN   m_pUnk;
 
745
 
 
746
    // stored command data
 
747
    REFERENCE_TIME     m_time;
 
748
    GUID*       m_iid;
 
749
    long        m_dispidMethod;
 
750
    short       m_wFlags;
 
751
    VARIANT*    m_pvarResult;
 
752
    BOOL        m_bStream;
 
753
    CDispParams m_DispParams;
 
754
    DISPID      m_DispId;         //  For get and put
 
755
 
 
756
    // we use this for ITypeInfo access
 
757
    CBaseDispatch   m_Dispatch;
 
758
 
 
759
    // save retval here
 
760
    HRESULT     m_hrResult;
 
761
};
 
762
 
 
763
 
 
764
// a list of CDeferredCommand objects. this is a base class providing
 
765
// the basics of access to the list. If you want to use CDeferredCommand
 
766
// objects then your queue needs to be derived from this class.
 
767
 
 
768
class AM_NOVTABLE CCmdQueue
 
769
{
 
770
public:
 
771
    CCmdQueue(__inout_opt HRESULT *phr = NULL);
 
772
    virtual ~CCmdQueue();
 
773
 
 
774
    // returns a new CDeferredCommand object that will be initialised with
 
775
    // the parameters and will be added to the queue during construction.
 
776
    // returns S_OK if successfully created otherwise an error and
 
777
    // no object has been queued.
 
778
    virtual HRESULT  New(
 
779
        __out CDeferredCommand **ppCmd,
 
780
        __in LPUNKNOWN   pUnk,
 
781
        REFTIME     time,
 
782
        __in GUID*       iid,
 
783
        long        dispidMethod,
 
784
        short       wFlags,
 
785
        long        cArgs,
 
786
        __in_ecount(cArgs) VARIANT*    pDispParams,
 
787
        __out VARIANT*    pvarResult,
 
788
        __out short*      puArgErr,
 
789
        BOOL        bStream
 
790
    );
 
791
 
 
792
    // called by the CDeferredCommand object to add and remove itself
 
793
    // from the queue
 
794
    virtual HRESULT Insert(__in CDeferredCommand* pCmd);
 
795
    virtual HRESULT Remove(__in CDeferredCommand* pCmd);
 
796
 
 
797
    // Command-Due Checking
 
798
    //
 
799
    // There are two schemes of synchronisation: coarse and accurate. In
 
800
    // coarse mode, you wait till the time arrives and then execute the cmd.
 
801
    // In accurate mode, you wait until you are processing the sample that
 
802
    // will appear at the time, and then execute the command. It's up to the
 
803
    // filter which one it will implement. The filtergraph will always
 
804
    // implement coarse mode for commands queued at the filtergraph.
 
805
    //
 
806
    // If you want coarse sync, you probably want to wait until there is a
 
807
    // command due, and then execute it. You can do this by calling
 
808
    // GetDueCommand. If you have several things to wait for, get the
 
809
    // event handle from GetDueHandle() and when this is signalled then call
 
810
    // GetDueCommand. Stream time will only advance between calls to Run and
 
811
    // EndRun. Note that to avoid an extra thread there is no guarantee that
 
812
    // if the handle is set there will be a command ready. Each time the
 
813
    // event is signalled, call GetDueCommand (probably with a 0 timeout);
 
814
    // This may return E_ABORT.
 
815
    //
 
816
    // If you want accurate sync, you must call GetCommandDueFor, passing
 
817
    // as a parameter the stream time of the samples you are about to process.
 
818
    // This will return:
 
819
    //   -- a stream-time command due at or before that stream time
 
820
    //   -- a presentation-time command due at or before the
 
821
    //      time that stream time will be presented (only between Run
 
822
    //      and EndRun calls, since outside of this, the mapping from
 
823
    //      stream time to presentation time is not known.
 
824
    //   -- any presentation-time command due now.
 
825
    // This means that if you want accurate synchronisation on samples that
 
826
    // might be processed during Paused mode, you need to use
 
827
    // stream-time commands.
 
828
    //
 
829
    // In all cases, commands remain queued until Invoked or Cancelled. The
 
830
    // setting and resetting of the event handle is managed entirely by this
 
831
    // queue object.
 
832
 
 
833
    // set the clock used for timing
 
834
    virtual HRESULT SetSyncSource(__in_opt IReferenceClock*);
 
835
 
 
836
    // switch to run mode. Streamtime to Presentation time mapping known.
 
837
    virtual HRESULT Run(REFERENCE_TIME tStreamTimeOffset);
 
838
 
 
839
    // switch to Stopped or Paused mode. Time mapping not known.
 
840
    virtual HRESULT EndRun();
 
841
 
 
842
    // return a pointer to the next due command. Blocks for msTimeout
 
843
    // milliseconds until there is a due command.
 
844
    // Stream-time commands will only become due between Run and Endrun calls.
 
845
    // The command remains queued until invoked or cancelled.
 
846
    // Returns E_ABORT if timeout occurs, otherwise S_OK (or other error).
 
847
    // Returns an AddRef-ed object
 
848
    virtual HRESULT GetDueCommand(__out CDeferredCommand ** ppCmd, long msTimeout);
 
849
 
 
850
    // return the event handle that will be signalled whenever
 
851
    // there are deferred commands due for execution (when GetDueCommand
 
852
    // will not block).
 
853
    HANDLE GetDueHandle() {
 
854
        return HANDLE(m_evDue);
 
855
    };
 
856
 
 
857
    // return a pointer to a command that will be due for a given time.
 
858
    // Pass in a stream time here. The stream time offset will be passed
 
859
    // in via the Run method.
 
860
    // Commands remain queued until invoked or cancelled.
 
861
    // This method will not block. It will report VFW_E_NOT_FOUND if there
 
862
    // are no commands due yet.
 
863
    // Returns an AddRef-ed object
 
864
    virtual HRESULT GetCommandDueFor(REFERENCE_TIME tStream, __out CDeferredCommand**ppCmd);
 
865
 
 
866
    // check if a given time is due (TRUE if it is due yet)
 
867
    BOOL CheckTime(CRefTime time, BOOL bStream) {
 
868
 
 
869
        // if no clock, nothing is due!
 
870
        if (!m_pClock) {
 
871
            return FALSE;
 
872
        }
 
873
 
 
874
        // stream time
 
875
        if (bStream) {
 
876
 
 
877
            // not valid if not running
 
878
            if (!m_bRunning) {
 
879
                return FALSE;
 
880
            }
 
881
            // add on known stream time offset to get presentation time
 
882
            time += m_StreamTimeOffset;
 
883
        }
 
884
 
 
885
        CRefTime Now;
 
886
        m_pClock->GetTime((REFERENCE_TIME*)&Now);
 
887
        return (time <= Now);
 
888
    };
 
889
 
 
890
protected:
 
891
 
 
892
    // protect access to lists etc
 
893
    CCritSec m_Lock;
 
894
 
 
895
    // commands queued in presentation time are stored here
 
896
    CGenericList<CDeferredCommand> m_listPresentation;
 
897
 
 
898
    // commands queued in stream time are stored here
 
899
    CGenericList<CDeferredCommand> m_listStream;
 
900
 
 
901
    // set when any commands are due
 
902
    CAMEvent m_evDue;
 
903
 
 
904
    // creates an advise for the earliest time required, if any
 
905
    void SetTimeAdvise(void);
 
906
 
 
907
    // advise id from reference clock (0 if no outstanding advise)
 
908
    DWORD_PTR m_dwAdvise;
 
909
 
 
910
    // advise time is for this presentation time
 
911
    CRefTime m_tCurrentAdvise;
 
912
 
 
913
    // the reference clock we are using (addrefed)
 
914
    IReferenceClock* m_pClock;
 
915
 
 
916
    // true when running
 
917
    BOOL m_bRunning;
 
918
 
 
919
    // contains stream time offset when m_bRunning is true
 
920
    CRefTime m_StreamTimeOffset;
 
921
};
 
922
 
 
923
#endif // __CTLUTIL__