【问题标题】:Flutter: How to make a ListView transparent to pointer events (but not its non-transparent contents)?Flutter:如何使 ListView 对指针事件透明(但不是它的非透明内容)?
【发布时间】:2019-12-25 04:02:15
【问题描述】:

我有一个ScrollableListView 或任何其他),它包含一个透明小部件,比如Container(height:200)。我可以通过小部件和可滚动查看(换句话说,我可以看到可滚动后面的小部件)。

我怎样才能点击透明小部件和可滚动小部件,以便到达可滚动小部件后面的小部件?

ListView(
  children: [
    Container(height: 200), // Transparent.
    Container(color: Colors.red, height: 200),
    ],
);

注意,我不能用IgnorePointer 包裹滚动条,因为我仍然想点击滚动条中不透明的小部件。

【问题讨论】:

  • 您所说的“包含透明小部件”是什么意思?作为可滚动下方的子级或堆叠在可滚动父级下方?
  • 我的意思是上面的Container(height: 200)
  • “我到达了可滚动对象后面的小部件”是什么意思?
  • 您能否详细说明您想要达到的视觉效果?我不认为您可以通过透明小部件点击,但您可以更改布局,使其在视觉上保持不变,并且您要点击的小部件实际上位于顶部。
  • @Ovidiu 想象一下,您在一个覆盖整个屏幕的 Stack 中有一个 ListView。 ListView 位于顶部。您可以通过不透明的小部件拖动它。你可以点击透明的。

标签: flutter flutter-layout flutter-sliver


【解决方案1】:

我能想到的唯一合理的解决方案是在透明容器上添加一个GestureDetector,这将为您提供水龙头的全局位置:

GestureDetector(
  onTapUp: (TapUpDetails tapUpDetails) {
    print("onTapUp global: " + tapUpDetails.globalPosition.toString());
  },

然后将Key添加到列表后面的widget,并使用它来获取widget的矩形左上角的全局位置,以及widget的大小,并使用这些来获取小部件的矩形:

RenderBox renderBox = _key.currentContext.findRenderObject();
Offset topLeftCorner = renderBox.localToGlobal(Offset.zero);
Size size = renderBox.size;
Rect rectangle = topLeftCorner & size;

如果背景小部件不移动,您可以在下一帧的initState 内使用WidgetsBinding.instance.addPostFrameCallback 执行此操作(如果在initState 内同步执行,渲染对象将为空)并保存Rect - 否则你将不得不在每次点击时重新计算它。

最后在透明容器上的每一次点击,你可以计算点击的位置是否在背景小部件的边界内,并调用相应的代码:

// if tap is within boundaries of the background widget
if (rectangle.contains(tapUpDetails.globalPosition)) {
  // your code here
}

【讨论】:

  • 感谢您的回答。最后我改变了我的要求,不再需要这个,所以我没有机会测试你的答案。但我认为它可以工作,所以我会接受它。如果有一天我再次需要它,我会尝试实现它并回来告诉你。
猜你喜欢
  • 2016-02-15
  • 1970-01-01
  • 2016-06-30
  • 1970-01-01
  • 1970-01-01
  • 2013-05-16
  • 2015-11-12
  • 1970-01-01
相关资源
最近更新 更多