]> git.sesse.net Git - casparcg/commitdiff
2.0.0.2:
authorronag <ronag@362d55ac-95cf-4e76-9f9a-cbaa9c17b72d>
Mon, 8 Nov 2010 16:47:06 +0000 (16:47 +0000)
committerronag <ronag@362d55ac-95cf-4e76-9f9a-cbaa9c17b72d>
Mon, 8 Nov 2010 16:47:06 +0000 (16:47 +0000)
- Mayor restructuring.

git-svn-id: https://casparcg.svn.sourceforge.net/svnroot/casparcg/server/branches/2.0.0.2@240 362d55ac-95cf-4e76-9f9a-cbaa9c17b72d

82 files changed:
common/concurrency/executor.h
common/gl/pixel_buffer_object.cpp
common/gl/pixel_buffer_object.h
common/gl/utility.h
core/channel.cpp [new file with mode: 0644]
core/channel.h [new file with mode: 0644]
core/consumer/bluefish/bluefish_consumer.cpp
core/consumer/bluefish/bluefish_consumer.h
core/consumer/bluefish/memory.h
core/consumer/bluefish/util.h
core/consumer/decklink/DecklinkVideoConsumer.cpp
core/consumer/decklink/DecklinkVideoConsumer.h
core/consumer/frame_consumer.h
core/consumer/frame_consumer_device.cpp [new file with mode: 0644]
core/consumer/frame_consumer_device.h [new file with mode: 0644]
core/consumer/oal/oal_consumer.cpp
core/consumer/oal/oal_consumer.h
core/consumer/ogl/ogl_consumer.cpp
core/consumer/ogl/ogl_consumer.h
core/core.vcxproj
core/core.vcxproj.filters
core/processor/composite_frame.cpp [new file with mode: 0644]
core/processor/composite_frame.h [new file with mode: 0644]
core/processor/frame.cpp [new file with mode: 0644]
core/processor/frame.h [new file with mode: 0644]
core/processor/frame_processor_device.cpp [new file with mode: 0644]
core/processor/frame_processor_device.h [new file with mode: 0644]
core/processor/frame_renderer.cpp [new file with mode: 0644]
core/processor/frame_renderer.h [new file with mode: 0644]
core/processor/frame_shader.cpp [new file with mode: 0644]
core/processor/frame_shader.h [new file with mode: 0644]
core/producer/color/color_producer.cpp
core/producer/color/color_producer.h
core/producer/ffmpeg/ffmpeg_producer.cpp
core/producer/ffmpeg/ffmpeg_producer.h
core/producer/ffmpeg/input.cpp
core/producer/ffmpeg/input.h
core/producer/ffmpeg/packet.h
core/producer/ffmpeg/video/video_transformer.cpp
core/producer/ffmpeg/video/video_transformer.h
core/producer/flash/FlashAxContainer.cpp
core/producer/flash/FlashAxContainer.h
core/producer/flash/cg_producer.cpp
core/producer/flash/cg_producer.h
core/producer/flash/ct_producer.cpp
core/producer/flash/ct_producer.h
core/producer/flash/flash_producer.cpp
core/producer/flash/flash_producer.h
core/producer/frame_producer.h
core/producer/frame_producer_device.cpp [new file with mode: 0644]
core/producer/frame_producer_device.h [new file with mode: 0644]
core/producer/image/image_loader.cpp
core/producer/image/image_producer.cpp
core/producer/image/image_producer.h
core/producer/image/image_scroll_producer.cpp
core/producer/image/image_scroll_producer.h
core/producer/layer.cpp [new file with mode: 0644]
core/producer/layer.h [new file with mode: 0644]
core/producer/transition/transition_producer.cpp
core/producer/transition/transition_producer.h
core/protocol/amcp/AMCPCommand.h
core/protocol/amcp/AMCPCommandsImpl.cpp
core/protocol/amcp/AMCPCommandsImpl.h
core/protocol/amcp/AMCPProtocolStrategy.cpp
core/protocol/amcp/AMCPProtocolStrategy.h
core/protocol/cii/CIIProtocolStrategy.cpp
core/protocol/cii/CIIProtocolStrategy.h
core/protocol/clk/CLKProtocolStrategy.cpp
core/protocol/clk/CLKProtocolStrategy.h
core/protocol/media.cpp
core/protocol/media.h
core/server.cpp
core/server.h
core/video/pixel_format.h [new file with mode: 0644]
core/video/video_format.cpp [new file with mode: 0644]
core/video/video_format.h [new file with mode: 0644]
shell/caspar.config
shell/main.cpp
test/mock/mock_frame.h
test/mock/mock_frame_factory.h
test/mock/mock_frame_producer.h
test/producer/transition/transition_producer_test.cpp

index 9bf016d24c5e7f7b05281b4ca66f72936982b3ef..9f1c46c15041cf429a3f6cca498c4000aed8bc8e 100644 (file)
@@ -96,6 +96,11 @@ public:
        {\r
                return begin_invoke(std::forward<Func>(func)).get();\r
        }\r
+\r
+       void set_capacity(size_t capacity)\r
+       {\r
+               execution_queue_.set_capacity(capacity);\r
+       }\r
        \r
 private:\r
 \r
index c82670f63236cd85c4e258650ef8bbe86824e2d0..f0cdc85e6f3aae6b7201de9b3d63e5a210110cd5 100644 (file)
@@ -72,8 +72,7 @@ struct pixel_buffer_object::implementation : boost::noncopyable
                        GL(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE));\r
                        GL(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE));\r
 \r
-                       GL(glTexImage2D(GL_TEXTURE_2D, 0, internal_, width_, height_, 0, format_, \r
-                                                               GL_UNSIGNED_BYTE, NULL));\r
+                       GL(glTexImage2D(GL_TEXTURE_2D, 0, internal_, width_, height_, 0, format_, GL_UNSIGNED_BYTE, NULL));\r
                }\r
                GL(glBindTexture(GL_TEXTURE_2D, texture_));\r
        }\r
@@ -85,8 +84,7 @@ struct pixel_buffer_object::implementation : boost::noncopyable
                        GL(glUnmapBuffer(GL_PIXEL_UNPACK_BUFFER));\r
                mapped_ = false;\r
                bind_texture();\r
-               GL(glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, width_, height_, format_, \r
-                                                       GL_UNSIGNED_BYTE, NULL));\r
+               GL(glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, width_, height_, format_, GL_UNSIGNED_BYTE, NULL));\r
                unbind_pbo(GL_PIXEL_UNPACK_BUFFER);\r
                writing_ = true;\r
        }\r
@@ -98,11 +96,10 @@ struct pixel_buffer_object::implementation : boost::noncopyable
 \r
                bind_pbo(GL_PIXEL_UNPACK_BUFFER);\r
                GL(glBufferData(GL_PIXEL_UNPACK_BUFFER, size_, NULL, GL_STREAM_DRAW));\r
-               auto data = static_cast<unsigned char*>(glMapBuffer(GL_PIXEL_UNPACK_BUFFER, GL_WRITE_ONLY));\r
+               auto data = glMapBuffer(GL_PIXEL_UNPACK_BUFFER, GL_WRITE_ONLY);\r
                unbind_pbo(GL_PIXEL_UNPACK_BUFFER);             \r
                if(!data)\r
-                       BOOST_THROW_EXCEPTION(invalid_operation() \r
-                                                                       << msg_info("glMapBuffer failed"));\r
+                       BOOST_THROW_EXCEPTION(invalid_operation() << msg_info("glMapBuffer failed"));\r
                writing_ = false;\r
                mapped_ = true;\r
                return data;\r
@@ -126,7 +123,7 @@ struct pixel_buffer_object::implementation : boost::noncopyable
                        BOOST_THROW_EXCEPTION(invalid_operation());\r
 \r
                bind_pbo(GL_PIXEL_PACK_BUFFER);\r
-               auto data = static_cast<unsigned char*>(glMapBuffer(GL_PIXEL_PACK_BUFFER, GL_READ_ONLY));   \r
+               auto data = glMapBuffer(GL_PIXEL_PACK_BUFFER, GL_READ_ONLY);   \r
                unbind_pbo(GL_PIXEL_PACK_BUFFER);\r
                if(!data)\r
                        BOOST_THROW_EXCEPTION(std::bad_alloc());\r
@@ -135,6 +132,19 @@ struct pixel_buffer_object::implementation : boost::noncopyable
                return data;\r
        }\r
 \r
+       void is_smooth(bool smooth)\r
+       {\r
+               if(smooth)\r
+               {\r
+                       GL(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR));\r
+                       GL(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR));\r
+               }\r
+               else\r
+               {\r
+                       GL(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST));\r
+                       GL(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST));\r
+               }\r
+       }\r
        \r
        GLuint pbo_;\r
        GLuint texture_;\r
@@ -167,4 +177,5 @@ size_t pixel_buffer_object::height() const {return impl_->height_;}
 size_t pixel_buffer_object::size() const {return impl_->size_;}\r
 bool pixel_buffer_object::is_reading() const { return impl_->reading_;}\r
 bool pixel_buffer_object::is_writing() const { return impl_->writing_;}\r
+void pixel_buffer_object::is_smooth(bool smooth){impl_->is_smooth(smooth);}\r
 }}}
\ No newline at end of file
index 65b0a6a36dba5fca8cf87e5a556e5e801afe08a5..2ea40cf79d70c7144807d9bcbbb29f1cdc94a774 100644 (file)
@@ -25,6 +25,8 @@ public:
        void begin_read();\r
        void* end_read();\r
 \r
+       void is_smooth(bool smooth);\r
+\r
        void bind_texture();\r
 \r
        size_t width() const;\r
index 00d78c0f6ac8a128828f8fe734984e27cbb51c1d..c80ce3013abfeb1bf18214f2e0a9ca9a549a34e2 100644 (file)
 #include <boost/lexical_cast.hpp>\r
 \r
 namespace caspar { namespace common { namespace gl {\r
+\r
+struct gl_error : virtual caspar_exception{};\r
                \r
 inline void SMFL_GLCheckError(const std::string& expr, const std::string& File, unsigned int Line)\r
 {\r
-    // Get the last error\r
-    GLenum ErrorCode = glGetError();\r
-\r
-    if (ErrorCode != GL_NO_ERROR)\r
-    {\r
-        std::string Error = "unknown error";\r
-        std::string Desc  = "no description";\r
-\r
-        // Decode the error code\r
-        switch (ErrorCode)\r
-        {\r
-            case GL_INVALID_ENUM :\r
-            {\r
-                Error = "GL_INVALID_ENUM";\r
-                Desc  = "an unacceptable value has been specified for an enumerated argument";\r
-                break;\r
-            }\r
-\r
-            case GL_INVALID_VALUE :\r
-            {\r
-                Error = "GL_INVALID_VALUE";\r
-                Desc  = "a numeric argument is out of range";\r
-                break;\r
-            }\r
-\r
-            case GL_INVALID_OPERATION :\r
-            {\r
-                Error = "GL_INVALID_OPERATION";\r
-                Desc  = "the specified operation is not allowed in the current state";\r
-                break;\r
-            }\r
-\r
-            case GL_STACK_OVERFLOW :\r
-            {\r
-                Error = "GL_STACK_OVERFLOW";\r
-                Desc  = "this command would cause a stack overflow";\r
-                break;\r
-            }\r
-\r
-            case GL_STACK_UNDERFLOW :\r
-            {\r
-                Error = "GL_STACK_UNDERFLOW";\r
-                Desc  = "this command would cause a stack underflow";\r
-                break;\r
-            }\r
-\r
-            case GL_OUT_OF_MEMORY :\r
-            {\r
-                Error = "GL_OUT_OF_MEMORY";\r
-                Desc  = "there is not enough memory left to execute the command";\r
-                break;\r
-            }\r
-\r
-            case GL_INVALID_FRAMEBUFFER_OPERATION_EXT :\r
-            {\r
-                Error = "GL_INVALID_FRAMEBUFFER_OPERATION_EXT";\r
-                Desc  = "the object bound to FRAMEBUFFER_BINDING_EXT is not \"framebuffer complete\"";\r
-                break;\r
-            }\r
-        }\r
-\r
-        // Log the error\r
-        CASPAR_LOG(error) << "An internal OpenGL call failed in "\r
-                  << File.substr(File.find_last_of("\\/") + 1).c_str() << " (" << Line << ") : "\r
-                  << Error.c_str() << ", " << Desc.c_str()\r
+       // Get the last error\r
+       GLenum ErrorCode = glGetError();\r
+\r
+       if (ErrorCode != GL_NO_ERROR)\r
+       {\r
+               std::string Error = "unknown error";\r
+               std::string Desc  = "no description";\r
+\r
+               // Decode the error code\r
+               switch (ErrorCode)\r
+               {\r
+                       case GL_INVALID_ENUM :\r
+                       {\r
+                               Error = "GL_INVALID_ENUM";\r
+                               Desc  = "an unacceptable value has been specified for an enumerated argument";\r
+                               break;\r
+                       }\r
+\r
+                       case GL_INVALID_VALUE :\r
+                       {\r
+                               Error = "GL_INVALID_VALUE";\r
+                               Desc  = "a numeric argument is out of range";\r
+                               break;\r
+                       }\r
+\r
+                       case GL_INVALID_OPERATION :\r
+                       {\r
+                               Error = "GL_INVALID_OPERATION";\r
+                               Desc  = "the specified operation is not allowed in the current state";\r
+                               break;\r
+                       }\r
+\r
+                       case GL_STACK_OVERFLOW :\r
+                       {\r
+                               Error = "GL_STACK_OVERFLOW";\r
+                               Desc  = "this command would cause a stack overflow";\r
+                               break;\r
+                       }\r
+\r
+                       case GL_STACK_UNDERFLOW :\r
+                       {\r
+                               Error = "GL_STACK_UNDERFLOW";\r
+                               Desc  = "this command would cause a stack underflow";\r
+                               break;\r
+                       }\r
+\r
+                       case GL_OUT_OF_MEMORY :\r
+                       {\r
+                               Error = "GL_OUT_OF_MEMORY";\r
+                               Desc  = "there is not enough memory left to execute the command";\r
+                               break;\r
+                       }\r
+\r
+                       case GL_INVALID_FRAMEBUFFER_OPERATION_EXT :\r
+                       {\r
+                               Error = "GL_INVALID_FRAMEBUFFER_OPERATION_EXT";\r
+                               Desc  = "the object bound to FRAMEBUFFER_BINDING_EXT is not \"framebuffer complete\"";\r
+                               break;\r
+                       }\r
+               }\r
+\r
+               // Log the error\r
+               CASPAR_LOG(error) << "An internal OpenGL call failed in "\r
+                                 << File.substr(File.find_last_of("\\/") + 1).c_str() << " (" << Line << ") : "\r
+                                 << Error.c_str() << ", " << Desc.c_str()\r
                                  << ", " << expr.c_str()\r
-                  << std::endl;\r
-    }\r
+                                 << std::endl;\r
+       }\r
 }\r
 \r
 #ifdef _DEBUG\r
diff --git a/core/channel.cpp b/core/channel.cpp
new file mode 100644 (file)
index 0000000..bdbe421
--- /dev/null
@@ -0,0 +1,82 @@
+#include "StdAfx.h"\r
+\r
+#include "channel.h"\r
+\r
+#include <boost/noncopyable.hpp>\r
+\r
+#include <memory>\r
+\r
+namespace caspar { namespace core {\r
+\r
+struct channel::implementation : boost::noncopyable\r
+{\r
+public:\r
+       implementation(const frame_producer_device_ptr& producer_device, const frame_processor_device_ptr& processor_device, const frame_consumer_device_ptr& consumer_device)\r
+               : producer_device_(producer_device), processor_device_(processor_device), consumer_device_(consumer_device)\r
+       {\r
+       }\r
+       \r
+       void load(int render_layer, const frame_producer_ptr& producer, load_option::type option = load_option::none)\r
+       {\r
+               producer_device_->load(render_layer, producer, option);\r
+       }\r
+\r
+       void pause(int render_layer)\r
+       {\r
+               producer_device_->pause(render_layer);\r
+       }\r
+\r
+       void play(int render_layer)\r
+       {\r
+               producer_device_->play(render_layer);\r
+       }\r
+\r
+       void stop(int render_layer)\r
+       {\r
+               producer_device_->stop(render_layer);\r
+       }\r
+\r
+       void clear(int render_layer)\r
+       {\r
+               producer_device_->clear(render_layer);\r
+       }\r
+\r
+       void clear()\r
+       {\r
+               producer_device_->clear();\r
+       }\r
+       \r
+       frame_producer_ptr active(int render_layer) const\r
+       {\r
+               return producer_device_->active(render_layer);\r
+       }\r
+\r
+       frame_producer_ptr background(int render_layer) const\r
+       {\r
+               return producer_device_->background(render_layer);\r
+       }\r
+\r
+       const video_format_desc get_video_format_desc() const\r
+       {\r
+               return processor_device_->get_video_format_desc();\r
+       }\r
+\r
+private:\r
+       const frame_producer_device_ptr producer_device_;\r
+       const frame_processor_device_ptr processor_device_;\r
+       const frame_consumer_device_ptr consumer_device_;\r
+};\r
+\r
+channel::channel(const frame_producer_device_ptr& producer_device, const frame_processor_device_ptr& processor_device, const frame_consumer_device_ptr& consumer_device)\r
+       : impl_(new implementation(producer_device, processor_device, consumer_device)){}\r
+void channel::load(int render_layer, const frame_producer_ptr& producer, load_option::type option){impl_->load(render_layer, producer, option);}\r
+void channel::pause(int render_layer){impl_->pause(render_layer);}\r
+void channel::play(int render_layer){impl_->play(render_layer);}\r
+void channel::stop(int render_layer){impl_->stop(render_layer);}\r
+void channel::clear(int render_layer){impl_->clear(render_layer);}\r
+void channel::clear(){impl_->clear();}\r
+frame_producer_ptr channel::active(int render_layer) const{    return impl_->active(render_layer);}\r
+frame_producer_ptr channel::background(int render_layer) const{return impl_->background(render_layer);}\r
+const video_format_desc channel::get_video_format_desc() const{        return impl_->get_video_format_desc();}\r
+\r
+}}
\ No newline at end of file
diff --git a/core/channel.h b/core/channel.h
new file mode 100644 (file)
index 0000000..2e89bc6
--- /dev/null
@@ -0,0 +1,43 @@
+#pragma once\r
+\r
+#include "producer/frame_producer_device.h"\r
+#include "consumer/frame_consumer_device.h"\r
+#include "processor/frame_processor_device.h"\r
+\r
+#include <boost/noncopyable.hpp>\r
+\r
+#include <memory>\r
+\r
+namespace caspar { namespace core {\r
+\r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+/// \class     channel\r
+///\r
+/// \brief     Channel. \r
+///            \r
+///                |**********| <-   empty frame   <- |***********| <-   frame format  <- |**********|\r
+/// CONTROLLER ->  | PRODUCER |                       | PROCESSOR |                       | CONSUMER |  -> DISPLAY DEVICE\r
+///                |**********| -> rendered frames -> |***********| -> processed frame -> |**********|\r
+///   \r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+class channel : boost::noncopyable\r
+{\r
+public:\r
+       channel(const frame_producer_device_ptr& producer_device, const frame_processor_device_ptr& processor_device, const frame_consumer_device_ptr& consumer_device);\r
+       \r
+       void load(int render_layer, const frame_producer_ptr& producer, load_option::type option = load_option::none);\r
+       void pause(int render_layer);\r
+       void play(int render_layer);\r
+       void stop(int render_layer);\r
+       void clear(int render_layer);\r
+       void clear();   \r
+       frame_producer_ptr active(int render_layer) const;\r
+       frame_producer_ptr background(int render_layer) const;\r
+       const video_format_desc get_video_format_desc() const;\r
+private:\r
+       struct implementation;\r
+       std::shared_ptr<implementation> impl_;\r
+};\r
+typedef std::shared_ptr<channel> channel_ptr;\r
+\r
+}}
\ No newline at end of file
index 7185c4fde85e0929ea7769e41836b920267cac06..52e917d70747bffe8f8fc5f1b7dea46f365d497f 100644 (file)
@@ -28,7 +28,7 @@
 #include "exception.h"\r
 #include "memory.h"\r
 \r
-#include "../../frame/gpu_frame.h"\r
+#include "../../processor/frame.h"\r
 \r
 #include <boost/thread.hpp>\r
 \r
@@ -41,7 +41,7 @@ namespace caspar { namespace core { namespace bluefish {
        \r
 struct consumer::implementation\r
 {\r
-       implementation::implementation(const frame_format_desc& format_desc, unsigned int device_index, bool embed_audio) \r
+       implementation::implementation(const video_format_desc& format_desc, unsigned int device_index, bool embed_audio) \r
                : device_index_(device_index), format_desc_(format_desc), sdk_(BlueVelvetFactory4()), current_id_(0), embed_audio_(embed_audio)\r
        {\r
                mem_fmt_                = MEM_FMT_ARGB_PC;\r
@@ -66,7 +66,7 @@ struct consumer::implementation
                //blue_detach_from_device(&pBlueDevice);\r
                \r
                vid_fmt_ = VID_FMT_INVALID;\r
-               auto desiredVideoFormat = vid_fmt_from_frame_format(format_desc_.format);\r
+               auto desiredVideoFormat = vid_fmt_from_video_format(format_desc_.format);\r
                int videoModeCount = sdk_->count_video_mode();\r
                for(int videoModeIndex=1; videoModeIndex <= videoModeCount; ++videoModeIndex) \r
                {\r
@@ -172,7 +172,7 @@ struct consumer::implementation
                        CASPAR_LOG(error) << "BLUECARD ERROR: Failed to disable video output. (device " << device_index_ << TEXT(")");          \r
        }\r
 \r
-       void display(const gpu_frame_ptr& frame)\r
+       void display(const frame_ptr& frame)\r
        {\r
                if(frame == nullptr)\r
                        return;\r
@@ -183,7 +183,7 @@ struct consumer::implementation
                frame_buffer_.push(frame);\r
        }\r
 \r
-       void do_display(const gpu_frame_ptr& frame)\r
+       void do_display(const frame_ptr& frame)\r
        {\r
                auto hanc = hanc_buffers_[current_id_];         \r
                current_id_ = (current_id_+1) % hanc_buffers_.size();           \r
@@ -264,7 +264,7 @@ struct consumer::implementation
                {\r
                        try\r
                        {\r
-                               gpu_frame_ptr frame;\r
+                               frame_ptr frame;\r
                                frame_buffer_.pop(frame);\r
                                if(frame == nullptr)\r
                                        return;\r
@@ -281,11 +281,11 @@ struct consumer::implementation
        BlueVelvetPtr sdk_;\r
        \r
        unsigned int device_index_;\r
-       frame_format_desc format_desc_;\r
+       video_format_desc format_desc_;\r
        \r
        std::exception_ptr exception_;\r
        boost::thread thread_;\r
-       tbb::concurrent_bounded_queue<gpu_frame_ptr> frame_buffer_;\r
+       tbb::concurrent_bounded_queue<frame_ptr> frame_buffer_;\r
        \r
        unsigned long   mem_fmt_;\r
        unsigned long   upd_fmt_;\r
@@ -293,16 +293,15 @@ struct consumer::implementation
        unsigned long   res_fmt_; \r
        unsigned long   engine_mode_;\r
 \r
-       gpu_frame_ptr transferring_frame_;\r
+       frame_ptr transferring_frame_;\r
 \r
        std::vector<page_locked_buffer_ptr> hanc_buffers_;\r
        int current_id_;\r
        bool embed_audio_;\r
 };\r
 \r
-consumer::consumer(const frame_format_desc& format_desc, unsigned int device_index, bool embed_audio) : impl_(new implementation(format_desc, device_index, embed_audio)){}    \r
-void consumer::display(const gpu_frame_ptr& frame){impl_->display(frame);}\r
-const frame_format_desc& consumer::get_frame_format_desc() const { return impl_->format_desc_;}\r
+consumer::consumer(const video_format_desc& format_desc, unsigned int device_index, bool embed_audio) : impl_(new implementation(format_desc, device_index, embed_audio)){}    \r
+void consumer::display(const frame_ptr& frame){impl_->display(frame);}\r
 \r
 }}}\r
 \r
index 53e247eddcbef8f2dfab442281448569b23caf2c..9c7d8242bba4c2aea8249f9c6150c898cdb72390 100644 (file)
@@ -19,7 +19,7 @@
 */\r
 #pragma once\r
 \r
-#include "../../frame/frame_fwd.h"\r
+#include "../../video/video_format.h"\r
 #include "../../consumer/frame_consumer.h"\r
 \r
 namespace caspar { namespace core { namespace bluefish {\r
@@ -27,11 +27,10 @@ namespace caspar { namespace core { namespace bluefish {
 class consumer : public frame_consumer\r
 {\r
 public:\r
-       consumer(const frame_format_desc& format_desc, unsigned int deviceIndex, bool embed_audio = false);\r
+       consumer(const video_format_desc& format_desc, unsigned int deviceIndex, bool embed_audio = false);\r
        \r
-       void display(const gpu_frame_ptr&);\r
+       void display(const frame_ptr&);\r
                \r
-       const frame_format_desc& get_frame_format_desc() const;\r
        virtual bool has_sync_clock() const {return false;}\r
 private:\r
        struct implementation;\r
index c79e2e9ceeb9970b17839d6a7b274de1ae1f3981..18856d046c7f5b7c4823e71446e86020004ece67 100644 (file)
@@ -3,7 +3,7 @@
 #include <Windows.h>\r
 \r
 #include <BlueVelvet4.h>\r
-#include "../../frame/frame_format.h"\r
+#include "../../video/video_format.h"\r
 #include "exception.h"\r
 \r
 namespace caspar { namespace core { namespace bluefish {\r
index 490be7ccc9e637c6e1a7baafa2491c3ca51f2caa..6c8eddbf626b0a2b154f47156619884436b16a94 100644 (file)
@@ -1,7 +1,7 @@
 #pragma once\r
 \r
 #include <BlueVelvet4.h>\r
-#include "../../frame/frame_format.h"\r
+#include "../../video/video_format.h"\r
 \r
 #include <memory>\r
 \r
@@ -17,24 +17,24 @@ inline bool is_epoch_card(int card_type)
                        card_type == CRD_BLUE_EPOCH_ULTRA;\r
 }\r
 \r
-inline EVideoMode vid_fmt_from_frame_format(const frame_format& fmt) \r
+inline EVideoMode vid_fmt_from_video_format(const video_format::type& fmt) \r
 {\r
        switch(fmt)\r
        {\r
-       case frame_format::pal:                 return VID_FMT_PAL;\r
-       case frame_format::ntsc:                return VID_FMT_NTSC;\r
-       case frame_format::x576p2500:   return VID_FMT_INVALID; //not supported\r
-       case frame_format::x720p5000:   return VID_FMT_720P_5000;\r
-       case frame_format::x720p5994:   return VID_FMT_720P_5994;\r
-       case frame_format::x720p6000:   return VID_FMT_720P_6000;\r
-       case frame_format::x1080p2397:  return VID_FMT_1080P_2397;\r
-       case frame_format::x1080p2400:  return VID_FMT_1080P_2400;\r
-       case frame_format::x1080i5000:  return VID_FMT_1080I_5000;\r
-       case frame_format::x1080i5994:  return VID_FMT_1080I_5994;\r
-       case frame_format::x1080i6000:  return VID_FMT_1080I_6000;\r
-       case frame_format::x1080p2500:  return VID_FMT_1080P_2500;\r
-       case frame_format::x1080p2997:  return VID_FMT_1080P_2997;\r
-       case frame_format::x1080p3000:  return VID_FMT_1080P_3000;\r
+       case video_format::pal:                 return VID_FMT_PAL;\r
+       case video_format::ntsc:                return VID_FMT_NTSC;\r
+       case video_format::x576p2500:   return VID_FMT_INVALID; //not supported\r
+       case video_format::x720p5000:   return VID_FMT_720P_5000;\r
+       case video_format::x720p5994:   return VID_FMT_720P_5994;\r
+       case video_format::x720p6000:   return VID_FMT_720P_6000;\r
+       case video_format::x1080p2397:  return VID_FMT_1080P_2397;\r
+       case video_format::x1080p2400:  return VID_FMT_1080P_2400;\r
+       case video_format::x1080i5000:  return VID_FMT_1080I_5000;\r
+       case video_format::x1080i5994:  return VID_FMT_1080I_5994;\r
+       case video_format::x1080i6000:  return VID_FMT_1080I_6000;\r
+       case video_format::x1080p2500:  return VID_FMT_1080P_2500;\r
+       case video_format::x1080p2997:  return VID_FMT_1080P_2997;\r
+       case video_format::x1080p3000:  return VID_FMT_1080P_3000;\r
        default:                                                return VID_FMT_INVALID;\r
        }\r
 }\r
index 24c64f4f15e28ba3f09a903093a023c84defbf94..01589fda9d368d1501fc4e922267d2b8704a007f 100644 (file)
 #include "DecklinkVideoConsumer.h"\r
 #include "DeckLinkAPI_h.h"\r
 \r
-#include "../../frame/frame_format.h"\r
+#include "../../video/video_format.h"\r
 #include "../../../common/utility/memory.h"\r
 \r
-#include "../../renderer/render_device.h"\r
+#include "../../producer/frame_producer_device.h"\r
 \r
 #include <tbb/concurrent_queue.h>\r
 #include <boost/thread.hpp>\r
@@ -56,7 +56,7 @@ struct DecklinkVideoConsumer::Implementation : public IDeckLinkVideoOutputCallba
                explicit DecklinkVideoFrame(DecklinkFrameManager* pFactory)\r
                {\r
                        IDeckLinkMutableVideoFrame* frame = NULL;\r
-                       const frame_format_desc& format_desc = pFactory->pConsumerImpl_->get_frame_format_desc();\r
+                       const video_format_desc& format_desc = pFactory->pConsumerImpl_->get_video_format_desc();\r
                        if(pFactory->pConsumerImpl_->pDecklinkOutput_->CreateVideoFrame(format_desc.width, format_desc.height, format_desc.size/format_desc.height, bmdFormat8BitBGRA, bmdFrameFlagDefault, &frame) != S_OK) \r
                        {\r
                                throw std::exception("DECKLINK: Failed to create frame");\r
@@ -122,7 +122,7 @@ struct DecklinkVideoConsumer::Implementation : public IDeckLinkVideoOutputCallba
                        return pResult;\r
                }\r
 \r
-               void DisplayFrame(const gpu_frame_ptr& frame)\r
+               void DisplayFrame(const frame_ptr& frame)\r
                {\r
                        if(frame != NULL) \r
                        {\r
@@ -177,8 +177,8 @@ struct DecklinkVideoConsumer::Implementation : public IDeckLinkVideoOutputCallba
                        return std::make_shared<DecklinkVideoFrame>(this);\r
                }\r
 \r
-               const frame_format_desc& get_frame_format_desc() const {\r
-                       return pConsumerImpl_->get_frame_format_desc();\r
+               const video_format_desc& get_video_format_desc() const {\r
+                       return pConsumerImpl_->get_video_format_desc();\r
                }\r
 \r
                Implementation* pConsumerImpl_;\r
@@ -193,17 +193,17 @@ struct DecklinkVideoConsumer::Implementation : public IDeckLinkVideoOutputCallba
 \r
        std::shared_ptr<DecklinkPlaybackStrategy> pPlayback_;\r
        DecklinkFrameManagerPtr pFrameManager_;\r
-       frame_format currentFormat_;\r
-       frame_format_desc format_desc_;\r
+       video_format::type currentFormat_;\r
+       video_format_desc format_desc_;\r
 \r
        std::exception_ptr pException_;\r
        boost::thread thread_;\r
-       tbb::concurrent_bounded_queue<gpu_frame_ptr> frameBuffer_;\r
+       tbb::concurrent_bounded_queue<frame_ptr> frameBuffer_;\r
 \r
 //     IDeckLinkMutableVideoFrame* pNextFrame_;\r
 \r
-       explicit Implementation(const frame_format_desc& format_desc, bool internalKey) \r
-               : format_desc_(format_desc), currentFormat_(frame_format::pal), internalKey_(internalKey)\r
+       explicit Implementation(const video_format_desc& format_desc, bool internalKey) \r
+               : format_desc_(format_desc), currentFormat_(video_format::pal), internalKey_(internalKey)\r
        {\r
        \r
                CComPtr<IDeckLinkIterator> pDecklinkIterator;\r
@@ -242,7 +242,7 @@ struct DecklinkVideoConsumer::Implementation : public IDeckLinkVideoOutputCallba
                ReleaseDevice();\r
        }\r
        \r
-       void DisplayFrame(const gpu_frame_ptr& frame)\r
+       void DisplayFrame(const frame_ptr& frame)\r
        {\r
                if(frame == nullptr)\r
                        return;         \r
@@ -259,7 +259,7 @@ struct DecklinkVideoConsumer::Implementation : public IDeckLinkVideoOutputCallba
                {\r
                        try\r
                        {       \r
-                               gpu_frame_ptr frame;\r
+                               frame_ptr frame;\r
                                frameBuffer_.pop(frame);\r
                                if(frame == nullptr)\r
                                        return;\r
@@ -406,43 +406,43 @@ struct DecklinkVideoConsumer::Implementation : public IDeckLinkVideoOutputCallba
                return S_OK;\r
        }\r
 \r
-       const frame_format_desc& get_frame_format_desc() const \r
+       const video_format_desc& get_video_format_desc() const \r
        {\r
-               return frame_format_desc::format_descs[currentFormat_];\r
+               return video_format_desc::format_descs[currentFormat_];\r
        }\r
 \r
-       unsigned long GetDecklinkVideoFormat(frame_format fmt) \r
+       unsigned long GetDecklinkVideoFormat(video_format::type fmt) \r
        {\r
                switch(fmt)\r
                {\r
-               case frame_format::pal:                 return bmdModePAL;\r
-               case frame_format::ntsc:                return bmdModeNTSC;\r
-               case frame_format::x576p2500:   return ULONG_MAX;       //not supported\r
-               case frame_format::x720p5000:   return bmdModeHD720p50;\r
-               case frame_format::x720p5994:   return bmdModeHD720p5994;\r
-               case frame_format::x720p6000:   return bmdModeHD720p60;\r
-               case frame_format::x1080p2397:  return bmdModeHD1080p2398;\r
-               case frame_format::x1080p2400:  return bmdModeHD1080p24;\r
-               case frame_format::x1080i5000:  return bmdModeHD1080i50;\r
-               case frame_format::x1080i5994:  return bmdModeHD1080i5994;\r
-               case frame_format::x1080i6000:  return bmdModeHD1080i6000;\r
-               case frame_format::x1080p2500:  return bmdModeHD1080p25;\r
-               case frame_format::x1080p2997:  return bmdModeHD1080p2997;\r
-               case frame_format::x1080p3000:  return bmdModeHD1080p30;\r
+               case video_format::pal:                 return bmdModePAL;\r
+               case video_format::ntsc:                return bmdModeNTSC;\r
+               case video_format::x576p2500:   return ULONG_MAX;       //not supported\r
+               case video_format::x720p5000:   return bmdModeHD720p50;\r
+               case video_format::x720p5994:   return bmdModeHD720p5994;\r
+               case video_format::x720p6000:   return bmdModeHD720p60;\r
+               case video_format::x1080p2397:  return bmdModeHD1080p2398;\r
+               case video_format::x1080p2400:  return bmdModeHD1080p24;\r
+               case video_format::x1080i5000:  return bmdModeHD1080i50;\r
+               case video_format::x1080i5994:  return bmdModeHD1080i5994;\r
+               case video_format::x1080i6000:  return bmdModeHD1080i6000;\r
+               case video_format::x1080p2500:  return bmdModeHD1080p25;\r
+               case video_format::x1080p2997:  return bmdModeHD1080p2997;\r
+               case video_format::x1080p3000:  return bmdModeHD1080p30;\r
                default:                                                return ULONG_MAX;\r
                }\r
        }\r
 };\r
 \r
-DecklinkVideoConsumer::DecklinkVideoConsumer(const frame_format_desc& format_desc, bool internalKey) : pImpl_(new Implementation(format_desc, internalKey))\r
+DecklinkVideoConsumer::DecklinkVideoConsumer(const video_format_desc& format_desc, bool internalKey) : pImpl_(new Implementation(format_desc, internalKey))\r
 {}\r
 \r
-void DecklinkVideoConsumer::display(const gpu_frame_ptr& frame)\r
+void DecklinkVideoConsumer::display(const frame_ptr& frame)\r
 {\r
        pImpl_->DisplayFrame(frame);\r
 }\r
 \r
-const frame_format_desc& DecklinkVideoConsumer::get_frame_format_desc() const\r
+const video_format_desc& DecklinkVideoConsumer::get_video_format_desc() const\r
 {\r
        return pImpl_->format_desc_;\r
 }\r
index 099f296b9ad0fed2b84e850e6545ca71162997ce..b0da679dffbb13045ebb81cc56045efc43714801 100644 (file)
 \r
 #include "../../consumer/frame_consumer.h"\r
 \r
-#include "../../frame/frame_fwd.h"\r
+#include "../../video/video_format.h"\r
 \r
 namespace caspar { namespace core { namespace decklink {\r
 \r
 class DecklinkVideoConsumer : public frame_consumer\r
 {\r
 public:\r
-       explicit DecklinkVideoConsumer(const frame_format_desc& format_desc, bool internalKey = false);\r
+       explicit DecklinkVideoConsumer(const video_format_desc& format_desc, bool internalKey = false);\r
        \r
-       void display(const gpu_frame_ptr&);\r
-       const frame_format_desc& get_frame_format_desc() const;\r
+       void display(const frame_ptr&);\r
+       const video_format_desc& get_video_format_desc() const;\r
 private:\r
        struct Implementation;\r
        std::tr1::shared_ptr<Implementation> pImpl_;\r
index e65cbf04c84b815fb17814999f07f9995c7ffe47..632a895b42c8745288f5c5a2f458621ad649fabd 100644 (file)
@@ -19,7 +19,8 @@
 */\r
 #pragma once\r
 \r
-#include "../frame/frame_fwd.h"\r
+#include "../video/video_format.h"\r
+#include "../processor/frame.h"\r
 \r
 #include <boost/noncopyable.hpp>\r
 \r
@@ -31,9 +32,8 @@ struct frame_consumer : boost::noncopyable
 {\r
        virtual ~frame_consumer() {}\r
 \r
-       virtual const frame_format_desc& get_frame_format_desc() const = 0;\r
-       virtual void prepare(const gpu_frame_ptr&){}\r
-       virtual void display(const gpu_frame_ptr&){}\r
+       virtual void prepare(const frame_ptr&){}\r
+       virtual void display(const frame_ptr&){}\r
        virtual bool has_sync_clock() const {return false;}\r
 };\r
 typedef std::shared_ptr<frame_consumer> frame_consumer_ptr;\r
diff --git a/core/consumer/frame_consumer_device.cpp b/core/consumer/frame_consumer_device.cpp
new file mode 100644 (file)
index 0000000..d556e99
--- /dev/null
@@ -0,0 +1,147 @@
+#include "../StdAfx.h"\r
+\r
+#ifdef _MSC_VER\r
+#pragma warning (disable : 4244)\r
+#endif\r
+\r
+#include "frame_consumer_device.h"\r
+\r
+#include "../video/video_format.h"\r
+#include "../processor/frame.h"\r
+#include "../processor/frame_processor_device.h"\r
+\r
+#include <tbb/concurrent_queue.h>\r
+#include <tbb/atomic.h>\r
+\r
+#include <boost/foreach.hpp>\r
+#include <boost/thread.hpp>\r
+\r
+#include <boost/date_time/posix_time/posix_time.hpp>\r
+\r
+#include <boost/range/algorithm_ext/erase.hpp>\r
+\r
+namespace caspar { namespace core {\r
+\r
+class video_sync_clock\r
+{\r
+public:\r
+       video_sync_clock(const video_format_desc& format_desc)\r
+       {\r
+               period_ = static_cast<long>(render_video_format_period(format_desc)*1000000.0);\r
+               time_ = boost::posix_time::microsec_clock::local_time();\r
+       }\r
+\r
+       void synchronize()\r
+       {\r
+               auto remaining = boost::posix_time::microseconds(period_) -     (boost::posix_time::microsec_clock::local_time() - time_);\r
+               if(remaining > boost::posix_time::microseconds(5000))\r
+                       boost::this_thread::sleep(remaining - boost::posix_time::microseconds(5000));\r
+               time_ = boost::posix_time::microsec_clock::local_time();\r
+       }\r
+private:\r
+       boost::posix_time::ptime time_;\r
+       long period_;\r
+};\r
+\r
+struct frame_consumer_device::implementation\r
+{\r
+public:\r
+       implementation(const frame_processor_device_ptr& frame_processor, const video_format_desc& format_desc, const std::vector<frame_consumer_ptr>& consumers) \r
+               : frame_processor_(frame_processor), consumers_(consumers), fmt_(format_desc)\r
+       {\r
+               if(consumers.empty())\r
+                       BOOST_THROW_EXCEPTION(invalid_argument() << arg_name_info("consumer") \r
+                               << msg_info("frame_consumer_device requires atleast one consumer."));\r
+\r
+               //if(std::any_of(consumers.begin(), consumers.end(), \r
+               //      [&](const frame_consumer_ptr& pConsumer)\r
+               //      { return pConsumer->get_video_format_desc() != format_desc;}))\r
+               //{\r
+               //      BOOST_THROW_EXCEPTION(invalid_argument() << arg_name_info("consumer") \r
+               //              << msg_info("All consumers must have same frameformat as frame_consumer_device."));\r
+               //}\r
+\r
+               needs_clock_ = !std::any_of(consumers.begin(), consumers.end(), std::mem_fn(&frame_consumer::has_sync_clock));\r
+               frame_buffer_.set_capacity(3);\r
+               is_running_ = true;\r
+               display_thread_ = boost::thread([=]{run();});\r
+       }\r
+\r
+       ~implementation()\r
+       {\r
+               is_running_ = false;\r
+               display_thread_.join();\r
+       }\r
+                               \r
+       void run()\r
+       {\r
+               CASPAR_LOG(info) << L"Started frame_consumer_device thread.";\r
+               win32_exception::install_handler();\r
+                               \r
+               video_sync_clock clock(fmt_);\r
+                               \r
+               while(is_running_)\r
+               {\r
+                       if(needs_clock_)\r
+                               clock.synchronize();\r
+                       \r
+                       frame_ptr frame;\r
+                       if(!frame_processor_->try_receive(frame))\r
+                       {\r
+                               CASPAR_LOG(trace) << "Display Buffer Underrun.";\r
+                               frame_processor_->receive(frame);\r
+                       }\r
+                       if(frame != nullptr)                    \r
+                               display_frame(frame);                   \r
+               }\r
+               \r
+               CASPAR_LOG(info) << L"Ended frame_consumer_device thread.";\r
+       }\r
+\r
+       void display_frame(const frame_ptr& frame)\r
+       {\r
+               BOOST_FOREACH(const frame_consumer_ptr& consumer, consumers_)\r
+               {\r
+                       try\r
+                       {\r
+                               consumer->prepare(frame);\r
+                               prepared_frames_.push_back(frame);\r
+\r
+                               if(prepared_frames_.size() > 2)\r
+                               {\r
+                                       consumer->display(prepared_frames_.front());\r
+                                       prepared_frames_.pop_front();\r
+                               }\r
+                       }\r
+                       catch(...)\r
+                       {\r
+                               CASPAR_LOG_CURRENT_EXCEPTION();\r
+                               boost::range::remove_erase(consumers_, consumer);\r
+                               CASPAR_LOG(warning) << "Removed consumer from frame_consumer_device.";\r
+                               if(consumers_.empty())\r
+                               {\r
+                                       CASPAR_LOG(warning) << "No consumers available. Shutting down frame_consumer_device.";\r
+                                       is_running_ = false;\r
+                               }\r
+                       }\r
+               }\r
+       }\r
+\r
+       std::deque<frame_ptr> prepared_frames_;\r
+               \r
+       boost::thread display_thread_;\r
+\r
+       tbb::atomic<bool> is_running_;\r
+       tbb::concurrent_bounded_queue<frame_ptr> frame_buffer_;\r
+\r
+       bool needs_clock_;\r
+       std::vector<frame_consumer_ptr> consumers_;\r
+\r
+       video_format_desc fmt_;\r
+\r
+       frame_processor_device_ptr frame_processor_;\r
+};\r
+\r
+frame_consumer_device::frame_consumer_device(const frame_processor_device_ptr& frame_processor, const video_format_desc& format_desc, const std::vector<frame_consumer_ptr>& consumers)\r
+       : impl_(new implementation(frame_processor, format_desc, consumers)){}\r
+}}
\ No newline at end of file
diff --git a/core/consumer/frame_consumer_device.h b/core/consumer/frame_consumer_device.h
new file mode 100644 (file)
index 0000000..06182fa
--- /dev/null
@@ -0,0 +1,22 @@
+#pragma once\r
+\r
+#include "../consumer/frame_consumer.h"\r
+\r
+#include <vector>\r
+\r
+namespace caspar { namespace core {\r
+\r
+class frame_processor_device;\r
+typedef std::shared_ptr<frame_processor_device> frame_processor_device_ptr;\r
+\r
+class frame_consumer_device\r
+{\r
+public:\r
+       frame_consumer_device(const frame_processor_device_ptr& frame_processor, const video_format_desc& format_desc, const std::vector<frame_consumer_ptr>& consumers);\r
+private:\r
+       struct implementation;\r
+       std::shared_ptr<implementation> impl_;\r
+};\r
+typedef std::shared_ptr<frame_consumer_device> frame_consumer_device_ptr;\r
+\r
+}}
\ No newline at end of file
index 5d88f6bc817b9114eb9578faf84bb671e260e53b..6fd9ccb61da0e1c7bd5393b87ac330bcda0f311f 100644 (file)
@@ -22,8 +22,8 @@
 \r
 #include "oal_consumer.h"\r
 \r
-#include "../../frame/gpu_frame.h"\r
-#include "../../frame/frame_format.h"\r
+#include "../../processor/frame.h"\r
+#include "../../video/video_format.h"\r
 \r
 #include <SFML/Audio.hpp>\r
 \r
@@ -33,7 +33,7 @@ namespace caspar { namespace core { namespace oal {
 \r
 struct consumer::implementation : public sf::SoundStream, boost::noncopyable\r
 {\r
-       implementation(const frame_format_desc& format_desc) : format_desc_(format_desc), container_(5)\r
+       implementation() : container_(5)\r
        {\r
                input_.set_capacity(2);\r
                sf::SoundStream::Initialize(2, 48000);\r
@@ -45,7 +45,7 @@ struct consumer::implementation : public sf::SoundStream, boost::noncopyable
                Stop();\r
        }\r
        \r
-       void push(const gpu_frame_ptr& frame)\r
+       void push(const frame_ptr& frame)\r
        {\r
                // NOTE: tbb::concurrent_queue does not have rvalue support. \r
                // Use shared_ptr to emulate move semantics\r
@@ -88,10 +88,8 @@ struct consumer::implementation : public sf::SoundStream, boost::noncopyable
 \r
        boost::circular_buffer<std::vector<short>> container_;\r
        tbb::concurrent_bounded_queue<std::shared_ptr<std::vector<short>>> input_;\r
-       frame_format_desc format_desc_;\r
 };\r
 \r
-consumer::consumer(const frame_format_desc& format_desc) : impl_(new implementation(format_desc)){}\r
-const frame_format_desc& consumer::get_frame_format_desc() const{return impl_->format_desc_;}\r
-void consumer::prepare(const gpu_frame_ptr& frame){impl_->push(frame);}\r
+consumer::consumer(const video_format_desc&) : impl_(new implementation()){}\r
+void consumer::prepare(const frame_ptr& frame){impl_->push(frame);}\r
 }}}\r
index bc1f2865e1953ac51fef3e06704c8c1c757a2f57..fcad25fbe314314dab4a408ad30f6b42d1cfc49b 100644 (file)
@@ -26,10 +26,9 @@ namespace caspar { namespace core { namespace oal {
 class consumer : public frame_consumer\r
 {\r
 public:        \r
-       explicit consumer(const frame_format_desc& format_desc);\r
+       explicit consumer(const video_format_desc& format_desc);\r
        \r
-       const frame_format_desc& get_frame_format_desc() const; \r
-       void prepare(const gpu_frame_ptr& frame);\r
+       void prepare(const frame_ptr& frame);\r
        virtual bool has_sync_clock() const {return true;}\r
 private:\r
        struct implementation;\r
index 7316c6708973c05916868826680d452c69fc525c..f58373caa3941489cebed0f2aef9af93fb241044 100644 (file)
@@ -22,8 +22,8 @@
 \r
 #include "ogl_consumer.h"\r
 \r
-#include "../../frame/frame_format.h"\r
-#include "../../frame/gpu_frame.h"\r
+#include "../../video/video_format.h"\r
+#include "../../processor/frame.h"\r
 #include "../../../common/utility/memory.h"\r
 #include "../../../common/gl/utility.h"\r
 #include "../../../common/gl/pixel_buffer_object.h"\r
@@ -39,7 +39,7 @@ namespace caspar { namespace core { namespace ogl{
 \r
 struct consumer::implementation : boost::noncopyable\r
 {      \r
-       implementation(const frame_format_desc& format_desc, unsigned int screen_index, stretch stretch, bool windowed) \r
+       implementation(const video_format_desc& format_desc, unsigned int screen_index, stretch stretch, bool windowed) \r
                : index_(0), format_desc_(format_desc), stretch_(stretch), screen_width_(0), screen_height_(0), windowed_(windowed)\r
        {               \r
 #ifdef _WIN32\r
@@ -155,7 +155,7 @@ struct consumer::implementation : boost::noncopyable
                return std::make_pair(width, height);\r
        }\r
 \r
-       void render(const gpu_frame_ptr& frame)\r
+       void render(const frame_ptr& frame)\r
        {               \r
                index_ = (index_ + 1) % 2;\r
                int next_index = (index_ + 1) % 2;\r
@@ -175,7 +175,7 @@ struct consumer::implementation : boost::noncopyable
                pbos_[next_index].begin_write();\r
        }\r
                        \r
-       void display(const gpu_frame_ptr& frame)\r
+       void display(const frame_ptr& frame)\r
        {\r
                if(frame == nullptr)\r
                        return;         \r
@@ -190,7 +190,7 @@ struct consumer::implementation : boost::noncopyable
        {                       \r
                init();\r
                                \r
-               gpu_frame_ptr frame;\r
+               frame_ptr frame;\r
                do\r
                {\r
                        try\r
@@ -229,17 +229,16 @@ struct consumer::implementation : boost::noncopyable
        unsigned int screenY_;\r
                                \r
        stretch stretch_;\r
-       frame_format_desc format_desc_;\r
+       video_format_desc format_desc_;\r
 \r
        std::exception_ptr exception_;\r
        boost::thread thread_;\r
-       tbb::concurrent_bounded_queue<gpu_frame_ptr> frame_buffer_;\r
+       tbb::concurrent_bounded_queue<frame_ptr> frame_buffer_;\r
 \r
        sf::Window window_;\r
 };\r
 \r
-consumer::consumer(const frame_format_desc& format_desc, unsigned int screen_index, stretch stretch, bool windowed)\r
+consumer::consumer(const video_format_desc& format_desc, unsigned int screen_index, stretch stretch, bool windowed)\r
 : impl_(new implementation(format_desc, screen_index, stretch, windowed)){}\r
-const frame_format_desc& consumer::get_frame_format_desc() const{return impl_->format_desc_;}\r
-void consumer::display(const gpu_frame_ptr& frame){impl_->display(frame);}\r
+void consumer::display(const frame_ptr& frame){impl_->display(frame);}\r
 }}}\r
index 1c68350cc29f220b355e34e2f47621219d47ccc6..0e30fc54d2ccc1dcdc24532d5fa4326dad55c3ac 100644 (file)
@@ -36,10 +36,9 @@ enum stretch
 class consumer : public frame_consumer\r
 {\r
 public:        \r
-       explicit consumer(const frame_format_desc& format_desc, unsigned int screen_index = 0, stretch stretch = stretch::fill, bool windowed = false);\r
+       explicit consumer(const video_format_desc& format_desc, unsigned int screen_index = 0, stretch stretch = stretch::fill, bool windowed = false);\r
        \r
-       const frame_format_desc& get_frame_format_desc() const; \r
-       void display(const gpu_frame_ptr& frame);\r
+       void display(const frame_ptr& frame);\r
 private:\r
        struct implementation;\r
        std::shared_ptr<implementation> impl_;\r
index 7c4e8f5902894dd6cb5e1523d65b4a0fd16717df..5ed60d3db9b1ca93752f37f42d89e8a34acf6a5f 100644 (file)
     </PostBuildEvent>\r
   </ItemDefinitionGroup>\r
   <ItemGroup>\r
+    <ClInclude Include="channel.h" />\r
     <ClInclude Include="config.h" />\r
     <ClInclude Include="consumer\bluefish\exception.h" />\r
     <ClInclude Include="consumer\bluefish\fwd.h" />\r
     <ClInclude Include="consumer\bluefish\memory.h" />\r
     <ClInclude Include="consumer\bluefish\bluefish_consumer.h" />\r
     <ClInclude Include="consumer\bluefish\util.h" />\r
+    <ClInclude Include="consumer\frame_consumer_device.h" />\r
     <ClInclude Include="consumer\decklink\DeckLinkAPI_h.h" />\r
     <ClInclude Include="consumer\decklink\DecklinkVideoConsumer.h" />\r
     <ClInclude Include="consumer\frame_consumer.h" />\r
     <ClInclude Include="consumer\oal\oal_consumer.h" />\r
     <ClInclude Include="consumer\ogl\ogl_consumer.h" />\r
-    <ClInclude Include="frame\gpu_composite_frame.h" />\r
-    <ClInclude Include="frame\frame_factory.h" />\r
-    <ClInclude Include="frame\frame_format.h" />\r
-    <ClInclude Include="frame\frame_fwd.h" />\r
-    <ClInclude Include="frame\gpu_frame.h" />\r
-    <ClInclude Include="frame\gpu_frame_device.h" />\r
-    <ClInclude Include="frame\gpu_frame_renderer.h" />\r
-    <ClInclude Include="frame\gpu_frame_shader.h" />\r
-    <ClInclude Include="frame\gpu_frame_desc.h" />\r
+    <ClInclude Include="processor\composite_frame.h" />\r
+    <ClInclude Include="processor\frame.h" />\r
+    <ClInclude Include="processor\frame_processor_device.h" />\r
+    <ClInclude Include="processor\frame_renderer.h" />\r
+    <ClInclude Include="processor\frame_shader.h" />\r
     <ClInclude Include="producer\color\color_producer.h" />\r
     <ClInclude Include="producer\ffmpeg\audio\audio_decoder.h" />\r
     <ClInclude Include="producer\ffmpeg\ffmpeg_producer.h" />\r
     <ClInclude Include="producer\image\image_loader.h" />\r
     <ClInclude Include="producer\image\image_producer.h" />\r
     <ClInclude Include="producer\image\image_scroll_producer.h" />\r
+    <ClInclude Include="producer\layer.h" />\r
+    <ClInclude Include="producer\frame_producer_device.h" />\r
     <ClInclude Include="producer\transition\transition_producer.h" />\r
     <ClInclude Include="protocol\amcp\AMCPCommand.h" />\r
     <ClInclude Include="protocol\amcp\AMCPCommandQueue.h" />\r
     <ClInclude Include="protocol\clk\CLKCommand.h" />\r
     <ClInclude Include="protocol\clk\CLKProtocolStrategy.h" />\r
     <ClInclude Include="protocol\media.h" />\r
-    <ClInclude Include="renderer\display_device.h" />\r
-    <ClInclude Include="renderer\renderer_fwd.h" />\r
-    <ClInclude Include="renderer\render_device.h" />\r
-    <ClInclude Include="renderer\layer.h" />\r
     <ClInclude Include="server.h" />\r
+    <ClInclude Include="video\pixel_format.h" />\r
+    <ClInclude Include="video\video_format.h" />\r
     <CustomBuildStep Include="consumers\bluefish\BluefishException.h" />\r
     <CustomBuildStep Include="consumers\bluefish\BluefishFrameManager.h" />\r
     <CustomBuildStep Include="consumers\bluefish\BluefishPlaybackStrategy.h" />\r
     <ClInclude Include="StdAfx.h" />\r
   </ItemGroup>\r
   <ItemGroup>\r
+    <ClCompile Include="channel.cpp" />\r
     <ClCompile Include="consumer\bluefish\bluefish_consumer.cpp">\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../../StdAfx.h</PrecompiledHeaderFile>\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../../StdAfx.h</PrecompiledHeaderFile>\r
     </ClCompile>\r
+    <ClCompile Include="consumer\frame_consumer_device.cpp">\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+    </ClCompile>\r
     <ClCompile Include="consumer\decklink\DeckLinkAPI_i.c">\r
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">NotUsing</PrecompiledHeader>\r
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">NotUsing</PrecompiledHeader>\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../../StdAfx.h</PrecompiledHeaderFile>\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../../StdAfx.h</PrecompiledHeaderFile>\r
     </ClCompile>\r
-    <ClCompile Include="frame\gpu_composite_frame.cpp">\r
+    <ClCompile Include="processor\composite_frame.cpp">\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
     </ClCompile>\r
-    <ClCompile Include="frame\frame_format.cpp">\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">..\stdafx.h</PrecompiledHeaderFile>\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">..\stdafx.h</PrecompiledHeaderFile>\r
-    </ClCompile>\r
-    <ClCompile Include="frame\gpu_frame.cpp">\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../stdafx.h</PrecompiledHeaderFile>\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../stdafx.h</PrecompiledHeaderFile>\r
+    <ClCompile Include="processor\frame.cpp">\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
     </ClCompile>\r
-    <ClCompile Include="frame\gpu_frame_device.cpp">\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../stdafx.h</PrecompiledHeaderFile>\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../stdafx.h</PrecompiledHeaderFile>\r
+    <ClCompile Include="processor\frame_processor_device.cpp">\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
     </ClCompile>\r
-    <ClCompile Include="frame\gpu_frame_renderer.cpp">\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../stdafx.h</PrecompiledHeaderFile>\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../stdafx.h</PrecompiledHeaderFile>\r
+    <ClCompile Include="processor\frame_renderer.cpp">\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
     </ClCompile>\r
-    <ClCompile Include="frame\gpu_frame_shader.cpp">\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../stdafx.h</PrecompiledHeaderFile>\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../stdafx.h</PrecompiledHeaderFile>\r
+    <ClCompile Include="processor\frame_shader.cpp">\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
     </ClCompile>\r
     <ClCompile Include="producer\color\color_producer.cpp">\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../../StdAfx.h</PrecompiledHeaderFile>\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../../StdAfx.h</PrecompiledHeaderFile>\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../../StdAfx.h</PrecompiledHeaderFile>\r
     </ClCompile>\r
+    <ClCompile Include="producer\layer.cpp">\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+    </ClCompile>\r
+    <ClCompile Include="producer\frame_producer_device.cpp">\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+    </ClCompile>\r
     <ClCompile Include="producer\transition\transition_producer.cpp">\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../../StdAfx.h</PrecompiledHeaderFile>\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../../StdAfx.h</PrecompiledHeaderFile>\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
       <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
     </ClCompile>\r
-    <ClCompile Include="renderer\display_device.cpp">\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
-    </ClCompile>\r
-    <ClCompile Include="renderer\render_device.cpp">\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
-    </ClCompile>\r
-    <ClCompile Include="renderer\layer.cpp">\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
-      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
-    </ClCompile>\r
-    <ClCompile Include="server.cpp">\r
-      <ExpandAttributedSource Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">false</ExpandAttributedSource>\r
-      <PreprocessToFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">false</PreprocessToFile>\r
-    </ClCompile>\r
+    <ClCompile Include="server.cpp" />\r
     <ClCompile Include="StdAfx.cpp">\r
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Create</PrecompiledHeader>\r
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">Create</PrecompiledHeader>\r
     </ClCompile>\r
+    <ClCompile Include="video\video_format.cpp">\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+      <PrecompiledHeaderFile Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">../StdAfx.h</PrecompiledHeaderFile>\r
+    </ClCompile>\r
   </ItemGroup>\r
   <ItemGroup>\r
     <Midl Include="consumer\decklink\DeckLinkAPI.idl">\r
index 1ba5136f93289ebbda49c43a6ab1f68bb836ddc7..819ea8bd63f8d312cc675a88fa888c0e1dbdacea 100644 (file)
@@ -4,12 +4,6 @@
     <Filter Include="Source">\r
       <UniqueIdentifier>{0361bd88-1d96-4d86-b3ad-34d40e2319c6}</UniqueIdentifier>\r
     </Filter>\r
-    <Filter Include="Source\renderer">\r
-      <UniqueIdentifier>{db784096-c412-4d20-86f0-481e5e2979c5}</UniqueIdentifier>\r
-    </Filter>\r
-    <Filter Include="Source\frame">\r
-      <UniqueIdentifier>{69627759-fb18-42fa-8339-66ce27062c90}</UniqueIdentifier>\r
-    </Filter>\r
     <Filter Include="Source\consumer">\r
       <UniqueIdentifier>{35d7835f-f813-4b4b-8d8d-8a35dfef68d3}</UniqueIdentifier>\r
     </Filter>\r
     <Filter Include="Source\protocol\osc">\r
       <UniqueIdentifier>{23166bfa-06eb-4da9-8a0d-1ae5eac4348b}</UniqueIdentifier>\r
     </Filter>\r
-    <Filter Include="Source\frame\gpu">\r
-      <UniqueIdentifier>{91076088-a8dc-43e2-b401-ca2b8462fd06}</UniqueIdentifier>\r
-    </Filter>\r
     <Filter Include="My Amplifier Results">\r
       <UniqueIdentifier>{bb801cd9-8dc8-4300-a5c7-a7f5ee0805fb}</UniqueIdentifier>\r
     </Filter>\r
+    <Filter Include="Source\video">\r
+      <UniqueIdentifier>{f19ced4f-4ad2-4c0a-b51f-50e89909d669}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="Source\processor">\r
+      <UniqueIdentifier>{53e41831-70b4-4214-bc38-77e0d7aa288b}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="Source\processor\renderer">\r
+      <UniqueIdentifier>{30fe40ca-8bf0-4a46-a882-16d07b2b441e}</UniqueIdentifier>\r
+    </Filter>\r
   </ItemGroup>\r
   <ItemGroup>\r
     <ClInclude Include="StdAfx.h">\r
     <ClInclude Include="protocol\clk\CLKProtocolStrategy.h">\r
       <Filter>Source\protocol\clk</Filter>\r
     </ClInclude>\r
-    <ClInclude Include="renderer\render_device.h">\r
-      <Filter>Source\renderer</Filter>\r
-    </ClInclude>\r
-    <ClInclude Include="renderer\layer.h">\r
-      <Filter>Source\renderer</Filter>\r
-    </ClInclude>\r
-    <ClInclude Include="renderer\renderer_fwd.h">\r
-      <Filter>Source\renderer</Filter>\r
-    </ClInclude>\r
-    <ClInclude Include="frame\frame_fwd.h">\r
-      <Filter>Source\frame</Filter>\r
-    </ClInclude>\r
-    <ClInclude Include="frame\frame_format.h">\r
-      <Filter>Source\frame</Filter>\r
-    </ClInclude>\r
-    <ClInclude Include="server.h">\r
-      <Filter>Source</Filter>\r
-    </ClInclude>\r
     <ClInclude Include="consumer\decklink\DecklinkVideoConsumer.h">\r
       <Filter>Source\consumer\decklink</Filter>\r
     </ClInclude>\r
     <ClInclude Include="protocol\media.h">\r
       <Filter>Source\protocol</Filter>\r
     </ClInclude>\r
-    <ClInclude Include="frame\gpu_frame.h">\r
-      <Filter>Source\frame\gpu</Filter>\r
-    </ClInclude>\r
-    <ClInclude Include="frame\frame_factory.h">\r
-      <Filter>Source\frame</Filter>\r
-    </ClInclude>\r
     <ClInclude Include="producer\frame_producer.h">\r
       <Filter>Source\producer</Filter>\r
     </ClInclude>\r
     <ClInclude Include="producer\ffmpeg\video\video_transformer.h">\r
       <Filter>Source\producer\ffmpeg\video</Filter>\r
     </ClInclude>\r
-    <ClInclude Include="producer\flash\bitmap.h">\r
-      <Filter>Source\producer\flash</Filter>\r
-    </ClInclude>\r
     <ClInclude Include="producer\flash\cg_producer.h">\r
       <Filter>Source\producer\flash</Filter>\r
     </ClInclude>\r
     <ClInclude Include="consumer\bluefish\bluefish_consumer.h">\r
       <Filter>Source\consumer\bluefish</Filter>\r
     </ClInclude>\r
-    <ClInclude Include="frame\gpu_composite_frame.h">\r
-      <Filter>Source\frame\gpu</Filter>\r
-    </ClInclude>\r
-    <ClInclude Include="renderer\display_device.h">\r
-      <Filter>Source\renderer</Filter>\r
-    </ClInclude>\r
     <ClInclude Include="config.h">\r
       <Filter>Source</Filter>\r
     </ClInclude>\r
     <ClInclude Include="consumer\frame_consumer.h">\r
       <Filter>Source\consumer</Filter>\r
     </ClInclude>\r
-    <ClInclude Include="frame\gpu_frame_desc.h">\r
-      <Filter>Source\frame\gpu</Filter>\r
+    <ClInclude Include="producer\flash\bitmap.h">\r
+      <Filter>Source\producer\flash</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="producer\layer.h">\r
+      <Filter>Source\producer</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="video\pixel_format.h">\r
+      <Filter>Source\video</Filter>\r
     </ClInclude>\r
-    <ClInclude Include="frame\gpu_frame_device.h">\r
-      <Filter>Source\frame\gpu</Filter>\r
+    <ClInclude Include="video\video_format.h">\r
+      <Filter>Source\video</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="consumer\frame_consumer_device.h">\r
+      <Filter>Source\consumer</Filter>\r
     </ClInclude>\r
-    <ClInclude Include="frame\gpu_frame_renderer.h">\r
-      <Filter>Source\frame\gpu</Filter>\r
+    <ClInclude Include="producer\frame_producer_device.h">\r
+      <Filter>Source\producer</Filter>\r
     </ClInclude>\r
-    <ClInclude Include="frame\gpu_frame_shader.h">\r
-      <Filter>Source\frame\gpu</Filter>\r
+    <ClInclude Include="server.h">\r
+      <Filter>Source</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="channel.h">\r
+      <Filter>Source</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="processor\frame_processor_device.h">\r
+      <Filter>Source\processor</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="processor\frame.h">\r
+      <Filter>Source\processor</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="processor\composite_frame.h">\r
+      <Filter>Source\processor</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="processor\frame_shader.h">\r
+      <Filter>Source\processor\renderer</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="processor\frame_renderer.h">\r
+      <Filter>Source\processor\renderer</Filter>\r
     </ClInclude>\r
   </ItemGroup>\r
   <ItemGroup>\r
     <ClCompile Include="protocol\clk\CLKCommand.cpp">\r
       <Filter>Source\protocol\clk</Filter>\r
     </ClCompile>\r
-    <ClCompile Include="renderer\render_device.cpp">\r
-      <Filter>Source\renderer</Filter>\r
-    </ClCompile>\r
-    <ClCompile Include="renderer\layer.cpp">\r
-      <Filter>Source\renderer</Filter>\r
-    </ClCompile>\r
-    <ClCompile Include="frame\frame_format.cpp">\r
-      <Filter>Source\frame</Filter>\r
-    </ClCompile>\r
-    <ClCompile Include="server.cpp">\r
-      <Filter>Source</Filter>\r
-    </ClCompile>\r
     <ClCompile Include="consumer\decklink\DecklinkVideoConsumer.cpp">\r
       <Filter>Source\consumer\decklink</Filter>\r
     </ClCompile>\r
     <ClCompile Include="protocol\media.cpp">\r
       <Filter>Source\protocol</Filter>\r
     </ClCompile>\r
-    <ClCompile Include="frame\gpu_frame.cpp">\r
-      <Filter>Source\frame\gpu</Filter>\r
-    </ClCompile>\r
     <ClCompile Include="producer\ffmpeg\video\video_transformer.cpp">\r
       <Filter>Source\producer\ffmpeg\video</Filter>\r
     </ClCompile>\r
-    <ClCompile Include="producer\flash\bitmap.cpp">\r
-      <Filter>Source\producer\flash</Filter>\r
-    </ClCompile>\r
     <ClCompile Include="producer\flash\cg_producer.cpp">\r
       <Filter>Source\producer\flash</Filter>\r
     </ClCompile>\r
     <ClCompile Include="consumer\bluefish\bluefish_consumer.cpp">\r
       <Filter>Source\consumer\bluefish</Filter>\r
     </ClCompile>\r
-    <ClCompile Include="frame\gpu_composite_frame.cpp">\r
-      <Filter>Source\frame\gpu</Filter>\r
+    <ClCompile Include="producer\flash\bitmap.cpp">\r
+      <Filter>Source\producer\flash</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="producer\layer.cpp">\r
+      <Filter>Source\producer</Filter>\r
     </ClCompile>\r
-    <ClCompile Include="renderer\display_device.cpp">\r
-      <Filter>Source\renderer</Filter>\r
+    <ClCompile Include="video\video_format.cpp">\r
+      <Filter>Source\video</Filter>\r
     </ClCompile>\r
-    <ClCompile Include="frame\gpu_frame_device.cpp">\r
-      <Filter>Source\frame\gpu</Filter>\r
+    <ClCompile Include="consumer\frame_consumer_device.cpp">\r
+      <Filter>Source\consumer</Filter>\r
     </ClCompile>\r
-    <ClCompile Include="frame\gpu_frame_renderer.cpp">\r
-      <Filter>Source\frame\gpu</Filter>\r
+    <ClCompile Include="producer\frame_producer_device.cpp">\r
+      <Filter>Source\producer</Filter>\r
     </ClCompile>\r
-    <ClCompile Include="frame\gpu_frame_shader.cpp">\r
-      <Filter>Source\frame\gpu</Filter>\r
+    <ClCompile Include="server.cpp">\r
+      <Filter>Source</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="processor\frame_processor_device.cpp">\r
+      <Filter>Source\processor</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="processor\frame.cpp">\r
+      <Filter>Source\processor</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="processor\composite_frame.cpp">\r
+      <Filter>Source\processor</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="processor\frame_renderer.cpp">\r
+      <Filter>Source\processor\renderer</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="processor\frame_shader.cpp">\r
+      <Filter>Source\processor\renderer</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="channel.cpp">\r
+      <Filter>Source</Filter>\r
     </ClCompile>\r
   </ItemGroup>\r
   <ItemGroup>\r
diff --git a/core/processor/composite_frame.cpp b/core/processor/composite_frame.cpp
new file mode 100644 (file)
index 0000000..407a1d2
--- /dev/null
@@ -0,0 +1,117 @@
+#include "../StdAfx.h"\r
+\r
+#include "composite_frame.h"\r
+#include "../../common/gl/utility.h"\r
+#include "../../common/utility/memory.h"\r
+\r
+#include <boost/range/algorithm.hpp>\r
+\r
+#include <algorithm>\r
+#include <numeric>\r
+\r
+#include <tbb/parallel_for.h>\r
+\r
+namespace caspar { namespace core {\r
+       \r
+struct composite_frame::implementation : boost::noncopyable\r
+{\r
+       implementation(composite_frame* self) : self_(self){}\r
+\r
+       void begin_write()\r
+       {\r
+               boost::range::for_each(frames_, std::mem_fn(&frame::begin_write));              \r
+       }\r
+\r
+       void end_write()\r
+       {\r
+               boost::range::for_each(frames_, std::mem_fn(&frame::end_write));                                \r
+       }\r
+       \r
+       void begin_read()\r
+       {       \r
+               boost::range::for_each(frames_, std::mem_fn(&frame::begin_read));               \r
+       }\r
+\r
+       void end_read()\r
+       {\r
+               boost::range::for_each(frames_, std::mem_fn(&frame::end_read)); \r
+       }\r
+\r
+       void draw(const frame_shader_ptr& shader)\r
+       {\r
+               glPushMatrix();\r
+               glTranslated(self_->x()*2.0, self_->y()*2.0, 0.0);\r
+               boost::range::for_each(frames_, std::bind(&frame::draw, std::placeholders::_1, shader));\r
+               glPopMatrix();\r
+       }\r
+               \r
+       void add(const frame_ptr& frame)\r
+       {\r
+               if(frame == nullptr || frame == frame::empty())\r
+                       return;\r
+\r
+               frames_.push_back(frame);\r
+\r
+               if(self_->audio_data().empty())\r
+                       self_->audio_data() = std::move(frame->audio_data());\r
+               else\r
+               {\r
+                       tbb::parallel_for\r
+                       (\r
+                               tbb::blocked_range<size_t>(0, frame->audio_data().size()),\r
+                               [&](const tbb::blocked_range<size_t>& r)\r
+                               {\r
+                                       for(size_t n = r.begin(); n < r.end(); ++n)\r
+                                       {\r
+                                               self_->audio_data()[n] = static_cast<short>(\r
+                                                       static_cast<int>(self_->audio_data()[n]) + \r
+                                                       static_cast<int>(frame->audio_data()[n]) & 0xFFFF);     \r
+                                       }\r
+                               }\r
+                       );\r
+               }\r
+       }\r
+\r
+       unsigned char* data(size_t)\r
+       {\r
+               BOOST_THROW_EXCEPTION(invalid_operation());\r
+       }\r
+\r
+       composite_frame* self_;\r
+       std::vector<frame_ptr> frames_;\r
+       size_t size_;\r
+};\r
+\r
+#if defined(_MSC_VER)\r
+#pragma warning (disable : 4355) // 'this' : used in base member initializer list\r
+#endif\r
+\r
+composite_frame::composite_frame() \r
+       : frame(0, 0), impl_(new implementation(this)){}\r
+void composite_frame::begin_write(){impl_->begin_write();}\r
+void composite_frame::end_write(){impl_->end_write();} \r
+void composite_frame::begin_read(){impl_->begin_read();}\r
+void composite_frame::end_read(){impl_->end_read();}\r
+void composite_frame::draw(const frame_shader_ptr& shader){impl_->draw(shader);}\r
+unsigned char* composite_frame::data(size_t index){return impl_->data(index);}\r
+void composite_frame::add(const frame_ptr& frame){impl_->add(frame);}\r
+\r
+frame_ptr composite_frame::interlace(const frame_ptr& frame1, const frame_ptr& frame2, video_update_format::type mode)\r
+{                      \r
+       auto result = std::make_shared<composite_frame>();\r
+       result->add(frame1);\r
+       result->add(frame2);\r
+       if(mode == video_update_format::upper)\r
+       {\r
+               frame1->update_fmt(video_update_format::upper);\r
+               frame2->update_fmt(video_update_format::lower);\r
+       }\r
+       else\r
+       {\r
+               frame1->update_fmt(video_update_format::lower);\r
+               frame2->update_fmt(video_update_format::upper);\r
+       }\r
+       return result;\r
+}\r
+\r
+}}
\ No newline at end of file
diff --git a/core/processor/composite_frame.h b/core/processor/composite_frame.h
new file mode 100644 (file)
index 0000000..a120da9
--- /dev/null
@@ -0,0 +1,33 @@
+#pragma once\r
+\r
+#include <memory>\r
+\r
+#include <Glee.h>\r
+\r
+#include "frame.h"\r
+\r
+namespace caspar { namespace core {\r
+       \r
+class composite_frame : public frame\r
+{\r
+public:\r
+       composite_frame();\r
+                                               \r
+       void add(const frame_ptr& frame);\r
+\r
+       static frame_ptr interlace(const frame_ptr& frame1,     const frame_ptr& frame2, video_update_format::type mode);\r
+       \r
+private:\r
+       virtual unsigned char* data(size_t index);\r
+       virtual void begin_write();\r
+       virtual void end_write();\r
+       virtual void begin_read();\r
+       virtual void end_read();\r
+       virtual void draw(const frame_shader_ptr& shader);\r
+\r
+       struct implementation;\r
+       std::shared_ptr<implementation> impl_;\r
+};\r
+typedef std::shared_ptr<composite_frame> gpu_composite_frame_ptr;\r
+       \r
+}}
\ No newline at end of file
diff --git a/core/processor/frame.cpp b/core/processor/frame.cpp
new file mode 100644 (file)
index 0000000..e1d089f
--- /dev/null
@@ -0,0 +1,196 @@
+#include "../StdAfx.h"\r
+\r
+#include "frame.h"\r
+#include "../video/pixel_format.h"\r
+#include "../../common/utility/memory.h"\r
+#include "../../common/gl/utility.h"\r
+#include "../../common/gl/pixel_buffer_object.h"\r
+\r
+#include <boost/range/algorithm.hpp>\r
+\r
+namespace caspar { namespace core {\r
+       \r
+struct rectangle\r
+{\r
+       rectangle(double left, double top, double right, double bottom)\r
+               : left(left), top(top), right(right), bottom(bottom)\r
+       {}\r
+       double left;\r
+       double top;\r
+       double right;\r
+       double bottom;\r
+};\r
+\r
+GLubyte progressive_pattern[] = {\r
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,\r
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,\r
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,\r
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,\r
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,\r
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,\r
+       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,\r
+       0xff, 0xff, 0xFF, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff};\r
+       \r
+GLubyte upper_pattern[] = {\r
+       0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00,\r
+       0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00,\r
+       0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00,\r
+       0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00,\r
+       0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00,\r
+       0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00,\r
+       0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00,\r
+       0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00};\r
+               \r
+GLubyte lower_pattern[] = {\r
+       0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, \r
+       0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, \r
+       0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, \r
+       0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff,\r
+       0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff,\r
+       0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff,\r
+       0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff,\r
+       0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff};\r
+                                                                                                                                                                                                                                                                                                               \r
+struct frame::implementation : boost::noncopyable\r
+{\r
+       implementation(size_t width, size_t height)\r
+               : alpha_(1.0f), x_(0.0f), y_(0.0f), update_fmt_(video_update_format::progressive), texcoords_(0.0, 1.0, 1.0, 0.0), pixel_data_(4, nullptr)\r
+       {       \r
+               desc_.planes[0] = pixel_format_desc::plane(width, height, 4);\r
+               desc_.pix_fmt = pixel_format::bgra;\r
+               pixel_data_.resize(4, 0);\r
+               if(width >= 2 && height >= 2)\r
+               {\r
+                       pbo_.push_back(std::make_shared<common::gl::pixel_buffer_object>(width, height, GL_BGRA));\r
+                       end_write();\r
+               }\r
+       }\r
+\r
+       implementation(const pixel_format_desc& desc)\r
+               : alpha_(1.0f), x_(0.0f), y_(0.0f), update_fmt_(video_update_format::progressive), texcoords_(0.0, 1.0, 1.0, 0.0), pixel_data_(4, nullptr)\r
+       {                       \r
+               desc_ = desc;\r
+\r
+               for(size_t n = 0; n < desc_.planes.size(); ++n)\r
+               {\r
+                       if(desc_.planes[n].size == 0)\r
+                               break;\r
+\r
+                       GLuint format = [&]() -> GLuint\r
+                       {\r
+                               switch(desc_.planes[n].channels)\r
+                               {\r
+                               case 1: return GL_LUMINANCE;\r
+                               case 2: return GL_LUMINANCE_ALPHA;\r
+                               case 3: return GL_BGR;\r
+                               case 4: return GL_BGRA;\r
+                               default: BOOST_THROW_EXCEPTION(out_of_range() << msg_info("1-4 channels are supported") << arg_name_info("desc.planes.channels")); \r
+                               }\r
+                       }();\r
+\r
+                       pbo_.push_back(std::make_shared<common::gl::pixel_buffer_object>(desc_.planes[n].width, desc_.planes[n].height, format));\r
+               }\r
+               end_write();\r
+       }\r
+       \r
+       void begin_write()\r
+       {\r
+               pixel_data_ = std::vector<void*>(4, 0);\r
+               boost::range::for_each(pbo_, std::mem_fn(&common::gl::pixel_buffer_object::begin_write));\r
+       }\r
+\r
+       void end_write()\r
+       {\r
+               boost::range::transform(pbo_, pixel_data_.begin(), std::mem_fn(&common::gl::pixel_buffer_object::end_write));\r
+       }\r
+       \r
+       void begin_read()\r
+       {       \r
+               pixel_data_ = std::vector<void*>(4, 0);\r
+               boost::range::for_each(pbo_, std::mem_fn(&common::gl::pixel_buffer_object::begin_read));\r
+       }\r
+\r
+       void end_read()\r
+       {\r
+               boost::range::transform(pbo_, pixel_data_.begin(), std::mem_fn(&common::gl::pixel_buffer_object::end_read));\r
+       }\r
+\r
+       void draw(const frame_shader_ptr& shader)\r
+       {\r
+               shader->use(desc_);\r
+               glPushMatrix();\r
+               glTranslated(x_*2.0, y_*2.0, 0.0);\r
+               glColor4d(1.0, 1.0, 1.0, alpha_);\r
+\r
+               if(update_fmt_ == video_update_format::progressive)\r
+                       glPolygonStipple(progressive_pattern);\r
+               else if(update_fmt_ == video_update_format::upper)\r
+                       glPolygonStipple(upper_pattern);\r
+               else if(update_fmt_ == video_update_format::lower)\r
+                       glPolygonStipple(lower_pattern);\r
+\r
+               for(size_t n = 0; n < pbo_.size(); ++n)\r
+               {\r
+                       glActiveTexture(GL_TEXTURE0+n);\r
+                       pbo_[n]->bind_texture();\r
+               }\r
+               glBegin(GL_QUADS);\r
+                       glTexCoord2d(texcoords_.left,   texcoords_.bottom); glVertex2d(-1.0, -1.0);\r
+                       glTexCoord2d(texcoords_.right,  texcoords_.bottom); glVertex2d( 1.0, -1.0);\r
+                       glTexCoord2d(texcoords_.right,  texcoords_.top);        glVertex2d( 1.0,  1.0);\r
+                       glTexCoord2d(texcoords_.left,   texcoords_.top);        glVertex2d(-1.0,  1.0);\r
+               glEnd();\r
+               glPopMatrix();\r
+       }\r
+\r
+       unsigned char* data(size_t index)\r
+       {\r
+               if(pbo_.size() < index)\r
+                       BOOST_THROW_EXCEPTION(out_of_range());\r
+               return static_cast<unsigned char*>(pixel_data_[index]);\r
+       }\r
+\r
+       void reset()\r
+       {\r
+               audio_data_.clear();\r
+               alpha_          = 1.0f;\r
+               x_                      = 0.0f;\r
+               y_                      = 0.0f;\r
+               texcoords_      = rectangle(0.0, 1.0, 1.0, 0.0);\r
+               update_fmt_ = video_update_format::progressive;\r
+       }\r
+\r
+       std::vector<common::gl::pixel_buffer_object_ptr> pbo_;\r
+       std::vector<void*> pixel_data_; \r
+       std::vector<short> audio_data_;\r
+\r
+       double alpha_;\r
+       double x_;\r
+       double y_;\r
+       video_update_format::type update_fmt_;\r
+       rectangle texcoords_;\r
+\r
+       pixel_format_desc desc_;\r
+};\r
+\r
+frame::frame(size_t width, size_t height) \r
+       : impl_(new implementation(width, height)){}\r
+frame::frame(const pixel_format_desc& desc)\r
+       : impl_(new implementation(desc)){}\r
+void frame::draw(const frame_shader_ptr& shader){impl_->draw(shader);}\r
+void frame::begin_write(){impl_->begin_write();}\r
+void frame::end_write(){impl_->end_write();}   \r
+void frame::begin_read(){impl_->begin_read();}\r
+void frame::end_read(){impl_->end_read();}\r
+void frame::pix_fmt(pixel_format::type format) {impl_->desc_.pix_fmt = format;}\r
+unsigned char* frame::data(size_t index){return impl_->data(index);}\r
+size_t frame::size(size_t index) const { return impl_->desc_.planes[index].size; }\r
+std::vector<short>& frame::audio_data() { return impl_->audio_data_; }\r
+void frame::reset(){impl_->reset();}\r
+void frame::alpha(double value){ impl_->alpha_ = value;}\r
+void frame::translate(double x, double y) { impl_->x_ += x; impl_->y_ += y; }\r
+void frame::texcoords(double left, double top, double right, double bottom){impl_->texcoords_ = rectangle(left, top, right, bottom);}\r
+void frame::update_fmt(video_update_format::type fmt){ impl_->update_fmt_ = fmt;}\r
+double frame::x() const { return impl_->x_;}\r
+double frame::y() const { return impl_->y_;}\r
+}}
\ No newline at end of file
diff --git a/core/processor/frame.h b/core/processor/frame.h
new file mode 100644 (file)
index 0000000..aa6001e
--- /dev/null
@@ -0,0 +1,64 @@
+#pragma once\r
+\r
+#include "frame_shader.h"\r
+\r
+#include "../video/video_format.h"\r
+#include "../video/pixel_format.h"\r
+\r
+#include <memory>\r
+#include <array>\r
+\r
+#include <boost/noncopyable.hpp>\r
+\r
+#include <boost/tuple/tuple.hpp>\r
+\r
+#include <vector>\r
+\r
+namespace caspar { namespace core {\r
+       \r
+class frame :  boost::noncopyable\r
+{\r
+public:\r
+       virtual ~frame(){}\r
+                       \r
+       virtual unsigned char* data(size_t index = 0);\r
+       virtual size_t size(size_t index = 0) const;\r
+                               \r
+       virtual std::vector<short>& audio_data();\r
+\r
+       virtual void alpha(double value);\r
+       virtual void translate(double x, double y);\r
+       virtual void texcoords(double left, double top, double right, double bottom);\r
+       virtual void update_fmt(video_update_format::type fmt); \r
+       virtual void pix_fmt(pixel_format::type fmt);\r
+       \r
+       virtual double x() const;\r
+       virtual double y() const;\r
+\r
+       static std::shared_ptr<frame> empty()\r
+       {\r
+               static auto my_null_frame = std::shared_ptr<frame>(new frame(0,0));\r
+               return my_null_frame;\r
+       }\r
+               \r
+       virtual void begin_write();\r
+       virtual void end_write();\r
+       virtual void begin_read();\r
+       virtual void end_read();\r
+       virtual void draw(const frame_shader_ptr& shader);\r
+\r
+protected:\r
+       frame(size_t width, size_t height);\r
+       frame(const pixel_format_desc& desc);\r
+\r
+       friend class frame_processor_device;\r
+\r
+       virtual void reset();\r
+\r
+private:\r
+       struct implementation;\r
+       std::shared_ptr<implementation> impl_;\r
+};\r
+typedef std::shared_ptr<frame> frame_ptr;\r
+       \r
+}}
\ No newline at end of file
diff --git a/core/processor/frame_processor_device.cpp b/core/processor/frame_processor_device.cpp
new file mode 100644 (file)
index 0000000..ea3d223
--- /dev/null
@@ -0,0 +1,167 @@
+#include "../StdAfx.h"\r
+\r
+#include "frame_processor_device.h"\r
+\r
+#include "frame_renderer.h"\r
+#include "frame.h"\r
+#include "composite_frame.h"\r
+\r
+#include "../video/video_format.h"\r
+\r
+#include "../../common/exception/exceptions.h"\r
+#include "../../common/concurrency/executor.h"\r
+#include "../../common/gl/utility.h"\r
+\r
+#include <Glee.h>\r
+#include <SFML/Window.hpp>\r
+\r
+#include <tbb/concurrent_queue.h>\r
+#include <tbb/concurrent_unordered_map.h>\r
+#include <tbb/concurrent_vector.h>\r
+\r
+#include <boost/range/algorithm.hpp>\r
+#include <boost/thread.hpp>\r
+\r
+#include <functional>\r
+\r
+namespace caspar { namespace core {\r
+       \r
+struct frame_processor_device::implementation : boost::noncopyable\r
+{      \r
+       implementation(frame_processor_device* self, const video_format_desc& format_desc) \r
+               : fmt_(format_desc)\r
+       {               \r
+               boost::promise<frame_ptr> promise;\r
+               active_frame_ = promise.get_future();\r
+               promise.set_value(nullptr);\r
+\r
+               input_.set_capacity(2);\r
+               output_.set_capacity(2);\r
+               executor_.start();\r
+               executor_.invoke([=]\r
+               {\r
+                       ogl_context_.reset(new sf::Context());\r
+                       ogl_context_->SetActive(true);\r
+                       GL(glEnable(GL_POLYGON_STIPPLE));\r
+                       GL(glEnable(GL_TEXTURE_2D));\r
+                       GL(glEnable(GL_BLEND));\r
+                       GL(glDisable(GL_DEPTH_TEST));\r
+                       GL(glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA));                  \r
+                       GL(glClearColor(0.0, 0.0, 0.0, 0.0));\r
+                       GL(glViewport(0, 0, format_desc.width, format_desc.height));\r
+                       glLoadIdentity();   \r
+\r
+                       renderer_ = std::make_shared<frame_renderer>(*self, format_desc);\r
+               });\r
+       }\r
+\r
+       ~implementation()\r
+       {\r
+               executor_.stop();\r
+       }\r
+                                       \r
+       frame_ptr create_frame(const pixel_format_desc& desc, void* tag)\r
+       {\r
+               size_t key = reinterpret_cast<size_t>(tag);\r
+               auto& pool = writing_pools_[key];\r
+               \r
+               frame_ptr my_frame;\r
+               if(!pool.try_pop(my_frame))\r
+               {\r
+                       my_frame = executor_.invoke([&]\r
+                       {\r
+                               return std::shared_ptr<frame>(new frame(desc));\r
+                       });\r
+               }\r
+               \r
+               auto destructor = [=]\r
+               {\r
+                       my_frame->reset();\r
+                       writing_pools_[key].push(my_frame);\r
+               };\r
+\r
+               return frame_ptr(my_frame.get(), [=](frame*)                                                    \r
+               {\r
+                       executor_.begin_invoke(destructor);\r
+               });\r
+       }\r
+\r
+       void release_tag(void* tag)\r
+       {\r
+               writing_pools_[reinterpret_cast<size_t>(tag)].clear();\r
+       }\r
+       \r
+       void send(const frame_ptr& input_frame)\r
+       {                       \r
+               input_.push(input_frame);\r
+               executor_.begin_invoke([=]\r
+               {\r
+                       try\r
+                       {\r
+                               frame_ptr output_frame;\r
+                               input_.pop(output_frame);\r
+                               output_.push(renderer_->render(output_frame));\r
+                       }\r
+                       catch(...)\r
+                       {\r
+                               CASPAR_LOG_CURRENT_EXCEPTION();\r
+                       }\r
+               });     \r
+       }\r
+\r
+       void receive(frame_ptr& output_frame)\r
+       {\r
+               output_.pop(output_frame);\r
+       }\r
+\r
+       bool try_receive(frame_ptr& output_frame)\r
+       {\r
+               return output_.try_pop(output_frame);\r
+       }\r
+       \r
+       video_format_desc fmt_;\r
+                               \r
+       typedef tbb::concurrent_bounded_queue<frame_ptr> frame_queue;\r
+       tbb::concurrent_unordered_map<size_t, frame_queue> writing_pools_;\r
+       frame_queue reading_pool_;      \r
+                               \r
+       std::unique_ptr<sf::Context> ogl_context_;\r
+\r
+       boost::unique_future<frame_ptr> active_frame_;\r
+       \r
+       common::executor executor_;\r
+       \r
+       frame_queue input_;\r
+       frame_queue output_;    \r
+\r
+       frame_renderer_ptr renderer_;\r
+};\r
+       \r
+#if defined(_MSC_VER)\r
+#pragma warning (disable : 4355) // 'this' : used in base member initializer list\r
+#endif\r
+\r
+frame_processor_device::frame_processor_device(const video_format_desc& format_desc) \r
+       : impl_(new implementation(this, format_desc)){}\r
+frame_ptr frame_processor_device::create_frame(const  pixel_format_desc& desc, void* tag){return impl_->create_frame(desc, tag);}\r
+void frame_processor_device::release_tag(void* tag){impl_->release_tag(tag);}\r
+void frame_processor_device::send(const frame_ptr& frame){impl_->send(frame);}\r
+void frame_processor_device::receive(frame_ptr& frame){impl_->receive(frame);}\r
+bool frame_processor_device::try_receive(frame_ptr& frame){return impl_->try_receive(frame);}\r
+const video_format_desc frame_processor_device::get_video_format_desc() const { return impl_->fmt_;}\r
+frame_ptr frame_processor_device::create_frame(size_t width, size_t height, void* tag)\r
+{\r
+       pixel_format_desc desc;\r
+       desc.pix_fmt = pixel_format::bgra;\r
+       desc.planes[0] = pixel_format_desc::plane(width, height, 4);\r
+       return create_frame(desc, tag);\r
+}\r
+                       \r
+frame_ptr frame_processor_device::create_frame(void* tag)\r
+{\r
+       pixel_format_desc desc;\r
+       desc.pix_fmt = pixel_format::bgra;\r
+       desc.planes[0] = pixel_format_desc::plane(get_video_format_desc().width, get_video_format_desc().height, 4);\r
+       return create_frame(desc, tag);\r
+}\r
+}}
\ No newline at end of file
diff --git a/core/processor/frame_processor_device.h b/core/processor/frame_processor_device.h
new file mode 100644 (file)
index 0000000..91b1ae6
--- /dev/null
@@ -0,0 +1,53 @@
+/*\r
+* copyright (c) 2010 Sveriges Television AB <info@casparcg.com>\r
+*\r
+*  This file is part of CasparCG.\r
+*\r
+*    CasparCG is free software: you can redistribute it and/or modify\r
+*    it under the terms of the GNU General Public License as published by\r
+*    the Free Software Foundation, either version 3 of the License, or\r
+*    (at your option) any later version.\r
+*\r
+*    CasparCG is distributed in the hope that it will be useful,\r
+*    but WITHOUT ANY WARRANTY; without even the implied warranty of\r
+*    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r
+*    GNU General Public License for more details.\r
+\r
+*    You should have received a copy of the GNU General Public License\r
+*    along with CasparCG.  If not, see <http://www.gnu.org/licenses/>.\r
+*\r
+*/\r
+#pragma once\r
+\r
+#include <memory>\r
+#include <vector>\r
+\r
+#include "../video/video_format.h"\r
+#include "../processor/frame.h"\r
+#include "../consumer/frame_consumer_device.h"\r
+\r
+namespace caspar { namespace core {\r
+\r
+class frame_processor_device : boost::noncopyable\r
+{\r
+public:\r
+       frame_processor_device(const video_format_desc& format_desc);\r
+               \r
+       void send(const frame_ptr& frame);\r
+       void receive(frame_ptr& frame);\r
+       bool try_receive(frame_ptr& frame);\r
+       \r
+       frame_ptr create_frame(const pixel_format_desc& desc, void* tag);               \r
+       frame_ptr create_frame(size_t width, size_t height, void* tag);                 \r
+       frame_ptr create_frame(void* tag);\r
+\r
+       void release_tag(void* tag);\r
+\r
+       const video_format_desc get_video_format_desc() const;\r
+private:\r
+       struct implementation;\r
+       std::shared_ptr<implementation> impl_;\r
+};\r
+typedef std::shared_ptr<frame_processor_device> frame_processor_device_ptr;\r
+\r
+}}
\ No newline at end of file
diff --git a/core/processor/frame_renderer.cpp b/core/processor/frame_renderer.cpp
new file mode 100644 (file)
index 0000000..c17e341
--- /dev/null
@@ -0,0 +1,93 @@
+#include "../StdAfx.h"\r
+\r
+#include "frame_renderer.h"\r
+\r
+#include "../processor/frame.h"\r
+\r
+#include "../video/video_format.h"\r
+#include "../processor/frame_processor_device.h"\r
+\r
+#include "../../common/exception/exceptions.h"\r
+#include "../../common/gl/utility.h"\r
+#include "../../common/gl/frame_buffer_object.h"\r
+\r
+#include <Glee.h>\r
+\r
+#include <tbb/concurrent_queue.h>\r
+\r
+#include <boost/range/algorithm_ext/erase.hpp>\r
+#include <boost/range/algorithm.hpp>\r
+\r
+#include <functional>\r
+\r
+namespace caspar { namespace core {\r
+       \r
+struct frame_renderer::implementation : boost::noncopyable\r
+{      \r
+       implementation(frame_processor_device& frame_processor, const video_format_desc& format_desc) \r
+               : frame_processor_(frame_processor), format_desc_(format_desc), index_(0), shader_(std::make_shared<frame_shader>(format_desc)), \r
+                       writing_(2, frame::empty()), output_frame_(frame::empty())\r
+       {       \r
+               fbo_.create(format_desc_.width, format_desc_.height);\r
+               fbo_.bind_pixel_source();\r
+       }\r
+                               \r
+       frame_ptr render(const frame_ptr& frame)\r
+       {\r
+               frame_ptr result;\r
+               try\r
+               {\r
+                       index_ = (index_ + 1) % 2;\r
+                       int next_index = (index_ + 1) % 2;\r
+\r
+                       // 1. Start asynchronous DMA transfer to video memory.\r
+                       writing_[index_] = std::move(frame);            \r
+                       // Lock frame and give pointer ownership to OpenGL.\r
+                       writing_[index_]->begin_write();\r
+                               \r
+                       // 3. Output to external buffer.\r
+                       output_frame_->end_read();\r
+                       result = output_frame_;\r
+                       \r
+                       // Clear framebuffer.\r
+                       GL(glClear(GL_COLOR_BUFFER_BIT));       \r
+\r
+                       // 2. Draw to framebuffer and start asynchronous DMA transfer \r
+                       // to page-locked memory.\r
+                       writing_[next_index]->draw(shader_);\r
+                               \r
+                       // Create an output frame\r
+                       auto temp_frame = frame_processor_.create_frame(this);\r
+                       \r
+                       // Read from framebuffer into page-locked memory.\r
+                       temp_frame->begin_read();\r
+                       temp_frame->audio_data() = std::move(writing_[next_index]->audio_data());\r
+\r
+                       output_frame_ = temp_frame;\r
+\r
+                       // Return frames to pool.\r
+                       writing_[next_index]->end_write();\r
+                       writing_[next_index] = nullptr;\r
+               }\r
+               catch(...)\r
+               {\r
+                       CASPAR_LOG_CURRENT_EXCEPTION();\r
+               }\r
+               return result == frame::empty() ? nullptr : result;;\r
+       }\r
+\r
+       size_t index_;\r
+\r
+       frame_ptr output_frame_;                        \r
+       video_format_desc format_desc_;\r
+       frame_processor_device& frame_processor_;\r
+\r
+       std::vector<frame_ptr> writing_;\r
+       \r
+       common::gl::frame_buffer_object fbo_;\r
+       frame_shader_ptr shader_;\r
+};\r
+       \r
+frame_renderer::frame_renderer(frame_processor_device& frame_processor, const video_format_desc& format_desc) : impl_(new implementation(frame_processor, format_desc)){}\r
+frame_ptr frame_renderer::render(const frame_ptr& frames){ return impl_->render(frames);}\r
+}}
\ No newline at end of file
diff --git a/core/processor/frame_renderer.h b/core/processor/frame_renderer.h
new file mode 100644 (file)
index 0000000..ef314c3
--- /dev/null
@@ -0,0 +1,44 @@
+/*\r
+* copyright (c) 2010 Sveriges Television AB <info@casparcg.com>\r
+*\r
+*  This file is part of CasparCG.\r
+*\r
+*    CasparCG is free software: you can redistribute it and/or modify\r
+*    it under the terms of the GNU General Public License as published by\r
+*    the Free Software Foundation, either version 3 of the License, or\r
+*    (at your option) any later version.\r
+*\r
+*    CasparCG is distributed in the hope that it will be useful,\r
+*    but WITHOUT ANY WARRANTY; without even the implied warranty of\r
+*    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r
+*    GNU General Public License for more details.\r
+\r
+*    You should have received a copy of the GNU General Public License\r
+*    along with CasparCG.  If not, see <http://www.gnu.org/licenses/>.\r
+*\r
+*/\r
+#pragma once\r
+\r
+#include "frame_processor_device.h"\r
+\r
+#include "../video/video_format.h"\r
+\r
+#include <boost/noncopyable.hpp>\r
+\r
+#include <memory>\r
+\r
+namespace caspar { namespace core {\r
+\r
+class frame_renderer :  boost::noncopyable\r
+{\r
+public:\r
+       frame_renderer(frame_processor_device& frame_processor, const video_format_desc& format_desc_);\r
+               \r
+       frame_ptr render(const frame_ptr& frames);\r
+private:\r
+       struct implementation;\r
+       std::shared_ptr<implementation> impl_;\r
+};\r
+typedef std::shared_ptr<frame_renderer> frame_renderer_ptr;\r
+\r
+}}
\ No newline at end of file
diff --git a/core/processor/frame_shader.cpp b/core/processor/frame_shader.cpp
new file mode 100644 (file)
index 0000000..00f5410
--- /dev/null
@@ -0,0 +1,243 @@
+#include "../StdAfx.h"\r
+\r
+#include "frame_shader.h"\r
+\r
+#include "../../common/exception/exceptions.h"\r
+#include "../../common/gl/utility.h"\r
+\r
+#include <Glee.h>\r
+\r
+#include <boost/noncopyable.hpp>\r
+\r
+#include <unordered_map>\r
+\r
+namespace caspar { namespace core {\r
+       \r
+class shader_program : boost::noncopyable\r
+{\r
+public:\r
+       shader_program() : program_(0){}\r
+       shader_program(shader_program&& other) : program_(other.program_){}\r
+       shader_program& operator=(shader_program&& other) \r
+       {\r
+               program_ = other.program_; \r
+               other.program_ = 0; \r
+               return *this;\r
+       }\r
+\r
+       shader_program(const std::string& fragment_source_str) : program_(0)\r
+       {\r
+               GLint success;\r
+\r
+               try\r
+               {               \r
+                       const char* fragment_source = fragment_source_str.c_str();\r
+                       static const char* vertex_source = \r
+                               "void main()"\r
+                               "{"\r
+                                       "gl_TexCoord[0] = gl_MultiTexCoord0;"\r
+                                       "gl_FrontColor = gl_Color;"\r
+                                       "gl_Position = ftransform();"\r
+                               "}";\r
+                       \r
+                       auto vertex_shader   = glCreateShaderObjectARB(GL_VERTEX_SHADER_ARB);\r
+                       auto fragmemt_shader = glCreateShaderObjectARB(GL_FRAGMENT_SHADER_ARB);\r
+\r
+                       GL(glShaderSourceARB(vertex_shader, 1, &vertex_source,   NULL));\r
+                       GL(glCompileShaderARB(vertex_shader));\r
+\r
+                       GL(glGetObjectParameterivARB(vertex_shader, GL_OBJECT_COMPILE_STATUS_ARB, &success));\r
+                       if (success == GL_FALSE)\r
+                       {\r
+                               char info[2048];\r
+                               GL(glGetInfoLogARB(vertex_shader, sizeof(info), 0, info));\r
+                               GL(glDeleteObjectARB(vertex_shader));\r
+                               GL(glDeleteObjectARB(fragmemt_shader));\r
+                               GL(glDeleteObjectARB(program_));\r
+                               std::stringstream str;\r
+                               str << "Failed to compile vertex shader:" << std::endl << info << std::endl;\r
+                               BOOST_THROW_EXCEPTION(common::gl::gl_error() << msg_info(str.str()));\r
+                       }\r
+\r
+                       GL(glShaderSourceARB(fragmemt_shader, 1, &fragment_source, NULL));\r
+                       GL(glCompileShaderARB(fragmemt_shader));\r
+\r
+                       GL(glGetObjectParameterivARB(fragmemt_shader, GL_OBJECT_COMPILE_STATUS_ARB, &success));\r
+                       if (success == GL_FALSE)\r
+                       {\r
+                               char info[2048];\r
+                               GL(glGetInfoLogARB(fragmemt_shader, sizeof(info), 0, info));\r
+                               GL(glDeleteObjectARB(vertex_shader));\r
+                               GL(glDeleteObjectARB(fragmemt_shader));\r
+                               GL(glDeleteObjectARB(program_));\r
+                               std::stringstream str;\r
+                               str << "Failed to compile fragment shader:" << std::endl << info << std::endl;\r
+                               BOOST_THROW_EXCEPTION(common::gl::gl_error() << msg_info(str.str()));\r
+                       }\r
+                       \r
+                       program_ = glCreateProgramObjectARB();\r
+\r
+                       GL(glAttachObjectARB(program_, vertex_shader));\r
+                       GL(glAttachObjectARB(program_, fragmemt_shader));\r
+\r
+                       GL(glDeleteObjectARB(vertex_shader));\r
+                       GL(glDeleteObjectARB(fragmemt_shader));\r
+\r
+                       GL(glLinkProgramARB(program_));\r
+\r
+                       GL(glGetObjectParameterivARB(program_, GL_OBJECT_LINK_STATUS_ARB, &success));\r
+                       if (success == GL_FALSE)\r
+                       {\r
+                               char info[2048];\r
+                               GL(glGetInfoLogARB(program_, sizeof(info), 0, info));\r
+                               GL(glDeleteObjectARB(program_));\r
+                               std::stringstream str;\r
+                               str << "Failed to link shader program:" << std::endl << info << std::endl;\r
+                               BOOST_THROW_EXCEPTION(common::gl::gl_error() << msg_info(str.str()));\r
+                       }\r
+                       GL(glUseProgramObjectARB(program_));\r
+                       glUniform1i(glGetUniformLocation(program_, "plane[0]"), 0);\r
+                       glUniform1i(glGetUniformLocation(program_, "plane[1]"), 1);\r
+                       glUniform1i(glGetUniformLocation(program_, "plane[2]"), 2);\r
+                       glUniform1i(glGetUniformLocation(program_, "plane[3]"), 3);\r
+               }\r
+               catch(...)\r
+               {\r
+                       CASPAR_LOG_CURRENT_EXCEPTION();\r
+                       throw;\r
+               }\r
+       }\r
+\r
+       ~shader_program()\r
+       {\r
+               glDeleteProgram(program_);\r
+       }\r
+\r
+       void use()\r
+       {       \r
+               GL(glUseProgramObjectARB(program_));            \r
+       }\r
+       \r
+private:\r
+       GLuint program_;\r
+};\r
+typedef std::shared_ptr<shader_program> shader_program_ptr;\r
+\r
+struct frame_shader::implementation\r
+{\r
+       implementation(const video_format_desc& format_desc) \r
+               : current_(pixel_format::invalid), format_desc_(format_desc)\r
+       {\r
+               std::string common = \r
+                       "uniform sampler2D      plane[4];                                                                                       "\r
+                       "uniform vec4           plane_size[4];                                                                          "\r
+                                                                                                                                                               \r
+                       // NOTE: YCbCr, ITU-R, http://www.intersil.com/data/an/an9717.pdf               \r
+                       // TODO: Support for more yuv formats might be needed.                                  \r
+                       "vec4 ycbcra_to_bgra(float y, float cb, float cr, float a)                              "\r
+                       "{                                                                                                                                              "\r
+                       "       vec4 color;                                                                                                                     "\r
+                       "                                                                                                                                               "\r
+                       "       cb -= 0.5;                                                                                                                      "\r
+                       "       cr -= 0.5;                                                                                                                      "\r
+                       "       y = 1.164*(y-0.0625);                                                                                           "\r
+                       "                                                                                                                                               "\r
+                       "       color.r = y + 1.596 * cr;                                                                                       "\r
+                       "       color.g = y - 0.813 * cr - 0.337633 * cb;                                                       "\r
+                       "       color.b = y + 2.017 * cb;                                                                                       "\r
+                       "       color.a = a;                                                                                                            "\r
+                       "                                                                                                                                               "\r
+                       "       return color;                                                                                                           "\r
+                       "}                                                                                                                                              ";\r
+                       \r
+               shaders_[pixel_format::abgr] = common +\r
+\r
+                       "void main()                                                                                                                    "\r
+                       "{                                                                                                                                              "\r
+                               "vec4 abgr = texture2D(plane[0], gl_TexCoord[0].st);                            "\r
+                               "gl_FragColor = abgr.argb * gl_Color;                                                           "\r
+                       "}                                                                                                                                              ";\r
+               \r
+               shaders_[pixel_format::argb] = common +\r
+\r
+                       "void main()                                                                                                                    "       \r
+                       "{                                                                                                                                              "\r
+                               "vec4 argb = texture2D(plane[0], gl_TexCoord[0].st);                            "\r
+                               "gl_FragColor = argb.grab * gl_Color;                                                           "       \r
+                       "}                                                                                                                                              ";\r
+               \r
+               shaders_[pixel_format::bgra] = common +\r
+\r
+                       "void main()                                                                                                                    "\r
+                       "{                                                                                                                                              "\r
+                               "vec4 bgra = texture2D(plane[0], gl_TexCoord[0].st);                            "\r
+                               "gl_FragColor = bgra.rgba * gl_Color;                                                           "\r
+                       "}                                                                                                                                              ";\r
+               \r
+               shaders_[pixel_format::rgba] = common +\r
+\r
+                       "void main()                                                                                                                    "\r
+                       "{                                                                                                                                              "\r
+                               "vec4 rgba = texture2D(plane[0], gl_TexCoord[0].st);                            "\r
+                               "gl_FragColor = rgba.bgra * gl_Color;                                                           "\r
+                       "}                                                                                                                                              ";\r
+               \r
+               shaders_[pixel_format::ycbcr] = common +\r
+\r
+                       "void main()                                                                                                                    "\r
+                       "{                                                                                                                                              "\r
+                               "float y  = texture2D(plane[0], gl_TexCoord[0].st).r;                           "\r
+                               "float cb = texture2D(plane[1], gl_TexCoord[0].st).r;                           "\r
+                               "float cr = texture2D(plane[2], gl_TexCoord[0].st).r;                           "\r
+                               "float a = 1.0;                                                                                                         "       \r
+                               "gl_FragColor = ycbcra_to_bgra(y, cb, cr, a) * gl_Color;                        "\r
+                       "}                                                                                                                                              ";\r
+               \r
+               shaders_[pixel_format::ycbcra] = common +\r
+\r
+                       "void main()                                                                                                                    "\r
+                       "{                                                                                                                                              "\r
+                               "float y  = texture2D(plane[0], gl_TexCoord[0].st).r;                           "\r
+                               "float cb = texture2D(plane[1], gl_TexCoord[0].st).r;                           "\r
+                               "float cr = texture2D(plane[2], gl_TexCoord[0].st).r;                           "\r
+                               "float a  = texture2D(plane[3], gl_TexCoord[0].st).r;                           "\r
+                               "gl_FragColor = ycbcra_to_bgra(y, cb, cr, a) * gl_Color;                        "\r
+                       "}                                                                                                                                              ";\r
+       }\r
+\r
+       void use(const pixel_format_desc& desc)\r
+       {\r
+               set_pixel_format(desc.pix_fmt);\r
+//             set_size(desc);\r
+       }\r
+\r
+       void set_pixel_format(pixel_format::type format)\r
+       {\r
+               if(current_ == format)\r
+                       return;\r
+               current_ = format;\r
+               shaders_[format].use();\r
+       }\r
+\r
+       //void set_size(pixel_format_desc& desc)\r
+       //{\r
+       //      for(int n = 0; n < 4; ++n)\r
+       //      {\r
+       //              std::string name = std::string("plane_size[") + boost::lexical_cast<std::string>(n) + "]";\r
+       //              GL(glUniform4f(shaders_[current_].get_location(name), \r
+       //                      static_cast<float>(desc.planes[n].width), \r
+       //                      static_cast<float>(desc.planes[n].height),\r
+       //                      1.0f/static_cast<float>(desc.planes[n].width),\r
+       //                      1.0f/static_cast<float>(desc.planes[n].height)));\r
+       //      }\r
+       //}     \r
+\r
+       video_format_desc format_desc_;\r
+       pixel_format::type current_;\r
+       std::unordered_map<pixel_format::type, shader_program> shaders_;\r
+};\r
+\r
+frame_shader::frame_shader(const video_format_desc& format_desc) : impl_(new implementation(format_desc)){}\r
+void frame_shader::use(const pixel_format_desc& desc){impl_->use(desc);}\r
+\r
+}}
\ No newline at end of file
diff --git a/core/processor/frame_shader.h b/core/processor/frame_shader.h
new file mode 100644 (file)
index 0000000..64fd493
--- /dev/null
@@ -0,0 +1,23 @@
+#pragma once\r
+\r
+#include "../video/video_format.h"\r
+#include "../video/pixel_format.h"\r
+\r
+#include <memory>\r
+#include <array>\r
+\r
+namespace caspar { namespace core {\r
+       \r
+class frame_shader\r
+{\r
+public:\r
+       frame_shader(const video_format_desc& format_desc);\r
+       void use(const pixel_format_desc& image);\r
+\r
+private:\r
+       struct implementation;\r
+       std::shared_ptr<implementation> impl_;\r
+};\r
+typedef std::shared_ptr<frame_shader> frame_shader_ptr;\r
+\r
+}}
\ No newline at end of file
index 59f2f6076087498a6e133f166665dce9d766569c..4fcdb7e4b5d80305bf1c469e9a9866a6bb1432e4 100644 (file)
@@ -22,7 +22,7 @@
 \r
 #include "color_producer.h"\r
 \r
-#include "../../frame/frame_format.h"\r
+#include "../../video/video_format.h"\r
 \r
 #include <intrin.h>\r
 #pragma intrinsic(__movsd, __stosd)\r
@@ -32,32 +32,29 @@ namespace caspar { namespace core {
 class color_producer : public frame_producer\r
 {\r
 public:\r
-       explicit color_producer(unsigned int color_value, const frame_format_desc& format_desc\r
-               : color_value_(color_value), format_desc_(format_desc){}\r
+       explicit color_producer(unsigned int color_value) \r
+               : color_value_(color_value){}\r
 \r
        ~color_producer()\r
        {\r
-               if(factory_)\r
-                       factory_->release_frames(this);\r
+               if(frame_processor_)\r
+                       frame_processor_->release_tag(this);\r
        }\r
 \r
-       gpu_frame_ptr render_frame()\r
+       frame_ptr render_frame()\r
        { \r
                return frame_;\r
        }\r
 \r
-       const frame_format_desc& get_frame_format_desc() const { return format_desc_; }\r
-       \r
-       void initialize(const frame_factory_ptr& factory)\r
+       void initialize(const frame_processor_device_ptr& frame_processor)\r
        {\r
-               factory_ = factory;\r
-               frame_ = factory->create_frame(format_desc_, this);\r
-               __stosd(reinterpret_cast<unsigned long*>(frame_->data()), color_value_, format_desc_.size / sizeof(unsigned long));\r
+               frame_processor_ = frame_processor;\r
+               frame_ = frame_processor->create_frame(this);\r
+               __stosd(reinterpret_cast<unsigned long*>(frame_->data()), color_value_, frame_->size() / sizeof(unsigned long));\r
        }\r
 \r
-       frame_factory_ptr factory_;\r
-       frame_format_desc format_desc_;\r
-       gpu_frame_ptr frame_;\r
+       frame_processor_device_ptr frame_processor_;\r
+       frame_ptr frame_;\r
        unsigned int color_value_;\r
 };\r
 \r
@@ -94,11 +91,11 @@ unsigned int get_pixel_color_value(const std::wstring& parameter)
        return color.value;\r
 }\r
 \r
-frame_producer_ptr create_color_producer(const std::vector<std::wstring>& params, const frame_format_desc& format_desc)\r
+frame_producer_ptr create_color_producer(const std::vector<std::wstring>& params)\r
 {\r
        if(params.empty() || params[0].at(0) != '#')\r
                return nullptr;\r
-       return std::make_shared<color_producer>(get_pixel_color_value(params[0]), format_desc);\r
+       return std::make_shared<color_producer>(get_pixel_color_value(params[0]));\r
 }\r
 \r
 }}
\ No newline at end of file
index ccef8d773b13c145aeddabf884ebad1e1b88d5f5..65607bbe2f83732cced17826fff457fa308d7c01 100644 (file)
@@ -26,6 +26,6 @@
 \r
 namespace caspar { namespace core {\r
        \r
-frame_producer_ptr create_color_producer(const std::vector<std::wstring>& params, const frame_format_desc& format_desc);\r
+frame_producer_ptr create_color_producer(const std::vector<std::wstring>& params);\r
 \r
 }}\r
index b27b0673cf6cd65b135037f4d7624139e82338f6..a603a043207f1de8878e178c74b7fe8230baa7c2 100644 (file)
@@ -27,7 +27,7 @@ extern "C"
 #include "video/video_decoder.h"\r
 #include "video/video_transformer.h"\r
 \r
-#include "../../frame/frame_format.h"\r
+#include "../../video/video_format.h"\r
 #include "../../../common/utility/find_file.h"\r
 #include "../../../common/utility/memory.h"\r
 #include "../../../common/utility/scope_exit.h"\r
@@ -49,16 +49,16 @@ namespace caspar { namespace core { namespace ffmpeg{
 struct ffmpeg_producer : public frame_producer\r
 {\r
 public:\r
-       ffmpeg_producer(const std::wstring& filename, const  std::vector<std::wstring>& params, const frame_format_desc& format_desc\r
-               : filename_(filename), format_desc_(format_desc)\r
+       ffmpeg_producer(const std::wstring& filename, const  std::vector<std::wstring>& params) \r
+               : filename_(filename)\r
        {\r
-       if(!boost::filesystem::exists(filename))\r
-               BOOST_THROW_EXCEPTION(file_not_found() <<  boost::errinfo_file_name(common::narrow(filename)));\r
+               if(!boost::filesystem::exists(filename))\r
+                       BOOST_THROW_EXCEPTION(file_not_found() <<  boost::errinfo_file_name(common::narrow(filename)));\r
                \r
                static boost::once_flag flag = BOOST_ONCE_INIT;\r
                boost::call_once(av_register_all, flag);        \r
                                \r
-               input_.reset(new input(format_desc_));\r
+               input_.reset(new input());\r
                input_->set_loop(std::find(params.begin(), params.end(), L"LOOP") != params.end());\r
                input_->load(common::narrow(filename_));\r
                video_decoder_.reset(new video_decoder());\r
@@ -76,12 +76,12 @@ public:
                input_->start();\r
        }\r
                \r
-       void initialize(const frame_factory_ptr& factory)\r
+       void initialize(const frame_processor_device_ptr& frame_processor)\r
        {\r
-               video_transformer_->initialize(factory);\r
+               video_transformer_->initialize(frame_processor);\r
        }\r
                \r
-       gpu_frame_ptr render_frame()\r
+       frame_ptr render_frame()\r
        {\r
                while(ouput_channel_.empty() && !input_->is_eof())\r
                {                                                                               \r
@@ -115,13 +115,13 @@ public:
                                        audio_chunk_channel_.pop_front();\r
                                }\r
                                \r
-                               gpu_frame_ptr frame = video_frame_channel_.front();\r
+                               frame_ptr frame = video_frame_channel_.front();\r
                                video_frame_channel_.pop_front();\r
                                ouput_channel_.push(std::move(frame));\r
                        }                               \r
                }\r
 \r
-               gpu_frame_ptr frame;\r
+               frame_ptr frame;\r
                if(!ouput_channel_.empty())\r
                {\r
                        frame = ouput_channel_.front();\r
@@ -129,9 +129,7 @@ public:
                }\r
                return frame;\r
        }\r
-\r
-       const frame_format_desc& get_frame_format_desc() const { return format_desc_; }\r
-               \r
+                       \r
        bool has_audio_;\r
 \r
        // Filter 1 : Input\r
@@ -141,27 +139,26 @@ public:
        video_decoder_uptr                                      video_decoder_;\r
        video_transformer_uptr                          video_transformer_;\r
        //std::deque<video_packet_ptr>          videoDecodedPacketChannel_;\r
-       std::deque<gpu_frame_ptr>                       video_frame_channel_;\r
+       std::deque<frame_ptr>                   video_frame_channel_;\r
        \r
        // Filter 3 : Audio Decoding\r
        audio_decoder_uptr                                      audio_decoder_;\r
        std::deque<std::vector<short>>          audio_chunk_channel_;\r
 \r
        // Filter 4 : Merge Video and Audio\r
-       std::queue<gpu_frame_ptr>                       ouput_channel_;\r
+       std::queue<frame_ptr>                   ouput_channel_;\r
        \r
        std::wstring                                            filename_;\r
-       frame_format_desc                                       format_desc_;\r
 };\r
 \r
-frame_producer_ptr create_ffmpeg_producer(const  std::vector<std::wstring>& params, const frame_format_desc& format_desc)\r
+frame_producer_ptr create_ffmpeg_producer(const  std::vector<std::wstring>& params)\r
 {\r
        std::wstring filename = params[0];\r
        std::wstring result_filename = common::find_file(server::media_folder() + filename, list_of(L"mpg")(L"avi")(L"mov")(L"dv")(L"wav")(L"mp3")(L"mp4")(L"f4v")(L"flv"));\r
        if(result_filename.empty())\r
                return nullptr;\r
 \r
-       return std::make_shared<ffmpeg_producer>(result_filename, params, format_desc);\r
+       return std::make_shared<ffmpeg_producer>(result_filename, params);\r
 }\r
 \r
 }}}
\ No newline at end of file
index 233a085930fcb7b107b4caa1c0d25ac39a25fd22..bee1e01b623dbeff118bcd197bf6bfd316f596c2 100644 (file)
@@ -7,6 +7,6 @@
 \r
 namespace caspar { namespace core { namespace ffmpeg {\r
        \r
-frame_producer_ptr create_ffmpeg_producer(const  std::vector<std::wstring>& params, const frame_format_desc& format_desc);\r
+frame_producer_ptr create_ffmpeg_producer(const  std::vector<std::wstring>& params);\r
 \r
 }}}
\ No newline at end of file
index 4032d73483294a55684135c261352c0e94b912ac..1af0b279efe6aa1dc25368834658dd829c6c1e36 100644 (file)
@@ -2,7 +2,7 @@
 \r
 #include "input.h"\r
 \r
-#include "../../frame/frame_format.h"\r
+#include "../../video/video_format.h"\r
 #include "../../../common/utility/memory.h"\r
 #include "../../../common/utility/scope_exit.h"\r
 \r
@@ -18,8 +18,8 @@ namespace caspar { namespace core { namespace ffmpeg{
                \r
 struct input::implementation : boost::noncopyable\r
 {\r
-       implementation(const frame_format_desc& format_desc\r
-               : video_frame_rate_(25.0), video_s_index_(-1), audio_s_index_(-1), video_codec_(nullptr), audio_codec_(nullptr), format_desc_(format_desc)\r
+       implementation() \r
+               : video_frame_rate_(25.0), video_s_index_(-1), audio_s_index_(-1), video_codec_(nullptr), audio_codec_(nullptr)\r
        {\r
                loop_ = false;\r
                //file_buffer_size_ = 0;                \r
@@ -142,7 +142,7 @@ struct input::implementation : boost::noncopyable
                        {\r
                                if(packet->stream_index == video_s_index_)              \r
                                {\r
-                                       video_packet_buffer_.push(std::make_shared<video_packet>(packet, format_desc_, video_codec_context_.get(), video_codec_)); // NOTE: video_packet makes a copy of AVPacket\r
+                                       video_packet_buffer_.push(std::make_shared<video_packet>(packet, video_codec_context_.get(), video_codec_)); // NOTE: video_packet makes a copy of AVPacket\r
                                        //file_buffer_size_ += packet->size;\r
                                }\r
                                else if(packet->stream_index == audio_s_index_)         \r
@@ -238,11 +238,9 @@ struct input::implementation : boost::noncopyable
        tbb::atomic<bool> is_running_;\r
 \r
        double video_frame_rate_;\r
-\r
-       frame_format_desc format_desc_;\r
 };\r
 \r
-input::input(const frame_format_desc& format_desc) : impl_(new implementation(format_desc)){}\r
+input::input() : impl_(new implementation()){}\r
 void input::load(const std::string& filename){impl_->load(filename);}\r
 void input::set_loop(bool value){impl_->loop_ = value;}\r
 const std::shared_ptr<AVCodecContext>& input::get_video_codec_context() const{return impl_->video_codec_context_;}\r
index acb30f668dfc8f432fd348f68885637ecc94ece2..4c0beec0829dcc74c23cd55fc34411d5b8f08436 100644 (file)
@@ -3,7 +3,6 @@
 #include "packet.h"\r
 \r
 #include <system_error>\r
-#include "../../frame/frame_fwd.h"\r
 \r
 namespace caspar { namespace core { namespace ffmpeg{  \r
        \r
@@ -12,7 +11,7 @@ typedef std::shared_ptr<AVFormatContext> AVFormatContextPtr;
 class input : boost::noncopyable\r
 {\r
 public:\r
-       input(const frame_format_desc& format_desc);\r
+       input();\r
        void load(const std::string& filename);\r
        const std::shared_ptr<AVCodecContext>& get_video_codec_context() const;\r
        const std::shared_ptr<AVCodecContext>& get_audio_codec_context() const;\r
index fc2bf90464069cd31d8b82ccfb3a9e1d07fc4d48..2df954d55b1a11214187a69ee640d529e87651a0 100644 (file)
@@ -1,7 +1,7 @@
 #pragma once\r
 \r
-#include "../../frame/gpu_frame.h"\r
-#include "../../frame/frame_format.h"\r
+#include "../../processor/frame.h"\r
+#include "../../video/video_format.h"\r
 \r
 #include <tbb/scalable_allocator.h>\r
 #include <type_traits>\r
@@ -29,8 +29,8 @@ struct ffmpeg_error: virtual boost::exception, virtual std::exception { };
 \r
 struct video_packet : boost::noncopyable\r
 {\r
-       video_packet(const AVPacketPtr& packet, const frame_format_desc& format_desc, AVCodecContext* codec_context, AVCodec* codec) \r
-               :  size(packet->size), codec_context(codec_context), codec(codec), format_desc(format_desc), \r
+       video_packet(const AVPacketPtr& packet, AVCodecContext* codec_context, AVCodec* codec) \r
+               :  size(packet->size), codec_context(codec_context), codec(codec), \r
                        data(static_cast<uint8_t*>(scalable_aligned_malloc(packet->size, 16)))\r
        {\r
                memcpy(const_cast<uint8_t*>(data), packet->data, packet->size);\r
@@ -45,9 +45,8 @@ struct video_packet : boost::noncopyable
        const uint8_t* const                    data;\r
        AVCodecContext* const                   codec_context;\r
        const AVCodec* const                    codec;\r
-       gpu_frame_ptr                                           frame;\r
+       frame_ptr                                               frame;\r
        AVFramePtr                                              decoded_frame;\r
-       const frame_format_desc&                format_desc;\r
 };     \r
 typedef std::shared_ptr<video_packet> video_packet_ptr;\r
 \r
index 70543bae9d0b01af6686737a0ccdecd18114a7ef..2849f872da18b5a42ee003e715f5780787aeb659 100644 (file)
@@ -2,11 +2,11 @@
 \r
 #include "video_transformer.h"\r
 \r
-#include "../../../frame/frame_format.h"\r
+#include "../../../video/video_format.h"\r
 #include "../../../../common/utility/memory.h"\r
-#include "../../../frame/gpu_frame.h"\r
-#include "../../../frame/gpu_frame.h"\r
-#include "../../../frame/frame_factory.h"\r
+#include "../../../processor/frame.h"\r
+#include "../../../processor/frame.h"\r
+#include "../../../processor/frame_processor_device.h"\r
 \r
 #include <tbb/parallel_for.h>\r
 #include <tbb/atomic.h>\r
@@ -25,7 +25,7 @@ extern "C"
 \r
 namespace caspar { namespace core { namespace ffmpeg{\r
        \r
-pixel_format get_pixel_format(PixelFormat pix_fmt)\r
+pixel_format::type get_pixel_format(PixelFormat pix_fmt)\r
 {\r
        switch(pix_fmt)\r
        {\r
@@ -39,7 +39,7 @@ pixel_format get_pixel_format(PixelFormat pix_fmt)
                case PIX_FMT_YUV411P:   return pixel_format::ycbcr;\r
                case PIX_FMT_YUV410P:   return pixel_format::ycbcr;\r
                case PIX_FMT_YUVA420P:  return pixel_format::ycbcra;\r
-               default:                                return pixel_format::invalid_pixel_format;\r
+               default:                                return pixel_format::invalid;\r
        }\r
 }\r
 \r
@@ -49,8 +49,8 @@ struct video_transformer::implementation : boost::noncopyable
 \r
        ~implementation()\r
        {\r
-               if(factory_)\r
-                       factory_->release_frames(this);\r
+               if(frame_processor_)\r
+                       frame_processor_->release_tag(this);\r
        }\r
 \r
        video_packet_ptr execute(const video_packet_ptr video_packet)\r
@@ -68,7 +68,7 @@ struct video_transformer::implementation : boost::noncopyable
                case PIX_FMT_RGBA:\r
                case PIX_FMT_ABGR:\r
                        {\r
-                               video_packet->frame = factory_->create_frame(width, height, this);\r
+                               video_packet->frame = frame_processor_->create_frame(width, height, this);\r
                                tbb::parallel_for(0, height, 1, [&](int y)\r
                                {\r
                                        common::aligned_memcpy(\r
@@ -95,23 +95,22 @@ struct video_transformer::implementation : boost::noncopyable
                                size_t size2 = dummy_pict.data[2] - dummy_pict.data[1];\r
                                size_t h2 = size2/dummy_pict.linesize[1];\r
 \r
-                               gpu_frame_desc desc;\r
-                               desc.planes[0] = plane(dummy_pict.linesize[0], height, 1);\r
-                               desc.planes[1] = plane(dummy_pict.linesize[1], h2, 1);\r
-                               desc.planes[2] = plane(dummy_pict.linesize[2], h2, 1);\r
-                               desc.plane_count = 3;\r
+                               pixel_format_desc desc;\r
+                               desc.planes[0] = pixel_format_desc::plane(dummy_pict.linesize[0], height, 1);\r
+                               desc.planes[1] = pixel_format_desc::plane(dummy_pict.linesize[1], h2, 1);\r
+                               desc.planes[2] = pixel_format_desc::plane(dummy_pict.linesize[2], h2, 1);\r
 \r
-                               if(pix_fmt == PIX_FMT_YUVA420P)                 \r
-                               {\r
-                                       desc.planes[3] = plane(dummy_pict.linesize[3], height, 1);\r
-                                       desc.plane_count = 4;\r
-                               }\r
+                               if(pix_fmt == PIX_FMT_YUVA420P)                                         \r
+                                       desc.planes[3] = pixel_format_desc::plane(dummy_pict.linesize[3], height, 1);                           \r
 \r
                                desc.pix_fmt = get_pixel_format(pix_fmt);\r
-                               video_packet->frame = factory_->create_frame(desc, this);\r
+                               video_packet->frame = frame_processor_->create_frame(desc, this);\r
 \r
-                               tbb::parallel_for(0, static_cast<int>(desc.plane_count), 1, [&](int n)\r
+                               tbb::parallel_for(0, static_cast<int>(desc.planes.size()), 1, [&](int n)\r
                                {\r
+                                       if(desc.planes[n].size == 0)\r
+                                               return;\r
+\r
                                        tbb::parallel_for(0, static_cast<int>(desc.planes[n].height), 1, [&](int y)\r
                                        {\r
                                                memcpy(\r
@@ -129,7 +128,7 @@ struct video_transformer::implementation : boost::noncopyable
                                        CASPAR_LOG(warning) << "Hardware accelerated color transform not supported.";\r
                                        sw_warning_ = true;\r
                                }\r
-                               video_packet->frame = factory_->create_frame(width, height, this);\r
+                               video_packet->frame = frame_processor_->create_frame(width, height, this);\r
 \r
                                AVFrame av_frame;       \r
                                avcodec_get_frame_defaults(&av_frame);\r
@@ -145,23 +144,24 @@ struct video_transformer::implementation : boost::noncopyable
                        }\r
                }\r
 \r
+               // TODO:\r
                if(video_packet->codec->id == CODEC_ID_DVVIDEO) // Move up one field\r
-                       video_packet->frame->translate(0.0f, 1.0/static_cast<double>(video_packet->format_desc.height));\r
+                       video_packet->frame->translate(0.0f, 1.0/static_cast<double>(frame_processor_->get_video_format_desc().height));\r
                \r
                return video_packet;\r
        }\r
 \r
-       void initialize(const frame_factory_ptr& factory)\r
+       void initialize(const frame_processor_device_ptr& frame_processor)\r
        {\r
-               factory_ = factory;\r
+               frame_processor_ = frame_processor;\r
        }\r
 \r
-       frame_factory_ptr factory_;\r
+       frame_processor_device_ptr frame_processor_;\r
        std::shared_ptr<SwsContext> sws_context_;\r
        bool sw_warning_;\r
 };\r
 \r
 video_transformer::video_transformer() : impl_(new implementation()){}\r
 video_packet_ptr video_transformer::execute(const video_packet_ptr& video_packet){return impl_->execute(video_packet);}\r
-void video_transformer::initialize(const frame_factory_ptr& factory){impl_->initialize(factory); }\r
+void video_transformer::initialize(const frame_processor_device_ptr& frame_processor){impl_->initialize(frame_processor); }\r
 }}}
\ No newline at end of file
index 61803538e93c35daba709e96b794810093c7e3b4..8ffe249be2b0223d27ba869774af9862693f5a0f 100644 (file)
@@ -2,7 +2,7 @@
 \r
 #include "../packet.h"\r
 \r
-#include "../../../frame/frame_fwd.h"\r
+#include "../../../processor/frame_processor_device.h"\r
 \r
 namespace caspar { namespace core { namespace ffmpeg{\r
 \r
@@ -11,7 +11,7 @@ class video_transformer : boost::noncopyable
 public:\r
        video_transformer();\r
        video_packet_ptr execute(const video_packet_ptr& video_packet); \r
-       void initialize(const frame_factory_ptr& factory);\r
+       void initialize(const frame_processor_device_ptr& frame_processor);\r
 private:\r
        struct implementation;\r
        std::shared_ptr<implementation> impl_;\r
index ddb966ecf094f98f42f95c66be54d3804da0dff9..b95369d5ee1afabd1565c16a918d713d921e06a2 100644 (file)
@@ -21,7 +21,7 @@
 #include "..\..\stdafx.h"\r
 \r
 #include "FlashAxContainer.h"\r
-#include "..\..\frame\frame_format.h"\r
+#include "..\..\video\video_format.h"\r
 #include "flash_producer.h"\r
 #include "TimerHelper.h"\r
 \r
@@ -774,7 +774,7 @@ HRESULT FlashAxContainer::CreateAxControl()
        return S_OK;\r
 }\r
 \r
-HRESULT FlashAxContainer::SetFormat(const frame_format_desc& format_desc) \r
+HRESULT FlashAxContainer::SetFormat(const video_format_desc& format_desc) \r
 {\r
        if(m_spInPlaceObjectWindowless == nullptr)\r
                return E_FAIL;\r
@@ -827,7 +827,7 @@ bool FlashAxContainer::DrawControl(HDC targetDC)
        assert(SUCCEEDED(hr));\r
        bInvalidRect_ = false;\r
 \r
-/*     const frame_format_desc& format_desc = frame_format_desc::format_descs[format_];\r
+/*     const video_format_desc& format_desc = video_format_desc::format_descs[format_];\r
 \r
        //Trying to redraw just the dirty rectangles. Doesn't seem to work when the movie uses "filters", such as glow, dropshadow etc.\r
        std::vector<flash::DirtyRect>::iterator it = bDirtyRects_.begin();\r
index dd94080b6441e07ab27f4ef9c8faf5a1839c7522..d480006dee6c43846551fc12b2d7025db61367b2 100644 (file)
@@ -35,8 +35,8 @@
 \r
 #pragma warning(push)\r
 \r
-#include "..\..\frame\gpu_frame.h"\r
-#include "..\..\frame\frame_format.h"\r
+#include "..\..\processor\frame.h"\r
+#include "..\..\video\video_format.h"\r
 \r
 #include <ocmm.h>\r
 #include <vector>\r
@@ -259,7 +259,7 @@ public:
        flash::flash_producer* pflash_producer_;\r
        std::vector<DirtyRect> bDirtyRects_;\r
 \r
-       HRESULT SetFormat(const frame_format_desc&);\r
+       HRESULT SetFormat(const video_format_desc&);\r
        bool IsReadyToRender() const;\r
        void EnterFullscreen();\r
 \r
index 362ad9a41b6b76a269dbbe75511ff84fb4812f7d..fb34d92d80799a433832f3613959ea61922b1f9e 100644 (file)
@@ -7,9 +7,9 @@
 #include "cg_producer.h"\r
 #include "flash_producer.h"\r
 \r
-#include "../../renderer/render_device.h"\r
-#include "../../frame/frame_format.h"\r
-#include "../../frame/gpu_frame.h"\r
+#include "../../producer/frame_producer_device.h"\r
+#include "../../video/video_format.h"\r
+#include "../../processor/frame.h"\r
 #include "../../Server.h"\r
 \r
 #include <boost/filesystem.hpp>\r
@@ -153,23 +153,23 @@ struct cg_producer::implementation : boost::noncopyable
 {\r
 public:\r
 \r
-       implementation(const frame_format_desc& fmtDesc) : format_desc_(fmtDesc)\r
+       implementation()\r
        {\r
                if(boost::filesystem::exists(server::template_folder()+TEXT("cg.fth.18")))\r
                {\r
-                       flash_producer_ = std::make_shared<flash_producer>(server::template_folder()+TEXT("cg.fth.18"), fmtDesc);\r
+                       flash_producer_ = std::make_shared<flash_producer>(server::template_folder()+TEXT("cg.fth.18"));\r
                        proxy_.reset(new flash_cg_proxy18());\r
                        CASPAR_LOG(info) << L"Running version 1.8 template graphics.";\r
                }\r
                else if(boost::filesystem::exists(server::template_folder()+TEXT("cg.fth.17")))\r
                {\r
-                       flash_producer_ = std::make_shared<flash_producer>(server::template_folder()+TEXT("cg.fth.17"), fmtDesc);\r
+                       flash_producer_ = std::make_shared<flash_producer>(server::template_folder()+TEXT("cg.fth.17"));\r
                        proxy_.reset(new flash_cg_proxy17());\r
                        CASPAR_LOG(info) << L"Running version 1.7 template graphics.";\r
                }\r
                else if(boost::filesystem::exists(server::template_folder()+TEXT("cg.fth"))) \r
                {\r
-                       flash_producer_ = std::make_shared<flash_producer>(server::template_folder()+TEXT("cg.fth"), fmtDesc);\r
+                       flash_producer_ = std::make_shared<flash_producer>(server::template_folder()+TEXT("cg.fth"));\r
                        proxy_.reset(new flash_cg_proxy16());\r
                        CASPAR_LOG(info) << L"Running version 1.6 template graphics.";\r
                }\r
@@ -239,42 +239,41 @@ public:
                flash_producer_->param(proxy_->invoke(layer, label));\r
        }\r
 \r
-       gpu_frame_ptr render_frame()\r
+       frame_ptr render_frame()\r
        {\r
                return flash_producer_ ? flash_producer_->render_frame() : nullptr;\r
        }\r
                \r
-       void initialize(const frame_factory_ptr& factory)\r
+       void initialize(const frame_processor_device_ptr& frame_processor)\r
        {\r
-               factory_ = factory;\r
+               frame_processor_ = frame_processor;\r
                if(flash_producer_)\r
-                       flash_producer_->initialize(factory_);\r
+                       flash_producer_->initialize(frame_processor_);\r
        }\r
 \r
-       frame_format_desc format_desc_;\r
        flash_producer_ptr flash_producer_;\r
        std::unique_ptr<flash_cg_proxy> proxy_;\r
-       frame_factory_ptr factory_;\r
+       frame_processor_device_ptr frame_processor_;\r
 };\r
        \r
 // This is somewhat a hack... needs redesign\r
-cg_producer_ptr get_default_cg_producer(const renderer::render_device_ptr& render_device, unsigned int render_layer)\r
+cg_producer_ptr get_default_cg_producer(const channel_ptr& channel, unsigned int render_layer)\r
 {\r
-       if(!render_device)\r
-               BOOST_THROW_EXCEPTION(null_argument() << msg_info("render_device"));\r
+       if(!channel)\r
+               BOOST_THROW_EXCEPTION(null_argument() << msg_info("channel"));\r
        \r
-       auto producer = std::dynamic_pointer_cast<cg_producer>(render_device->active(render_layer));\r
+       auto producer = std::dynamic_pointer_cast<cg_producer>(channel->active(render_layer));\r
        if(!producer)\r
        {\r
-               producer = std::make_shared<cg_producer>(render_device->get_frame_format_desc());               \r
-               render_device->load(render_layer, producer, renderer::load_option::auto_play); \r
+               producer = std::make_shared<cg_producer>();             \r
+               channel->load(render_layer, producer, load_option::auto_play); \r
        }\r
        \r
        return producer;\r
 }\r
 \r
-cg_producer::cg_producer(const frame_format_desc& fmtDesc) : impl_(new implementation(fmtDesc)){}\r
-gpu_frame_ptr cg_producer::render_frame(){return impl_->render_frame();}\r
+cg_producer::cg_producer() : impl_(new implementation()){}\r
+frame_ptr cg_producer::render_frame(){return impl_->render_frame();}\r
 void cg_producer::clear(){impl_->clear();}\r
 void cg_producer::add(int layer, const std::wstring& templateName,  bool playOnLoad, const std::wstring& startFromLabel, const std::wstring& data){impl_->add(layer, templateName, playOnLoad, startFromLabel, data);}\r
 void cg_producer::remove(int layer){impl_->remove(layer);}\r
@@ -283,6 +282,5 @@ void cg_producer::stop(int layer, unsigned int mixOutDuration){impl_->stop(layer
 void cg_producer::next(int layer){impl_->next(layer);}\r
 void cg_producer::update(int layer, const std::wstring& data){impl_->update(layer, data);}\r
 void cg_producer::invoke(int layer, const std::wstring& label){impl_->invoke(layer, label);}\r
-const frame_format_desc& cg_producer::get_frame_format_desc() const { return impl_->format_desc_; }\r
-void cg_producer::initialize(const frame_factory_ptr& factory){impl_->initialize(factory);}\r
+void cg_producer::initialize(const frame_processor_device_ptr& frame_processor){impl_->initialize(frame_processor);}\r
 }}}
\ No newline at end of file
index 1fdb7428a134f182b60e3fdb486f32c4a3439528..997f5cd311847f93214822af4d947e0708c1325f 100644 (file)
@@ -1,17 +1,17 @@
 #pragma once\r
 \r
 #include "../frame_producer.h"\r
-#include "../../frame/frame_fwd.h"\r
-#include "../../renderer/render_device.h"\r
+#include "../../video/video_format.h"\r
+#include "../../channel.h"\r
 \r
 namespace caspar { namespace core { namespace flash{\r
                \r
 class cg_producer : public frame_producer\r
 {\r
 public:\r
-       cg_producer(const frame_format_desc& format_desc);\r
+       cg_producer();\r
        \r
-       gpu_frame_ptr render_frame();\r
+       frame_ptr render_frame();\r
 \r
        void clear();\r
        void add(int layer, const std::wstring& template_name,  bool play_on_load, const std::wstring& start_from_label = TEXT(""), const std::wstring& data = TEXT(""));\r
@@ -22,8 +22,8 @@ public:
        void update(int layer, const std::wstring& data);\r
        void invoke(int layer, const std::wstring& label);\r
 \r
-       const frame_format_desc& get_frame_format_desc() const;\r
-       void initialize(const frame_factory_ptr& factory);\r
+       const video_format_desc& get_video_format_desc() const;\r
+       void initialize(const frame_processor_device_ptr& frame_processor);\r
 private:\r
        struct implementation;\r
        std::shared_ptr<implementation> impl_;\r
@@ -32,6 +32,6 @@ typedef std::shared_ptr<cg_producer> cg_producer_ptr;
 \r
 static const unsigned int CG_DEFAULT_LAYER = 5000;\r
 \r
-cg_producer_ptr get_default_cg_producer(const renderer::render_device_ptr& render_device, unsigned int layer_index = CG_DEFAULT_LAYER);\r
+cg_producer_ptr get_default_cg_producer(const channel_ptr& channel, unsigned int layer_index = CG_DEFAULT_LAYER);\r
 \r
 }}}
\ No newline at end of file
index 14ad97b42cdcc5235c66c99ce2d5bbbde5c697d2..3eb1e4f4706115075c7824e469aa22221a10a2ca 100644 (file)
@@ -25,7 +25,7 @@
 #include "cg_producer.h"\r
 \r
 #include "../../../common/utility/find_file.h"\r
-#include "../../frame/gpu_frame.h"\r
+#include "../../processor/frame.h"\r
 #include "../../server.h"\r
 \r
 #include <boost/assign/list_of.hpp>\r
@@ -34,7 +34,7 @@ using namespace boost::assign;
 \r
 namespace caspar { namespace core { namespace flash {\r
        \r
-frame_producer_ptr create_ct_producer(const std::vector<std::wstring>& params, const frame_format_desc& format_desc\r
+frame_producer_ptr create_ct_producer(const std::vector<std::wstring>& params) \r
 {\r
        std::wstring filename = params[0];\r
        std::wstring result_filename = common::find_file(server::media_folder() + filename, list_of(L"ct"));\r
@@ -46,7 +46,7 @@ frame_producer_ptr create_ct_producer(const std::vector<std::wstring>& params, c
        while((pos = fixed_filename.find(TEXT('\\'), pos)) != std::wstring::npos) \r
                fixed_filename[pos] = TEXT('/');\r
        \r
-       cg_producer_ptr cg_producer(new cg_producer(format_desc));\r
+       cg_producer_ptr cg_producer(new cg_producer());\r
        cg_producer->add(0, filename, 1);\r
        return cg_producer;\r
 }\r
index 50edc9a854ce3ee2fd28270c7e2aff7358fd3a01..5e54a097c0b2e4dc82bfd7188173676e4f05bec5 100644 (file)
@@ -23,6 +23,6 @@
 \r
 namespace caspar { namespace core { namespace flash{\r
                \r
-frame_producer_ptr create_ct_producer(const std::vector<std::wstring>& params, const frame_format_desc& format_desc);\r
+frame_producer_ptr create_ct_producer(const std::vector<std::wstring>& params);\r
 \r
 }}}
\ No newline at end of file
index 03c835b6655d16d392383b11ecbd8a1f84518849..b20646223155f77feabb1b8764e7c52a64f49941 100644 (file)
 #include "TimerHelper.h"\r
 #include "bitmap.h"\r
 \r
-#include "../../frame/frame_format.h"\r
+#include "../../video/video_format.h"\r
 #include "../../../common/utility/find_file.h"\r
 #include "../../server.h"\r
 #include "../../../common/concurrency/executor.h"\r
 #include "../../../common/utility/memory.h"\r
 #include "../../../common/utility/scope_exit.h"\r
 \r
-#include "../../frame/gpu_frame.h"\r
-#include "../../frame/gpu_composite_frame.h"\r
+#include "../../processor/frame.h"\r
+#include "../../processor/composite_frame.h"\r
 \r
 #include <boost/assign.hpp>\r
 #include <boost/filesystem.hpp>\r
@@ -58,8 +58,8 @@ extern __declspec(selectany) CAtlModule* _pAtlModule = &_AtlModule;
 \r
 struct flash_producer::implementation\r
 {      \r
-       implementation(flash_producer* self, const std::wstring& filename, const frame_format_desc& format_desc\r
-               : flashax_container_(nullptr), filename_(filename), self_(self), format_desc_(format_desc),\r
+       implementation(flash_producer* self, const std::wstring& filename) \r
+               : flashax_container_(nullptr), filename_(filename), self_(self),\r
                        bitmap_pool_(new bitmap_pool), executor_([=]{run();}), invalid_count_(0)\r
        {       \r
                if(!boost::filesystem::exists(filename))\r
@@ -71,8 +71,8 @@ struct flash_producer::implementation
        ~implementation() \r
        {\r
                stop();\r
-               if(factory_)\r
-                       factory_->release_frames(this);\r
+               if(frame_processor_)\r
+                       frame_processor_->release_tag(this);\r
        }\r
 \r
        void start(bool force = true)\r
@@ -111,7 +111,7 @@ struct flash_producer::implementation
                                        BOOST_THROW_EXCEPTION(caspar_exception() << msg_info("Failed to Set Scale Mode"));\r
                                                                                                \r
                                // stop if failed\r
-                               if(FAILED(flashax_container_->SetFormat(format_desc_))) \r
+                               if(FAILED(flashax_container_->SetFormat(frame_processor_->get_video_format_desc()))) \r
                                        BOOST_THROW_EXCEPTION(caspar_exception() << msg_info("Failed to Set Format"));\r
 \r
                                current_frame_ = nullptr; // Force re-render of current frame                   \r
@@ -227,17 +227,18 @@ struct flash_producer::implementation
                                return;\r
                        }\r
 \r
-                       bool is_progressive = format_desc_.mode == video_mode::progressive || (flashax_container_->GetFPS() - format_desc_.fps/2 == 0);\r
+                       auto format_desc = frame_processor_->get_video_format_desc();\r
+                       bool is_progressive = format_desc.update == video_update_format::progressive || (flashax_container_->GetFPS() - format_desc.fps/2 == 0);\r
 \r
-                       gpu_frame_ptr result;\r
+                       frame_ptr result;\r
 \r
                        if(is_progressive)                                                      \r
                                result = do_render_frame();             \r
                        else\r
                        {\r
-                               gpu_frame_ptr frame1 = do_render_frame();\r
-                               gpu_frame_ptr frame2 = do_render_frame();\r
-                               result = gpu_composite_frame::interlace(frame1, frame2, format_desc_.mode);\r
+                               frame_ptr frame1 = do_render_frame();\r
+                               frame_ptr frame2 = do_render_frame();\r
+                               result = composite_frame::interlace(frame1, frame2, format_desc.update);\r
                        }\r
 \r
                        frame_buffer_.push(result);\r
@@ -245,8 +246,10 @@ struct flash_producer::implementation
                }\r
        }\r
                \r
-       gpu_frame_ptr do_render_frame()\r
+       frame_ptr do_render_frame()\r
        {\r
+               auto format_desc = frame_processor_->get_video_format_desc();\r
+\r
                flashax_container_->Tick();\r
                invalid_count_ = !flashax_container_->InvalidRectangle() ? std::min(2, invalid_count_+1) : 0;\r
                if(current_frame_ == nullptr || invalid_count_ < 2)\r
@@ -255,7 +258,7 @@ struct flash_producer::implementation
                        if(!bitmap_pool_->try_pop(frame))                                       \r
                        {       \r
                                CASPAR_LOG(trace) << "Allocated bitmap";\r
-                               frame = std::make_shared<bitmap>(format_desc_.width, format_desc_.height);                                      \r
+                               frame = std::make_shared<bitmap>(format_desc.width, format_desc.height);                                        \r
                                common::clear(frame->data(), frame->size());\r
                        }\r
                        flashax_container_->DrawControl(frame->hdc());\r
@@ -268,36 +271,35 @@ struct flash_producer::implementation
                        });\r
                }       \r
 \r
-               auto frame = factory_->create_frame(format_desc_, this);\r
+               auto frame = frame_processor_->create_frame(format_desc.width, format_desc.height, this);\r
                common::aligned_parallel_memcpy(frame->data(), current_frame_->data(), current_frame_->size()); \r
 \r
                return frame;\r
        }\r
                \r
-       gpu_frame_ptr render_frame()\r
+       frame_ptr render_frame()\r
        {\r
                if(!frame_buffer_.try_pop(last_frame_) && is_empty_)\r
-                       return gpu_frame::null();\r
+                       return frame::empty();\r
                \r
                return last_frame_;\r
        }\r
 \r
-       void initialize(const frame_factory_ptr& factory)\r
+       void initialize(const frame_processor_device_ptr& frame_processor)\r
        {\r
-               factory_ = factory;\r
+               frame_processor_ = frame_processor;\r
                start(false);\r
        }\r
        \r
        typedef tbb::concurrent_bounded_queue<bitmap_ptr> bitmap_pool;\r
        std::shared_ptr<bitmap_pool> bitmap_pool_;\r
-       frame_format_desc format_desc_;\r
 \r
        CComObject<flash::FlashAxContainer>* flashax_container_;\r
                \r
-       tbb::concurrent_bounded_queue<gpu_frame_ptr> frame_buffer_;\r
-       gpu_frame_ptr last_frame_;\r
+       tbb::concurrent_bounded_queue<frame_ptr> frame_buffer_;\r
+       frame_ptr last_frame_;\r
        bitmap_ptr current_frame_;\r
-       \r
+               \r
        std::wstring filename_;\r
        flash_producer* self_;\r
 \r
@@ -305,14 +307,13 @@ struct flash_producer::implementation
        common::executor executor_;\r
        int invalid_count_;\r
 \r
-       frame_factory_ptr factory_;\r
+       frame_processor_device_ptr frame_processor_;\r
 };\r
 \r
-flash_producer::flash_producer(const std::wstring& filename, const frame_format_desc& format_desc) : impl_(new implementation(this, filename, format_desc)){}\r
-gpu_frame_ptr flash_producer::render_frame(){return impl_->render_frame();}\r
+flash_producer::flash_producer(const std::wstring& filename) : impl_(new implementation(this, filename)){}\r
+frame_ptr flash_producer::render_frame(){return impl_->render_frame();}\r
 void flash_producer::param(const std::wstring& param){impl_->param(param);}\r
-const frame_format_desc& flash_producer::get_frame_format_desc() const { return impl_->format_desc_; } \r
-void flash_producer::initialize(const frame_factory_ptr& factory) { impl_->initialize(factory);}\r
+void flash_producer::initialize(const frame_processor_device_ptr& frame_processor) { impl_->initialize(frame_processor);}\r
 \r
 std::wstring flash_producer::find_template(const std::wstring& template_name)\r
 {\r
@@ -325,13 +326,13 @@ std::wstring flash_producer::find_template(const std::wstring& template_name)
        return L"";\r
 }\r
 \r
-flash_producer_ptr create_flash_producer(const std::vector<std::wstring>& params, const frame_format_desc& format_desc)\r
+flash_producer_ptr create_flash_producer(const std::vector<std::wstring>& params)\r
 {\r
        // TODO: Check for flash support\r
        auto filename = params[0];\r
        std::wstring result_filename = common::find_file(server::media_folder() + filename, list_of(L"swf"));\r
 \r
-       return result_filename.empty() ? nullptr : std::make_shared<flash_producer>(result_filename, format_desc);\r
+       return result_filename.empty() ? nullptr : std::make_shared<flash_producer>(result_filename);\r
 }\r
 \r
 }}}
\ No newline at end of file
index 26b1ae5a2289b23f4428ec9215d29c56949dc766..ddfa354e8a676664b7880455058047fba134547c 100644 (file)
@@ -42,10 +42,10 @@ public:
        /// <summary> Timeout for blocking while trying to stop the producer. </summary>\r
        static const int STOP_TIMEOUT = 2000;\r
 \r
-       flash_producer(const std::wstring& filename, const frame_format_desc& format_desc);\r
-       gpu_frame_ptr render_frame();\r
-       const frame_format_desc& get_frame_format_desc() const;\r
-       void initialize(const frame_factory_ptr& factory);\r
+       flash_producer(const std::wstring& filename);\r
+       frame_ptr render_frame();\r
+       const video_format_desc& get_video_format_desc() const;\r
+       void initialize(const frame_processor_device_ptr& frame_processor);\r
 \r
        void param(const std::wstring& param);\r
        \r
@@ -61,6 +61,6 @@ private:
 \r
 typedef std::tr1::shared_ptr<flash_producer> flash_producer_ptr;\r
 \r
-flash_producer_ptr create_flash_producer(const std::vector<std::wstring>& params, const frame_format_desc& format_desc);\r
+flash_producer_ptr create_flash_producer(const std::vector<std::wstring>& params);\r
 \r
 }}}
\ No newline at end of file
index 9189c69fcb0c978c849870cfbec42f01f3da489c..6d3f29c6197882aa7cf955f4fd3f7323e2e49b3e 100644 (file)
@@ -19,9 +19,8 @@
 */\r
 #pragma once\r
 \r
-#include "../frame/frame_fwd.h"\r
-#include "../frame/gpu_frame.h"\r
-#include "../frame/frame_factory.h"\r
+#include "../processor/frame.h"\r
+#include "../processor/frame_processor_device.h"\r
 \r
 #include <boost/noncopyable.hpp>\r
 \r
@@ -35,7 +34,7 @@ public:
        virtual ~frame_producer(){}     \r
 \r
        ////////////////////////////////////////////////////////////////////////////////////////////////////\r
-       /// \fn virtual gpu_frame_ptr :::render_frame() = 0;\r
+       /// \fn virtual frame_ptr :::render_frame() = 0;\r
        ///\r
        /// \brief      Renders a frame.\r
        ///             \r
@@ -43,7 +42,7 @@ public:
        ///\r
        /// \return     The frame. \r
        ////////////////////////////////////////////////////////////////////////////////////////////////////\r
-       virtual gpu_frame_ptr render_frame() = 0;\r
+       virtual frame_ptr render_frame() = 0;\r
 \r
        ////////////////////////////////////////////////////////////////////////////////////////////////////\r
        /// \fn virtual std::shared_ptr<frame_producer> :::get_following_producer() const\r
@@ -62,24 +61,15 @@ public:
        /// \param      producer        The leading producer.\r
        ////////////////////////////////////////////////////////////////////////////////////////////////////\r
        virtual void set_leading_producer(const std::shared_ptr<frame_producer>& /*producer*/) {}\r
-\r
-       ////////////////////////////////////////////////////////////////////////////////////////////////////\r
-       /// \fn virtual const frame_format_desc& :::get_frame_format_desc() const = 0;\r
-       ///\r
-       /// \brief      Gets the frame format description. \r
-       ///\r
-       /// \return     The frame format description. \r
-       ////////////////////////////////////////////////////////////////////////////////////////////////////\r
-       virtual const frame_format_desc& get_frame_format_desc() const = 0;\r
-\r
+       \r
        ////////////////////////////////////////////////////////////////////////////////////////////////////\r
-       /// \fn virtual void :::initialize(const frame_factory_ptr& factory) = 0;\r
+       /// \fn virtual void :::initialize(const frame_processor_device_ptr& frame_processor) = 0;\r
        ///\r
-       /// \brief      Provides the frame factory used to create frames and initializes the producer. \r
+       /// \brief      Provides the frame frame_processor used to create frames and initializes the producer. \r
        ///\r
-       /// \param      factory The frame factory\r
+       /// \param      frame_processor The frame frame_processor\r
        ////////////////////////////////////////////////////////////////////////////////////////////////////\r
-       virtual void initialize(const frame_factory_ptr& factory) = 0;\r
+       virtual void initialize(const frame_processor_device_ptr& frame_processor) = 0;\r
 };\r
 typedef std::shared_ptr<frame_producer> frame_producer_ptr;\r
 \r
diff --git a/core/producer/frame_producer_device.cpp b/core/producer/frame_producer_device.cpp
new file mode 100644 (file)
index 0000000..744e6c1
--- /dev/null
@@ -0,0 +1,165 @@
+#include "..\StdAfx.h"\r
+\r
+#include "frame_producer_device.h"\r
+\r
+#include "layer.h"\r
+\r
+#include "../video/video_format.h"\r
+#include "../processor/composite_frame.h"\r
+\r
+#include "../../common/utility/scope_exit.h"\r
+#include "../../common/utility/memory.h"\r
+\r
+#include <boost/thread.hpp>\r
+#include <boost/range/algorithm_ext/erase.hpp>\r
+#include <boost/range/algorithm.hpp>\r
+#include <boost/foreach.hpp>\r
+\r
+#include <tbb/concurrent_vector.h>\r
+#include <tbb/parallel_for.h>\r
+#include <tbb/mutex.h>\r
+       \r
+namespace caspar { namespace core {\r
+       \r
+std::vector<frame_ptr> render_frames(std::map<int, layer>& layers)\r
+{      \r
+       std::vector<frame_ptr> frames(layers.size(), nullptr);\r
+       tbb::parallel_for(tbb::blocked_range<size_t>(0, frames.size()), \r
+       [&](const tbb::blocked_range<size_t>& r)\r
+       {\r
+               auto it = layers.begin();\r
+               std::advance(it, r.begin());\r
+               for(size_t i = r.begin(); i != r.end(); ++i, ++it)\r
+                       frames[i] = it->second.render_frame();\r
+       });             \r
+       return frames;\r
+}\r
+\r
+struct frame_producer_device::implementation : boost::noncopyable\r
+{      \r
+       implementation(const frame_processor_device_ptr& frame_processor)  \r
+               : frame_processor_(frame_processor)\r
+       {       \r
+               is_running_ = true;\r
+               \r
+               render_thread_ = boost::thread([=]{run();});\r
+       }\r
+                       \r
+       ~implementation()\r
+       {\r
+               is_running_ = false;\r
+               render_thread_.join();\r
+       }\r
+               \r
+       void run()\r
+       {               \r
+               CASPAR_LOG(info) << L"Started frame_producer_device thread";\r
+               win32_exception::install_handler();\r
+               \r
+               while(is_running_)\r
+               {\r
+                       try\r
+                       {       \r
+                               std::vector<frame_ptr> next_frames;\r
+                               {\r
+                                       tbb::mutex::scoped_lock lock(layers_mutex_);    \r
+                                       next_frames = render_frames(layers_);\r
+                               }                               \r
+                               auto rendered_frame = std::make_shared<composite_frame>();\r
+                               boost::range::for_each(next_frames, std::bind(&composite_frame::add, rendered_frame, std::placeholders::_1));   \r
+                               frame_processor_->send(rendered_frame);\r
+                       }\r
+                       catch(...)\r
+                       {\r
+                               CASPAR_LOG_CURRENT_EXCEPTION();\r
+                               layers_.clear();\r
+                               CASPAR_LOG(error) << "Unexpected exception. Cleared layers in render-device";\r
+                       }\r
+               }\r
+\r
+               CASPAR_LOG(info) << L"Ended frame_producer_device thread";\r
+       }\r
+\r
+       void load(int render_layer, const frame_producer_ptr& producer, load_option::type option)\r
+       {\r
+               producer->initialize(frame_processor_);\r
+               tbb::mutex::scoped_lock lock(layers_mutex_);\r
+               layers_[render_layer].load(producer, option);\r
+       }\r
+                       \r
+       void pause(int render_layer)\r
+       {               \r
+               tbb::mutex::scoped_lock lock(layers_mutex_);\r
+               auto it = layers_.find(render_layer);\r
+               if(it != layers_.end())\r
+                       it->second.pause();             \r
+       }\r
+\r
+       void play(int render_layer)\r
+       {               \r
+               tbb::mutex::scoped_lock lock(layers_mutex_);\r
+               auto it = layers_.find(render_layer);\r
+               if(it != layers_.end())\r
+                       it->second.play();              \r
+       }\r
+\r
+       void stop(int render_layer)\r
+       {               \r
+               tbb::mutex::scoped_lock lock(layers_mutex_);\r
+               auto it = layers_.find(render_layer);\r
+               if(it != layers_.end())\r
+                       it->second.stop();\r
+       }\r
+\r
+       void clear(int render_layer)\r
+       {\r
+               tbb::mutex::scoped_lock lock(layers_mutex_);\r
+               auto it = layers_.find(render_layer);\r
+               if(it != layers_.end())\r
+                       it->second.clear();             \r
+       }\r
+               \r
+       void clear()\r
+       {\r
+               tbb::mutex::scoped_lock lock(layers_mutex_);\r
+               layers_.clear();\r
+       }               \r
+\r
+       frame_producer_ptr active(int render_layer) const\r
+       {\r
+               tbb::mutex::scoped_lock lock(layers_mutex_);\r
+               auto it = layers_.find(render_layer);\r
+               return it != layers_.end() ? it->second.active() : nullptr;\r
+       }\r
+       \r
+       frame_producer_ptr background(int render_layer) const\r
+       {\r
+               tbb::mutex::scoped_lock lock(layers_mutex_);\r
+               auto it = layers_.find(render_layer);\r
+               return it != layers_.end() ? it->second.background() : nullptr;\r
+       }\r
+       \r
+\r
+       std::function<void(frame_ptr)> output_;\r
+                       \r
+       boost::thread render_thread_;\r
+                                       \r
+       mutable tbb::mutex layers_mutex_;\r
+       std::map<int, layer> layers_;\r
+       \r
+       tbb::atomic<bool> is_running_;  \r
+       \r
+       frame_processor_device_ptr frame_processor_;\r
+};\r
+\r
+frame_producer_device::frame_producer_device(const frame_processor_device_ptr& frame_processor) \r
+       : impl_(new implementation(frame_processor)){}\r
+void frame_producer_device::load(int render_layer, const frame_producer_ptr& producer, load_option::type option){impl_->load(render_layer, producer, option);}\r
+void frame_producer_device::pause(int render_layer){impl_->pause(render_layer);}\r
+void frame_producer_device::play(int render_layer){impl_->play(render_layer);}\r
+void frame_producer_device::stop(int render_layer){impl_->stop(render_layer);}\r
+void frame_producer_device::clear(int render_layer){impl_->clear(render_layer);}\r
+void frame_producer_device::clear(){impl_->clear();}\r
+frame_producer_ptr frame_producer_device::active(int render_layer) const {return impl_->active(render_layer);}\r
+frame_producer_ptr frame_producer_device::background(int render_layer) const {return impl_->background(render_layer);}\r
+}}\r
diff --git a/core/producer/frame_producer_device.h b/core/producer/frame_producer_device.h
new file mode 100644 (file)
index 0000000..4c06d5f
--- /dev/null
@@ -0,0 +1,33 @@
+#pragma once\r
+\r
+#include "../processor/frame_processor_device.h"\r
+#include "../consumer/frame_consumer.h"\r
+#include "../video/video_format.h"\r
+\r
+#include "layer.h"\r
+\r
+#include <functional>\r
+\r
+namespace caspar { namespace core {\r
+               \r
+class frame_producer_device : boost::noncopyable\r
+{      \r
+public:\r
+       frame_producer_device(const frame_processor_device_ptr& frame_processor);\r
+       \r
+       void load(int render_layer, const frame_producer_ptr& producer, load_option::type option = load_option::none);  \r
+       void pause(int render_layer);\r
+       void play(int render_layer);\r
+       void stop(int render_layer);\r
+       void clear(int render_layer);\r
+       void clear();\r
+       \r
+       frame_producer_ptr active(int render_layer) const;\r
+       frame_producer_ptr background(int render_layer) const;\r
+private:\r
+       struct implementation;\r
+       std::shared_ptr<implementation> impl_;\r
+};\r
+typedef std::shared_ptr<frame_producer_device> frame_producer_device_ptr;\r
+\r
+}}\r
index cb2c6ef31dabbe720ebc3b55bd817a81c7444fff..4ab918a771267ae23edc9a18058b61631f853fd2 100644 (file)
@@ -4,7 +4,7 @@
 \r
 #include "../../../common/exception/Exceptions.h"\r
 \r
-#include "../../frame/gpu_frame.h"\r
+#include "../../processor/frame.h"\r
 #include "../../../common/utility/memory.h"\r
 \r
 #if defined(_MSC_VER)\r
index 9e2240d36ba16383e8a111e71b99f41bbe530087..ea16838b55c47f4c91d78ea9c3edb58fe48ac107 100644 (file)
@@ -3,8 +3,8 @@
 #include "image_producer.h"\r
 #include "image_loader.h"\r
 \r
-#include "../../frame/frame_factory.h"\r
-#include "../../frame/frame_format.h"\r
+#include "../../processor/frame_processor_device.h"\r
+#include "../../video/video_format.h"\r
 #include "../../server.h"\r
 #include "../../../common/utility/find_file.h"\r
 #include "../../../common/utility/memory.h"\r
@@ -17,46 +17,36 @@ namespace caspar { namespace core { namespace image{
 \r
 struct image_producer : public frame_producer\r
 {\r
-       image_producer(const std::wstring& filename, const frame_format_desc& format_desc) : format_desc_(format_desc), filename_(filename)     {}\r
+       image_producer(const std::wstring& filename) : filename_(filename)      {}\r
 \r
        ~image_producer()\r
        {\r
-               if(factory_)\r
-                       factory_->release_frames(this);\r
+               if(frame_processor_)\r
+                       frame_processor_->release_tag(this);\r
        }\r
 \r
-       gpu_frame_ptr render_frame(){return frame_;}\r
+       frame_ptr render_frame(){return frame_;}\r
 \r
-       void initialize(const frame_factory_ptr& factory)\r
+       void initialize(const frame_processor_device_ptr& frame_processor)\r
        {\r
-               factory_ = factory;\r
+               frame_processor_ = frame_processor;\r
                auto bitmap = load_image(filename_);\r
-               if(FreeImage_GetWidth(bitmap.get()) != format_desc_.width || FreeImage_GetHeight(bitmap.get()) == format_desc_.height)\r
-               {\r
-                       bitmap = std::shared_ptr<FIBITMAP>(FreeImage_Rescale(bitmap.get(), format_desc_.width, format_desc_.width, FILTER_BICUBIC), FreeImage_Unload);\r
-                       if(!bitmap)\r
-                               BOOST_THROW_EXCEPTION(invalid_argument() << msg_info("Unsupported image format."));\r
-               }\r
-\r
                FreeImage_FlipVertical(bitmap.get());\r
-               frame_ = factory->create_frame(format_desc_, this);\r
-               common::aligned_parallel_memcpy(frame_->data(), FreeImage_GetBits(bitmap.get()), format_desc_.size);\r
+               frame_ = frame_processor->create_frame(FreeImage_GetWidth(bitmap.get()), FreeImage_GetHeight(bitmap.get()), this);\r
+               common::aligned_parallel_memcpy(frame_->data(), FreeImage_GetBits(bitmap.get()), frame_->size());\r
        }\r
-\r
-       const frame_format_desc& get_frame_format_desc() const { return format_desc_; } \r
-\r
-       frame_factory_ptr factory_;\r
+       \r
+       frame_processor_device_ptr frame_processor_;\r
        std::wstring filename_;\r
-       frame_format_desc format_desc_;\r
-       gpu_frame_ptr frame_;\r
+       frame_ptr frame_;\r
 };\r
 \r
-frame_producer_ptr create_image_producer(const  std::vector<std::wstring>& params, const frame_format_desc& format_desc)\r
+frame_producer_ptr create_image_producer(const  std::vector<std::wstring>& params)\r
 {\r
        std::wstring filename = params[0];\r
        std::wstring resultFilename = common::find_file(server::media_folder() + filename, list_of(L"png")(L"tga")(L"bmp")(L"jpg")(L"jpeg"));\r
        if(!resultFilename.empty())\r
-               return std::make_shared<image_producer>(resultFilename, format_desc);\r
+               return std::make_shared<image_producer>(resultFilename);\r
 \r
        return nullptr;\r
 }\r
index c5f77889147916b94893bda0a74d11c771d88aff..88a913ccbd009e0ffe96565b779ce2b94e7330cd 100644 (file)
@@ -7,6 +7,6 @@
 \r
 namespace caspar { namespace core { namespace image {\r
 \r
-frame_producer_ptr create_image_producer(const std::vector<std::wstring>& params, const frame_format_desc& format_desc);\r
+frame_producer_ptr create_image_producer(const std::vector<std::wstring>& params);\r
 \r
 }}}
\ No newline at end of file
index 35191ba3410e47d0d80f1b7c2e2e58995af45e24..dc41bdc45ab1ba3b7f4a70a908d303dcb06ad4dc 100644 (file)
@@ -4,10 +4,10 @@
 \r
 #include "image_loader.h"\r
 \r
-#include "../../frame/gpu_frame.h"\r
-#include "../../frame/gpu_composite_frame.h"\r
-#include "../../frame/frame_format.h"\r
-#include "../../frame/frame_factory.h"\r
+#include "../../processor/frame.h"\r
+#include "../../processor/composite_frame.h"\r
+#include "../../video/video_format.h"\r
+#include "../../processor/frame_processor_device.h"\r
 #include "../../server.h"\r
 #include "../../../common/utility/find_file.h"\r
 #include "../../../common/utility/memory.h"\r
@@ -32,8 +32,8 @@ struct image_scroll_producer : public frame_producer
 {\r
        static const int DEFAULT_SCROLL_SPEED = 50;\r
 \r
-       image_scroll_producer(const std::wstring& filename, const std::vector<std::wstring>& params, const frame_format_desc& format_desc\r
-               : format_desc_(format_desc), speed_(image_scroll_producer::DEFAULT_SCROLL_SPEED), direction_(direction::Up), offset_(0)\r
+       image_scroll_producer(const std::wstring& filename, const std::vector<std::wstring>& params) \r
+               : speed_(image_scroll_producer::DEFAULT_SCROLL_SPEED), direction_(direction::Up), offset_(0)\r
        {\r
                load_and_pad_image(filename);\r
 \r
@@ -50,24 +50,12 @@ struct image_scroll_producer : public frame_producer
                }\r
 \r
                loop_ = std::find(params.begin(), params.end(), L"LOOP") != params.end();\r
-                               \r
-               if(image_width_ - format_desc.width > image_height_ - format_desc_.height)\r
-                       direction_ = speed_ < 0 ? direction::Right : direction::Left;\r
-               else\r
-                       direction_ = speed_ < 0 ? direction::Down : direction::Up;\r
-\r
-               if (direction_ == direction::Down)\r
-                       offset_ = image_height_ - format_desc_.height;\r
-               else if (direction_ == direction::Right)\r
-                       offset_ = image_width_ - format_desc_.width;\r
-\r
-               speed_ = static_cast<int>(abs(static_cast<double>(speed_) / format_desc.fps));\r
        }\r
        \r
        ~image_scroll_producer()\r
        {\r
-               if(factory_)\r
-                       factory_->release_frames(this);\r
+               if(frame_processor_)\r
+                       frame_processor_->release_tag(this);\r
        }\r
 \r
        void load_and_pad_image(const std::wstring& filename)\r
@@ -89,9 +77,9 @@ struct image_scroll_producer : public frame_producer
                        common::aligned_parallel_memcpy(&image_.get()[i * image_width_ * 4], &pBits[i* width * 4], width * 4);\r
        }\r
 \r
-       gpu_frame_ptr do_render_frame()\r
+       frame_ptr do_render_frame()\r
        {\r
-               gpu_frame_ptr frame = factory_->create_frame(format_desc_, this);\r
+               frame_ptr frame = frame_processor_->create_frame(format_desc_.width, format_desc_.height, this);\r
                common::clear(frame->data(), format_desc_.size);\r
 \r
                const int delta_x = direction_ == direction::Left ? speed_ : -speed_;\r
@@ -134,25 +122,38 @@ struct image_scroll_producer : public frame_producer
                return frame;\r
        }\r
                \r
-       gpu_frame_ptr render_frame()\r
+       frame_ptr render_frame()\r
        {               \r
-               if(format_desc_.mode != video_mode::progressive)                                \r
+               if(format_desc_.update != video_update_format::progressive)                             \r
                {\r
-                       gpu_frame_ptr frame1;\r
-                       gpu_frame_ptr frame2;\r
+                       frame_ptr frame1;\r
+                       frame_ptr frame2;\r
                        tbb::parallel_invoke([&]{ frame1 = do_render_frame(); }, [&]{ frame2 = do_render_frame(); });\r
-                       return gpu_composite_frame::interlace(frame1, frame2, format_desc_.mode);\r
+                       return composite_frame::interlace(frame1, frame2, format_desc_.update);\r
                }                       \r
 \r
                return render_frame();  \r
        }\r
        \r
-       void initialize(const frame_factory_ptr& factory)\r
+       void initialize(const frame_processor_device_ptr& frame_processor)\r
        {\r
-               factory_ = factory;\r
+               frame_processor_ = frame_processor;\r
+               format_desc_ = frame_processor_->get_video_format_desc();\r
+                               \r
+               if(image_width_ - format_desc_.width > image_height_ - format_desc_.height)\r
+                       direction_ = speed_ < 0 ? direction::Right : direction::Left;\r
+               else\r
+                       direction_ = speed_ < 0 ? direction::Down : direction::Up;\r
+\r
+               if (direction_ == direction::Down)\r
+                       offset_ = image_height_ - format_desc_.height;\r
+               else if (direction_ == direction::Right)\r
+                       offset_ = image_width_ - format_desc_.width;\r
+\r
+               speed_ = static_cast<int>(abs(static_cast<double>(speed_) / format_desc_.fps));\r
        }\r
 \r
-       const frame_format_desc& get_frame_format_desc() const { return format_desc_; } \r
+       const video_format_desc& get_video_format_desc() const { return format_desc_; } \r
        \r
        int image_width_;\r
        int image_height_;\r
@@ -162,17 +163,17 @@ struct image_scroll_producer : public frame_producer
 \r
        tbb::atomic<bool> loop_;\r
        std::shared_ptr<unsigned char> image_;\r
-       frame_format_desc format_desc_;\r
+       video_format_desc format_desc_;\r
 \r
-       frame_factory_ptr factory_;\r
+       frame_processor_device_ptr frame_processor_;\r
 };\r
 \r
-frame_producer_ptr create_image_scroll_producer(const std::vector<std::wstring>& params, const frame_format_desc& format_desc)\r
+frame_producer_ptr create_image_scroll_producer(const std::vector<std::wstring>& params)\r
 {\r
        std::wstring filename = params[0];\r
        auto result_filename = common::find_file(server::media_folder() + filename, list_of(L"spng")(L"stga")(L"sbmp")(L"sjpg")(L"sjpeg"));\r
        if(!result_filename.empty())\r
-               return std::make_shared<image_scroll_producer>(result_filename, params, format_desc);\r
+               return std::make_shared<image_scroll_producer>(result_filename, params);\r
 \r
        return nullptr;\r
 }\r
index bd3190b89d92a3ff30330169f9849d5accc08949..72da2d5a0a16eb434c036ec57ef3011a4f4fb8a5 100644 (file)
@@ -7,6 +7,6 @@
 \r
 namespace caspar { namespace core { namespace image {\r
        \r
-frame_producer_ptr create_image_scroll_producer(const std::vector<std::wstring>& params, const frame_format_desc& format_desc);\r
+frame_producer_ptr create_image_scroll_producer(const std::vector<std::wstring>& params);\r
 \r
 }}}
\ No newline at end of file
diff --git a/core/producer/layer.cpp b/core/producer/layer.cpp
new file mode 100644 (file)
index 0000000..c053ea7
--- /dev/null
@@ -0,0 +1,113 @@
+#include "../stdafx.h"\r
+\r
+#include "layer.h"\r
+\r
+#include "../producer/frame_producer.h"\r
+\r
+#include "../video/video_format.h"\r
+\r
+namespace caspar { namespace core {\r
+\r
+struct layer::implementation\r
+{              \r
+       implementation() \r
+               : preview_frame_(nullptr), active_(nullptr), \r
+                       background_(nullptr), last_frame_(nullptr) {}\r
+       \r
+       void load(const frame_producer_ptr& frame_producer, load_option::type option)\r
+       {\r
+               if(frame_producer == nullptr) \r
+                       BOOST_THROW_EXCEPTION(null_argument() << arg_name_info("frame_producer"));\r
+                       \r
+               last_frame_ = nullptr;\r
+               background_ = frame_producer;\r
+               if(option == load_option::preview)              \r
+               {\r
+                       last_frame_ = frame_producer->render_frame();\r
+                       if(last_frame_ != nullptr)\r
+                               last_frame_->audio_data().clear(); // No audio\r
+                       active_ = nullptr;      \r
+               }\r
+               else if(option == load_option::auto_play)\r
+                       play();                 \r
+       }\r
+       \r
+       void play()\r
+       {                       \r
+               if(background_ != nullptr)\r
+               {\r
+                       background_->set_leading_producer(active_);\r
+                       active_     = background_;\r
+                       background_ = nullptr;\r
+               }\r
+\r
+               is_paused_ = false;\r
+       }\r
+\r
+       void pause()\r
+       {\r
+               is_paused_ = true;\r
+       }\r
+\r
+       void stop()\r
+       {\r
+               active_     = nullptr;\r
+               last_frame_ = nullptr;\r
+       }\r
+\r
+       void clear()\r
+       {\r
+               active_     = nullptr;\r
+               background_ = nullptr;\r
+               last_frame_ = nullptr;\r
+       }\r
+       \r
+       frame_ptr render_frame()\r
+       {               \r
+               if(!active_ || is_paused_)\r
+                       return last_frame_;\r
+\r
+               try\r
+               {\r
+                       last_frame_ = active_->render_frame();\r
+\r
+                       if(last_frame_ == nullptr)\r
+                       {\r
+                               active_ = active_->get_following_producer();\r
+                               last_frame_ = render_frame();\r
+                       }\r
+               }\r
+               catch(...)\r
+               {\r
+                       CASPAR_LOG_CURRENT_EXCEPTION();\r
+                       active_ = nullptr;\r
+                       CASPAR_LOG(warning) << "Removed producer from layer.";\r
+               }\r
+\r
+               return last_frame_;\r
+       }       \r
+               \r
+       tbb::atomic<bool> is_paused_;\r
+       frame_ptr last_frame_;\r
+       frame_ptr preview_frame_;\r
+       frame_producer_ptr active_;\r
+       frame_producer_ptr background_;\r
+};\r
+\r
+layer::layer() : impl_(new implementation()){}\r
+layer::layer(layer&& other) : impl_(std::move(other.impl_)){other.impl_ = nullptr;}\r
+layer& layer::operator=(layer&& other)\r
+{\r
+       impl_ = std::move(other.impl_); \r
+       other.impl_ = nullptr;\r
+       return *this;\r
+}\r
+void layer::load(const frame_producer_ptr& frame_producer, load_option::type option){return impl_->load(frame_producer, option);}      \r
+void layer::play(){impl_->play();}\r
+void layer::pause(){impl_->pause();}\r
+void layer::stop(){impl_->stop();}\r
+void layer::clear(){impl_->clear();}\r
+frame_ptr layer::render_frame() {return impl_->render_frame();}\r
+frame_producer_ptr layer::active() const { return impl_->active_;}\r
+frame_producer_ptr layer::background() const { return impl_->background_;}\r
+}}
\ No newline at end of file
diff --git a/core/producer/layer.h b/core/producer/layer.h
new file mode 100644 (file)
index 0000000..e67b994
--- /dev/null
@@ -0,0 +1,43 @@
+#pragma once\r
+\r
+#include "../producer/frame_producer.h"\r
+\r
+namespace caspar { namespace core {\r
+\r
+struct load_option\r
+{\r
+       enum type\r
+       {\r
+               none,\r
+               preview,\r
+               auto_play\r
+       };\r
+};\r
+\r
+class layer\r
+{\r
+       layer(const layer& other);\r
+       layer& operator=(const layer& other);\r
+public:\r
+       layer();\r
+       layer(layer&& other);\r
+       layer& operator=(layer&& other);\r
+\r
+       void load(const frame_producer_ptr& producer, load_option::type option = load_option::none);    \r
+       void play();\r
+       void pause();\r
+       void stop();\r
+       void clear();\r
+               \r
+       frame_producer_ptr active() const;\r
+       frame_producer_ptr background() const;\r
+\r
+       frame_ptr render_frame();\r
+private:\r
+       struct implementation;\r
+       std::shared_ptr<implementation> impl_;\r
+};\r
+typedef std::shared_ptr<layer> layer_ptr;\r
+typedef std::unique_ptr<layer> layer_uptr;\r
+\r
+}}
\ No newline at end of file
index d8e4c3a33e3cb94f936ed73b00bc74a4666e9dc6..6a24c1384ff82ff0eaddb380a3e64e6dba1cc7ef 100644 (file)
 \r
 #include "transition_producer.h"\r
 \r
-#include "../../frame/frame_format.h"\r
-#include "../../frame/gpu_frame.h"\r
-#include "../../frame/gpu_composite_frame.h"\r
-#include "../../frame/frame_factory.h"\r
+#include "../../video/video_format.h"\r
+#include "../../processor/frame.h"\r
+#include "../../processor/composite_frame.h"\r
+#include "../../processor/frame_processor_device.h"\r
 \r
 #include "../../../common/utility/memory.h"\r
-#include "../../renderer/render_device.h"\r
+#include "../../producer/frame_producer_device.h"\r
 \r
 #include <boost/range/algorithm/copy.hpp>\r
 \r
@@ -35,8 +35,8 @@ namespace caspar { namespace core {
 \r
 struct transition_producer::implementation : boost::noncopyable\r
 {\r
-       implementation(const frame_producer_ptr& dest, const transition_info& info, const frame_format_desc& format_desc\r
-               : current_frame_(0), info_(info), format_desc_(format_desc), dest_producer_(dest)\r
+       implementation(const frame_producer_ptr& dest, const transition_info& info) \r
+               : current_frame_(0), info_(info), dest_producer_(dest)\r
        {\r
                if(!dest)\r
                        BOOST_THROW_EXCEPTION(null_argument() << arg_name_info("dest"));\r
@@ -52,29 +52,40 @@ struct transition_producer::implementation : boost::noncopyable
                source_producer_ = producer;\r
        }\r
                \r
-       gpu_frame_ptr render_frame()\r
+       frame_ptr render_frame()\r
        {\r
-               if(current_frame_++ >= info_.duration)\r
-                       return nullptr;\r
+               if(current_frame_ == 0)\r
+                       CASPAR_LOG(info) << "Transition started.";\r
 \r
-               gpu_frame_ptr source;\r
-               gpu_frame_ptr dest;\r
+               frame_ptr result = [&]() -> frame_ptr\r
+               {\r
+                       if(current_frame_++ >= info_.duration)\r
+                               return nullptr;\r
 \r
-               tbb::parallel_invoke\r
-               (\r
-                       [&]{dest = render_frame(dest_producer_);},\r
-                       [&]{source = render_frame(source_producer_);}\r
-               );\r
+                       frame_ptr source;\r
+                       frame_ptr dest;\r
+\r
+                       tbb::parallel_invoke\r
+                       (\r
+                               [&]{dest = render_frame(dest_producer_);},\r
+                               [&]{source = render_frame(source_producer_);}\r
+                       );\r
 \r
-               return compose(dest, source);\r
+                       return compose(dest, source);\r
+               }();\r
+\r
+               if(result == nullptr)\r
+                       CASPAR_LOG(info) << "Transition ended.";\r
+\r
+               return result;\r
        }\r
 \r
-       gpu_frame_ptr render_frame(frame_producer_ptr& producer)\r
+       frame_ptr render_frame(frame_producer_ptr& producer)\r
        {\r
                if(producer == nullptr)\r
                        return nullptr;\r
 \r
-               gpu_frame_ptr frame;\r
+               frame_ptr frame;\r
                try\r
                {\r
                        frame = producer->render_frame();\r
@@ -90,7 +101,7 @@ struct transition_producer::implementation : boost::noncopyable
                        producer->get_following_producer() != nullptr)\r
                {\r
                        auto following = producer->get_following_producer();\r
-                       following->initialize(factory_);\r
+                       following->initialize(frame_processor_);\r
                        following->set_leading_producer(producer);\r
                        producer = following;\r
                        return render_frame(producer);\r
@@ -98,7 +109,7 @@ struct transition_producer::implementation : boost::noncopyable
                return frame;\r
        }\r
                        \r
-       void set_volume(const gpu_frame_ptr& frame, int volume)\r
+       void set_volume(const frame_ptr& frame, int volume)\r
        {\r
                if(!frame)\r
                        return;\r
@@ -107,16 +118,16 @@ struct transition_producer::implementation : boost::noncopyable
                        frame->audio_data()[n] = static_cast<short>((static_cast<int>(frame->audio_data()[n])*volume)>>8);\r
        }\r
                \r
-       gpu_frame_ptr compose(const gpu_frame_ptr& dest_frame, gpu_frame_ptr src_frame) \r
+       frame_ptr compose(const frame_ptr& dest_frame, frame_ptr src_frame) \r
        {       \r
-               if(info_.type == transition_type::cut)          \r
+               if(info_.type == transition::cut)               \r
                        return src_frame;\r
 \r
                if(!dest_frame)\r
                        return nullptr;\r
                                                                \r
                double alpha = static_cast<double>(current_frame_)/static_cast<double>(info_.duration);\r
-               int volume = static_cast<int>(static_cast<double>(current_frame_)/static_cast<double>(info_.duration)*256.0);\r
+               int volume = static_cast<int>(alpha*256.0);\r
                                \r
                tbb::parallel_invoke\r
                (\r
@@ -124,16 +135,16 @@ struct transition_producer::implementation : boost::noncopyable
                        [&]{set_volume(src_frame, 256-volume);}\r
                );\r
                \r
-               if(info_.type == transition_type::mix)\r
+               if(info_.type == transition::mix)\r
                        dest_frame->alpha(alpha);               \r
-               else if(info_.type == transition_type::slide)\r
+               else if(info_.type == transition::slide)\r
                {       \r
                        if(info_.direction == transition_direction::from_left)                  \r
                                dest_frame->translate(-1.0+alpha, 0.0);                 \r
                        else if(info_.direction == transition_direction::from_right)\r
                                dest_frame->translate(1.0-alpha, 0.0);          \r
                }\r
-               else if(info_.type == transition_type::push)\r
+               else if(info_.type == transition::push)\r
                {\r
                        if(info_.direction == transition_direction::from_left)          \r
                        {\r
@@ -148,51 +159,48 @@ struct transition_producer::implementation : boost::noncopyable
                                        src_frame->translate(0.0-alpha, 0.0);\r
                        }\r
                }\r
-               else if(info_.type == transition_type::wipe)\r
+               else if(info_.type == transition::wipe)\r
                {\r
                        if(info_.direction == transition_direction::from_left)          \r
                        {\r
                                dest_frame->translate(-1.0+alpha, 0.0);\r
-                               dest_frame->texcoords(rectangle(-1.0+alpha, 1.0, alpha, 0.0));\r
+                               dest_frame->texcoords(-1.0+alpha, 1.0, alpha, 0.0);\r
                        }\r
                        else if(info_.direction == transition_direction::from_right)\r
                        {\r
                                dest_frame->translate(1.0-alpha, 0.0);\r
-                               dest_frame->texcoords(rectangle(1.0-alpha, 1.0, 2.0-alpha, 0.0));\r
+                               dest_frame->texcoords(1.0-alpha, 1.0, 2.0-alpha, 0.0);\r
                        }\r
                }\r
                                                \r
-               auto composite = std::make_shared<gpu_composite_frame>();\r
+               auto composite = std::make_shared<composite_frame>();\r
                if(src_frame)\r
                        composite->add(src_frame);\r
                composite->add(dest_frame);\r
                return composite;\r
        }\r
                \r
-       void initialize(const frame_factory_ptr& factory)\r
+       void initialize(const frame_processor_device_ptr& frame_processor)\r
        {\r
-               dest_producer_->initialize(factory);\r
-               factory_ = factory;\r
+               dest_producer_->initialize(frame_processor);\r
+               frame_processor_ = frame_processor;\r
        }\r
-\r
-       const frame_format_desc         format_desc_;\r
-\r
+       \r
        frame_producer_ptr                      source_producer_;\r
        frame_producer_ptr                      dest_producer_;\r
        \r
        unsigned short                          current_frame_;\r
        \r
        const transition_info           info_;\r
-       frame_factory_ptr                       factory_;\r
+       frame_processor_device_ptr      frame_processor_;\r
 };\r
 \r
-transition_producer::transition_producer(const frame_producer_ptr& dest, const transition_info& info, const frame_format_desc& format_desc\r
-       : impl_(new implementation(dest, info, format_desc)){}\r
-gpu_frame_ptr transition_producer::render_frame(){return impl_->render_frame();}\r
+transition_producer::transition_producer(const frame_producer_ptr& dest, const transition_info& info) \r
+       : impl_(new implementation(dest, info)){}\r
+frame_ptr transition_producer::render_frame(){return impl_->render_frame();}\r
 frame_producer_ptr transition_producer::get_following_producer() const{return impl_->get_following_producer();}\r
 void transition_producer::set_leading_producer(const frame_producer_ptr& producer) { impl_->set_leading_producer(producer); }\r
-const frame_format_desc& transition_producer::get_frame_format_desc() const { return impl_->format_desc_; } \r
-void transition_producer::initialize(const frame_factory_ptr& factory) { impl_->initialize(factory);}\r
+void transition_producer::initialize(const frame_processor_device_ptr& frame_processor) { impl_->initialize(frame_processor);}\r
 \r
 }}\r
 \r
index f67b4736cfaac3aef382370dcd54d29d70f51180..65a1bfb6e0721511bd7c6fb78f1271fc928f51c9 100644 (file)
 \r
 namespace caspar { namespace core {\r
 \r
-enum transition_type\r
+struct transition\r
 {\r
-       cut = 1,\r
-       mix,\r
-       push,\r
-       slide,\r
-       wipe\r
+       enum type\r
+       {\r
+\r
+               cut = 1,\r
+               mix,\r
+               push,\r
+               slide,\r
+               wipe\r
+       };\r
 };\r
 \r
-enum transition_direction\r
+struct transition_direction\r
 {\r
-       from_left = 1,\r
-       from_right\r
+       enum type\r
+       {\r
+               from_left = 1,\r
+               from_right\r
+       };\r
 };\r
 \r
 struct transition_info\r
 {\r
-       transition_info() : type(transition_type::cut), duration(0), direction(transition_direction::from_left){}\r
+       transition_info() : type(transition::cut), duration(0), direction(transition_direction::from_left){}\r
     \r
-       size_t                                  duration;\r
-       transition_direction    direction;\r
-       transition_type                 type;\r
+       size_t                                          duration;\r
+       transition_direction::type      direction;\r
+       transition::type                        type;\r
 };\r
 \r
 class transition_producer : public frame_producer\r
 {\r
 public:\r
-       transition_producer(const frame_producer_ptr& destination, const transition_info& info, const frame_format_desc& fmt);\r
+       transition_producer(const frame_producer_ptr& destination, const transition_info& info);\r
 \r
-       gpu_frame_ptr render_frame();\r
+       frame_ptr render_frame();\r
 \r
        frame_producer_ptr get_following_producer() const;\r
        void set_leading_producer(const frame_producer_ptr& producer);\r
-       const frame_format_desc& get_frame_format_desc() const;\r
-       virtual void initialize(const frame_factory_ptr& factory);\r
+       virtual void initialize(const frame_processor_device_ptr& frame_processor);\r
 private:\r
        struct implementation;\r
        std::shared_ptr<implementation> impl_;\r
index a79a8fad728b4ac33b79ed82209b76f2fd49ba4a..f53226cacbbc8934fb4287c781a676476619ee33 100644 (file)
@@ -21,8 +21,9 @@
 \r
 #include "../../../common/io/clientinfo.h"\r
 #include "../../consumer/frame_consumer.h"\r
+#include "../../channel.h"\r
+\r
 #include <boost/algorithm/string.hpp>\r
-#include "../../renderer/render_device.h"\r
 \r
 namespace caspar { namespace core {\r
 namespace amcp {\r
@@ -54,8 +55,8 @@ namespace amcp {
                void SetClientInfo(IO::ClientInfoPtr& s){pClientInfo_ = s;}\r
                IO::ClientInfoPtr GetClientInfo(){return pClientInfo_;}\r
 \r
-               void SetChannel(const renderer::render_device_ptr& pChannel){pChannel_ = pChannel;}\r
-               renderer::render_device_ptr GetChannel(){return pChannel_;}\r
+               void SetChannel(const channel_ptr& pChannel){pChannel_ = pChannel;}\r
+               channel_ptr GetChannel(){return pChannel_;}\r
 \r
                void SetChannelIndex(unsigned int channelIndex){channelIndex_ = channelIndex;}\r
                unsigned int GetChannelIndex(){return channelIndex_;}\r
@@ -80,7 +81,7 @@ namespace amcp {
                unsigned int channelIndex_;\r
                int layerIndex_;\r
                IO::ClientInfoPtr pClientInfo_;\r
-               renderer::render_device_ptr pChannel_;\r
+               channel_ptr pChannel_;\r
                AMCPCommandScheduling scheduling_;\r
                std::wstring replyString_;\r
        };\r
index c9a0535cc3ee4dc61836b872eab166b621d6d7ab..f178266d663cae34af42abc843529f91e108235f 100644 (file)
@@ -23,7 +23,7 @@
 #include "AMCPCommandsImpl.h"\r
 #include "AMCPProtocolStrategy.h"\r
 #include "../../producer/frame_producer.h"\r
-#include "../../Frame/frame_format.h"\r
+#include "../../video/video_format.h"\r
 #include "../../producer/flash/flash_producer.h"\r
 #include "../../producer/transition/transition_producer.h"\r
 #include <boost/lexical_cast.hpp>\r
@@ -74,7 +74,7 @@ std::wstring ListMedia()
 {      \r
        std::wstringstream replyString;\r
        for (boost::filesystem::wrecursive_directory_iterator itr(server::media_folder()), end; itr != end; ++itr)\r
-    {                  \r
+       {                       \r
                if(boost::filesystem::is_regular_file(itr->path()))\r
                {\r
                        std::wstring clipttype = TEXT(" N/A ");\r
@@ -117,7 +117,7 @@ std::wstring ListTemplates()
        std::wstringstream replyString;\r
 \r
        for (boost::filesystem::wrecursive_directory_iterator itr(server::template_folder()), end; itr != end; ++itr)\r
-    {          \r
+       {               \r
                if(boost::filesystem::is_regular_file(itr->path()) && itr->path().extension() == L".ft")\r
                {\r
                        auto relativePath = boost::filesystem::wpath(itr->path().file_string().substr(server::template_folder().size()-1, itr->path().file_string().size()));\r
@@ -170,9 +170,9 @@ bool LoadCommand::DoExecute()
        //Perform loading of the clip\r
        try\r
        {\r
-               auto pFP = load_media(_parameters,  GetChannel()->get_frame_format_desc());     \r
+               auto pFP = load_media(_parameters);     \r
                bool autoPlay = std::find(_parameters.begin(), _parameters.end(), TEXT("AUTOPLAY")) != _parameters.end();               \r
-               GetChannel()->load(GetLayerIndex(), pFP, autoPlay ? renderer::load_option::auto_play : renderer::load_option::preview);\r
+               GetChannel()->load(GetLayerIndex(), pFP, autoPlay ? load_option::auto_play : load_option::preview);\r
        \r
                CASPAR_LOG(info) << "Loaded " <<  _parameters[0] << TEXT(" successfully");\r
 \r
@@ -210,15 +210,15 @@ bool LoadbgCommand::DoExecute()
                std::wstring transitionType = _parameters[transitionParameterIndex];\r
 \r
                if(transitionType == TEXT("CUT"))\r
-                       transitionInfo.type = transition_type::cut;\r
+                       transitionInfo.type = transition::cut;\r
                else if(transitionType == TEXT("MIX"))\r
-                       transitionInfo.type = transition_type::mix;\r
+                       transitionInfo.type = transition::mix;\r
                else if(transitionType == TEXT("PUSH"))\r
-                       transitionInfo.type = transition_type::push;\r
+                       transitionInfo.type = transition::push;\r
                else if(transitionType == TEXT("SLIDE"))\r
-                       transitionInfo.type = transition_type::slide;\r
+                       transitionInfo.type = transition::slide;\r
                else if(transitionType == TEXT("WIPE"))\r
-                       transitionInfo.type = transition_type::wipe;\r
+                       transitionInfo.type = transition::wipe;\r
 \r
                if(_parameters.size() > static_cast<unsigned short>(transitionParameterIndex+1))        //duration\r
                {\r
@@ -245,13 +245,13 @@ bool LoadbgCommand::DoExecute()
        //Perform loading of the clip\r
        try\r
        {\r
-               auto pFP = load_media(_parameters,  GetChannel()->get_frame_format_desc());\r
+               auto pFP = load_media(_parameters);\r
                if(pFP == nullptr)\r
                        BOOST_THROW_EXCEPTION(file_not_found() << msg_info(_parameters.size() > 0 ? common::narrow(_parameters[0]) : ""));\r
 \r
-               pFP = std::make_shared<transition_producer>(pFP, transitionInfo, GetChannel()->get_frame_format_desc());\r
+               pFP = std::make_shared<transition_producer>(pFP, transitionInfo);\r
                bool autoPlay = std::find(_parameters.begin(), _parameters.end(), TEXT("AUTOPLAY")) != _parameters.end();\r
-               GetChannel()->load(GetLayerIndex(), pFP, autoPlay ? renderer::load_option::auto_play : renderer::load_option::none); // TODO: LOOP\r
+               GetChannel()->load(GetLayerIndex(), pFP, autoPlay ? load_option::auto_play : load_option::none); // TODO: LOOP\r
        \r
                CASPAR_LOG(info) << "Loaded " << _parameters[0] << TEXT(" successfully to background");\r
                SetReplyString(TEXT("202 LOADBG OK\r\n"));\r
@@ -727,9 +727,9 @@ bool CinfCommand::DoExecute()
        return false;\r
 }\r
 \r
-void GenerateChannelInfo(int index, const renderer::render_device_ptr& pChannel, std::wstringstream& replyString)\r
+void GenerateChannelInfo(int index, const channel_ptr& pChannel, std::wstringstream& replyString)\r
 {\r
-       replyString << index << TEXT(" ") << pChannel->get_frame_format_desc().name  << TEXT("\r\n") << (pChannel->active(0) != nullptr ? TEXT(" PLAYING") : TEXT(" STOPPED"));\r
+       replyString << index << TEXT(" ") << pChannel->get_video_format_desc().name  << TEXT("\r\n") << (pChannel->active(0) != nullptr ? TEXT(" PLAYING") : TEXT(" STOPPED"));\r
 }\r
 \r
 bool InfoCommand::DoExecute()\r
index 885ea1b773dfc22c3b20cd7c0a02c16af9ff64a8..efb3128db0333420584e9d5af2f35827756c169f 100644 (file)
@@ -102,10 +102,10 @@ class CinfCommand : public AMCPCommandBase<false, AddToQueue, 1>
 class InfoCommand : public AMCPCommandBase<false, AddToQueue, 0>\r
 {\r
 public:\r
-       InfoCommand(const std::vector<renderer::render_device_ptr>& channels) : channels_(channels){}\r
+       InfoCommand(const std::vector<channel_ptr>& channels) : channels_(channels){}\r
        bool DoExecute();\r
 private:\r
-       const std::vector<renderer::render_device_ptr>& channels_;\r
+       const std::vector<channel_ptr>& channels_;\r
 };\r
 \r
 class VersionCommand : public AMCPCommandBase<false, AddToQueue, 0>\r
index a49b27f8ae7f173bd730b1965e9cdd27d8371715..3fb1ee4d1b3628864948e6c8d88167af88711fd9 100644 (file)
@@ -19,7 +19,7 @@
 */\r
  \r
 #include "../../StdAfx.h"\r
-#include "../../renderer/render_device.h"\r
+#include "../../producer/frame_producer_device.h"\r
 \r
 #include "AMCPProtocolStrategy.h"\r
 \r
@@ -47,12 +47,12 @@ using IO::ClientInfoPtr;
 \r
 const std::wstring AMCPProtocolStrategy::MessageDelimiter = TEXT("\r\n");\r
 \r
-inline renderer::render_device_ptr GetChannelSafe(unsigned int index, const std::vector<renderer::render_device_ptr>& channels)\r
+inline channel_ptr GetChannelSafe(unsigned int index, const std::vector<channel_ptr>& channels)\r
 {\r
        return index < channels.size() ? channels[index] : nullptr;\r
 }\r
 \r
-AMCPProtocolStrategy::AMCPProtocolStrategy(const std::vector<renderer::render_device_ptr>& channels) : channels_(channels) {\r
+AMCPProtocolStrategy::AMCPProtocolStrategy(const std::vector<channel_ptr>& channels) : channels_(channels) {\r
        AMCPCommandQueuePtr pGeneralCommandQueue(new AMCPCommandQueue());\r
        if(!pGeneralCommandQueue->Start()) {\r
                CASPAR_LOG(error) << "Failed to start the general command-queue";\r
@@ -63,7 +63,7 @@ AMCPProtocolStrategy::AMCPProtocolStrategy(const std::vector<renderer::render_de
                commandQueues_.push_back(pGeneralCommandQueue);\r
 \r
 \r
-       renderer::render_device_ptr pChannel;\r
+       channel_ptr pChannel;\r
        unsigned int index = -1;\r
        //Create a commandpump for each channel\r
        while((pChannel = GetChannelSafe(++index, channels_)) != 0) {\r
@@ -257,7 +257,7 @@ AMCPCommandPtr AMCPProtocolStrategy::InterpretCommandString(const std::wstring&
                                        goto ParseFinnished;\r
                                }\r
 \r
-                               renderer::render_device_ptr pChannel = GetChannelSafe(channelIndex, channels_);\r
+                               channel_ptr pChannel = GetChannelSafe(channelIndex, channels_);\r
                                if(pChannel == 0) {\r
                                        goto ParseFinnished;\r
                                }\r
index 0e191c6f0875de0cf416c14c42de219e441a1170..e95c3ecba6859339e8ea74c8e34e5e02b5d80488 100644 (file)
 #include "../../../common/io/protocolstrategy.h"\r
 #include "AMCPCommand.h"\r
 #include "AMCPCommandQueue.h"\r
+#include "../../channel.h"\r
+\r
+#include <boost/noncopyable.hpp>\r
 \r
 namespace caspar { namespace core { namespace amcp {\r
 \r
-class AMCPProtocolStrategy : public IO::IProtocolStrategy\r
+class AMCPProtocolStrategy : public IO::IProtocolStrategy, boost::noncopyable\r
 {\r
        enum MessageParserState {\r
                New = 0,\r
@@ -40,7 +43,7 @@ class AMCPProtocolStrategy : public IO::IProtocolStrategy
        AMCPProtocolStrategy& operator=(const AMCPProtocolStrategy&);\r
 \r
 public:\r
-       AMCPProtocolStrategy(const std::vector<renderer::render_device_ptr>& channels);\r
+       AMCPProtocolStrategy(const std::vector<channel_ptr>& channels);\r
        virtual ~AMCPProtocolStrategy();\r
 \r
        virtual void Parse(const TCHAR* pData, int charCount, IO::ClientInfoPtr pClientInfo);\r
@@ -59,7 +62,7 @@ private:
 \r
        bool QueueCommand(AMCPCommandPtr);\r
 \r
-       const std::vector<renderer::render_device_ptr>& channels_;\r
+       std::vector<channel_ptr> channels_;\r
        std::vector<AMCPCommandQueuePtr> commandQueues_;\r
        static const std::wstring MessageDelimiter;\r
 };\r
index fa0fd4656a8957c419e505443cdc98f623a18e20..9236a7b0e2af2f9fde8081684576940bae28fada 100644 (file)
@@ -42,7 +42,7 @@ using namespace common;
 const std::wstring CIIProtocolStrategy::MessageDelimiter = TEXT("\r\n");\r
 const TCHAR CIIProtocolStrategy::TokenDelimiter = TEXT('\\');\r
 \r
-CIIProtocolStrategy::CIIProtocolStrategy(const std::vector<renderer::render_device_ptr>& channels) \r
+CIIProtocolStrategy::CIIProtocolStrategy(const std::vector<channel_ptr>& channels) \r
 {\r
        if(channels.empty())\r
                BOOST_THROW_EXCEPTION(invalid_argument() << arg_name_info("channels"));\r
@@ -187,7 +187,7 @@ void CIIProtocolStrategy::WriteTemplateData(const std::wstring& templateName, co
        \r
        std::vector<std::wstring> params;\r
        params.push_back(server::template_folder()+TEXT("CG.fth"));\r
-       auto pFP = flash::create_flash_producer(params, GetChannel()->get_frame_format_desc());\r
+       auto pFP = flash::create_flash_producer(params);\r
        if(pFP != 0)\r
        {\r
                //TODO: Initialize with valid FrameFactory\r
@@ -221,11 +221,11 @@ void CIIProtocolStrategy::DisplayTemplate(const std::wstring& titleName)
 void CIIProtocolStrategy::DisplayMediaFile(const std::wstring& filename) \r
 {\r
        transition_info transition;\r
-       transition.type = transition_type::mix;\r
+       transition.type = transition::mix;\r
        transition.duration = 12;\r
 \r
-       auto pFP = load_media(boost::assign::list_of(filename), pChannel_->get_frame_format_desc());\r
-       auto pTransition = std::make_shared<transition_producer>(pFP, transition, pChannel_->get_frame_format_desc());\r
+       auto pFP = load_media(boost::assign::list_of(filename));\r
+       auto pTransition = std::make_shared<transition_producer>(pFP, transition);\r
 \r
        try\r
        {\r
index c109dcd9054b32439cc2863a59b0bf1476fa7d48..8c5de41dba7ae3667e4d2e294108ee935dc5a17b 100644 (file)
  \r
 #pragma once\r
 \r
+#include "../../channel.h"\r
+\r
 #include "../../../common/io/ProtocolStrategy.h"\r
 #include "CIICommand.h"\r
+\r
 #include "../../consumer/frame_consumer.h"\r
+#include "../../producer/frame_producer_device.h"\r
+\r
 #include "../../../common/concurrency/executor.h"\r
-#include "../../renderer/render_device.h"\r
 \r
 namespace caspar { namespace core { namespace cii {\r
 \r
 class CIIProtocolStrategy : public IO::IProtocolStrategy\r
 {\r
 public:\r
-       CIIProtocolStrategy(const std::vector<renderer::render_device_ptr>& channels);\r
+       CIIProtocolStrategy(const std::vector<channel_ptr>& channels);\r
 \r
        void Parse(const TCHAR* pData, int charCount, IO::ClientInfoPtr pClientInfo);\r
        UINT GetCodepage() {return 28591;}      //ISO 8859-1\r
 \r
        void SetProfile(const std::wstring& profile) {currentProfile_ = profile;}\r
 \r
-       renderer::render_device_ptr GetChannel() const{return this->pChannel_;}\r
+       channel_ptr GetChannel() const{return this->pChannel_;}\r
 \r
        void DisplayMediaFile(const std::wstring& filename);\r
        void DisplayTemplate(const std::wstring& titleName);\r
@@ -82,7 +86,7 @@ private:
        std::wstring currentMessage_;\r
 \r
        std::wstring currentProfile_;\r
-       renderer::render_device_ptr pChannel_;\r
+       channel_ptr pChannel_;\r
 };\r
 \r
 }}}
\ No newline at end of file
index 9c5d8f05f3b88845fab982a2dd60d88561c1de10..4b56c8bcfe6257ac9c31b0a6580967e2fb9fc379 100644 (file)
@@ -23,7 +23,7 @@
 #include "CLKProtocolStrategy.h"\r
 \r
 #include "..\..\producer\flash\cg_producer.h"\r
-#include "..\..\renderer\render_device.h"\r
+#include "..\..\producer\frame_producer_device.h"\r
 \r
 #include <string>\r
 #include <sstream>\r
@@ -33,7 +33,7 @@ namespace caspar { namespace core { namespace CLK {
 \r
 using namespace common;\r
 \r
-CLKProtocolStrategy::CLKProtocolStrategy(const std::vector<renderer::render_device_ptr>& channels) \r
+CLKProtocolStrategy::CLKProtocolStrategy(const std::vector<channel_ptr>& channels) \r
        : currentState_(ExpectingNewCommand), bClockLoaded_(false) \r
 {      \r
        if(channels.empty())\r
index 382b9e7aea8a07ad3f96a785d1ec4f7ab0e39185..1fbb4065f0249dfac7c1ea2c954320fe308473e6 100644 (file)
 \r
 #include "CLKCommand.h"\r
 #include "../../../common/io/ProtocolStrategy.h"\r
-#include "../../renderer/render_device.h"\r
+#include "../../producer/frame_producer_device.h"\r
+#include "../../channel.h"\r
 \r
 namespace caspar { namespace core { namespace CLK {\r
 \r
 class CLKProtocolStrategy : public IO::IProtocolStrategy\r
 {\r
 public:\r
-       CLKProtocolStrategy(const std::vector<renderer::render_device_ptr>& channels);\r
+       CLKProtocolStrategy(const std::vector<channel_ptr>& channels);\r
 \r
        void Parse(const TCHAR* pData, int charCount, IO::ClientInfoPtr pClientInfo);\r
        UINT GetCodepage() { return 28591; }    //ISO 8859-1\r
@@ -48,7 +49,7 @@ private:
        CLKCommand currentCommand_;\r
        std::wstringstream currentCommandString_;\r
 \r
-       renderer::render_device_ptr pChannel_;\r
+       channel_ptr pChannel_;\r
 \r
        bool bClockLoaded_;\r
 };\r
index a2ad3fd4e1dd3a50143f28da2fdc71eae9ed8c65..8a10e22b4ab4667f67622d4a30b7c26a2345ef12 100644 (file)
@@ -18,11 +18,11 @@ using namespace boost::assign;
 \r
 namespace caspar { namespace core { \r
        \r
-frame_producer_ptr load_media(const std::vector<std::wstring>& params, const frame_format_desc& format_desc)\r
+frame_producer_ptr load_media(const std::vector<std::wstring>& params)\r
 {              \r
-       typedef std::function<frame_producer_ptr(const std::vector<std::wstring>&, const frame_format_desc&)> ProducerFactory;\r
+       typedef std::function<frame_producer_ptr(const std::vector<std::wstring>&)> producer_factory;\r
 \r
-       const auto producerFactories = list_of<ProducerFactory>\r
+       const auto producer_factories = list_of<producer_factory>\r
                (&flash::create_flash_producer)\r
                (&flash::create_ct_producer)\r
                (&image::create_image_producer)\r
@@ -33,21 +33,21 @@ frame_producer_ptr load_media(const std::vector<std::wstring>& params, const fra
        if(params.empty())\r
                BOOST_THROW_EXCEPTION(invalid_argument() << arg_name_info("params") << arg_value_info(""));\r
 \r
-       frame_producer_ptr pProducer;\r
-       std::any_of(producerFactories.begin(), producerFactories.end(), [&](const ProducerFactory& producerFactory) -> bool\r
+       frame_producer_ptr producer;\r
+       std::any_of(producer_factories.begin(), producer_factories.end(), [&](const producer_factory& factory) -> bool\r
                {\r
                        try\r
                        {\r
-                               pProducer = producerFactory(params, format_desc);\r
+                               producer = factory(params);\r
                        }\r
                        catch(...)\r
                        {\r
                                CASPAR_LOG_CURRENT_EXCEPTION();\r
                        }\r
-                       return pProducer != nullptr;\r
+                       return producer != nullptr;\r
                });\r
 \r
-       return pProducer;\r
+       return producer;\r
 }\r
 \r
 }}\r
index 2ae9e7ab35e8d362427ccc324c426852c46de01c..bb7b06afef909d307a84bd100a114471277513c3 100644 (file)
@@ -1,6 +1,5 @@
 #pragma once\r
 \r
-#include "../frame/frame_fwd.h"\r
 #include "../producer/frame_producer.h"\r
 \r
 #include <string>\r
@@ -8,6 +7,6 @@
 \r
 namespace caspar { namespace core { \r
        \r
-frame_producer_ptr load_media(const std::vector<std::wstring>& params, const frame_format_desc& format_desc);\r
+frame_producer_ptr load_media(const std::vector<std::wstring>& params);\r
 \r
 }}\r
index 7bcb551f94f22a712376ffbf8c8182128286520a..3e62f131ec339ae6ca5b4abbc2208dc3f3e6d83c 100644 (file)
@@ -1,6 +1,7 @@
 #include "StdAfx.h"\r
 \r
 #include "server.h"\r
+#include "channel.h"\r
 \r
 #include "consumer/oal/oal_consumer.h"\r
 #ifndef DISABLE_BLUEFISH\r
 #include <boost/property_tree/ptree.hpp>\r
 #include <boost/property_tree/xml_parser.hpp>\r
 \r
+#include "producer/frame_producer_device.h"\r
+#include "consumer/frame_consumer_device.h"\r
+#include "processor/frame_processor_device.h"\r
+\r
 namespace caspar { namespace core {\r
 \r
 struct server::implementation : boost::noncopyable\r
@@ -111,7 +116,10 @@ struct server::implementation : boost::noncopyable
                                }\r
                        }\r
                        \r
-                       channels_.push_back(std::make_shared<renderer::render_device>(format_desc, consumers));\r
+                       auto processor_device = std::make_shared<frame_processor_device>(format_desc);\r
+                       auto producer_device = std::make_shared<frame_producer_device>(processor_device);\r
+                       auto consumer_device = std::make_shared<frame_consumer_device>(processor_device, format_desc, consumers);\r
+                       channels_.push_back(std::make_shared<channel>(producer_device, processor_device, consumer_device));\r
                }\r
        }\r
                \r
@@ -139,7 +147,6 @@ struct server::implementation : boost::noncopyable
                        catch(...)\r
                        {\r
                                CASPAR_LOG_CURRENT_EXCEPTION();\r
-                               throw;\r
                        }\r
                }\r
        }\r
@@ -157,8 +164,8 @@ struct server::implementation : boost::noncopyable
        }\r
 \r
        std::vector<IO::AsyncEventServerPtr> async_servers_;\r
-\r
-       std::vector<renderer::render_device_ptr> channels_;\r
+       \r
+       std::vector<channel_ptr> channels_;\r
 \r
        int logLevel_;\r
 \r
@@ -199,6 +206,8 @@ const std::wstring& server::data_folder()
        return server::implementation::data_folder_;\r
 }\r
 \r
-const std::vector<renderer::render_device_ptr>& server::get_channels() const{ return impl_->channels_; }\r
-\r
+const std::vector<channel_ptr> server::get_channels() const\r
+{\r
+       return impl_->channels_;\r
+}\r
 }}
\ No newline at end of file
index 7d46b108e91565155aca264aae496ba3146e3e9a..52b2e41f089eb7a5de17c188d3bfd91d84507637 100644 (file)
@@ -1,6 +1,8 @@
 #pragma once\r
 \r
-#include "renderer/renderer_fwd.h"\r
+#include "channel.h"\r
+\r
+#include "producer/frame_producer_device.h"\r
 \r
 #include <common/exception/exceptions.h>\r
 \r
@@ -20,9 +22,10 @@ public:
        static const std::wstring& media_folder();\r
        static const std::wstring& log_folder();\r
        static const std::wstring& template_folder();           \r
-       static const std::wstring& data_folder();       \r
+       static const std::wstring& data_folder();\r
+\r
+       const std::vector<channel_ptr> get_channels() const;\r
 \r
-       const std::vector<renderer::render_device_ptr>& get_channels() const;\r
 private:\r
        struct implementation;\r
        std::shared_ptr<implementation> impl_;\r
diff --git a/core/video/pixel_format.h b/core/video/pixel_format.h
new file mode 100644 (file)
index 0000000..c819811
--- /dev/null
@@ -0,0 +1,50 @@
+#pragma once\r
+\r
+#include <memory>\r
+#include <array>\r
+\r
+namespace caspar { namespace core {\r
+       \r
+struct pixel_format\r
+{\r
+       enum type\r
+       {\r
+               bgra,\r
+               rgba,\r
+               argb,\r
+               abgr,\r
+               ycbcr,\r
+               ycbcra,\r
+               count,\r
+               invalid\r
+       };\r
+};\r
+\r
+struct pixel_format_desc\r
+{\r
+       struct plane\r
+       {\r
+               plane() : width(0), height(0), size(0), channels(0){}\r
+               plane(size_t width, size_t height, size_t channels)\r
+                       : width(width), height(height), size(width*height*channels), channels(channels)\r
+               {}\r
+               size_t width;\r
+               size_t height;\r
+               size_t size;\r
+               size_t channels;\r
+       };\r
+\r
+       pixel_format_desc() : pix_fmt(pixel_format::invalid)\r
+       {\r
+               planes[0] = plane();\r
+               planes[1] = plane();\r
+               planes[2] = plane();\r
+               planes[3] = plane();\r
+       }\r
+\r
+       pixel_format::type pix_fmt;\r
+\r
+       std::array<plane, 4> planes;\r
+};\r
+       \r
+}}
\ No newline at end of file
diff --git a/core/video/video_format.cpp b/core/video/video_format.cpp
new file mode 100644 (file)
index 0000000..73f839e
--- /dev/null
@@ -0,0 +1,62 @@
+/*\r
+* copyright (c) 2010 Sveriges Television AB <info@casparcg.com>\r
+*\r
+*  This file is part of CasparCG.\r
+*\r
+*    CasparCG is free software: you can redistribute it and/or modify\r
+*    it under the terms of the GNU General Public License as published by\r
+*    the Free Software Foundation, either version 3 of the License, or\r
+*    (at your option) any later version.\r
+*\r
+*    CasparCG is distributed in the hope that it will be useful,\r
+*    but WITHOUT ANY WARRANTY; without even the implied warranty of\r
+*    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r
+*    GNU General Public License for more details.\r
+\r
+*    You should have received a copy of the GNU General Public License\r
+*    along with CasparCG.  If not, see <http://www.gnu.org/licenses/>.\r
+*\r
+*/\r
\r
+#include "..\StdAfx.h"\r
+\r
+#include "video_format.h"\r
+\r
+#include <boost/algorithm/string.hpp>\r
+\r
+#define DEFINE_VIDEOFORMATDESC(w, h, m, f, s, fmt) { (fmt), (w), (h), (m), (f), (w)*(h)*4, (s) }\r
+\r
+namespace caspar { namespace core {\r
+\r
+const video_format_desc video_format_desc::format_descs[video_format::count] =  \r
+{                                                                         \r
+       DEFINE_VIDEOFORMATDESC(720,  576,  video_update_format::upper,                  50,                     TEXT("PAL"),            video_format::pal               ), \r
+       DEFINE_VIDEOFORMATDESC(720,  486,  video_update_format::lower,                  60/1.001,       TEXT("NTSC"),           video_format::ntsc              ), \r
+       DEFINE_VIDEOFORMATDESC(720,  576,  video_update_format::progressive,            25,                     TEXT("576p2500"),       video_format::x576p2500 ),\r
+       DEFINE_VIDEOFORMATDESC(1280, 720,  video_update_format::progressive,            25,                     TEXT("720p2500"),       video_format::x720p2500 ), \r
+       DEFINE_VIDEOFORMATDESC(1280, 720,  video_update_format::progressive,            50,                     TEXT("720p5000"),       video_format::x720p5000 ), \r
+       DEFINE_VIDEOFORMATDESC(1280, 720,  video_update_format::progressive,            60/1.001,       TEXT("720p5994"),       video_format::x720p5994 ),\r
+       DEFINE_VIDEOFORMATDESC(1280, 720,  video_update_format::progressive,            60,                     TEXT("720p6000"),       video_format::x720p6000 ),\r
+       DEFINE_VIDEOFORMATDESC(1920, 1080, video_update_format::progressive,            24/1.001,       TEXT("1080p2397"),      video_format::x1080p2397),\r
+       DEFINE_VIDEOFORMATDESC(1920, 1080, video_update_format::progressive,            24,                     TEXT("1080p2400"),      video_format::x1080p2400),\r
+       DEFINE_VIDEOFORMATDESC(1920, 1080, video_update_format::upper,                  50,                     TEXT("1080i5000"),      video_format::x1080i5000),\r
+       DEFINE_VIDEOFORMATDESC(1920, 1080, video_update_format::upper,                  60/1.001,       TEXT("1080i5994"),      video_format::x1080i5994),\r
+       DEFINE_VIDEOFORMATDESC(1920, 1080, video_update_format::upper,                  60,                     TEXT("1080i6000"),      video_format::x1080i6000),\r
+       DEFINE_VIDEOFORMATDESC(1920, 1080, video_update_format::progressive,            25,                     TEXT("1080p2500"),      video_format::x1080p2500),\r
+       DEFINE_VIDEOFORMATDESC(1920, 1080, video_update_format::progressive,            30/1.001,       TEXT("1080p2997"),      video_format::x1080p2997),\r
+       DEFINE_VIDEOFORMATDESC(1920, 1080, video_update_format:: progressive,   30,                     TEXT("1080p3000"),      video_format::x1080p3000)\r
+};\r
+\r
+video_format::type get_video_format(const std::wstring& name)\r
+{\r
+       for(int n = 0; n < video_format::count; ++n)\r
+       {\r
+               if(boost::iequals(video_format_desc::format_descs[n].name, name))\r
+                       return static_cast<video_format::type>(n);\r
+       }\r
+\r
+       return video_format::invalid;\r
+}\r
+\r
+}}\r
+\r
diff --git a/core/video/video_format.h b/core/video/video_format.h
new file mode 100644 (file)
index 0000000..58359c7
--- /dev/null
@@ -0,0 +1,118 @@
+#pragma once\r
+\r
+#include <string>\r
+\r
+#include "../../common/compiler/vs/disable_silly_warnings.h"\r
+\r
+namespace caspar { namespace core {\r
+       \r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+/// \enum      video_format\r
+///\r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+struct video_format \r
+{ \r
+       enum type\r
+       {\r
+               pal = 0,\r
+               ntsc,\r
+               x576p2500,\r
+               x720p2500,\r
+               x720p5000,\r
+               x720p5994,\r
+               x720p6000,\r
+               x1080p2397,\r
+               x1080p2400,\r
+               x1080i5000,\r
+               x1080i5994,\r
+               x1080i6000,\r
+               x1080p2500,\r
+               x1080p2997,\r
+               x1080p3000,\r
+               count,\r
+               invalid\r
+       };\r
+};\r
+\r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+/// \enum      video_update_format\r
+///\r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+struct video_update_format \r
+{ \r
+       enum type\r
+       {\r
+                       progressive,\r
+                       lower,\r
+                       upper\r
+       };\r
+};\r
+\r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+/// \struct    video_format_desc\r
+///\r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+struct video_format_desc\r
+{\r
+       video_format::type                      format;\r
+\r
+       size_t                                          width;\r
+       size_t                                          height;\r
+       video_update_format::type       update;\r
+       double                                          fps;\r
+       size_t                                          size;\r
+       std::wstring                            name;\r
+\r
+       static const video_format_desc format_descs[video_format::count];\r
+};\r
+\r
+inline bool operator==(const video_format_desc& rhs, const video_format_desc& lhs)\r
+{\r
+       return rhs.format == lhs.format;\r
+}\r
+\r
+inline bool operator!=(const video_format_desc& rhs, const video_format_desc& lhs)\r
+{\r
+       return !(rhs == lhs);\r
+}\r
+\r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+/// \fn        video_format get_video_format(const std::wstring& strVideoMode);\r
+///\r
+/// \brief     Gets the *video_format* associated with the specified name.\r
+///\r
+/// \param     name    Name of the *video_format*.. \r
+///\r
+/// \return    The video format. \r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+video_format::type get_video_format(const std::wstring& name);\r
+\r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+/// \fn        video_format get_video_format_desc(const std::wstring& strVideoMode);\r
+///\r
+/// \brief     Gets the *video_format_desc* associated with the specified name.\r
+///\r
+/// \param     name    Name of the *video_format_desc*.. \r
+///\r
+/// \return    The video format. \r
+////////////////////////////////////////////////////////////////////////////////////////////////////\r
+inline video_format_desc get_video_format_desc(const std::wstring& name, video_format::type default_format = video_format::x576p2500)\r
+{                      \r
+       auto casparVideoFormat = default_format;\r
+       if(!name.empty())\r
+               casparVideoFormat = get_video_format(name);\r
+       return video_format_desc::format_descs[casparVideoFormat];\r
+}\r
+\r
+inline double render_video_format_period(const video_format_desc& format_desc)\r
+{\r
+       return 1.0/(format_desc.update == video_update_format::progressive ? format_desc.fps : format_desc.fps/2.0);\r
+}\r
+\r
+inline std::wostream& operator<<(std::wostream& out, const video_format_desc& format_desc)\r
+{\r
+  out << format_desc.name.c_str();\r
+  return out;\r
+}\r
+\r
+}}
\ No newline at end of file
index 6678d2514b9094deee90bf6ac562c7ba57ed1097..f8a7e235300f7d000d79e35d5e7cae7811f1870e 100644 (file)
@@ -8,25 +8,25 @@
   </paths>\r
   <channels>\r
     <channel>\r
-      <videomode>1080p2500</videomode>\r
+      <videomode>PAL</videomode>\r
       <consumers>\r
-        <ogl>\r
+        <!--ogl>\r
           <device>1</device>\r
           <stretch>uniform</stretch>\r
           <windowed>true</windowed>\r
         </ogl>\r
-        <audio/>\r
-        <!--bluefish>\r
+        <audio/-->\r
+        <bluefish>\r
           <device>1</device> \r
           <embedded-audio>true</embedded-audio>\r
-        </bluefish-->\r
+        </bluefish>\r
       </consumers>\r
     </channel>\r
   </channels>\r
   <controllers>\r
-    <tcpcontroller>\r
+    <!--tcpcontroller>\r
       <port>5250</port>\r
       <protocol>AMCP</protocol>\r
-    </tcpcontroller>\r
+    </tcpcontroller-->\r
   </controllers>\r
 </configuration>
\ No newline at end of file
index 5218a02457133d54b2fddd14e7a3f3c0d7b7f604..8adf99c5da5f4a7b74b04685d03abab3afe6c228 100644 (file)
@@ -121,4 +121,4 @@ int main(int argc, wchar_t* argv[])
        CASPAR_LOG(debug) << "Ended Main Thread";\r
 \r
        return 0;\r
-}\r
+}
\ No newline at end of file
index 85f9fc928cf01bf7858e9fd5717e6609b49f7f58..d6c741ad6a33573064c23d8293865b5b777fc007 100644 (file)
@@ -1,10 +1,10 @@
 #pragma once\r
 \r
-#include <core/frame/gpu_frame.h>\r
+#include <core/processor/frame.h>\r
 \r
-struct mock_frame : public caspar::core::gpu_frame\r
+struct mock_frame : public caspar::core::frame\r
 {\r
-       mock_frame(void* tag, short volume = 100) : caspar::core::gpu_frame(0,0), tag(tag)\r
+       mock_frame(void* tag, short volume = 100) : caspar::core::frame(0,0), tag(tag)\r
        {\r
                audio_data().resize(100, volume);\r
        }\r
index 483f3861e266f7b69514c0e04628de15a3caba3c..d558cbb72f27acbe99ae609e769330dc9578ab4f 100644 (file)
@@ -1,11 +1,11 @@
 #pragma once\r
 \r
-#include <core/frame/frame_factory.h>\r
-#include <core/frame/gpu_frame.h>\r
+#include <core/video/frame_factory.h>\r
+#include <core/processor/frame.h>\r
 \r
 struct mock_frame_factory : public caspar::core::frame_factory\r
 {\r
-       virtual gpu_frame_ptr create_frame(size_t width, size_t height)\r
+       virtual frame_ptr create_frame(size_t width, size_t height)\r
        {\r
                return std::make_shared<mock_frame>();\r
        }\r
index 1c7af7e24fbc5e454c8ef1564872e83bd9fe0b50..7acab1d15199cefee144a0ee4c9637b3f2b2821c 100644 (file)
@@ -14,7 +14,7 @@ public:
        mock_frame_producer(bool null = false, bool throws = false) \r
                : null_(null), throws_(throws), initialized_(false), volume_(100){}\r
        void set_volume(short volume) { volume_ = volume;}\r
-       gpu_frame_ptr render_frame()\r
+       frame_ptr render_frame()\r
        { \r
                if(throws_)\r
                        BOOST_THROW_EXCEPTION(caspar_exception());\r
@@ -28,12 +28,12 @@ public:
        { return following_; }\r
        void set_leading_producer(const std::shared_ptr<frame_producer>& leading) \r
        { leading_ = leading; }\r
-       const frame_format_desc& get_frame_format_desc() const\r
+       const video_format_desc& get_video_format_desc() const\r
        { \r
-               static frame_format_desc format;\r
+               static video_format_desc format;\r
                return format;\r
        }\r
-       void initialize(const frame_factory_ptr& factory)\r
+       void initialize(const frame_processor_device_ptr& factory)\r
        {initialized_ = true;}\r
        void set_following_producer(const std::shared_ptr<frame_producer>& following)\r
        {following_ = following;}\r
index 72ddeaaffb183cc81a97cd9931214d06437e7ea2..bb2271f06b2aad7427b78046f2fc700a30af1f58 100644 (file)
@@ -3,19 +3,19 @@
 #include "../../mock/mock_frame_producer.h"\r
 #include "../../mock/mock_frame.h"\r
 \r
-#include <core/frame/frame_format.h>\r
-#include <core/frame/gpu_frame.h>\r
+#include <core/video/video_format.h>\r
+#include <core/processor/frame.h>\r
 #include <core/producer/transition/transition_producer.h>\r
 #include <common/exception/exceptions.h>\r
 \r
 using namespace caspar;\r
 using namespace caspar::core;\r
 \r
-frame_format_desc test_format = frame_format_desc::format_descs[frame_format::pal];\r
+video_format_desc test_format = video_format_desc::format_descs[video_format::pal];\r
 \r
 TEST(transition_producer, constructor_dest_nullptr) \r
 {\r
-       ASSERT_THROW(transition_producer(nullptr, transition_info(), test_format);\r
+       ASSERT_THROW(transition_producer(nullptr, transition_info());\r
                                        , null_argument);       \r
 }\r
 \r
@@ -23,25 +23,16 @@ TEST(transition_producer, get_following_producer)
 {\r
        auto dest = std::make_shared<mock_frame_producer>();\r
        \r
-       transition_producer producer(dest, transition_info(), test_format);\r
+       transition_producer producer(dest, transition_info());\r
 \r
        ASSERT_TRUE(producer.get_following_producer() == dest);\r
 }\r
 \r
-TEST(transition_producer, get_frame_format_desc) \r
-{\r
-       auto dest = std::make_shared<mock_frame_producer>();\r
-       \r
-       transition_producer producer(dest, transition_info(), test_format);\r
-\r
-       ASSERT_TRUE(producer.get_frame_format_desc() == test_format);\r
-}\r
-\r
 TEST(transition_producer, null_dest_get_frame) \r
 {\r
        auto source = std::make_shared<mock_frame_producer>();\r
        \r
-       transition_producer producer(nullptr, transition_info(), test_format);\r
+       transition_producer producer(nullptr, transition_info());\r
        producer.set_leading_producer(source);\r
 \r
        ASSERT_TRUE(producer.render_frame() == nullptr);\r
@@ -52,9 +43,9 @@ TEST(transition_producer, null_source_get_frame_cut)
        auto dest = std::make_shared<mock_frame_producer>();\r
        \r
        transition_info info;\r
-       info.type = transition_type::cut;\r
+       info.type = transition::cut;\r
 \r
-       transition_producer producer(dest, info, test_format);\r
+       transition_producer producer(dest, info);\r
 \r
        ASSERT_TRUE(producer.render_frame() == nullptr);\r
 }\r
@@ -63,7 +54,7 @@ TEST(transition_producer, initialize)
 {\r
        auto dest = std::make_shared<mock_frame_producer>();\r
        \r
-       transition_producer producer(dest, transition_info(), test_format);\r
+       transition_producer producer(dest, transition_info());\r
        producer.initialize(nullptr);\r
        \r
        ASSERT_TRUE(dest->is_initialized());\r
@@ -75,10 +66,10 @@ TEST(transition_producer, duration)
        auto source = std::make_shared<mock_frame_producer>();\r
        \r
        transition_info info;\r
-       info.type = transition_type::cut;\r
+       info.type = transition::cut;\r
        info.duration = 3;\r
 \r
-       transition_producer producer(dest, info, test_format);\r
+       transition_producer producer(dest, info);\r
        producer.set_leading_producer(source);\r
 \r
        for(int n = 0; n < info.duration; ++n)\r