blob: f5e2212ffc044e439fa5234b3e0090b0bbbd04e6 [file] [log] [blame]
// Copyright 2014 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 'package:flutter/material.dart';
import 'package:vector_math/vector_math_64.dart';
import 'dart:math';
class RotatedWireCube extends StatefulWidget {
const RotatedWireCube({required this.cubeColor, super.key});
final Color cubeColor;
@override
State<StatefulWidget> createState() => _RotatedWireCubeState();
}
class _RotatedWireCubeState extends State<RotatedWireCube>
with SingleTickerProviderStateMixin {
late final AnimationController _animation;
@override
void initState() {
super.initState();
_animation = AnimationController(
vsync: this,
lowerBound: 0,
upperBound: 2 * pi,
duration: const Duration(seconds: 15),
)..repeat();
}
@override
void dispose() {
_animation.dispose();
super.dispose();
}
@override
Widget build(BuildContext context) {
return AnimatedBuilder(
animation: _animation,
builder: (context, child) {
return CustomPaint(
size: const Size(200, 200),
painter: _RotatedWireCubePainter(
angle: _animation.value,
color: widget.cubeColor,
),
);
},
);
}
}
class _RotatedWireCubePainter extends CustomPainter {
static List<Vector3> vertices = [
Vector3(-0.5, -0.5, -0.5),
Vector3(0.5, -0.5, -0.5),
Vector3(0.5, 0.5, -0.5),
Vector3(-0.5, 0.5, -0.5),
Vector3(-0.5, -0.5, 0.5),
Vector3(0.5, -0.5, 0.5),
Vector3(0.5, 0.5, 0.5),
Vector3(-0.5, 0.5, 0.5),
];
static const List<List<int>> edges = [
[0, 1], [1, 2], [2, 3], [3, 0], // Front face
[4, 5], [5, 6], [6, 7], [7, 4], // Back face
[0, 4], [1, 5], [2, 6], [3, 7], // Connecting front and back
];
final double angle;
final Color color;
_RotatedWireCubePainter({required this.angle, required this.color});
Offset scaleAndCenter(Vector3 point, double size, Offset center) {
final scale = size / 2;
return Offset(center.dx + point.x * scale, center.dy - point.y * scale);
}
@override
void paint(Canvas canvas, Size size) {
final rotatedVertices = vertices
.map((vertex) => Matrix4.rotationX(angle).transformed3(vertex))
.map((vertex) => Matrix4.rotationY(angle).transformed3(vertex))
.map((vertex) => Matrix4.rotationZ(angle).transformed3(vertex))
.toList();
final center = Offset(size.width / 2, size.height / 2);
final paint = Paint()
..color = color
..style = PaintingStyle.stroke
..strokeWidth = 2;
for (var edge in edges) {
final p1 = scaleAndCenter(rotatedVertices[edge[0]], size.width, center);
final p2 = scaleAndCenter(rotatedVertices[edge[1]], size.width, center);
canvas.drawLine(p1, p2, paint);
}
}
@override
bool shouldRepaint(_RotatedWireCubePainter oldDelegate) => true;
}