1 /////////////////////////////////////////////////////////////////////////////
2 // Name: src/msw/mediactrl_am.cpp
3 // Purpose: ActiveMovie/WMP6/PocketPC 2000 Media Backend for Windows
4 // Author: Ryan Norton <wxprojects@comcast.net>
5 // Modified by:
6 // Created: 01/29/05
7 // Copyright: (c) Ryan Norton
8 // Licence: wxWindows licence
9 /////////////////////////////////////////////////////////////////////////////
10
11 // TODO: Actually test HTTP proxies...
12
13 //-----------------Introduction----------------------------------------------
14 // This is the media backend for Windows Media Player 6 and ActiveMovie.
15 //
16 // We use a combination of the WMP 6 IMediaPlayer interface as well as the
17 // ActiveMovie interface IActiveMovie.
18 //
19 // For supporting HTTP proxies and such we query the media player
20 // interface (IActiveMovie) for the INSPlay (NetShow) interface.
21 //
22 // The IMediaPlayer/IActiveMovie are rather clean and straightforward
23 // interfaces that are fairly simplistic.
24 //
25 // Docs for IMediaPlayer are at
26 // http://msdn.microsoft.com/library/en-us/wmp6sdk/htm/microsoftwindowsmediaplayercontrolversion64sdk.asp
27
28 //===========================================================================
29 // DECLARATIONS
30 //===========================================================================
31
32 //---------------------------------------------------------------------------
33 // Pre-compiled header stuff
34 //---------------------------------------------------------------------------
35
36 // For compilers that support precompilation, includes "wx.h".
37 #include "wx/wxprec.h"
38
39
40 #if wxUSE_MEDIACTRL && wxUSE_ACTIVEX
41
42 #include "wx/mediactrl.h"
43
44 #ifndef WX_PRECOMP
45 #include "wx/log.h"
46 #include "wx/dcclient.h"
47 #include "wx/timer.h"
48 #include "wx/math.h" // log10 & pow
49 #include "wx/stopwatch.h"
50 #endif
51
52 #include "wx/msw/private.h" // user info and wndproc setting/getting
53 #include "wx/dynlib.h"
54
55 //---------------------------------------------------------------------------
56 // wxActiveXContainer - includes all the COM-specific stuff we need
57 //---------------------------------------------------------------------------
58 #include "wx/msw/ole/activex.h"
59
60 //---------------------------------------------------------------------------
61 // IIDS - used by CoCreateInstance and IUnknown::QueryInterface
62 //
63 // [idl name] [idl decription]
64 // amcompat.idl Microsoft Active Movie Control (Ver 2.0)
65 // nscompat.idl Microsoft NetShow Player (Ver 1.0)
66 // msdxm.idl Windows Media Player (Ver 1.0)
67 // quartz.idl
68 //
69 // First, when I say I "from XXX.idl", I mean I go into the COM Browser
70 // ($Microsoft Visual Studio$/Common/Tools/OLEVIEW.EXE), open
71 // "type libraries", open a specific type library (for quartz for example its
72 // "ActiveMovie control type library (V1.0)"), save it as an .idl, compile the
73 // idl using the midl compiler that comes with visual studio with the /h
74 // argument to make it generate stubs (a .h & .c file), then clean up the
75 // generated interfaces I want with the STDMETHOD wrappers and then put them
76 // into mediactrl.cpp.
77 //
78 // Some of these are not used but are kept here for future reference anyway
79 //---------------------------------------------------------------------------
80 wxCLANG_WARNING_SUPPRESS(unused-const-variable)
81 const IID IID_IActiveMovie = {0x05589FA2,0xC356,0x11CE,{0xBF,0x01,0x00,0xAA,0x00,0x55,0x59,0x5A}};
82 const IID IID_IActiveMovie2 = {0xB6CD6554,0xE9CB,0x11D0,{0x82,0x1F,0x00,0xA0,0xC9,0x1F,0x9C,0xA0}};
83 const IID IID_IActiveMovie3 = {0x265EC140,0xAE62,0x11D1,{0x85,0x00,0x00,0xA0,0xC9,0x1F,0x9C,0xA0}};
84
85 const IID IID_INSOPlay = {0x2179C5D1,0xEBFF,0x11CF,{0xB6,0xFD,0x00,0xAA,0x00,0xB4,0xE2,0x20}};
86 const IID IID_INSPlay = {0xE7C4BE80,0x7960,0x11D0,{0xB7,0x27,0x00,0xAA,0x00,0xB4,0xE2,0x20}};
87 const IID IID_INSPlay1 = {0x265EC141,0xAE62,0x11D1,{0x85,0x00,0x00,0xA0,0xC9,0x1F,0x9C,0xA0}};
88
89 const IID IID_IMediaPlayer = {0x22D6F311,0xB0F6,0x11D0,{0x94,0xAB,0x00,0x80,0xC7,0x4C,0x7E,0x95}};
90 const IID IID_IMediaPlayer2 = {0x20D4F5E0,0x5475,0x11D2,{0x97,0x74,0x00,0x00,0xF8,0x08,0x55,0xE6}};
91
92
93 const CLSID CLSID_ActiveMovie = {0x05589FA1,0xC356,0x11CE,{0xBF,0x01,0x00,0xAA,0x00,0x55,0x59,0x5A}};
94 const CLSID CLSID_MediaPlayer = {0x22D6F312,0xB0F6,0x11D0,{0x94,0xAB,0x00,0x80,0xC7,0x4C,0x7E,0x95}};
95 const CLSID CLSID_NSPlay = {0x2179C5D3,0xEBFF,0x11CF,{0xB6,0xFD,0x00,0xAA,0x00,0xB4,0xE2,0x20}};
96
97 const IID IID_IAMOpenProgress = {0x8E1C39A1, 0xDE53, 0x11CF,{0xAA, 0x63, 0x00, 0x80, 0xC7, 0x44, 0x52, 0x8D}};
98
99 // QUARTZ
100 const CLSID CLSID_FilgraphManager = {0xE436EBB3,0x524F,0x11CE,{0x9F,0x53,0x00,0x20,0xAF,0x0B,0xA7,0x70}};
101 const IID IID_IMediaEvent = {0x56A868B6,0x0AD4,0x11CE,{0xB0,0x3A,0x00,0x20,0xAF,0x0B,0xA7,0x70}};
102
103 //?? QUARTZ Also?
104 const CLSID CLSID_VideoMixingRenderer9 ={0x51B4ABF3, 0x748F, 0x4E3B,{0xA2, 0x76, 0xC8, 0x28, 0x33, 0x0E, 0x92, 0x6A}};
105 const IID IID_IVMRWindowlessControl9 = {0x8F537D09, 0xF85E, 0x4414,{0xB2, 0x3B, 0x50, 0x2E, 0x54, 0xC7, 0x99, 0x27}};
106 const IID IID_IFilterGraph = {0x56A8689F, 0x0AD4, 0x11CE,{0xB0, 0x3A, 0x00, 0x20, 0xAF, 0x0B, 0xA7, 0x70}};
107 const IID IID_IGraphBuilder = {0x56A868A9, 0x0AD4, 0x11CE,{0xB0, 0x3A, 0x00, 0x20, 0xAF, 0x0B, 0xA7, 0x70}};
108 const IID IID_IVMRFilterConfig9 = {0x5A804648, 0x4F66, 0x4867,{0x9C, 0x43, 0x4F, 0x5C, 0x82, 0x2C, 0xF1, 0xB8}};
109 const IID IID_IBaseFilter = {0x56A86895, 0x0AD4, 0x11CE,{0xB0, 0x3A, 0x00, 0x20, 0xAF, 0x0B, 0xA7, 0x70}};
110 wxCLANG_WARNING_RESTORE(unused-const-variable)
111
112 //---------------------------------------------------------------------------
113 // QUARTZ COM INTERFACES (dumped from quartz.idl from MSVC COM Browser)
114 //---------------------------------------------------------------------------
115
116 struct IAMOpenProgress : public IUnknown
117 {
118 STDMETHOD(QueryProgress)(LONGLONG *pllTotal, LONGLONG *pllCurrent) PURE;
119 STDMETHOD(AbortOperation)(void) PURE;
120 };
121
122 struct IMediaEvent : public IDispatch
123 {
124 STDMETHOD(GetEventHandle)(LONG_PTR *) PURE;
125 STDMETHOD(GetEvent)(long *, LONG_PTR *, LONG_PTR *, long) PURE;
126 STDMETHOD(WaitForCompletion)(long, long *) PURE;
127 STDMETHOD(CancelDefaultHandling)(long) PURE;
128 STDMETHOD(RestoreDefaultHandling)(long) PURE;
129 STDMETHOD(FreeEventParams)(long, LONG_PTR, LONG_PTR) PURE;
130 };
131
132 //---------------------------------------------------------------------------
133 // ACTIVEMOVIE COM INTERFACES (dumped from amcompat.idl from MSVC COM Browser)
134 //---------------------------------------------------------------------------
135
136 enum ReadyStateConstants
137 {
138 amvUninitialized = 0,
139 amvLoading = 1,
140 amvInteractive = 3,
141 amvComplete = 4
142 };
143
144 enum StateConstants
145 {
146 amvNotLoaded = -1,
147 amvStopped = 0,
148 amvPaused = 1,
149 amvRunning = 2
150 };
151
152 enum DisplayModeConstants
153 {
154 amvTime = 0,
155 amvFrames = 1
156 };
157
158 enum WindowSizeConstants
159 {
160 amvOriginalSize = 0,
161 amvDoubleOriginalSize = 1,
162 amvOneSixteenthScreen = 2,
163 amvOneFourthScreen = 3,
164 amvOneHalfScreen = 4
165 };
166
167 enum AppearanceConstants
168 {
169 amvFlat = 0,
170 amv3D = 1
171 };
172
173 enum BorderStyleConstants
174 {
175 amvNone = 0,
176 amvFixedSingle = 1
177 };
178
179 struct IActiveMovie : public IDispatch
180 {
181 STDMETHOD(AboutBox)( void) PURE;
182 STDMETHOD(Run)( void) PURE;
183 STDMETHOD(Pause)( void) PURE;
184 STDMETHOD(Stop)( void) PURE;
185 STDMETHOD(get_ImageSourceWidth)(long __RPC_FAR *pWidth) PURE;
186 STDMETHOD(get_ImageSourceHeight)(long __RPC_FAR *pHeight) PURE;
187 STDMETHOD(get_Author)(BSTR __RPC_FAR *pbstrAuthor) PURE;
188 STDMETHOD(get_Title)(BSTR __RPC_FAR *pbstrTitle) PURE;
189 STDMETHOD(get_Copyright)(BSTR __RPC_FAR *pbstrCopyright) PURE;
190 STDMETHOD(get_Description)(BSTR __RPC_FAR *pbstrDescription) PURE;
191 STDMETHOD(get_Rating)(BSTR __RPC_FAR *pbstrRating) PURE;
192 STDMETHOD(get_FileName)(BSTR __RPC_FAR *pbstrFileName) PURE;
193 STDMETHOD(put_FileName)(BSTR pbstrFileName) PURE;
194 STDMETHOD(get_Duration)(double __RPC_FAR *pValue) PURE;
195 STDMETHOD(get_CurrentPosition)(double __RPC_FAR *pValue) PURE;
196 STDMETHOD(put_CurrentPosition)(double pValue) PURE;
197 STDMETHOD(get_PlayCount)(long __RPC_FAR *pPlayCount) PURE;
198 STDMETHOD(put_PlayCount)(long pPlayCount) PURE;
199 STDMETHOD(get_SelectionStart)(double __RPC_FAR *pValue) PURE;
200 STDMETHOD(put_SelectionStart)(double pValue) PURE;
201 STDMETHOD(get_SelectionEnd)(double __RPC_FAR *pValue) PURE;
202 STDMETHOD(put_SelectionEnd)(double pValue) PURE;
203 STDMETHOD(get_CurrentState)(StateConstants __RPC_FAR *pState) PURE;
204 STDMETHOD(get_Rate)(double __RPC_FAR *pValue) PURE;
205 STDMETHOD(put_Rate)(double pValue) PURE;
206 STDMETHOD(get_Volume)(long __RPC_FAR *pValue) PURE;
207 STDMETHOD(put_Volume)(long pValue) PURE;
208 STDMETHOD(get_Balance)(long __RPC_FAR *pValue) PURE;
209 STDMETHOD(put_Balance)(long pValue) PURE;
210 STDMETHOD(get_EnableContextMenu)(VARIANT_BOOL __RPC_FAR *pEnable) PURE;
211 STDMETHOD(put_EnableContextMenu)(VARIANT_BOOL pEnable) PURE;
212 STDMETHOD(get_ShowDisplay)(VARIANT_BOOL __RPC_FAR *Show) PURE;
213 STDMETHOD(put_ShowDisplay)(VARIANT_BOOL Show) PURE;
214 STDMETHOD(get_ShowControls)(VARIANT_BOOL __RPC_FAR *Show) PURE;
215 STDMETHOD(put_ShowControls)(VARIANT_BOOL Show) PURE;
216 STDMETHOD(get_ShowPositionControls)(VARIANT_BOOL __RPC_FAR *Show) PURE;
217 STDMETHOD(put_ShowPositionControls)(VARIANT_BOOL Show) PURE;
218 STDMETHOD(get_ShowSelectionControls)(VARIANT_BOOL __RPC_FAR *Show) PURE;
219 STDMETHOD(put_ShowSelectionControls)(VARIANT_BOOL Show) PURE;
220 STDMETHOD(get_ShowTracker)(VARIANT_BOOL __RPC_FAR *Show) PURE;
221 STDMETHOD(put_ShowTracker)(VARIANT_BOOL Show) PURE;
222 STDMETHOD(get_EnablePositionControls)(VARIANT_BOOL __RPC_FAR *Enable) PURE;
223 STDMETHOD(put_EnablePositionControls)(VARIANT_BOOL Enable) PURE;
224 STDMETHOD(get_EnableSelectionControls)(VARIANT_BOOL __RPC_FAR *Enable) PURE;
225 STDMETHOD(put_EnableSelectionControls)(VARIANT_BOOL Enable) PURE;
226 STDMETHOD(get_EnableTracker)(VARIANT_BOOL __RPC_FAR *Enable) PURE;
227 STDMETHOD(put_EnableTracker)(VARIANT_BOOL Enable) PURE;
228 STDMETHOD(get_AllowHideDisplay)(VARIANT_BOOL __RPC_FAR *Show) PURE;
229 STDMETHOD(put_AllowHideDisplay)(VARIANT_BOOL Show) PURE;
230 STDMETHOD(get_AllowHideControls)(VARIANT_BOOL __RPC_FAR *Show) PURE;
231 STDMETHOD(put_AllowHideControls)(VARIANT_BOOL Show) PURE;
232 STDMETHOD(get_DisplayMode)(DisplayModeConstants __RPC_FAR *pValue) PURE;
233 STDMETHOD(put_DisplayMode)(DisplayModeConstants pValue) PURE;
234 STDMETHOD(get_AllowChangeDisplayMode)(VARIANT_BOOL __RPC_FAR *fAllow) PURE;
235 STDMETHOD(put_AllowChangeDisplayMode)(VARIANT_BOOL fAllow) PURE;
236 STDMETHOD(get_FilterGraph)(IUnknown __RPC_FAR *__RPC_FAR *ppFilterGraph) PURE;
237 STDMETHOD(put_FilterGraph)(IUnknown __RPC_FAR *ppFilterGraph) PURE;
238 STDMETHOD(get_FilterGraphDispatch)(IDispatch __RPC_FAR *__RPC_FAR *pDispatch) PURE;
239 STDMETHOD(get_DisplayForeColor)(unsigned long __RPC_FAR *ForeColor) PURE;
240 STDMETHOD(put_DisplayForeColor)(unsigned long ForeColor) PURE;
241 STDMETHOD(get_DisplayBackColor)(unsigned long __RPC_FAR *BackColor) PURE;
242 STDMETHOD(put_DisplayBackColor)(unsigned long BackColor) PURE;
243 STDMETHOD(get_MovieWindowSize)(WindowSizeConstants __RPC_FAR *WindowSize) PURE;
244 STDMETHOD(put_MovieWindowSize)(WindowSizeConstants WindowSize) PURE;
245 STDMETHOD(get_FullScreenMode)(VARIANT_BOOL __RPC_FAR *pEnable) PURE;
246 STDMETHOD(put_FullScreenMode)(VARIANT_BOOL pEnable) PURE;
247 STDMETHOD(get_AutoStart)(VARIANT_BOOL __RPC_FAR *pEnable) PURE;
248 STDMETHOD(put_AutoStart)(VARIANT_BOOL pEnable) PURE;
249 STDMETHOD(get_AutoRewind)(VARIANT_BOOL __RPC_FAR *pEnable) PURE;
250 STDMETHOD(put_AutoRewind)(VARIANT_BOOL pEnable) PURE;
251 STDMETHOD(get_hWnd)(long __RPC_FAR *hWnd) PURE;
252 STDMETHOD(get_Appearance)(AppearanceConstants __RPC_FAR *pAppearance) PURE;
253 STDMETHOD(put_Appearance)(AppearanceConstants pAppearance) PURE;
254 STDMETHOD(get_BorderStyle)(BorderStyleConstants __RPC_FAR *pBorderStyle) PURE;
255 STDMETHOD(put_BorderStyle)(BorderStyleConstants pBorderStyle) PURE;
256 STDMETHOD(get_Enabled)(VARIANT_BOOL __RPC_FAR *pEnabled) PURE;
257 STDMETHOD(put_Enabled)(VARIANT_BOOL pEnabled) PURE;
258 STDMETHOD(get_Info)(long __RPC_FAR *ppInfo) PURE;
259 };
260
261
262
263 struct IActiveMovie2 : public IActiveMovie
264 {
265 STDMETHOD(IsSoundCardEnabled)(VARIANT_BOOL __RPC_FAR *pbSoundCard) PURE;
266 STDMETHOD(get_ReadyState)(ReadyStateConstants __RPC_FAR *pValue) PURE;
267 };
268
269 struct IActiveMovie3 : public IActiveMovie2
270 {
271 STDMETHOD(get_MediaPlayer)(IDispatch __RPC_FAR *__RPC_FAR *ppDispatch) PURE;
272 };
273
274
275 //---------------------------------------------------------------------------
276 // MEDIAPLAYER COM INTERFACES (dumped from msdxm.idl from MSVC COM Browser)
277 //---------------------------------------------------------------------------
278
279 enum MPPlayStateConstants
280 {
281 mpStopped = 0,
282 mpPaused = 1,
283 mpPlaying = 2,
284 mpWaiting = 3,
285 mpScanForward = 4,
286 mpScanReverse = 5,
287 mpClosed = 6
288 };
289
290 enum MPDisplaySizeConstants
291 {
292 mpDefaultSize = 0,
293 mpHalfSize = 1,
294 mpDoubleSize = 2,
295 mpFullScreen = 3,
296 mpFitToSize = 4,
297 mpOneSixteenthScreen = 5,
298 mpOneFourthScreen = 6,
299 mpOneHalfScreen = 7
300 };
301
302 enum MPReadyStateConstants
303 {
304 mpReadyStateUninitialized = 0,
305 mpReadyStateLoading = 1,
306 mpReadyStateInteractive = 3,
307 mpReadyStateComplete = 4
308 };
309
310 typedef unsigned long VB_OLE_COLOR;
311
312 enum MPDisplayModeConstants
313 {
314 mpTime = 0,
315 mpFrames = 1
316 };
317
318 enum MPMoreInfoType
319 {
320 mpShowURL = 0,
321 mpClipURL = 1,
322 mpBannerURL = 2
323 };
324
325 enum MPMediaInfoType
326 {
327 mpShowFilename = 0,
328 mpShowTitle = 1,
329 mpShowAuthor = 2,
330 mpShowCopyright = 3,
331 mpShowRating = 4,
332 mpShowDescription = 5,
333 mpShowLogoIcon = 6,
334 mpClipFilename = 7,
335 mpClipTitle = 8,
336 mpClipAuthor = 9,
337 mpClipCopyright = 10,
338 mpClipRating = 11,
339 mpClipDescription = 12,
340 mpClipLogoIcon = 13,
341 mpBannerImage = 14,
342 mpBannerMoreInfo = 15,
343 mpWatermark = 16
344 };
345
346 enum DVDMenuIDConstants
347 {
348 dvdMenu_Title = 2,
349 dvdMenu_Root = 3,
350 dvdMenu_Subpicture = 4,
351 dvdMenu_Audio = 5,
352 dvdMenu_Angle = 6,
353 dvdMenu_Chapter = 7
354 };
355
356 enum MPShowDialogConstants
357 {
358 mpShowDialogHelp = 0,
359 mpShowDialogStatistics = 1,
360 mpShowDialogOptions = 2,
361 mpShowDialogContextMenu = 3
362 };
363
364
365 struct IMediaPlayer : public IDispatch
366 {
367 STDMETHOD(get_CurrentPosition)(double __RPC_FAR *pCurrentPosition) PURE;
368 STDMETHOD(put_CurrentPosition)(double pCurrentPosition) PURE;
369 STDMETHOD(get_Duration)(double __RPC_FAR *pDuration) PURE;
370 STDMETHOD(get_ImageSourceWidth)(long __RPC_FAR *pWidth) PURE;
371 STDMETHOD(get_ImageSourceHeight)(long __RPC_FAR *pHeight) PURE;
372 STDMETHOD(get_MarkerCount)(long __RPC_FAR *pMarkerCount) PURE;
373 STDMETHOD(get_CanScan)(VARIANT_BOOL __RPC_FAR *pCanScan) PURE;
374 STDMETHOD(get_CanSeek)(VARIANT_BOOL __RPC_FAR *pCanSeek) PURE;
375 STDMETHOD(get_CanSeekToMarkers)(VARIANT_BOOL __RPC_FAR *pCanSeekToMarkers) PURE;
376 STDMETHOD(get_CurrentMarker)(long __RPC_FAR *pCurrentMarker) PURE;
377 STDMETHOD(put_CurrentMarker)(long pCurrentMarker) PURE;
378 STDMETHOD(get_FileName)(BSTR __RPC_FAR *pbstrFileName) PURE;
379 STDMETHOD(put_FileName)(BSTR pbstrFileName) PURE;
380 STDMETHOD(get_SourceLink)(BSTR __RPC_FAR *pbstrSourceLink) PURE;
381 STDMETHOD(get_CreationDate)(DATE __RPC_FAR *pCreationDate) PURE;
382 STDMETHOD(get_ErrorCorrection)(BSTR __RPC_FAR *pbstrErrorCorrection) PURE;
383 STDMETHOD(get_Bandwidth)(long __RPC_FAR *pBandwidth) PURE;
384 STDMETHOD(get_SourceProtocol)(long __RPC_FAR *pSourceProtocol) PURE;
385 STDMETHOD(get_ReceivedPackets)(long __RPC_FAR *pReceivedPackets) PURE;
386 STDMETHOD(get_RecoveredPackets)(long __RPC_FAR *pRecoveredPackets) PURE;
387 STDMETHOD(get_LostPackets)(long __RPC_FAR *pLostPackets) PURE;
388 STDMETHOD(get_ReceptionQuality)(long __RPC_FAR *pReceptionQuality) PURE;
389 STDMETHOD(get_BufferingCount)(long __RPC_FAR *pBufferingCount) PURE;
390 STDMETHOD(get_IsBroadcast)(VARIANT_BOOL __RPC_FAR *pIsBroadcast) PURE;
391 STDMETHOD(get_BufferingProgress)(long __RPC_FAR *pBufferingProgress) PURE;
392 STDMETHOD(get_ChannelName)(BSTR __RPC_FAR *pbstrChannelName) PURE;
393 STDMETHOD(get_ChannelDescription)(BSTR __RPC_FAR *pbstrChannelDescription) PURE;
394 STDMETHOD(get_ChannelURL)(BSTR __RPC_FAR *pbstrChannelURL) PURE;
395 STDMETHOD(get_ContactAddress)(BSTR __RPC_FAR *pbstrContactAddress) PURE;
396 STDMETHOD(get_ContactPhone)(BSTR __RPC_FAR *pbstrContactPhone) PURE;
397 STDMETHOD(get_ContactEmail)(BSTR __RPC_FAR *pbstrContactEmail) PURE;
398 STDMETHOD(get_BufferingTime)(double __RPC_FAR *pBufferingTime) PURE;
399 STDMETHOD(put_BufferingTime)(double pBufferingTime) PURE;
400 STDMETHOD(get_AutoStart)(VARIANT_BOOL __RPC_FAR *pAutoStart) PURE;
401 STDMETHOD(put_AutoStart)(VARIANT_BOOL pAutoStart) PURE;
402 STDMETHOD(get_AutoRewind)(VARIANT_BOOL __RPC_FAR *pAutoRewind) PURE;
403 STDMETHOD(put_AutoRewind)(VARIANT_BOOL pAutoRewind) PURE;
404 STDMETHOD(get_Rate)(double __RPC_FAR *pRate) PURE;
405 STDMETHOD(put_Rate)(double pRate) PURE;
406 STDMETHOD(get_SendKeyboardEvents)(VARIANT_BOOL __RPC_FAR *pSendKeyboardEvents) PURE;
407 STDMETHOD(put_SendKeyboardEvents)(VARIANT_BOOL pSendKeyboardEvents) PURE;
408 STDMETHOD(get_SendMouseClickEvents)(VARIANT_BOOL __RPC_FAR *pSendMouseClickEvents) PURE;
409 STDMETHOD(put_SendMouseClickEvents)(VARIANT_BOOL pSendMouseClickEvents) PURE;
410 STDMETHOD(get_SendMouseMoveEvents)(VARIANT_BOOL __RPC_FAR *pSendMouseMoveEvents) PURE;
411 STDMETHOD(put_SendMouseMoveEvents)(VARIANT_BOOL pSendMouseMoveEvents) PURE;
412 STDMETHOD(get_PlayCount)(long __RPC_FAR *pPlayCount) PURE;
413 STDMETHOD(put_PlayCount)(long pPlayCount) PURE;
414 STDMETHOD(get_ClickToPlay)(VARIANT_BOOL __RPC_FAR *pClickToPlay) PURE;
415 STDMETHOD(put_ClickToPlay)(VARIANT_BOOL pClickToPlay) PURE;
416 STDMETHOD(get_AllowScan)(VARIANT_BOOL __RPC_FAR *pAllowScan) PURE;
417 STDMETHOD(put_AllowScan)(VARIANT_BOOL pAllowScan) PURE;
418 STDMETHOD(get_EnableContextMenu)(VARIANT_BOOL __RPC_FAR *pEnableContextMenu) PURE;
419 STDMETHOD(put_EnableContextMenu)(VARIANT_BOOL pEnableContextMenu) PURE;
420 STDMETHOD(get_CursorType)(long __RPC_FAR *pCursorType) PURE;
421 STDMETHOD(put_CursorType)(long pCursorType) PURE;
422 STDMETHOD(get_CodecCount)(long __RPC_FAR *pCodecCount) PURE;
423 STDMETHOD(get_AllowChangeDisplaySize)(VARIANT_BOOL __RPC_FAR *pAllowChangeDisplaySize) PURE;
424 STDMETHOD(put_AllowChangeDisplaySize)( VARIANT_BOOL pAllowChangeDisplaySize) PURE;
425 STDMETHOD(get_IsDurationValid)(VARIANT_BOOL __RPC_FAR *pIsDurationValid) PURE;
426 STDMETHOD(get_OpenState)(long __RPC_FAR *pOpenState) PURE;
427 STDMETHOD(get_SendOpenStateChangeEvents)(VARIANT_BOOL __RPC_FAR *pSendOpenStateChangeEvents) PURE;
428 STDMETHOD(put_SendOpenStateChangeEvents)(VARIANT_BOOL pSendOpenStateChangeEvents) PURE;
429 STDMETHOD(get_SendWarningEvents)( VARIANT_BOOL __RPC_FAR *pSendWarningEvents) PURE;
430 STDMETHOD(put_SendWarningEvents)(VARIANT_BOOL pSendWarningEvents) PURE;
431 STDMETHOD(get_SendErrorEvents)(VARIANT_BOOL __RPC_FAR *pSendErrorEvents) PURE;
432 STDMETHOD(put_SendErrorEvents)(VARIANT_BOOL pSendErrorEvents) PURE;
433 STDMETHOD(get_PlayState)(MPPlayStateConstants __RPC_FAR *pPlayState) PURE;
434 STDMETHOD(get_SendPlayStateChangeEvents)(VARIANT_BOOL __RPC_FAR *pSendPlayStateChangeEvents) PURE;
435 STDMETHOD(put_SendPlayStateChangeEvents)(VARIANT_BOOL pSendPlayStateChangeEvents) PURE;
436 STDMETHOD(get_DisplaySize)(MPDisplaySizeConstants __RPC_FAR *pDisplaySize) PURE;
437 STDMETHOD(put_DisplaySize)(MPDisplaySizeConstants pDisplaySize) PURE;
438 STDMETHOD(get_InvokeURLs)(VARIANT_BOOL __RPC_FAR *pInvokeURLs) PURE;
439 STDMETHOD(put_InvokeURLs)(VARIANT_BOOL pInvokeURLs) PURE;
440 STDMETHOD(get_BaseURL)(BSTR __RPC_FAR *pbstrBaseURL) PURE;
441 STDMETHOD(put_BaseURL)(BSTR pbstrBaseURL) PURE;
442 STDMETHOD(get_DefaultFrame)(BSTR __RPC_FAR *pbstrDefaultFrame) PURE;
443 STDMETHOD(put_DefaultFrame)(BSTR pbstrDefaultFrame) PURE;
444 STDMETHOD(get_HasError)(VARIANT_BOOL __RPC_FAR *pHasError) PURE;
445 STDMETHOD(get_ErrorDescription)(BSTR __RPC_FAR *pbstrErrorDescription) PURE;
446 STDMETHOD(get_ErrorCode)(long __RPC_FAR *pErrorCode) PURE;
447 STDMETHOD(get_AnimationAtStart)(VARIANT_BOOL __RPC_FAR *pAnimationAtStart) PURE;
448 STDMETHOD(put_AnimationAtStart)(VARIANT_BOOL pAnimationAtStart) PURE;
449 STDMETHOD(get_TransparentAtStart)( VARIANT_BOOL __RPC_FAR *pTransparentAtStart) PURE;
450 STDMETHOD(put_TransparentAtStart)(VARIANT_BOOL pTransparentAtStart) PURE;
451 STDMETHOD(get_Volume)(long __RPC_FAR *pVolume) PURE;
452 STDMETHOD(put_Volume)(long pVolume) PURE;
453 STDMETHOD(get_Balance)(long __RPC_FAR *pBalance) PURE;
454 STDMETHOD(put_Balance)(long pBalance) PURE;
455 STDMETHOD(get_ReadyState)(MPReadyStateConstants __RPC_FAR *pValue) PURE;
456 STDMETHOD(get_SelectionStart)(double __RPC_FAR *pValue) PURE;
457 STDMETHOD(put_SelectionStart)(double pValue) PURE;
458 STDMETHOD(get_SelectionEnd)(double __RPC_FAR *pValue) PURE;
459 STDMETHOD(put_SelectionEnd)(double pValue) PURE;
460 STDMETHOD(get_ShowDisplay)(VARIANT_BOOL __RPC_FAR *Show) PURE;
461 STDMETHOD(put_ShowDisplay)(VARIANT_BOOL Show) PURE;
462 STDMETHOD(get_ShowControls)(VARIANT_BOOL __RPC_FAR *Show) PURE;
463 STDMETHOD(put_ShowControls)(VARIANT_BOOL Show) PURE;
464 STDMETHOD(get_ShowPositionControls)(VARIANT_BOOL __RPC_FAR *Show) PURE;
465 STDMETHOD(put_ShowPositionControls)(VARIANT_BOOL Show) PURE;
466 STDMETHOD(get_ShowTracker)(VARIANT_BOOL __RPC_FAR *Show) PURE;
467 STDMETHOD(put_ShowTracker)(VARIANT_BOOL Show) PURE;
468 STDMETHOD(get_EnablePositionControls)(VARIANT_BOOL __RPC_FAR *Enable) PURE;
469 STDMETHOD(put_EnablePositionControls)(VARIANT_BOOL Enable) PURE;
470 STDMETHOD(get_EnableTracker)(VARIANT_BOOL __RPC_FAR *Enable) PURE;
471 STDMETHOD(put_EnableTracker)(VARIANT_BOOL Enable) PURE;
472 STDMETHOD(get_Enabled)(VARIANT_BOOL __RPC_FAR *pEnabled) PURE;
473 STDMETHOD(put_Enabled)(VARIANT_BOOL pEnabled) PURE;
474 STDMETHOD(get_DisplayForeColor)(VB_OLE_COLOR __RPC_FAR *ForeColor) PURE;
475 STDMETHOD(put_DisplayForeColor)(VB_OLE_COLOR ForeColor) PURE;
476 STDMETHOD(get_DisplayBackColor)(VB_OLE_COLOR __RPC_FAR *BackColor) PURE;
477 STDMETHOD(put_DisplayBackColor)(VB_OLE_COLOR BackColor) PURE;
478 STDMETHOD(get_DisplayMode)(MPDisplayModeConstants __RPC_FAR *pValue) PURE;
479 STDMETHOD(put_DisplayMode)(MPDisplayModeConstants pValue) PURE;
480 STDMETHOD(get_VideoBorder3D)(VARIANT_BOOL __RPC_FAR *pVideoBorderWidth) PURE;
481 STDMETHOD(put_VideoBorder3D)(VARIANT_BOOL pVideoBorderWidth) PURE;
482 STDMETHOD(get_VideoBorderWidth)(long __RPC_FAR *pVideoBorderWidth) PURE;
483 STDMETHOD(put_VideoBorderWidth)(long pVideoBorderWidth) PURE;
484 STDMETHOD(get_VideoBorderColor)(VB_OLE_COLOR __RPC_FAR *pVideoBorderWidth) PURE;
485 STDMETHOD(put_VideoBorderColor)(VB_OLE_COLOR pVideoBorderWidth) PURE;
486 STDMETHOD(get_ShowGotoBar)(VARIANT_BOOL __RPC_FAR *pbool) PURE;
487 STDMETHOD(put_ShowGotoBar)(VARIANT_BOOL pbool) PURE;
488 STDMETHOD(get_ShowStatusBar)(VARIANT_BOOL __RPC_FAR *pbool) PURE;
489 STDMETHOD(put_ShowStatusBar)(VARIANT_BOOL pbool) PURE;
490 STDMETHOD(get_ShowCaptioning)(VARIANT_BOOL __RPC_FAR *pbool) PURE;
491 STDMETHOD(put_ShowCaptioning)(VARIANT_BOOL pbool) PURE;
492 STDMETHOD(get_ShowAudioControls)(VARIANT_BOOL __RPC_FAR *pbool) PURE;
493 STDMETHOD(put_ShowAudioControls)(VARIANT_BOOL pbool) PURE;
494 STDMETHOD(get_CaptioningID)( BSTR __RPC_FAR *pstrText) PURE;
495 STDMETHOD(put_CaptioningID)(BSTR pstrText) PURE;
496 STDMETHOD(get_Mute)(VARIANT_BOOL __RPC_FAR *vbool) PURE;
497 STDMETHOD(put_Mute)(VARIANT_BOOL vbool) PURE;
498 STDMETHOD(get_CanPreview)(VARIANT_BOOL __RPC_FAR *pCanPreview) PURE;
499 STDMETHOD(get_PreviewMode)(VARIANT_BOOL __RPC_FAR *pPreviewMode) PURE;
500 STDMETHOD(put_PreviewMode)(VARIANT_BOOL pPreviewMode) PURE;
501 STDMETHOD(get_HasMultipleItems)(VARIANT_BOOL __RPC_FAR *pHasMuliItems) PURE;
502 STDMETHOD(get_Language)(long __RPC_FAR *pLanguage) PURE;
503 STDMETHOD(put_Language)(long pLanguage) PURE;
504 STDMETHOD(get_AudioStream)(long __RPC_FAR *pStream) PURE;
505 STDMETHOD(put_AudioStream)(long pStream) PURE;
506 STDMETHOD(get_SAMIStyle)(BSTR __RPC_FAR *pbstrStyle) PURE;
507 STDMETHOD(put_SAMIStyle)(BSTR pbstrStyle) PURE;
508 STDMETHOD(get_SAMILang)(BSTR __RPC_FAR *pbstrLang) PURE;
509 STDMETHOD(put_SAMILang)(BSTR pbstrLang) PURE;
510 STDMETHOD(get_SAMIFileName)(BSTR __RPC_FAR *pbstrFileName) PURE;
511 STDMETHOD(put_SAMIFileName)(BSTR pbstrFileName) PURE;
512 STDMETHOD(get_StreamCount)( long __RPC_FAR *pStreamCount) PURE;
513 STDMETHOD(get_ClientId)(BSTR __RPC_FAR *pbstrClientId) PURE;
514 STDMETHOD(get_ConnectionSpeed)(long __RPC_FAR *plConnectionSpeed) PURE;
515 STDMETHOD(get_AutoSize)(VARIANT_BOOL __RPC_FAR *pbool) PURE;
516 STDMETHOD(put_AutoSize)(VARIANT_BOOL pbool) PURE;
517 STDMETHOD(get_EnableFullScreenControls)(VARIANT_BOOL __RPC_FAR *pbVal) PURE;
518 STDMETHOD(put_EnableFullScreenControls)(VARIANT_BOOL pbVal) PURE;
519 STDMETHOD(get_ActiveMovie)(IDispatch __RPC_FAR *__RPC_FAR *ppdispatch) PURE;
520 STDMETHOD(get_NSPlay)(IDispatch __RPC_FAR *__RPC_FAR *ppdispatch) PURE;
521 STDMETHOD(get_WindowlessVideo)(VARIANT_BOOL __RPC_FAR *pbool) PURE;
522 STDMETHOD(put_WindowlessVideo)(VARIANT_BOOL pbool) PURE;
523 STDMETHOD(Play)(void) PURE;
524 STDMETHOD(Stop)(void) PURE;
525 STDMETHOD(Pause)(void) PURE;
526 STDMETHOD(GetMarkerTime)(long MarkerNum,
527 double __RPC_FAR *pMarkerTime) PURE;
528 STDMETHOD(GetMarkerName)(long MarkerNum,
529 BSTR __RPC_FAR *pbstrMarkerName) PURE;
530 STDMETHOD(AboutBox)(void) PURE;
531 STDMETHOD(GetCodecInstalled)(long CodecNum,
532 VARIANT_BOOL __RPC_FAR *pCodecInstalled) PURE;
533 STDMETHOD(GetCodecDescription)(long CodecNum,
534 BSTR __RPC_FAR *pbstrCodecDescription) PURE;
535 STDMETHOD(GetCodecURL)(long CodecNum,
536 BSTR __RPC_FAR *pbstrCodecURL) PURE;
537 STDMETHOD(GetMoreInfoURL)(MPMoreInfoType MoreInfoType,
538 BSTR __RPC_FAR *pbstrMoreInfoURL) PURE;
539 STDMETHOD(GetMediaInfoString)(MPMediaInfoType MediaInfoType,
540 BSTR __RPC_FAR *pbstrMediaInfo) PURE;
541 STDMETHOD(Cancel)(void) PURE;
542 STDMETHOD(Open)(BSTR bstrFileName) PURE;
543 STDMETHOD(IsSoundCardEnabled)(VARIANT_BOOL __RPC_FAR *pbSoundCard) PURE;
544 STDMETHOD(Next)(void) PURE;
545 STDMETHOD(Previous)(void) PURE;
546 STDMETHOD(StreamSelect)(long StreamNum) PURE;
547 STDMETHOD(FastForward)(void) PURE;
548 STDMETHOD(FastReverse)(void) PURE;
549 STDMETHOD(GetStreamName)(long StreamNum,
550 BSTR __RPC_FAR *pbstrStreamName) PURE;
551 STDMETHOD(GetStreamGroup)(long StreamNum,
552 long __RPC_FAR *pStreamGroup) PURE;
553 STDMETHOD(GetStreamSelected)(long StreamNum, VARIANT_BOOL __RPC_FAR *pStreamSelected) PURE;
554 };
555
556 struct IMediaPlayer2 : public IMediaPlayer
557 {
558 STDMETHOD(get_DVD)(struct IMediaPlayerDvd __RPC_FAR *__RPC_FAR *ppdispatch) PURE;
559 STDMETHOD(GetMediaParameter)(long EntryNum, BSTR bstrParameterName, BSTR __RPC_FAR *pbstrParameterValue) PURE;
560 STDMETHOD(GetMediaParameterName)(long EntryNum, long Index, BSTR __RPC_FAR *pbstrParameterName) PURE;
561 STDMETHOD(get_EntryCount)(long __RPC_FAR *pNumberEntries) PURE;
562 STDMETHOD(GetCurrentEntry)(long __RPC_FAR *pEntryNumber) PURE;
563 STDMETHOD(SetCurrentEntry)(long EntryNumber) PURE;
564 STDMETHOD(ShowDialog)(MPShowDialogConstants mpDialogIndex) PURE;
565 };
566
567 //---------------------------------------------------------------------------
568 // NETSHOW COM INTERFACES (dumped from nscompat.idl from MSVC COM Browser)
569 //---------------------------------------------------------------------------
570
571 struct INSOPlay : public IDispatch
572 {
573 STDMETHOD(get_ImageSourceWidth)(long __RPC_FAR *pWidth) PURE;
574 STDMETHOD(get_ImageSourceHeight)(long __RPC_FAR *pHeight) PURE;
575 STDMETHOD(get_Duration)(double __RPC_FAR *pDuration) PURE;
576 STDMETHOD(get_Author)(BSTR __RPC_FAR *pbstrAuthor) PURE;
577 STDMETHOD(get_Copyright)(BSTR __RPC_FAR *pbstrCopyright) PURE;
578 STDMETHOD(get_Description)(BSTR __RPC_FAR *pbstrDescription) PURE;
579 STDMETHOD(get_Rating)(BSTR __RPC_FAR *pbstrRating) PURE;
580 STDMETHOD(get_Title)(BSTR __RPC_FAR *pbstrTitle) PURE;
581 STDMETHOD(get_SourceLink)(BSTR __RPC_FAR *pbstrSourceLink) PURE;
582 STDMETHOD(get_MarkerCount)(long __RPC_FAR *pMarkerCount) PURE;
583 STDMETHOD(get_CanScan)(VARIANT_BOOL __RPC_FAR *pCanScan) PURE;
584 STDMETHOD(get_CanSeek)(VARIANT_BOOL __RPC_FAR *pCanSeek) PURE;
585 STDMETHOD(get_CanSeekToMarkers)(VARIANT_BOOL __RPC_FAR *pCanSeekToMarkers) PURE;
586 STDMETHOD(get_CreationDate)(DATE __RPC_FAR *pCreationDate) PURE;
587 STDMETHOD(get_Bandwidth)(long __RPC_FAR *pBandwidth) PURE;
588 STDMETHOD(get_ErrorCorrection)(BSTR __RPC_FAR *pbstrErrorCorrection) PURE;
589 STDMETHOD(get_AutoStart)(VARIANT_BOOL __RPC_FAR *pAutoStart) PURE;
590 STDMETHOD(put_AutoStart)(VARIANT_BOOL pAutoStart) PURE;
591 STDMETHOD(get_AutoRewind)(VARIANT_BOOL __RPC_FAR *pAutoRewind) PURE;
592 STDMETHOD(put_AutoRewind)(VARIANT_BOOL pAutoRewind) PURE;
593 STDMETHOD(get_AllowChangeControlType)(VARIANT_BOOL __RPC_FAR *pAllowChangeControlType) PURE;
594 STDMETHOD(put_AllowChangeControlType)(VARIANT_BOOL pAllowChangeControlType) PURE;
595 STDMETHOD(get_InvokeURLs)(VARIANT_BOOL __RPC_FAR *pInvokeURLs) PURE;
596 STDMETHOD(put_InvokeURLs)(VARIANT_BOOL pInvokeURLs) PURE;
597 STDMETHOD(get_EnableContextMenu)(VARIANT_BOOL __RPC_FAR *pEnableContextMenu) PURE;
598 STDMETHOD(put_EnableContextMenu)(VARIANT_BOOL pEnableContextMenu) PURE;
599 STDMETHOD(get_TransparentAtStart)(VARIANT_BOOL __RPC_FAR *pTransparentAtStart) PURE;
600 STDMETHOD(put_TransparentAtStart)(VARIANT_BOOL pTransparentAtStart) PURE;
601 STDMETHOD(get_TransparentOnStop)(VARIANT_BOOL __RPC_FAR *pTransparentOnStop) PURE;
602 STDMETHOD(put_TransparentOnStop)(VARIANT_BOOL pTransparentOnStop) PURE;
603 STDMETHOD(get_ClickToPlay)(VARIANT_BOOL __RPC_FAR *pClickToPlay) PURE;
604 STDMETHOD(put_ClickToPlay)(VARIANT_BOOL pClickToPlay) PURE;
605 STDMETHOD(get_FileName)(BSTR __RPC_FAR *pbstrFileName) PURE;
606 STDMETHOD(put_FileName)(BSTR pbstrFileName) PURE;
607 STDMETHOD(get_CurrentPosition)(double __RPC_FAR *pCurrentPosition) PURE;
608 STDMETHOD(put_CurrentPosition)(double pCurrentPosition) PURE;
609 STDMETHOD(get_Rate)(double __RPC_FAR *pRate) PURE;
610 STDMETHOD(put_Rate)(double pRate) PURE;
611 STDMETHOD(get_CurrentMarker)(long __RPC_FAR *pCurrentMarker) PURE;
612 STDMETHOD(put_CurrentMarker)(long pCurrentMarker) PURE;
613 STDMETHOD(get_PlayCount)(long __RPC_FAR *pPlayCount) PURE;
614 STDMETHOD(put_PlayCount)(long pPlayCount) PURE;
615 STDMETHOD(get_CurrentState)(long __RPC_FAR *pCurrentState) PURE;
616 STDMETHOD(get_DisplaySize)(long __RPC_FAR *pDisplaySize) PURE;
617 STDMETHOD(put_DisplaySize)(long pDisplaySize) PURE;
618 STDMETHOD(get_MainWindow)(long __RPC_FAR *pMainWindow) PURE;
619 STDMETHOD(get_ControlType)(long __RPC_FAR *pControlType) PURE;
620 STDMETHOD(put_ControlType)(long pControlType) PURE;
621 STDMETHOD(get_AllowScan)(VARIANT_BOOL __RPC_FAR *pAllowScan) PURE;
622 STDMETHOD(put_AllowScan)(VARIANT_BOOL pAllowScan) PURE;
623 STDMETHOD(get_SendKeyboardEvents)(VARIANT_BOOL __RPC_FAR *pSendKeyboardEvents) PURE;
624 STDMETHOD(put_SendKeyboardEvents)(VARIANT_BOOL pSendKeyboardEvents) PURE;
625 STDMETHOD(get_SendMouseClickEvents)(VARIANT_BOOL __RPC_FAR *pSendMouseClickEvents) PURE;
626 STDMETHOD(put_SendMouseClickEvents)(VARIANT_BOOL pSendMouseClickEvents) PURE;
627 STDMETHOD(get_SendMouseMoveEvents)(VARIANT_BOOL __RPC_FAR *pSendMouseMoveEvents) PURE;
628 STDMETHOD(put_SendMouseMoveEvents)(VARIANT_BOOL pSendMouseMoveEvents) PURE;
629 STDMETHOD(get_SendStateChangeEvents)(VARIANT_BOOL __RPC_FAR *pSendStateChangeEvents) PURE;
630 STDMETHOD(put_SendStateChangeEvents)(VARIANT_BOOL pSendStateChangeEvents) PURE;
631 STDMETHOD(get_ReceivedPackets)(long __RPC_FAR *pReceivedPackets) PURE;
632 STDMETHOD(get_RecoveredPackets)(long __RPC_FAR *pRecoveredPackets) PURE;
633 STDMETHOD(get_LostPackets)(long __RPC_FAR *pLostPackets) PURE;
634 STDMETHOD(get_ReceptionQuality)(long __RPC_FAR *pReceptionQuality) PURE;
635 STDMETHOD(get_BufferingCount)(long __RPC_FAR *pBufferingCount) PURE;
636 STDMETHOD(get_CursorType)(long __RPC_FAR *pCursorType) PURE;
637 STDMETHOD(put_CursorType)(long pCursorType) PURE;
638 STDMETHOD(get_AnimationAtStart)(VARIANT_BOOL __RPC_FAR *pAnimationAtStart) PURE;
639 STDMETHOD(put_AnimationAtStart)(VARIANT_BOOL pAnimationAtStart) PURE;
640 STDMETHOD(get_AnimationOnStop)(VARIANT_BOOL __RPC_FAR *pAnimationOnStop) PURE;
641 STDMETHOD(put_AnimationOnStop)(VARIANT_BOOL pAnimationOnStop) PURE;
642 STDMETHOD(Play)(void) PURE;
643 STDMETHOD(Pause)(void) PURE;
644 STDMETHOD(Stop)(void) PURE;
645 STDMETHOD(GetMarkerTime)(long MarkerNum, double __RPC_FAR *pMarkerTime) PURE;
646 STDMETHOD(GetMarkerName)(long MarkerNum, BSTR __RPC_FAR *pbstrMarkerName) PURE;
647 };
648
649 struct INSPlay : public INSOPlay
650 {
651 STDMETHOD(get_ChannelName)(BSTR __RPC_FAR *pbstrChannelName) PURE;
652 STDMETHOD(get_ChannelDescription)(BSTR __RPC_FAR *pbstrChannelDescription) PURE;
653 STDMETHOD(get_ChannelURL)(BSTR __RPC_FAR *pbstrChannelURL) PURE;
654 STDMETHOD(get_ContactAddress)(BSTR __RPC_FAR *pbstrContactAddress) PURE;
655 STDMETHOD(get_ContactPhone)(BSTR __RPC_FAR *pbstrContactPhone) PURE;
656 STDMETHOD(get_ContactEmail)(BSTR __RPC_FAR *pbstrContactEmail) PURE;
657 STDMETHOD(get_AllowChangeDisplaySize)(VARIANT_BOOL __RPC_FAR *pAllowChangeDisplaySize) PURE;
658 STDMETHOD(put_AllowChangeDisplaySize)(VARIANT_BOOL pAllowChangeDisplaySize) PURE;
659 STDMETHOD(get_CodecCount)(long __RPC_FAR *pCodecCount) PURE;
660 STDMETHOD(get_IsBroadcast)(VARIANT_BOOL __RPC_FAR *pIsBroadcast) PURE;
661 STDMETHOD(get_IsDurationValid)(VARIANT_BOOL __RPC_FAR *pIsDurationValid) PURE;
662 STDMETHOD(get_SourceProtocol)(long __RPC_FAR *pSourceProtocol) PURE;
663 STDMETHOD(get_OpenState)(long __RPC_FAR *pOpenState) PURE;
664 STDMETHOD(get_SendOpenStateChangeEvents)(VARIANT_BOOL __RPC_FAR *pSendOpenStateChangeEvents) PURE;
665 STDMETHOD(put_SendOpenStateChangeEvents)(VARIANT_BOOL pSendOpenStateChangeEvents) PURE;
666 STDMETHOD(get_SendWarningEvents)(VARIANT_BOOL __RPC_FAR *pSendWarningEvents) PURE;
667 STDMETHOD(put_SendWarningEvents)(VARIANT_BOOL pSendWarningEvents) PURE;
668 STDMETHOD(get_SendErrorEvents)(VARIANT_BOOL __RPC_FAR *pSendErrorEvents) PURE;
669 STDMETHOD(put_SendErrorEvents)(VARIANT_BOOL pSendErrorEvents) PURE;
670 STDMETHOD(get_HasError)(VARIANT_BOOL __RPC_FAR *pHasError) PURE;
671 STDMETHOD(get_ErrorDescription)(BSTR __RPC_FAR *pbstrErrorDescription) PURE;
672 STDMETHOD(get_ErrorCode)(long __RPC_FAR *pErrorCode) PURE;
673 STDMETHOD(get_PlayState)(long __RPC_FAR *pPlayState) PURE;
674 STDMETHOD(get_SendPlayStateChangeEvents)(VARIANT_BOOL __RPC_FAR *pSendPlayStateChangeEvents) PURE;
675 STDMETHOD(put_SendPlayStateChangeEvents)(VARIANT_BOOL pSendPlayStateChangeEvents) PURE;
676 STDMETHOD(get_BufferingTime)(double __RPC_FAR *pBufferingTime) PURE;
677 STDMETHOD(put_BufferingTime)(double pBufferingTime) PURE;
678 STDMETHOD(get_UseFixedUDPPort)(VARIANT_BOOL __RPC_FAR *pUseFixedUDPPort) PURE;
679 STDMETHOD(put_UseFixedUDPPort)(VARIANT_BOOL pUseFixedUDPPort) PURE;
680 STDMETHOD(get_FixedUDPPort)(long __RPC_FAR *pFixedUDPPort) PURE;
681 STDMETHOD(put_FixedUDPPort)(long pFixedUDPPort) PURE;
682 STDMETHOD(get_UseHTTPProxy)(VARIANT_BOOL __RPC_FAR *pUseHTTPProxy) PURE;
683 STDMETHOD(put_UseHTTPProxy)(VARIANT_BOOL pUseHTTPProxy) PURE;
684 STDMETHOD(get_EnableAutoProxy)(VARIANT_BOOL __RPC_FAR *pEnableAutoProxy) PURE;
685 STDMETHOD(put_EnableAutoProxy)(VARIANT_BOOL pEnableAutoProxy) PURE;
686 STDMETHOD(get_HTTPProxyHost)(BSTR __RPC_FAR *pbstrHTTPProxyHost) PURE;
687 STDMETHOD(put_HTTPProxyHost)(BSTR pbstrHTTPProxyHost) PURE;
688 STDMETHOD(get_HTTPProxyPort)(long __RPC_FAR *pHTTPProxyPort) PURE;
689 STDMETHOD(put_HTTPProxyPort)(long pHTTPProxyPort) PURE;
690 STDMETHOD(get_EnableMulticast)(VARIANT_BOOL __RPC_FAR *pEnableMulticast) PURE;
691 STDMETHOD(put_EnableMulticast)(VARIANT_BOOL pEnableMulticast) PURE;
692 STDMETHOD(get_EnableUDP)(VARIANT_BOOL __RPC_FAR *pEnableUDP) PURE;
693 STDMETHOD(put_EnableUDP)(VARIANT_BOOL pEnableUDP) PURE;
694 STDMETHOD(get_EnableTCP)(VARIANT_BOOL __RPC_FAR *pEnableTCP) PURE;
695 STDMETHOD(put_EnableTCP)(VARIANT_BOOL pEnableTCP) PURE;
696 STDMETHOD(get_EnableHTTP)(VARIANT_BOOL __RPC_FAR *pEnableHTTP) PURE;
697 STDMETHOD(put_EnableHTTP)(VARIANT_BOOL pEnableHTTP) PURE;
698 STDMETHOD(get_BufferingProgress)(long __RPC_FAR *pBufferingProgress) PURE;
699 STDMETHOD(get_BaseURL)(BSTR __RPC_FAR *pbstrBaseURL) PURE;
700 STDMETHOD(put_BaseURL)(BSTR pbstrBaseURL) PURE;
701 STDMETHOD(get_DefaultFrame)(BSTR __RPC_FAR *pbstrDefaultFrame) PURE;
702 STDMETHOD(put_DefaultFrame)(BSTR pbstrDefaultFrame) PURE;
703 STDMETHOD(AboutBox)(void) PURE;
704 STDMETHOD(Cancel)(void) PURE;
705 STDMETHOD(GetCodecInstalled)(long CodecNum, VARIANT_BOOL __RPC_FAR *pCodecInstalled) PURE;
706 STDMETHOD(GetCodecDescription)(long CodecNum, BSTR __RPC_FAR *pbstrCodecDescription) PURE;
707 STDMETHOD(GetCodecURL)(long CodecNum, BSTR __RPC_FAR *pbstrCodecURL) PURE;
708 STDMETHOD(Open)(BSTR bstrFileName) PURE;
709 };
710
711
712 struct INSPlay1 : public INSPlay
713 {
714 STDMETHOD(get_MediaPlayer)(IDispatch __RPC_FAR *__RPC_FAR *ppdispatch) PURE;
715 };
716
717 //---------------------------------------------------------------------------
718 // MISC COM INTERFACES
719 //---------------------------------------------------------------------------
720 typedef enum _FilterState
721 {
722 State_Stopped,
723 State_Paused,
724 State_Running
725 } FILTER_STATE;
726 typedef enum _PinDirection {
727 PINDIR_INPUT,
728 PINDIR_OUTPUT
729 } PIN_DIRECTION;
730
731 typedef struct _FilterInfo {
732 WCHAR achName[128];
733 struct IFilterGraph *pGraph;
734 } FILTER_INFO;
735
736 typedef struct _PinInfo {
737 struct IBaseFilter *pFilter;
738 PIN_DIRECTION dir;
739 WCHAR achName[128];
740 } PIN_INFO;
741
742 struct IBaseFilter;
743 struct IPin;
744 struct IEnumFilters;
745 typedef struct _MediaType {
746 GUID majortype;
747 GUID subtype;
748 BOOL bFixedSizeSamples;
749 BOOL bTemporalCompression;
750 ULONG lSampleSize;
751 GUID formattype;
752 IUnknown *pUnk;
753 ULONG cbFormat;
754 BYTE *pbFormat;
755 } AM_MEDIA_TYPE;
756
757 struct IFilterGraph : public IUnknown
758 {
759 STDMETHOD(AddFilter)(IBaseFilter *, LPCWSTR) PURE;
760 STDMETHOD(RemoveFilter)(IBaseFilter *) PURE;
761 STDMETHOD(EnumFilters)(IEnumFilters **) PURE;
762 STDMETHOD(FindFilterByName)(LPCWSTR, IBaseFilter **) PURE;
763 STDMETHOD(ConnectDirect)(IPin *, IPin *, const AM_MEDIA_TYPE *) PURE;
764 STDMETHOD(Reconnect)(IPin *) PURE;
765 STDMETHOD(Disconnect)(IPin *) PURE;
766 STDMETHOD(SetDefaultSyncSource)() PURE;
767 };
768
769 struct IGraphBuilder : public IFilterGraph
770 {
771 STDMETHOD(Connect)(IPin *, IPin *) PURE;
772 STDMETHOD(Render)(IPin *) PURE;
773 STDMETHOD(RenderFile)(LPCWSTR, LPCWSTR) PURE;
774 STDMETHOD(AddSourceFilter)(LPCWSTR, LPCWSTR, IBaseFilter **) PURE;
775 STDMETHOD(SetLogFile)(DWORD_PTR) PURE;
776 STDMETHOD(Abort)() PURE;
777 STDMETHOD(ShouldOperationContinue)() PURE;
778 };
779
780 struct IReferenceClock;
781 struct IEnumPins;
782 #define REFERENCE_TIME LONGLONG
783 struct IMediaFilter : public IPersist
784 {
785 STDMETHOD(Stop)( void) PURE;
786 STDMETHOD(Pause)( void) PURE;
787 STDMETHOD(Run)(REFERENCE_TIME tStart) PURE;
788 STDMETHOD(GetState)(DWORD dwMilliSecsTimeout,
789 FILTER_STATE *State) PURE;
790 STDMETHOD(SetSyncSource)(IReferenceClock *pClock) PURE;
791 STDMETHOD(GetSyncSource)(IReferenceClock **pClock) PURE;
792 };
793
794 struct IBaseFilter : public IMediaFilter
795 {
796 STDMETHOD(EnumPins)(IEnumPins **ppEnum) PURE;
797 STDMETHOD(FindPin)(LPCWSTR Id, IPin **ppPin) PURE;
798 STDMETHOD(QueryFilterInfo)(FILTER_INFO *pInfo) PURE;
799 STDMETHOD(JoinFilterGraph)(IFilterGraph *pGraph, LPCWSTR pName) PURE;
800 STDMETHOD(QueryVendorInfo)(LPWSTR *pVendorInfo) PURE;
801 };
802
803
804 //---------------------------------------------------------------------------
805 //
806 // wxAMMediaBackend
807 //
808 //---------------------------------------------------------------------------
809
810 typedef BOOL (WINAPI* LPAMGETERRORTEXT)(HRESULT, wxChar *, DWORD);
811
812 class WXDLLIMPEXP_MEDIA wxAMMediaBackend : public wxMediaBackendCommonBase
813 {
814 public:
815 wxAMMediaBackend();
816 virtual ~wxAMMediaBackend();
817
818 virtual bool CreateControl(wxControl* ctrl, wxWindow* parent,
819 wxWindowID id,
820 const wxPoint& pos,
821 const wxSize& size,
822 long style,
823 const wxValidator& validator,
824 const wxString& name) wxOVERRIDE;
825
826 virtual bool Play() wxOVERRIDE;
827 virtual bool Pause() wxOVERRIDE;
828 virtual bool Stop() wxOVERRIDE;
829
830 virtual bool Load(const wxString& fileName) wxOVERRIDE;
831 virtual bool Load(const wxURI& location) wxOVERRIDE;
832 virtual bool Load(const wxURI& location, const wxURI& proxy) wxOVERRIDE;
833
834 bool DoLoad(const wxString& location);
835 void FinishLoad();
836
837 virtual wxMediaState GetState() wxOVERRIDE;
838
839 virtual bool SetPosition(wxLongLong where) wxOVERRIDE;
840 virtual wxLongLong GetPosition() wxOVERRIDE;
841 virtual wxLongLong GetDuration() wxOVERRIDE;
842
843 virtual void Move(int x, int y, int w, int h) wxOVERRIDE;
844 wxSize GetVideoSize() const wxOVERRIDE;
845
846 virtual double GetPlaybackRate() wxOVERRIDE;
847 virtual bool SetPlaybackRate(double) wxOVERRIDE;
848
849 virtual double GetVolume() wxOVERRIDE;
850 virtual bool SetVolume(double) wxOVERRIDE;
851
852 virtual bool ShowPlayerControls(wxMediaCtrlPlayerControls flags) wxOVERRIDE;
853
854 void DoGetDownloadProgress(wxLongLong*, wxLongLong*);
GetDownloadProgress()855 virtual wxLongLong GetDownloadProgress() wxOVERRIDE
856 {
857 wxLongLong progress, total;
858 DoGetDownloadProgress(&progress, &total);
859 return progress;
860 }
GetDownloadTotal()861 virtual wxLongLong GetDownloadTotal() wxOVERRIDE
862 {
863 wxLongLong progress, total;
864 DoGetDownloadProgress(&progress, &total);
865 return total;
866 }
867
868 wxActiveXContainer* m_pAX; // ActiveX host
869 IActiveMovie* m_pAM;
870 IMediaPlayer* m_pMP;
871
GetMP()872 IMediaPlayer* GetMP() {return m_pMP;}
GetAM()873 IActiveMovie* GetAM() {return m_pAM;}
874 wxSize m_bestSize; // Cached size
875
876 // Stuff for getting useful debugging strings
877 #if wxDEBUG_LEVEL
878 wxDynamicLibrary m_dllQuartz;
879 LPAMGETERRORTEXT m_lpAMGetErrorText;
880 wxString GetErrorString(HRESULT hrdsv);
881 #endif // wxDEBUG_LEVEL
882 wxEvtHandler* m_evthandler;
883
884 friend class wxAMMediaEvtHandler;
885 wxDECLARE_DYNAMIC_CLASS(wxAMMediaBackend);
886 };
887
888 class WXDLLIMPEXP_MEDIA wxAMMediaEvtHandler : public wxEvtHandler
889 {
890 public:
wxAMMediaEvtHandler(wxAMMediaBackend * amb)891 wxAMMediaEvtHandler(wxAMMediaBackend *amb) :
892 m_amb(amb), m_bLoadEventSent(false)
893 {
894 m_amb->m_pAX->Bind(
895 wxEVT_ACTIVEX,
896 &wxAMMediaEvtHandler::OnActiveX, this,
897 m_amb->m_pAX->GetId()
898 );
899 }
900
901 void OnActiveX(wxActiveXEvent& event);
902
903 private:
904 wxAMMediaBackend *m_amb;
905 bool m_bLoadEventSent; // Whether or not FinishLoaded was already called
906 // prevents it being called multiple times
907
908 wxDECLARE_NO_COPY_CLASS(wxAMMediaEvtHandler);
909 };
910
911 //===========================================================================
912 // IMPLEMENTATION
913 //===========================================================================
914
915 //---------------------------------------------------------------------------
916 //
917 // wxAMMediaBackend
918 //
919 //---------------------------------------------------------------------------
920
921 wxIMPLEMENT_DYNAMIC_CLASS(wxAMMediaBackend, wxMediaBackend);
922
923 //---------------------------------------------------------------------------
924 // Usual debugging macros
925 //---------------------------------------------------------------------------
926 #if wxDEBUG_LEVEL
927 #define MAX_ERROR_TEXT_LEN 160
928
929 // Get the error string for Active Movie
GetErrorString(HRESULT hrdsv)930 wxString wxAMMediaBackend::GetErrorString(HRESULT hrdsv)
931 {
932 wxChar szError[MAX_ERROR_TEXT_LEN];
933 if( m_lpAMGetErrorText != NULL &&
934 (*m_lpAMGetErrorText)(hrdsv, szError, MAX_ERROR_TEXT_LEN) == 0)
935 {
936 return wxString::Format(wxT("DirectShow error \"%s\" \n")
937 wxT("(numeric %X)\n")
938 wxT("occurred"),
939 szError, (int)hrdsv);
940 }
941 else
942 {
943 return wxString::Format(wxT("Unknown error \n")
944 wxT("(numeric %X)\n")
945 wxT("occurred"),
946 (int)hrdsv);
947 }
948 }
949
950 #define wxAMFAIL(x) wxFAIL_MSG(GetErrorString(x));
951 #define wxVERIFY(x) wxASSERT((x))
952 #define wxAMLOG(x) wxLogDebug(GetErrorString(x))
953 #else
954 #define wxAMVERIFY(x) (x)
955 #define wxVERIFY(x) (x)
956 #define wxAMLOG(x)
957 #define wxAMFAIL(x)
958 #endif
959
960 //---------------------------------------------------------------------------
961 // wxAMMediaBackend Constructor
962 //---------------------------------------------------------------------------
wxAMMediaBackend()963 wxAMMediaBackend::wxAMMediaBackend()
964 :m_pAX(NULL),
965 m_pAM(NULL),
966 m_pMP(NULL),
967 m_bestSize(wxDefaultSize)
968 {
969 m_evthandler = NULL;
970 }
971
972 //---------------------------------------------------------------------------
973 // wxAMMediaBackend Destructor
974 //---------------------------------------------------------------------------
~wxAMMediaBackend()975 wxAMMediaBackend::~wxAMMediaBackend()
976 {
977 if(m_pAX)
978 {
979 m_pAX->DissociateHandle();
980 delete m_pAX;
981 m_pAM->Release();
982
983 if (GetMP())
984 GetMP()->Release();
985
986 if (m_evthandler)
987 {
988 m_ctrl->RemoveEventHandler(m_evthandler);
989 delete m_evthandler;
990 }
991 }
992 }
993
994 //---------------------------------------------------------------------------
995 // wxAMMediaBackend::CreateControl
996 //---------------------------------------------------------------------------
CreateControl(wxControl * ctrl,wxWindow * parent,wxWindowID id,const wxPoint & pos,const wxSize & size,long style,const wxValidator & validator,const wxString & name)997 bool wxAMMediaBackend::CreateControl(wxControl* ctrl, wxWindow* parent,
998 wxWindowID id,
999 const wxPoint& pos,
1000 const wxSize& size,
1001 long style,
1002 const wxValidator& validator,
1003 const wxString& name)
1004 {
1005 // First get the AMGetErrorText procedure in debug
1006 // mode for more meaningful messages
1007 #if wxDEBUG_LEVEL
1008 if ( m_dllQuartz.Load(wxT("quartz.dll"), wxDL_VERBATIM) )
1009 {
1010 m_lpAMGetErrorText = (LPAMGETERRORTEXT)
1011 m_dllQuartz.GetSymbolAorW(wxT("AMGetErrorText"));
1012 }
1013 #endif // wxDEBUG_LEVEL
1014
1015
1016
1017 // Now determine which (if any) media player interface is
1018 // available - IMediaPlayer or IActiveMovie
1019 if( ::CoCreateInstance(CLSID_MediaPlayer, NULL,
1020 CLSCTX_INPROC_SERVER,
1021 IID_IMediaPlayer, (void**)&m_pMP) != 0 )
1022 {
1023 if( ::CoCreateInstance(CLSID_ActiveMovie, NULL,
1024 CLSCTX_INPROC_SERVER,
1025 IID_IActiveMovie, (void**)&m_pAM) != 0 )
1026 return false;
1027 m_pAM->QueryInterface(IID_IMediaPlayer, (void**)&m_pMP);
1028 }
1029 else
1030 {
1031 m_pMP->QueryInterface(IID_IActiveMovie, (void**)&m_pAM);
1032 }
1033
1034 //
1035 // Create window
1036 // By default wxWindow(s) is created with a border -
1037 // so we need to get rid of those
1038 //
1039 // Since we don't have a child window like most other
1040 // backends, we don't need wxCLIP_CHILDREN
1041 //
1042 if ( !ctrl->wxControl::Create(parent, id, pos, size,
1043 (style & ~wxBORDER_MASK) | wxBORDER_NONE,
1044 validator, name) )
1045 return false;
1046
1047 //
1048 // Now create the ActiveX container along with the media player
1049 // interface and query them
1050 //
1051 m_ctrl = wxStaticCast(ctrl, wxMediaCtrl);
1052 m_pAX = new wxActiveXContainer(ctrl,
1053 m_pMP ? IID_IMediaPlayer : IID_IActiveMovie, m_pAM
1054 );
1055 // Connect for events
1056 m_evthandler = new wxAMMediaEvtHandler(this);
1057 m_ctrl->PushEventHandler(m_evthandler);
1058
1059 //
1060 // Here we set up wx-specific stuff for the default
1061 // settings wxMediaCtrl says it will stay to
1062 //
1063 if(GetMP())
1064 {
1065 GetMP()->put_DisplaySize(mpFitToSize);
1066 // TODO: Unsure what actual effect this has
1067 // In DirectShow Windowless video results in less delay when
1068 // dragging, for example - but this doesn't appear to really do anything
1069 // in practice (it may be something different...)...
1070 GetMP()->put_WindowlessVideo(VARIANT_TRUE);
1071
1072 }
1073 else
1074 GetAM()->put_MovieWindowSize(amvDoubleOriginalSize);
1075
1076 // by default true
1077 GetAM()->put_AutoStart(VARIANT_FALSE);
1078 // by default enabled
1079 wxAMMediaBackend::ShowPlayerControls(wxMEDIACTRLPLAYERCONTROLS_NONE);
1080 // by default with AM only 0.5
1081 wxAMMediaBackend::SetVolume(1.0);
1082
1083 // don't erase the background of our control window so that resizing is a
1084 // bit smoother
1085 m_ctrl->SetBackgroundStyle(wxBG_STYLE_PAINT);
1086
1087 // success
1088 return true;
1089 }
1090
1091 //---------------------------------------------------------------------------
1092 // wxAMMediaBackend::Load (file version)
1093 //---------------------------------------------------------------------------
Load(const wxString & fileName)1094 bool wxAMMediaBackend::Load(const wxString& fileName)
1095 {
1096 return DoLoad(fileName);
1097 }
1098
1099 //---------------------------------------------------------------------------
1100 // wxAMMediaBackend::Load (URL Version)
1101 //---------------------------------------------------------------------------
Load(const wxURI & location)1102 bool wxAMMediaBackend::Load(const wxURI& location)
1103 {
1104 // Turn off loading from a proxy as user
1105 // may have set it previously
1106 INSPlay* pPlay = NULL;
1107 GetAM()->QueryInterface(IID_INSPlay, (void**) &pPlay);
1108 if(pPlay)
1109 {
1110 pPlay->put_UseHTTPProxy(VARIANT_FALSE);
1111 pPlay->Release();
1112 }
1113
1114 return DoLoad(location.BuildURI());
1115 }
1116
1117 //---------------------------------------------------------------------------
1118 // wxAMMediaBackend::Load (URL Version with Proxy)
1119 //---------------------------------------------------------------------------
Load(const wxURI & location,const wxURI & proxy)1120 bool wxAMMediaBackend::Load(const wxURI& location, const wxURI& proxy)
1121 {
1122 // Set the proxy of the NETSHOW interface
1123 INSPlay* pPlay = NULL;
1124 GetAM()->QueryInterface(IID_INSPlay, (void**) &pPlay);
1125
1126 if(pPlay)
1127 {
1128 pPlay->put_UseHTTPProxy(VARIANT_TRUE);
1129 pPlay->put_HTTPProxyHost(wxBasicString(proxy.GetServer()));
1130 pPlay->put_HTTPProxyPort(wxAtoi(proxy.GetPort()));
1131 pPlay->Release();
1132 }
1133
1134 return DoLoad(location.BuildURI());
1135 }
1136
1137 //---------------------------------------------------------------------------
1138 // wxAMMediaBackend::DoLoad
1139 //
1140 // Called by all functions - this actually renders
1141 // the file and sets up the filter graph
1142 //---------------------------------------------------------------------------
DoLoad(const wxString & location)1143 bool wxAMMediaBackend::DoLoad(const wxString& location)
1144 {
1145 HRESULT hr;
1146
1147 // Play the movie the normal way through the embedded
1148 // WMP. Supposively Open is better in theory because
1149 // the docs say its async and put_FileName is not -
1150 // but in practice they both seem to be async anyway
1151 if(GetMP())
1152 hr = GetMP()->Open( wxBasicString(location) );
1153 else
1154 hr = GetAM()->put_FileName( wxBasicString(location) );
1155
1156 if(FAILED(hr))
1157 {
1158 wxAMLOG(hr);
1159 return false;
1160 }
1161
1162 m_bestSize = wxDefaultSize;
1163 return true;
1164 }
1165
1166 //---------------------------------------------------------------------------
1167 // wxAMMediaBackend::FinishLoad
1168 //
1169 // Called when the media has finished loaded and is ready to play
1170 //
1171 // Here we get the original size of the video and
1172 // send the loaded event to our watcher :).
1173 //---------------------------------------------------------------------------
FinishLoad()1174 void wxAMMediaBackend::FinishLoad()
1175 {
1176 NotifyMovieLoaded();
1177 }
1178
1179 //---------------------------------------------------------------------------
1180 // wxAMMediaBackend::ShowPlayerControls
1181 //---------------------------------------------------------------------------
ShowPlayerControls(wxMediaCtrlPlayerControls flags)1182 bool wxAMMediaBackend::ShowPlayerControls(wxMediaCtrlPlayerControls flags)
1183 {
1184 // Note that IMediaPlayer doesn't have a statusbar by
1185 // default but IActiveMovie does - so let's try to keep
1186 // the interface consistent.
1187 if(!flags)
1188 {
1189 GetAM()->put_Enabled(VARIANT_FALSE);
1190 GetAM()->put_ShowControls(VARIANT_FALSE);
1191 if(GetMP())
1192 GetMP()->put_ShowStatusBar(VARIANT_FALSE);
1193 }
1194 else
1195 {
1196 GetAM()->put_Enabled(VARIANT_TRUE);
1197 GetAM()->put_ShowControls(VARIANT_TRUE);
1198
1199 GetAM()->put_ShowPositionControls(
1200 (flags & wxMEDIACTRLPLAYERCONTROLS_STEP) ?
1201 VARIANT_TRUE : VARIANT_FALSE);
1202
1203 if(GetMP())
1204 {
1205 GetMP()->put_ShowStatusBar(VARIANT_TRUE);
1206 GetMP()->put_ShowAudioControls(
1207 (flags & wxMEDIACTRLPLAYERCONTROLS_VOLUME) ?
1208 VARIANT_TRUE : VARIANT_FALSE);
1209 }
1210 }
1211
1212 return true;
1213 }
1214
1215 //---------------------------------------------------------------------------
1216 // wxAMMediaBackend::Play
1217 //
1218 // Plays the stream. If it is non-seekable, it will restart it (implicit).
1219 //
1220 // Note that we use SUCCEEDED here because run/pause/stop tend to be overly
1221 // picky and return warnings on pretty much every call
1222 //---------------------------------------------------------------------------
Play()1223 bool wxAMMediaBackend::Play()
1224 {
1225 // Actually try to play the movie (will fail if not loaded completely)
1226 HRESULT hr = GetAM()->Run();
1227 if(SUCCEEDED(hr))
1228 {
1229 return true;
1230 }
1231 wxAMLOG(hr);
1232 return false;
1233 }
1234
1235 //---------------------------------------------------------------------------
1236 // wxAMMediaBackend::Pause
1237 //
1238 // Pauses the stream.
1239 //---------------------------------------------------------------------------
Pause()1240 bool wxAMMediaBackend::Pause()
1241 {
1242 HRESULT hr = GetAM()->Pause();
1243 if(SUCCEEDED(hr))
1244 return true;
1245 wxAMLOG(hr);
1246 return false;
1247 }
1248
1249 //---------------------------------------------------------------------------
1250 // wxAMMediaBackend::Stop
1251 //
1252 // Stops the stream.
1253 //---------------------------------------------------------------------------
Stop()1254 bool wxAMMediaBackend::Stop()
1255 {
1256 HRESULT hr = GetAM()->Stop();
1257 if(SUCCEEDED(hr))
1258 {
1259 // Seek to beginning
1260 wxAMMediaBackend::SetPosition(0);
1261 return true;
1262 }
1263 wxAMLOG(hr);
1264 return false;
1265 }
1266
1267 //---------------------------------------------------------------------------
1268 // wxAMMediaBackend::SetPosition
1269 //
1270 // 1) Translates the current position's time to directshow time,
1271 // which is in a scale of 1 second (in a double)
1272 // 2) Sets the play position of the IActiveMovie interface -
1273 // passing NULL as the stop position means to keep the old
1274 // stop position
1275 //---------------------------------------------------------------------------
SetPosition(wxLongLong where)1276 bool wxAMMediaBackend::SetPosition(wxLongLong where)
1277 {
1278 HRESULT hr = GetAM()->put_CurrentPosition(
1279 ((LONGLONG)where.GetValue()) / 1000.0
1280 );
1281 if(FAILED(hr))
1282 {
1283 wxAMLOG(hr);
1284 return false;
1285 }
1286
1287 return true;
1288 }
1289
1290 //---------------------------------------------------------------------------
1291 // wxAMMediaBackend::GetPosition
1292 //
1293 // 1) Obtains the current play and stop positions from IMediaSeeking
1294 // 2) Returns the play position translated to our time base
1295 //---------------------------------------------------------------------------
GetPosition()1296 wxLongLong wxAMMediaBackend::GetPosition()
1297 {
1298 double outCur;
1299 HRESULT hr = GetAM()->get_CurrentPosition(&outCur);
1300 if(FAILED(hr))
1301 {
1302 wxAMLOG(hr);
1303 return 0;
1304 }
1305
1306 // h,m,s,milli - outCur is in 1 second (double)
1307 outCur *= 1000;
1308 wxLongLong ll;
1309 ll.Assign(outCur);
1310
1311 return ll;
1312 }
1313
1314 //---------------------------------------------------------------------------
1315 // wxAMMediaBackend::GetVolume and SetVolume()
1316 //
1317 // Notice that for the IActiveMovie interface value ranges from 0 (MAX volume)
1318 // to -10000 (minimum volume) and the scale is logarithmic in 0.01db per step.
1319 //---------------------------------------------------------------------------
1320
GetVolume()1321 double wxAMMediaBackend::GetVolume()
1322 {
1323 long lVolume;
1324 HRESULT hr = GetAM()->get_Volume(&lVolume);
1325 if(FAILED(hr))
1326 {
1327 wxAMLOG(hr);
1328 return 0.0;
1329 }
1330
1331 double dVolume = lVolume / 2000.; // volume is now in [-5..0] range
1332 dVolume = pow(10.0, dVolume); // [10^-5, 1]
1333 dVolume -= 0.00001; // [0, 1-10^-5]
1334 dVolume /= 1 - 0.00001; // [0, 1]
1335
1336 return dVolume;
1337 }
1338
SetVolume(double dVolume)1339 bool wxAMMediaBackend::SetVolume(double dVolume)
1340 {
1341 // inverse the transformation above
1342 long lVolume = static_cast<long>(2000*log10(dVolume + (1 - dVolume)*0.00001));
1343
1344 HRESULT hr = GetAM()->put_Volume(lVolume);
1345 if(FAILED(hr))
1346 {
1347 wxAMLOG(hr);
1348 return false;
1349 }
1350 return true;
1351 }
1352
1353 //---------------------------------------------------------------------------
1354 // wxAMMediaBackend::GetDuration
1355 //
1356 // 1) Obtains the duration of the media from IActiveMovie
1357 // 2) Converts that value to our time base, and returns it
1358 //
1359 // NB: With VBR MP3 files the default DirectShow MP3 render does not
1360 // read the Xing header correctly, resulting in skewed values for duration
1361 // and seeking
1362 //---------------------------------------------------------------------------
GetDuration()1363 wxLongLong wxAMMediaBackend::GetDuration()
1364 {
1365 double outDuration;
1366 HRESULT hr = GetAM()->get_Duration(&outDuration);
1367 switch ( hr )
1368 {
1369 default:
1370 wxAMLOG(hr);
1371 wxFALLTHROUGH;
1372
1373 case S_FALSE:
1374 return 0;
1375
1376 case S_OK:
1377 // outDuration is in seconds, we need milliseconds
1378 #ifdef wxLongLong_t
1379 return static_cast<wxLongLong_t>(outDuration * 1000);
1380 #else
1381 // In principle it's possible to have video of duration greater
1382 // than ~1193 hours which corresponds LONG_MAX in milliseconds so
1383 // cast to wxLongLong first and multiply by 1000 only then to avoid
1384 // the overflow (resulting in maximal duration of ~136 years).
1385 return wxLongLong(static_cast<long>(outDuration)) * 1000;
1386 #endif
1387 }
1388 }
1389
1390 //---------------------------------------------------------------------------
1391 // wxAMMediaBackend::GetState
1392 //
1393 // Returns the cached state
1394 //---------------------------------------------------------------------------
GetState()1395 wxMediaState wxAMMediaBackend::GetState()
1396 {
1397 StateConstants nState;
1398 HRESULT hr = GetAM()->get_CurrentState(&nState);
1399 if(FAILED(hr))
1400 {
1401 wxAMLOG(hr);
1402 return wxMEDIASTATE_STOPPED;
1403 }
1404
1405 return (wxMediaState)nState;
1406 }
1407
1408 //---------------------------------------------------------------------------
1409 // wxAMMediaBackend::GetPlaybackRate
1410 //
1411 // Pretty simple way of obtaining the playback rate from
1412 // the IActiveMovie interface
1413 //---------------------------------------------------------------------------
GetPlaybackRate()1414 double wxAMMediaBackend::GetPlaybackRate()
1415 {
1416 double dRate;
1417 HRESULT hr = GetAM()->get_Rate(&dRate);
1418 if(FAILED(hr))
1419 {
1420 wxAMLOG(hr);
1421 return 0.0;
1422 }
1423 return dRate;
1424 }
1425
1426 //---------------------------------------------------------------------------
1427 // wxAMMediaBackend::SetPlaybackRate
1428 //
1429 // Sets the playback rate of the media - DirectShow is pretty good
1430 // about this, actually
1431 //---------------------------------------------------------------------------
SetPlaybackRate(double dRate)1432 bool wxAMMediaBackend::SetPlaybackRate(double dRate)
1433 {
1434 HRESULT hr = GetAM()->put_Rate(dRate);
1435 if(FAILED(hr))
1436 {
1437 wxAMLOG(hr);
1438 return false;
1439 }
1440
1441 return true;
1442 }
1443
1444 //---------------------------------------------------------------------------
1445 // wxAMMediaBackend::GetDownloadXXX
1446 //
1447 // Queries for and gets the total size of the file and the current
1448 // progress in downloading that file from the IAMOpenProgress
1449 // interface from the media player interface's filter graph
1450 //---------------------------------------------------------------------------
DoGetDownloadProgress(wxLongLong * pLoadProgress,wxLongLong * pLoadTotal)1451 void wxAMMediaBackend::DoGetDownloadProgress(wxLongLong* pLoadProgress,
1452 wxLongLong* pLoadTotal)
1453 {
1454 IUnknown* pFG = NULL;
1455
1456 HRESULT hr = m_pAM->get_FilterGraph(&pFG);
1457
1458 // notice that the call above may return S_FALSE and leave pFG NULL
1459 if(SUCCEEDED(hr) && pFG)
1460 {
1461 IAMOpenProgress* pOP = NULL;
1462 hr = pFG->QueryInterface(IID_IAMOpenProgress, (void**)&pOP);
1463 if(SUCCEEDED(hr) && pOP)
1464 {
1465 LONGLONG
1466 loadTotal = 0,
1467 loadProgress = 0;
1468 hr = pOP->QueryProgress(&loadTotal, &loadProgress);
1469 pOP->Release();
1470
1471 if(SUCCEEDED(hr))
1472 {
1473 *pLoadProgress = loadProgress;
1474 *pLoadTotal = loadTotal;
1475 pFG->Release();
1476 return;
1477 }
1478 }
1479 pFG->Release();
1480 }
1481
1482 *pLoadProgress = 0;
1483 *pLoadTotal = 0;
1484 }
1485
1486 //---------------------------------------------------------------------------
1487 // wxAMMediaBackend::GetVideoSize
1488 //
1489 // Obtains the cached original video size
1490 //---------------------------------------------------------------------------
GetVideoSize() const1491 wxSize wxAMMediaBackend::GetVideoSize() const
1492 {
1493 if (m_bestSize == wxDefaultSize)
1494 {
1495 wxAMMediaBackend* self = wxConstCast(this, wxAMMediaBackend);
1496 long w = 0;
1497 long h = 0;
1498
1499 self->GetAM()->get_ImageSourceWidth(&w);
1500 self->GetAM()->get_ImageSourceHeight(&h);
1501
1502 if (w != 0 && h != 0)
1503 self->m_bestSize.Set(w, h);
1504 else
1505 return wxSize(0,0);
1506 }
1507
1508 return m_bestSize;
1509 }
1510
1511 //---------------------------------------------------------------------------
1512 // wxAMMediaBackend::Move
1513 //
1514 // We take care of this in our redrawing
1515 //---------------------------------------------------------------------------
Move(int WXUNUSED (x),int WXUNUSED (y),int WXUNUSED (w),int WXUNUSED (h))1516 void wxAMMediaBackend::Move(int WXUNUSED(x), int WXUNUSED(y),
1517 int WXUNUSED(w), int WXUNUSED(h))
1518 {
1519 }
1520
1521 //---------------------------------------------------------------------------
1522 // wxAMMediaBackend::OnActiveX
1523 //
1524 // Handle events sent from our activex control (IActiveMovie/IMediaPlayer).
1525 //
1526 // The weird numbers in the switch statement here are "dispatch ids"
1527 // (the numbers in the id field like ( id(xxx) ) ) from amcompat.idl
1528 // and msdxm.idl.
1529 //---------------------------------------------------------------------------
OnActiveX(wxActiveXEvent & event)1530 void wxAMMediaEvtHandler::OnActiveX(wxActiveXEvent& event)
1531 {
1532 // cast to unsigned long to fix narrowing error with case 0xfffffd9f
1533 // when using clang
1534 switch (static_cast<unsigned long>(event.GetDispatchId()))
1535 {
1536 case 0x00000001: // statechange in IActiveMovie
1537 case 0x00000bc4: // playstatechange in IMediaPlayer
1538 if(event.ParamCount() >= 2)
1539 {
1540 switch (event[1].GetInteger())
1541 {
1542 case 0: // stopping
1543 if( m_amb->wxAMMediaBackend::GetPosition() ==
1544 m_amb->wxAMMediaBackend::GetDuration() )
1545 {
1546 if ( m_amb->SendStopEvent() )
1547 {
1548 // Seek to beginning of movie
1549 m_amb->wxAMMediaBackend::SetPosition(0);
1550
1551 // send the event to our child
1552 m_amb->QueueFinishEvent();
1553 }
1554 }
1555 else
1556 {
1557 m_amb->QueueStopEvent();
1558 }
1559 break;
1560 case 1: // pause
1561 m_amb->QueuePauseEvent();
1562 break;
1563 case 2: // play
1564 m_amb->QueuePlayEvent();
1565 break;
1566 default:
1567 break;
1568 }
1569 }
1570 else
1571 event.Skip();
1572 break;
1573
1574 case 0x00000032: // opencomplete in IActiveMovie
1575 if(!m_bLoadEventSent)
1576 {
1577 m_amb->FinishLoad();
1578 }
1579 break;
1580
1581 case 0xfffffd9f: // readystatechange in IActiveMovie2 and IMediaPlayer
1582 if(event.ParamCount() >= 1)
1583 {
1584 if(event[0].GetInteger() == 0)
1585 {
1586 m_bLoadEventSent = false;
1587 }
1588 // Originally this was >= 3 here but on 3 we can't get the
1589 // size of the video (will error) - however on 4
1590 // it won't play on downloaded things until it is
1591 // completely downloaded so we use the lesser of two evils...
1592 else if(event[0].GetInteger() == 3 &&
1593 !m_bLoadEventSent)
1594 {
1595 m_bLoadEventSent = true;
1596 m_amb->FinishLoad();
1597 }
1598 }
1599 else
1600 event.Skip();
1601 break;
1602
1603 default:
1604 event.Skip();
1605 return;
1606 }
1607 }
1608
1609 //---------------------------------------------------------------------------
1610 // End of wxAMMediaBackend
1611 //---------------------------------------------------------------------------
1612
1613 // Allow the user code to use wxFORCE_LINK_MODULE() to ensure that this object
1614 // file is not discarded by the linker.
1615 #include "wx/link.h"
1616 wxFORCE_LINK_THIS_MODULE(wxmediabackend_am)
1617
1618 #endif // wxUSE_MEDIACTRL && wxUSE_ACTIVEX
1619