]> git.sesse.net Git - casparcg/blob - core/frame/composite_gpu_frame.cpp
2.0.0.2:
[casparcg] / core / frame / composite_gpu_frame.cpp
1 #include "../StdAfx.h"\r
2 \r
3 #include "composite_gpu_frame.h"\r
4 #include "../../common/gl/utility.h"\r
5 #include "../../common/utility/memory.h"\r
6 \r
7 #include <algorithm>\r
8 #include <numeric>\r
9 \r
10 namespace caspar {\r
11         \r
12 struct composite_gpu_frame::implementation\r
13 {\r
14         implementation(composite_gpu_frame* self) : self_(self){}\r
15 \r
16         void write_lock()\r
17         {\r
18                 std::for_each(frames_.begin(), frames_.end(), std::mem_fn(&gpu_frame::write_lock));             \r
19         }\r
20 \r
21         bool write_unlock()\r
22         {\r
23                 return std::all_of(frames_.begin(), frames_.end(), std::mem_fn(&gpu_frame::write_unlock));                      \r
24         }\r
25         \r
26         void read_lock(GLenum mode)\r
27         {       \r
28                 std::for_each(frames_.begin(), frames_.end(), std::bind(&gpu_frame::read_lock, std::placeholders::_1, mode));           \r
29         }\r
30 \r
31         bool read_unlock()\r
32         {\r
33                 return std::all_of(frames_.begin(), frames_.end(), std::mem_fn(&gpu_frame::read_unlock));               \r
34         }\r
35 \r
36         void draw()\r
37         {\r
38                 glPushMatrix();\r
39                 glTranslatef(self_->x()*2.0f, self_->y()*2.0f, 0.0f);\r
40                 std::for_each(frames_.begin(), frames_.end(), std::mem_fn(&gpu_frame::draw));\r
41                 glPopMatrix();\r
42         }\r
43                 \r
44         void add(const gpu_frame_ptr& frame)\r
45         {\r
46                 frames_.push_back(frame);\r
47 \r
48                 if(audio_data_.empty())\r
49                         audio_data_ = std::move(frame->audio_data());\r
50                 else\r
51                 {\r
52                         for(size_t n = 0; n < frame->audio_data().size(); ++n)\r
53                                 audio_data_[n] = static_cast<short>(static_cast<int>(audio_data_[n]) + static_cast<int>(frame->audio_data()[n]) & 0xFFFF);                              \r
54                 }\r
55         }\r
56 \r
57         unsigned char* data()\r
58         {\r
59                 BOOST_THROW_EXCEPTION(invalid_operation());\r
60         }\r
61 \r
62         composite_gpu_frame* self_;\r
63         std::vector<gpu_frame_ptr> frames_;\r
64         size_t size_;\r
65         std::vector<short> audio_data_;\r
66 };\r
67 \r
68 #pragma warning (disable : 4355)\r
69 \r
70 composite_gpu_frame::composite_gpu_frame(size_t width, size_t height) : gpu_frame(width, height), impl_(new implementation(this)){}\r
71 void composite_gpu_frame::write_lock(){impl_->write_lock();}\r
72 bool composite_gpu_frame::write_unlock(){return impl_->write_unlock();} \r
73 void composite_gpu_frame::read_lock(GLenum mode){impl_->read_lock(mode);}\r
74 bool composite_gpu_frame::read_unlock(){return impl_->read_unlock();}\r
75 void composite_gpu_frame::draw(){impl_->draw();}\r
76 unsigned char* composite_gpu_frame::data(){return impl_->data();}\r
77 const std::vector<short>& composite_gpu_frame::audio_data() const { return impl_->audio_data_; }        \r
78 std::vector<short>& composite_gpu_frame::audio_data() { return impl_->audio_data_; }\r
79 void composite_gpu_frame::reset(){impl_->audio_data_.clear();}\r
80 void composite_gpu_frame::add(const gpu_frame_ptr& frame){impl_->add(frame);}\r
81 \r
82 }