首页 > 解决方案 > 即使使用 MediaQuery.of(context),不同设备的小部件大小也不一致

问题描述

我的应用程序分辨率有问题。我在 Pageview 和 GridList 上使用的卡片有不同的大小,具体取决于我使用的设备。无论设备的类型和大小如何,我都希望它们相同。

我在用着

Mediaquery.of<context).size 
Mediaquery.of<context).devicePixelRatio

获取设备的高度、宽度和像素比。

这些是与我使用的设备相关的打印:

Emulator (Pixel 3a):
I/flutter (11909): height: 759.2727272727273
I/flutter (11909): width: 392.72727272727275
I/flutter (11909): pixel ratio: 2.75

My phone (Galaxy S9):
I/flutter ( 8712): height: 692.0
I/flutter ( 8712): width: 360.0
I/flutter ( 8712): pixel ratio: 3.0

我在 S9 上的屏幕分辨率实际上是 FHD+ 2220x1080,与 Pixel 3a 的分辨率相同。我不知道为什么它显示的分辨率那么低,为什么它们也不同!这是没有意义的。

这是我的代码:(都在 CustomScrollView 中)

SliverToBoxAdapter(
  child: Padding(
    padding: const EdgeInsets.all(20.0),
    child: Text(
      I18n.of(context).bestSelling,
      style: kHeaderTextStyle,
    ),
  ),
),
SliverToBoxAdapter(
  child: Container(
    height: screenSize.height / 3.5,
    child: PageView.builder(
      controller: PageController(
        initialPage: 1,
        viewportFraction: 0.14*screenRatio,
      ),
      scrollDirection: Axis.horizontal,
      itemCount: bestProducts.length,
      itemBuilder: (context, index) {
        return ProductCardBS(bestProducts[index]);
      },
    ),
  ),
),
SliverToBoxAdapter(
  child: Padding(
    padding: const EdgeInsets.all(20.0),
    child: Text(
      I18n.of(context).sales,
      style: kHeaderTextStyle,
    ),
  ),
),
SliverPadding(
  padding: const EdgeInsets.only(
    left: 24,
    right: 24,
    bottom: 8.0,
  ),
  sliver: SliverGrid(
    delegate: SliverChildBuilderDelegate(
      (_, index) {
        return ProductCard(saleProducts[index]);
      },
      childCount: saleProducts.length,
    ),
    gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
      crossAxisCount: 2,
      mainAxisSpacing: 6.0,
      crossAxisSpacing: 6.0,
      childAspectRatio: 0.215 * screenRatio,
    ),
  ),
),

我还尝试将 screenRatio 更改为 screenSize.height ,但无论哪种方式我都会得到不同的尺寸。

这些是与代码相关的图片,第一个来自我的 S9,第二个来自 Pixel 3a:

在此处输入图像描述 在此处输入图像描述

注意卡片的高度是如何不同的。

标签: flutterflutter-layout

解决方案


媒体查询不会给你物理像素的数量。这就是为什么你的屏幕有 2220x1080 像素,但它会说它更少。

如果您想要确切的像素数,您可以使用window来自dart:ui.

var screenSize = window.physicalSize;

并使用SizedBox小部件将小部件强制为精确大小。

此外,您可能不应该将 viewportFraction 与任何东西相乘。它已经占您屏幕的百分比。

viewportFraction: 0.14*screenRatio, -> viewportFraction: 0.14,

还有一个叫做的小部件FractionallySizedBox总是占据屏幕的相同部分:

FractionallySizedBox(
      heightFactor: 0.2,
      widthFactor: 0.28,
      child: ...,
    ),

推荐阅读