Skip to content
This repository was archived by the owner on Apr 29, 2021. It is now read-only.

[Widget] Add Cupertino ActivityIndicator Widget #389

Merged
merged 1 commit into from
Nov 22, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
130 changes: 130 additions & 0 deletions Runtime/cupertino/activity_indicator.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,130 @@
using System;
using Unity.UIWidgets.animation;
using Unity.UIWidgets.foundation;
using Unity.UIWidgets.ui;
using Unity.UIWidgets.widgets;
using UnityEngine;
using Canvas = Unity.UIWidgets.ui.Canvas;
using Color = Unity.UIWidgets.ui.Color;

namespace Unity.UIWidgets.cupertino {
static class CupertinoActivityIndicatorUtils {
public const float _kDefaultIndicatorRadius = 10.0f;
public const float _kTwoPI = Mathf.PI * 2.0f;
public const int _kTickCount = 12;
public const int _kHalfTickCount = _kTickCount / 2;
public static readonly Color _kTickColor = CupertinoColors.lightBackgroundGray;
public static readonly Color _kActiveTickColor = new Color(0xFF9D9D9D);
}

public class CupertinoActivityIndicator : StatefulWidget {
public CupertinoActivityIndicator(
Key key = null,
bool animating = true,
float radius = CupertinoActivityIndicatorUtils._kDefaultIndicatorRadius
) : base(key: key) {
D.assert(radius > 0);
this.animating = animating;
this.radius = radius;
}

public readonly bool animating;
public readonly float radius;

public override State createState() {
return new _CupertinoActivityIndicatorState();
}
}

class _CupertinoActivityIndicatorState : TickerProviderStateMixin<CupertinoActivityIndicator> {
AnimationController _controller;

public override void initState() {
base.initState();
this._controller = new AnimationController(
duration: TimeSpan.FromSeconds(1),
vsync: this
);

if (this.widget.animating) {
this._controller.repeat();
}
}

public override void didUpdateWidget(StatefulWidget oldWidget) {
base.didUpdateWidget(oldWidget: oldWidget);
if (oldWidget is CupertinoActivityIndicator _oldWidget) {
if (this.widget.animating != _oldWidget.animating) {
if (this.widget.animating) {
this._controller.repeat();
}
else {
this._controller.stop();
}
}
}
}

public override void dispose() {
this._controller.dispose();
base.dispose();
}

public override Widget build(BuildContext context) {
return new SizedBox(
height: this.widget.radius * 2,
width: this.widget.radius * 2,
child: new CustomPaint(
painter: new _CupertinoActivityIndicatorPainter(
position: this._controller,
radius: this.widget.radius
)
)
);
}
}

class _CupertinoActivityIndicatorPainter : AbstractCustomPainter {
public _CupertinoActivityIndicatorPainter(
Animation<float> position,
float radius
) : base(repaint: position) {
this.tickFundamentalRRect = RRect.fromLTRBXY(
left: -radius,
top: 1.0f * radius / CupertinoActivityIndicatorUtils._kDefaultIndicatorRadius,
right: -radius / 2.0f,
bottom: -1.0f * radius / CupertinoActivityIndicatorUtils._kDefaultIndicatorRadius,
radiusX: 1.0f,
radiusY: 1.0f
);
this.position = position;
}

readonly Animation<float> position;
readonly RRect tickFundamentalRRect;

public override void paint(Canvas canvas, Size size) {
Paint paint = new Paint();

canvas.save();
canvas.translate(size.width / 2.0f, size.height / 2.0f);

int activeTick = (CupertinoActivityIndicatorUtils._kTickCount * this.position.value).floor();

for (int i = 0; i < CupertinoActivityIndicatorUtils._kTickCount; ++i) {
float t = (((i + activeTick) % CupertinoActivityIndicatorUtils._kTickCount) /
CupertinoActivityIndicatorUtils._kHalfTickCount).clamp(0, 1);
paint.color = Color.lerp(a: CupertinoActivityIndicatorUtils._kActiveTickColor,
b: CupertinoActivityIndicatorUtils._kTickColor, t: t);
canvas.drawRRect(rect: this.tickFundamentalRRect, paint: paint);
canvas.rotate(-CupertinoActivityIndicatorUtils._kTwoPI / CupertinoActivityIndicatorUtils._kTickCount);
}

canvas.restore();
}

public override bool shouldRepaint(CustomPainter oldPainter) {
return (oldPainter as _CupertinoActivityIndicatorPainter).position != this.position;
}
}
}
11 changes: 11 additions & 0 deletions Runtime/cupertino/activity_indicator.cs.meta

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 0 additions & 1 deletion Runtime/cupertino/button.cs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
using System;
using RSG;
using Unity.UIWidgets.animation;
using Unity.UIWidgets.foundation;
using Unity.UIWidgets.gestures;
Expand Down
2 changes: 2 additions & 0 deletions Runtime/cupertino/slider.cs
Original file line number Diff line number Diff line change
Expand Up @@ -174,6 +174,8 @@ public _RenderCupertinoSlider(
this._divisions = divisions;
this._activeColor = activeColor;
this._onChanged = onChanged;
this.onChangeStart = onChangeStart;
this.onChangeEnd = onChangeEnd;
this._drag = new HorizontalDragGestureRecognizer();
this._drag.onStart = this._handleDragStart;
this._drag.onUpdate = this._handleDragUpdate;
Expand Down