1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
|
#include "ecore_xcb_private.h"
# ifdef ECORE_XCB_DAMAGE
# include <xcb/damage.h>
# endif
/* local variables */
static Eina_Bool _damage_avail = EINA_FALSE;
/* external variables */
int _ecore_xcb_event_damage = -1;
void
_ecore_xcb_damage_init(void)
{
LOGFN(__FILE__, __LINE__, __FUNCTION__);
#ifdef ECORE_XCB_DAMAGE
xcb_prefetch_extension_data(_ecore_xcb_conn, &xcb_damage_id);
#endif
}
void
_ecore_xcb_damage_finalize(void)
{
#ifdef ECORE_XCB_DAMAGE
const xcb_query_extension_reply_t *ext_reply;
#endif
LOGFN(__FILE__, __LINE__, __FUNCTION__);
#ifdef ECORE_XCB_DAMAGE
ext_reply = xcb_get_extension_data(_ecore_xcb_conn, &xcb_damage_id);
if ((ext_reply) && (ext_reply->present))
{
xcb_damage_query_version_cookie_t cookie;
xcb_damage_query_version_reply_t *reply;
cookie =
xcb_damage_query_version_unchecked(_ecore_xcb_conn,
XCB_DAMAGE_MAJOR_VERSION,
XCB_DAMAGE_MINOR_VERSION);
reply = xcb_damage_query_version_reply(_ecore_xcb_conn, cookie, NULL);
if (reply)
{
_damage_avail = EINA_TRUE;
free(reply);
}
if (_damage_avail)
_ecore_xcb_event_damage = ext_reply->first_event;
}
#endif
}
/**
* @defgroup Ecore_X_Damage_Group X Damage Extension Functions
*
* Functions related to the X Damage Extension.
*/
EAPI Eina_Bool
ecore_x_damage_query(void)
{
return _damage_avail;
}
/**
* Create a damage object
*
* @param drawable The drawable to monitor
* @param level The level of the damage report
* @return The damage object
*
* Creates a damage object to monitor changes to @p drawable,
* with the level @p level.
*
* @ingroup Ecore_X_Damage_Group
*/
EAPI Ecore_X_Damage
ecore_x_damage_new(Ecore_X_Drawable drawable,
Ecore_X_Damage_Report_Level level)
{
Ecore_X_Damage damage = 0;
LOGFN(__FILE__, __LINE__, __FUNCTION__);
CHECK_XCB_CONN;
if (!_damage_avail) return 0;
#ifdef ECORE_XCB_DAMAGE
damage = xcb_generate_id(_ecore_xcb_conn);
xcb_damage_create(_ecore_xcb_conn, damage, drawable, level);
// ecore_x_flush();
#endif
return damage;
}
/**
* Destroy a damage object
*
* @param The damage object to destroy
*
* Destroys the damage object @p damage
*
* @ingroup Ecore_X_Damage_Group
*/
EAPI void
ecore_x_damage_free(Ecore_X_Damage damage)
{
LOGFN(__FILE__, __LINE__, __FUNCTION__);
CHECK_XCB_CONN;
if (!_damage_avail) return;
#ifdef ECORE_XCB_DAMAGE
xcb_damage_destroy(_ecore_xcb_conn, damage);
// ecore_x_flush();
#endif
}
/**
* Synchronously modifies the region
*
* @param damage The damage object to destroy
* @param repair The repair region
* @param parts The parts region
*
* Synchronously modifies the regions in the following manner:
* If @p repair is @c XCB_NONE:
* 1) parts = damage
* 2) damage = <empty>
* Otherwise:
* 1) parts = damage INTERSECT repair
* 2) damage = damage - parts
* 3) Generate DamageNotify for remaining damage areas
*
* @ingroup Ecore_X_Damage_Group
*/
EAPI void
ecore_x_damage_subtract(Ecore_X_Damage damage,
Ecore_X_Region repair,
Ecore_X_Region parts)
{
LOGFN(__FILE__, __LINE__, __FUNCTION__);
CHECK_XCB_CONN;
if (!_damage_avail) return;
#ifdef ECORE_XCB_DAMAGE
xcb_damage_subtract(_ecore_xcb_conn, damage, repair, parts);
// ecore_x_flush();
#endif
}
|