18a2953fe6b74960e402826a1578705b13f9f4dc
[reactos.git] / reactos / subsys / win32k / eng / clip.c
1 /*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS kernel
4 * PURPOSE: GDI Clipping Functions
5 * FILE: subsys/win32k/eng/clip.c
6 * PROGRAMER: Jason Filby
7 * REVISION HISTORY:
8 * 21/8/1999: Created
9 */
10
11 #include <ddk/winddi.h>
12 #include <ddk/ntddk.h>
13 #include "objects.h"
14 #include "clip.h"
15 #include <include/object.h>
16
17 #define NDEBUG
18 #include <win32k/debug1.h>
19
20 VOID IntEngDeleteClipRegion(CLIPOBJ *ClipObj)
21 {
22 HCLIP HClip = AccessHandleFromUserObject(ClipObj);
23 FreeGDIHandle(HClip);
24 }
25
26 CLIPOBJ * IntEngCreateClipRegion( ULONG count, PRECTL pRect, RECTL rcBounds )
27 {
28 HCLIP hClip;
29 CLIPGDI* clipInt;
30 CLIPOBJ* clipUser;
31 DPRINT("IntEngCreateClipRegion count: %d\n", count);
32 if( count > 1 ){
33 hClip = (HCLIP)CreateGDIHandle( sizeof( CLIPGDI ) + count*sizeof(RECTL),
34 sizeof( CLIPOBJ ) );
35
36 if( hClip ){
37 clipInt = (CLIPGDI*)AccessInternalObject( hClip );
38 RtlCopyMemory( clipInt->EnumRects.arcl, pRect, count*sizeof(RECTL));
39 clipInt->EnumRects.c=count;
40
41 clipUser = (CLIPOBJ*)AccessUserObject( hClip );
42 ASSERT( clipUser );
43
44 clipUser->iDComplexity = DC_COMPLEX;
45 clipUser->iFComplexity = (count <= 4)? FC_RECT4: FC_COMPLEX;
46 clipUser->iMode = TC_RECTANGLES;
47 RtlCopyMemory( &(clipUser->rclBounds), &rcBounds, sizeof( RECTL ) );
48
49 return clipUser;
50 }
51 return NULL;
52 }
53 else{
54 hClip = (HCLIP)CreateGDIHandle( sizeof( CLIPGDI ),
55 sizeof( CLIPOBJ ) );
56 if( hClip ){
57 clipInt = (CLIPGDI*)AccessInternalObject( hClip );
58 RtlCopyMemory( clipInt->EnumRects.arcl, &rcBounds, sizeof( RECTL ));
59 clipInt->EnumRects.c = 1;
60
61 clipUser = (CLIPOBJ*)AccessUserObject( hClip );
62 ASSERT( clipUser );
63
64 clipUser->iDComplexity = ((rcBounds.top==rcBounds.bottom)&&(rcBounds.left==rcBounds.right))?
65 DC_TRIVIAL:DC_RECT;
66 clipUser->iFComplexity = FC_RECT;
67 clipUser->iMode = TC_RECTANGLES;
68 DPRINT("IntEngCreateClipRegion: iDComplexity: %d\n", clipUser->iDComplexity);
69 RtlCopyMemory( &(clipUser->rclBounds), &rcBounds, sizeof( RECTL ) );
70 return clipUser;
71 }
72 }
73 return NULL;
74 }
75
76 CLIPOBJ * STDCALL
77 EngCreateClip(VOID)
78 {
79 return EngAllocMem(FL_ZERO_MEMORY, sizeof(CLIPOBJ), 0);
80 }
81
82 VOID STDCALL
83 EngDeleteClip(CLIPOBJ *ClipRegion)
84 {
85 EngFreeMem(ClipRegion);
86 }
87
88 ULONG STDCALL
89 CLIPOBJ_cEnumStart(IN PCLIPOBJ ClipObj,
90 IN BOOL ShouldDoAll,
91 IN ULONG ClipType,
92 IN ULONG BuildOrder,
93 IN ULONG MaxRects)
94 {
95 CLIPGDI *ClipGDI = (CLIPGDI*)AccessInternalObjectFromUserObject(ClipObj);
96
97 ClipGDI->EnumPos = 0;
98 ClipGDI->EnumMax = (MaxRects>0)? MaxRects : ClipGDI->EnumRects.c;
99
100 if( !((BuildOrder == CD_ANY) || (BuildOrder == CD_LEFTDOWN ))){
101 UNIMPLEMENTED;
102 }
103 ClipGDI->EnumOrder = BuildOrder;
104
105 // Return the number of rectangles enumerated
106 if( (MaxRects > 0) && (ClipGDI->EnumRects.c>MaxRects) )
107 {
108 return 0xFFFFFFFF;
109 }
110
111 return ClipGDI->EnumRects.c;
112 }
113
114 BOOL STDCALL
115 CLIPOBJ_bEnum(IN PCLIPOBJ ClipObj,
116 IN ULONG ObjSize,
117 OUT ULONG *EnumRects)
118 {
119 CLIPGDI *ClipGDI = (CLIPGDI*)AccessInternalObjectFromUserObject(ClipObj);
120 ULONG nCopy;
121 PENUMRECTS pERects = (PENUMRECTS)EnumRects;
122
123 //calculate how many rectangles we should copy
124 nCopy = MIN( ClipGDI->EnumMax - ClipGDI->EnumPos,
125 MIN( ClipGDI->EnumRects.c - ClipGDI->EnumPos,
126 (ObjSize - sizeof(ULONG)) / sizeof(RECTL)));
127
128 RtlCopyMemory( pERects->arcl, ClipGDI->EnumRects.arcl + ClipGDI->EnumPos,
129 nCopy * sizeof(RECTL) );
130 pERects->c = nCopy;
131
132 ClipGDI->EnumPos+=nCopy;
133
134 return ClipGDI->EnumPos < ClipGDI->EnumRects.c;
135 }