1/*
2	Copyright 1999, Be Incorporated.   All Rights Reserved.
3	This file may be used under the terms of the Be Sample Code License.
4
5	Other authors:
6	Rudolf Cornelissen 4/2003-11/2004
7*/
8
9#define MODULE_BIT 0x20000000
10
11#include "acc_std.h"
12
13status_t SET_CURSOR_SHAPE(uint16 width, uint16 height, uint16 hot_x, uint16 hot_y, uint8 *andMask, uint8 *xorMask)
14{
15	LOG(4,("SET_CURSOR_SHAPE: width %d, height %d, hot_x %d, hot_y %d\n",
16		width, height, hot_x, hot_y));
17
18	if ((width != 16) || (height != 16))
19	{
20		return B_ERROR;
21	}
22	else if ((hot_x >= width) || (hot_y >= height))
23	{
24		return B_ERROR;
25	}
26	else
27	{
28		nm_crtc_cursor_define(andMask,xorMask);
29
30		/* Update cursor variables appropriately. */
31		si->cursor.width = width;
32		si->cursor.height = height;
33		si->cursor.hot_x = hot_x;
34		si->cursor.hot_y = hot_y;
35	}
36
37	return B_OK;
38}
39
40/* Move the cursor to the specified position on the desktop, taking account of virtual/dual issues */
41void MOVE_CURSOR(uint16 x, uint16 y)
42{
43	uint16 hds = si->dm.h_display_start;	/* the current horizontal starting pixel */
44	uint16 vds = si->dm.v_display_start;	/* the current vertical starting line */
45	uint16 h_adjust;
46	uint16 h_display = si->dm.timing.h_display; /* local copy needed for flatpanel */
47	uint16 v_display = si->dm.timing.v_display; /* local copy needed for flatpanel */
48
49	/* clamp cursor to display */
50	if (x >= si->dm.virtual_width) x = si->dm.virtual_width - 1;
51	if (y >= si->dm.virtual_height) y = si->dm.virtual_height - 1;
52
53	/* store, for our info */
54	si->cursor.x = x;
55	si->cursor.y = y;
56
57	/* setting up minimum amount to scroll not needed:
58	 * Neomagic cards can always do pixelprecise panning */
59	h_adjust = 0x00;
60
61	/* if internal panel is active correct visible screensize! */
62	if (nm_general_output_read() & 0x02)
63	{
64		if (h_display > si->ps.panel_width) h_display = si->ps.panel_width;
65		if (v_display > si->ps.panel_height) v_display = si->ps.panel_height;
66	}
67
68	/* adjust h/v_display_start to move cursor onto screen */
69	if (x >= (h_display + hds))
70	{
71		hds = ((x - h_display) + 1 + h_adjust) & ~h_adjust;
72		/* make sure we stay within the display! */
73		if ((hds + h_display) > si->dm.virtual_width)
74			hds -= (h_adjust + 1);
75	}
76	else if (x < hds)
77		hds = x & ~h_adjust;
78
79	if (y >= (v_display + vds))
80		vds = y - v_display + 1;
81	else if (y < vds)
82		vds = y;
83
84	/* reposition the desktop _and_ the overlay on the display if required */
85	if ((hds!=si->dm.h_display_start) || (vds!=si->dm.v_display_start))
86	{
87		MOVE_DISPLAY(hds,vds);
88		nm_bes_move_overlay();
89	}
90
91	/* put cursor in correct physical position */
92	if (x > (hds + si->cursor.hot_x)) x -= hds + si->cursor.hot_x;
93	else x = 0;
94	if (y > (vds + si->cursor.hot_y)) y -= vds + si->cursor.hot_y;
95	else y = 0;
96
97	/* position the cursor on the display */
98	nm_crtc_cursor_position(x,y);
99}
100
101void SHOW_CURSOR(bool is_visible)
102{
103	/* record for our info */
104	si->cursor.is_visible = is_visible;
105
106	if (is_visible)
107		nm_crtc_cursor_show();
108	else
109		nm_crtc_cursor_hide();
110}
111