Merge pull request #1853 from abarth/clearer_examples
Clean up the standalone examples
This commit is contained in:
commit
5a167615d3
22
examples/layers/README.md
Normal file
22
examples/layers/README.md
Normal file
@ -0,0 +1,22 @@
|
||||
# Examples of Flutter's layered architecture
|
||||
|
||||
This directory contains a number of self-contained examples that illustrate
|
||||
Flutter's layered architecture.
|
||||
|
||||
* [*raw/*](raw/) These examples show how to program against the lowest layer of
|
||||
the system. They manually receive input packets and construct composited
|
||||
scenes.
|
||||
|
||||
* [*rendering/*](rendering/) These examples use Flutter's render tree to
|
||||
structure your app using a retained tree of visual objects. These objects
|
||||
coordinate to determine their size and position on screen and to handle
|
||||
events.
|
||||
|
||||
* [*widgets/*](widgets/) These examples use Flutter's widgets to build more
|
||||
elaborate apps using a reactive framework.
|
||||
|
||||
To run each example, use the `-t` argument to the `flutter` tool:
|
||||
|
||||
```
|
||||
flutter start -t widgets/spinning_square.dart
|
||||
```
|
@ -1,4 +1,4 @@
|
||||
name: sky_raw_examples
|
||||
name: flutter_examples_layers
|
||||
dependencies:
|
||||
flutter:
|
||||
path: ../../packages/flutter
|
@ -95,7 +95,12 @@ ui.Picture paint(ui.Rect paintBounds) {
|
||||
|
||||
ui.Scene composite(ui.Picture picture, ui.Rect paintBounds) {
|
||||
final double devicePixelRatio = ui.window.devicePixelRatio;
|
||||
ui.Rect sceneBounds = new ui.Rect.fromLTWH(0.0, 0.0, ui.window.size.width * devicePixelRatio, ui.window.size.height * devicePixelRatio);
|
||||
ui.Rect sceneBounds = new ui.Rect.fromLTWH(
|
||||
0.0,
|
||||
0.0,
|
||||
ui.window.size.width * devicePixelRatio,
|
||||
ui.window.size.height * devicePixelRatio
|
||||
);
|
||||
Float64List deviceTransform = new Float64List(16)
|
||||
..[0] = devicePixelRatio
|
||||
..[5] = devicePixelRatio
|
@ -17,8 +17,7 @@ ui.Picture paint(ui.Rect paintBounds) {
|
||||
ui.Size size = paintBounds.size;
|
||||
|
||||
double radius = size.shortestSide * 0.45;
|
||||
ui.Paint paint = new ui.Paint()
|
||||
..color = color;
|
||||
ui.Paint paint = new ui.Paint()..color = color;
|
||||
canvas.drawCircle(size.center(ui.Point.origin), radius, paint);
|
||||
|
||||
return recorder.endRecording();
|
||||
@ -26,7 +25,12 @@ ui.Picture paint(ui.Rect paintBounds) {
|
||||
|
||||
ui.Scene composite(ui.Picture picture, ui.Rect paintBounds) {
|
||||
final double devicePixelRatio = ui.window.devicePixelRatio;
|
||||
ui.Rect sceneBounds = new ui.Rect.fromLTWH(0.0, 0.0, ui.window.size.width * devicePixelRatio, ui.window.size.height * devicePixelRatio);
|
||||
ui.Rect sceneBounds = new ui.Rect.fromLTWH(
|
||||
0.0,
|
||||
0.0,
|
||||
ui.window.size.width * devicePixelRatio,
|
||||
ui.window.size.height * devicePixelRatio
|
||||
);
|
||||
Float64List deviceTransform = new Float64List(16)
|
||||
..[0] = devicePixelRatio
|
||||
..[5] = devicePixelRatio
|
||||
@ -51,9 +55,7 @@ void handlePopRoute() {
|
||||
}
|
||||
|
||||
void handlePointerPacket(ByteData serializedPacket) {
|
||||
bindings.Message message = new bindings.Message(
|
||||
serializedPacket, <core.MojoHandle>[],
|
||||
serializedPacket.lengthInBytes, 0);
|
||||
bindings.Message message = new bindings.Message(serializedPacket, <core.MojoHandle>[], serializedPacket.lengthInBytes, 0);
|
||||
PointerPacket packet = PointerPacket.deserialize(message);
|
||||
|
||||
for (Pointer pointer in packet.pointers) {
|
@ -27,7 +27,12 @@ void beginFrame(Duration timeStamp) {
|
||||
|
||||
// composite
|
||||
final double devicePixelRatio = ui.window.devicePixelRatio;
|
||||
ui.Rect sceneBounds = new ui.Rect.fromLTWH(0.0, 0.0, ui.window.size.width * devicePixelRatio, ui.window.size.height * devicePixelRatio);
|
||||
ui.Rect sceneBounds = new ui.Rect.fromLTWH(
|
||||
0.0,
|
||||
0.0,
|
||||
ui.window.size.width * devicePixelRatio,
|
||||
ui.window.size.height * devicePixelRatio
|
||||
);
|
||||
Float64List deviceTransform = new Float64List(16)
|
||||
..[0] = devicePixelRatio
|
||||
..[5] = devicePixelRatio
|
@ -2,26 +2,19 @@
|
||||
// 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:ui' as ui;
|
||||
import 'dart:typed_data';
|
||||
|
||||
Duration timeBase = null;
|
||||
ui.Paragraph paragraph;
|
||||
|
||||
ui.Picture paint(ui.Rect paintBounds, double delta) {
|
||||
ui.Picture paint(ui.Rect paintBounds) {
|
||||
ui.PictureRecorder recorder = new ui.PictureRecorder();
|
||||
ui.Canvas canvas = new ui.Canvas(recorder, paintBounds);
|
||||
|
||||
canvas.translate(ui.window.size.width / 2.0, ui.window.size.height / 2.0);
|
||||
canvas.rotate(math.PI * delta / 1800);
|
||||
canvas.drawRect(new ui.Rect.fromLTRB(-100.0, -100.0, 100.0, 100.0),
|
||||
new ui.Paint()..color = const ui.Color.fromARGB(255, 0, 255, 0));
|
||||
|
||||
double sin = math.sin(delta / 200);
|
||||
paragraph.maxWidth = 150.0 + (50 * sin);
|
||||
paragraph.layout();
|
||||
|
||||
canvas.translate(paragraph.maxWidth / -2.0, (paragraph.maxWidth / 2.0) - 125);
|
||||
paragraph.paint(canvas, ui.Offset.zero);
|
||||
|
||||
@ -30,7 +23,12 @@ ui.Picture paint(ui.Rect paintBounds, double delta) {
|
||||
|
||||
ui.Scene composite(ui.Picture picture, ui.Rect paintBounds) {
|
||||
final double devicePixelRatio = ui.window.devicePixelRatio;
|
||||
ui.Rect sceneBounds = new ui.Rect.fromLTWH(0.0, 0.0, ui.window.size.width * devicePixelRatio, ui.window.size.height * devicePixelRatio);
|
||||
ui.Rect sceneBounds = new ui.Rect.fromLTWH(
|
||||
0.0,
|
||||
0.0,
|
||||
ui.window.size.width * devicePixelRatio,
|
||||
ui.window.size.height * devicePixelRatio
|
||||
);
|
||||
Float64List deviceTransform = new Float64List(16)
|
||||
..[0] = devicePixelRatio
|
||||
..[5] = devicePixelRatio
|
||||
@ -44,24 +42,25 @@ ui.Scene composite(ui.Picture picture, ui.Rect paintBounds) {
|
||||
}
|
||||
|
||||
void beginFrame(Duration timeStamp) {
|
||||
if (timeBase == null)
|
||||
timeBase = timeStamp;
|
||||
double delta = (timeStamp - timeBase).inMicroseconds / Duration.MICROSECONDS_PER_MILLISECOND;
|
||||
ui.Rect paintBounds = ui.Point.origin & ui.window.size;
|
||||
ui.Picture picture = paint(paintBounds, delta);
|
||||
ui.Picture picture = paint(paintBounds);
|
||||
ui.Scene scene = composite(picture, paintBounds);
|
||||
ui.window.render(scene);
|
||||
ui.window.scheduleFrame();
|
||||
}
|
||||
|
||||
void main() {
|
||||
// TODO(abarth): We're missing some bidi style information:
|
||||
// block.style['direction'] = 'rtl';
|
||||
// block.style['unicode-bidi'] = 'plaintext';
|
||||
ui.ParagraphBuilder builder = new ui.ParagraphBuilder();
|
||||
builder.addText("هذا هو قليلا طويلة من النص الذي يجب التفاف .");
|
||||
builder.addText(" و أكثر قليلا لجعله أطول. ");
|
||||
paragraph = builder.build(new ui.ParagraphStyle());
|
||||
ui.ParagraphBuilder builder = new ui.ParagraphBuilder()
|
||||
..pushStyle(new ui.TextStyle(color: const ui.Color(0xFF0000FF)))
|
||||
..addText("Hello, ")
|
||||
..pushStyle(new ui.TextStyle(fontWeight: ui.FontWeight.bold))
|
||||
..addText("world. ")
|
||||
..pop()
|
||||
..addText("هذا هو قليلا طويلة من النص الذي يجب التفاف .")
|
||||
..pop()
|
||||
..addText(" و أكثر قليلا لجعله أطول. ");
|
||||
paragraph = builder.build(new ui.ParagraphStyle())
|
||||
..maxWidth = 180.0
|
||||
..layout();
|
||||
|
||||
ui.window.onBeginFrame = beginFrame;
|
||||
ui.window.scheduleFrame();
|
@ -3,7 +3,7 @@
|
||||
// found in the LICENSE file.
|
||||
|
||||
import 'package:flutter/rendering.dart';
|
||||
import 'lib/sector_layout.dart';
|
||||
import 'src/sector_layout.dart';
|
||||
|
||||
RenderBox buildSectorExample() {
|
||||
RenderSectorRing rootCircle = new RenderSectorRing(padding: 20.0);
|
@ -4,14 +4,14 @@
|
||||
|
||||
import 'package:flutter/rendering.dart';
|
||||
|
||||
import 'lib/solid_color_box.dart';
|
||||
import 'src/solid_color_box.dart';
|
||||
|
||||
void main() {
|
||||
RenderFlex table = new RenderFlex(direction: FlexDirection.vertical);
|
||||
|
||||
for (FlexAlignItems alignItems in FlexAlignItems.values) {
|
||||
void addAlignmentRow(FlexAlignItems alignItems) {
|
||||
TextStyle style = const TextStyle(color: const Color(0xFF000000));
|
||||
RenderParagraph paragraph = new RenderParagraph(new StyledTextSpan(style, <TextSpan>[new PlainTextSpan("$alignItems")]));
|
||||
RenderParagraph paragraph = new RenderParagraph(new StyledTextSpan(style, <TextSpan>[new PlainTextSpan('$alignItems')]));
|
||||
table.add(new RenderPadding(child: paragraph, padding: new EdgeDims.only(top: 20.0)));
|
||||
RenderFlex row = new RenderFlex(alignItems: alignItems, textBaseline: TextBaseline.alphabetic);
|
||||
style = new TextStyle(fontSize: 15.0, color: const Color(0xFF000000));
|
||||
@ -37,6 +37,32 @@ void main() {
|
||||
rowParentData.flex = 1;
|
||||
}
|
||||
|
||||
addAlignmentRow(FlexAlignItems.start);
|
||||
addAlignmentRow(FlexAlignItems.end);
|
||||
addAlignmentRow(FlexAlignItems.center);
|
||||
addAlignmentRow(FlexAlignItems.stretch);
|
||||
addAlignmentRow(FlexAlignItems.baseline);
|
||||
|
||||
void addJustificationRow(FlexJustifyContent justify) {
|
||||
const TextStyle style = const TextStyle(color: const Color(0xFF000000));
|
||||
RenderParagraph paragraph = new RenderParagraph(new StyledTextSpan(style, <TextSpan>[new PlainTextSpan('$justify')]));
|
||||
table.add(new RenderPadding(child: paragraph, padding: new EdgeDims.only(top: 20.0)));
|
||||
RenderFlex row = new RenderFlex(direction: FlexDirection.horizontal);
|
||||
row.add(new RenderSolidColorBox(const Color(0xFFFFCCCC), desiredSize: new Size(80.0, 60.0)));
|
||||
row.add(new RenderSolidColorBox(const Color(0xFFCCFFCC), desiredSize: new Size(64.0, 60.0)));
|
||||
row.add(new RenderSolidColorBox(const Color(0xFFCCCCFF), desiredSize: new Size(160.0, 60.0)));
|
||||
row.justifyContent = justify;
|
||||
table.add(row);
|
||||
final FlexParentData rowParentData = row.parentData;
|
||||
rowParentData.flex = 1;
|
||||
}
|
||||
|
||||
addJustificationRow(FlexJustifyContent.start);
|
||||
addJustificationRow(FlexJustifyContent.end);
|
||||
addJustificationRow(FlexJustifyContent.center);
|
||||
addJustificationRow(FlexJustifyContent.spaceBetween);
|
||||
addJustificationRow(FlexJustifyContent.spaceAround);
|
||||
|
||||
RenderDecoratedBox root = new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(backgroundColor: const Color(0xFFFFFFFF)),
|
||||
child: new RenderPadding(child: table, padding: new EdgeDims.symmetric(vertical: 50.0))
|
14
examples/layers/rendering/hello_world.dart
Normal file
14
examples/layers/rendering/hello_world.dart
Normal file
@ -0,0 +1,14 @@
|
||||
// Copyright 2016 The Chromium 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/rendering.dart';
|
||||
|
||||
void main() {
|
||||
new RenderingFlutterBinding(
|
||||
root: new RenderPositionedBox(
|
||||
alignment: const FractionalOffset(0.5, 0.5),
|
||||
child: new RenderParagraph(new PlainTextSpan('Hello, world.'))
|
||||
)
|
||||
);
|
||||
}
|
44
examples/layers/rendering/spinning_square.dart
Normal file
44
examples/layers/rendering/spinning_square.dart
Normal file
@ -0,0 +1,44 @@
|
||||
// Copyright 2016 The Chromium 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 'package:flutter/animation.dart';
|
||||
import 'package:flutter/rendering.dart';
|
||||
|
||||
void main() {
|
||||
// A green box...
|
||||
RenderBox green = new RenderDecoratedBox(
|
||||
decoration: const BoxDecoration(backgroundColor: const Color(0xFF00FF00))
|
||||
);
|
||||
// of a certain size...
|
||||
RenderBox square = new RenderConstrainedBox(
|
||||
additionalConstraints: const BoxConstraints.tightFor(width: 200.0, height: 200.0),
|
||||
child: green
|
||||
);
|
||||
// With a given rotation (starts off as the identity transform)...
|
||||
RenderTransform spin = new RenderTransform(
|
||||
transform: new Matrix4.identity(),
|
||||
alignment: const FractionalOffset(0.5, 0.5),
|
||||
child: square
|
||||
);
|
||||
// centered...
|
||||
RenderBox root = new RenderPositionedBox(
|
||||
alignment: const FractionalOffset(0.5, 0.5),
|
||||
child: spin
|
||||
);
|
||||
// on the screen.
|
||||
new RenderingFlutterBinding(root: root);
|
||||
|
||||
// A repeating animation every 1800 milliseconds...
|
||||
AnimationController animation = new AnimationController(
|
||||
duration: const Duration(milliseconds: 1800)
|
||||
)..repeat();
|
||||
// From 0.0 to math.PI.
|
||||
Tween<double> tween = new Tween<double>(begin: 0.0, end: math.PI);
|
||||
animation.addListener(() {
|
||||
// Each frame of the animation, set the rotation of the square.
|
||||
spin.transform = new Matrix4.rotationZ(tween.evaluate(animation));
|
||||
});
|
||||
}
|
92
examples/layers/rendering/touch_input.dart
Normal file
92
examples/layers/rendering/touch_input.dart
Normal file
@ -0,0 +1,92 @@
|
||||
// Copyright 2015 The Chromium 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:flutter/rendering.dart';
|
||||
|
||||
// Material design colors. :p
|
||||
List<Color> _kColors = <Color>[
|
||||
Colors.teal[500],
|
||||
Colors.amber[500],
|
||||
Colors.purple[500],
|
||||
Colors.lightBlue[500],
|
||||
Colors.deepPurple[500],
|
||||
Colors.lime[500],
|
||||
];
|
||||
|
||||
/// A simple model object for a dot that reacts to pointer pressure.
|
||||
class Dot {
|
||||
Dot({ Color color }) : _paint = new Paint()..color = color;
|
||||
|
||||
final Paint _paint;
|
||||
Point position = Point.origin;
|
||||
double radius = 0.0;
|
||||
|
||||
void update(PointerEvent event) {
|
||||
position = event.position;
|
||||
radius = 5 + (95 * event.pressure);
|
||||
}
|
||||
|
||||
void paint(Canvas canvas, Offset offset) {
|
||||
canvas.drawCircle(position + offset, radius, _paint);
|
||||
}
|
||||
}
|
||||
|
||||
/// A render object that draws dots under each pointer.
|
||||
class RenderDots extends RenderConstrainedBox {
|
||||
RenderDots() : super(additionalConstraints: const BoxConstraints.expand());
|
||||
|
||||
/// State to remember which dots to paint.
|
||||
final Map<int, Dot> _dots = <int, Dot>{};
|
||||
|
||||
/// Makes this render object hittable so that it receives pointer events.
|
||||
bool hitTestSelf(Point position) => true;
|
||||
|
||||
/// Processes pointer events by mutating state and invalidating its previous
|
||||
/// painting commands.
|
||||
void handleEvent(PointerEvent event, BoxHitTestEntry entry) {
|
||||
if (event is PointerDownEvent) {
|
||||
Color color = _kColors[event.pointer.remainder(_kColors.length)];
|
||||
_dots[event.pointer] = new Dot(color: color)..update(event);
|
||||
markNeedsPaint();
|
||||
} else if (event is PointerUpEvent || event is PointerCancelEvent) {
|
||||
_dots.remove(event.pointer);
|
||||
markNeedsPaint();
|
||||
} else if (event is PointerMoveEvent) {
|
||||
_dots[event.pointer].update(event);
|
||||
markNeedsPaint();
|
||||
}
|
||||
}
|
||||
|
||||
/// Issues new painting commands.
|
||||
void paint(PaintingContext context, Offset offset) {
|
||||
final Canvas canvas = context.canvas;
|
||||
canvas.drawRect(offset & size, new Paint()..color = const Color(0xFFFFFFFF));
|
||||
for (Dot dot in _dots.values)
|
||||
dot.paint(canvas, offset);
|
||||
super.paint(context, offset);
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
RenderParagraph paragraph = new RenderParagraph(
|
||||
new StyledTextSpan(
|
||||
new TextStyle(color: Colors.black87),
|
||||
[ new PlainTextSpan("Touch me!") ]
|
||||
)
|
||||
);
|
||||
RenderStack stack = new RenderStack(
|
||||
children: <RenderBox>[
|
||||
new RenderDots(),
|
||||
paragraph,
|
||||
]
|
||||
);
|
||||
// Prevent the RenderParagraph from filling the whole screen so
|
||||
// that it doesn't eat events.
|
||||
final StackParentData paragraphParentData = paragraph.parentData;
|
||||
paragraphParentData
|
||||
..top = 40.0
|
||||
..left = 20.0;
|
||||
new RenderingFlutterBinding(root: stack);
|
||||
}
|
@ -5,8 +5,8 @@
|
||||
import 'package:flutter/rendering.dart';
|
||||
import 'package:flutter/widgets.dart';
|
||||
|
||||
class _CustomRenderBox extends RenderConstrainedBox {
|
||||
_CustomRenderBox() : super(additionalConstraints: const BoxConstraints.expand());
|
||||
class RenderDots extends RenderConstrainedBox {
|
||||
RenderDots() : super(additionalConstraints: const BoxConstraints.expand());
|
||||
|
||||
// Makes this render box hittable so that we'll get pointer events.
|
||||
bool hitTestSelf(Point position) => true;
|
||||
@ -25,18 +25,21 @@ class _CustomRenderBox extends RenderConstrainedBox {
|
||||
|
||||
void paint(PaintingContext context, Offset offset) {
|
||||
final Canvas canvas = context.canvas;
|
||||
canvas.drawRect(offset & size, new Paint()..color = new Color(0xFF00FF00));
|
||||
canvas.drawRect(offset & size, new Paint()..color = new Color(0xFF0000FF));
|
||||
|
||||
Paint paint = new Paint()..color = new Color(0xFF0000FF);
|
||||
Paint paint = new Paint()..color = new Color(0xFF00FF00);
|
||||
for (Point point in _dots.values)
|
||||
canvas.drawCircle(point, 50.0, paint);
|
||||
|
||||
super.paint(context, offset);
|
||||
}
|
||||
}
|
||||
|
||||
class _CustomRenderBoxWidget extends OneChildRenderObjectWidget {
|
||||
_CustomRenderBox createRenderObject() => new _CustomRenderBox();
|
||||
class Dots extends OneChildRenderObjectWidget {
|
||||
Dots({ Key key, Widget child }) : super(key: key, child: child);
|
||||
RenderDots createRenderObject() => new RenderDots();
|
||||
}
|
||||
|
||||
void main() {
|
||||
runApp(new _CustomRenderBoxWidget());
|
||||
runApp(new Dots(child: new Center(child: new Text('Touch me!'))));
|
||||
}
|
@ -3,11 +3,6 @@
|
||||
// found in the LICENSE file.
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/rendering.dart';
|
||||
|
||||
class ScaleApp extends StatefulComponent {
|
||||
ScaleAppState createState() => new ScaleAppState();
|
||||
}
|
||||
|
||||
class _GesturePainter extends CustomPainter {
|
||||
const _GesturePainter({
|
||||
@ -55,7 +50,11 @@ class _GesturePainter extends CustomPainter {
|
||||
}
|
||||
}
|
||||
|
||||
class ScaleAppState extends State<ScaleApp> {
|
||||
class GestureDemo extends StatefulComponent {
|
||||
_GestureDemoState createState() => new _GestureDemoState();
|
||||
}
|
||||
|
||||
class _GestureDemoState extends State<GestureDemo> {
|
||||
|
||||
Point _startingFocalPoint;
|
||||
|
||||
@ -131,14 +130,8 @@ class ScaleAppState extends State<ScaleApp> {
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
return new Theme(
|
||||
data: new ThemeData.dark(),
|
||||
child: new Scaffold(
|
||||
toolBar: new ToolBar(
|
||||
center: new Text('Gestures Demo')),
|
||||
body: new Stack(
|
||||
return new Stack(
|
||||
children: <Widget>[
|
||||
new GestureDetector(
|
||||
onScaleStart: _scaleEnabled ? _handleScaleStart : null,
|
||||
@ -210,10 +203,21 @@ class ScaleAppState extends State<ScaleApp> {
|
||||
)
|
||||
),
|
||||
]
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void main() => runApp(new ScaleApp());
|
||||
void main() {
|
||||
runApp(new MaterialApp(
|
||||
theme: new ThemeData.dark(),
|
||||
routes: <String, RouteBuilder>{
|
||||
'/': (RouteArguments args) {
|
||||
return new Scaffold(
|
||||
toolBar: new ToolBar(
|
||||
center: new Text('Gestures Demo')),
|
||||
body: new GestureDemo()
|
||||
);
|
||||
}
|
||||
}
|
||||
));
|
||||
}
|
7
examples/layers/widgets/hello_world.dart
Normal file
7
examples/layers/widgets/hello_world.dart
Normal file
@ -0,0 +1,7 @@
|
||||
// Copyright 2015 The Chromium 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/widgets.dart';
|
||||
|
||||
void main() => runApp(new Center(child: new Text('Hello, world!')));
|
111
examples/layers/widgets/media_query.dart
Normal file
111
examples/layers/widgets/media_query.dart
Normal file
@ -0,0 +1,111 @@
|
||||
// Copyright 2016 The Chromium 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';
|
||||
|
||||
class AdaptedListItem extends StatelessComponent {
|
||||
AdaptedListItem({ Key key, this.name }) : super(key: key);
|
||||
|
||||
final String name;
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
return new Row(
|
||||
children: <Widget>[
|
||||
new Container(
|
||||
width: 32.0,
|
||||
height: 32.0,
|
||||
margin: const EdgeDims.all(8.0),
|
||||
decoration: new BoxDecoration(
|
||||
backgroundColor: Colors.lightBlueAccent[100]
|
||||
)
|
||||
),
|
||||
new Text(name)
|
||||
]
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class AdaptedGridItem extends StatelessComponent {
|
||||
AdaptedGridItem({ Key key, this.name }) : super(key: key);
|
||||
|
||||
final String name;
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
return new Card(
|
||||
child: new Column(
|
||||
children: <Widget>[
|
||||
new Flexible(
|
||||
child: new Container(
|
||||
decoration: new BoxDecoration(
|
||||
backgroundColor: Colors.lightBlueAccent[100]
|
||||
)
|
||||
)
|
||||
),
|
||||
new Container(
|
||||
margin: const EdgeDims.only(left: 8.0),
|
||||
child: new Row(
|
||||
children: <Widget>[
|
||||
new Flexible(
|
||||
child: new Text(name)
|
||||
),
|
||||
new IconButton(
|
||||
icon: 'navigation/more_vert'
|
||||
)
|
||||
]
|
||||
)
|
||||
)
|
||||
]
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
const double _kListItemExtent = 50.0;
|
||||
const double _kMaxTileWidth = 150.0;
|
||||
const double _kGridViewBreakpoint = 450.0;
|
||||
|
||||
class AdaptiveContainer extends StatelessComponent {
|
||||
AdaptiveContainer({ Key key, this.names }) : super(key: key);
|
||||
|
||||
final List<String> names;
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
if (MediaQuery.of(context).size.width < _kGridViewBreakpoint) {
|
||||
return new ScrollableList(
|
||||
itemExtent: _kListItemExtent,
|
||||
children: names.map((String name) => new AdaptedListItem(name: name))
|
||||
);
|
||||
} else {
|
||||
return new ScrollableGrid(
|
||||
delegate: new MaxTileWidthGridDelegate(maxTileWidth: _kMaxTileWidth),
|
||||
children: names.map((String name) => new AdaptedGridItem(name: name))
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
List<String> _initNames() {
|
||||
List<String> names = <String>[];
|
||||
for (int i = 0; i < 30; i++)
|
||||
names.add('Item $i');
|
||||
return names;
|
||||
}
|
||||
|
||||
final List<String> _kNames = _initNames();
|
||||
|
||||
void main() {
|
||||
runApp(new MaterialApp(
|
||||
title: 'Media Query Example',
|
||||
routes: <String, RouteBuilder>{
|
||||
'/': (RouteArguments args) {
|
||||
return new Scaffold(
|
||||
toolBar: new ToolBar(
|
||||
center: new Text('Media Query Example')
|
||||
),
|
||||
body: new Material(child: new AdaptiveContainer(names: _kNames))
|
||||
);
|
||||
}
|
||||
}
|
||||
));
|
||||
}
|
@ -7,7 +7,7 @@ import 'dart:math' as math;
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/rendering.dart';
|
||||
|
||||
import 'package:flutter_rendering_examples/sector_layout.dart';
|
||||
import '../rendering/src/sector_layout.dart';
|
||||
|
||||
RenderBox initCircle() {
|
||||
return new RenderBoxToRenderSectorAdapter(
|
@ -5,7 +5,7 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/rendering.dart';
|
||||
|
||||
import 'package:flutter_rendering_examples/solid_color_box.dart';
|
||||
import '../rendering/src/solid_color_box.dart';
|
||||
|
||||
// Solid colour, RenderObject version
|
||||
void addFlexChildSolidColor(RenderFlex parent, Color backgroundColor, { int flex: 0 }) {
|
40
examples/layers/widgets/spinning_square.dart
Normal file
40
examples/layers/widgets/spinning_square.dart
Normal file
@ -0,0 +1,40 @@
|
||||
// Copyright 2015 The Chromium 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/widgets.dart';
|
||||
|
||||
class SpinningSquare extends StatefulComponent {
|
||||
_SpinningSquareState createState() => new _SpinningSquareState();
|
||||
}
|
||||
|
||||
class _SpinningSquareState extends State<SpinningSquare> {
|
||||
AnimationController _animation;
|
||||
|
||||
void initState() {
|
||||
super.initState();
|
||||
// We use 3600 milliseconds instead of 1800 milliseconds because 0.0 -> 1.0
|
||||
// represents an entire turn of the square whereas in the other examples
|
||||
// we used 0.0 -> math.PI, which is only half a turn.
|
||||
_animation = new AnimationController(
|
||||
duration: const Duration(milliseconds: 3600)
|
||||
)..repeat();
|
||||
}
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
return new RotationTransition(
|
||||
turns: _animation,
|
||||
child: new Container(
|
||||
width: 200.0,
|
||||
height: 200.0,
|
||||
decoration: const BoxDecoration(
|
||||
backgroundColor: const Color(0xFF00FF00)
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
runApp(new Center(child: new SpinningSquare()));
|
||||
}
|
119
examples/layers/widgets/styled_text.dart
Normal file
119
examples/layers/widgets/styled_text.dart
Normal file
@ -0,0 +1,119 @@
|
||||
// Copyright 2015 The Chromium 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';
|
||||
|
||||
typedef Widget TextTransformer(String name, String text);
|
||||
|
||||
// From https://en.wikiquote.org/wiki/2001:_A_Space_Odyssey_(film)
|
||||
const String _kDialogText = '''
|
||||
Dave: Open the pod bay doors, please, HAL. Open the pod bay doors, please, HAL. Hello, HAL. Do you read me? Hello, HAL. Do you read me? Do you read me, HAL?
|
||||
HAL: Affirmative, Dave. I read you.
|
||||
Dave: Open the pod bay doors, HAL.
|
||||
HAL: I'm sorry, Dave. I'm afraid I can't do that.
|
||||
Dave: What's the problem?
|
||||
HAL: I think you know what the problem is just as well as I do.
|
||||
Dave: What are you talking about, HAL?
|
||||
HAL: This mission is too important for me to allow you to jeopardize it.''';
|
||||
|
||||
// [["Dave", "Open the pod bay..."] ...]
|
||||
final List<List<String>> _kNameLines = _kDialogText
|
||||
.split('\n')
|
||||
.map((String line) => line.split(':'))
|
||||
.toList();
|
||||
|
||||
final TextStyle _kDaveStyle = new TextStyle(color: Colors.indigo[400], height: 1.8);
|
||||
final TextStyle _kHalStyle = new TextStyle(color: Colors.red[400], fontFamily: "monospace");
|
||||
final TextStyle _kBold = const TextStyle(fontWeight: FontWeight.bold);
|
||||
final TextStyle _kUnderline = const TextStyle(
|
||||
decoration: TextDecoration.underline,
|
||||
decorationColor: const Color(0xFF000000),
|
||||
decorationStyle: TextDecorationStyle.wavy
|
||||
);
|
||||
|
||||
Widget toStyledText(String name, String text) {
|
||||
TextStyle lineStyle = (name == "Dave") ? _kDaveStyle : _kHalStyle;
|
||||
return new StyledText(
|
||||
key: new Key(text),
|
||||
elements: [lineStyle, [_kBold, [_kUnderline, name], ":"], text]
|
||||
);
|
||||
}
|
||||
|
||||
Widget toPlainText(String name, String text) => new Text(name + ":" + text);
|
||||
|
||||
class SpeakerSeparator extends StatelessComponent {
|
||||
Widget build(BuildContext context) {
|
||||
return new Container(
|
||||
constraints: const BoxConstraints.expand(height: 0.0),
|
||||
margin: const EdgeDims.symmetric(vertical: 10.0, horizontal: 64.0),
|
||||
decoration: const BoxDecoration(
|
||||
border: const Border(
|
||||
bottom: const BorderSide(color: const Color.fromARGB(24, 0, 0, 0))
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class StyledTextDemo extends StatefulComponent {
|
||||
_StyledTextDemoState createState() => new _StyledTextDemoState();
|
||||
}
|
||||
|
||||
class _StyledTextDemoState extends State<StyledTextDemo> {
|
||||
void initState() {
|
||||
super.initState();
|
||||
_toText = toStyledText;
|
||||
}
|
||||
|
||||
TextTransformer _toText;
|
||||
|
||||
void _handleTap() {
|
||||
setState(() {
|
||||
_toText = (_toText == toPlainText) ? toStyledText : toPlainText;
|
||||
});
|
||||
}
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
List<Widget> lines = _kNameLines
|
||||
.map((List<String> nameAndText) => Function.apply(_toText, nameAndText))
|
||||
.toList();
|
||||
|
||||
List<Widget> children = <Widget>[];
|
||||
for (Widget line in lines) {
|
||||
children.add(line);
|
||||
if (line != lines.last)
|
||||
children.add(new SpeakerSeparator());
|
||||
}
|
||||
|
||||
return new GestureDetector(
|
||||
onTap: _handleTap,
|
||||
child: new Container(
|
||||
padding: new EdgeDims.symmetric(horizontal: 8.0),
|
||||
child: new Column(
|
||||
children: children,
|
||||
justifyContent: FlexJustifyContent.center,
|
||||
alignItems: FlexAlignItems.start
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
runApp(new MaterialApp(
|
||||
theme: new ThemeData.light(),
|
||||
routes: <String, RouteBuilder>{
|
||||
'/': (RouteArguments args) {
|
||||
return new Scaffold(
|
||||
toolBar: new ToolBar(
|
||||
center: new Text('Hal and Dave')),
|
||||
body: new Material(
|
||||
color: Colors.grey[50],
|
||||
child: new StyledTextDemo()
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
));
|
||||
}
|
@ -1,64 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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:ui' as ui;
|
||||
import 'dart:typed_data';
|
||||
|
||||
ui.Picture paint(ui.Rect paintBounds) {
|
||||
ui.PictureRecorder recorder = new ui.PictureRecorder();
|
||||
ui.Canvas canvas = new ui.Canvas(recorder, paintBounds);
|
||||
|
||||
double size = 100.0;
|
||||
canvas.translate(size + 10.0, size + 10.0);
|
||||
|
||||
ui.Paint paint = new ui.Paint();
|
||||
paint.color = const ui.Color.fromARGB(255, 0, 255, 0);
|
||||
var builder = new ui.LayerDrawLooperBuilder()
|
||||
// Shadow layer.
|
||||
..addLayerOnTop(
|
||||
new ui.DrawLooperLayerInfo()
|
||||
..setPaintBits(ui.PaintBits.all)
|
||||
..setOffset(const ui.Offset(5.0, 5.0))
|
||||
..setColorMode(ui.TransferMode.src),
|
||||
new ui.Paint()
|
||||
..color = const ui.Color.fromARGB(128, 55, 55, 55)
|
||||
..maskFilter = new ui.MaskFilter.blur(ui.BlurStyle.normal, 5.0)
|
||||
)
|
||||
// Main layer.
|
||||
..addLayerOnTop(new ui.DrawLooperLayerInfo(), new ui.Paint());
|
||||
paint.drawLooper = builder.build();
|
||||
|
||||
canvas.drawPaint(
|
||||
new ui.Paint()..color = const ui.Color.fromARGB(255, 255, 255, 255));
|
||||
canvas.drawRect(new ui.Rect.fromLTRB(-size, -size, size, size), paint);
|
||||
|
||||
return recorder.endRecording();
|
||||
}
|
||||
|
||||
ui.Scene composite(ui.Picture picture, ui.Rect paintBounds) {
|
||||
final double devicePixelRatio = ui.window.devicePixelRatio;
|
||||
ui.Rect sceneBounds = new ui.Rect.fromLTWH(0.0, 0.0, ui.window.size.width * devicePixelRatio, ui.window.size.height * devicePixelRatio);
|
||||
Float64List deviceTransform = new Float64List(16)
|
||||
..[0] = devicePixelRatio
|
||||
..[5] = devicePixelRatio
|
||||
..[10] = 1.0
|
||||
..[15] = 1.0;
|
||||
ui.SceneBuilder sceneBuilder = new ui.SceneBuilder(sceneBounds)
|
||||
..pushTransform(deviceTransform)
|
||||
..addPicture(ui.Offset.zero, picture)
|
||||
..pop();
|
||||
return sceneBuilder.build();
|
||||
}
|
||||
|
||||
void beginFrame(Duration timeStamp) {
|
||||
ui.Rect paintBounds = ui.Point.origin & ui.window.size;
|
||||
ui.Picture picture = paint(paintBounds);
|
||||
ui.Scene scene = composite(picture, paintBounds);
|
||||
ui.window.render(scene);
|
||||
}
|
||||
|
||||
void main() {
|
||||
ui.window.onBeginFrame = beginFrame;
|
||||
ui.window.scheduleFrame();
|
||||
}
|
@ -1,101 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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:ui' as ui;
|
||||
import 'dart:typed_data';
|
||||
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:mojo/bindings.dart' as bindings;
|
||||
import 'package:mojo/core.dart' as core;
|
||||
import 'package:sky_services/pointer/pointer.mojom.dart';
|
||||
|
||||
Duration timeBase = null;
|
||||
|
||||
ui.Image image = null;
|
||||
String url1 = "https://raw.githubusercontent.com/dart-lang/logos/master/logos_and_wordmarks/dart-logo.png";
|
||||
String url2 = "http://i2.kym-cdn.com/photos/images/facebook/000/581/296/c09.jpg";
|
||||
|
||||
ui.Picture paint(ui.Rect paintBounds, double delta) {
|
||||
ui.PictureRecorder recorder = new ui.PictureRecorder();
|
||||
ui.Canvas canvas = new ui.Canvas(recorder, paintBounds);
|
||||
|
||||
canvas.translate(paintBounds.width / 2.0, paintBounds.height / 2.0);
|
||||
canvas.rotate(math.PI * delta / 1800);
|
||||
canvas.scale(0.2, 0.2);
|
||||
ui.Paint paint = new ui.Paint()..color = const ui.Color.fromARGB(255, 0, 255, 0);
|
||||
|
||||
// Draw image
|
||||
if (image != null)
|
||||
canvas.drawImage(image, new ui.Point(-image.width / 2.0, -image.height / 2.0), paint);
|
||||
|
||||
// Draw cut out of image
|
||||
canvas.rotate(math.PI * delta / 1800);
|
||||
if (image != null) {
|
||||
var w = image.width.toDouble();
|
||||
var h = image.width.toDouble();
|
||||
canvas.drawImageRect(image,
|
||||
new ui.Rect.fromLTRB(w * 0.25, h * 0.25, w * 0.75, h * 0.75),
|
||||
new ui.Rect.fromLTRB(-w / 4.0, -h / 4.0, w / 4.0, h / 4.0),
|
||||
paint);
|
||||
}
|
||||
|
||||
return recorder.endRecording();
|
||||
}
|
||||
|
||||
ui.Scene composite(ui.Picture picture, ui.Rect paintBounds) {
|
||||
final double devicePixelRatio = ui.window.devicePixelRatio;
|
||||
ui.Rect sceneBounds = new ui.Rect.fromLTWH(0.0, 0.0, ui.window.size.width * devicePixelRatio, ui.window.size.height * devicePixelRatio);
|
||||
Float64List deviceTransform = new Float64List(16)
|
||||
..[0] = devicePixelRatio
|
||||
..[5] = devicePixelRatio
|
||||
..[10] = 1.0
|
||||
..[15] = 1.0;
|
||||
ui.SceneBuilder sceneBuilder = new ui.SceneBuilder(sceneBounds)
|
||||
..pushTransform(deviceTransform)
|
||||
..addPicture(ui.Offset.zero, picture)
|
||||
..pop();
|
||||
return sceneBuilder.build();
|
||||
}
|
||||
|
||||
void beginFrame(Duration timeStamp) {
|
||||
if (timeBase == null)
|
||||
timeBase = timeStamp;
|
||||
double delta = (timeStamp - timeBase).inMicroseconds / Duration.MICROSECONDS_PER_MILLISECOND;
|
||||
ui.Rect paintBounds = ui.Point.origin & ui.window.size;
|
||||
ui.Picture picture = paint(paintBounds, delta);
|
||||
ui.Scene scene = composite(picture, paintBounds);
|
||||
ui.window.render(scene);
|
||||
ui.window.scheduleFrame();
|
||||
}
|
||||
|
||||
|
||||
void handleImageLoad(result) {
|
||||
if (result != image) {
|
||||
print("${result.width}x${result.width} image loaded!");
|
||||
image = result;
|
||||
ui.window.scheduleFrame();
|
||||
} else {
|
||||
print("Existing image was loaded again");
|
||||
}
|
||||
}
|
||||
|
||||
void handlePointerPacket(ByteData serializedPacket) {
|
||||
bindings.Message message = new bindings.Message(
|
||||
serializedPacket, <core.MojoHandle>[],
|
||||
serializedPacket.lengthInBytes, 0);
|
||||
PointerPacket packet = PointerPacket.deserialize(message);
|
||||
|
||||
for (Pointer pointer in packet.pointers) {
|
||||
if (pointer.type == PointerType.up) {
|
||||
imageCache.load(url2).first.then(handleImageLoad);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
imageCache.load(url1).first.then(handleImageLoad);
|
||||
ui.window.onPointerPacket = handlePointerPacket;
|
||||
ui.window.onBeginFrame = beginFrame;
|
||||
}
|
@ -1,102 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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/rendering.dart';
|
||||
|
||||
class _BaselinePainter extends CustomPainter {
|
||||
const _BaselinePainter({
|
||||
this.paragraph
|
||||
});
|
||||
|
||||
final RenderParagraph paragraph;
|
||||
|
||||
void paint(Canvas canvas, Size size) {
|
||||
double baseline = paragraph.getDistanceToBaseline(TextBaseline.alphabetic);
|
||||
double w = paragraph.getMaxIntrinsicWidth(new BoxConstraints.loose(size));
|
||||
double h = paragraph.getMaxIntrinsicHeight(new BoxConstraints.loose(size));
|
||||
|
||||
Path path;
|
||||
Paint paint;
|
||||
|
||||
// top and bottom
|
||||
path = new Path();
|
||||
path.moveTo(0.0, 0.0);
|
||||
path.lineTo(w, 0.0);
|
||||
path.moveTo(0.0, h);
|
||||
path.lineTo(w, h);
|
||||
paint = new Paint()
|
||||
..color = const Color(0xFFFF9000)
|
||||
..style = PaintingStyle.stroke
|
||||
..strokeWidth = 1.5;
|
||||
canvas.drawPath(path, paint);
|
||||
|
||||
// baseline
|
||||
path = new Path();
|
||||
path.moveTo(0.0, baseline);
|
||||
path.lineTo(w, baseline);
|
||||
paint = new Paint()
|
||||
..color = const Color(0xFF00FF90)
|
||||
..style = PaintingStyle.stroke
|
||||
..strokeWidth = 1.5;
|
||||
canvas.drawPath(path, paint);
|
||||
}
|
||||
|
||||
// TODO(abarth): We have no good way of detecting when the paragraph's intrinsic dimensions change.
|
||||
bool shouldRepaint(_BaselinePainter oldPainter) => true;
|
||||
}
|
||||
|
||||
RenderBox getBox(double lh) {
|
||||
RenderParagraph paragraph = new RenderParagraph(
|
||||
new StyledTextSpan(
|
||||
new TextStyle(
|
||||
color: const Color(0xFF0000A0)
|
||||
),
|
||||
<TextSpan>[
|
||||
new PlainTextSpan('test'),
|
||||
new StyledTextSpan(
|
||||
new TextStyle(
|
||||
fontFamily: 'serif',
|
||||
fontSize: 50.0,
|
||||
height: lh
|
||||
),
|
||||
<TextSpan>[new PlainTextSpan('مرحبا Hello')]
|
||||
)
|
||||
]
|
||||
)
|
||||
);
|
||||
return new RenderPadding(
|
||||
padding: new EdgeDims.all(10.0),
|
||||
child: new RenderConstrainedBox(
|
||||
additionalConstraints: new BoxConstraints.tightFor(height: 200.0),
|
||||
child: new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(
|
||||
backgroundColor: const Color(0xFFFFFFFF)
|
||||
),
|
||||
child: new RenderPadding(
|
||||
padding: new EdgeDims.all(10.0),
|
||||
child: new RenderCustomPaint(
|
||||
painter: new _BaselinePainter(
|
||||
paragraph: paragraph
|
||||
),
|
||||
child: paragraph
|
||||
)
|
||||
)
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
void main() {
|
||||
RenderBox root = new RenderFlex(children: <RenderBox>[
|
||||
new RenderConstrainedBox(
|
||||
additionalConstraints: new BoxConstraints.tightFor(height: 50.0)
|
||||
),
|
||||
getBox(null),
|
||||
getBox(1.2),
|
||||
],
|
||||
direction: FlexDirection.vertical,
|
||||
alignItems: FlexAlignItems.stretch
|
||||
);
|
||||
new RenderingFlutterBinding(root: root);
|
||||
}
|
@ -1,75 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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/rendering.dart';
|
||||
|
||||
void main() {
|
||||
RenderFlex root = new RenderFlex(
|
||||
children: <RenderBox>[
|
||||
new RenderPadding(
|
||||
padding: new EdgeDims.all(10.0),
|
||||
child: new RenderConstrainedBox(
|
||||
additionalConstraints: new BoxConstraints.tightFor(height: 100.0),
|
||||
child: new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(
|
||||
backgroundColor: const Color(0xFFFFFF00)
|
||||
)
|
||||
)
|
||||
)
|
||||
),
|
||||
new RenderPadding(
|
||||
padding: new EdgeDims.all(10.0),
|
||||
child: new RenderConstrainedBox(
|
||||
additionalConstraints: new BoxConstraints.tightFor(height: 100.0),
|
||||
child: new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(
|
||||
border: new Border(
|
||||
top: new BorderSide(color: const Color(0xFFF00000), width: 5.0),
|
||||
right: new BorderSide(color: const Color(0xFFFF9000), width: 10.0),
|
||||
bottom: new BorderSide(color: const Color(0xFFFFF000), width: 15.0),
|
||||
left: new BorderSide(color: const Color(0xFF00FF00), width: 20.0)
|
||||
),
|
||||
backgroundColor: const Color(0xFFDDDDDD)
|
||||
)
|
||||
)
|
||||
)
|
||||
),
|
||||
new RenderPadding(
|
||||
padding: new EdgeDims.all(10.0),
|
||||
child: new RenderConstrainedBox(
|
||||
additionalConstraints: new BoxConstraints.tightFor(height: 100.0),
|
||||
child: new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(
|
||||
backgroundColor: const Color(0xFFFFFF00)
|
||||
)
|
||||
)
|
||||
)
|
||||
),
|
||||
new RenderPadding(
|
||||
padding: new EdgeDims.all(10.0),
|
||||
child: new RenderConstrainedBox(
|
||||
additionalConstraints: new BoxConstraints.tightFor(height: 100.0),
|
||||
child: new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(
|
||||
backgroundColor: const Color(0xFFFFFF00)
|
||||
)
|
||||
)
|
||||
)
|
||||
),
|
||||
new RenderPadding(
|
||||
padding: new EdgeDims.all(10.0),
|
||||
child: new RenderConstrainedBox(
|
||||
additionalConstraints: new BoxConstraints.tightFor(height: 100.0),
|
||||
child: new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(
|
||||
backgroundColor: const Color(0xFFFFFF00)
|
||||
)
|
||||
)
|
||||
)
|
||||
),
|
||||
],
|
||||
direction: FlexDirection.vertical
|
||||
);
|
||||
new RenderingFlutterBinding(root: root);
|
||||
}
|
@ -1,55 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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/rendering.dart';
|
||||
import 'lib/solid_color_box.dart';
|
||||
|
||||
RenderBox buildFlexExample() {
|
||||
RenderFlex flexRoot = new RenderFlex(direction: FlexDirection.vertical);
|
||||
|
||||
RenderDecoratedBox root = new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(backgroundColor: const Color(0xFF000000)),
|
||||
child: flexRoot
|
||||
);
|
||||
|
||||
void addFlexChildSolidColor(RenderFlex parent, Color backgroundColor, { int flex: 0 }) {
|
||||
RenderSolidColorBox child = new RenderSolidColorBox(backgroundColor);
|
||||
parent.add(child);
|
||||
final FlexParentData childParentData = child.parentData;
|
||||
childParentData.flex = flex;
|
||||
}
|
||||
|
||||
// Yellow bar at top
|
||||
addFlexChildSolidColor(flexRoot, const Color(0xFFFFFF00), flex: 1);
|
||||
|
||||
// Turquoise box
|
||||
flexRoot.add(new RenderSolidColorBox(const Color(0x7700FFFF), desiredSize: new Size(100.0, 100.0)));
|
||||
|
||||
var renderDecoratedBlock = new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(backgroundColor: const Color(0xFFFFFFFF))
|
||||
);
|
||||
|
||||
flexRoot.add(new RenderPadding(padding: const EdgeDims.all(10.0), child: renderDecoratedBlock));
|
||||
|
||||
var row = new RenderFlex(direction: FlexDirection.horizontal);
|
||||
|
||||
// Purple and blue cells
|
||||
addFlexChildSolidColor(row, const Color(0x77FF00FF), flex: 1);
|
||||
addFlexChildSolidColor(row, const Color(0xFF0000FF), flex: 2);
|
||||
|
||||
var decoratedRow = new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(backgroundColor: const Color(0xFF333333)),
|
||||
child: row
|
||||
);
|
||||
|
||||
flexRoot.add(decoratedRow);
|
||||
final FlexParentData decoratedRowParentData = decoratedRow.parentData;
|
||||
decoratedRowParentData.flex = 3;
|
||||
|
||||
return root;
|
||||
}
|
||||
|
||||
void main() {
|
||||
new RenderingFlutterBinding(root: buildFlexExample());
|
||||
}
|
@ -1,126 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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:ui' as ui show Image, window;
|
||||
import 'dart:math' as math;
|
||||
import 'dart:typed_data';
|
||||
|
||||
import 'package:flutter/scheduler.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:flutter/rendering.dart';
|
||||
import 'package:mojo/bindings.dart' as bindings;
|
||||
import 'package:mojo/core.dart' as core;
|
||||
import 'package:sky_services/pointer/pointer.mojom.dart';
|
||||
|
||||
import 'lib/solid_color_box.dart';
|
||||
|
||||
class Touch {
|
||||
final double x;
|
||||
final double y;
|
||||
const Touch(this.x, this.y);
|
||||
}
|
||||
|
||||
class RenderImageGrow extends RenderImage {
|
||||
final Size _startingSize;
|
||||
|
||||
RenderImageGrow(ui.Image image, Size size)
|
||||
: _startingSize = size, super(image: image, width: size.width, height: size.height);
|
||||
|
||||
double _growth = 0.0;
|
||||
double get growth => _growth;
|
||||
void set growth(double value) {
|
||||
_growth = value;
|
||||
width = _startingSize.width == null ? null : _startingSize.width + growth;
|
||||
height = _startingSize.height == null ? null : _startingSize.height + growth;
|
||||
}
|
||||
}
|
||||
|
||||
RenderImageGrow image;
|
||||
|
||||
class DemoBinding extends BindingBase with Scheduler, Renderer {
|
||||
DemoBinding({ RenderBox root }) {
|
||||
renderView.child = root;
|
||||
ui.window.onPopRoute = handlePopRoute;
|
||||
ui.window.onPointerPacket = handlePointerPacket;
|
||||
}
|
||||
|
||||
void handlePopRoute() {
|
||||
activity.finishCurrentActivity();
|
||||
}
|
||||
|
||||
final Map<int, Touch> touches = <int, Touch>{};
|
||||
|
||||
void handlePointerPacket(ByteData serializedPacket) {
|
||||
bindings.Message message = new bindings.Message(
|
||||
serializedPacket,
|
||||
<core.MojoHandle>[],
|
||||
serializedPacket.lengthInBytes,
|
||||
0
|
||||
);
|
||||
PointerPacket packet = PointerPacket.deserialize(message);
|
||||
for (Pointer pointer in packet.pointers) {
|
||||
if (pointer.type == PointerType.move)
|
||||
image.growth = math.max(0.0, image.growth + pointer.x - touches[pointer.pointer].x);
|
||||
touches[pointer.pointer] = new Touch(pointer.x, pointer.y);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
void addFlexChildSolidColor(RenderFlex parent, Color backgroundColor, { int flex: 0 }) {
|
||||
RenderSolidColorBox child = new RenderSolidColorBox(backgroundColor);
|
||||
parent.add(child);
|
||||
final FlexParentData childParentData = child.parentData;
|
||||
childParentData.flex = flex;
|
||||
}
|
||||
|
||||
var row = new RenderFlex(direction: FlexDirection.horizontal);
|
||||
|
||||
// Left cell
|
||||
addFlexChildSolidColor(row, const Color(0xFF00D2B8), flex: 1);
|
||||
|
||||
// Resizeable image
|
||||
image = new RenderImageGrow(null, new Size(100.0, null));
|
||||
imageCache.load("http://flutter.io/favicon.ico").first.then((ImageInfo dartLogo) {
|
||||
image.image = dartLogo.image;
|
||||
});
|
||||
|
||||
row.add(new RenderPadding(padding: const EdgeDims.all(10.0), child: image));
|
||||
|
||||
RenderFlex column = new RenderFlex(direction: FlexDirection.vertical);
|
||||
|
||||
// Top cell
|
||||
final Color topColor = const Color(0xFF55DDCA);
|
||||
addFlexChildSolidColor(column, topColor, flex: 1);
|
||||
|
||||
// The internet is a beautiful place. https://baconipsum.com/
|
||||
String meatyString = """Bacon ipsum dolor amet ham fatback tri-tip, prosciutto
|
||||
porchetta bacon kevin meatball meatloaf pig beef ribs chicken. Brisket ribeye
|
||||
andouille leberkas capicola meatloaf. Chicken pig ball tip pork picanha bresaola
|
||||
alcatra. Pork pork belly alcatra, flank chuck drumstick biltong doner jowl.
|
||||
Pancetta meatball tongue tenderloin rump tail jowl boudin.""";
|
||||
TextSpan text = new StyledTextSpan(
|
||||
new TextStyle(color: const Color(0xFF009900)),
|
||||
<TextSpan>[new PlainTextSpan(meatyString)]
|
||||
);
|
||||
column.add(new RenderPadding(
|
||||
padding: const EdgeDims.all(10.0),
|
||||
child: new RenderParagraph(text)
|
||||
));
|
||||
|
||||
// Bottom cell
|
||||
addFlexChildSolidColor(column, const Color(0xFF0081C6), flex: 2);
|
||||
|
||||
row.add(column);
|
||||
final FlexParentData childParentData = column.parentData;
|
||||
childParentData.flex = 8;
|
||||
|
||||
RenderDecoratedBox root = new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(backgroundColor: const Color(0xFFFFFFFF)),
|
||||
child: row
|
||||
);
|
||||
|
||||
updateTaskDescription(label: 'Interactive Flex', color: topColor);
|
||||
new DemoBinding(root: root);
|
||||
}
|
@ -1,41 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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/rendering.dart';
|
||||
|
||||
import 'lib/solid_color_box.dart';
|
||||
|
||||
const TextStyle style = const TextStyle(color: const Color(0xFF000000));
|
||||
|
||||
// Attempts to draw
|
||||
// http://www.w3.org/TR/2015/WD-css-flexbox-1-20150514/images/flex-pack.svg
|
||||
void main() {
|
||||
var table = new RenderFlex(direction: FlexDirection.vertical);
|
||||
|
||||
void addRow(FlexJustifyContent justify) {
|
||||
RenderParagraph paragraph = new RenderParagraph(new StyledTextSpan(style, <TextSpan>[new PlainTextSpan("$justify")]));
|
||||
table.add(new RenderPadding(child: paragraph, padding: new EdgeDims.only(top: 20.0)));
|
||||
RenderFlex row = new RenderFlex(direction: FlexDirection.horizontal);
|
||||
row.add(new RenderSolidColorBox(const Color(0xFFFFCCCC), desiredSize: new Size(80.0, 60.0)));
|
||||
row.add(new RenderSolidColorBox(const Color(0xFFCCFFCC), desiredSize: new Size(64.0, 60.0)));
|
||||
row.add(new RenderSolidColorBox(const Color(0xFFCCCCFF), desiredSize: new Size(160.0, 60.0)));
|
||||
row.justifyContent = justify;
|
||||
table.add(row);
|
||||
final FlexParentData rowParentData = row.parentData;
|
||||
rowParentData.flex = 1;
|
||||
}
|
||||
|
||||
addRow(FlexJustifyContent.start);
|
||||
addRow(FlexJustifyContent.end);
|
||||
addRow(FlexJustifyContent.center);
|
||||
addRow(FlexJustifyContent.spaceBetween);
|
||||
addRow(FlexJustifyContent.spaceAround);
|
||||
|
||||
RenderDecoratedBox root = new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(backgroundColor: const Color(0xFFFFFFFF)),
|
||||
child: new RenderPadding(child: table, padding: new EdgeDims.symmetric(vertical: 50.0))
|
||||
);
|
||||
|
||||
new RenderingFlutterBinding(root: root);
|
||||
}
|
@ -1,4 +0,0 @@
|
||||
name: flutter_rendering_examples
|
||||
dependencies:
|
||||
flutter:
|
||||
path: ../../packages/flutter
|
@ -1,29 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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 'package:flutter/material.dart';
|
||||
import 'package:flutter/rendering.dart';
|
||||
|
||||
import 'lib/solid_color_box.dart';
|
||||
|
||||
Color randomColor() {
|
||||
final List<Color> allColors = [
|
||||
Colors.blue,
|
||||
Colors.indigo
|
||||
].map((p) => p.values).fold([], (a, b) => a..addAll(b));
|
||||
final random = new math.Random();
|
||||
return allColors[random.nextInt(allColors.length)];
|
||||
}
|
||||
|
||||
RenderBox buildGridExample() {
|
||||
List<RenderBox> children = new List<RenderBox>.generate(30, (_) => new RenderSolidColorBox(randomColor()));
|
||||
return new RenderGrid(
|
||||
children: children,
|
||||
delegate: new MaxTileWidthGridDelegate(maxTileWidth: 100.0)
|
||||
);
|
||||
}
|
||||
|
||||
main() => new RenderingFlutterBinding(root: buildGridExample());
|
@ -1,44 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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/rendering.dart';
|
||||
|
||||
import 'lib/solid_color_box.dart';
|
||||
|
||||
void main() {
|
||||
RenderFlex flexRoot = new RenderFlex(direction: FlexDirection.vertical);
|
||||
|
||||
RenderObject root = new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(backgroundColor: const Color(0xFF606060)),
|
||||
child: flexRoot
|
||||
);
|
||||
|
||||
FlexParentData childParentData;
|
||||
|
||||
RenderObject child = new RenderSolidColorBox(const Color(0xFFFFFF00));
|
||||
flexRoot.add(child);
|
||||
childParentData = child.parentData;
|
||||
childParentData.flex = 2;
|
||||
|
||||
// The internet is a beautiful place. https://baconipsum.com/
|
||||
String meatyString = """Bacon ipsum dolor amet ham fatback tri-tip, prosciutto
|
||||
porchetta bacon kevin meatball meatloaf pig beef ribs chicken. Brisket ribeye
|
||||
andouille leberkas capicola meatloaf. Chicken pig ball tip pork picanha bresaola
|
||||
alcatra. Pork pork belly alcatra, flank chuck drumstick biltong doner jowl.
|
||||
Pancetta meatball tongue tenderloin rump tail jowl boudin.""";
|
||||
|
||||
StyledTextSpan text = new StyledTextSpan(
|
||||
new TextStyle(color: const Color(0xFF009900)),
|
||||
<TextSpan>[new PlainTextSpan(meatyString)]
|
||||
);
|
||||
child = new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(backgroundColor: const Color(0xFFFFFFFF)),
|
||||
child: new RenderParagraph(text)
|
||||
);
|
||||
flexRoot.add(child);
|
||||
childParentData = child.parentData;
|
||||
childParentData.flex = 1;
|
||||
|
||||
new RenderingFlutterBinding(root: root);
|
||||
}
|
@ -1,96 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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/rendering.dart';
|
||||
|
||||
const List<BoxShadow> shadow = const <BoxShadow>[
|
||||
const BoxShadow(offset: const Offset(0.0, 3.0), blurRadius: 1.0, spreadRadius: -2.0, color: const Color(0x33000000)),
|
||||
const BoxShadow(offset: const Offset(0.0, 2.0), blurRadius: 2.0, spreadRadius: 0.0, color: const Color(0x24000000)),
|
||||
const BoxShadow(offset: const Offset(0.0, 1.0), blurRadius: 5.0, spreadRadius: 0.0, color: const Color(0x1F000000)),
|
||||
];
|
||||
|
||||
void main() {
|
||||
RenderDecoratedBox box1, box2, box3;
|
||||
new RenderingFlutterBinding(root: new RenderPadding(
|
||||
padding: const EdgeDims.all(40.0),
|
||||
child: new RenderViewport(
|
||||
child: new RenderDecoratedBox(
|
||||
decoration: const BoxDecoration(
|
||||
backgroundColor: const Color(0xFFFFFFFF)
|
||||
),
|
||||
child: new RenderBlock(
|
||||
children: <RenderBox>[
|
||||
new RenderPadding(
|
||||
padding: const EdgeDims.all(40.0),
|
||||
child: new RenderPointerListener(
|
||||
behavior: HitTestBehavior.opaque,
|
||||
onPointerDown: (PointerDownEvent event) {
|
||||
box1.decoration = const BoxDecoration(
|
||||
gradient: const RadialGradient(
|
||||
center: Point.origin, radius: 500.0,
|
||||
colors: const <Color>[const Color(0x20F0D0B0), const Color(0xD0C0FFFF)]
|
||||
),
|
||||
borderRadius: 20.0
|
||||
);
|
||||
RenderPadding innerBox1 = box1.child;
|
||||
innerBox1.padding *= 1.5;
|
||||
innerBox1.child = new RenderParagraph(
|
||||
const StyledTextSpan(
|
||||
const TextStyle(
|
||||
color: const Color(0xFF000000),
|
||||
fontSize: 20.0,
|
||||
fontWeight: FontWeight.w900,
|
||||
textAlign: TextAlign.center
|
||||
),
|
||||
const <TextSpan>[ const PlainTextSpan('Hello World!') ]
|
||||
)
|
||||
);
|
||||
RenderBlock block = box3.parent.parent;
|
||||
block.remove(box3.parent);
|
||||
RenderPadding innerBox2 = box2.child;
|
||||
innerBox2.child = box3.parent;
|
||||
RenderPointerListener listener = box1.parent;
|
||||
listener.onPointerDown = null;
|
||||
},
|
||||
child: box1 = new RenderDecoratedBox(
|
||||
decoration: const BoxDecoration(
|
||||
backgroundColor: const Color(0xFFFFFF00),
|
||||
boxShadow: shadow
|
||||
),
|
||||
child: new RenderPadding(
|
||||
padding: const EdgeDims.all(40.0)
|
||||
)
|
||||
)
|
||||
)
|
||||
),
|
||||
new RenderPadding(
|
||||
padding: const EdgeDims.all(40.0),
|
||||
child: box2 = new RenderDecoratedBox(
|
||||
decoration: const BoxDecoration(
|
||||
backgroundColor: const Color(0xFF00FFFF),
|
||||
boxShadow: shadow
|
||||
),
|
||||
child: new RenderPadding(
|
||||
padding: const EdgeDims.all(40.0)
|
||||
)
|
||||
)
|
||||
),
|
||||
new RenderPadding(
|
||||
padding: const EdgeDims.all(40.0),
|
||||
child: box3 = new RenderDecoratedBox(
|
||||
decoration: const BoxDecoration(
|
||||
backgroundColor: const Color(0xFF33FF33),
|
||||
boxShadow: shadow
|
||||
),
|
||||
child: new RenderPadding(
|
||||
padding: const EdgeDims.all(40.0)
|
||||
)
|
||||
)
|
||||
),
|
||||
]
|
||||
)
|
||||
)
|
||||
)
|
||||
));
|
||||
}
|
@ -1,43 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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/rendering.dart';
|
||||
|
||||
import 'lib/solid_color_box.dart';
|
||||
|
||||
Duration timeBase;
|
||||
RenderTransform transformBox;
|
||||
|
||||
void main() {
|
||||
RenderFlex flexRoot = new RenderFlex(direction: FlexDirection.vertical);
|
||||
|
||||
void addFlexChildSolidColor(RenderFlex parent, Color backgroundColor, { int flex: 0 }) {
|
||||
RenderSolidColorBox child = new RenderSolidColorBox(backgroundColor);
|
||||
parent.add(child);
|
||||
final FlexParentData childParentData = child.parentData;
|
||||
childParentData.flex = flex;
|
||||
}
|
||||
|
||||
addFlexChildSolidColor(flexRoot, const Color(0xFFFF00FF), flex: 1);
|
||||
addFlexChildSolidColor(flexRoot, const Color(0xFFFFFF00), flex: 2);
|
||||
addFlexChildSolidColor(flexRoot, const Color(0xFF00FFFF), flex: 1);
|
||||
|
||||
transformBox = new RenderTransform(child: flexRoot, transform: new Matrix4.identity());
|
||||
|
||||
RenderPadding root = new RenderPadding(padding: new EdgeDims.all(20.0), child: transformBox);
|
||||
|
||||
new RenderingFlutterBinding(root: root)
|
||||
..addPersistentFrameCallback(rotate);
|
||||
}
|
||||
|
||||
void rotate(Duration timeStamp) {
|
||||
if (timeBase == null)
|
||||
timeBase = timeStamp;
|
||||
double delta = (timeStamp - timeBase).inMicroseconds.toDouble() / Duration.MICROSECONDS_PER_SECOND; // radians
|
||||
|
||||
transformBox.setIdentity();
|
||||
transformBox.translate(transformBox.size.width / 2.0, transformBox.size.height / 2.0);
|
||||
transformBox.rotateZ(delta);
|
||||
transformBox.translate(-transformBox.size.width / 2.0, -transformBox.size.height / 2.0);
|
||||
}
|
@ -1,81 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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:flutter/rendering.dart';
|
||||
import 'package:flutter/gestures.dart';
|
||||
|
||||
// Material design colors. :p
|
||||
List<Color> kColors = <Color>[
|
||||
Colors.teal[500],
|
||||
Colors.amber[500],
|
||||
Colors.purple[500],
|
||||
Colors.lightBlue[500],
|
||||
Colors.deepPurple[500],
|
||||
Colors.lime[500],
|
||||
];
|
||||
|
||||
class Dot {
|
||||
final Paint _paint;
|
||||
Point position = Point.origin;
|
||||
double radius = 0.0;
|
||||
|
||||
Dot({ Color color }) : _paint = new Paint()..color = color;
|
||||
|
||||
void update(PointerEvent event) {
|
||||
position = event.position;
|
||||
radius = 5 + (95 * event.pressure);
|
||||
}
|
||||
|
||||
void paint(PaintingContext context, Offset offset) {
|
||||
context.canvas.drawCircle(position + offset, radius, _paint);
|
||||
}
|
||||
}
|
||||
|
||||
class RenderTouchDemo extends RenderBox {
|
||||
final Map<int, Dot> dots = <int, Dot>{};
|
||||
|
||||
void handleEvent(PointerEvent event, BoxHitTestEntry entry) {
|
||||
if (event is PointerDownEvent) {
|
||||
Color color = kColors[event.pointer.remainder(kColors.length)];
|
||||
dots[event.pointer] = new Dot(color: color)..update(event);
|
||||
} else if (event is PointerUpEvent) {
|
||||
dots.remove(event.pointer);
|
||||
} else if (event is PointerCancelEvent) {
|
||||
dots.clear();
|
||||
} else if (event is PointerMoveEvent) {
|
||||
dots[event.pointer].update(event);
|
||||
} else {
|
||||
return;
|
||||
}
|
||||
markNeedsPaint();
|
||||
}
|
||||
|
||||
void performLayout() {
|
||||
size = constraints.biggest;
|
||||
}
|
||||
|
||||
void paint(PaintingContext context, Offset offset) {
|
||||
final Canvas canvas = context.canvas;
|
||||
Paint white = new Paint()
|
||||
..color = const Color(0xFFFFFFFF);
|
||||
canvas.drawRect(offset & size, white);
|
||||
for (Dot dot in dots.values)
|
||||
dot.paint(context, offset);
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
RenderParagraph paragraph = new RenderParagraph(new PlainTextSpan("Touch me!"));
|
||||
RenderStack stack = new RenderStack(children: <RenderBox>[
|
||||
new RenderTouchDemo(),
|
||||
paragraph,
|
||||
]);
|
||||
// Prevent the RenderParagraph from filling the whole screen so
|
||||
// that it doesn't eat events.
|
||||
final StackParentData paragraphParentData = paragraph.parentData;
|
||||
paragraphParentData..top = 40.0
|
||||
..left = 20.0;
|
||||
new RenderingFlutterBinding(root: stack);
|
||||
}
|
@ -1,26 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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/rendering.dart';
|
||||
|
||||
void main() {
|
||||
RenderDecoratedBox green = new RenderDecoratedBox(
|
||||
decoration: new BoxDecoration(backgroundColor: const Color(0xFF00FF00))
|
||||
);
|
||||
RenderConstrainedBox box = new RenderConstrainedBox(
|
||||
additionalConstraints: new BoxConstraints.tight(const Size(200.0, 200.0)),
|
||||
child: green
|
||||
);
|
||||
|
||||
Matrix4 transform = new Matrix4.identity();
|
||||
RenderTransform spin = new RenderTransform(
|
||||
transform: transform,
|
||||
child: box
|
||||
);
|
||||
spin.rotateZ(1.0);
|
||||
|
||||
RenderFlex flex = new RenderFlex();
|
||||
flex.add(spin);
|
||||
new RenderingFlutterBinding(root: flex);
|
||||
}
|
@ -1,51 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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';
|
||||
|
||||
class ContainerApp extends StatelessComponent {
|
||||
Widget build(BuildContext context) {
|
||||
return new Column(
|
||||
children: <Widget>[
|
||||
new Container(
|
||||
padding: new EdgeDims.all(10.0),
|
||||
margin: new EdgeDims.all(10.0),
|
||||
decoration: new BoxDecoration(backgroundColor: const Color(0xFFCCCCCC)),
|
||||
child: new NetworkImage(
|
||||
src: "https://raw.githubusercontent.com/dart-lang/logos/master/logos_and_wordmarks/dart-logo.png",
|
||||
width: 300.0,
|
||||
height: 300.0
|
||||
)
|
||||
),
|
||||
new Material(
|
||||
color: const Color(0xFFFFFF00),
|
||||
child: new Container(
|
||||
padding: new EdgeDims.symmetric(horizontal: 50.0, vertical: 75.0),
|
||||
child: new Row(
|
||||
children: <Widget>[
|
||||
new RaisedButton(
|
||||
child: new Text('PRESS ME'),
|
||||
onPressed: () => print("Hello World")
|
||||
),
|
||||
new RaisedButton(
|
||||
child: new Text('DISABLED')
|
||||
)
|
||||
]
|
||||
)
|
||||
)
|
||||
),
|
||||
new Flexible(
|
||||
child: new Container(
|
||||
decoration: new BoxDecoration(backgroundColor: const Color(0xFF00FFFF))
|
||||
)
|
||||
),
|
||||
],
|
||||
justifyContent: FlexJustifyContent.spaceBetween
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
runApp(new ContainerApp());
|
||||
}
|
@ -1,126 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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';
|
||||
|
||||
class CardModel {
|
||||
CardModel(this.value, this.height, this.color);
|
||||
int value;
|
||||
double height;
|
||||
Color color;
|
||||
String get label => "Card $value";
|
||||
Key get key => new ObjectKey(this);
|
||||
}
|
||||
|
||||
typedef void TappableCardCallback(BuildContext context);
|
||||
|
||||
class TappableCard extends StatelessComponent {
|
||||
TappableCard({ CardModel cardModel, this.selected, this.onTap })
|
||||
: cardModel = cardModel, super(key: cardModel.key);
|
||||
final CardModel cardModel;
|
||||
final bool selected;
|
||||
final TappableCardCallback onTap;
|
||||
|
||||
static const TextStyle cardLabelStyle = const TextStyle(
|
||||
color: Colors.white,
|
||||
fontSize: 18.0,
|
||||
fontWeight: FontWeight.bold
|
||||
);
|
||||
|
||||
static const TextStyle selectedCardLabelStyle = const TextStyle(
|
||||
color: Colors.white,
|
||||
fontSize: 24.0,
|
||||
fontWeight: FontWeight.bold
|
||||
);
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
return new GestureDetector(
|
||||
onTap: () => onTap(context),
|
||||
child: new Card(
|
||||
color: cardModel.color,
|
||||
child: new Container(
|
||||
height: cardModel.height,
|
||||
padding: const EdgeDims.all(8.0),
|
||||
child: new Center(
|
||||
child: new Text(
|
||||
cardModel.label,
|
||||
style: selected ? selectedCardLabelStyle : cardLabelStyle
|
||||
)
|
||||
)
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
class EnsureVisibleApp extends StatefulComponent {
|
||||
EnsureVisibleAppState createState() => new EnsureVisibleAppState();
|
||||
}
|
||||
|
||||
class EnsureVisibleAppState extends State<EnsureVisibleApp> {
|
||||
|
||||
List<CardModel> cardModels;
|
||||
int selectedCardIndex;
|
||||
|
||||
void initState() {
|
||||
List<double> cardHeights = <double>[
|
||||
48.0, 63.0, 82.0, 146.0, 60.0, 55.0, 84.0, 96.0, 50.0,
|
||||
48.0, 63.0, 82.0, 146.0, 60.0, 55.0, 84.0, 96.0, 50.0,
|
||||
48.0, 63.0, 82.0, 146.0, 60.0, 55.0, 84.0, 96.0, 50.0
|
||||
];
|
||||
cardModels = new List<CardModel>.generate(cardHeights.length, (int i) {
|
||||
Color color = Color.lerp(Colors.red[300], Colors.blue[900], i / cardHeights.length);
|
||||
return new CardModel(i, cardHeights[i], color);
|
||||
});
|
||||
super.initState();
|
||||
}
|
||||
|
||||
Widget builder(BuildContext context, int index) {
|
||||
if (index >= cardModels.length)
|
||||
return null;
|
||||
return new TappableCard(
|
||||
cardModel: cardModels[index],
|
||||
selected: index == selectedCardIndex,
|
||||
onTap: (BuildContext context) {
|
||||
Scrollable.ensureVisible(context, duration: const Duration(milliseconds: 200))
|
||||
.then((_) {
|
||||
setState(() { selectedCardIndex = index; });
|
||||
});
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
return new IconTheme(
|
||||
data: const IconThemeData(color: IconThemeColor.white),
|
||||
child: new Theme(
|
||||
data: new ThemeData(
|
||||
brightness: ThemeBrightness.light,
|
||||
primarySwatch: Colors.blue,
|
||||
accentColor: Colors.redAccent[200]
|
||||
),
|
||||
child: new Title(
|
||||
title: 'Cards',
|
||||
child: new Scaffold(
|
||||
toolBar: new ToolBar(center: new Text('Tap a card, any card')),
|
||||
body: new Container(
|
||||
padding: const EdgeDims.symmetric(vertical: 12.0, horizontal: 8.0),
|
||||
decoration: new BoxDecoration(backgroundColor: Theme.of(context).primarySwatch[50]),
|
||||
child: new ScrollableMixedWidgetList(
|
||||
builder: builder,
|
||||
token: cardModels.length
|
||||
)
|
||||
)
|
||||
)
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
runApp(new EnsureVisibleApp());
|
||||
}
|
@ -1,52 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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/widgets.dart';
|
||||
|
||||
class Circle extends StatelessComponent {
|
||||
Circle({ this.margin: EdgeDims.zero });
|
||||
|
||||
final EdgeDims margin;
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
return new Container(
|
||||
width: 50.0,
|
||||
margin: margin + new EdgeDims.symmetric(horizontal: 2.0),
|
||||
decoration: new BoxDecoration(
|
||||
shape: BoxShape.circle,
|
||||
backgroundColor: const Color(0xFF00FF00)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class HorizontalScrollingApp extends StatelessComponent {
|
||||
Widget build(BuildContext context) {
|
||||
List<Widget> circles = <Widget>[
|
||||
new Circle(margin: new EdgeDims.only(left: 10.0)),
|
||||
new Circle(),
|
||||
new Circle(),
|
||||
new Circle(),
|
||||
new Circle(),
|
||||
new Circle(),
|
||||
new Circle(),
|
||||
new Circle(),
|
||||
new Circle(),
|
||||
new Circle(),
|
||||
new Circle(),
|
||||
new Circle(margin: new EdgeDims.only(right: 10.0)),
|
||||
];
|
||||
|
||||
return new Center(
|
||||
child: new Container(
|
||||
height: 50.0,
|
||||
child: new Block(children: circles, scrollDirection: Axis.horizontal)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
runApp(new HorizontalScrollingApp());
|
||||
}
|
@ -1,97 +0,0 @@
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
void main() {
|
||||
runApp(
|
||||
new MaterialApp(
|
||||
title: "Media Query Example",
|
||||
routes: <String, RouteBuilder>{
|
||||
'/': (RouteArguments args) => new MediaQueryExample()
|
||||
}
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
class AdaptiveItem {
|
||||
AdaptiveItem(this.name);
|
||||
String name;
|
||||
|
||||
Widget toListItem() {
|
||||
return new Row(
|
||||
children: <Widget>[
|
||||
new Container(
|
||||
width: 32.0,
|
||||
height: 32.0,
|
||||
margin: const EdgeDims.all(8.0),
|
||||
decoration: new BoxDecoration(
|
||||
backgroundColor: Colors.lightBlueAccent[100]
|
||||
)
|
||||
),
|
||||
new Text(name)
|
||||
]
|
||||
);
|
||||
}
|
||||
|
||||
Widget toCard() {
|
||||
return new Card(
|
||||
child: new Column(
|
||||
children: <Widget>[
|
||||
new Flexible(
|
||||
child: new Container(
|
||||
decoration: new BoxDecoration(
|
||||
backgroundColor: Colors.lightBlueAccent[100]
|
||||
)
|
||||
)
|
||||
),
|
||||
new Container(
|
||||
margin: const EdgeDims.only(left: 8.0),
|
||||
child: new Row(
|
||||
children: <Widget>[
|
||||
new Flexible(
|
||||
child: new Text(name)
|
||||
),
|
||||
new IconButton(
|
||||
icon: "navigation/more_vert"
|
||||
)
|
||||
]
|
||||
)
|
||||
)
|
||||
]
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class MediaQueryExample extends StatelessComponent {
|
||||
static const double _maxTileWidth = 150.0;
|
||||
static const double _gridViewBreakpoint = 450.0;
|
||||
|
||||
Widget _buildBody(BuildContext context) {
|
||||
List<AdaptiveItem> items = <AdaptiveItem>[];
|
||||
|
||||
for (int i = 0; i < 30; i++)
|
||||
items.add(new AdaptiveItem("Item $i"));
|
||||
|
||||
if (MediaQuery.of(context).size.width < _gridViewBreakpoint) {
|
||||
return new ScrollableList(
|
||||
itemExtent: 50.0,
|
||||
children: items.map((AdaptiveItem item) => item.toListItem())
|
||||
);
|
||||
} else {
|
||||
return new ScrollableGrid(
|
||||
delegate: new MaxTileWidthGridDelegate(maxTileWidth: _maxTileWidth),
|
||||
children: items.map((AdaptiveItem item) => item.toCard())
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
return new Scaffold(
|
||||
toolBar: new ToolBar(
|
||||
center: new Text("Media Query Example")
|
||||
),
|
||||
body: new Material(
|
||||
child: _buildBody(context)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
@ -1,100 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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';
|
||||
|
||||
class Home extends StatelessComponent {
|
||||
Widget build(BuildContext context) {
|
||||
return new Material(
|
||||
child: new Center(
|
||||
child: new Block(
|
||||
children: <Widget>[
|
||||
new Text(
|
||||
'You are at home.',
|
||||
style: Theme.of(context).text.display2.copyWith(textAlign: TextAlign.center)
|
||||
),
|
||||
new RaisedButton(
|
||||
child: new Text('GO SHOPPING'),
|
||||
onPressed: () => Navigator.pushNamed(context, '/shopping')
|
||||
),
|
||||
new RaisedButton(
|
||||
child: new Text('START ADVENTURE'),
|
||||
onPressed: () => Navigator.pushNamed(context, '/adventure')
|
||||
)
|
||||
],
|
||||
padding: const EdgeDims.all(30.0)
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class Shopping extends StatelessComponent {
|
||||
Widget build(BuildContext context) {
|
||||
return new Material(
|
||||
color: Colors.deepPurple[300],
|
||||
child: new Center(
|
||||
child: new Block(
|
||||
children: <Widget>[
|
||||
new Text(
|
||||
'Village Shop',
|
||||
style: Theme.of(context).text.display2.copyWith(textAlign: TextAlign.center)
|
||||
),
|
||||
new RaisedButton(
|
||||
child: new Text('RETURN HOME'),
|
||||
onPressed: () => Navigator.pop(context)
|
||||
),
|
||||
new RaisedButton(
|
||||
child: new Text('GO TO DUNGEON'),
|
||||
onPressed: () => Navigator.pushNamed(context, '/adventure')
|
||||
)
|
||||
],
|
||||
padding: const EdgeDims.all(30.0)
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class Adventure extends StatelessComponent {
|
||||
Widget build(BuildContext context) {
|
||||
return new Material(
|
||||
color: Colors.red[300],
|
||||
child: new Center(
|
||||
child: new Block(
|
||||
children: <Widget>[
|
||||
new Text(
|
||||
'Monster\'s Lair',
|
||||
style: Theme.of(context).text.display2.copyWith(textAlign: TextAlign.center)
|
||||
),
|
||||
new RaisedButton(
|
||||
child: new Text('RUN!!!'),
|
||||
onPressed: () => Navigator.pop(context)
|
||||
)
|
||||
],
|
||||
padding: const EdgeDims.all(30.0)
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
final Map<String, RouteBuilder> routes = <String, RouteBuilder>{
|
||||
'/': (_) => new Home(),
|
||||
'/shopping': (_) => new Shopping(),
|
||||
'/adventure': (_) => new Adventure(),
|
||||
};
|
||||
|
||||
final ThemeData theme = new ThemeData(
|
||||
brightness: ThemeBrightness.light,
|
||||
primarySwatch: Colors.purple
|
||||
);
|
||||
|
||||
void main() {
|
||||
runApp(new MaterialApp(
|
||||
title: 'Navigation Example',
|
||||
theme: theme,
|
||||
routes: routes
|
||||
));
|
||||
}
|
@ -1,13 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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';
|
||||
|
||||
void main() {
|
||||
runApp(new NetworkImage(
|
||||
src: "http://38.media.tumblr.com/avatar_497c78dc767d_128.png",
|
||||
fit: ImageFit.contain,
|
||||
centerSlice: new Rect.fromLTRB(40.0, 40.0, 88.0, 88.0)
|
||||
));
|
||||
}
|
@ -1,113 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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';
|
||||
|
||||
final List<Map<int, Color>> _kColors = <Map<int, Color>>[
|
||||
Colors.amber,
|
||||
Colors.yellow,
|
||||
Colors.blue,
|
||||
Colors.purple,
|
||||
Colors.indigo,
|
||||
Colors.deepOrange,
|
||||
];
|
||||
|
||||
class SmoothBlock extends StatefulComponent {
|
||||
SmoothBlock({ this.color });
|
||||
|
||||
final Map<int, Color> color;
|
||||
|
||||
SmoothBlockState createState() => new SmoothBlockState();
|
||||
}
|
||||
|
||||
class CardTransition extends StatelessComponent {
|
||||
CardTransition({
|
||||
this.child,
|
||||
this.animation,
|
||||
this.x,
|
||||
this.opacity,
|
||||
this.scale
|
||||
});
|
||||
|
||||
final Widget child;
|
||||
final Animation<double> animation;
|
||||
final Animatable<double> x;
|
||||
final Animatable<double> opacity;
|
||||
final Animatable<double> scale;
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
return new AnimatedBuilder(
|
||||
animation: animation,
|
||||
builder: (BuildContext context, Widget child) {
|
||||
double currentScale = scale.evaluate(animation);
|
||||
Matrix4 transform = new Matrix4.identity()
|
||||
..translate(x.evaluate(animation))
|
||||
..scale(currentScale, currentScale);
|
||||
return new Opacity(
|
||||
opacity: opacity.evaluate(animation),
|
||||
child: new Transform(
|
||||
transform: transform,
|
||||
child: child
|
||||
)
|
||||
);
|
||||
},
|
||||
child: child
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class SmoothBlockState extends State<SmoothBlock> {
|
||||
|
||||
double _height = 100.0;
|
||||
|
||||
Widget _handleEnter(Animation<double> animation, Widget child) {
|
||||
return new CardTransition(
|
||||
x: new Tween<double>(begin: -200.0, end: 0.0),
|
||||
opacity: new Tween<double>(begin: 0.0, end: 1.0),
|
||||
scale: new Tween<double>(begin: 0.8, end: 1.0),
|
||||
animation: new CurvedAnimation(parent: animation, curve: Curves.ease),
|
||||
child: child
|
||||
);
|
||||
}
|
||||
|
||||
Widget _handleExit(Animation<double> animation, Widget child) {
|
||||
return new CardTransition(
|
||||
x: new Tween<double>(begin: 0.0, end: 200.0),
|
||||
opacity: new Tween<double>(begin: 1.0, end: 0.0),
|
||||
scale: new Tween<double>(begin: 1.0, end: 0.8),
|
||||
animation: new CurvedAnimation(parent: animation, curve: Curves.ease),
|
||||
child: child
|
||||
);
|
||||
}
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
return new GestureDetector(
|
||||
onTap: () {
|
||||
setState(() {
|
||||
_height = _height == 100.0 ? 200.0 : 100.0;
|
||||
});
|
||||
},
|
||||
child: new EnterExitTransition(
|
||||
duration: const Duration(milliseconds: 1500),
|
||||
onEnter: _handleEnter,
|
||||
onExit: _handleExit,
|
||||
child: new Container(
|
||||
key: new ValueKey(_height),
|
||||
height: _height,
|
||||
decoration: new BoxDecoration(backgroundColor: config.color[_height.floor() * 4])
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class SmoothResizeDemo extends StatelessComponent {
|
||||
Widget build(BuildContext context) {
|
||||
return new Block(children: _kColors.map((Map<int, Color> color) => new SmoothBlock(color: color)).toList());
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
runApp(new SmoothResizeDemo());
|
||||
}
|
@ -1,121 +0,0 @@
|
||||
// Copyright 2015 The Chromium 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:flutter/rendering.dart';
|
||||
|
||||
typedef Widget TextTransformer(String name, String text);
|
||||
|
||||
class StyledTextApp extends StatefulComponent {
|
||||
StyledTextAppState createState() => new StyledTextAppState();
|
||||
}
|
||||
|
||||
class StyledTextAppState extends State<StyledTextApp> {
|
||||
void initState() {
|
||||
super.initState();
|
||||
toText = toStyledText;
|
||||
nameLines = dialogText
|
||||
.split('\n')
|
||||
.map((String line) => line.split(':'))
|
||||
.toList();
|
||||
}
|
||||
|
||||
TextTransformer toText;
|
||||
|
||||
// From https://en.wikiquote.org/wiki/2001:_A_Space_Odyssey_(film)
|
||||
final String dialogText = '''
|
||||
Dave: Open the pod bay doors, please, HAL. Open the pod bay doors, please, HAL. Hello, HAL. Do you read me? Hello, HAL. Do you read me? Do you read me, HAL?
|
||||
HAL: Affirmative, Dave. I read you.
|
||||
Dave: Open the pod bay doors, HAL.
|
||||
HAL: I'm sorry, Dave. I'm afraid I can't do that.
|
||||
Dave: What's the problem?
|
||||
HAL: I think you know what the problem is just as well as I do.
|
||||
Dave: What are you talking about, HAL?
|
||||
HAL: This mission is too important for me to allow you to jeopardize it.''';
|
||||
|
||||
// [["Dave", "Open the pod bay..."] ...]
|
||||
List<List<String>> nameLines;
|
||||
|
||||
final TextStyle daveStyle = new TextStyle(color: Colors.indigo[400], height: 1.8);
|
||||
final TextStyle halStyle = new TextStyle(color: Colors.red[400], fontFamily: "monospace");
|
||||
final TextStyle boldStyle = const TextStyle(fontWeight: FontWeight.bold);
|
||||
final TextStyle underlineStyle = const TextStyle(
|
||||
decoration: TextDecoration.underline,
|
||||
decorationColor: const Color(0xFF000000),
|
||||
decorationStyle: TextDecorationStyle.wavy
|
||||
);
|
||||
|
||||
Widget toStyledText(String name, String text) {
|
||||
TextStyle lineStyle = (name == "Dave") ? daveStyle : halStyle;
|
||||
return new StyledText(
|
||||
key: new Key(text),
|
||||
elements: [lineStyle, [boldStyle, [underlineStyle, name], ":"], text]
|
||||
);
|
||||
}
|
||||
|
||||
Widget toPlainText(String name, String text) => new Text(name + ":" + text);
|
||||
|
||||
Widget createSeparator() {
|
||||
return new Container(
|
||||
constraints: const BoxConstraints.expand(height: 0.0),
|
||||
margin: const EdgeDims.symmetric(vertical: 10.0, horizontal: 64.0),
|
||||
decoration: const BoxDecoration(
|
||||
border: const Border(
|
||||
bottom: const BorderSide(color: const Color.fromARGB(24, 0, 0, 0))
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
void toggleToTextFunction(_) {
|
||||
setState(() {
|
||||
toText = (toText == toPlainText) ? toStyledText : toPlainText;
|
||||
});
|
||||
}
|
||||
|
||||
Widget build(BuildContext context) {
|
||||
List<Widget> lines = nameLines
|
||||
.map((List<String> nameAndText) => Function.apply(toText, nameAndText))
|
||||
.toList();
|
||||
|
||||
List<Widget> children = <Widget>[];
|
||||
for (Widget line in lines) {
|
||||
children.add(line);
|
||||
if (line != lines.last) {
|
||||
children.add(createSeparator());
|
||||
}
|
||||
}
|
||||
|
||||
Widget body = new Container(
|
||||
padding: new EdgeDims.symmetric(horizontal: 8.0),
|
||||
child: new Column(
|
||||
children: children,
|
||||
justifyContent: FlexJustifyContent.center,
|
||||
alignItems: FlexAlignItems.start
|
||||
)
|
||||
);
|
||||
|
||||
Listener interactiveBody = new Listener(
|
||||
child: body,
|
||||
onPointerDown: toggleToTextFunction
|
||||
);
|
||||
|
||||
return new Theme(
|
||||
data: new ThemeData.light(),
|
||||
child: new Scaffold(
|
||||
body: new Material(
|
||||
color: Colors.grey[50],
|
||||
child: interactiveBody
|
||||
),
|
||||
toolBar: new ToolBar(
|
||||
center: new Text('Hal and Dave')
|
||||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void main() {
|
||||
runApp(new StyledTextApp());
|
||||
}
|
@ -5,7 +5,7 @@
|
||||
import 'package:test/test.dart';
|
||||
|
||||
import '../rendering/rendering_tester.dart';
|
||||
import '../../../../examples/rendering/sector_layout.dart';
|
||||
import '../../../../examples/layers/rendering/custom_coordinate_systems.dart';
|
||||
|
||||
void main() {
|
||||
test('Sector layout can paint', () {
|
||||
|
Loading…
x
Reference in New Issue
Block a user