xref: /haiku/src/kits/interface/Screen.cpp (revision 922e7ba1f3228e6f28db69b0ded8f86eb32dea17)
1 /*
2  * Copyright 2003-2009, Haiku Inc.
3  * Distributed under the terms of the MIT License.
4  *
5  * Authors:
6  *		Stefano Ceccherini (burton666@libero.it)
7  *		Axel Dörfler, axeld@pinc-software.de
8  */
9 
10 
11 /*!	BScreen lets you retrieve and change the display settings. */
12 
13 
14 #include <Screen.h>
15 
16 #include <Window.h>
17 
18 #include <PrivateScreen.h>
19 
20 
21 using namespace BPrivate;
22 
23 
24 /*!	\brief Creates a BScreen object which represents the display with the given
25 		screen_id
26 	\param id The screen_id of the screen to get.
27 
28 	In the current implementation, there is only one display (B_MAIN_SCREEN_ID).
29 	To be sure that the object was correctly constructed, call IsValid().
30 */
31 BScreen::BScreen(screen_id id)
32 {
33 	fScreen = BPrivateScreen::Get(id.id);
34 }
35 
36 
37 /*!	\brief Creates a BScreen object which represents the display which contains
38 	the given BWindow.
39 	\param window A BWindow.
40 */
41 BScreen::BScreen(BWindow* window)
42 {
43 	fScreen = BPrivateScreen::Get(window);
44 }
45 
46 
47 /*!	\brief Releases the resources allocated by the constructor.
48 */
49 BScreen::~BScreen()
50 {
51 	BPrivateScreen::Put(fScreen);
52 }
53 
54 
55 /*! \brief Checks if the BScreen object represents a real screen connected to
56 		the computer.
57 	\return \c true if the BScreen object is valid, \c false if not.
58 */
59 bool
60 BScreen::IsValid()
61 {
62 	return fScreen != NULL && fScreen->IsValid();
63 }
64 
65 
66 /*!	\brief In the current implementation, this function always returns B_ERROR.
67 	\return Always \c B_ERROR.
68 */
69 status_t
70 BScreen::SetToNext()
71 {
72 	if (fScreen != NULL) {
73 		BPrivateScreen* screen = BPrivateScreen::GetNext(fScreen);
74 		if (screen != NULL) {
75 			fScreen = screen;
76 			return B_OK;
77 		}
78 	}
79 	return B_ERROR;
80 }
81 
82 
83 /*!	\brief Returns the color space of the screen display.
84 	\return \c B_CMAP8, \c B_RGB15, or \c B_RGB32, or \c B_NO_COLOR_SPACE
85 		if the screen object is invalid.
86 */
87 color_space
88 BScreen::ColorSpace()
89 {
90 	if (fScreen != NULL)
91 		return fScreen->ColorSpace();
92 	return B_NO_COLOR_SPACE;
93 }
94 
95 
96 /*!	\brief Returns the rectangle that locates the screen in the screen
97 		coordinate system.
98 	\return a BRect that locates the screen in the screen coordinate system.
99 */
100 BRect
101 BScreen::Frame()
102 {
103 	if (fScreen != NULL)
104 		return fScreen->Frame();
105 	return BRect(0, 0, 0, 0);
106 }
107 
108 
109 /*!	\brief Returns the identifier for the screen.
110 	\return A screen_id struct that identifies the screen.
111 
112 	In the current implementation, this function always returns
113 	\c B_MAIN_SCREEN_ID, even if the object is invalid.
114 */
115 screen_id
116 BScreen::ID()
117 {
118 	if (fScreen != NULL) {
119 		screen_id id = { fScreen->ID() };
120 		return id;
121 	}
122 
123 	return B_MAIN_SCREEN_ID;
124 }
125 
126 
127 /*!	\brief Blocks until the monitor has finished the current vertical retrace.
128 	\return \c B_OK, or \c B_ERROR if the screen object is invalid.
129 */
130 status_t
131 BScreen::WaitForRetrace()
132 {
133 	return WaitForRetrace(B_INFINITE_TIMEOUT);
134 }
135 
136 
137 /*!	\brief Blocks until the monitor has finished the current vertical retrace,
138 	or until the given timeout has passed.
139 	\param timeout A bigtime_t which indicates the time to wait before
140 		returning.
141 	\return \c B_OK if the monitor has retraced in the given amount of time,
142 		\c B_ERROR otherwise.
143 */
144 status_t
145 BScreen::WaitForRetrace(bigtime_t timeout)
146 {
147 	if (fScreen != NULL)
148 		return fScreen->WaitForRetrace(timeout);
149 	return B_ERROR;
150 }
151 
152 
153 /*!	\brief Returns the index of the 8-bit color that,
154 		most closely matches the given 32-bit color.
155 	\param r The red value for a 32-bit color.
156 	\param g The green value for a 32-bit color.
157 	\param b The blue value for a 32-bit color.
158 	\param a The alpha value for a 32-bit color.
159 	\return An index for a 8-bit color in the screen's color map.
160 */
161 uint8
162 BScreen::IndexForColor(uint8 r, uint8 g, uint8 b, uint8 a)
163 {
164 	if (fScreen != NULL)
165 		return fScreen->IndexForColor(r, g, b, a);
166 	return 0;
167 }
168 
169 
170 /*!	\brief Returns the 32-bit color representation of a given 8-bit color index.
171 	\param index The 8-bit color index to convert.
172 	\return A rgb_color struct which represents the given 8-bit color index.
173 */
174 rgb_color
175 BScreen::ColorForIndex(const uint8 index)
176 {
177 	if (fScreen != NULL)
178 		return fScreen->ColorForIndex(index);
179 	return rgb_color();
180 }
181 
182 
183 /*!	\brief Returns the "inversion" of the given 8-bit color.
184 	\param index An 8-bit color index.
185 	\return An 8-bit color index that represents the "inversion" of the given
186 		color.
187 */
188 uint8
189 BScreen::InvertIndex(uint8 index)
190 {
191 	if (fScreen != NULL)
192 		return fScreen->InvertIndex(index);
193 	return 0;
194 }
195 
196 
197 /*!	\brief Returns the color map of the current display.
198 	\return A pointer to the object's color_map.
199 */
200 const color_map*
201 BScreen::ColorMap()
202 {
203 	if (fScreen != NULL)
204 		return fScreen->ColorMap();
205 	return NULL;
206 }
207 
208 
209 /*!	\brief Copies the screen's contents into the first argument BBitmap.
210 	\param screen_shot A pointer to a BBitmap pointer, where the function will
211 		allocate a BBitmap for you.
212 	\param draw_cursor Specifies if you want the cursor to be drawn.
213 	\param bound Let you specify the area you want copied. If it's NULL, the
214 		entire screen is copied.
215 	\return \c B_OK if the operation was succesful, \c B_ERROR on failure.
216 */
217 status_t
218 BScreen::GetBitmap(BBitmap** _bitmap, bool drawCursor, BRect* bounds)
219 {
220 	if (fScreen != NULL)
221 		return fScreen->GetBitmap(_bitmap, drawCursor, bounds);
222 	return B_ERROR;
223 }
224 
225 
226 /*!	\brief Copies the screen's contents into the first argument BBitmap.
227 	\param screen_shot A pointer to an allocated BBitmap, where the function
228 		will store the screen's content.
229 	\param draw_cursor Specifies if you want the cursor to be drawn.
230 	\param bound Let you specify the area you want copied. If it's NULL, the
231 		entire screen is copied.
232 	\return \c B_OK if the operation was succesful, \c B_ERROR on failure.
233 
234 	The only difference between this method and GetBitmap() is that ReadBitmap
235 	requires you to allocate a BBitmap, while the latter will allocate a BBitmap
236 	for you.
237 */
238 status_t
239 BScreen::ReadBitmap(BBitmap* buffer, bool drawCursor, BRect* bounds)
240 {
241 	if (fScreen != NULL)
242 		return fScreen->ReadBitmap(buffer, drawCursor, bounds);
243 	return B_ERROR;
244 }
245 
246 
247 /*!	\brief Returns the color of the desktop.
248 	\return An rgb_color structure which is the color of the desktop.
249 */
250 rgb_color
251 BScreen::DesktopColor()
252 {
253 	if (fScreen != NULL)
254 		return fScreen->DesktopColor(B_CURRENT_WORKSPACE_INDEX);
255 
256 	return rgb_color();
257 }
258 
259 
260 /*!	\brief Returns the color of the desktop in the given workspace.
261 	\param workspace The workspace of which you want to have the color.
262 	\return An rgb_color structure which is the color of the desktop in the
263 		given workspace.
264 */
265 rgb_color
266 BScreen::DesktopColor(uint32 workspace)
267 {
268 	if (fScreen != NULL)
269 		return fScreen->DesktopColor(workspace);
270 
271 	return rgb_color();
272 }
273 
274 
275 /*!	\brief Set the color of the desktop.
276 	\param rgb The color you want to paint the desktop background.
277 	\param stick If you pass \c true here, the color will be maintained across
278 		boots.
279 */
280 void
281 BScreen::SetDesktopColor(rgb_color rgb, bool stick)
282 {
283 	if (fScreen != NULL)
284 		fScreen->SetDesktopColor(rgb, B_CURRENT_WORKSPACE_INDEX, stick);
285 }
286 
287 
288 /*!	\brief Set the color of the desktop in the given workspace.
289 	\param rgb The color you want to paint the desktop background.
290 	\param index The workspace you want to change the color.
291 	\param stick If you pass \c true here, the color will be maintained across
292 		boots.
293 */
294 void
295 BScreen::SetDesktopColor(rgb_color rgb, uint32 index, bool stick)
296 {
297 	if (fScreen != NULL)
298 		fScreen->SetDesktopColor(rgb, index, stick);
299 }
300 
301 
302 /*!	\brief Attempts to adjust the supplied mode so that it's a supported mode.
303 	\param target The mode you want to be adjusted.
304 	\param low The lower limit you want target to be adjusted.
305 	\param high The higher limit you want target to be adjusted.
306 	\return
307 		- \c B_OK if target (as returned) is supported and falls into the
308 			limits.
309 		- \c B_BAD_VALUE if target (as returned) is supported but doesn't fall
310 			into the limits.
311 		- \c B_ERROR if target isn't supported.
312 */
313 status_t
314 BScreen::ProposeMode(display_mode* target, const display_mode* low,
315 	const display_mode* high)
316 {
317 	if (fScreen != NULL)
318 		return fScreen->ProposeMode(target, low, high);
319 	return B_ERROR;
320 }
321 
322 
323 /*!	\brief allocates and returns a list of the display_modes
324 		that the graphics card supports.
325 	\param mode_list A pointer to a mode_list pointer, where the function will
326 		allocate an array of display_mode structures.
327 	\param count A pointer to an integer, where the function will store the
328 		amount of available display modes.
329 	\return \c B_OK.
330 */
331 status_t
332 BScreen::GetModeList(display_mode** _modeList, uint32* _count)
333 {
334 	if (fScreen != NULL)
335 		return fScreen->GetModeList(_modeList, _count);
336 	return B_ERROR;
337 }
338 
339 
340 /*!	\brief Copies the current display_mode into mode.
341 	\param mode A pointer to a display_mode structure,
342 		where the current display_mode will be copied.
343 	\return \c B_OK if the operation was succesful.
344 */
345 status_t
346 BScreen::GetMode(display_mode* mode)
347 {
348 	if (fScreen != NULL)
349 		return fScreen->GetMode(B_CURRENT_WORKSPACE_INDEX, mode);
350 	return B_ERROR;
351 }
352 
353 
354 /*!	\brief Copies the current display_mode of the given workspace into mode.
355 	\param workspace The index of the workspace to query.
356 	\param mode A pointer to a display_mode structure,
357 		where the current display_mode will be copied.
358 	\return \c B_OK if the operation was succesful.
359 */
360 status_t
361 BScreen::GetMode(uint32 workspace, display_mode* mode)
362 {
363 	if (fScreen != NULL)
364 		return fScreen->GetMode(workspace, mode);
365 	return B_ERROR;
366 }
367 
368 
369 /*!	\brief Set the screen to the given mode.
370 	\param mode A pointer to a display_mode.
371 	\param makeDefault If true, the mode becomes the default for the screen.
372 	\return \c B_OK.
373 */
374 status_t
375 BScreen::SetMode(display_mode* mode, bool makeDefault)
376 {
377 	if (fScreen != NULL)
378 		return fScreen->SetMode(B_CURRENT_WORKSPACE_INDEX, mode, makeDefault);
379 	return B_ERROR;
380 }
381 
382 
383 /*!	\brief Set the given workspace to the given mode.
384 	\param workspace The index of the workspace that you want to change.
385 	\param mode A pointer to a display_mode.
386 	\param makeDefault If true, the mode becomes the default for the workspace.
387 	\return \c B_OK.
388 */
389 status_t
390 BScreen::SetMode(uint32 workspace, display_mode* mode, bool makeDefault)
391 {
392 	if (fScreen != NULL)
393 		return fScreen->SetMode(workspace, mode, makeDefault);
394 	return B_ERROR;
395 }
396 
397 
398 /*!	\brief Returns information about the graphics card.
399 	\param info An accelerant_device_info struct where to store the retrieved
400 		info.
401 	\return \c B_OK if the operation went fine, otherwise an error code.
402 */
403 status_t
404 BScreen::GetDeviceInfo(accelerant_device_info* info)
405 {
406 	if (fScreen != NULL)
407 		return fScreen->GetDeviceInfo(info);
408 	return B_ERROR;
409 }
410 
411 
412 status_t
413 BScreen::GetMonitorInfo(monitor_info* info)
414 {
415 	if (fScreen != NULL)
416 		return fScreen->GetMonitorInfo(info);
417 	return B_ERROR;
418 }
419 
420 
421 /*!	\brief Returns, in low and high, the minimum and maximum pixel clock rates
422 		that are possible for the given mode.
423 	\param mode A pointer to a display_mode.
424 	\param low A pointer to an int where the function will store the lowest
425 		available pixel clock.
426 	\param high A pointer to an int where the function wills tore the highest
427 		available pixel clock.
428 	\return \c B_OK if the operation went fine, otherwise an error code.
429 */
430 status_t
431 BScreen::GetPixelClockLimits(display_mode* mode, uint32* _low, uint32* _high)
432 {
433 	if (fScreen != NULL)
434 		return fScreen->GetPixelClockLimits(mode, _low, _high);
435 	return B_ERROR;
436 }
437 
438 
439 /*!	\brief Fills out the dtc structure with the timing constraints of the
440 		current display mode.
441 	\param dtc A pointer to a display_timing_constraints structure where the
442 		function will store the timing constraints of the current mode.
443 	\return \c B_OK if the operation went fine, otherwise an error code.
444 */
445 status_t
446 BScreen::GetTimingConstraints(display_timing_constraints* constraints)
447 {
448 	if (fScreen != NULL)
449 		return fScreen->GetTimingConstraints(constraints);
450 	return B_ERROR;
451 }
452 
453 
454 /*!	\brief Lets you set the VESA Display Power Management Signaling state for
455 		the screen.
456 	\param dpms_state The DPMS state you want to be set.
457 		valid values are:
458 		- \c B_DPMS_ON
459 		- \c B_DPMS_STAND_BY
460 		- \c B_DPMS_SUSPEND
461 		- \c B_DPMS_OFF
462 	\return \c B_OK if the operation went fine, otherwise an error code.
463 */
464 status_t
465 BScreen::SetDPMS(uint32 dpmsState)
466 {
467 	if (fScreen != NULL)
468 		return fScreen->SetDPMS(dpmsState);
469 	return B_ERROR;
470 }
471 
472 
473 /*!	\brief Returns the current DPMS state of the screen.
474 */
475 uint32
476 BScreen::DPMSState()
477 {
478 	if (fScreen != NULL)
479 		return fScreen->DPMSState();
480 	return 0;
481 }
482 
483 
484 /*!	\brief Indicates which DPMS modes the monitor supports.
485 */
486 uint32
487 BScreen::DPMSCapabilites()
488 {
489 	if (fScreen != NULL)
490 		return fScreen->DPMSCapabilites();
491 	return 0;
492 }
493 
494 
495 //	#pragma mark - Deprecated methods
496 
497 
498 /*!	\brief Returns the BPrivateScreen used by the BScreen object.
499 	\return A pointer to the BPrivateScreen class internally used by the BScreen
500 		object.
501 */
502 BPrivate::BPrivateScreen*
503 BScreen::private_screen()
504 {
505 	return fScreen;
506 }
507 
508 
509 /*!	\brief Deprecated, use ProposeMode() instead.
510 */
511 status_t
512 BScreen::ProposeDisplayMode(display_mode* target, const display_mode* low,
513 	const display_mode* high)
514 {
515 	return ProposeMode(target, low, high);
516 }
517 
518 
519 /*!	\brief Returns the base address of the framebuffer.
520 */
521 void*
522 BScreen::BaseAddress()
523 {
524 	if (fScreen != NULL)
525 		return fScreen->BaseAddress();
526 	return NULL;
527 }
528 
529 
530 /*!	\brief Returns the amount of bytes per row of the framebuffer.
531 */
532 uint32
533 BScreen::BytesPerRow()
534 {
535 	if (fScreen != NULL)
536 		return fScreen->BytesPerRow();
537 	return 0;
538 }
539