Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
W
wine-cw
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
wine
wine-cw
Commits
e8d86b7c
Commit
e8d86b7c
authored
Jun 23, 2004
by
Alexandre Julliard
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Moved visible region calculation to the server.
parent
00844ee0
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
9 changed files
with
265 additions
and
123 deletions
+265
-123
winpos.c
dlls/x11drv/winpos.c
+53
-122
server_protocol.h
include/wine/server_protocol.h
+20
-1
Makefile.in
server/Makefile.in
+1
-0
protocol.def
server/protocol.def
+11
-0
region.c
server/region.c
+0
-0
request.h
server/request.h
+2
-0
trace.c
server/trace.c
+32
-0
user.h
server/user.h
+20
-0
window.c
server/window.c
+126
-0
No files found.
dlls/x11drv/winpos.c
View file @
e8d86b7c
...
...
@@ -121,79 +121,46 @@ static int clip_children( HWND parent, HWND last, HRGN hrgn, int whole_window )
/***********************************************************************
* get_visible_region
*
* Compute the visible region of a window
* get_server_visible_region
*/
static
HRGN
get_
visible_region
(
WND
*
win
,
HWND
top
,
UINT
flags
,
int
mode
)
static
HRGN
get_
server_visible_region
(
HWND
hwnd
,
HWND
top
,
UINT
flags
)
{
HRGN
rgn
;
RECT
rect
;
int
xoffset
,
yoffset
;
X11DRV_WND_DATA
*
data
=
win
->
pDriverData
;
if
(
flags
&
DCX_WINDOW
)
{
xoffset
=
win
->
rectWindow
.
left
;
yoffset
=
win
->
rectWindow
.
top
;
}
else
{
xoffset
=
win
->
rectClient
.
left
;
yoffset
=
win
->
rectClient
.
top
;
}
if
(
flags
&
DCX_PARENTCLIP
)
GetClientRect
(
win
->
parent
,
&
rect
);
else
if
(
flags
&
DCX_WINDOW
)
rect
=
data
->
whole_rect
;
else
rect
=
win
->
rectClient
;
RGNDATA
*
data
;
HRGN
ret
=
0
;
size_t
size
=
256
;
BOOL
retry
=
FALSE
;
/* vis region is relative to the start of the client/window area */
OffsetRect
(
&
rect
,
-
xoffset
,
-
yoffset
);
if
(
!
(
rgn
=
CreateRectRgn
(
rect
.
left
,
rect
.
top
,
rect
.
right
,
rect
.
bottom
)))
return
0
;
if
((
flags
&
DCX_CLIPCHILDREN
)
&&
(
mode
!=
ClipByChildren
))
{
/* we need to clip children by hand */
if
(
clip_children
(
win
->
hwndSelf
,
0
,
rgn
,
(
flags
&
DCX_WINDOW
)
)
==
NULLREGION
)
return
rgn
;
}
if
(
top
&&
top
!=
win
->
hwndSelf
)
/* need to clip siblings of ancestors */
do
{
WND
*
parent
,
*
ptr
=
WIN_FindWndPtr
(
win
->
hwndSelf
);
HRGN
tmp
=
0
;
OffsetRgn
(
rgn
,
xoffset
,
yoffset
);
for
(;;)
if
(
!
(
data
=
HeapAlloc
(
GetProcessHeap
(),
0
,
sizeof
(
*
data
)
+
size
-
1
)))
return
0
;
SERVER_START_REQ
(
get_visible_region
)
{
if
(
ptr
->
dwStyle
&
WS_CLIPSIBLINGS
)
req
->
window
=
hwnd
;
req
->
top_win
=
top
;
req
->
flags
=
flags
;
wine_server_set_reply
(
req
,
data
->
Buffer
,
size
);
if
(
!
wine_server_call_err
(
req
))
{
if
(
clip_children
(
ptr
->
parent
,
ptr
->
hwndSelf
,
rgn
,
FALSE
)
==
NULLREGION
)
break
;
if
(
reply
->
total_size
<=
size
)
{
size_t
reply_size
=
wine_server_reply_size
(
reply
);
data
->
rdh
.
dwSize
=
sizeof
(
data
->
rdh
);
data
->
rdh
.
iType
=
RDH_RECTANGLES
;
data
->
rdh
.
nCount
=
reply_size
/
sizeof
(
RECT
);
data
->
rdh
.
nRgnSize
=
reply_size
;
ret
=
ExtCreateRegion
(
NULL
,
size
,
data
);
}
else
{
size
=
reply
->
total_size
;
retry
=
TRUE
;
}
}
if
(
ptr
->
hwndSelf
==
top
)
break
;
if
(
!
(
parent
=
WIN_FindWndPtr
(
ptr
->
parent
)))
break
;
WIN_ReleaseWndPtr
(
ptr
);
ptr
=
parent
;
/* clip to parent client area */
if
(
tmp
)
SetRectRgn
(
tmp
,
0
,
0
,
ptr
->
rectClient
.
right
-
ptr
->
rectClient
.
left
,
ptr
->
rectClient
.
bottom
-
ptr
->
rectClient
.
top
);
else
tmp
=
CreateRectRgn
(
0
,
0
,
ptr
->
rectClient
.
right
-
ptr
->
rectClient
.
left
,
ptr
->
rectClient
.
bottom
-
ptr
->
rectClient
.
top
);
CombineRgn
(
rgn
,
rgn
,
tmp
,
RGN_AND
);
OffsetRgn
(
rgn
,
ptr
->
rectClient
.
left
,
ptr
->
rectClient
.
top
);
xoffset
+=
ptr
->
rectClient
.
left
;
yoffset
+=
ptr
->
rectClient
.
top
;
}
WIN_ReleaseWndPtr
(
ptr
);
/* make it relative to the target window again */
OffsetRgn
(
rgn
,
-
xoffset
,
-
yoffset
);
if
(
tmp
)
DeleteObject
(
tmp
);
}
return
rgn
;
SERVER_END_REQ
;
HeapFree
(
GetProcessHeap
(),
0
,
data
);
}
while
(
retry
);
return
ret
;
}
...
...
@@ -426,52 +393,24 @@ BOOL X11DRV_GetDC( HWND hwnd, HDC hdc, HRGN hrgn, DWORD flags )
HWND
top
=
0
;
X11DRV_WND_DATA
*
data
=
win
->
pDriverData
;
struct
x11drv_escape_set_drawable
escape
;
BOOL
visible
;
escape
.
mode
=
IncludeInferiors
;
/* don't clip siblings if using parent clip region */
if
(
flags
&
DCX_PARENTCLIP
)
flags
&=
~
DCX_CLIPSIBLINGS
;
/* find the top parent in the hierarchy that isn't clipping siblings */
visible
=
(
win
->
dwStyle
&
WS_VISIBLE
)
!=
0
;
if
(
visible
)
{
HWND
*
list
=
WIN_ListParents
(
hwnd
);
if
(
list
)
{
int
i
;
for
(
i
=
0
;
list
[
i
]
!=
GetDesktopWindow
();
i
++
)
{
LONG
style
=
GetWindowLongW
(
list
[
i
],
GWL_STYLE
);
if
(
!
(
style
&
WS_VISIBLE
))
{
visible
=
FALSE
;
top
=
0
;
break
;
}
if
(
!
(
style
&
WS_CLIPSIBLINGS
))
top
=
list
[
i
];
}
HeapFree
(
GetProcessHeap
(),
0
,
list
);
}
if
(
!
top
&&
visible
&&
!
(
flags
&
DCX_CLIPSIBLINGS
))
top
=
hwnd
;
}
if
(
top
)
top
=
GetAncestor
(
hwnd
,
GA_ROOT
);
if
(
top
!=
hwnd
)
{
HWND
parent
=
GetAncestor
(
top
,
GA_PARENT
);
escape
.
org
.
x
=
escape
.
org
.
y
=
0
;
if
(
flags
&
DCX_WINDOW
)
{
escape
.
org
.
x
=
win
->
rectWindow
.
left
-
win
->
rectClient
.
left
;
escape
.
org
.
y
=
win
->
rectWindow
.
top
-
win
->
rectClient
.
top
;
}
MapWindowPoints
(
hwnd
,
parent
,
&
escape
.
org
,
1
);
MapWindowPoints
(
hwnd
,
top
,
&
escape
.
org
,
1
);
escape
.
drawable_org
.
x
=
escape
.
drawable_org
.
y
=
0
;
MapWindowPoints
(
parent
,
0
,
&
escape
.
drawable_org
,
1
);
/* have to use the parent so that we include siblings */
if
(
parent
)
escape
.
drawable
=
X11DRV_get_client_window
(
parent
);
else
escape
.
drawable
=
root_window
;
MapWindowPoints
(
top
,
0
,
&
escape
.
drawable_org
,
1
);
escape
.
drawable
=
X11DRV_get_client_window
(
top
);
}
else
{
...
...
@@ -482,23 +421,22 @@ BOOL X11DRV_GetDC( HWND hwnd, HDC hdc, HRGN hrgn, DWORD flags )
escape
.
org
.
y
=
0
;
escape
.
drawable_org
=
escape
.
org
;
}
else
if
(
flags
&
DCX_WINDOW
)
{
escape
.
drawable
=
data
->
whole_window
;
escape
.
org
.
x
=
win
->
rectWindow
.
left
-
data
->
whole_rect
.
left
;
escape
.
org
.
y
=
win
->
rectWindow
.
top
-
data
->
whole_rect
.
top
;
escape
.
drawable_org
.
x
=
data
->
whole_rect
.
left
-
win
->
rectClient
.
left
;
escape
.
drawable_org
.
y
=
data
->
whole_rect
.
top
-
win
->
rectClient
.
top
;
}
else
{
escape
.
drawable
=
data
->
client_window
;
escape
.
org
.
x
=
0
;
escape
.
org
.
y
=
0
;
escape
.
drawable_org
=
escape
.
org
;
if
(
flags
&
DCX_CLIPCHILDREN
)
escape
.
mode
=
ClipByChildren
;
/* can use X11 clipping */
escape
.
drawable
=
data
->
whole_window
;
escape
.
drawable_org
.
x
=
data
->
whole_rect
.
left
;
escape
.
drawable_org
.
y
=
data
->
whole_rect
.
top
;
if
(
flags
&
DCX_WINDOW
)
{
escape
.
org
.
x
=
win
->
rectWindow
.
left
-
data
->
whole_rect
.
left
;
escape
.
org
.
y
=
win
->
rectWindow
.
top
-
data
->
whole_rect
.
top
;
}
else
{
escape
.
org
.
x
=
win
->
rectClient
.
left
-
data
->
whole_rect
.
left
;
escape
.
org
.
y
=
win
->
rectClient
.
top
-
data
->
whole_rect
.
top
;
}
}
MapWindowPoints
(
hwnd
,
0
,
&
escape
.
drawable_org
,
1
);
}
escape
.
code
=
X11DRV_SET_DRAWABLE
;
...
...
@@ -508,17 +446,10 @@ BOOL X11DRV_GetDC( HWND hwnd, HDC hdc, HRGN hrgn, DWORD flags )
SetHookFlags16
(
HDC_16
(
hdc
),
DCHF_VALIDATEVISRGN
))
/* DC was dirty */
{
/* need to recompute the visible region */
HRGN
visRgn
;
HRGN
visRgn
=
get_server_visible_region
(
hwnd
,
top
,
flags
)
;
if
(
visible
)
{
visRgn
=
get_visible_region
(
win
,
top
,
flags
,
escape
.
mode
);
if
(
flags
&
(
DCX_EXCLUDERGN
|
DCX_INTERSECTRGN
))
CombineRgn
(
visRgn
,
visRgn
,
hrgn
,
(
flags
&
DCX_INTERSECTRGN
)
?
RGN_AND
:
RGN_DIFF
);
}
else
visRgn
=
CreateRectRgn
(
0
,
0
,
0
,
0
);
if
(
flags
&
(
DCX_EXCLUDERGN
|
DCX_INTERSECTRGN
))
CombineRgn
(
visRgn
,
visRgn
,
hrgn
,
(
flags
&
DCX_INTERSECTRGN
)
?
RGN_AND
:
RGN_DIFF
);
SelectVisRgn16
(
HDC_16
(
hdc
),
HRGN_16
(
visRgn
)
);
DeleteObject
(
visRgn
);
...
...
include/wine/server_protocol.h
View file @
e8d86b7c
...
...
@@ -2614,6 +2614,22 @@ struct get_windows_offset_reply
struct
get_visible_region_request
{
struct
request_header
__header
;
user_handle_t
window
;
user_handle_t
top_win
;
unsigned
int
flags
;
};
struct
get_visible_region_reply
{
struct
reply_header
__header
;
size_t
total_size
;
/* VARARG(region,rectangles); */
};
struct
set_window_property_request
{
struct
request_header
__header
;
...
...
@@ -3189,6 +3205,7 @@ enum request
REQ_set_window_text
,
REQ_inc_window_paint_count
,
REQ_get_windows_offset
,
REQ_get_visible_region
,
REQ_set_window_property
,
REQ_remove_window_property
,
REQ_get_window_property
,
...
...
@@ -3369,6 +3386,7 @@ union generic_request
struct
set_window_text_request
set_window_text_request
;
struct
inc_window_paint_count_request
inc_window_paint_count_request
;
struct
get_windows_offset_request
get_windows_offset_request
;
struct
get_visible_region_request
get_visible_region_request
;
struct
set_window_property_request
set_window_property_request
;
struct
remove_window_property_request
remove_window_property_request
;
struct
get_window_property_request
get_window_property_request
;
...
...
@@ -3547,6 +3565,7 @@ union generic_reply
struct
set_window_text_reply
set_window_text_reply
;
struct
inc_window_paint_count_reply
inc_window_paint_count_reply
;
struct
get_windows_offset_reply
get_windows_offset_reply
;
struct
get_visible_region_reply
get_visible_region_reply
;
struct
set_window_property_reply
set_window_property_reply
;
struct
remove_window_property_reply
remove_window_property_reply
;
struct
get_window_property_reply
get_window_property_reply
;
...
...
@@ -3574,6 +3593,6 @@ union generic_reply
struct
set_global_windows_reply
set_global_windows_reply
;
};
#define SERVER_PROTOCOL_VERSION 14
3
#define SERVER_PROTOCOL_VERSION 14
4
#endif
/* __WINE_WINE_SERVER_PROTOCOL_H */
server/Makefile.in
View file @
e8d86b7c
...
...
@@ -29,6 +29,7 @@ C_SRCS = \
process.c
\
ptrace.c
\
queue.c
\
region.c
\
registry.c
\
request.c
\
semaphore.c
\
...
...
server/protocol.def
View file @
e8d86b7c
...
...
@@ -1838,6 +1838,17 @@ enum message_type
@END
/* Get the visible region of a window */
@REQ(get_visible_region)
user_handle_t window; /* handle to the window */
user_handle_t top_win; /* top window to clip against */
unsigned int flags; /* DCX flags */
@REPLY
size_t total_size; /* total size of the resulting region */
VARARG(region,rectangles); /* list of rectangles for the region */
@END
/* Set a window property */
@REQ(set_window_property)
user_handle_t window; /* handle to the window */
...
...
server/region.c
0 → 100644
View file @
e8d86b7c
This diff is collapsed.
Click to expand it.
server/request.h
View file @
e8d86b7c
...
...
@@ -251,6 +251,7 @@ DECL_HANDLER(get_window_text);
DECL_HANDLER
(
set_window_text
);
DECL_HANDLER
(
inc_window_paint_count
);
DECL_HANDLER
(
get_windows_offset
);
DECL_HANDLER
(
get_visible_region
);
DECL_HANDLER
(
set_window_property
);
DECL_HANDLER
(
remove_window_property
);
DECL_HANDLER
(
get_window_property
);
...
...
@@ -430,6 +431,7 @@ static const req_handler req_handlers[REQ_NB_REQUESTS] =
(
req_handler
)
req_set_window_text
,
(
req_handler
)
req_inc_window_paint_count
,
(
req_handler
)
req_get_windows_offset
,
(
req_handler
)
req_get_visible_region
,
(
req_handler
)
req_set_window_property
,
(
req_handler
)
req_remove_window_property
,
(
req_handler
)
req_get_window_property
,
...
...
server/trace.c
View file @
e8d86b7c
...
...
@@ -375,6 +375,21 @@ static void dump_varargs_input_records( size_t size )
remove_data
(
size
);
}
static
void
dump_varargs_rectangles
(
size_t
size
)
{
const
rectangle_t
*
rect
=
cur_data
;
size_t
len
=
size
/
sizeof
(
*
rect
);
fputc
(
'{'
,
stderr
);
while
(
len
>
0
)
{
dump_rectangle
(
rect
++
);
if
(
--
len
)
fputc
(
','
,
stderr
);
}
fputc
(
'}'
,
stderr
);
remove_data
(
size
);
}
static
void
dump_varargs_properties
(
size_t
size
)
{
const
property_data_t
*
prop
=
cur_data
;
...
...
@@ -2161,6 +2176,20 @@ static void dump_get_windows_offset_reply( const struct get_windows_offset_reply
fprintf
(
stderr
,
" y=%d"
,
req
->
y
);
}
static
void
dump_get_visible_region_request
(
const
struct
get_visible_region_request
*
req
)
{
fprintf
(
stderr
,
" window=%p,"
,
req
->
window
);
fprintf
(
stderr
,
" top_win=%p,"
,
req
->
top_win
);
fprintf
(
stderr
,
" flags=%08x"
,
req
->
flags
);
}
static
void
dump_get_visible_region_reply
(
const
struct
get_visible_region_reply
*
req
)
{
fprintf
(
stderr
,
" total_size=%d,"
,
req
->
total_size
);
fprintf
(
stderr
,
" region="
);
dump_varargs_rectangles
(
cur_size
);
}
static
void
dump_set_window_property_request
(
const
struct
set_window_property_request
*
req
)
{
fprintf
(
stderr
,
" window=%p,"
,
req
->
window
);
...
...
@@ -2630,6 +2659,7 @@ static const dump_func req_dumpers[REQ_NB_REQUESTS] = {
(
dump_func
)
dump_set_window_text_request
,
(
dump_func
)
dump_inc_window_paint_count_request
,
(
dump_func
)
dump_get_windows_offset_request
,
(
dump_func
)
dump_get_visible_region_request
,
(
dump_func
)
dump_set_window_property_request
,
(
dump_func
)
dump_remove_window_property_request
,
(
dump_func
)
dump_get_window_property_request
,
...
...
@@ -2806,6 +2836,7 @@ static const dump_func reply_dumpers[REQ_NB_REQUESTS] = {
(
dump_func
)
0
,
(
dump_func
)
0
,
(
dump_func
)
dump_get_windows_offset_reply
,
(
dump_func
)
dump_get_visible_region_reply
,
(
dump_func
)
0
,
(
dump_func
)
dump_remove_window_property_reply
,
(
dump_func
)
dump_get_window_property_reply
,
...
...
@@ -2982,6 +3013,7 @@ static const char * const req_names[REQ_NB_REQUESTS] = {
"set_window_text"
,
"inc_window_paint_count"
,
"get_windows_offset"
,
"get_visible_region"
,
"set_window_property"
,
"remove_window_property"
,
"get_window_property"
,
...
...
server/user.h
View file @
e8d86b7c
...
...
@@ -24,6 +24,7 @@
#include "wine/server_protocol.h"
struct
thread
;
struct
region
;
struct
window
;
struct
msg_queue
;
struct
hook_table
;
...
...
@@ -64,6 +65,25 @@ extern int attach_thread_input( struct thread *thread_from, struct thread *threa
extern
void
post_message
(
user_handle_t
win
,
unsigned
int
message
,
unsigned
int
wparam
,
unsigned
int
lparam
);
/* region functions */
extern
struct
region
*
create_region
(
const
rectangle_t
*
rects
,
unsigned
int
nb_rects
);
extern
void
free_region
(
struct
region
*
region
);
extern
void
set_region_rect
(
struct
region
*
region
,
const
rectangle_t
*
rect
);
extern
rectangle_t
*
get_region_data
(
const
struct
region
*
region
,
size_t
*
total_size
);
extern
rectangle_t
*
get_region_data_and_free
(
struct
region
*
region
,
size_t
*
total_size
);
extern
int
is_region_empty
(
const
struct
region
*
region
);
extern
void
get_region_extents
(
const
struct
region
*
region
,
rectangle_t
*
rect
);
extern
void
offset_region
(
struct
region
*
region
,
int
x
,
int
y
);
extern
struct
region
*
copy_region
(
struct
region
*
dst
,
const
struct
region
*
src
);
extern
struct
region
*
intersect_region
(
struct
region
*
dst
,
const
struct
region
*
src1
,
const
struct
region
*
src2
);
extern
struct
region
*
subtract_region
(
struct
region
*
dst
,
const
struct
region
*
src1
,
const
struct
region
*
src2
);
extern
struct
region
*
union_region
(
struct
region
*
dst
,
const
struct
region
*
src1
,
const
struct
region
*
src2
);
static
inline
struct
region
*
create_empty_region
(
void
)
{
return
create_region
(
NULL
,
0
);
}
/* window functions */
extern
void
destroy_thread_windows
(
struct
thread
*
thread
);
...
...
server/window.c
View file @
e8d86b7c
...
...
@@ -463,6 +463,114 @@ user_handle_t find_window_to_repaint( user_handle_t parent, struct thread *threa
}
/* clip all children of a given window out of the visible region */
static
struct
region
*
clip_children
(
struct
window
*
parent
,
struct
window
*
last
,
struct
region
*
region
,
int
offset_x
,
int
offset_y
)
{
struct
window
*
ptr
;
struct
region
*
tmp
=
create_empty_region
();
if
(
!
tmp
)
return
NULL
;
for
(
ptr
=
parent
->
first_child
;
ptr
&&
ptr
!=
last
;
ptr
=
ptr
->
next
)
{
if
(
!
(
ptr
->
style
&
WS_VISIBLE
))
continue
;
if
(
ptr
->
ex_style
&
WS_EX_TRANSPARENT
)
continue
;
set_region_rect
(
tmp
,
&
ptr
->
window_rect
);
offset_region
(
tmp
,
offset_x
,
offset_y
);
if
(
!
(
region
=
subtract_region
(
region
,
region
,
tmp
)))
break
;
if
(
is_region_empty
(
region
))
break
;
}
free_region
(
tmp
);
return
region
;
}
/* compute the visible region of a window */
static
struct
region
*
get_visible_region
(
struct
window
*
win
,
struct
window
*
top
,
unsigned
int
flags
)
{
struct
region
*
tmp
,
*
region
;
struct
window
*
ptr
;
rectangle_t
rect
;
int
offset_x
,
offset_y
;
if
(
!
(
region
=
create_empty_region
()))
return
NULL
;
/* first check if all ancestors are visible */
for
(
ptr
=
win
;
ptr
!=
top_window
;
ptr
=
ptr
->
parent
)
if
(
!
(
ptr
->
style
&
WS_VISIBLE
))
return
region
;
/* empty region */
/* retrieve window rectangle in parent coordinates */
if
((
flags
&
DCX_PARENTCLIP
)
&&
win
->
parent
)
{
rect
.
left
=
rect
.
top
=
0
;
rect
.
right
=
win
->
parent
->
client_rect
.
right
-
win
->
parent
->
client_rect
.
left
;
rect
.
bottom
=
win
->
parent
->
client_rect
.
bottom
-
win
->
parent
->
client_rect
.
top
;
offset_x
=
win
->
client_rect
.
left
;
offset_y
=
win
->
client_rect
.
top
;
}
else
if
(
flags
&
DCX_WINDOW
)
{
rect
=
win
->
window_rect
;
offset_x
=
win
->
window_rect
.
left
;
offset_y
=
win
->
window_rect
.
top
;
}
else
{
rect
=
win
->
client_rect
;
offset_x
=
win
->
client_rect
.
left
;
offset_y
=
win
->
client_rect
.
top
;
}
/* create a region relative to the window itself */
set_region_rect
(
region
,
&
rect
);
offset_region
(
region
,
-
offset_x
,
-
offset_y
);
/* clip children */
if
(
flags
&
DCX_CLIPCHILDREN
)
{
if
(
!
clip_children
(
win
,
NULL
,
region
,
offset_x
-
win
->
client_rect
.
left
,
offset_y
-
win
->
client_rect
.
top
))
goto
error
;
}
/* clip siblings of ancestors */
if
(
top
&&
top
!=
win
&&
(
tmp
=
create_empty_region
())
!=
NULL
)
{
offset_region
(
region
,
offset_x
,
offset_y
);
/* make it relative to parent */
while
(
win
->
parent
)
{
if
(
win
->
style
&
WS_CLIPSIBLINGS
)
{
if
(
!
clip_children
(
win
->
parent
,
win
,
region
,
0
,
0
))
goto
error
;
if
(
is_region_empty
(
region
))
break
;
}
if
(
win
==
top
)
break
;
/* clip to parent client area */
win
=
win
->
parent
;
offset_x
+=
win
->
client_rect
.
left
;
offset_y
+=
win
->
client_rect
.
top
;
offset_region
(
region
,
win
->
client_rect
.
left
,
win
->
client_rect
.
top
);
set_region_rect
(
tmp
,
&
win
->
client_rect
);
if
(
!
intersect_region
(
region
,
region
,
tmp
))
goto
error
;
if
(
is_region_empty
(
region
))
break
;
}
offset_region
(
region
,
-
offset_x
,
-
offset_y
);
/* make it relative to target window again */
free_region
(
tmp
);
}
return
region
;
error:
free_region
(
region
);
return
NULL
;
}
/* get the window class of a window */
struct
window_class
*
get_window_class
(
user_handle_t
window
)
{
...
...
@@ -825,6 +933,24 @@ DECL_HANDLER(get_windows_offset)
}
/* get the visible region of a window */
DECL_HANDLER
(
get_visible_region
)
{
struct
region
*
region
;
struct
window
*
win
=
get_window
(
req
->
window
);
struct
window
*
top
=
NULL
;
if
(
!
win
)
return
;
if
(
req
->
top_win
&&
!
(
top
=
get_window
(
req
->
top_win
)))
return
;
if
((
region
=
get_visible_region
(
win
,
top
,
req
->
flags
)))
{
rectangle_t
*
data
=
get_region_data_and_free
(
region
,
&
reply
->
total_size
);
set_reply_data_ptr
(
data
,
min
(
reply
->
total_size
,
get_reply_max_size
())
);
}
}
/* set a window property */
DECL_HANDLER
(
set_window_property
)
{
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment