ReactOS  0.4.15-dev-1201-gb2cf5a4
pointer.c
Go to the documentation of this file.
1 /*
2  * PROJECT: ReactOS Framebuffer Display Driver
3  * LICENSE: Microsoft NT4 DDK Sample Code License
4  * FILE: win32ss/drivers/displays/framebuf_new/pointer.c
5  * PURPOSE: Hardware Pointer Support
6  * PROGRAMMERS: Copyright (c) 1992-1995 Microsoft Corporation
7  */
8 
9 #include "driver.h"
10 
12 PPDEV ppdev,
15 XLATEOBJ *pxlo);
16 
18 PPDEV ppdev,
20 
22 SURFOBJ *pso,
25 XLATEOBJ *pxlo,
26 LONG x,
27 LONG y,
28 FLONG fl);
29 
30 /******************************Public*Routine******************************\
31 * DrvMovePointer
32 *
33 * Moves the hardware pointer to a new position.
34 *
35 \**************************************************************************/
36 
38 (
39  SURFOBJ *pso,
40  LONG x,
41  LONG y,
42  RECTL *prcl
43 )
44 {
45  PPDEV ppdev = (PPDEV) pso->dhpdev;
46  DWORD returnedDataLength;
47  VIDEO_POINTER_POSITION NewPointerPosition;
48 
49  // We don't use the exclusion rectangle because we only support
50  // hardware Pointers. If we were doing our own Pointer simulations
51  // we would want to update prcl so that the engine would call us
52  // to exclude out pointer before drawing to the pixels in prcl.
53 
55 
56  if (x == -1)
57  {
58  //
59  // A new position of (-1,-1) means hide the pointer.
60  //
61 
62  if (EngDeviceIoControl(ppdev->hDriver,
64  NULL,
65  0,
66  NULL,
67  0,
68  &returnedDataLength))
69  {
70  //
71  // Not the end of the world, print warning in checked build.
72  //
73 
74  DISPDBG((1, "DISP vMoveHardwarePointer failed IOCTL_VIDEO_DISABLE_POINTER\n"));
75  }
76  }
77  else
78  {
79  NewPointerPosition.Column = (SHORT) x - (SHORT) (ppdev->ptlHotSpot.x);
80  NewPointerPosition.Row = (SHORT) y - (SHORT) (ppdev->ptlHotSpot.y);
81 
82  //
83  // Call miniport driver to move Pointer.
84  //
85 
86  if (EngDeviceIoControl(ppdev->hDriver,
88  &NewPointerPosition,
89  sizeof(VIDEO_POINTER_POSITION),
90  NULL,
91  0,
92  &returnedDataLength))
93  {
94  //
95  // Not the end of the world, print warning in checked build.
96  //
97 
98  DISPDBG((1, "DISP vMoveHardwarePointer failed IOCTL_VIDEO_SET_POINTER_POSITION\n"));
99  }
100  }
101 }
102 
103 /******************************Public*Routine******************************\
104 * DrvSetPointerShape
105 *
106 * Sets the new pointer shape.
107 *
108 \**************************************************************************/
109 
111 (
112  SURFOBJ *pso,
113  SURFOBJ *psoMask,
114  SURFOBJ *psoColor,
115  XLATEOBJ *pxlo,
116  LONG xHot,
117  LONG yHot,
118  LONG x,
119  LONG y,
120  RECTL *prcl,
121  FLONG fl
122 )
123 {
124  PPDEV ppdev = (PPDEV) pso->dhpdev;
125  DWORD returnedDataLength;
126 
127  // We don't use the exclusion rectangle because we only support
128  // hardware Pointers. If we were doing our own Pointer simulations
129  // we would want to update prcl so that the engine would call us
130  // to exclude out pointer before drawing to the pixels in prcl.
132 
134  {
135  // Mini-port has no hardware Pointer support.
136  return(SPS_ERROR);
137  }
138 
139  // See if we are being asked to hide the pointer
140 
141  if (psoMask == (SURFOBJ *) NULL)
142  {
143  if (EngDeviceIoControl(ppdev->hDriver,
145  NULL,
146  0,
147  NULL,
148  0,
149  &returnedDataLength))
150  {
151  //
152  // It should never be possible to fail.
153  // Message supplied for debugging.
154  //
155 
156  DISPDBG((1, "DISP bSetHardwarePointerShape failed IOCTL_VIDEO_DISABLE_POINTER\n"));
157  }
158 
159  return(TRUE);
160  }
161 
162  ppdev->ptlHotSpot.x = xHot;
163  ppdev->ptlHotSpot.y = yHot;
164 
166  {
167  if (ppdev->fHwCursorActive) {
168  ppdev->fHwCursorActive = FALSE;
169 
170  if (EngDeviceIoControl(ppdev->hDriver,
172  NULL,
173  0,
174  NULL,
175  0,
176  &returnedDataLength)) {
177 
178  DISPDBG((1, "DISP bSetHardwarePointerShape failed IOCTL_VIDEO_DISABLE_POINTER\n"));
179  }
180  }
181 
182  //
183  // Mini-port declines to realize this Pointer
184  //
185 
186  return(SPS_DECLINE);
187  }
188  else
189  {
190  ppdev->fHwCursorActive = TRUE;
191  }
192 
193  return(SPS_ACCEPT_NOEXCLUDE);
194 }
195 
196 /******************************Public*Routine******************************\
197 * bSetHardwarePointerShape
198 *
199 * Changes the shape of the Hardware Pointer.
200 *
201 * Returns: True if successful, False if Pointer shape can't be hardware.
202 *
203 \**************************************************************************/
204 
206 SURFOBJ *pso,
209 XLATEOBJ *pxlo,
210 LONG x,
211 LONG y,
212 FLONG fl)
213 {
214  PPDEV ppdev = (PPDEV) pso->dhpdev;
215  PVIDEO_POINTER_ATTRIBUTES pPointerAttributes = ppdev->pPointerAttributes;
216  DWORD returnedDataLength;
217 
218  if (psoColor != (SURFOBJ *) NULL)
219  {
222  {
223  pPointerAttributes->Flags |= VIDEO_MODE_COLOR_POINTER;
224  } else {
225  return(FALSE);
226  }
227 
228  } else {
229 
231  bCopyMonoPointer(ppdev, psoMask))
232  {
233  pPointerAttributes->Flags |= VIDEO_MODE_MONO_POINTER;
234  } else {
235  return(FALSE);
236  }
237  }
238 
239  //
240  // Initialize Pointer attributes and position
241  //
242 
243  pPointerAttributes->Enable = 1;
244 
245  //
246  // if x,y = -1,-1 then pass them directly to the miniport so that
247  // the cursor will be disabled
248 
249  pPointerAttributes->Column = (SHORT)(x);
250  pPointerAttributes->Row = (SHORT)(y);
251 
252  if ((x != -1) || (y != -1)) {
253  pPointerAttributes->Column -= (SHORT)(ppdev->ptlHotSpot.x);
254  pPointerAttributes->Row -= (SHORT)(ppdev->ptlHotSpot.y);
255  }
256 
257  //
258  // set animate flags
259  //
260 
261  if (fl & SPS_ANIMATESTART) {
262  pPointerAttributes->Flags |= VIDEO_MODE_ANIMATE_START;
263  } else if (fl & SPS_ANIMATEUPDATE) {
264  pPointerAttributes->Flags |= VIDEO_MODE_ANIMATE_UPDATE;
265  }
266 
267  //
268  // Set the new Pointer shape.
269  //
270 
271  if (EngDeviceIoControl(ppdev->hDriver,
273  pPointerAttributes,
274  ppdev->cjPointerAttributes,
275  NULL,
276  0,
277  &returnedDataLength)) {
278 
279  DISPDBG((1, "DISP:Failed IOCTL_VIDEO_SET_POINTER_ATTR call\n"));
280  return(FALSE);
281  }
282 
283  return(TRUE);
284 }
285 
286 /******************************Public*Routine******************************\
287 * bCopyMonoPointer
288 *
289 * Copies two monochrome masks into a buffer of the maximum size handled by the
290 * miniport, with any extra bits set to 0. The masks are converted to topdown
291 * form if they aren't already. Returns TRUE if we can handle this pointer in
292 * hardware, FALSE if not.
293 *
294 \**************************************************************************/
295 
297  PPDEV ppdev,
298  SURFOBJ *pso)
299 {
300  ULONG cy;
301  PBYTE pjSrcAnd, pjSrcXor;
302  LONG lDeltaSrc, lDeltaDst;
303  LONG lSrcWidthInBytes;
304  ULONG cxSrc = pso->sizlBitmap.cx;
305  ULONG cySrc = pso->sizlBitmap.cy;
306  ULONG cxSrcBytes;
307  PVIDEO_POINTER_ATTRIBUTES pPointerAttributes = ppdev->pPointerAttributes;
308  PBYTE pjDstAnd = pPointerAttributes->Pixels;
309  PBYTE pjDstXor = pPointerAttributes->Pixels;
310 
311  // Make sure the new pointer isn't too big to handle
312  // (*2 because both masks are in there)
313  if ((cxSrc > ppdev->PointerCapabilities.MaxWidth) ||
314  (cySrc > (ppdev->PointerCapabilities.MaxHeight * 2)))
315  {
316  return(FALSE);
317  }
318 
319  pjDstXor += ((ppdev->PointerCapabilities.MaxWidth + 7) / 8) *
320  ppdev->pPointerAttributes->Height;
321 
322  // set the desk and mask to 0xff
323  RtlFillMemory(pjDstAnd, ppdev->pPointerAttributes->WidthInBytes *
324  ppdev->pPointerAttributes->Height, 0xFF);
325 
326  // Zero the dest XOR mask
327  RtlZeroMemory(pjDstXor, ppdev->pPointerAttributes->WidthInBytes *
328  ppdev->pPointerAttributes->Height);
329 
330  cxSrcBytes = (cxSrc + 7) / 8;
331 
332  if ((lDeltaSrc = pso->lDelta) < 0)
333  {
334  lSrcWidthInBytes = -lDeltaSrc;
335  } else {
336  lSrcWidthInBytes = lDeltaSrc;
337  }
338 
339  pjSrcAnd = (PBYTE) pso->pvBits;
340 
341  // If the incoming pointer bitmap is bottomup, we'll flip it to topdown to
342  // save the miniport some work
343  if (!(pso->fjBitmap & BMF_TOPDOWN))
344  {
345  // Copy from the bottom
346  pjSrcAnd += lSrcWidthInBytes * (cySrc - 1);
347  }
348 
349  // Height of just AND mask
350  cySrc = cySrc / 2;
351 
352  // Point to XOR mask
353  pjSrcXor = pjSrcAnd + (cySrc * lDeltaSrc);
354 
355  // Offset from end of one dest scan to start of next
356  lDeltaDst = ppdev->pPointerAttributes->WidthInBytes;
357 
358  for (cy = 0; cy < cySrc; ++cy)
359  {
360  RtlCopyMemory(pjDstAnd, pjSrcAnd, cxSrcBytes);
361  RtlCopyMemory(pjDstXor, pjSrcXor, cxSrcBytes);
362 
363  // Point to next source and dest scans
364  pjSrcAnd += lDeltaSrc;
365  pjSrcXor += lDeltaSrc;
366  pjDstAnd += lDeltaDst;
367  pjDstXor += lDeltaDst;
368  }
369 
370  return(TRUE);
371 }
372 
373 /******************************Public*Routine******************************\
374 * bCopyColorPointer
375 *
376 * Copies the mono and color masks into the buffer of maximum size
377 * handled by the miniport with any extra bits set to 0. Color translation
378 * is handled at this time. The masks are converted to topdown form if they
379 * aren't already. Returns TRUE if we can handle this pointer in hardware,
380 * FALSE if not.
381 *
382 \**************************************************************************/
384 PPDEV ppdev,
387 XLATEOBJ *pxlo)
388 {
389  return(FALSE);
390 }
391 
392 
393 /******************************Public*Routine******************************\
394 * bInitPointer
395 *
396 * Initialize the Pointer attributes.
397 *
398 \**************************************************************************/
399 
401 {
402  DWORD returnedDataLength;
403 
405  ppdev->cjPointerAttributes = 0; // initialized in screen.c
406 
407  //
408  // Ask the miniport whether it provides pointer support.
409  //
410 
411  if (EngDeviceIoControl(ppdev->hDriver,
413  NULL,
414  0,
415  &ppdev->PointerCapabilities,
416  sizeof(ppdev->PointerCapabilities),
417  &returnedDataLength))
418  {
419  return(FALSE);
420  }
421 
422  //
423  // If neither mono nor color hardware pointer is supported, there's no
424  // hardware pointer support and we're done.
425  //
426 
429  {
430  return(TRUE);
431  }
432 
433  //
434  // Note: The buffer itself is allocated after we set the
435  // mode. At that time we know the pixel depth and we can
436  // allocate the correct size for the color pointer if supported.
437  //
438 
439  //
440  // Set the asynchronous support status (async means miniport is capable of
441  // drawing the Pointer at any time, with no interference with any ongoing
442  // drawing operation)
443  //
444 
446  {
447  pdevinfo->flGraphicsCaps |= GCAPS_ASYNCMOVE;
448  }
449  else
450  {
451  pdevinfo->flGraphicsCaps &= ~GCAPS_ASYNCMOVE;
452  }
453 
454  return(TRUE);
455 }
#define SPS_ANIMATESTART
Definition: winddi.h:4037
VIDEO_POINTER_CAPABILITIES PointerCapabilities
Definition: driver.h:44
NTSYSAPI VOID NTAPI RtlCopyMemory(VOID UNALIGNED *Destination, CONST VOID UNALIGNED *Source, ULONG Length)
#define IOCTL_VIDEO_SET_POINTER_ATTR
Definition: ntddvdeo.h:164
#define VIDEO_MODE_COLOR_POINTER
Definition: ntddvdeo.h:455
#define IOCTL_VIDEO_QUERY_POINTER_CAPABILITIES
Definition: ntddvdeo.h:128
#define TRUE
Definition: types.h:120
#define UNREFERENCED_PARAMETER(P)
Definition: ntbasedef.h:317
#define BMF_TOPDOWN
Definition: winddi.h:1180
GLint GLint GLint GLint GLint x
Definition: gl.h:1548
#define IOCTL_VIDEO_DISABLE_POINTER
Definition: ntddvdeo.h:80
#define SPS_ACCEPT_NOEXCLUDE
Definition: winddi.h:4030
#define VIDEO_MODE_MONO_POINTER
Definition: ntddvdeo.h:454
LONG y
Definition: windef.h:330
POINTL ptlHotSpot
Definition: driver.h:43
NTSTATUS(* NTAPI)(IN PFILE_FULL_EA_INFORMATION EaBuffer, IN ULONG EaLength, OUT PULONG ErrorOffset)
Definition: IoEaTest.cpp:117
_In_ FLONG fl
Definition: winddi.h:1279
#define GCAPS_ASYNCMOVE
Definition: winddi.h:335
#define FALSE
Definition: types.h:117
unsigned int BOOL
Definition: ntddk_ex.h:94
long LONG
Definition: pedump.c:60
VOID APIENTRY DrvMovePointer(IN SURFOBJ *pso, IN LONG x, IN LONG y, IN RECTL *prcl)
Definition: pointer.c:62
short SHORT
Definition: pedump.c:59
BOOL NTAPI bSetHardwarePointerShape(SURFOBJ *pso, SURFOBJ *psoMask, SURFOBJ *psoColor, XLATEOBJ *pxlo, LONG x, LONG y, FLONG fl)
Definition: pointer.c:205
_In_opt_ SURFOBJ _In_opt_ SURFOBJ _In_ XLATEOBJ _In_ LONG _In_ LONG yHot
Definition: winddi.h:4049
HANDLE hDriver
Definition: framebuf.h:35
BOOL NTAPI bInitPointer(PPDEV ppdev, DEVINFO *pdevinfo)
Definition: pointer.c:400
DWORD cjPointerAttributes
Definition: driver.h:46
_Out_opt_ int _Out_opt_ int * cy
Definition: commctrl.h:581
smooth NULL
Definition: ftsmooth.c:416
unsigned long FLONG
Definition: ntbasedef.h:367
#define SPS_ANIMATEUPDATE
Definition: winddi.h:4038
_In_ HANDLE _In_ SURFOBJ * pso
Definition: winddi.h:3664
if(!(yy_init))
Definition: macro.lex.yy.c:714
BOOL NTAPI bCopyMonoPointer(PPDEV ppdev, SURFOBJ *psoMask)
Definition: pointer.c:296
#define RtlFillMemory(Dest, Length, Fill)
Definition: winternl.h:593
_In_opt_ SURFOBJ _In_opt_ SURFOBJ _In_ XLATEOBJ _In_ LONG xHot
Definition: winddi.h:4049
unsigned long DWORD
Definition: ntddk_ex.h:95
LONG x
Definition: windef.h:329
#define DISPDBG(arg)
Definition: debug.h:23
struct _VIDEO_POINTER_ATTRIBUTES * PVIDEO_POINTER_ATTRIBUTES
BOOL NTAPI bCopyColorPointer(PPDEV ppdev, SURFOBJ *psoMask, SURFOBJ *psoColor, XLATEOBJ *pxlo)
Definition: pointer.c:383
struct _PDEV * PPDEV
Definition: framebuf.h:33
#define SPS_DECLINE
Definition: winddi.h:4029
#define SPS_ERROR
Definition: winddi.h:4028
_In_opt_ SURFOBJ _In_opt_ SURFOBJ * psoColor
Definition: winddi.h:4049
PVIDEO_POINTER_ATTRIBUTES pPointerAttributes
Definition: driver.h:45
FLONG flGraphicsCaps
Definition: winddi.h:390
_In_opt_ SURFOBJ _In_opt_ SURFOBJ * psoMask
Definition: winddi.h:3433
GLint GLint GLint GLint GLint GLint y
Definition: gl.h:1548
_In_ ULONG _In_ CLIPOBJ _In_ RECTL * prcl
Definition: winddi.h:3529
#define VIDEO_MODE_ASYNC_POINTER
Definition: ntddvdeo.h:453
ULONG APIENTRY DrvSetPointerShape(IN SURFOBJ *pso, IN SURFOBJ *psoMask, IN SURFOBJ *psoColor, IN XLATEOBJ *pxlo, IN LONG xHot, IN LONG yHot, IN LONG x, IN LONG y, IN RECTL *prcl, IN FLONG fl)
Definition: pointer.c:35
unsigned int ULONG
Definition: retypes.h:1
#define VIDEO_MODE_ANIMATE_UPDATE
Definition: ntddvdeo.h:457
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
BOOL fHwCursorActive
Definition: driver.h:47
BYTE * PBYTE
Definition: pedump.c:66
#define VIDEO_MODE_ANIMATE_START
Definition: ntddvdeo.h:456
#define IOCTL_VIDEO_SET_POINTER_POSITION
Definition: ntddvdeo.h:167
_In_ SURFOBJ _In_ CLIPOBJ _In_opt_ XLATEOBJ * pxlo
Definition: winddi.h:3414