如何伪造键盘移键。 Qt,Windows 10
Posted
技术标签:
【中文标题】如何伪造键盘移键。 Qt,Windows 10【英文标题】:How to fake a keyboard shift press. Qt, Windows 10 【发布时间】:2018-08-20 04:44:34 【问题描述】:我为基于触控的平板电脑开发了一些软件。该装置没有键盘,只有一个触摸屏(触摸屏模拟鼠标)。操作系统是 Windows 10,我们使用 Qt 作为图形用户界面框架。
我们依赖于一个类库点云库,它有一个组件,当我们单击鼠标左键时,该组件需要按下 SHIFT 键才能使某些事情发生。
我需要让底层软件组件相信已按下 SHIFT 键。
我试图通过“Qt 手段”将按键事件发送到 Qt 小部件,但假的 SHIFT 按键似乎没有到达底层 sw。零件。可能是因为它位于与 Qt 无关的类库中,并且该软件类库可能以不同方式检查关键事件(例如通过操作系统调用、c++ std 方式或类似方式)。
在尝试“Qt 方式”时这似乎不起作用:
QKeyEvent key_press(QEvent::KeyPress, Qt::Key_Shift, Qt::ShiftModifier);
QApplication::sendEvent(ui->qvtkWidget, &key_press);
因此,我可能需要使用操作系统方法来伪造 SHIFT 按键。
问题: 如何从 Qt 执行 OS 系统调用或类似操作,以使底层软件组件认为已按下并按住 SHIFT 键(同时用户按下鼠标左键)。
【问题讨论】:
也许这可以帮助你:batchloaf.wordpress.com/2012/04/17/… 强烈的迹象表明这是XY Problem。请解释点云库的确切作用,当您按住 shift 单击时(以及在哪里)。如果一切都失败了,您是否尝试过发送QMouseEvent?它允许您在单击时发送键盘修饰符。但是,根据库的确定方式,是否按住 [Shift] 键,您可能不走运。尤其是与 Qt 一起使用时,会出现令人麻木的消息处理实现。 由于我怀疑按下 shift 键是您的实际目标,而只是达到目的的一种手段,因此更优雅的方法是直接告诉底层软件组件将其行为更改为(无论行为按下shift键时有)。当然,这可能需要对底层软件组件进行修改,如果这不可能,那么您可能会留下黑客(例如假装按下 shift 键)作为您唯一的选择,但这不是最好的方法。 【参考方案1】:您想要的不是伪造换档键输入,而是在交互级别禁用换档检查。绝对是 XY 问题。
vtk InteractorStyle 类负责处理用户输入事件。您可以在 pcl_visualizer.cpp 的line 506 中看到
boost::signals2::connection
pcl::visualization::PCLVisualizer::registerPointPickingCallback (boost::function<void (const pcl::visualization::PointPickingEvent&)> callback)
return (style_->registerPointPickingCallback (callback));
回调在PCLVisualizerInteractorStyle
类中注册。
您可以在PCLVisualizer
的构造中传递您自己的自定义交互器样式,以便您可以安全地覆盖这个样式。要使用的构造函数是这个one
PCLVisualizer (int &argc, char **argv, const std::string &name="", PCLVisualizerInteractorStyle *style=PCLVisualizerInteractorStyle::New(), const bool create_interactor=true)
PointPickingCallback
类在初始化默认交互器样式时被 added automatically 作为鼠标回调。因此,为了覆盖此行为,您需要从 PCLVisualizerInteractorStyle
派生自己的类并覆盖 Initialize()
方法,并在构造时将此新的交互器样式传递给 PCLVisualizer
。
PointPickingCallback
中的 Execute 方法是检查 shift 键的地方。
void
pcl::visualization::PointPickingCallback::Execute (vtkObject *caller, unsigned long eventid, void*)
PCLVisualizerInteractorStyle *style = reinterpret_cast<PCLVisualizerInteractorStyle*>(caller);
vtkRenderWindowInteractor* iren = reinterpret_cast<pcl::visualization::PCLVisualizerInteractorStyle*>(caller)->GetInteractor ();
if (style->CurrentMode == 0)
if ((eventid == vtkCommand::LeftButtonPressEvent) && (iren->GetShiftKey () > 0))
float x = 0, y = 0, z = 0;
int idx = performSinglePick (iren, x, y, z);
// Create a PointPickingEvent if a point was selected
[... and so on]
总的来说,您需要:
-
从
PointPickingCallback
派生一个新类,该类覆盖Execute
方法中对shift 键的检查。
从 PCLVisualizerInteractorStyle
派生并覆盖 Initialize
方法以注册新的自定义 PointPickingCallback
类,该类不检查 shift 键,作为鼠标回调。
将新的交互器样式传递给PCLVisualizer
。
值得注意。可视化器支持两种选择模式:区域选择的橡皮筋和单点选择,可以通过按“x”键互换。我认为默认选择的是橡皮筋,这就是为什么它可能会首先检查是否按下了那个 shift 键。
【讨论】:
【参考方案2】:不确定其他解决方案是否正确,但我找到了一个更简单的解决方案。
使用可视化工具setupInteractor()
函数并通过QVTKWidget::interactor()->GetInteractorStyle()->GetInteractor()
将QVTKWidget
的交互器赋予它
这应该在你按下 shift 时起作用。
【讨论】:
以上是关于如何伪造键盘移键。 Qt,Windows 10的主要内容,如果未能解决你的问题,请参考以下文章