blob: 77b54f6204a805dbe9210f2d42a79644dbb3ec62 [file] [log] [blame]
// Copyright 2013 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
import 'dart:math' as math;
import 'dart:typed_data';
import 'package:test/bootstrap/browser.dart';
import 'package:test/test.dart';
import 'package:ui/ui.dart' as ui;
import 'package:web_engine_tester/golden_tester.dart';
import '../common/test_initialization.dart';
import 'utils.dart';
void main() {
internalBootstrapBrowserTest(() => testMain);
}
const ui.Rect kBlueSquareRegion = ui.Rect.fromLTRB(0, 0, 25, 25);
const ui.Rect kRedCircleRegion = ui.Rect.fromLTRB(25, 0, 50, 25);
const ui.Rect kMagentaStarRegion = ui.Rect.fromLTRB(0, 25, 30, 55);
const ui.Rect kGreenSquiggleRegion = ui.Rect.fromLTRB(30, 25, 50, 55);
const ui.Rect kTotalAtlasRegion = ui.Rect.fromLTRB(0, 0, 55, 55);
ui.Image generateAtlas() {
final ui.PictureRecorder recorder = ui.PictureRecorder();
final ui.Canvas canvas = ui.Canvas(recorder);
canvas.drawColor(const ui.Color(0), ui.BlendMode.src);
// Draw the square
canvas.save();
canvas.clipRect(kBlueSquareRegion);
canvas.drawRect(
// Inset the square by one pixel so it doesn't bleed into the other sprites.
kBlueSquareRegion.deflate(1.0),
ui.Paint()..color = const ui.Color(0xFF0000FF)
);
canvas.restore();
// Draw the circle
canvas.save();
canvas.clipRect(kRedCircleRegion);
canvas.drawCircle(
kRedCircleRegion.center,
// Make the circle one pixel smaller than the bounds to it doesn't bleed
// into the other shapes.
(kRedCircleRegion.width / 2.0) - 1.0,
ui.Paint()..color = const ui.Color(0xFFFF0000));
canvas.restore();
// Draw the star
canvas.save();
canvas.clipRect(kMagentaStarRegion);
final ui.Offset starCenter = kMagentaStarRegion.center;
// Make the star one pixel smaller than the bounds so that it doesn't bleed
// into the other shapes.
final double radius = (kMagentaStarRegion.height / 2.0) - 1.0;
// Start at the top (rotated 90 degrees)
double theta = -math.pi / 2.0;
// Rotate two fifths of the circle each time
const double rotation = 4.0 * math.pi / 5.0;
final ui.Path starPath = ui.Path();
starPath.moveTo(
starCenter.dx + radius * math.cos(theta),
starCenter.dy + radius * math.sin(theta)
);
for (int i = 0; i < 5; i++) {
theta += rotation;
starPath.lineTo(
starCenter.dx + radius * math.cos(theta),
starCenter.dy + radius * math.sin(theta)
);
}
canvas.drawPath(
starPath,
ui.Paint()
..color = const ui.Color(0xFFFF00FF)
..style = ui.PaintingStyle.fill
);
canvas.restore();
// Draw the Squiggle
canvas.save();
canvas.clipRect(kGreenSquiggleRegion);
final ui.Path squigglePath = ui.Path();
squigglePath.moveTo(kGreenSquiggleRegion.topCenter.dx, kGreenSquiggleRegion.topCenter.dy + 2.0);
squigglePath.cubicTo(
kGreenSquiggleRegion.left - 10.0, kGreenSquiggleRegion.top + kGreenSquiggleRegion.height * 0.33,
kGreenSquiggleRegion.right + 10.0, kGreenSquiggleRegion.top + kGreenSquiggleRegion.height * 0.66,
kGreenSquiggleRegion.bottomCenter.dx, kGreenSquiggleRegion.bottomCenter.dy - 2.0
);
canvas.drawPath(
squigglePath,
ui.Paint()
..color = const ui.Color(0xFF00FF00)
..style = ui.PaintingStyle.stroke
..strokeWidth = 5.0
);
canvas.restore();
final ui.Picture picture = recorder.endRecording();
return picture.toImageSync(
kTotalAtlasRegion.width.toInt(),
kTotalAtlasRegion.height.toInt()
);
}
Future<void> testMain() async {
setUpUnitTests(
withImplicitView: true,
setUpTestViewDimensions: false,
);
const ui.Rect region = ui.Rect.fromLTWH(0, 0, 300, 300);
test('render atlas', () async {
final ui.PictureRecorder recorder = ui.PictureRecorder();
final ui.Canvas canvas = ui.Canvas(recorder, region);
final ui.Image atlas = generateAtlas();
canvas.drawImage(atlas, ui.Offset.zero, ui.Paint());
await drawPictureUsingCurrentRenderer(recorder.endRecording());
await matchGoldenFile('ui_atlas.png', region: region);
}, skip: isHtml); // HTML renderer doesn't support drawAtlas
test('drawAtlas', () async {
final ui.PictureRecorder recorder = ui.PictureRecorder();
final ui.Canvas canvas = ui.Canvas(recorder, region);
final ui.Image atlas = generateAtlas();
final List<ui.RSTransform> transforms = List<ui.RSTransform>.generate(
12, (int index) {
const double radius = 100;
const double rotation = math.pi / 6.0;
final double angle = rotation * index;
final double scos = math.sin(angle);
final double ssin = math.cos(angle);
return ui.RSTransform(
scos,
ssin,
region.center.dx + radius * scos,
region.center.dy + radius * ssin,
);
}
);
final List<ui.Rect> rects = <ui.Rect>[
kBlueSquareRegion,
kRedCircleRegion,
kMagentaStarRegion,
kGreenSquiggleRegion,
kBlueSquareRegion,
kRedCircleRegion,
kMagentaStarRegion,
kGreenSquiggleRegion,
kBlueSquareRegion,
kRedCircleRegion,
kMagentaStarRegion,
kGreenSquiggleRegion,
];
canvas.drawAtlas(
atlas, transforms, rects, null, null, null, ui.Paint());
await drawPictureUsingCurrentRenderer(recorder.endRecording());
await matchGoldenFile('ui_draw_atlas.png', region: region);
}, skip: isHtml); // HTML renderer doesn't support drawAtlas
test('drawAtlasRaw', () async {
final ui.PictureRecorder recorder = ui.PictureRecorder();
final ui.Canvas canvas = ui.Canvas(recorder, region);
final ui.Image atlas = generateAtlas();
final Float32List transforms = Float32List(12 * 4);
for (int i = 0; i < 12; i++) {
const double radius = 100;
const double rotation = math.pi / 6.0;
final double angle = rotation * i;
final double scos = math.sin(angle);
final double ssin = math.cos(angle);
transforms[i * 4] = scos;
transforms[i * 4 + 1] = ssin;
transforms[i * 4 + 2] = region.center.dx + radius * scos;
transforms[i * 4 + 3] = region.center.dy + radius * ssin;
}
final List<ui.Rect> rects = <ui.Rect>[
kBlueSquareRegion,
kRedCircleRegion,
kMagentaStarRegion,
kGreenSquiggleRegion,
kBlueSquareRegion,
kRedCircleRegion,
kMagentaStarRegion,
kGreenSquiggleRegion,
kBlueSquareRegion,
kRedCircleRegion,
kMagentaStarRegion,
kGreenSquiggleRegion,
];
final Float32List rawRects = Float32List(rects.length * 4);
for (int i = 0; i < rects.length; i++) {
rawRects[i * 4] = rects[i].left;
rawRects[i * 4 + 1] = rects[i].top;
rawRects[i * 4 + 2] = rects[i].right;
rawRects[i * 4 + 3] = rects[i].bottom;
}
final Int32List colors = Int32List(12);
for (int i = 0; i < 12; i++) {
final int rgb = 0xFF << (8 * (i % 3));
colors[i] = 0xFF000000 | rgb;
}
canvas.drawRawAtlas(
atlas,
transforms,
rawRects,
colors,
ui.BlendMode.dstIn,
null,
ui.Paint()
);
await drawPictureUsingCurrentRenderer(recorder.endRecording());
await matchGoldenFile('ui_draw_atlas_raw.png', region: region);
}, skip: isHtml); // HTML renderer doesn't support drawAtlas
}