900字范文,内容丰富有趣,生活中的好帮手!
900字范文 > hid多点触摸触摸屏调试_向配备触摸板的笔记本电脑添加多点触摸手势支持

hid多点触摸触摸屏调试_向配备触摸板的笔记本电脑添加多点触摸手势支持

时间:2023-01-16 20:43:15

相关推荐

hid多点触摸触摸屏调试_向配备触摸板的笔记本电脑添加多点触摸手势支持

hid多点触摸触摸屏调试

多点触摸界面为在应用程序中集成新的交互模式提供了很多好处。 Mac OS X和Microsoft®Windows®上较新的硬件和驱动程序允许通过单击和单击以外的各种手势创建更有效的应用程序导航。 本文提供了在较旧的支持Linux®的硬件上添加一些新手势支持所需的工具和代码。 基于synclient程序的输出,此处提供的Perl代码使您可以将特定的应用程序功能分配给“三指轻扫”以及打开和关闭捏合手势。

要求

硬件

此处提供的代码仅适用于配备Synaptics TouchPad的计算机,并且恰巧是在IBM®ThinkPad T30上开发的。 从Acer Aspires到Toshiba Tecras,许多笔记本电脑上都可以找到Synaptics触摸板。 请查阅“ 相关主题 ”以获取Synaptics TouchPad软件项目的硬件兼容性列表,以查看是否遇到了麻烦。

软件

您需要具有evdev支持的现代Linux内核。 幸运的是,大多数现代发行版都内置了此功能。Synaptics软件包还附带了许多发行版,其中包括用于监视TouchPad事件的synclient 。 例如,Fedora Core还包括适当的X Window System配置,以使用户只需进行最少的修改就可以使用TouchPad。 其他发行版,例如Ubuntu V7.10,可能需要进一步配置,然后Synaptics软件包(使用sudo apt-get install tpconfig命令sudo apt-get install tpconfig)才能正常工作。 咨询相关主题在Linux下实现与Synaptics的TouchPad的基本功能的更多信息。

您还需要CPAN的Time :: HiRes模块来提供亚秒级的计时控制,以处理TouchPad事件。 另外,您需要X11 :: GuiTest模块将合成的X Window事件发送到应用程序。 请参阅相关的主题为这些工具。

确保基本功能

如果使用触摸板启用了鼠标控制,请检查是否有足够的多指检测以支持手势。 运行synclient -m 100并尝试在触摸板上进行不同的触摸。 您应该看到类似于以下的输出。

清单1.示例synclient -m 100输出

timex y z f w l r u d mmulti gl gm gr gdx gdy13.872 5680 4409 0 0 0 0 0 0 0 0 00000000 0 0 0 0 014.891 1072 3945 28 1 4 0 0 0 0 0 00000000 0 0 0 0 014.994 3529 2667 104 2 5 0 0 0 0 0 00000000 0 0 0 0 015.605 3669 3667 0 0 0 0 0 0 0 0 00000000 0 0 0 0 016.625 2628 2841 255 3 5 0 0 0 0 0 00000000 0 0 0 0 017.951 3117 2843 255 3 5 0 0 0 0 0 00000000 0 0 0 0 018.053 2902 3142 3 1 15 0 0 0 0 0 00000000 0 0 0 0 018.155 2430 3062 0 0 0 0 0 0 0 0 00000000 0 0 0 0 0

尝试用一,二和三指触摸以确保正确检测到事件。 确保触摸板能够检测到三个手指,因为要添加的第一个手势是“三指轻扫”。 请注意,在宽泛变化的空间中按两根手指时,TouchPad如何拾取零根手指以及X和Y坐标读数。 下面的处理脚本利用这些特征来帮助检测打开和关闭捏。 按Ctrl + c退出synclient程序。

通用程序方法

使用syclient输出来监视TouchPad状态是向Linux应用程序添加更多接口选项的简单有效的方法。 下面介绍的gestureListener.pl程序打开了一个管道,可以从synclient程序读取数据,并处理TouchPad事件以检测手势。 这些手势与发送到X Window System中当前对焦应用程序的键盘命令相关联。

滑动手势

三指轻扫是一种相对简单的手势检测方式,它只需要在触摸板上向左或向右移动三个手指即可。 清单2显示了开始处理synclient输出以进行手势检测所需的gestureListener.pl程序的开始。

清单2.gestureListener.pl程序开始

#!/usr/bin/perl -w # gestureListener.pl listens for pinch and swipe eventsuse strict;use Time::HiRes();use X11::GUITest qw( :ALL );my @xHist = ();# x coordinate historymy @yHist = ();# y coordinate historymy @xHistThree = ();# x coordinate history (three fingers)my $lastTime = 0; # time monitor for TouchPad event resetmy $eventTime = 0; # ensure enough time has passed between eventsmy $eventString = "default"; # the event to executemy $centerTouchPad = 3000; my $openSt = 1000; # start of open pinchmy $openEn = 500;# end of open pinchmy $closeSt = 1000; # start of close pinchmy $closeEn = 1000; # end of close pinchmy $synCmd = qq{synclient TouchpadOff=1 -m 10};my $currWind = GetInputFocus();die "couldn't get input window" unless $currWind;open(INFILE," $synCmd |") or die "can't read from synclient";

请注意,centerTouchPad变量和其他参数可能需要根据您的特定Synaptics硬件或驱动程序级别进行自定义。 synclient命令的TouchPadOff=1选项关闭常规的TouchPad事件。 红色的“鼠标棒”(在ThinkPads和其他设备上)仍然可用,并且支持PS2和USB鼠标。 无需关闭TouchPad,但可以减少从滑动和捏起识别与手势无关的鼠标事件的问题。

调用GetInputFocus可以找到焦点窗口的当前窗口标识符。 这允许SendKeys命令(稍后使用)将合成的X Window事件发送到当前在焦点窗口中。 清单3启动主程序循环并读取synclient输出。

清单3.主逻辑循环开始

while( my $line = <INFILE>){chomp($line);my( $time, $x, $y, $z, $f ) = split " ", $line;next if( $time =~ /time/ ); #ignore header linesif( $time - $lastTime > 1 ){ @xHist = ();@yHist = ();@xHistThree = ();}#if time reset$lastTime = $time;

在每次超时时重置事件检测历史记录阵列对于消除TouchPad手势之间的残留是至关重要的。 清单4显示了主程序循环中三指检测的开始。

清单4.三指处理

# three finger swipe detectionif( $f eq "3" ){@xHist = ();@yHist = ();push @xHistThree, $x;if( @xHistThree > 10 ){ my @srt = sort @xHistThree;my @revSrt = reverse sort @xHistThree;if( "@srt" eq "@xHistThree" ){ # alt + right arrow - forward$eventString = "'%({RIG})";}elsif( "@revSrt" eq "@xHistThree" ) { # alt + left arrow - back$eventString = "'%({LEF})";}#if forward or backward@xHistThree= ();}#if more than 10 data points in 3 finger array

收集到10点的三指数据后,将处理X坐标以创建升序和降序排序。 如果升序排序与X坐标的当前值匹配,则设置向右滑动的条件。 相反,如果降序匹配,则设置向左滑动条件。eventString变量将保持此条件,并将如下所示执行。

清单5.继续执行主要逻辑,执行事件

}else{ # reset all data points, yes you can have 0 fingers at x,y@xHist = ();@yHist = (); @xHistThree = ();}# if not one or two or three fingers# only process one event per time windowif( $eventString ne "default" ){ if( abs(time - $eventTime) > 1 ){ $eventTime = time;SendKeys( "$eventString");}#if enough time has passed$eventString = "default";}#if non default event}#synclient line inclose(INFILE);

此时,如果未检测到三个手指,则会重置用于捏或划的每个数据结构。 如果已设置事件,并且当前时间与上次事件执行时间相距甚远,则会执行新事件。SendKeys子例程将适当的事件(Alt +向左或向右箭头)发送到当前关注的应用程序。 如演示视频中所示(请参阅参考资料 ),这三个手指手势用于在浏览历史记录中前后移动。

捏手势

捏手势的检测要复杂得多,尤其是在用于开发本文的较旧硬件上。 使用kst之类的工具实时监视打开和关闭手势是从TouchPad数据中提取相关功能的一种有用方法。 将清单6中的代码插入65行(else上方),以开始进行捏捏检测部分。

清单6.捏捏检测

}elsif( $f eq "2" || $f eq "1" ){# accept 1 or 2 finger entries as part of pinch section@xHistThree = ();push @xHist, $x;push @yHist, $y;if( @xHist > 50 ){if( (getStrAvg(\@xHist) > $closeSt && getStrAvg(\@yHist) > $closeSt) &&(getEndAvg(\@yHist) < $closeEn && getEndAvg(\@yHist) < $closeEn) ){# wide to narrow detected, now search for enough 'wiggle'my $tenX = 0; my $tenY = 0;for my $each( @xHist[40..49] ){ $tenX += $each }for my $each( @yHist[40..49] ){ $tenY += $each }$tenX = $tenX / 10;$tenY = $tenY / 10;my $diffX = 0;my $diffY = 0;for my $each( @xHist[40..49] ){ $diffX += abs( $each - $tenX ) }for my $each( @yHist[40..49] ){ $diffY += abs( $each - $tenY ) }# ctrl - decrease font sizeif( ($diffX+$diffY) > 80 ){ $eventString = "^({-})" }@xHist = ();@yHist = ();@xHistThree = ();}#if x and y in range}#if enough data for 50 close pinch detection

捏住检测步骤的一部分可以接受一根或两根手指,以增强整体跟踪效果。 通过在捏捏运动中接受一两次触摸,可以更轻松地处理触摸和释放的稍微偏移的时间,以及在捏捏运动期间将一个手指从触摸板稍微移开的情况。

收集到50个或更多数据点后,将计算过去50个数据点的平均开始和结束位置。 第三个if语句执行四个单独的检查,以确保起点和终点位于正确的部分以进行近距离捏合检测-特别是如果起点的X和Y平均值必须大于近距离起点, 。 即,手指的位置需要在角上。 相反,端点必须在紧密捏合的端点内。getStrAvggetEndAvg创建三个起点和终点的平均值,这是检查的更可靠数据点。

真正的多点触摸功能将允许读取每个手指位置的X和Y坐标。 可用的Synaptics硬件不具有此功能,但是确实提供了一致的行为,因为将两指触摸点“平均”为synclient程序的一个输出。 监视synclient程序的输出显示,当两个手指在西南和东北角触摸时,其值会从TouchPad的角Swift移到中心。 如果手指放在角落,synclient输出将显示X和Y坐标保持在中心附近。 当手指移向中心时,此自动平均显示出轻微的扰动。 数据中的摆动由上面的代码部分检测到,表示捏紧,这与将手指保持在角落而不移动时数据点的合成平均相反。

X和Y坐标历史记录的十个尾随值被平均。 然后计算最后10个尾随值中的每个值与最后10个尾随值的平均值之间的差。 如果总体差异足够大(在这种情况下,大于80),则表明已检测到足够的摆动,并在eventString设置了close-pinch条件。

在清单103的第103行中添加清单7中所示的代码(if闭合括号,if闭合小节50点下方),用于检测打开小节。

清单7.捏捏检测

#open pinch requires substantially fewer data pointsif( @xHist > 10 ){if( (getStrAvg(\@xHist) < $openSt && getStrAvg(\@yHist) < $openSt) &&(getEndAvg(\@yHist) > $openEn && getEndAvg(\@yHist) > $openEn) ){# ctrl + increase font size$eventString = "^({+})"; @xHist = ();@yHist = ();@xHistThree = ();}#if absx and absy}#if enough data

除了需要更少的数据点来可靠地检测张开的捏以外,摆动检测步骤不是必需的。 通过使用kst之类的程序进行实时监视,synclient输出显示了针对打开捏手势收集的更多数据点。 在打开捏手势期间,两个手指位置的自动平均不会对synclient X和Y坐标产生很大影响。 因此,不再需要为了精确的手势检测而识别摆动。 清单8显示了getStrAvggetEndAvg平均子例程。

清单8.两个平均例程

sub getStrAvg{my $arrRef = $_[0];my $val = (@$arrRef[0] + @$arrRef[1] + @$arrRef[2]) / 3;$val = abs( $val - $centerTouchPad ); return($val);}#getStrAvgsub getEndAvg{ my $arrRef = $_[0];my $val = (@$arrRef[@$arrRef-3] + @$arrRef[@$arrRef-2] + @$arrRef[@$arrRef-1]) / 3;$val = abs( $val - $centerTouchPad );return($val);}#getEndAvg

将清单8中所示的代码放在第144行(文件末尾)以完成gestureListener.pl程序。getStrAvggetEndAvg分别负责返回前三个数组元素的平均值和后三个数组元素的平均值。

用法

激活程序是运行命令perl gestureListener.pl的简单问题。 使您的Web浏览窗口成为焦点,并尝试左右滑动浏览历史记录。 请注意,由于触控板尺寸较小以及硬件功能的固有局限性,在可靠触发手势事件之前可能需要进行一些练习。 请参阅演示视频(请参阅参考资料 ),以获取在作者的ThinkPad上起作用的手势示例。 如果您想重新启用TouchPad的“鼠标功能”,请在退出gestureListener.pl程序后运行synclient TouchPadOff=0

结论和更多示例

手势与事件之间的联系

请记住,SendKeys命令将向当前关注的应用程序发送适当的命令(Alt + Left,Ctrl +/-等),而不考虑它触发的功能是什么。 要考虑的一个相对简单的更改是根据窗口名称指定不同的击键或鼠标事件以发送到应用程序。

进一步的例子和修改

此处介绍的对synclient输出进行分析和处理以及合成X事件创建的组合只是Synaptics TouchPad新增功能的一条途径。 考虑添加其他手势识别,例如通过从synclient输出中进一步提取特征来进行捏旋转。 或者,修改Synaptics驱动程序源代码以在内核级别支持其他功能,并重写应用程序以更好地利用这些新的输入通道。

翻译自: /developerworks/opensource/library/os-touchpad/index.html

hid多点触摸触摸屏调试

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。