[xiph-commits] r16902 - in trunk/oggdsf/src/lib/plugin/AxPlayer: . Res
cristianadam at svn.xiph.org
cristianadam at svn.xiph.org
Mon Feb 15 16:14:26 PST 2010
Author: cristianadam
Date: 2010-02-15 16:14:26 -0800 (Mon, 15 Feb 2010)
New Revision: 16902
Added:
trunk/oggdsf/src/lib/plugin/AxPlayer/CustomVMR7Allocator.cpp
trunk/oggdsf/src/lib/plugin/AxPlayer/CustomVMR7Allocator.h
trunk/oggdsf/src/lib/plugin/AxPlayer/DDrawUtil.cpp
trunk/oggdsf/src/lib/plugin/AxPlayer/DDrawUtil.h
trunk/oggdsf/src/lib/plugin/AxPlayer/DShowUtil.cpp
trunk/oggdsf/src/lib/plugin/AxPlayer/DShowUtil.h
trunk/oggdsf/src/lib/plugin/AxPlayer/DShowVideoPlayer.cpp
trunk/oggdsf/src/lib/plugin/AxPlayer/DShowVideoPlayer.h
trunk/oggdsf/src/lib/plugin/AxPlayer/FilterGraph.cpp
trunk/oggdsf/src/lib/plugin/AxPlayer/FilterGraph.h
trunk/oggdsf/src/lib/plugin/AxPlayer/Guid.h
trunk/oggdsf/src/lib/plugin/AxPlayer/_IVideoTagBehaviorEvents_CP.h
Modified:
trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.cpp
trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.idl
trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.vcproj
trunk/oggdsf/src/lib/plugin/AxPlayer/Res/AxPlayer.rc
trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.cpp
trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.h
trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.rgs
trunk/oggdsf/src/lib/plugin/AxPlayer/stdafx.h
trunk/oggdsf/src/lib/plugin/AxPlayer/test.html
Log:
Basic playback support.
Modified: trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.cpp
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.cpp 2010-02-15 02:14:14 UTC (rev 16901)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.cpp 2010-02-16 00:14:26 UTC (rev 16902)
@@ -1,6 +1,34 @@
-// AxPlayer.cpp : Implementation of DLL Exports.
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
-
#include "stdafx.h"
#include "resource.h"
#include "AxPlayer_i.h"
@@ -11,7 +39,7 @@
namespace
{
// Conform with http://wiki.whatwg.org/wiki/FAQ#What_is_the_namespace_declaration.3F
- const wchar_t* HTML5NS = L"http://www.w3.org/1999/xhtml";
+ const wchar_t* HTML5NS = L"http://www.w3.org/1999/xhtml/video";
}
// Used to determine whether the DLL can be unloaded by OLE
Modified: trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.idl
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.idl 2010-02-15 02:14:14 UTC (rev 16901)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.idl 2010-02-16 00:14:26 UTC (rev 16902)
@@ -18,6 +18,16 @@
interface IVideoTagBehavior : IDispatch{
};
[
+ object,
+ uuid(F3486DCF-295B-499C-97F6-33CB1FC8D783),
+ dual,
+ nonextensible,
+ helpstring("IHTMLEventsSink Interface"),
+ pointer_default(unique)
+]
+interface IHTMLEventsSink : IDispatch{
+};
+[
uuid(4856ADA6-564F-41B8-ACAA-E98ABD004A84),
version(1.0),
helpstring("AxPlayer 1.0 Type Library")
@@ -36,11 +46,19 @@
};
[
uuid(7CC95AE6-C1FA-40CC-AB17-3E91DA2F77CA),
- helpstring("HTML5 <video> and <audio> implementation.")
+ helpstring("HTML5 <video> and <audio> implementation")
]
coclass VideoTagBehavior
{
[default] interface IVideoTagBehavior;
[default, source] dispinterface _IVideoTagBehaviorEvents;
};
+ [
+ uuid(8CCDB61D-0D74-464A-84EE-F33C3E1F0B8B),
+ helpstring("HTMLEventsSink Class")
+ ]
+ coclass HTMLEventsSink
+ {
+ [default] interface IHTMLEventsSink;
+ };
};
Modified: trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.vcproj
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.vcproj 2010-02-15 02:14:14 UTC (rev 16901)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/AxPlayer.vcproj 2010-02-16 00:14:26 UTC (rev 16902)
@@ -21,7 +21,7 @@
<Configurations>
<Configuration
Name="Debug|Win32"
- OutputDirectory="$(PlatformName)\$(ConfigurationName)"
+ OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
ConfigurationType="2"
UseOfATL="2"
@@ -62,7 +62,7 @@
BasicRuntimeChecks="3"
RuntimeLibrary="3"
UsePrecompiledHeader="2"
- WarningLevel="3"
+ WarningLevel="4"
DebugInformationFormat="4"
/>
<Tool
@@ -81,6 +81,7 @@
Name="VCLinkerTool"
RegisterOutput="true"
IgnoreImportLibrary="true"
+ AdditionalDependencies="ddraw.lib"
LinkIncremental="2"
ModuleDefinitionFile=".\AxPlayer.def"
GenerateDebugInformation="true"
@@ -111,7 +112,7 @@
</Configuration>
<Configuration
Name="Debug|x64"
- OutputDirectory="$(PlatformName)\$(ConfigurationName)"
+ OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
ConfigurationType="2"
UseOfATL="2"
@@ -145,7 +146,7 @@
<Tool
Name="VCCLCompilerTool"
Optimization="0"
- AdditionalIncludeDirectories=""Generated Files";res;..\..\helper\common\"
+ AdditionalIncludeDirectories=""Generated Files";res;..\..\helper\"
PreprocessorDefinitions="WIN32;_WINDOWS;_DEBUG;_USRDLL;_MERGE_PROXYSTUB"
MinimalRebuild="true"
BasicRuntimeChecks="3"
@@ -169,6 +170,7 @@
<Tool
Name="VCLinkerTool"
IgnoreImportLibrary="true"
+ AdditionalDependencies="ddraw.lib"
LinkIncremental="2"
ModuleDefinitionFile=".\AxPlayer.def"
GenerateDebugInformation="true"
@@ -199,7 +201,7 @@
</Configuration>
<Configuration
Name="Release|Win32"
- OutputDirectory="$(PlatformName)\$(ConfigurationName)"
+ OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
ConfigurationType="2"
UseOfATL="2"
@@ -234,11 +236,12 @@
<Tool
Name="VCCLCompilerTool"
Optimization="2"
- AdditionalIncludeDirectories=""Generated Files";res;..\..\helper\common\"
+ AdditionalIncludeDirectories=""Generated Files";res;..\..\helper"
PreprocessorDefinitions="WIN32;_WINDOWS;NDEBUG;_USRDLL;_MERGE_PROXYSTUB"
+ ExceptionHandling="2"
RuntimeLibrary="2"
UsePrecompiledHeader="2"
- WarningLevel="3"
+ WarningLevel="4"
DebugInformationFormat="3"
/>
<Tool
@@ -257,6 +260,7 @@
Name="VCLinkerTool"
RegisterOutput="true"
IgnoreImportLibrary="true"
+ AdditionalDependencies="ddraw.lib"
LinkIncremental="1"
ModuleDefinitionFile=".\AxPlayer.def"
GenerateDebugInformation="true"
@@ -289,7 +293,7 @@
</Configuration>
<Configuration
Name="Release|x64"
- OutputDirectory="$(PlatformName)\$(ConfigurationName)"
+ OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
ConfigurationType="2"
UseOfATL="2"
@@ -323,8 +327,9 @@
<Tool
Name="VCCLCompilerTool"
Optimization="2"
- AdditionalIncludeDirectories=""Generated Files";res;..\..\helper\common\"
+ AdditionalIncludeDirectories=""Generated Files";res;..\..\helper\"
PreprocessorDefinitions="WIN32;_WINDOWS;NDEBUG;_USRDLL;_MERGE_PROXYSTUB"
+ ExceptionHandling="2"
RuntimeLibrary="2"
UsePrecompiledHeader="2"
WarningLevel="3"
@@ -345,6 +350,7 @@
<Tool
Name="VCLinkerTool"
IgnoreImportLibrary="true"
+ AdditionalDependencies="ddraw.lib"
LinkIncremental="1"
ModuleDefinitionFile=".\AxPlayer.def"
GenerateDebugInformation="true"
@@ -397,6 +403,14 @@
>
</File>
<File
+ RelativePath=".\CustomVMR7Allocator.cpp"
+ >
+ </File>
+ <File
+ RelativePath=".\DDrawUtil.cpp"
+ >
+ </File>
+ <File
RelativePath=".\dlldatax.c"
>
<FileConfiguration
@@ -477,6 +491,18 @@
</FileConfiguration>
</File>
<File
+ RelativePath=".\DShowUtil.cpp"
+ >
+ </File>
+ <File
+ RelativePath=".\DShowVideoPlayer.cpp"
+ >
+ </File>
+ <File
+ RelativePath=".\FilterGraph.cpp"
+ >
+ </File>
+ <File
RelativePath=".\stdafx.cpp"
>
<FileConfiguration
@@ -527,6 +553,14 @@
>
</File>
<File
+ RelativePath=".\CustomVMR7Allocator.h"
+ >
+ </File>
+ <File
+ RelativePath=".\DDrawUtil.h"
+ >
+ </File>
+ <File
RelativePath=".\dlldatax.h"
>
</File>
@@ -535,6 +569,14 @@
>
</File>
<File
+ RelativePath=".\DShowVideoPlayer.h"
+ >
+ </File>
+ <File
+ RelativePath=".\FilterGraph.h"
+ >
+ </File>
+ <File
RelativePath=".\Res\resource.h"
>
</File>
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/CustomVMR7Allocator.cpp
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/CustomVMR7Allocator.cpp (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/CustomVMR7Allocator.cpp 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,117 @@
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+
+#include "StdAfx.h"
+#include "CustomVMR7Allocator.h"
+#include <uuids.h>
+
+CustomVMR7Allocator::CustomVMR7Allocator():
+m_notifyWindow(0),
+m_presentImageMessage(0)
+{
+}
+
+CustomVMR7Allocator::~CustomVMR7Allocator()
+{
+}
+
+
+HRESULT CustomVMR7Allocator::CreateDefaultSurfaceAllocator()
+{
+ return m_defaultAllocator.CoCreateInstance(CLSID_AllocPresenter, 0, CLSCTX_INPROC_SERVER);
+}
+
+// IVMRSurfaceAllocator Methods
+HRESULT __stdcall CustomVMR7Allocator::AllocateSurface(DWORD_PTR dwUserID, VMRALLOCATIONINFO *lpAllocInfo,
+ DWORD *lpdwActualBuffers, LPDIRECTDRAWSURFACE7 *lplpSurface)
+{
+ ATLASSERT(m_defaultAllocator && "Missing default allocator");
+ return m_defaultAllocator->AllocateSurface(dwUserID, lpAllocInfo, lpdwActualBuffers, lplpSurface);
+}
+
+HRESULT __stdcall CustomVMR7Allocator::FreeSurface(DWORD_PTR dwID)
+{
+ ATLASSERT(m_defaultAllocator && "Missing default allocator");
+ return m_defaultAllocator->FreeSurface(dwID);
+}
+
+HRESULT __stdcall CustomVMR7Allocator::PrepareSurface(DWORD_PTR dwUserID,LPDIRECTDRAWSURFACE7 lpSurface,
+ DWORD dwSurfaceFlags)
+{
+ ATLASSERT(m_defaultAllocator && "Missing default allocator");
+ return m_defaultAllocator->PrepareSurface(dwUserID, lpSurface, dwSurfaceFlags);
+}
+
+HRESULT __stdcall CustomVMR7Allocator::AdviseNotify(IVMRSurfaceAllocatorNotify *lpIVMRSurfAllocNotify)
+{
+ ATLASSERT(m_defaultAllocator && "Missing default allocator");
+ return m_defaultAllocator->AdviseNotify(lpIVMRSurfAllocNotify);
+}
+
+// IVMRImagePresenter Methods
+HRESULT __stdcall CustomVMR7Allocator::StartPresenting(DWORD_PTR /*dwUserID*/)
+{
+ return S_OK;
+}
+
+HRESULT __stdcall CustomVMR7Allocator::StopPresenting(DWORD_PTR /*dwUserID*/)
+{
+ return S_OK;
+}
+
+HRESULT __stdcall CustomVMR7Allocator::PresentImage(DWORD_PTR dwUserID, VMRPRESENTATIONINFO *lpPresInfo)
+{
+ ATLASSERT(m_notifyWindow && "SetNotifyWindow must be called first!");
+ ATLASSERT(m_presentImageMessage && "SetPresentImageMessage must be called first!");
+
+ ::SendMessage(m_notifyWindow, m_presentImageMessage, dwUserID, reinterpret_cast<LPARAM>(lpPresInfo));
+ return S_OK;
+}
+
+int CustomVMR7Allocator::GetPresentImageMessage() const
+{
+ return m_presentImageMessage;
+}
+
+void CustomVMR7Allocator::SetPresentImageMessage( int val )
+{
+ m_presentImageMessage = val;
+}
+
+HWND CustomVMR7Allocator::GetNotifyWindow() const
+{
+ return m_notifyWindow;
+}
+
+void CustomVMR7Allocator::SetNotifyWindow( HWND val )
+{
+ m_notifyWindow = val;
+}
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/CustomVMR7Allocator.h
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/CustomVMR7Allocator.h (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/CustomVMR7Allocator.h 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,83 @@
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+
+#ifndef CUSTOMVMR7ALLOCATOR_H
+#define CUSTOMVMR7ALLOCATOR_H
+
+#pragma once
+
+#include <ddraw.h>
+#include <strmif.h>
+
+class CustomVMR7Allocator:
+ public CComObjectRootEx<CComSingleThreadModel>,
+ public IVMRSurfaceAllocator,
+ public IVMRImagePresenter
+{
+public:
+
+ BEGIN_COM_MAP(CustomVMR7Allocator)
+ COM_INTERFACE_ENTRY(IVMRSurfaceAllocator)
+ COM_INTERFACE_ENTRY(IVMRImagePresenter)
+ END_COM_MAP()
+
+ CustomVMR7Allocator();
+ virtual ~CustomVMR7Allocator();
+
+ int GetPresentImageMessage() const;
+ void SetPresentImageMessage(int val);
+
+ HWND GetNotifyWindow() const;
+ void SetNotifyWindow(HWND val);
+
+ HRESULT CreateDefaultSurfaceAllocator();
+
+ // IVMRSurfaceAllocator Methods
+ virtual HRESULT __stdcall AllocateSurface(DWORD_PTR dwUserID, VMRALLOCATIONINFO *lpAllocInfo,
+ DWORD *lpdwActualBuffers, LPDIRECTDRAWSURFACE7 *lplpSurface);
+ virtual HRESULT __stdcall FreeSurface(DWORD_PTR dwID);
+ virtual HRESULT __stdcall PrepareSurface(DWORD_PTR dwUserID, LPDIRECTDRAWSURFACE7 lpSurface,
+ DWORD dwSurfaceFlags);
+ virtual HRESULT __stdcall AdviseNotify(IVMRSurfaceAllocatorNotify *lpIVMRSurfAllocNotify);
+
+ // IVMRImagePresenter Methods
+ virtual HRESULT __stdcall StartPresenting(DWORD_PTR dwUserID);
+ virtual HRESULT __stdcall StopPresenting(DWORD_PTR dwUserID);
+ virtual HRESULT __stdcall PresentImage(DWORD_PTR dwUserID, VMRPRESENTATIONINFO *lpPresInfo);
+
+protected:
+
+ CComPtr<IVMRSurfaceAllocator> m_defaultAllocator;
+ HWND m_notifyWindow;
+ int m_presentImageMessage;
+};
+
+#endif // CUSTOMVMR7ALLOCATOR_H
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/DDrawUtil.cpp
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/DDrawUtil.cpp (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/DDrawUtil.cpp 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,129 @@
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+
+#include "StdAfx.h"
+#include "DDrawUtil.h"
+
+#include <ddraw.h>
+
+std::string DDrawUtil::GetSurfaceDescFlags(unsigned long flags )
+{
+ typedef std::map<unsigned long, std::string> SurfaceDescFlagsToStringMap;
+ static SurfaceDescFlagsToStringMap surfaceDescFlagsToStringMap;
+
+#define ADD_FLAG(flag) \
+ surfaceDescFlagsToStringMap[flag] = #flag;
+
+ if (surfaceDescFlagsToStringMap.empty())
+ {
+ ADD_FLAG(DDSD_ALL);
+ ADD_FLAG(DDSD_ALPHABITDEPTH);
+ ADD_FLAG(DDSD_BACKBUFFERCOUNT);
+ ADD_FLAG(DDSD_CAPS);
+ ADD_FLAG(DDSD_CKDESTBLT);
+ ADD_FLAG(DDSD_CKDESTOVERLAY);
+ ADD_FLAG(DDSD_CKSRCBLT);
+ ADD_FLAG(DDSD_CKSRCOVERLAY);
+ ADD_FLAG(DDSD_HEIGHT);
+ ADD_FLAG(DDSD_LINEARSIZE);
+ ADD_FLAG(DDSD_MIPMAPCOUNT);
+ ADD_FLAG(DDSD_PITCH);
+ ADD_FLAG(DDSD_PIXELFORMAT);
+ ADD_FLAG(DDSD_REFRESHRATE);
+ ADD_FLAG(DDSD_WIDTH);
+ ADD_FLAG(DDSD_ZBUFFERBITDEPTH);
+ }
+#undef ADD_FLAG
+
+ std::string result;
+
+ SurfaceDescFlagsToStringMap::const_iterator it = surfaceDescFlagsToStringMap.begin();
+ for (; it != surfaceDescFlagsToStringMap.end(); ++it)
+ {
+ if ((it->first & flags) == it->first)
+ {
+ result += it->second;
+ result += " ";
+ }
+ }
+
+ return result;
+}
+
+std::string DDrawUtil::GetPixelFormatFlags(unsigned long flags )
+{
+ typedef std::map<unsigned long, std::string> PixelFormatFlagsToStringMap;
+ static PixelFormatFlagsToStringMap pixelFormatFlagsToStringMap;
+
+#define ADD_FLAG(flag) \
+ pixelFormatFlagsToStringMap[flag] = #flag;
+
+ if (pixelFormatFlagsToStringMap.empty())
+ {
+ ADD_FLAG(DDPF_ALPHA);
+ ADD_FLAG(DDPF_ALPHAPIXELS);
+ ADD_FLAG(DDPF_ALPHAPREMULT);
+ ADD_FLAG(DDPF_BUMPDUDV);
+// ADD_FLAG(DDPF_BUMPHEIGHT);
+ ADD_FLAG(DDPF_COMPRESSED);
+// ADD_FLAG(DDPF_D3DFORMAT);
+ ADD_FLAG(DDPF_FOURCC);
+ ADD_FLAG(DDPF_LUMINANCE);
+// ADD_FLAG(DDPF_LUMINANCEPIXELS);
+// ADD_FLAG(DDPF_NOVEL_TEXTURE_FORMAT);
+ ADD_FLAG(DDPF_PALETTEINDEXED1);
+ ADD_FLAG(DDPF_PALETTEINDEXED2);
+ ADD_FLAG(DDPF_PALETTEINDEXED4);
+ ADD_FLAG(DDPF_PALETTEINDEXED8);
+ ADD_FLAG(DDPF_PALETTEINDEXEDTO8);
+ ADD_FLAG(DDPF_RGB);
+ ADD_FLAG(DDPF_RGBTOYUV);
+ ADD_FLAG(DDPF_STENCILBUFFER);
+ ADD_FLAG(DDPF_YUV);
+ ADD_FLAG(DDPF_ZBUFFER);
+ ADD_FLAG(DDPF_ZPIXELS);
+ }
+#undef ADD_FLAG
+
+ std::string result;
+
+ PixelFormatFlagsToStringMap::const_iterator it = pixelFormatFlagsToStringMap.begin();
+ for (; it != pixelFormatFlagsToStringMap.end(); ++it)
+ {
+ if ((it->first & flags) == it->first)
+ {
+ result += it->second;
+ result += " ";
+ }
+ }
+
+ return result;
+}
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/DDrawUtil.h
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/DDrawUtil.h (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/DDrawUtil.h 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,44 @@
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+
+#ifndef DDRAWUTIL_H
+#define DDRAWUTIL_H
+
+#pragma once
+
+class DDrawUtil
+{
+public:
+ static std::string GetSurfaceDescFlags(unsigned long flags);
+ static std::string GetPixelFormatFlags(unsigned long flags);
+};
+
+#endif // DDRAWUTIL_H
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/DShowUtil.cpp
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/DShowUtil.cpp (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/DShowUtil.cpp 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,284 @@
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+
+#include "stdafx.h"
+#include <dshow.h>
+#include "DShowUtil.h"
+#include "Guid.h"
+#include <map>
+
+#include <vfwmsgs.h>
+
+RunningObjectTable::RunningObjectTable() :
+m_rotID(0)
+{
+}
+
+
+RunningObjectTable::~RunningObjectTable()
+{
+ Remove();
+}
+
+void RunningObjectTable::Add(const CComPtr<IFilterGraph2>& filterGraph)
+{
+ if (m_rotID)
+ {
+ LOG(logERROR) << "Filter Graph already added to Running Object Table, ID is not null!";
+ return;
+ }
+
+ CComPtr<IMoniker> moniker;
+ CComPtr<IRunningObjectTable> rot;
+
+ CHECK_HR(::GetRunningObjectTable(0, &rot));
+
+ CString monikerName;
+ monikerName.Format(L"FilterGraph %08p pid %08x", (DWORD_PTR)filterGraph.p, ::GetCurrentProcessId());
+
+ CHECK_HR(::CreateItemMoniker(L"!", monikerName, &moniker));
+
+ CHECK_HR(rot->Register(ROTFLAGS_REGISTRATIONKEEPSALIVE, filterGraph, moniker, &m_rotID));
+}
+
+void RunningObjectTable::Remove()
+{
+ CComPtr<IRunningObjectTable> rot;
+
+ CHECK_HR(::GetRunningObjectTable(0, &rot));
+
+ if (m_rotID != 0)
+ {
+ CHECK_HR(rot->Revoke(m_rotID));
+ m_rotID = 0;
+ }
+}
+
+CComPtr<IPin> DShowUtil::FindPin(const CComPtr<IBaseFilter>& filter, PIN_DIRECTION desiredDirection,
+ unsigned int pinNumber /*= 0*/)
+{
+ CComPtr<IEnumPins> enumerator;
+ CHECK_HR(filter->EnumPins(&enumerator));
+
+ CComPtr<IPin> pin;
+
+ unsigned int pinCounter = 0;
+
+ unsigned long fetched = 0;
+ while (enumerator->Next(1, &pin, &fetched) == S_OK)
+ {
+ PIN_DIRECTION direction;
+ CHECK_HR(pin->QueryDirection(&direction));
+
+ if (direction == desiredDirection)
+ {
+ if (pinCounter++ != pinNumber)
+ {
+ pin = 0;
+ continue;
+ }
+
+ return pin;
+ }
+ pin = 0;
+ }
+
+ return 0;
+}
+
+CComPtr<IBaseFilter> DShowUtil::AddFilterFromCLSID(const CComPtr<IFilterGraph2>& graphBuilder,
+ const GUID filterClsid, const wchar_t* filterName)
+{
+ CComPtr<IBaseFilter> filter;
+ HRESULT hr = filter.CoCreateInstance(filterClsid);
+ if (FAILED(hr))
+ {
+ LOG(logERROR) << "Failed to create filter instance: " << filterClsid
+ << ", error: 0x" << std::hex << hr;
+
+ AtlThrow(hr);
+ }
+
+ hr = graphBuilder->AddFilter(filter, filterName);
+ if (FAILED(hr))
+ {
+ LOG(logERROR) << "Failed to add filter " << filterName << " to graph, error: 0x" << std::hex << hr;
+ AtlThrow(hr);
+ }
+
+ return filter;
+}
+
+void DShowUtil::RemoveFilters(const CComPtr<IFilterGraph2>& graphBuilder)
+{
+ CComPtr<IEnumFilters> enumFilters;
+ CHECK_HR(graphBuilder->EnumFilters(&enumFilters));
+
+ CComPtr<IBaseFilter> filter;
+ ULONG fetched = 0;
+ while (enumFilters->Next(1, &filter, &fetched) == S_OK)
+ {
+ CHECK_HR(graphBuilder->RemoveFilter(filter));
+ filter = 0;
+ }
+}
+
+void DShowUtil::SaveGraph(const CComPtr<IFilterGraph2>& graphBuilder, const CString& path)
+{
+ try
+ {
+ const WCHAR wszStreamName[] = L"ActiveMovieGraph";
+
+ CComPtr<IStorage> storage;
+ CHECK_HR(StgCreateDocfile(path,
+ STGM_CREATE | STGM_TRANSACTED | STGM_READWRITE | STGM_SHARE_EXCLUSIVE,
+ 0, &storage));
+
+ CComPtr<IStream> stream;
+ CHECK_HR(storage->CreateStream(wszStreamName,
+ STGM_WRITE | STGM_CREATE | STGM_SHARE_EXCLUSIVE,
+ 0, 0, &stream));
+
+ CComPtr<IPersistStream> persist;
+ CHECK_HR(graphBuilder.QueryInterface(&persist));
+
+ CHECK_HR(persist->Save(stream, TRUE));
+
+ stream = 0;
+ persist = 0;
+
+ CHECK_HR(storage->Commit(STGC_DEFAULT));
+ }
+ catch (const CAtlException& except)
+ {
+ except.m_hr;
+ }
+}
+
+void DShowUtil::LoadGraph(const CComPtr<IFilterGraph2>& m_graphBuilder, const CString& path)
+{
+ try
+ {
+ CComPtr<IStorage> storage;
+ if (StgIsStorageFile(path) != S_OK)
+ {
+ LOG(logERROR) << "\"" << path << "\" is not a valid storage file!";
+ return;
+ }
+
+ CHECK_HR(StgOpenStorage(path, 0, STGM_TRANSACTED | STGM_READ | STGM_SHARE_DENY_WRITE, 0, 0, &storage));
+
+ CComPtr<IPersistStream> persistStream;
+ CHECK_HR(m_graphBuilder.QueryInterface(&persistStream));
+
+ CComPtr<IStream> stream;
+ CHECK_HR(storage->OpenStream(L"ActiveMovieGraph", 0, STGM_READ | STGM_SHARE_EXCLUSIVE, 0, &stream));
+
+ CHECK_HR(persistStream->Load(stream));
+ }
+ catch (const CAtlException& except)
+ {
+ except.m_hr;
+ }
+}
+
+CString DShowUtil::GetEventCodeString(long eventCode)
+{
+ typedef std::map<int, CString> EventCodeToString;
+ static EventCodeToString eventCodesMap;
+
+ if (eventCodesMap.empty())
+ {
+#define ADD_TO_MAP(x) eventCodesMap[x] = #x;
+
+ ADD_TO_MAP(EC_COMPLETE);
+ ADD_TO_MAP(EC_USERABORT);
+ ADD_TO_MAP(EC_ERRORABORT);
+ ADD_TO_MAP(EC_TIME);
+ ADD_TO_MAP(EC_REPAINT);
+ ADD_TO_MAP(EC_STREAM_ERROR_STOPPED);
+ ADD_TO_MAP(EC_STREAM_ERROR_STILLPLAYING);
+ ADD_TO_MAP(EC_ERROR_STILLPLAYING);
+ ADD_TO_MAP(EC_PALETTE_CHANGED);
+ ADD_TO_MAP(EC_VIDEO_SIZE_CHANGED);
+ ADD_TO_MAP(EC_QUALITY_CHANGE);
+ ADD_TO_MAP(EC_SHUTTING_DOWN);
+ ADD_TO_MAP(EC_CLOCK_CHANGED);
+ ADD_TO_MAP(EC_PAUSED);
+ ADD_TO_MAP(EC_OPENING_FILE);
+ ADD_TO_MAP(EC_BUFFERING_DATA);
+ ADD_TO_MAP(EC_FULLSCREEN_LOST);
+ ADD_TO_MAP(EC_ACTIVATE);
+ ADD_TO_MAP(EC_NEED_RESTART);
+ ADD_TO_MAP(EC_WINDOW_DESTROYED);
+ ADD_TO_MAP(EC_DISPLAY_CHANGED);
+ ADD_TO_MAP(EC_STARVATION);
+ ADD_TO_MAP(EC_OLE_EVENT);
+ ADD_TO_MAP(EC_NOTIFY_WINDOW);
+ ADD_TO_MAP(EC_STREAM_CONTROL_STOPPED);
+ ADD_TO_MAP(EC_STREAM_CONTROL_STARTED);
+ ADD_TO_MAP(EC_END_OF_SEGMENT);
+ ADD_TO_MAP(EC_SEGMENT_STARTED);
+ ADD_TO_MAP(EC_LENGTH_CHANGED);
+ ADD_TO_MAP(EC_DEVICE_LOST);
+ ADD_TO_MAP(EC_SAMPLE_NEEDED);
+ ADD_TO_MAP(EC_PROCESSING_LATENCY);
+ ADD_TO_MAP(EC_SAMPLE_LATENCY);
+ ADD_TO_MAP(EC_SCRUB_TIME);
+ ADD_TO_MAP(EC_STEP_COMPLETE);
+ ADD_TO_MAP(EC_TIMECODE_AVAILABLE);
+ ADD_TO_MAP(EC_EXTDEVICE_MODE_CHANGE);
+ ADD_TO_MAP(EC_STATE_CHANGE);
+ ADD_TO_MAP(EC_GRAPH_CHANGED);
+ ADD_TO_MAP(EC_CLOCK_UNSET);
+ ADD_TO_MAP(EC_VMR_RENDERDEVICE_SET);
+ ADD_TO_MAP(EC_VMR_SURFACE_FLIPPED);
+ ADD_TO_MAP(EC_VMR_RECONNECTION_FAILED);
+ ADD_TO_MAP(EC_PREPROCESS_COMPLETE);
+ ADD_TO_MAP(EC_CODECAPI_EVENT);
+
+#undef ADD_TO_MAP
+ }
+
+ EventCodeToString::const_iterator it = eventCodesMap.find(eventCode);
+ CString eventCodeString;
+
+ if (it != eventCodesMap.end())
+ {
+ eventCodeString.Format(L"%s (0x%x)", it->second, it->first);
+ }
+ else
+ {
+ eventCodeString.Format(L"0x%x", eventCode);
+ }
+
+ return eventCodeString;
+}
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/DShowUtil.h
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/DShowUtil.h (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/DShowUtil.h 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,66 @@
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+
+#ifndef DSHOWUTIL_H
+#define DSHOWUTIL_H
+
+class RunningObjectTable
+{
+public:
+ RunningObjectTable();
+ virtual ~RunningObjectTable();
+
+ void Add(const CComPtr<IFilterGraph2>& filterGraph);
+ void Remove();
+
+private:
+ DWORD m_rotID;
+};
+
+class DShowUtil
+{
+public:
+ static CComPtr<IPin> FindPin(const CComPtr<IBaseFilter>& filter,
+ PIN_DIRECTION desiredDirection,
+ unsigned int pinNumber = 0);
+
+ static CComPtr<IBaseFilter> AddFilterFromCLSID(const CComPtr<IFilterGraph2>& graphBuilder,
+ const GUID filterClsid,
+ const wchar_t* filterName);
+
+ static void RemoveFilters(const CComPtr<IFilterGraph2>& graphBuilder);
+
+ static void SaveGraph(const CComPtr<IFilterGraph2>& graphBuilder, const CString& path);
+ static void LoadGraph(const CComPtr<IFilterGraph2>& m_graphBuilder, const CString& path);
+ static CString DShowUtil::GetEventCodeString(long eventCode);
+};
+
+#endif // DSHOWUTIL_H
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/DShowVideoPlayer.cpp
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/DShowVideoPlayer.cpp (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/DShowVideoPlayer.cpp 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,400 @@
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+
+#include "StdAfx.h"
+#include "DShowVideoPlayer.h"
+#include <ddraw.h>
+#include "DDrawUtil.h"
+#include "DShowUtil.h"
+
+DShowVideoPlayer::DShowVideoPlayer() :
+m_isFirstFrame(false),
+m_executeFunctionOnThread(0),
+m_playerCallback(0),
+m_state(NotOpened)
+{
+ m_stopPlaybackEvent = ::CreateEvent(0, FALSE, FALSE, 0);
+ m_executeFunctionEvent = ::CreateEvent(0 , FALSE, FALSE, 0);
+}
+
+DShowVideoPlayer::~DShowVideoPlayer()
+{
+ ::CloseHandle(m_stopPlaybackEvent);
+ ::CloseHandle(m_executeFunctionEvent);
+}
+
+void DShowVideoPlayer::CreateBackBufferSurface(const CSize& videoSize)
+{
+ try
+ {
+ CHECK_HR(DirectDrawCreateEx(0, (void**)&m_directDraw7, IID_IDirectDraw7, 0));
+ CHECK_HR(m_directDraw7->SetCooperativeLevel(m_hWnd, DDSCL_NORMAL + DDSCL_MULTITHREADED));
+
+ // Create back buffer for conversion to RGB.
+ // Buffer will by default be in a format compatible to the primary surface.
+ LPDIRECTDRAWSURFACE7 surface = NULL;
+ DDSURFACEDESC2 descriptor = {0};
+ ZeroMemory(&descriptor, sizeof(DDSURFACEDESC2));
+
+ descriptor.dwSize = sizeof(DDSURFACEDESC2);
+ descriptor.dwFlags = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH;
+ descriptor.dwWidth = videoSize.cx;
+ descriptor.dwHeight = videoSize.cy;
+
+ descriptor.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN | DDSCAPS_SYSTEMMEMORY;
+
+ CHECK_HR(m_directDraw7->CreateSurface(&descriptor, &surface, 0));
+ m_backBuffer = surface;
+ }
+ catch (const CAtlException& /*except*/)
+ {
+ }
+}
+
+
+CComPtr<IDirectDrawSurface7> DShowVideoPlayer::GetScalingSurface(const CSize &aSize)
+{
+ if (m_scalingBuffer && aSize != m_scalingSize)
+ {
+ LOG(logDEBUG3) << __FUNCTIONW__ << " Releasing old scaling surface";
+
+ m_scalingBuffer = 0;
+ }
+
+ if (!m_scalingBuffer)
+ {
+ LOG(logDEBUG3) << __FUNCTIONW__ << " Creating new scaling surface";
+
+ // Create a new back buffer surface
+ DDSURFACEDESC2 descriptor = {0};
+ descriptor.dwSize = sizeof(DDSURFACEDESC2);
+ descriptor.dwFlags = DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH;
+ descriptor.dwWidth = aSize.cx;
+ descriptor.dwHeight = aSize.cy;
+ descriptor.ddsCaps.dwCaps = DDSCAPS_OFFSCREENPLAIN | DDSCAPS_SYSTEMMEMORY;
+
+ CHECK_HR(m_directDraw7->CreateSurface(&descriptor, &m_scalingBuffer, 0));
+
+ m_scalingSize = aSize;
+ }
+
+ return m_scalingBuffer;
+}
+
+HRESULT DShowVideoPlayer::Draw(RECT rcBounds, RECT rcUpdate, LONG lDrawFlags, HDC hdc, LPVOID pvDrawObject)
+{
+// CRect rect(rcBounds.left, rcBounds.top, rcBounds.left + m_width, rcBounds.top + m_height);
+ CRect rect(rcBounds);
+
+ HRESULT hr = S_OK;
+ try
+ {
+ CComPtr<IDirectDrawSurface> destSurface;
+
+ destSurface = reinterpret_cast<IDirectDrawSurface*>(pvDrawObject);
+
+ DDSURFACEDESC descriptor = {};
+ descriptor.dwSize = sizeof(DDSURFACEDESC);
+
+ CHECK_HR(destSurface->GetSurfaceDesc(&descriptor));
+
+ LOG(logDEBUG4) << __FUNCTIONW__ << " DirectDrawSurface: " << destSurface;
+ LOG(logDEBUG4) << "SurfaceDescFlags: " << DDrawUtil::GetSurfaceDescFlags(descriptor.dwFlags).c_str();
+ LOG(logDEBUG4) << "Pixel Format: " << std::endl
+ << "\tSize: " << descriptor.ddpfPixelFormat.dwSize << std::endl
+ << "\tFlags: " << DDrawUtil::GetPixelFormatFlags(descriptor.ddpfPixelFormat.dwFlags).c_str() << std::endl
+ << "\tFourCC: " << descriptor.ddpfPixelFormat.dwFourCC << std::endl
+ << "\tRGBBitCount: " << descriptor.ddpfPixelFormat.dwRGBBitCount << std::endl;
+
+ if (m_backBuffer)
+ {
+ // Use a third buffer to scale the picture
+ CComPtr<IDirectDrawSurface7> scaledSurface = GetScalingSurface(CSize(rect.Width(), rect.Height()));
+ CHECK_HR(scaledSurface->Blt(NULL, m_backBuffer, NULL, DDBLT_WAIT, NULL));
+
+ HDC destDC;
+ CHECK_HR(destSurface->GetDC(&destDC));
+
+ HDC scaledDC;
+ CHECK_HR(scaledSurface->GetDC(&scaledDC));
+
+ // Do not paint when the current displayed line is passing
+ // our rect, when it does and we draw we get tearing.
+ for(; ;)
+ {
+ DWORD scanLine;
+ hr = m_directDraw7->GetScanLine(&scanLine);
+
+ if (hr == DDERR_VERTICALBLANKINPROGRESS)
+ {
+ break;
+ }
+
+ if (FAILED(hr))
+ {
+ break;
+ }
+
+ if (scanLine >= (DWORD)rect.top && scanLine <= (DWORD)rect.bottom)
+ {
+ continue;
+ }
+
+ break;
+ }
+
+ ::BitBlt(destDC, rect.left, rect.top, rect.Width(), rect.Height(), scaledDC, 0, 0, SRCCOPY);
+
+ CHECK_HR(scaledSurface->ReleaseDC(scaledDC));
+ CHECK_HR(destSurface->ReleaseDC(destDC));
+ }
+ }
+ catch (const CAtlException& except)
+ {
+ hr = except.m_hr;
+ }
+
+ return hr;
+}
+
+int DShowVideoPlayer::GetWidth() const
+{
+ return m_width;
+}
+
+void DShowVideoPlayer::SetWidth(int val)
+{
+ m_width = val;
+}
+
+int DShowVideoPlayer::GetHeight() const
+{
+ return m_height;
+}
+
+void DShowVideoPlayer::SetHeight(int val)
+{
+ m_height = val;
+}
+
+CString DShowVideoPlayer::GetSrc() const
+{
+ return m_src;
+}
+
+void DShowVideoPlayer::SetSrc(const CString& val)
+{
+ m_src = val;
+}
+
+HRESULT DShowVideoPlayer::Play()
+{
+ m_executeFunctionOnThread = &DShowVideoPlayer::Thread_Play;
+ ::SetEvent(m_executeFunctionEvent);
+ m_state = Playing;
+
+ return S_OK;
+}
+
+HRESULT DShowVideoPlayer::Pause()
+{
+ m_executeFunctionOnThread = &DShowVideoPlayer::Thread_Pause;
+ ::SetEvent(m_executeFunctionEvent);
+ m_state = Paused;
+
+ return S_OK;
+}
+
+HRESULT DShowVideoPlayer::Stop()
+{
+ m_executeFunctionOnThread = &DShowVideoPlayer::Thread_Stop;
+ ::SetEvent(m_executeFunctionEvent);
+ m_state = Stopped;
+
+ return S_OK;
+}
+
+void DShowVideoPlayer::InitializePlaybackThread()
+{
+ unsigned int threadId;
+ m_playbackThreadHandle = reinterpret_cast<HANDLE>(_beginthreadex(0, 0,
+ PlaybackThreadFunc, this, 0, &threadId));
+}
+
+void DShowVideoPlayer::StopPlaybackThread()
+{
+ ::SetEvent(m_stopPlaybackEvent);
+ AtlWaitWithMessageLoop(m_playbackThreadHandle);
+}
+
+void DShowVideoPlayer::Thread_PrepareGraph()
+{
+ m_filterGraph.SetNotifyWindow(m_hWnd);
+ m_filterGraph.SetPresentImageMessage(WM_PRESENT_IMAGE);
+
+ m_isFirstFrame = true;
+ m_filterGraph.BuildGraph(GetSrc());
+
+ m_filterGraph.Pause();
+ m_state = Paused;
+}
+
+
+unsigned DShowVideoPlayer::PlaybackThreadFunc(void* arg)
+{
+ util::ComInitializer comInit;
+
+ DShowVideoPlayer* self = reinterpret_cast<DShowVideoPlayer*>(arg);
+
+ self->Thread_PrepareGraph();
+
+ HANDLE events[3];
+ events[0] = self->m_stopPlaybackEvent;
+ events[1] = self->m_executeFunctionEvent;
+ events[2] = self->m_filterGraph.GetMovieEventHandle();
+
+ bool exit;
+ do
+ {
+ exit = false;
+ DWORD result = ::WaitForMultipleObjects(sizeof(events) / sizeof HANDLE, events, FALSE, 10);
+
+ if (result == WAIT_OBJECT_0)
+ {
+ exit = true;
+ }
+ else if (result == WAIT_OBJECT_0 + 1)
+ {
+ self->Thread_ExecuteFunction();
+ }
+ else if (result == WAIT_OBJECT_0 + 2)
+ {
+ long eventCode = self->m_filterGraph.GetMovieEventCode();
+ LOG(logINFO) << __FUNCTIONW__ << " FilterGraph event code: " << DShowUtil::GetEventCodeString(eventCode);
+
+ switch(eventCode)
+ {
+ case EC_COMPLETE:
+ self->Thread_Pause();
+ break;
+ case EC_USERABORT:
+ case EC_ERRORABORT:
+ self->Thread_Stop();
+ break;
+ }
+ }
+ } while (!exit);
+
+ return 0;
+}
+
+CSize DShowVideoPlayer::GetSurfaceSize(const CComPtr<IDirectDrawSurface7>& surface)
+{
+ DDSURFACEDESC2 descriptor;
+ ZeroMemory(&descriptor, sizeof(DDSURFACEDESC2));
+ descriptor.dwSize = sizeof(DDSURFACEDESC2);
+
+ surface->GetSurfaceDesc(&descriptor);
+ return CSize(descriptor.dwWidth, descriptor.dwHeight);
+}
+
+LRESULT DShowVideoPlayer::OnPresentImage(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled)
+{
+ VMRPRESENTATIONINFO* frame = reinterpret_cast<VMRPRESENTATIONINFO*>(lParam);
+
+ if (m_isFirstFrame)
+ {
+ CSize videoSize = GetSurfaceSize(frame->lpSurf);
+ CreateBackBufferSurface(videoSize);
+
+ if (m_playerCallback)
+ {
+ m_playerCallback->MovieSize(videoSize);
+ }
+ m_isFirstFrame = false;
+ }
+
+ if (!m_backBuffer)
+ {
+ return 0;
+ }
+
+ HRESULT hr = m_backBuffer->BltFast(0, 0, frame->lpSurf, NULL, DDBLTFAST_DONOTWAIT);
+
+ LOG(logDEBUG2) << __FUNCTIONW__ << " Start: " << ReferenceTime(frame->rtStart)
+ << " End: " << ReferenceTime(frame->rtEnd) << " result: 0x" << std::hex << hr;
+
+ if (m_playerCallback)
+ {
+ m_playerCallback->Refresh();
+ }
+
+ return 0;
+}
+
+void DShowVideoPlayer::Thread_Play()
+{
+ m_filterGraph.Run();
+}
+
+void DShowVideoPlayer::Thread_Pause()
+{
+ m_filterGraph.Pause();
+}
+
+void DShowVideoPlayer::Thread_Stop()
+{
+ m_filterGraph.Stop();
+}
+
+
+void DShowVideoPlayer::Thread_ExecuteFunction()
+{
+ if (m_executeFunctionOnThread)
+ {
+ (this->*m_executeFunctionOnThread)();
+ }
+}
+
+DShowVideoPlayerCallback* DShowVideoPlayer::GetPlayerCallback() const
+{
+ return m_playerCallback;
+}
+
+void DShowVideoPlayer::SetPlayerCallback( DShowVideoPlayerCallback* val )
+{
+ m_playerCallback = val;
+}
+
+DShowVideoPlayer::PlayerState DShowVideoPlayer::GetState() const
+{
+ return m_state;
+}
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/DShowVideoPlayer.h
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/DShowVideoPlayer.h (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/DShowVideoPlayer.h 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,131 @@
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+
+#ifndef DSHOWVIDEOPLAYER_H
+#define DSHOWVIDEOPLAYER_H
+
+#pragma once
+
+#include <atlwin.h>
+#include "FilterGraph.h"
+
+class DShowVideoPlayerCallback
+{
+public:
+ virtual void Refresh() = 0;
+ virtual void MovieSize(const CSize& movieSize) = 0;
+};
+
+class DShowVideoPlayer : public CWindowImpl<DShowVideoPlayer>
+{
+public:
+ DShowVideoPlayer();
+ virtual ~DShowVideoPlayer();
+
+ static const int WM_PRESENT_IMAGE = WM_USER + 200;
+
+ BEGIN_MSG_MAP(DShowVideoPlayer)
+ MESSAGE_HANDLER(WM_PRESENT_IMAGE, OnPresentImage)
+ END_MSG_MAP()
+
+ enum PlayerState
+ {
+ NotOpened,
+ Playing,
+ Paused,
+ Stopped,
+ };
+
+ LRESULT OnPresentImage(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled);
+ HRESULT Draw(RECT rcBounds, RECT rcUpdate, LONG lDrawFlags, HDC hdc, LPVOID pvDrawObject);
+
+ int GetWidth() const;
+ void SetWidth(int val);
+
+ int GetHeight() const;
+ void SetHeight(int val);
+
+ CString GetSrc() const;
+ void SetSrc(const CString& val);
+
+ DShowVideoPlayerCallback* GetPlayerCallback() const;
+ void SetPlayerCallback(DShowVideoPlayerCallback* val);
+
+ void InitializePlaybackThread();
+ void StopPlaybackThread();
+ static unsigned __stdcall PlaybackThreadFunc(void* arg);
+
+ HRESULT Play();
+ HRESULT Pause();
+ HRESULT Stop();
+
+ DShowVideoPlayer::PlayerState GetState() const;
+
+private:
+ void Thread_PrepareGraph();
+
+ void Thread_Play();
+ void Thread_Pause();
+ void Thread_Stop();
+
+ void Thread_ExecuteFunction();
+
+ void CreateBackBufferSurface(const CSize& videoSize);
+ CSize GetSurfaceSize(const CComPtr<IDirectDrawSurface7>& surface);
+ CComPtr<IDirectDrawSurface7> GetScalingSurface(const CSize &aSize);
+
+private:
+ FilterGraph m_filterGraph;
+
+ CComPtr<IDirectDraw7> m_directDraw7;
+ CComPtr<IDirectDrawSurface7> m_backBuffer;
+ CComPtr<IDirectDrawSurface7> m_scalingBuffer;
+ CSize m_scalingSize;
+
+ int m_width;
+ int m_height;
+
+ CString m_src;
+
+ HANDLE m_playbackThreadHandle;
+ HANDLE m_stopPlaybackEvent;
+ HANDLE m_executeFunctionEvent;
+
+ DShowVideoPlayerCallback* m_playerCallback;
+
+ typedef void (DShowVideoPlayer::* ExecuteFunctionOnThread)();
+ ExecuteFunctionOnThread m_executeFunctionOnThread;
+
+ bool m_isFirstFrame;
+ PlayerState m_state;
+};
+
+#endif // DSHOWVIDEOPLAYER_H
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/FilterGraph.cpp
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/FilterGraph.cpp (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/FilterGraph.cpp 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,307 @@
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+
+#include "StdAfx.h"
+#include "FilterGraph.h"
+
+#include <InitGuid.h>
+#include <uuids.h>
+
+#include "DShowUtil.h"
+#include "CustomVMR7Allocator.h"
+
+namespace {
+ const GUID CLSID_OggDemuxPacketSourceFilter =
+ {0xc9361f5a, 0x3282, 0x4944, {0x98, 0x99, 0x6d, 0x99, 0xcd, 0xc5, 0x37, 0xb}};
+
+ const GUID CLSID_VorbisDecodeFilter =
+ {0x5a1d945, 0xa794, 0x44ef, {0xb4, 0x1a, 0x2f, 0x85, 0x1a, 0x11, 0x71, 0x55}};
+
+ const GUID CLSID_TheoraDecodeFilter =
+ {0x5187161, 0x5c36, 0x4324, {0xa7, 0x34, 0x22, 0xbf, 0x37, 0x50, 0x9f, 0x2d}};
+
+ const DWORD ALLOCATOR_ID = 0xDAC10542;
+}
+
+FilterGraph::FilterGraph() :
+m_customVmrAllocator(0),
+m_notifyWindow(0),
+m_presentImageMessage(0)
+{
+}
+
+void FilterGraph::BuildGraph(const CString& videoUrl)
+{
+ m_videoUrl = videoUrl;
+
+ try
+ {
+ CHECK_HR(m_graphBuilder.CoCreateInstance(CLSID_FilterGraph));
+
+ AddSourceFilter();
+ AddDecoders();
+ ConnectDecoders();
+ AddRenderers();
+ ConfigureVideoRenderer();
+ ConnnectRenderers();
+
+ CHECK_HR(m_graphBuilder.QueryInterface(&m_mediaControl));
+ CHECK_HR(m_graphBuilder.QueryInterface(&m_mediaEvent));
+ }
+ catch (const CAtlException& /*except*/)
+ {
+ }
+}
+
+
+FilterGraph::~FilterGraph()
+{
+ if (m_customVmrAllocator)
+ {
+ m_customVmrAllocator->Release();
+ }
+}
+
+void FilterGraph::AddSourceFilter()
+{
+ m_oggSource = DShowUtil::AddFilterFromCLSID(m_graphBuilder, CLSID_OggDemuxPacketSourceFilter,
+ L"Ogg Source Filter");
+
+ CComQIPtr<IFileSourceFilter> fileSource = m_oggSource;
+ CHECK_HR(fileSource->Load(m_videoUrl, 0));
+}
+
+void FilterGraph::AddDecoders()
+{
+ // Connect Vorbis audio decoder
+ m_vorbisDecoder = DShowUtil::AddFilterFromCLSID(m_graphBuilder, CLSID_VorbisDecodeFilter,
+ L"Vorbis Decoder");
+
+ // Connect Theora video decoder
+ m_theoraDecoder = DShowUtil::AddFilterFromCLSID(m_graphBuilder, CLSID_TheoraDecodeFilter,
+ L"Theora Decoder");
+}
+
+void FilterGraph::ConnectDecoders()
+{
+ // Connect vorbis decoder
+ CComPtr<IPin> vorbisDemuxOut = DShowUtil::FindPin(m_oggSource, PINDIR_OUTPUT, 1);
+ CComPtr<IPin> vorbisDecoderIn = DShowUtil::FindPin(m_vorbisDecoder, PINDIR_INPUT, 0);
+
+ CHECK_HR(m_graphBuilder->Connect(vorbisDemuxOut, vorbisDecoderIn));
+
+ // Connect theora decoder
+ CComPtr<IPin> theoraDemuxOut = DShowUtil::FindPin(m_oggSource, PINDIR_OUTPUT, 0);
+ CComPtr<IPin> theoraDecoderIn = DShowUtil::FindPin(m_theoraDecoder, PINDIR_INPUT, 0);
+
+ CHECK_HR(m_graphBuilder->Connect(theoraDemuxOut, theoraDecoderIn));
+}
+
+void FilterGraph::AddRenderers()
+{
+ // Add audio renderer
+ m_audioRenderer = DShowUtil::AddFilterFromCLSID(m_graphBuilder, CLSID_DSoundRender,
+ L"DirectSound Renderer");
+
+ // Add video renderer
+ m_videoRenderer = DShowUtil::AddFilterFromCLSID(m_graphBuilder, CLSID_VideoMixingRenderer,
+ L"Video Renderer");
+}
+
+void FilterGraph::ConnnectRenderers()
+{
+ // Connect audio renderer
+ CComPtr<IPin> vorbisDecoderOut = DShowUtil::FindPin(m_vorbisDecoder, PINDIR_OUTPUT, 0);
+ CComPtr<IPin> audioRendererIn = DShowUtil::FindPin(m_audioRenderer, PINDIR_INPUT, 0);
+
+ CHECK_HR(m_graphBuilder->Connect(vorbisDecoderOut, audioRendererIn));
+
+ // Connect video renderer
+ CComPtr<IPin> theoraDecoderOut = DShowUtil::FindPin(m_theoraDecoder, PINDIR_OUTPUT, 0);
+ CComPtr<IPin> videoRendererIn = DShowUtil::FindPin(m_videoRenderer, PINDIR_INPUT, 0);
+
+ CHECK_HR(m_graphBuilder->Connect(theoraDecoderOut, videoRendererIn));
+}
+
+void FilterGraph::ConfigureVideoRenderer()
+{
+ CComQIPtr<IVMRFilterConfig> config = m_videoRenderer;
+
+ if (!config)
+ {
+ return;
+ }
+
+ CHECK_HR(config->SetRenderingMode(VMRMode_Renderless));
+
+ CHECK_HR(m_videoRenderer.QueryInterface(&m_surfaceNotify));
+
+ // Connect our custom VMR7 allocator
+ CComObject<CustomVMR7Allocator>::CreateInstance(&m_customVmrAllocator);
+ m_customVmrAllocator->AddRef();
+
+ ATLASSERT(GetNotifyWindow() && "SetNotifyWindow should be called first!");
+ ATLASSERT(GetPresentImageMessage() && "SetPresentImageMessage should be called first!");
+ m_customVmrAllocator->SetNotifyWindow(GetNotifyWindow());
+ m_customVmrAllocator->SetPresentImageMessage(GetPresentImageMessage());
+
+ CHECK_HR(m_surfaceNotify->AdviseSurfaceAllocator(ALLOCATOR_ID, m_customVmrAllocator));
+ CHECK_HR(m_customVmrAllocator->CreateDefaultSurfaceAllocator());
+ CHECK_HR(m_customVmrAllocator->AdviseNotify(m_surfaceNotify));
+
+ CHECK_HR(config->SetNumberOfStreams(1));
+
+ CComQIPtr<IVMRMixerControl> mixerControl = m_videoRenderer;
+
+ DWORD mixingPrefs;
+ CHECK_HR(mixerControl->GetMixingPrefs(&mixingPrefs));
+
+ mixingPrefs &= ~MixerPref_RenderTargetMask;
+ mixingPrefs |= MixerPref_RenderTargetRGB;
+
+ CHECK_HR(mixerControl->SetMixingPrefs(mixingPrefs));
+}
+
+void FilterGraph::Run()
+{
+ LOG(logINFO) << __FUNCTIONW__;
+
+ if (!m_mediaControl)
+ {
+ return;
+ }
+
+ try
+ {
+ CHECK_HR(m_mediaControl->Run());
+ }
+ catch (const CAtlException& /*except*/)
+ {
+ }
+}
+
+void FilterGraph::Pause()
+{
+ LOG(logINFO) << __FUNCTIONW__;
+
+ if (!m_mediaControl)
+ {
+ return;
+ }
+
+ try
+ {
+ CHECK_HR(m_mediaControl->Pause());
+ }
+ catch (const CAtlException& /*except*/)
+ {
+ }
+}
+
+void FilterGraph::Stop()
+{
+ LOG(logINFO) << __FUNCTIONW__;
+
+ if (!m_mediaControl)
+ {
+ return;
+ }
+
+ try
+ {
+ CHECK_HR(m_mediaControl->Stop());
+ }
+ catch (const CAtlException& /*except*/)
+ {
+ }
+}
+
+HWND FilterGraph::GetNotifyWindow() const
+{
+ return m_notifyWindow;
+}
+
+void FilterGraph::SetNotifyWindow( HWND val )
+{
+ m_notifyWindow = val;
+}
+
+int FilterGraph::GetPresentImageMessage() const
+{
+ return m_presentImageMessage;
+}
+
+void FilterGraph::SetPresentImageMessage( int val )
+{
+ m_presentImageMessage = val;
+}
+
+HANDLE FilterGraph::GetMovieEventHandle()
+{
+ HANDLE movieEventHandle = INVALID_HANDLE_VALUE;
+
+ if (!m_mediaEvent)
+ {
+ return movieEventHandle;
+ }
+
+ try
+ {
+ CHECK_HR(m_mediaEvent->GetEventHandle((OAEVENT *)&movieEventHandle));
+ }
+ catch (const CAtlException& /*except*/)
+ {
+ }
+
+ return movieEventHandle;
+}
+
+long FilterGraph::GetMovieEventCode()
+{
+ long eventCode = 0;
+
+ if (!m_mediaEvent)
+ {
+ return eventCode;
+ }
+
+ try
+ {
+ LONG_PTR lParam1, lParam2;
+ CHECK_HR(m_mediaEvent->GetEvent(&eventCode, &lParam1, &lParam2, 0));
+ CHECK_HR(m_mediaEvent->FreeEventParams(eventCode, lParam1, lParam2));
+ }
+ catch (const CAtlException& /*except*/)
+ {
+ }
+
+ return eventCode;
+}
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/FilterGraph.h
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/FilterGraph.h (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/FilterGraph.h 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,93 @@
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+
+#ifndef FILTERGRAPH_H
+#define FILTERGRAPH_H
+
+#pragma once
+
+#include <dshow.h>
+#include <strmif.h>
+
+class CustomVMR7Allocator;
+
+class FilterGraph
+{
+public:
+ FilterGraph();
+ virtual ~FilterGraph();
+
+ void BuildGraph(const CString& videoUrl);
+
+ void Run();
+ void Pause();
+ void Stop();
+
+ HWND GetNotifyWindow() const;
+ void SetNotifyWindow(HWND val);
+
+ int GetPresentImageMessage() const;
+ void SetPresentImageMessage(int val);
+
+ HANDLE GetMovieEventHandle();
+ long GetMovieEventCode();
+
+private:
+ void AddSourceFilter();
+ void AddDecoders();
+ void ConnectDecoders();
+ void AddRenderers();
+ void ConfigureVideoRenderer();
+ void ConnnectRenderers();
+
+private:
+ CString m_videoUrl;
+
+ CComPtr<IFilterGraph2> m_graphBuilder;
+
+ CComPtr<IBaseFilter> m_oggSource;
+ CComPtr<IBaseFilter> m_vorbisDecoder;
+ CComPtr<IBaseFilter> m_theoraDecoder;
+
+ CComPtr<IBaseFilter> m_audioRenderer;
+ CComPtr<IBaseFilter> m_videoRenderer;
+
+ CComPtr<IVMRSurfaceAllocatorNotify> m_surfaceNotify;
+ CComObject<CustomVMR7Allocator>* m_customVmrAllocator;
+
+ CComPtr<IMediaControl> m_mediaControl;
+ CComPtr<IMediaEvent> m_mediaEvent;
+
+ HWND m_notifyWindow;
+ int m_presentImageMessage;
+};
+
+#endif // FILTERGRAPH_H
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/Guid.h
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/Guid.h (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/Guid.h 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,173 @@
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+
+#ifndef GUID_H
+#define GUID_H
+
+#include <iomanip>
+#include <sstream>
+#include <stdexcept>
+#include <cassert>
+#include <tchar.h>
+
+class Guid : public GUID
+{
+public:
+ typedef std::basic_string<TCHAR> string;
+ typedef std::basic_istringstream<TCHAR> istringstream;
+ typedef std::basic_ostringstream<TCHAR> ostringstream;
+ typedef std::basic_ostream<TCHAR> ostream;
+
+ Guid()
+ {
+ Data1 = 0;
+ Data2 = 0;
+ Data3 = 0;
+ Data4[0] = 0;
+ Data4[1] = 0;
+ Data4[2] = 0;
+ Data4[3] = 0;
+ Data4[4] = 0;
+ Data4[5] = 0;
+ Data4[6] = 0;
+ Data4[7] = 0;
+ }
+
+ Guid(const Guid& other)
+ {
+ Data1 = other.Data1;
+ Data2 = other.Data2;
+ Data3 = other.Data3;
+ Data4[0] = other.Data4[0];
+ Data4[1] = other.Data4[1];
+ Data4[2] = other.Data4[2];
+ Data4[3] = other.Data4[3];
+ Data4[4] = other.Data4[4];
+ Data4[5] = other.Data4[5];
+ Data4[6] = other.Data4[6];
+ Data4[7] = other.Data4[7];
+ }
+
+ template <class T>
+ T strToNum(const string &inputString, std::ios_base &(*f)(std::ios_base&) = std::dec)
+ {
+ T t;
+ istringstream stringStream(inputString);
+
+ if ((stringStream >> f >> t).fail())
+ {
+ throw std::runtime_error("Invalid conversion");
+ }
+ return t;
+ }
+
+ Guid (const string& stringGuid)
+ {
+ assert(stringGuid[0] == _T('{') &&
+ stringGuid[9] == _T('-') &&
+ stringGuid[14] == _T('-') &&
+ stringGuid[19] == _T('-') &&
+ stringGuid[24] == _T('-') &&
+ stringGuid[37] == _T('}'));
+
+ const string data1Str = stringGuid.substr(1, 8);
+ Data1 = strToNum<unsigned long>(data1Str, std::hex);
+
+ const string data2Str = stringGuid.substr(10, 4);
+ Data2 = strToNum<unsigned short>(data2Str, std::hex);
+
+ const string data3Str = stringGuid.substr(15, 4);
+ Data3 = strToNum<unsigned short>(data3Str, std::hex);
+
+ for (int i = 0; i < 2; ++i)
+ {
+ const string data4Str = stringGuid.substr(20 + i * 2, 2);
+ Data4[i] = static_cast<unsigned char>(strToNum<unsigned int>(data4Str, std::hex));
+ }
+
+ for (int i = 0; i < 6; ++i)
+ {
+ const string data4Str = stringGuid.substr(25 + i * 2, 2);
+ Data4[i + 2] = static_cast<unsigned char>(strToNum<unsigned int>(data4Str, std::hex));
+ }
+ }
+
+ operator string () const
+ {
+ ostringstream os;
+
+ os << _T("{");
+ ostream::char_type oldFill = os.fill(_T('0'));
+
+ os << std::hex << std::setw(8) << Data1 << _T("-");
+ os << std::hex << std::setw(4) << Data2 << _T("-");
+ os << std::hex << std::setw(4) << Data3 << _T("-");
+
+ for (int i = 0; i < 2; ++i)
+ {
+ os << std::hex << std::setw(2) << static_cast<unsigned short>(Data4[i]);
+ }
+
+ os << _T("-");
+
+ for (int i = 0; i < 6; ++i)
+ {
+ os << std::hex << std::setw(2) << static_cast<unsigned short>(Data4[i + 2]);
+ }
+
+ os << _T("}");
+ os.fill(oldFill);
+
+ return os.str();
+ }
+
+ string ToString() const
+ {
+ return operator string();
+ }
+
+ bool operator < (const Guid& other) const
+ {
+ return Data1 < other.Data1 &&
+ Data2 < other.Data2 &&
+ Data3 < other.Data3 &&
+ Data4[0] < other.Data4[0] &&
+ Data4[1] < other.Data4[1] &&
+ Data4[2] < other.Data4[2] &&
+ Data4[3] < other.Data4[3] &&
+ Data4[4] < other.Data4[4] &&
+ Data4[5] < other.Data4[5] &&
+ Data4[6] < other.Data4[6] &&
+ Data4[7] < other.Data4[7];
+ }
+};
+
+#endif // GUID_H
Modified: trunk/oggdsf/src/lib/plugin/AxPlayer/Res/AxPlayer.rc
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/Res/AxPlayer.rc 2010-02-15 02:14:14 UTC (rev 16901)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/Res/AxPlayer.rc 2010-02-16 00:14:26 UTC (rev 16902)
@@ -75,13 +75,13 @@
BEGIN
BLOCK "040904e4"
BEGIN
- VALUE "CompanyName", "TODO: <Company name>"
- VALUE "FileDescription", "TODO: <File description>"
+ VALUE "CompanyName", "Xiph.Org"
+ VALUE "FileDescription", "HTML5 <video> implementation"
VALUE "FileVersion", "1.0.0.1"
- VALUE "LegalCopyright", "TODO: (c) <Company name>. All rights reserved."
VALUE "InternalName", "AxPlayer.dll"
+ VALUE "LegalCopyright", "(c) 2010 Xiph.Org. All rights reserved."
VALUE "OriginalFilename", "AxPlayer.dll"
- VALUE "ProductName", "TODO: <Product name>"
+ VALUE "ProductName", "AxPlayer"
VALUE "ProductVersion", "1.0.0.1"
END
END
Modified: trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.cpp
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.cpp 2010-02-15 02:14:14 UTC (rev 16901)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.cpp 2010-02-16 00:14:26 UTC (rev 16902)
@@ -1,12 +1,46 @@
-// VideoTagBehavior.cpp : Implementation of VideoTagBehavior
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
#include "stdafx.h"
+#include <InitGuid.h>
#include "VideoTagBehavior.h"
#include "common/util.h"
+#include <ddraw.h>
// VideoTagBehavior
namespace {
- const wchar_t* VIDEO_TAG = L"VIDEO";
+ const wchar_t* VIDEO_TAG = L"video";
+ const wchar_t* SRC_ATTRIBUTE = L"src";
+ const wchar_t* WIDTH_ATTRIBUTE = L"width";
+ const wchar_t* HEIGHT_ATTRIBUTE = L"height";
}
VideoTagBehavior::VideoTagBehavior() :
@@ -31,37 +65,55 @@
HRESULT __stdcall VideoTagBehavior::Notify(LONG lEvent, VARIANT* pVar)
{
- LOG(logDEBUG) << __FUNCTIONW__ << " lEvent: " << lEvent << ", pVar: " << ToString((CComVariant)pVar);
+ LOG(logDEBUG) << __FUNCTIONW__ << " lEvent: " << lEvent;
- switch (lEvent)
+ HRESULT hr = S_OK;
+
+ try
{
- case BEHAVIOREVENT_CONTENTREADY:
- // End tag of element has been parsed (we can get at attributes)
- break;
- case BEHAVIOREVENT_DOCUMENTREADY:
- // HTML document has been parsed (we can get at the document object model)
+ switch (lEvent)
{
- HRESULT hr = m_site->GetElement(&m_element);
-
- CComPtr<IHTMLStyle> style;
- m_element->get_style(&style);
+ case BEHAVIOREVENT_CONTENTREADY:
+ // End tag of element has been parsed (we can get at attributes)
+ break;
+ case BEHAVIOREVENT_DOCUMENTREADY:
+ // HTML document has been parsed (we can get at the document object model)
+ {
+ CHECK_HR(m_site->GetElement(&m_element));
+
+ CComPtr<IHTMLStyle> style;
+ CHECK_HR(m_element->get_style(&style));
- style->put_pixelWidth(m_width);
- style->put_pixelHeight(m_height);
+ ParseElementAttributes();
- if (m_paintSite)
- {
- m_paintSite->InvalidateRect(0);
+ CHECK_HR(style->put_pixelWidth(m_width));
+ CHECK_HR(style->put_pixelHeight(m_height));
+
+ m_videoPlayer.SetWidth(m_width);
+ m_videoPlayer.SetHeight(m_height);
+
+ m_videoPlayer.Create(::GetDesktopWindow(), 0, L"PlayerWindow", WS_POPUP);
+ m_videoPlayer.SetPlayerCallback(this);
+ m_videoPlayer.InitializePlaybackThread();
+
+ CHECK_HR(HTMLEvents::DispEventAdvise(m_element));
}
+ break;
}
+ }
+ catch (const CAtlException& except)
+ {
+ hr = except.m_hr;
+ }
- break;
- }
return S_OK;
}
HRESULT __stdcall VideoTagBehavior::Detach()
{
+ m_videoPlayer.StopPlaybackThread();
+ m_videoPlayer.DestroyWindow();
+
return S_OK;
}
@@ -75,20 +127,25 @@
return E_POINTER;
}
- HRESULT hr = E_FAIL;
+ HRESULT hr = S_OK;
- if (wcsicmp(bstrBehavior, VIDEO_TAG) == 0)
+ try
{
- CComObject<VideoTagBehavior>* behavior;
- hr = CComObject<VideoTagBehavior>::CreateInstance(&behavior);
+ CComBSTR behavior(bstrBehavior);
+ behavior.ToLower();
- if (FAILED(hr))
+ if (behavior == VIDEO_TAG)
{
- return hr;
+ CComObject<VideoTagBehavior>* behavior;
+ CHECK_HR(CComObject<VideoTagBehavior>::CreateInstance(&behavior));
+
+ CHECK_HR(behavior->QueryInterface(IID_IElementBehavior, (void**)ppBehavior));
}
-
- hr = behavior->QueryInterface(IID_IElementBehavior, (void**)ppBehavior);
}
+ catch (const CAtlException& except)
+ {
+ hr = except.m_hr;
+ }
return hr;
}
@@ -166,11 +223,14 @@
{
pInfo->lFlags =
HTMLPAINTER_NOSAVEDC |
- HTMLPAINTER_SUPPORTS_XFORM;
+ HTMLPAINTER_SUPPORTS_XFORM |
+ HTMLPAINTER_OVERLAY |
+ HTMLPAINTER_SURFACE |
+ HTMLPAINTER_HITTEST;
pInfo->lZOrder = HTMLPAINT_ZORDER_REPLACE_ALL;
- memset(&pInfo->iidDrawObject, 0, sizeof(IID));
+ pInfo->iidDrawObject = IID_IDirectDrawSurface;
pInfo->rcExpand.left = 0;
pInfo->rcExpand.top = 0;
@@ -182,19 +242,31 @@
HRESULT __stdcall VideoTagBehavior::Draw(RECT rcBounds, RECT rcUpdate, LONG lDrawFlags, HDC hdc, LPVOID pvDrawObject)
{
- CRect rect(rcBounds.left, rcBounds.top,
- rcBounds.left + m_width, rcBounds.top + m_height);
-
- FillRect(hdc, &rect, (HBRUSH)GetStockObject(GRAY_BRUSH));
-
- return S_OK;
+ HRESULT hr = m_videoPlayer.Draw(rcBounds, rcUpdate, lDrawFlags, hdc, pvDrawObject);
+ return hr;
}
HRESULT __stdcall VideoTagBehavior::HitTestPoint(POINT pt, BOOL *pbHit, LONG *plPartID)
{
+ *pbHit = TRUE;
return S_OK;
}
+VARIANT_BOOL __stdcall VideoTagBehavior::OnClick()
+{
+ if (m_videoPlayer.GetState() == DShowVideoPlayer::Paused ||
+ m_videoPlayer.GetState() == DShowVideoPlayer::Stopped)
+ {
+ m_videoPlayer.Play();
+ }
+ else if (m_videoPlayer.GetState() == DShowVideoPlayer::Playing)
+ {
+ m_videoPlayer.Pause();
+ }
+
+ return VARIANT_FALSE;
+}
+
HRESULT __stdcall VideoTagBehavior::OnResize(SIZE pt)
{
LOG(logDEBUG) << __FUNCTIONW__ << ", "
@@ -202,3 +274,76 @@
return S_OK;
}
+
+HRESULT __stdcall VideoTagBehavior::SetInterfaceSafetyOptions(REFIID riid, DWORD dwOptionSetMask, DWORD dwEnabledOptions)
+{
+ m_dwCurrentSafety = m_dwCurrentSafety & ~dwEnabledOptions | dwOptionSetMask;
+ return S_OK;
+}
+
+void VideoTagBehavior::ParseElementAttributes()
+{
+ CComQIPtr<IHTMLDOMNode> node = m_element;
+
+ CComPtr<IDispatch> disp;
+ CHECK_HR(node->get_attributes(&disp));
+
+ CComQIPtr<IHTMLAttributeCollection> attributesList = disp;
+ disp = 0;
+
+ long attributesCount = 0;
+ CHECK_HR(attributesList->get_length(&attributesCount));
+
+ for (long i = 0; i < attributesCount; ++i)
+ {
+ CComVariant item(i);
+ CHECK_HR(attributesList->item(&item, &disp));
+
+ CComQIPtr<IHTMLDOMAttribute> attribute = disp;
+ disp = 0;
+
+ CComBSTR attributeName;
+ CHECK_HR(attribute->get_nodeName(&attributeName));
+
+ attributeName.ToLower();
+
+ if (attributeName == SRC_ATTRIBUTE)
+ {
+ CComVariant attributeValue;
+ CHECK_HR(attribute->get_nodeValue(&attributeValue));
+
+ LOG(logINFO) << SRC_ATTRIBUTE << " = \"" << attributeValue << "\"";
+
+ m_videoPlayer.SetSrc(attributeValue);
+ }
+ }
+}
+
+void VideoTagBehavior::Refresh()
+{
+ if (m_paintSite)
+ {
+ m_paintSite->InvalidateRect(0);
+ }
+}
+
+void VideoTagBehavior::MovieSize(const CSize& movieSize)
+{
+ m_width = movieSize.cx;
+ m_height = movieSize.cy;
+
+ try
+ {
+ CComPtr<IHTMLStyle> style;
+ CHECK_HR(m_element->get_style(&style));
+
+ CHECK_HR(style->put_pixelWidth(m_width));
+ CHECK_HR(style->put_pixelHeight(m_height));
+
+ m_videoPlayer.SetWidth(m_width);
+ m_videoPlayer.SetHeight(m_height);
+ }
+ catch (const CAtlException& /*except*/)
+ {
+ }
+}
Modified: trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.h
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.h 2010-02-15 02:14:14 UTC (rev 16901)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.h 2010-02-16 00:14:26 UTC (rev 16902)
@@ -1,18 +1,52 @@
-// VideoTagBehavior.h : Declaration of the VideoTagBehavior
+//===========================================================================
+// Copyright (C) 2010 Cristian Adam
+//
+//Redistribution and use in source and binary forms, with or without
+//modification, are permitted provided that the following conditions
+//are met:
+//
+//- Redistributions of source code must retain the above copyright
+// notice, this list of conditions and the following disclaimer.
+//
+//- Redistributions in binary form must reproduce the above copyright
+// notice, this list of conditions and the following disclaimer in the
+// documentation and/or other materials provided with the distribution.
+//
+//- Neither the name of Cristian Adam nor the names of contributors
+// may be used to endorse or promote products derived from this software
+// without specific prior written permission.
+//
+//THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+//``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+//LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+//PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE ORGANISATION OR
+//CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+//EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+//PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+//PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+//LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+//NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+//SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+//==============================================================
+#ifndef VIDEOTAGBEHAVIOUR_H
+#define VIDEOTAGBEHAVIOUR_H
+
#pragma once
#include "resource.h" // main symbols
#include "Generated Files\AxPlayer_i.h"
#include "_IVideoTagBehaviorEvents_CP.h"
+#include "DShowVideoPlayer.h"
+#include <MsHtmdid.h>
#if defined(_WIN32_WCE) && !defined(_CE_DCOM) && !defined(_CE_ALLOW_SINGLE_THREADED_OBJECTS_IN_MTA)
#error "Single-threaded COM objects are not properly supported on Windows CE platform, such as the Windows Mobile platforms that do not include full DCOM support. Define _CE_ALLOW_SINGLE_THREADED_OBJECTS_IN_MTA to force ATL to support creating single-thread COM object's and allow use of it's single-threaded COM object implementations. The threading model in your rgs file was set to 'Free' as that is the only threading model supported in non DCOM Windows CE platforms."
#endif
+typedef IDispEventImpl<1, VideoTagBehavior, &DIID_HTMLElementEvents, &LIBID_MSHTML, 4, 0> HTMLEvents;
-
// VideoTagBehavior
class ATL_NO_VTABLE VideoTagBehavior :
@@ -28,7 +62,9 @@
public IElementBehaviorLayout,
public IElementNamespaceFactory,
public IElementNamespaceFactoryCallback,
- public IHTMLPainter
+ public IHTMLPainter,
+ public HTMLEvents,
+ public DShowVideoPlayerCallback
{
public:
VideoTagBehavior();
@@ -55,6 +91,10 @@
CONNECTION_POINT_ENTRY(__uuidof(_IVideoTagBehaviorEvents))
END_CONNECTION_POINT_MAP()
+ BEGIN_SINK_MAP(VideoTagBehavior)
+ SINK_ENTRY_EX(1, DIID_HTMLElementEvents, DISPID_HTMLDOCUMENTEVENTS_ONCLICK, OnClick)
+ END_SINK_MAP()
+
DECLARE_PROTECT_FINAL_CONSTRUCT()
HRESULT FinalConstruct();
@@ -89,7 +129,19 @@
HRESULT __stdcall HitTestPoint(POINT pt, BOOL *pbHit, LONG *plPartID);
HRESULT __stdcall OnResize(SIZE pt);
+ // IObjectSafety override
+ HRESULT __stdcall SetInterfaceSafetyOptions(REFIID riid, DWORD dwOptionSetMask, DWORD dwEnabledOptions);
+
+ // Events
+ VARIANT_BOOL __stdcall OnClick();
+
+ // DShowVideoPlayerCallback
+ virtual void Refresh();
+ virtual void MovieSize(const CSize& movieSize);
+
private:
+ void ParseElementAttributes();
+private:
CComPtr<IElementBehaviorSite> m_site;
CComPtr<IElementBehaviorSiteOM2> m_omSite;
@@ -98,6 +150,12 @@
int m_width;
int m_height;
+
+ CSize m_movieSize;
+
+ DShowVideoPlayer m_videoPlayer;
};
OBJECT_ENTRY_AUTO(__uuidof(VideoTagBehavior), VideoTagBehavior)
+
+#endif // VIDEOTAGBEHAVIOUR_H
Modified: trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.rgs
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.rgs 2010-02-15 02:14:14 UTC (rev 16901)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/VideoTagBehavior.rgs 2010-02-16 00:14:26 UTC (rev 16902)
@@ -1,17 +1,17 @@
HKCR
{
- AxPlayer.VideoTagBehavior.1 = s 'VideoTagBehavior Class'
+ AxPlayer.VideoTagBehavior.1 = s 'HTML5 <video> and <audio> implementation'
{
CLSID = s '{7CC95AE6-C1FA-40CC-AB17-3E91DA2F77CA}'
}
- AxPlayer.VideoTagBehavior = s 'VideoTagBehavior Class'
+ AxPlayer.VideoTagBehavior = s 'HTML5 <video> and <audio> implementation'
{
CLSID = s '{7CC95AE6-C1FA-40CC-AB17-3E91DA2F77CA}'
CurVer = s 'AxPlayer.VideoTagBehavior.1'
}
NoRemove CLSID
{
- ForceRemove {7CC95AE6-C1FA-40CC-AB17-3E91DA2F77CA} = s 'VideoTagBehavior Class'
+ ForceRemove {7CC95AE6-C1FA-40CC-AB17-3E91DA2F77CA} = s 'HTML5 <video> and <audio> implementation'
{
ProgID = s 'AxPlayer.VideoTagBehavior.1'
VersionIndependentProgID = s 'AxPlayer.VideoTagBehavior'
Added: trunk/oggdsf/src/lib/plugin/AxPlayer/_IVideoTagBehaviorEvents_CP.h
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/_IVideoTagBehaviorEvents_CP.h (rev 0)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/_IVideoTagBehaviorEvents_CP.h 2010-02-16 00:14:26 UTC (rev 16902)
@@ -0,0 +1,8 @@
+#pragma once
+
+template <class T>
+class CProxy_IVideoTagBehaviorEvents : public IConnectionPointImpl<T, &__uuidof( _IVideoTagBehaviorEvents ), CComDynamicUnkArray>
+{
+ //Warning this class will be regenerated by the wizard.
+public:
+};
Modified: trunk/oggdsf/src/lib/plugin/AxPlayer/stdafx.h
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/stdafx.h 2010-02-15 02:14:14 UTC (rev 16901)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/stdafx.h 2010-02-16 00:14:26 UTC (rev 16902)
@@ -27,3 +27,4 @@
#include <msxml.h>
#include "common/Log.h"
+#include "common/util.h"
\ No newline at end of file
Modified: trunk/oggdsf/src/lib/plugin/AxPlayer/test.html
===================================================================
--- trunk/oggdsf/src/lib/plugin/AxPlayer/test.html 2010-02-15 02:14:14 UTC (rev 16901)
+++ trunk/oggdsf/src/lib/plugin/AxPlayer/test.html 2010-02-16 00:14:26 UTC (rev 16902)
@@ -1,14 +1,25 @@
-<html>
-<body>
-
-<p>This is a header </p>
-
-<video src="http://videos.mozilla.org/firefox/3.5/meet/meet.ogv"
- xmlns="http://www.w3.org/1999/xhtml">
- <p>your browser cannot handle video tag.</p>
-</video>
-
-<p>This is a footer </p>
-
-</body>
-</html>
+<html>
+<head><title>Big Buck Bunny</title></head>
+<style type="text/css">
+body { font-family:sans-serif }
+</style>
+
+<body>
+
+<h1>Big Buck Bunny</h1>
+
+
+<video src="http://127.0.0.1/BigBuckBunny.ogv" width="640" height="360" controls="true"
+ xmlns="http://www.w3.org/1999/xhtml/video"
+>
+<p>Your browser cannot handle video tag.</p>
+</video>
+
+
+<br/><br/>
+(c) copyright Blender Foundation | <a href="http://www.bigbuckbunny.org"><b>www.bigbuckbunny.org</b></a><br/>
+<a href="http://creativecommons.org/licenses/by/3.0/">Creative Commons Attribution 3.0</a>
+
+
+</body>
+</html>
More information about the commits
mailing list