简体   繁体   English

列子PageView的全屏交互

[英]Column child PageView interaction through the whole screen

I'm trying to create a screen as follows:我正在尝试按如下方式创建一个屏幕:

在此处输入图像描述

The bottom part is PageView.builder.底部是 PageView.builder。 I want it to be interactable through the whole screen.我希望它可以通过整个屏幕进行交互。

The first thing I came up with was wrapping them in a stack, creating an invisible PageView on the top, and synchronizing the bottom and invisible(top) PageViews' controllers.我想出的第一件事是将它们包装在一个堆栈中,在顶部创建一个不可见的 PageView,并同步底部和不可见(顶部)PageViews 的控制器。 But, in this case, the button doesn't receive input.但是,在这种情况下,按钮不会接收输入。

PS: Wrapping the top PageView by a listener with HitTestBehavior.translucent didn't work. PS:使用 HitTestBehavior.translucent 的侦听器包装顶部 PageView 不起作用。 I think PageView doesn't let tap events propagate.我认为 PageView 不会让点击事件传播。

How can I aproach this screen?我怎样才能接近这个屏幕?

class Test extends StatelessWidget {
  Test({Key? key}) : super(key: key);
  final pageController = PageController();
  final infoPages = [
    Container(
      color: Colors.blue[200],
      child: Text("info 1"),
    ),
    Container(
      color: Colors.blue[400],
      child: Text("info 2"),
    ),
    Container(
      color: Colors.blue[600],
      child: Text("info 3"),
    ),
  ];

  @override
  Widget build(BuildContext context) {
    return Column(
      children: [
        Expanded(
            flex: 2,
            child: Container(
              color: Colors.grey,
              child: Text("this is a static image"),
            )),
        Expanded(
          child: TextButton(
            onPressed: () {
              print("button pressed");
            },
            child: const Text("This is a static button"),
          ),
        ),
        Expanded(
          flex: 2,
          child: PageView.builder(
            controller: pageController,
            itemCount: infoPages.length,
            itemBuilder: ((context, index) {
              return infoPages[index];
            }),
          ),
        ),
      ],
    );
  }
}

Dear parallel universe me;亲爱的平行宇宙我; I solved it by wrapping it with a stack, disabling the PageView interaction, and controlling it with a GestureDetector.我通过用堆栈包装它、禁用 PageView 交互并使用 GestureDetector 控制它来解决它。

class Test extends StatefulWidget {
  Test({Key? key}) : super(key: key);

  @override
  State<Test> createState() => _TestState();
}

class _TestState extends State<Test> {
  final pageController = PageController();

  final infoPages = [
    Container(
      color: Colors.blue[200],
      child: Text("info 1"),
    ),
    Container(
      color: Colors.blue[400],
      child: Text("info 2"),
    ),
    Container(
      color: Colors.blue[600],
      child: Text("info 3"),
    ),
  ];

  late double offset;
  late double start;
  bool snap = true;

  @override
  Widget build(BuildContext context) {
    return Stack(children: [
      Column(
        children: [
          Expanded(
            flex: 2,
            child: Container(
              color: Colors.grey,
              child: Text("this is a static image"),
            ),
          ),
          Expanded(
            child: TextButton(
              onPressed: () {
                print("button pressed");
              },
              child: const Text("This is a static button"),
            ),
          ),
          Expanded(
            flex: 2,
            child: PageView.builder(
              pageSnapping: snap,
              physics: const NeverScrollableScrollPhysics(),
              controller: pageController,
              itemCount: infoPages.length,
              itemBuilder: ((context, index) {
                return infoPages[index];
              }),
            ),
          ),
        ],
      ),
      GestureDetector(
        onHorizontalDragStart: (details) {
          offset = pageController.offset;
          start = details.globalPosition.dx;
          setState(() {
            snap = false;
          });
        },
        onHorizontalDragUpdate: (details) {
          final dx = details.globalPosition.dx - start;
          double temp = offset - dx;
          pageController.jumpTo(temp);
        },
        onHorizontalDragEnd: (details) {
          setState(() {
            snap = true;
          });
        },
      )
    ]);
  }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM