Improve default constructor for positioned components (#667)

This commit is contained in:
pedia
2021-02-24 00:27:17 +08:00
committed by GitHub
parent ec09ce0ce6
commit 9735cf5e08
11 changed files with 95 additions and 47 deletions

View File

@@ -22,6 +22,7 @@
- Add utility methods to the Anchor class to make it more "enum like"
- Enable user-defined anchors
- Added `toImage` method for the `Sprite` class
- Add more optional arguments for unified constructors of components
## 1.0.0-rc6
- Use `Offset` type directly in `JoystickAction.update` calculations

View File

@@ -20,9 +20,11 @@ class MyGame extends BaseGame {
jsonData,
);
final spriteSize = Vector2.all(200);
final animationComponent =
SpriteAnimationComponent.fromSpriteAnimation(spriteSize, animation)
..position = size / 2 - Vector2.all(100);
final animationComponent = SpriteAnimationComponent(
position: size / 2 - Vector2.all(100),
size: spriteSize,
animation: animation,
);
add(animationComponent);
}

View File

@@ -34,9 +34,9 @@ class MyGame extends BaseGame {
}
SpriteAnimationComponent buildAnimationComponent(Image image) {
final ac = SpriteAnimationComponent.fromSpriteAnimation(
Vector2.all(100),
buildAnimation(image),
final ac = SpriteAnimationComponent(
size: Vector2.all(100),
animation: buildAnimation(image),
);
ac.x = size.x / 2 - ac.x / 2;
return ac;

View File

@@ -19,10 +19,17 @@ class MyGame extends BaseGame {
Future<void> onLoad() async {
final r = Random();
final image = await images.load('test.png');
List.generate(500, (i) => SpriteComponent.fromImage(Vector2.all(32), image))
.forEach((sprite) {
sprite.x = r.nextInt(size.x.toInt()).toDouble();
sprite.y = r.nextInt(size.y.toInt()).toDouble();
List.generate(
500,
(i) => SpriteComponent(
position: Vector2(
r.nextInt(size.x.toInt()).toDouble(),
r.nextInt(size.x.toInt()).toDouble(),
),
size: Vector2.all(32),
sprite: Sprite(image),
),
).forEach((sprite) {
add(sprite);
});
}

View File

@@ -27,31 +27,33 @@ class MyGame extends BaseGame {
spriteSheet.createAnimation(row: 1, stepTime: 0.1, to: 7);
final spriteSize = Vector2(80.0, 90.0);
final vampireComponent = SpriteAnimationComponent.fromSpriteAnimation(
spriteSize,
vampireAnimation,
)
..x = 150
..y = 100;
final vampireComponent = SpriteAnimationComponent(
position: Vector2(150, 100),
size: spriteSize,
animation: vampireAnimation,
);
final ghostComponent =
SpriteAnimationComponent.fromSpriteAnimation(spriteSize, ghostAnimation)
..x = 150
..y = 220;
final ghostComponent = SpriteAnimationComponent(
position: Vector2(150, 220),
size: spriteSize,
animation: ghostAnimation,
);
add(vampireComponent);
add(ghostComponent);
// Some plain sprites
final vampireSpriteComponent =
SpriteComponent.fromSprite(spriteSize, spriteSheet.getSprite(0, 0))
..x = 50
..y = 100;
final vampireSpriteComponent = SpriteComponent(
position: Vector2(50, 100),
size: spriteSize,
sprite: spriteSheet.getSprite(0, 0),
);
final ghostSpriteComponent =
SpriteComponent.fromSprite(spriteSize, spriteSheet.getSprite(1, 0))
..x = 50
..y = 220;
final ghostSpriteComponent = SpriteComponent(
position: Vector2(50, 220),
size: spriteSize,
sprite: spriteSheet.getSprite(1, 0),
);
add(vampireSpriteComponent);
add(ghostSpriteComponent);

View File

@@ -15,7 +15,11 @@ class NineTileBoxComponent extends PositionComponent {
/// Takes the [NineTileBox] instance used to render this box.
///
/// It uses the x, y, width and height coordinates from the [PositionComponent] to render.
NineTileBoxComponent(this.nineTileBox);
NineTileBoxComponent(
this.nineTileBox, {
Vector2 position,
Vector2 size,
}) : super(position: position, size: size);
@mustCallSuper
@override

View File

@@ -23,7 +23,7 @@ import 'mixins/hitbox.dart';
/// within this component's (width, height).
abstract class PositionComponent extends BaseComponent {
/// The position of this component on the screen (relative to the anchor).
Vector2 position = Vector2.zero();
Vector2 position;
/// X position of this component on the screen (relative to the anchor).
double get x => position.x;
@@ -35,7 +35,7 @@ abstract class PositionComponent extends BaseComponent {
/// The size that this component is rendered with.
/// This is not necessarily the source size of the asset.
Vector2 size = Vector2.zero();
Vector2 size;
/// Width (size) that this component is rendered with.
double get width => size.x;
@@ -87,12 +87,12 @@ abstract class PositionComponent extends BaseComponent {
/// Angle (with respect to the x-axis) this component should be rendered with.
/// It is rotated around its anchor.
double angle = 0.0;
double angle;
/// Anchor point for this component. This is where flame "grabs it".
/// The [position] is relative to this point inside the component.
/// The [angle] is rotated around this point.
Anchor anchor = Anchor.topLeft;
Anchor anchor;
/// Whether this component should be flipped on the X axis before being rendered.
bool renderFlipX = false;
@@ -116,6 +116,16 @@ abstract class PositionComponent extends BaseComponent {
topLeftPosition = rect.topLeft.toVector2();
}
PositionComponent({
Vector2 position,
Vector2 size,
this.angle = 0.0,
this.anchor = Anchor.topLeft,
this.renderFlipX = false,
this.renderFlipY = false,
}) : position = position ?? Vector2.zero(),
size = size ?? Vector2.zero();
@override
bool containsPoint(Vector2 point) {
final rectangle = Rectangle.fromRect(toAbsoluteRect(), angle: angle)

View File

@@ -14,18 +14,25 @@ class SpriteAnimationComponent extends PositionComponent {
bool removeOnFinish = false;
/// Creates a component with an empty animation which can be set later
SpriteAnimationComponent();
SpriteAnimationComponent({
Vector2 position,
Vector2 size,
this.animation,
this.overridePaint,
this.removeOnFinish = false,
}) : super(position: position, size: size);
/// Creates an [SpriteAnimationComponent] from an [animation] and a [size]
///
/// Optionally [removeOnFinish] can be set to true to have this component be auto removed from the [BaseGame] when the animation is finished.
@Deprecated('Use SpriteAnimationComponent instead')
SpriteAnimationComponent.fromSpriteAnimation(
Vector2 size,
this.animation, {
Vector2 position,
this.removeOnFinish = false,
}) : assert(animation != null) {
super.size.setFrom(size);
}
}) : assert(animation != null),
super(size: size, position: position);
/// Creates a SpriteAnimationComponent from a [size], an [image] and [data]. Check [SpriteAnimationData] for more info on the available options.
///

View File

@@ -24,14 +24,19 @@ class SpriteComponent extends PositionComponent {
Paint overridePaint;
/// Creates a component with an empty sprite which can be set later
SpriteComponent();
SpriteComponent({
Vector2 position,
Vector2 size,
this.sprite,
this.overridePaint,
}) : super(position: position, size: size);
SpriteComponent.fromImage(Vector2 size, Image image)
: this.fromSprite(size, Sprite(image));
SpriteComponent.fromSprite(Vector2 size, this.sprite) {
super.size.setFrom(size);
}
factory SpriteComponent.fromImage(
Vector2 size,
Image image, {
Vector2 position,
}) =>
SpriteComponent(size: size, sprite: Sprite(image), position: position);
@mustCallSuper
@override

View File

@@ -53,9 +53,12 @@ class TextBoxComponent extends PositionComponent {
String text, {
TextConfig config,
TextBoxConfig boxConfig,
Vector2 position,
Vector2 size,
}) : _text = text,
_boxConfig = boxConfig ?? TextBoxConfig(),
_config = config ?? TextConfig() {
_config = config ?? TextConfig(),
super(position: position, size: size) {
_lines = [];
double lineHeight;
text.split(' ').forEach((word) {

View File

@@ -3,6 +3,7 @@ import 'dart:ui';
import 'package:flutter/foundation.dart';
import 'package:flutter/painting.dart';
import '../extensions/vector2.dart';
import '../text_config.dart';
import 'position_component.dart';
@@ -28,8 +29,14 @@ class TextComponent extends PositionComponent {
_updateBox();
}
TextComponent(this._text, {TextConfig config})
: _config = config ?? TextConfig() {
TextComponent(
this._text, {
TextConfig config,
Vector2 position,
Vector2 size,
}) : assert(_text != null),
_config = config ?? TextConfig(),
super(position: position, size: size) {
_updateBox();
}