xref: /haiku/src/add-ons/media/media-add-ons/videowindow/VideoView.cpp (revision 0562493379cd52eb7103531f895f10bb8e77c085)
1 /*
2  * Copyright (C) 2006 Marcus Overhagen <marcus@overhagen.de>. All rights reserved.
3  *
4  * Distributed under the terms of the MIT License.
5  */
6 #include "VideoNode.h"
7 #include "VideoView.h"
8 #include "debug.h"
9 
10 #include <Bitmap.h>
11 #include <Locker.h>
12 #include <MediaRoster.h>
13 #include <Message.h>
14 
15 
16 #include <stdio.h>
17 #include <stdlib.h>
18 #include <string.h>
19 
20 
21 VideoView::VideoView(BRect frame, const char *name, uint32 resizeMask, uint32 flags, VideoNode *node)
22  :	BView(frame, name, resizeMask, flags)
23  ,	fVideoNode(node)
24  ,	fOverlayActive(false)
25 {
26 	SetViewColor(B_TRANSPARENT_COLOR);
27 }
28 
29 
30 VideoView::~VideoView()
31 {
32 }
33 
34 
35 void
36 VideoView::AttachedToWindow()
37 {
38 }
39 
40 
41 VideoNode *
42 VideoView::Node()
43 {
44 	return fVideoNode;
45 }
46 
47 
48 void
49 VideoView::OverlayLockAcquire()
50 {
51 	CALLED();
52 }
53 
54 
55 void
56 VideoView::OverlayLockRelease()
57 {
58 	CALLED();
59 	// overlaybitmap->UnlockBits
60 }
61 
62 
63 void
64 VideoView::OverlayScreenshotPrepare()
65 {
66 	CALLED();
67 /*
68 	fVideoNode->LockBitmap();
69 	if (fOverlayActive) {
70 		BBitmap *bmp = fVideoNode->Bitmap();
71 		if (bmp) {
72 //			Window()->UpdateIfNeeded();
73 //			Sync();
74 			BBitmap *tmp = new BBitmap(bmp->Bounds(), 0, B_RGB32);
75 //			ConvertBitmap(tmp, bmp);
76 			ClearViewOverlay();
77 			DrawBitmap(tmp, Bounds());
78 			delete tmp;
79 //			Sync();
80 		}
81 	}
82 	fVideoNode->UnlockBitmap();
83 */
84 }
85 
86 
87 void
88 VideoView::OverlayScreenshotCleanup()
89 {
90 	CALLED();
91 /*
92 	snooze(50000); // give app server some time to take the screenshot
93 	fVideoNode->LockBitmap();
94 	if (fOverlayActive) {
95 		BBitmap *bmp = fVideoNode->Bitmap();
96 		if (bmp) {
97 			DrawBitmap(bmp, Bounds());
98 			SetViewOverlay(bmp, bmp->Bounds(), Bounds(), &fOverlayKeyColor,
99 				B_FOLLOW_ALL, B_OVERLAY_FILTER_HORIZONTAL | B_OVERLAY_FILTER_VERTICAL);
100 			Invalidate();
101 		}
102 	}
103 	fVideoNode->UnlockBitmap();
104 */
105 }
106 
107 
108 void
109 VideoView::RemoveVideoDisplay()
110 {
111 	CALLED();
112 
113 	if (fOverlayActive) {
114 		ClearViewOverlay();
115 		fOverlayActive = false;
116 	}
117 	Invalidate();
118 }
119 
120 
121 void
122 VideoView::RemoveOverlay()
123 {
124 	CALLED();
125 	if (LockLooperWithTimeout(50000) == B_OK) {
126 		ClearViewOverlay();
127 		fOverlayActive = false;
128 		UnlockLooper();
129 	}
130 }
131 
132 
133 void
134 VideoView::Draw(BRect updateRect)
135 {
136 	if (fOverlayActive) {
137 		SetHighColor(fOverlayKeyColor);
138 		FillRect(updateRect);
139 	} else {
140 		fVideoNode->LockBitmap();
141 		BBitmap *bmp = fVideoNode->Bitmap();
142 		if (!bmp) {
143 			SetHighColor(0, 0, 0, 0);
144 			FillRect(updateRect);
145 		} else
146 			DrawBitmap(bmp, Bounds());
147 		fVideoNode->UnlockBitmap();
148 	}
149 }
150 
151 
152 void
153 VideoView::DrawFrame()
154 {
155 	//CALLED();
156 
157 	bool want_overlay = fVideoNode->IsOverlayActive();
158 
159 	if (!want_overlay && fOverlayActive) {
160 		if (LockLooperWithTimeout(50000) == B_OK) {
161 			ClearViewOverlay();
162 			UnlockLooper();
163 			fOverlayActive = false;
164 		} else {
165 			fprintf(stderr, "VideoView::DrawFrame: cannot ClearViewOverlay, as LockLooperWithTimeout failed\n");
166 		}
167 	}
168 
169 	if (want_overlay && !fOverlayActive) {
170 		fVideoNode->LockBitmap();
171 		BBitmap *bmp = fVideoNode->Bitmap();
172 		if (bmp && LockLooperWithTimeout(50000) == B_OK) {
173 			SetViewOverlay(bmp, bmp->Bounds(), Bounds(), &fOverlayKeyColor,
174 				B_FOLLOW_ALL, B_OVERLAY_FILTER_HORIZONTAL | B_OVERLAY_FILTER_VERTICAL);
175 			fOverlayActive = true;
176 
177 			Invalidate();
178 			UnlockLooper();
179 		}
180 		fVideoNode->UnlockBitmap();
181 	}
182 	if (!fOverlayActive) {
183 		if (LockLooperWithTimeout(50000) != B_OK)
184 			return;
185 		Invalidate();
186 		UnlockLooper();
187 	}
188 }
189 
190 
191 void
192 VideoView::MessageReceived(BMessage *msg)
193 {
194 	switch (msg->what) {
195 
196 		default:
197 			BView::MessageReceived(msg);
198 	}
199 }
200 
201 
202 bool
203 VideoView::IsOverlaySupported()
204 {
205 	struct colorcombo {
206 		color_space colspace;
207 		const char *name;
208 	} colspace[] = {
209 		{ B_RGB32,		"B_RGB32"},
210 		{ B_RGBA32,		"B_RGBA32"},
211 		{ B_RGB24,		"B_RGB24"},
212 		{ B_RGB16,		"B_RGB16"},
213 		{ B_RGB15,		"B_RGB15"},
214 		{ B_RGBA15,		"B_RGBA15"},
215 		{ B_RGB32_BIG,	"B_RGB32_BIG"},
216 		{ B_RGBA32_BIG,	"B_RGBA32_BIG "},
217 		{ B_RGB24_BIG,	"B_RGB24_BIG "},
218 		{ B_RGB16_BIG,	"B_RGB16_BIG "},
219 		{ B_RGB15_BIG,	"B_RGB15_BIG "},
220 		{ B_RGBA15_BIG, "B_RGBA15_BIG "},
221 		{ B_YCbCr422,	"B_YCbCr422"},
222 		{ B_YCbCr411,	"B_YCbCr411"},
223 		{ B_YCbCr444,	"B_YCbCr444"},
224 		{ B_YCbCr420,	"B_YCbCr420"},
225 		{ B_YUV422,		"B_YUV422"},
226 		{ B_YUV411,		"B_YUV411"},
227 		{ B_YUV444,		"B_YUV444"},
228 		{ B_YUV420,		"B_YUV420"},
229 		{ B_NO_COLOR_SPACE, NULL}
230 	};
231 
232 	bool supported = false;
233 	for (int i = 0; colspace[i].name; i++) {
234 		BBitmap *test = new BBitmap(BRect(0,0,320,240),	B_BITMAP_WILL_OVERLAY | B_BITMAP_RESERVE_OVERLAY_CHANNEL, colspace[i].colspace);
235 		if (test->InitCheck() == B_OK) {
236 			printf("Display supports %s (0x%08x) overlay\n", colspace[i].name, colspace[i].colspace);
237 			supported = true;
238 		}
239 		delete test;
240 //		if (supported)
241 //			break;
242 	}
243 	return supported;
244 }
245