2

我正在编辑使用Multi-Touch 协议的驱动程序文件。我的目标是将滑动手势从 (x1,y1) 绑定到 (x2,y2) 沿着一条线。

为此,我在键压检测功能中执行此功能:

static void do_swipe(struct kp *kp, long xstart, long ystart, long xend, long yend,
        int id) {
    printk("SWIPE! X1 %d Y1 %d X2 %d Y2 %d ID %d \n",xstart,ystart,xend,yend,id);
    int sx, sy;
    int dx = abs(xend - xstart);
    int dy = abs(yend - ystart);
    if (xstart < xend)
        sx = 1;
    else
        sx = -1;
    if (ystart < yend)
        sy = 1;
    else
        sy = -1;
    int err = dx - dy;
    long tempx = xstart;
    long tempy = ystart;
    while (1) {
        key_report(kp, tempx, tempy, id);
        //Touch is now detected with input_sync
        input_sync(kp->input);
        if(tempx == xend && tempy == yend) break;
        int e2 = 2 * err;
        if (e2 > (-1)*dy) {
            err = err - dy;
            tempx = tempx + sx;
        } else if (e2 < dx) {
            err = err + dx;
            tempy = tempy + sy;
        }
    }
    printk("END! X %d Y %d \n",tempx, tempy);

}

这个函数是一个编辑过的 Bresenham 的线算法,而不是画一条线,而是调用 key_report 来模拟给定坐标处的触摸。

static void key_report(struct kp *kp, long x, long y, int id) {
    if (x == 0 && y == 0) {
        //printk("---------- zero point --------------\n");
        ;
    } else {
        input_report_key(kp->input, BTN_TOUCH, 1);
        input_report_abs(kp->input, ABS_MT_TRACKING_ID, id);
        input_report_abs(kp->input, ABS_MT_TOUCH_MAJOR, 20);
        input_report_abs(kp->input, ABS_MT_WIDTH_MAJOR, 20);
        input_report_abs(kp->input, ABS_MT_POSITION_X, x);
        input_report_abs(kp->input, ABS_MT_POSITION_Y, y);
        input_mt_sync(kp->input);
    }
    release = 1;
}

其中 kp-> input 是这样定义的

struct input_dev *input;

编辑:我更新了代码,并且还附上了按键压力的通用代码,因为我希望驱动程序对每个按键压力只执行一次滑动,以避免滑动循环。

static void kp_work(struct kp *kp) {
int i, code, value;
kp_search_key(kp);
if (key_param[0] == 3) {
    if (kp->key_valid[4] == 1) {
        value = kp->key_value[4];
        kp->flagchan4 = 0;
        if (value >= 0 && value <= (9 + 40)) {
            if (key_param[99] == 1 ) {
                do_swipe(kp, key_param[25], key_param[26], key_param[97],
                        key_param[98], 12);
            } else
                key_report(kp, key_param[25], key_param[26], 12);
        } else if (value >= 392 - 40 && value <= (392 + 40)) {
            if (key_param[102] == 1) {
                do_swipe(kp, key_param[23], key_param[24], key_param[100],
                        key_param[101], 12);
            } else
                key_report(kp, key_param[23], key_param[24], 12);
        } 
        kp->flagchan4 = 0;
    } else {
        kp->flagchan4 = 1;
    }
}
input_sync(kp->input);
}

也许我可以对 kp->flagchan4 进行检查... 编辑:对 flagchan4 进行检查就可以了。

4

0 回答 0