示例#1
0
void
PtrAddEvent(int buttonMask, int x, int y, rfbClientPtr cl)
{
    int i;
    int valuators[2];
    ValuatorMask mask;
    static int oldButtonMask = 0;

    if (!ptrDevice)
        FatalError("Pointer device not initialized");

    if (cursorPosX != x || cursorPosY != y) {
        valuators[0] = x;
        valuators[1] = y;
        valuator_mask_set_range(&mask, 0, 2, valuators);
        QueuePointerEvents(ptrDevice, MotionNotify, 0, POINTER_ABSOLUTE,
                           &mask);

        cursorPosX = x;
        cursorPosY = y;
    }

    for (i = 0; i < 5; i++) {
        if ((buttonMask ^ oldButtonMask) & (1 << i)) {
            if (buttonMask & (1 << i)) {
                valuator_mask_set_range(&mask, 0, 0, NULL);
                QueuePointerEvents(ptrDevice, ButtonPress, i + 1,
                                   POINTER_RELATIVE, &mask);
            } else {
                valuator_mask_set_range(&mask, 0, 0, NULL);
                QueuePointerEvents(ptrDevice, ButtonRelease, i + 1,
                                   POINTER_RELATIVE, &mask);
            }
        }
    }

    oldButtonMask = buttonMask;
    mieqProcessInputEvents();
}
示例#2
0
/**
 * Enqueue a motion event.
 *
 */
void
winEnqueueMotion(int x, int y)
{
    int valuators[2];
    ValuatorMask mask;

    valuators[0] = x;
    valuators[1] = y;

    valuator_mask_set_range(&mask, 0, 2, valuators);
    QueuePointerEvents(g_pwinPointer, MotionNotify, 0,
                       POINTER_ABSOLUTE | POINTER_SCREEN, &mask);

}
示例#3
0
/**
 * Move the device's pointer to the x/y coordinates on the given screen.
 * This function generates and enqueues pointer events.
 *
 * @param pDev The device to move
 * @param pScreen The screen the device is on
 * @param x The x coordinate in per-screen coordinates
 * @param y The y coordinate in per-screen coordinates
 */
void
miPointerMove (DeviceIntPtr pDev, ScreenPtr pScreen, int x, int y)
{
    int i, nevents;
    int valuators[2];
    ValuatorMask mask;

    miPointerMoveNoEvent(pDev, pScreen, x, y);

    /* generate motion notify */
    valuators[0] = x;
    valuators[1] = y;

    if (!events)
    {
        events = InitEventList(GetMaximumEventsNum());

        if (!events)
        {
            FatalError("Could not allocate event store.\n");
            return;
        }
    }

    valuator_mask_set_range(&mask, 0, 2, valuators);
    nevents = GetPointerEvents(events, pDev, MotionNotify, 0,
                               POINTER_SCREEN | POINTER_ABSOLUTE | POINTER_NORAW, &mask);

    OsBlockSignals();
#ifdef XQUARTZ
    darwinEvents_lock();
#endif
    for (i = 0; i < nevents; i++)
        mieqEnqueue(pDev, &events[i]);
#ifdef XQUARTZ
    darwinEvents_unlock();
#endif
    OsReleaseSignals();
}
示例#4
0
static int
ProcXTestFakeInput(ClientPtr client)
{
    REQUEST(xXTestFakeInputReq);
    int nev, n, type, rc;
    xEvent *ev;
    DeviceIntPtr dev = NULL;
    WindowPtr root;
    Bool extension = FALSE;
    ValuatorMask mask;
    int valuators[MAX_VALUATORS] = { 0 };
    int numValuators = 0;
    int firstValuator = 0;
    int nevents = 0;
    int i;
    int base = 0;
    int flags = 0;
    int need_ptr_update = 1;

    nev = (stuff->length << 2) - sizeof(xReq);
    if ((nev % sizeof(xEvent)) || !nev)
        return BadLength;
    nev /= sizeof(xEvent);
    UpdateCurrentTime();
    ev = (xEvent *) &((xReq *) stuff)[1];
    type = ev->u.u.type & 0177;

    if (type >= EXTENSION_EVENT_BASE) {
        extension = TRUE;

        /* check device */
        rc = dixLookupDevice(&dev, stuff->deviceid & 0177, client,
                             DixWriteAccess);
        if (rc != Success) {
            client->errorValue = stuff->deviceid & 0177;
            return rc;
        }

        /* check type */
        type -= DeviceValuator;
        switch (type) {
        case XI_DeviceKeyPress:
        case XI_DeviceKeyRelease:
            if (!dev->key) {
                client->errorValue = ev->u.u.type;
                return BadValue;
            }
            break;
        case XI_DeviceButtonPress:
        case XI_DeviceButtonRelease:
            if (!dev->button) {
                client->errorValue = ev->u.u.type;
                return BadValue;
            }
            break;
        case XI_DeviceMotionNotify:
            if (!dev->valuator) {
                client->errorValue = ev->u.u.type;
                return BadValue;
            }
            break;
        case XI_ProximityIn:
        case XI_ProximityOut:
            if (!dev->proximity) {
                client->errorValue = ev->u.u.type;
                return BadValue;
            }
            break;
        default:
            client->errorValue = ev->u.u.type;
            return BadValue;
        }

        /* check validity */
        if (nev == 1 && type == XI_DeviceMotionNotify)
            return BadLength;   /* DevMotion must be followed by DevValuator */

        if (type == XI_DeviceMotionNotify) {
            firstValuator = ((deviceValuator *) (ev + 1))->first_valuator;
            if (firstValuator > dev->valuator->numAxes) {
                client->errorValue = ev->u.u.type;
                return BadValue;
            }

            if (ev->u.u.detail == xFalse)
                flags |= POINTER_ABSOLUTE;
        }
        else {
            firstValuator = 0;
            flags |= POINTER_ABSOLUTE;
        }

        if (nev > 1 && !dev->valuator) {
            client->errorValue = firstValuator;
            return BadValue;
        }

        /* check validity of valuator events */
        base = firstValuator;
        for (n = 1; n < nev; n++) {
            deviceValuator *dv = (deviceValuator *) (ev + n);
            if (dv->type != DeviceValuator) {
                client->errorValue = dv->type;
                return BadValue;
            }
            if (dv->first_valuator != base) {
                client->errorValue = dv->first_valuator;
                return BadValue;
            }
            switch (dv->num_valuators) {
            case 6:
                valuators[base + 5] = dv->valuator5;
            case 5:
                valuators[base + 4] = dv->valuator4;
            case 4:
                valuators[base + 3] = dv->valuator3;
            case 3:
                valuators[base + 2] = dv->valuator2;
            case 2:
                valuators[base + 1] = dv->valuator1;
            case 1:
                valuators[base] = dv->valuator0;
                break;
            default:
                client->errorValue = dv->num_valuators;
                return BadValue;
            }

            base += dv->num_valuators;
            numValuators += dv->num_valuators;

            if (firstValuator + numValuators > dev->valuator->numAxes) {
                client->errorValue = dv->num_valuators;
                return BadValue;
            }
        }
        type = type - XI_DeviceKeyPress + KeyPress;

    }
    else {
        if (nev != 1)
            return BadLength;
        switch (type) {
        case KeyPress:
        case KeyRelease:
            dev = PickKeyboard(client);
            break;
        case ButtonPress:
        case ButtonRelease:
            dev = PickPointer(client);
            break;
        case MotionNotify:
            dev = PickPointer(client);
            valuators[0] = ev->u.keyButtonPointer.rootX;
            valuators[1] = ev->u.keyButtonPointer.rootY;
            numValuators = 2;
            firstValuator = 0;
            if (ev->u.u.detail == xFalse)
                flags = POINTER_ABSOLUTE | POINTER_DESKTOP;
            break;
        default:
            client->errorValue = ev->u.u.type;
            return BadValue;
        }

        /* Technically the protocol doesn't allow for BadAccess here but
         * this can only happen when all MDs are disabled.  */
        if (!dev)
            return BadAccess;

        dev = GetXTestDevice(dev);
    }


    /* If the event has a time set, wait for it to pass */
    if (ev->u.keyButtonPointer.time) {
        TimeStamp activateTime;
        CARD32 ms;

        activateTime = currentTime;
        ms = activateTime.milliseconds + ev->u.keyButtonPointer.time;
        if (ms < activateTime.milliseconds)
            activateTime.months++;
        activateTime.milliseconds = ms;
        ev->u.keyButtonPointer.time = 0;

        /* see mbuf.c:QueueDisplayRequest (from the deprecated Multibuffer
         * extension) for code similar to this */

        if (!ClientSleepUntil(client, &activateTime, NULL, NULL)) {
            return BadAlloc;
        }
        /* swap the request back so we can simply re-execute it */
        if (client->swapped) {
            (void) XTestSwapFakeInput(client, (xReq *) stuff);
            swaps(&stuff->length);
        }
        ResetCurrentRequest(client);
        client->sequence--;
        return Success;
    }

    switch (type) {
    case KeyPress:
    case KeyRelease:
        if (!dev->key)
            return BadDevice;

        if (ev->u.u.detail < dev->key->xkbInfo->desc->min_key_code ||
            ev->u.u.detail > dev->key->xkbInfo->desc->max_key_code) {
            client->errorValue = ev->u.u.detail;
            return BadValue;
        }

        need_ptr_update = 0;
        break;
    case MotionNotify:
        if (!dev->valuator)
            return BadDevice;

        if (!(extension || ev->u.keyButtonPointer.root == None)) {
            rc = dixLookupWindow(&root, ev->u.keyButtonPointer.root,
                                 client, DixGetAttrAccess);
            if (rc != Success)
                return rc;
            if (root->parent) {
                client->errorValue = ev->u.keyButtonPointer.root;
                return BadValue;
            }

            /* Add the root window's offset to the valuators */
            if ((flags & POINTER_ABSOLUTE) && firstValuator <= 1 && numValuators > 0) {
                if (firstValuator == 0)
                    valuators[0] += root->drawable.pScreen->x;
                if (firstValuator < 2 && firstValuator + numValuators > 1)
                    valuators[1 - firstValuator] += root->drawable.pScreen->y;
            }
        }
        if (ev->u.u.detail != xTrue && ev->u.u.detail != xFalse) {
            client->errorValue = ev->u.u.detail;
            return BadValue;
        }

        /* FIXME: Xinerama! */

        break;
    case ButtonPress:
    case ButtonRelease:
        if (!dev->button)
            return BadDevice;

        if (!ev->u.u.detail || ev->u.u.detail > dev->button->numButtons) {
            client->errorValue = ev->u.u.detail;
            return BadValue;
        }
        break;
    }
    if (screenIsSaved == SCREEN_SAVER_ON)
        dixSaveScreens(serverClient, SCREEN_SAVER_OFF, ScreenSaverReset);

    switch (type) {
    case MotionNotify:
        valuator_mask_set_range(&mask, firstValuator, numValuators, valuators);
        nevents = GetPointerEvents(xtest_evlist, dev, type, 0, flags, &mask);
        break;
    case ButtonPress:
    case ButtonRelease:
        valuator_mask_set_range(&mask, firstValuator, numValuators, valuators);
        nevents = GetPointerEvents(xtest_evlist, dev, type, ev->u.u.detail,
                                   flags, &mask);
        break;
    case KeyPress:
    case KeyRelease:
        nevents =
            GetKeyboardEvents(xtest_evlist, dev, type, ev->u.u.detail);
        break;
    }

    for (i = 0; i < nevents; i++)
        mieqProcessDeviceEvent(dev, &xtest_evlist[i], miPointerGetScreen(inputInfo.pointer));

    if (need_ptr_update)
        miPointerUpdateSprite(dev);
    return Success;
}
示例#5
0
void
ExtInputAddEvent(rfbDevInfoPtr dev, int type, int buttons)
{
    ValuatorMask mask;

    if (!dev)
        FatalError("ExtInputDeviceAddEvent(): Invalid argument");

    if (rfbVirtualTablet) {
        int i;
        rfbDevInfoPtr vtDev;

        switch (dev->productID) {
        case rfbGIIDevTypeStylus:
            vtDev = &virtualTabletStylus;
            break;
        case rfbGIIDevTypeEraser:
            vtDev = &virtualTabletEraser;
            break;
        case rfbGIIDevTypeTouch:
            vtDev = &virtualTabletTouch;
            break;
        case rfbGIIDevTypePad:
            vtDev = &virtualTabletPad;
            break;
        default:
            if (stristr(dev->name, "stylus"))
                vtDev = &virtualTabletStylus;
            else if (stristr(dev->name, "eraser"))
                vtDev = &virtualTabletEraser;
            else if (stristr(dev->name, "touch"))
                vtDev = &virtualTabletTouch;
            else if (stristr(dev->name, "pad"))
                vtDev = &virtualTabletPad;
            else
                return;
        }

        if (dev->valFirst >= vtDev->numValuators ||
            buttons > vtDev->numButtons)
            return;

        vtDev->valFirst = dev->valFirst;
        vtDev->valCount = min(dev->valCount,
                              vtDev->numValuators - vtDev->valFirst);

        for (i = vtDev->valFirst; i < vtDev->valFirst + vtDev->valCount; i++)
				{
            vtDev->values[i] = (int)roundl(
                (double)(dev->values[i] - dev->valuators[i].rangeMin) /
                    (double)(dev->valuators[i].rangeMax -
                             dev->valuators[i].rangeMin) *
                (double)(vtDev->valuators[i].rangeMax -
                         vtDev->valuators[i].rangeMin) +
                (double)vtDev->valuators[i].rangeMin);
        }
        dev = vtDev;
    }

    if (dev->valCount > 0) {
        valuator_mask_set_range(&mask, 0, dev->numValuators, dev->values);
        QueuePointerEvents(dev->pDev, type, buttons,
                           dev->mode == Absolute ? POINTER_ABSOLUTE :
                           POINTER_RELATIVE, &mask);
    } else {
        valuator_mask_set_range(&mask, 0, 0, NULL);
        QueuePointerEvents(dev->pDev, type, buttons, POINTER_RELATIVE, &mask);
    }
    mieqProcessInputEvents();
}
示例#6
0
文件: Events.c 项目: Agnesa/xserver
void
xnestCollectEvents(void)
{
    XEvent X;
    int valuators[2];
    ValuatorMask mask;
    ScreenPtr pScreen;

    while (XCheckIfEvent(xnestDisplay, &X, xnestNotExposurePredicate, NULL)) {
        switch (X.type) {
        case KeyPress:
            xnestUpdateModifierState(X.xkey.state);
            xnestQueueKeyEvent(KeyPress, X.xkey.keycode);
            break;

        case KeyRelease:
            xnestUpdateModifierState(X.xkey.state);
            xnestQueueKeyEvent(KeyRelease, X.xkey.keycode);
            break;

        case ButtonPress:
            valuator_mask_set_range(&mask, 0, 0, NULL);
            xnestUpdateModifierState(X.xkey.state);
            lastEventTime = GetTimeInMillis();
            QueuePointerEvents(xnestPointerDevice, ButtonPress,
                               X.xbutton.button, POINTER_RELATIVE, &mask);
            break;

        case ButtonRelease:
            valuator_mask_set_range(&mask, 0, 0, NULL);
            xnestUpdateModifierState(X.xkey.state);
            lastEventTime = GetTimeInMillis();
            QueuePointerEvents(xnestPointerDevice, ButtonRelease,
                               X.xbutton.button, POINTER_RELATIVE, &mask);
            break;

        case MotionNotify:
            valuators[0] = X.xmotion.x;
            valuators[1] = X.xmotion.y;
            valuator_mask_set_range(&mask, 0, 2, valuators);
            lastEventTime = GetTimeInMillis();
            QueuePointerEvents(xnestPointerDevice, MotionNotify,
                               0, POINTER_ABSOLUTE, &mask);
            break;

        case FocusIn:
            if (X.xfocus.detail != NotifyInferior) {
                pScreen = xnestScreen(X.xfocus.window);
                if (pScreen)
                    xnestDirectInstallColormaps(pScreen);
            }
            break;

        case FocusOut:
            if (X.xfocus.detail != NotifyInferior) {
                pScreen = xnestScreen(X.xfocus.window);
                if (pScreen)
                    xnestDirectUninstallColormaps(pScreen);
            }
            break;

        case KeymapNotify:
            break;

        case EnterNotify:
            if (X.xcrossing.detail != NotifyInferior) {
                pScreen = xnestScreen(X.xcrossing.window);
                if (pScreen) {
                    NewCurrentScreen(inputInfo.pointer, pScreen, X.xcrossing.x,
                                     X.xcrossing.y);
                    valuators[0] = X.xcrossing.x;
                    valuators[1] = X.xcrossing.y;
                    valuator_mask_set_range(&mask, 0, 2, valuators);
                    lastEventTime = GetTimeInMillis();
                    QueuePointerEvents(xnestPointerDevice, MotionNotify,
                                       0, POINTER_ABSOLUTE, &mask);
                    xnestDirectInstallColormaps(pScreen);
                }
            }
            break;

        case LeaveNotify:
            if (X.xcrossing.detail != NotifyInferior) {
                pScreen = xnestScreen(X.xcrossing.window);
                if (pScreen) {
                    xnestDirectUninstallColormaps(pScreen);
                }
            }
            break;

        case DestroyNotify:
            if (xnestParentWindow != (Window) 0 &&
                X.xdestroywindow.window == xnestParentWindow)
                exit(0);
            break;

        case CirculateNotify:
        case ConfigureNotify:
        case GravityNotify:
        case MapNotify:
        case ReparentNotify:
        case UnmapNotify:
            break;

        default:
            ErrorF("xnest warning: unhandled event\n");
            break;
        }
    }
}