渐隐边缘列表视图- Flutter

vaqhlq81  于 2023-04-07  发布在  Flutter
关注(0)|答案(6)|浏览(196)

有没有人遇到过类似于Flutter的Android中的FadingEdgeLength的东西,这样当你向上滚动项目时,项目开始淡出屏幕顶部?
下面是我的界面建立起来的小工具。
如果有帮助的话,我指的是这些属性:
android:fadingEdgeLength=“10dp”
android:requiresFadingEdge=“horizontal”〉

@override
Widget build(BuildContext context) {
return Scaffold(
  appBar: AppBar(
    title: Text('CMS Users'),
  ),
  body: ListView.builder(
      padding: EdgeInsets.only(top: 20.0, left: 4.0),
      itemExtent: 70.0,
      itemCount: data == null ? 0 : data.length,
      itemBuilder: (BuildContext context, int index) {
        return Card(
          elevation: 10.0,
          child: InkWell(
            onTap: () {
              Navigator.push(
                  context,
                  new MaterialPageRoute(
                    builder: (BuildContext context) =>
                        new PeopleDetails("Profile Page", profiles[index]),
                  ));
            },
            child: ListTile(
              leading: CircleAvatar(
                child: Text(profiles[index].getInitials()),
                backgroundColor: Colors.deepPurple,
                radius: 30.0,
              ),
              title: Text(
                  data[index]["firstname"] + "." + data[index]["lastname"]),
              subtitle: Text(
                  data[index]["email"] + "\n" + data[index]["phonenumber"]),
            ),
          ),
        );
      }),
   );
 }
}
v9tzhpje

v9tzhpje1#

正如其他人所提到的,你可以把ListView放在ShaderMask下,但是通过一些额外的参数化,你可以得到更好的结果--至少如果你想达到我想要的效果。
也可以为LinearGradient设置[stops]列表:

  • 如果指定了[stops]列表,则必须与[colors]具有相同的长度。它指定了每个颜色从开始到结束的矢量分数,介于0.0和1.0之间。*

另外:**有混合模式,其中源的颜色通道被忽略,只有不透明度有影响。**BlendMode.dstOut在下面的例子中也是这样。正如你在截图中看到的,紫色没有具体使用,只用于矢量的分数。
你可以使用不同的[blendMode]设置,其中有很多。

void main() {
  runApp(
    MaterialApp(
      home: Scaffold(
        body: FadingListViewWidget(),
      ),
    ),
  );
}

class FadingListViewWidget extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return Center(
      child: Container(
        height: 320,
        child: ShaderMask(
          shaderCallback: (Rect rect) {
            return LinearGradient(
              begin: Alignment.topCenter,
              end: Alignment.bottomCenter,
              colors: [Colors.purple, Colors.transparent, Colors.transparent, Colors.purple],
              stops: [0.0, 0.1, 0.9, 1.0], // 10% purple, 80% transparent, 10% purple
            ).createShader(rect);
          },
          blendMode: BlendMode.dstOut,
          child: ListView.builder(
            itemCount: 100,
            itemBuilder: (BuildContext context, int index) {
              return Card(
                color: Colors.orangeAccent,
                child: ListTile(
                  title: Text('test test test test test test'),
                ),
              );
            },
          ),
        ),
      ),
    );
  }
}

5lhxktic

5lhxktic2#

您可以在ListView之上应用ShaderMask,并使用BlendMode来获得您想要的。

Widget animationsList() {
    return Expanded(
      child: ShaderMask(
        shaderCallback: (Rect bounds) {
            return LinearGradient(
              begin: Alignment.topCenter,
              end: Alignment.bottomCenter,
              colors: <Color>[Colors.transparent,Colors.red],
            ).createShader(bounds);
        },
        child: Container(height: 200.0, width: 200.0, color: Colors.blue,),
        blendMode: BlendMode.dstATop,
     ),
);
2o7dmzc5

2o7dmzc53#

我有类似的要求,所以我为这个任务创建了一个库。你可以在这里找到它:fading_edge_scrollview
要使用它,您需要将ScrollController添加到ListView,然后将此ListView作为子对象传递给FadingEdgeScrollView.fromScrollView构造函数

w8f9ii69

w8f9ii694#

使用Stack Package Listview,将Listview添加为第一个子级,第二个是带有LinearGradient的Positioned Container。示例来自我的代码:
堆栈:

return Stack(
                    children: <Widget>[
                      ListView(
                        scrollDirection: Axis.horizontal,
                        children: _myListOrderByDate,
                      ),
                      FadeEndListview(),
                    ],
                  );

覆盖类:

class FadeEndListview extends StatelessWidget {
  const FadeEndListview({
    Key key,
  }) : super(key: key);
  @override
  Widget build(BuildContext context) {
    return Positioned(
      right: 0,
      width: 8.0,
      height: kYoutubeThumbnailsHeight,
      child: Container(
        decoration: BoxDecoration(
          gradient: LinearGradient(
            begin: Alignment.centerRight,
            end: Alignment.centerLeft,
            stops: [0.0, 1.0],
            colors: [
                Theme.of(context).scaffoldBackgroundColor,
                Theme.of(context).scaffoldBackgroundColor.withOpacity(0.0),
            ],
          ),
        ),
      ),
    );
  }
}

它看起来像这样:

cotxawn7

cotxawn75#

试着用

Text(
        'This is big text, I am using Flutter and trying to fade text',
        overflow: TextOverflow.fade,
        maxLines: 1,
      ),
gwo2fgha

gwo2fgha6#

我把Krisztián Ódor的答案和ChatGPT的一个结果结合起来,得到了一个小部件,当用户滚动内容时,它会淡化一个ListView的内容,当ListView在任何一边时在这一边没有褪色。我这样做是因为在以前的版本中,我的部分内容由于褪色而不可见。该部件适用于两个滚动方向。要获得更多或更少的褪色调整停止在线性梯度。

import 'package:flutter/material.dart';

class FadingListView extends StatefulWidget {
  const FadingListView({required this.child, super.key});

  final ListView child;

  @override
  State<FadingListView> createState() => _FadingListViewState();
}

class _FadingListViewState extends State<FadingListView> {
  double _stopStart = 0;
  double _stopEnd = 1;

  @override
  Widget build(BuildContext context) {
    return NotificationListener<ScrollNotification>(
      onNotification: (scrollNotification) {
        setState(() {
          _stopStart = scrollNotification.metrics.pixels / 10;
          _stopEnd = (scrollNotification.metrics.maxScrollExtent -
                  scrollNotification.metrics.pixels) /
              10;

          _stopStart = _stopStart.clamp(0.0, 1.0);
          _stopEnd = _stopEnd.clamp(0.0, 1.0);
        });
        return true;
      },
      child: ShaderMask(
        shaderCallback: (Rect rect) {
          return LinearGradient(
            begin: widget.child.scrollDirection == Axis.horizontal
                ? Alignment.centerLeft
                : Alignment.topCenter,
            end: widget.child.scrollDirection == Axis.horizontal
                ? Alignment.centerRight
                : Alignment.bottomCenter,
            colors: const [
              Colors.black,
              Colors.transparent,
              Colors.transparent,
              Colors.black
            ],
            stops: [0.0, 0.05 * _stopStart, 1 - 0.05 * _stopEnd, 1.0],
          ).createShader(rect);
        },
        blendMode: BlendMode.dstOut,
        child: Padding(
          padding: const EdgeInsets.all(1.0),
          child: widget.child,
        ),
      ),
    );
  }
}

相关问题