baseline_test.dart 4.48 KB
Newer Older
Ian Hickson's avatar
Ian Hickson committed
1
// Copyright 2014 The Flutter Authors. All rights reserved.
2 3 4
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

5
import 'package:flutter/material.dart';
6
import 'package:flutter_test/flutter_test.dart';
7
import 'package:leak_tracker_flutter_testing/leak_tracker_flutter_testing.dart';
8 9

void main() {
10
  testWidgetsWithLeakTracking('Baseline - control test', (WidgetTester tester) async {
11
    await tester.pumpWidget(
12
      const Center(
13 14
        child: DefaultTextStyle(
          style: TextStyle(
15 16
            fontSize: 100.0,
          ),
17
          child: Text('X', textDirection: TextDirection.ltr),
18 19 20 21
        ),
      ),
    );
    expect(tester.renderObject<RenderBox>(find.text('X')).size, const Size(100.0, 100.0));
22
  });
23

24
  testWidgetsWithLeakTracking('Baseline - position test', (WidgetTester tester) async {
25
    await tester.pumpWidget(
26
      const Center(
27
        child: Baseline(
28
          baseline: 175.0,
29
          baselineType: TextBaseline.alphabetic,
30 31
          child: DefaultTextStyle(
            style: TextStyle(
32
              fontFamily: 'FlutterTest',
33 34
              fontSize: 100.0,
            ),
35
            child: Text('X', textDirection: TextDirection.ltr),
36 37 38 39 40
          ),
        ),
      ),
    );
    expect(tester.renderObject<RenderBox>(find.text('X')).size, const Size(100.0, 100.0));
41 42
    expect(
      tester.renderObject<RenderBox>(find.byType(Baseline)).size,
43
      const Size(100.0, 200),
44
    );
45
  });
46

47
  testWidgetsWithLeakTracking('Chip caches baseline', (WidgetTester tester) async {
48 49
    int calls = 0;
    await tester.pumpWidget(
50 51 52
      MaterialApp(
        home: Material(
          child: Baseline(
53 54
            baseline: 100.0,
            baselineType: TextBaseline.alphabetic,
55 56
            child: Chip(
              label: BaselineDetector(() {
57 58 59 60 61 62 63 64 65 66 67 68 69
                calls += 1;
              }),
            ),
          ),
        ),
      ),
    );
    expect(calls, 1);
    await tester.pump();
    expect(calls, 1);
    tester.renderObject<RenderBaselineDetector>(find.byType(BaselineDetector)).dirty();
    await tester.pump();
    expect(calls, 2);
70
  });
71

72
  testWidgetsWithLeakTracking('ListTile caches baseline', (WidgetTester tester) async {
73 74
    int calls = 0;
    await tester.pumpWidget(
75 76 77
      MaterialApp(
        home: Material(
          child: Baseline(
78 79
            baseline: 100.0,
            baselineType: TextBaseline.alphabetic,
80 81
            child: ListTile(
              title: BaselineDetector(() {
82 83 84 85 86 87 88 89 90 91 92 93 94 95
                calls += 1;
              }),
            ),
          ),
        ),
      ),
    );
    expect(calls, 1);
    await tester.pump();
    expect(calls, 1);
    tester.renderObject<RenderBaselineDetector>(find.byType(BaselineDetector)).dirty();
    await tester.pump();
    expect(calls, 2);
  });
96

97
  testWidgetsWithLeakTracking("LayoutBuilder returns child's baseline", (WidgetTester tester) async {
98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115
    await tester.pumpWidget(
      MaterialApp(
        home: Material(
          child: Baseline(
            baseline: 180.0,
            baselineType: TextBaseline.alphabetic,
            child: LayoutBuilder(
              builder: (BuildContext context, BoxConstraints constraints) {
                return BaselineDetector(() {});
              },
            ),
          ),
        ),
      ),
    );

    expect(tester.getRect(find.byType(BaselineDetector)).top, 160.0);
  });
116 117 118
}

class BaselineDetector extends LeafRenderObjectWidget {
119
  const BaselineDetector(this.callback, { super.key });
120 121 122 123

  final VoidCallback callback;

  @override
124
  RenderBaselineDetector createRenderObject(BuildContext context) => RenderBaselineDetector(callback);
125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153

  @override
  void updateRenderObject(BuildContext context, RenderBaselineDetector renderObject) {
    renderObject.callback = callback;
  }
}

class RenderBaselineDetector extends RenderBox {
  RenderBaselineDetector(this.callback);

  VoidCallback callback;

  @override
  bool get sizedByParent => true;

  @override
  double computeMinIntrinsicWidth(double height) => 0.0;

  @override
  double computeMaxIntrinsicWidth(double height) => 0.0;

  @override
  double computeMinIntrinsicHeight(double width) => 0.0;

  @override
  double computeMaxIntrinsicHeight(double width) => 0.0;

  @override
  double computeDistanceToActualBaseline(TextBaseline baseline) {
154
    callback();
155
    return 20.0;
156 157 158 159 160 161 162
  }

  void dirty() {
    markNeedsLayout();
  }

  @override
163 164
  Size computeDryLayout(BoxConstraints constraints) {
    return constraints.smallest;
165 166 167 168
  }

  @override
  void paint(PaintingContext context, Offset offset) { }
169
}