animcur: Run the timer from the device, not the screen
This is very slightly more efficient since the callback now doesn't need to walk every input device, instead we know exactly which device's cursor is being updated. AnimCurTimerNotify() gets outdented nicely as a result. A more important side effect is that we can stop using the TimerAbsolute mode and just pass in the relative delay. In AnimCurSetCursorPosition, we no longer need to rearm the timer with the new screen; it is enough to update the device's state. In AnimCurDisplayCursor we need to notice when we're switching from animated cursor to regular and cancel the existing timer. Reviewed-by: Robert Morell <rmorell@nvidia.com> Tested-by: Robert Morell <rmorell@nvidia.com> Signed-off-by: Adam Jackson <ajax@redhat.com>
This commit is contained in:
parent
cc3241a712
commit
094a63d56f
|
@ -55,6 +55,7 @@ typedef struct _AnimCurElt {
|
||||||
typedef struct _AnimCur {
|
typedef struct _AnimCur {
|
||||||
int nelt; /* number of elements in the elts array */
|
int nelt; /* number of elements in the elts array */
|
||||||
AnimCurElt *elts; /* actually allocated right after the structure */
|
AnimCurElt *elts; /* actually allocated right after the structure */
|
||||||
|
OsTimerPtr timer;
|
||||||
} AnimCurRec, *AnimCurPtr;
|
} AnimCurRec, *AnimCurPtr;
|
||||||
|
|
||||||
typedef struct _AnimScrPriv {
|
typedef struct _AnimScrPriv {
|
||||||
|
@ -65,8 +66,6 @@ typedef struct _AnimScrPriv {
|
||||||
RealizeCursorProcPtr RealizeCursor;
|
RealizeCursorProcPtr RealizeCursor;
|
||||||
UnrealizeCursorProcPtr UnrealizeCursor;
|
UnrealizeCursorProcPtr UnrealizeCursor;
|
||||||
RecolorCursorProcPtr RecolorCursor;
|
RecolorCursorProcPtr RecolorCursor;
|
||||||
OsTimerPtr timer;
|
|
||||||
Bool timer_set;
|
|
||||||
} AnimCurScreenRec, *AnimCurScreenPtr;
|
} AnimCurScreenRec, *AnimCurScreenPtr;
|
||||||
|
|
||||||
static unsigned char empty[4];
|
static unsigned char empty[4];
|
||||||
|
@ -130,49 +129,27 @@ AnimCurCursorLimits(DeviceIntPtr pDev,
|
||||||
static CARD32
|
static CARD32
|
||||||
AnimCurTimerNotify(OsTimerPtr timer, CARD32 now, void *arg)
|
AnimCurTimerNotify(OsTimerPtr timer, CARD32 now, void *arg)
|
||||||
{
|
{
|
||||||
ScreenPtr pScreen = arg;
|
DeviceIntPtr dev = arg;
|
||||||
|
ScreenPtr pScreen = dev->spriteInfo->anim.pScreen;
|
||||||
AnimCurScreenPtr as = GetAnimCurScreen(pScreen);
|
AnimCurScreenPtr as = GetAnimCurScreen(pScreen);
|
||||||
DeviceIntPtr dev;
|
|
||||||
Bool activeDevice = FALSE;
|
|
||||||
CARD32 soonest = ~0; /* earliest time to wakeup again */
|
|
||||||
|
|
||||||
for (dev = inputInfo.devices; dev; dev = dev->next) {
|
|
||||||
if (IsPointerDevice(dev) && pScreen == dev->spriteInfo->anim.pScreen) {
|
|
||||||
if (!activeDevice)
|
|
||||||
activeDevice = TRUE;
|
|
||||||
|
|
||||||
if ((INT32) (now - dev->spriteInfo->anim.time) >= 0) {
|
|
||||||
AnimCurPtr ac = GetAnimCur(dev->spriteInfo->anim.pCursor);
|
AnimCurPtr ac = GetAnimCur(dev->spriteInfo->anim.pCursor);
|
||||||
int elt = (dev->spriteInfo->anim.elt + 1) % ac->nelt;
|
int elt = (dev->spriteInfo->anim.elt + 1) % ac->nelt;
|
||||||
DisplayCursorProcPtr DisplayCursor;
|
DisplayCursorProcPtr DisplayCursor = pScreen->DisplayCursor;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Not a simple Unwrap/Wrap as this
|
* Not a simple Unwrap/Wrap as this isn't called along the DisplayCursor
|
||||||
* isn't called along the DisplayCursor
|
|
||||||
* wrapper chain.
|
* wrapper chain.
|
||||||
*/
|
*/
|
||||||
DisplayCursor = pScreen->DisplayCursor;
|
|
||||||
pScreen->DisplayCursor = as->DisplayCursor;
|
pScreen->DisplayCursor = as->DisplayCursor;
|
||||||
(void) (*pScreen->DisplayCursor) (dev,
|
(void) (*pScreen->DisplayCursor) (dev, pScreen, ac->elts[elt].pCursor);
|
||||||
pScreen,
|
|
||||||
ac->elts[elt].pCursor);
|
|
||||||
as->DisplayCursor = pScreen->DisplayCursor;
|
as->DisplayCursor = pScreen->DisplayCursor;
|
||||||
pScreen->DisplayCursor = DisplayCursor;
|
pScreen->DisplayCursor = DisplayCursor;
|
||||||
|
|
||||||
dev->spriteInfo->anim.elt = elt;
|
dev->spriteInfo->anim.elt = elt;
|
||||||
dev->spriteInfo->anim.time = now + ac->elts[elt].delay;
|
dev->spriteInfo->anim.time = now + ac->elts[elt].delay;
|
||||||
}
|
|
||||||
|
|
||||||
if (soonest > dev->spriteInfo->anim.time)
|
return ac->elts[elt].delay;
|
||||||
soonest = dev->spriteInfo->anim.time;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (activeDevice)
|
|
||||||
return soonest - now;
|
|
||||||
|
|
||||||
as->timer_set = FALSE;
|
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static Bool
|
static Bool
|
||||||
|
@ -198,17 +175,19 @@ AnimCurDisplayCursor(DeviceIntPtr pDev, ScreenPtr pScreen, CursorPtr pCursor)
|
||||||
pDev->spriteInfo->anim.pCursor = pCursor;
|
pDev->spriteInfo->anim.pCursor = pCursor;
|
||||||
pDev->spriteInfo->anim.pScreen = pScreen;
|
pDev->spriteInfo->anim.pScreen = pScreen;
|
||||||
|
|
||||||
if (!as->timer_set) {
|
ac->timer = TimerSet(ac->timer, 0, ac->elts[0].delay,
|
||||||
TimerSet(as->timer, TimerAbsolute, pDev->spriteInfo->anim.time,
|
AnimCurTimerNotify, pDev);
|
||||||
AnimCurTimerNotify, pScreen);
|
|
||||||
as->timer_set = TRUE;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
ret = TRUE;
|
ret = TRUE;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
CursorPtr old = pDev->spriteInfo->anim.pCursor;
|
||||||
|
|
||||||
|
if (old && IsAnimCur(old))
|
||||||
|
TimerCancel(GetAnimCur(old)->timer);
|
||||||
|
|
||||||
pDev->spriteInfo->anim.pCursor = 0;
|
pDev->spriteInfo->anim.pCursor = 0;
|
||||||
pDev->spriteInfo->anim.pScreen = 0;
|
pDev->spriteInfo->anim.pScreen = 0;
|
||||||
ret = (*pScreen->DisplayCursor) (pDev, pScreen, pCursor);
|
ret = (*pScreen->DisplayCursor) (pDev, pScreen, pCursor);
|
||||||
|
@ -227,12 +206,6 @@ AnimCurSetCursorPosition(DeviceIntPtr pDev,
|
||||||
Unwrap(as, pScreen, SetCursorPosition);
|
Unwrap(as, pScreen, SetCursorPosition);
|
||||||
if (pDev->spriteInfo->anim.pCursor) {
|
if (pDev->spriteInfo->anim.pCursor) {
|
||||||
pDev->spriteInfo->anim.pScreen = pScreen;
|
pDev->spriteInfo->anim.pScreen = pScreen;
|
||||||
|
|
||||||
if (!as->timer_set) {
|
|
||||||
TimerSet(as->timer, TimerAbsolute, pDev->spriteInfo->anim.time,
|
|
||||||
AnimCurTimerNotify, pScreen);
|
|
||||||
as->timer_set = TRUE;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
ret = (*pScreen->SetCursorPosition) (pDev, pScreen, x, y, generateEvent);
|
ret = (*pScreen->SetCursorPosition) (pDev, pScreen, x, y, generateEvent);
|
||||||
Wrap(as, pScreen, SetCursorPosition, AnimCurSetCursorPosition);
|
Wrap(as, pScreen, SetCursorPosition, AnimCurSetCursorPosition);
|
||||||
|
@ -307,11 +280,6 @@ AnimCurInit(ScreenPtr pScreen)
|
||||||
return FALSE;
|
return FALSE;
|
||||||
|
|
||||||
as = GetAnimCurScreen(pScreen);
|
as = GetAnimCurScreen(pScreen);
|
||||||
as->timer = TimerSet(NULL, TimerAbsolute, 0, AnimCurTimerNotify, pScreen);
|
|
||||||
if (!as->timer) {
|
|
||||||
return FALSE;
|
|
||||||
}
|
|
||||||
as->timer_set = FALSE;
|
|
||||||
|
|
||||||
Wrap(as, pScreen, CloseScreen, AnimCurCloseScreen);
|
Wrap(as, pScreen, CloseScreen, AnimCurCloseScreen);
|
||||||
|
|
||||||
|
@ -359,10 +327,14 @@ AnimCursorCreate(CursorPtr *cursors, CARD32 *deltas, int ncursor,
|
||||||
|
|
||||||
pCursor->id = cid;
|
pCursor->id = cid;
|
||||||
|
|
||||||
|
ac = GetAnimCur(pCursor);
|
||||||
|
ac->timer = TimerSet(NULL, 0, 0, AnimCurTimerNotify, NULL);
|
||||||
|
|
||||||
/* security creation/labeling check */
|
/* security creation/labeling check */
|
||||||
rc = XaceHook(XACE_RESOURCE_ACCESS, client, cid, RT_CURSOR, pCursor,
|
rc = XaceHook(XACE_RESOURCE_ACCESS, client, cid, RT_CURSOR, pCursor,
|
||||||
RT_NONE, NULL, DixCreateAccess);
|
RT_NONE, NULL, DixCreateAccess);
|
||||||
if (rc != Success) {
|
if (rc != Success) {
|
||||||
|
TimerFree(ac->timer);
|
||||||
dixFiniPrivates(pCursor, PRIVATE_CURSOR);
|
dixFiniPrivates(pCursor, PRIVATE_CURSOR);
|
||||||
free(pCursor);
|
free(pCursor);
|
||||||
return rc;
|
return rc;
|
||||||
|
@ -372,7 +344,6 @@ AnimCursorCreate(CursorPtr *cursors, CARD32 *deltas, int ncursor,
|
||||||
* Fill in the AnimCurRec
|
* Fill in the AnimCurRec
|
||||||
*/
|
*/
|
||||||
animCursorBits.refcnt++;
|
animCursorBits.refcnt++;
|
||||||
ac = GetAnimCur(pCursor);
|
|
||||||
ac->nelt = ncursor;
|
ac->nelt = ncursor;
|
||||||
ac->elts = (AnimCurElt *) (ac + 1);
|
ac->elts = (AnimCurElt *) (ac + 1);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue