449
450
XSelectInput(up->display, upw->clientWindow, 0);
450
451
HashTable_Delete(up->allWindows, GUINT_TO_POINTER(upw->clientWindow));
453
#if defined(VM_HAVE_X11_SHAPE_EXT)
454
if (up->shapeEventBase) {
455
XShapeSelectInput(up->display, upw->toplevelWindow, 0);
457
if (upw->clientWindow) {
458
XShapeSelectInput(up->display, upw->clientWindow, 0);
454
464
* Okay, now we may have two UnityPlatformWindows running around, one each for
1038
1052
} else if (event->atom == up->atoms._NET_WM_DESKTOP) {
1053
if (upw->wantSetDesktopNumberOnUnmap) {
1055
* We're to preserve _NET_WM_DESKTOP across unmapping and remapping a
1056
* window (most likely a taskbar). If we see PropertyDelete, assume
1057
* it's ours and reset the _NET_WM_DESKTOP property. If, however, we
1058
* instead see a PropertyNewValue (the only other possibility, hence
1059
* no "else" below), then we assume some other client wished to change
1060
* the property, and we forget about restoring _NET_WM_DESKTOP when
1061
* we remap the window later.
1063
if (event->state == PropertyDelete) {
1064
Debug("%s: PropertyDelete: _NET_WM_DESKTOP: %#lx. Resetting to %d.\n",
1065
__func__, upw->clientWindow, upw->onUnmapDesktopNumber);
1066
UPWindow_SetEWMHDesktop(up, upw, upw->onUnmapDesktopNumber);
1068
upw->wantSetDesktopNumberOnUnmap = FALSE;
1039
1071
regetDesktop = TRUE;
1040
1072
} else if (event->atom != up->atoms._NET_WM_WINDOW_TYPE) {
1916
1956
Window checkWindow;
1917
1957
Bool retval = FALSE;
1958
Bool triedLeader = FALSE;
1919
1960
checkWindow = upw->clientWindow ? upw->clientWindow : upw->toplevelWindow;
1921
1963
UnityPlatformResetErrorCount(up);
1922
1964
ret = XGetWindowProperty(up->display, checkWindow, up->atoms._NET_WM_PID, 0,
1923
1965
1024, False, AnyPropertyType,
1978
2020
XFree(classHint.res_class);
2023
if (!retval && !triedLeader) {
2025
* Last ditch - look for a client leader window and try all of the above
2028
checkWindow = UPWindowLookupClientLeader(up, upw);
2029
if (checkWindow != None) {
1981
2035
Debug("UnityX11GetWindowPath(%#lx) returning %s\n", upw->toplevelWindow,
1982
2036
retval ? "TRUE" : "FALSE");
2515
2569
XFree(rects); rects = NULL;
2573
* The X Shape Extension operates on unshaped windows by using default bounding
2574
* and clipping regions. I.e., XShapeGetRectangles will return a single rectangle
2575
* for an unshaped window. Without the following test, we'd end up informing the
2576
* Unity client that this window can be described by a single rectangle region,
2577
* and it'd expect further region updates when the window's geometry changes.
2579
* This wouldn't be a problem, except we don't receive XShapeEvents on these
2580
* windows when they're resized. To work around this, we make sure that the UWT
2581
* knows that unshaped windows are exactly that.
2588
XShapeQueryExtents(up->display, upw->toplevelWindow,
2589
&bShaped, &dummy, &dummy, &dummy, &dummy,
2590
&cShaped, &dummy, &dummy, &dummy, &dummy);
2591
if (!bShaped && !cShaped) {
2592
UnityWindowTracker_ChangeWindowRegion(up->tracker, upw->toplevelWindow, 0);
2518
2597
UnityPlatformResetErrorCount(up);
3727
3805
ASSERT(desktopId < up->desktopInfo.numDesktops);
3728
3806
guestDesktopId = up->desktopInfo.unityDesktopToGuest[desktopId];
3730
if (!upw->isViewable) {
3731
Atom currentDesktop = guestDesktopId; // Cast for 64-bit correctness.
3808
UPWindow_SetEWMHDesktop(up, upw, guestDesktopId);
3815
*------------------------------------------------------------------------------
3817
* UPWindow_SetEWMHDesktop --
3819
* Move the window to the specified desktop. ewmhDesktopId corresponds
3820
* to a desktop index to be used with _NET_WM_DESKTOP.
3823
* This will directly change _NET_WM_DESKTOP of an unmapped window,
3824
* and will instead request the window manager to update that property
3825
* for a mapped window.
3830
*------------------------------------------------------------------------------
3835
UPWindow_SetEWMHDesktop(UnityPlatform *up, // IN
3836
UnityPlatformWindow *upw, // IN
3837
uint32 ewmhDesktopId) // IN
3839
Atom data[5] = {0, 0, 0, 0, 0};
3844
if (!upw->isViewable || upw->wantSetDesktopNumberOnUnmap) {
3845
Atom currentDesktop = ewmhDesktopId; // Cast for 64-bit correctness.
3734
3848
* Sending the _NET_WM_DESKTOP client message only works if the
3736
3850
* eliminate race conditions, but if the window is not mapped, we
3737
3851
* also need to set the property on the window so that it shows
3738
3852
* up on the correct desktop when it is re-mapped.
3854
* wantSetDesktopNumberOnUnmap implies that we unmapped the window
3855
* in question. We evaluate this here, in addition to isViewable,
3856
* because it's totally possible that the window server processed
3857
* our unmap request, but we just haven't received the notification
3858
* yet. (In other words, if that's the case, isViewable may still
3741
3862
XChangeProperty(up->display, (Window)upw->clientWindow, up->atoms._NET_WM_DESKTOP,
3742
3863
XA_CARDINAL, 32, PropModeReplace, (unsigned char *)¤tDesktop, 1);
3745
data[0] = guestDesktopId;
3866
data[0] = ewmhDesktopId;
3746
3867
data[1] = 2; // Indicates that this was requested by the pager/taskbar/etc.
3747
3868
UnityPlatformSendClientMessage(up,
3748
3869
upw->rootWindow,
3749
3870
upw->clientWindow,
3750
3871
up->atoms._NET_WM_DESKTOP,
3877
*-----------------------------------------------------------------------------
3879
* UPWindowLookupClientLeader --
3881
* Given a UnityPlatformWindow, look up the associated "client leader"
3882
* window, identified by the WM_CLIENT_LEADER property, if it exists.
3885
* A valid window ID if found, otherwise None.
3890
*-----------------------------------------------------------------------------
3894
UPWindowLookupClientLeader(UnityPlatform *up, // IN
3895
UnityPlatformWindow *upw) // IN
3899
unsigned long itemsReturned;
3900
unsigned long bytesRemaining;
3901
unsigned char *valueReturned = NULL;
3904
Window leaderWindow = None;
3909
checkWindow = upw->clientWindow ? upw->clientWindow : upw->toplevelWindow;
3911
UnityPlatformResetErrorCount(up);
3912
XGetWindowProperty(up->display, checkWindow, up->atoms.WM_CLIENT_LEADER, 0,
3913
4, False, XA_WINDOW, &propertyType, &propertyFormat,
3914
&itemsReturned, &bytesRemaining, &valueReturned);
3916
if (UnityPlatformGetErrorCount(up) == 0 && propertyFormat == 32 &&
3917
itemsReturned == 1) {
3918
leaderWindow = *(XID *)valueReturned;
3921
XFree(valueReturned);
3923
return leaderWindow;