mirror of
https://github.com/flutter/flutter
synced 2024-10-14 04:02:56 +00:00
Switch from ui.tracing to dart:Developer Timeline
This change will let us remove the tracing interface from dart:ui and also makes these timeline events show up in Observatory.
This commit is contained in:
parent
e1b721f068
commit
c964a1f1f8
|
@ -2,43 +2,44 @@
|
|||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
import 'dart:developer';
|
||||
import 'dart:math' as math;
|
||||
import 'dart:ui' as ui;
|
||||
import 'dart:typed_data';
|
||||
import 'dart:ui' as ui;
|
||||
|
||||
Duration timeBase = null;
|
||||
|
||||
void beginFrame(Duration timeStamp) {
|
||||
ui.tracing.begin('beginFrame');
|
||||
if (timeBase == null)
|
||||
timeBase = timeStamp;
|
||||
double delta = (timeStamp - timeBase).inMicroseconds / Duration.MICROSECONDS_PER_MILLISECOND;
|
||||
Timeline.timeSync('beginFrame', () {
|
||||
if (timeBase == null)
|
||||
timeBase = timeStamp;
|
||||
double delta = (timeStamp - timeBase).inMicroseconds / Duration.MICROSECONDS_PER_MILLISECOND;
|
||||
|
||||
// paint
|
||||
ui.Rect paintBounds = ui.Point.origin & ui.window.size;
|
||||
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.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));
|
||||
ui.Picture picture = recorder.endRecording();
|
||||
// paint
|
||||
ui.Rect paintBounds = ui.Point.origin & ui.window.size;
|
||||
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.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));
|
||||
ui.Picture picture = recorder.endRecording();
|
||||
|
||||
// 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);
|
||||
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, paintBounds)
|
||||
..pop();
|
||||
ui.window.render(sceneBuilder.build());
|
||||
// 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);
|
||||
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, paintBounds)
|
||||
..pop();
|
||||
ui.window.render(sceneBuilder.build());
|
||||
});
|
||||
|
||||
ui.tracing.end('beginFrame');
|
||||
ui.window.scheduleFrame();
|
||||
}
|
||||
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
// found in the LICENSE file.
|
||||
|
||||
import 'dart:collection';
|
||||
import 'dart:developer';
|
||||
import 'dart:ui' as ui;
|
||||
|
||||
/// Slows down animations by this factor to help in development.
|
||||
|
@ -42,19 +43,9 @@ class Scheduler {
|
|||
|
||||
int get transientCallbackCount => _transientCallbacks.length;
|
||||
|
||||
/// Called by the engine to produce a new frame.
|
||||
///
|
||||
/// This function first calls all the callbacks registered by
|
||||
/// [requestAnimationFrame], then calls all the callbacks registered by
|
||||
/// [addPersistentFrameCallback], which typically drive the rendering pipeline,
|
||||
/// and finally calls the callbacks registered by [requestPostFrameCallback].
|
||||
void beginFrame(Duration rawTimeStamp) {
|
||||
assert(!_inFrame);
|
||||
_inFrame = true;
|
||||
Duration timeStamp = new Duration(
|
||||
microseconds: (rawTimeStamp.inMicroseconds / timeDilation).round());
|
||||
_haveScheduledVisualUpdate = false;
|
||||
|
||||
void _invokeAnimationCallbacks(Duration timeStamp) {
|
||||
Timeline.startSync('Animate');
|
||||
assert(_inFrame);
|
||||
Map<int, SchedulerCallback> callbacks = _transientCallbacks;
|
||||
_transientCallbacks = new Map<int, SchedulerCallback>();
|
||||
callbacks.forEach((int id, SchedulerCallback callback) {
|
||||
|
@ -62,6 +53,23 @@ class Scheduler {
|
|||
invokeCallback(callback, timeStamp);
|
||||
});
|
||||
_removedIds.clear();
|
||||
Timeline.finishSync();
|
||||
}
|
||||
|
||||
/// Called by the engine to produce a new frame.
|
||||
///
|
||||
/// This function first calls all the callbacks registered by
|
||||
/// [requestAnimationFrame], then calls all the callbacks registered by
|
||||
/// [addPersistentFrameCallback], which typically drive the rendering pipeline,
|
||||
/// and finally calls the callbacks registered by [requestPostFrameCallback].
|
||||
void beginFrame(Duration rawTimeStamp) {
|
||||
Timeline.startSync('Begin frame');
|
||||
assert(!_inFrame);
|
||||
_inFrame = true;
|
||||
Duration timeStamp = new Duration(
|
||||
microseconds: (rawTimeStamp.inMicroseconds / timeDilation).round());
|
||||
_haveScheduledVisualUpdate = false;
|
||||
_invokeAnimationCallbacks(timeStamp);
|
||||
|
||||
for (SchedulerCallback callback in _persistentCallbacks)
|
||||
invokeCallback(callback, timeStamp);
|
||||
|
@ -73,6 +81,7 @@ class Scheduler {
|
|||
invokeCallback(callback, timeStamp);
|
||||
|
||||
_inFrame = false;
|
||||
Timeline.finishSync();
|
||||
}
|
||||
|
||||
void invokeCallback(SchedulerCallback callback, Duration timeStamp) {
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
import 'dart:developer';
|
||||
import 'dart:math' as math;
|
||||
import 'dart:ui' as ui;
|
||||
|
||||
|
@ -610,7 +611,7 @@ abstract class RenderObject extends AbstractNode implements HitTestTarget {
|
|||
///
|
||||
/// See [FlutterBinding] for an example of how this function is used.
|
||||
static void flushLayout() {
|
||||
ui.tracing.begin('RenderObject.flushLayout');
|
||||
Timeline.startSync('Layout');
|
||||
_debugDoingLayout = true;
|
||||
try {
|
||||
// TODO(ianh): assert that we're not allowing previously dirty nodes to redirty themeselves
|
||||
|
@ -624,7 +625,7 @@ abstract class RenderObject extends AbstractNode implements HitTestTarget {
|
|||
}
|
||||
} finally {
|
||||
_debugDoingLayout = false;
|
||||
ui.tracing.end('RenderObject.flushLayout');
|
||||
Timeline.finishSync();
|
||||
}
|
||||
}
|
||||
void _layoutWithoutResize() {
|
||||
|
@ -962,7 +963,7 @@ abstract class RenderObject extends AbstractNode implements HitTestTarget {
|
|||
///
|
||||
/// See [FlutterBinding] for an example of how this function is used.
|
||||
static void flushPaint() {
|
||||
ui.tracing.begin('RenderObject.flushPaint');
|
||||
Timeline.startSync('Paint');
|
||||
_debugDoingPaint = true;
|
||||
try {
|
||||
List<RenderObject> dirtyNodes = _nodesNeedingPaint;
|
||||
|
@ -976,7 +977,7 @@ abstract class RenderObject extends AbstractNode implements HitTestTarget {
|
|||
assert(_nodesNeedingPaint.length == 0);
|
||||
} finally {
|
||||
_debugDoingPaint = false;
|
||||
ui.tracing.end('RenderObject.flushPaint');
|
||||
Timeline.finishSync();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
import 'dart:developer';
|
||||
import 'dart:ui' as ui;
|
||||
|
||||
import 'package:flutter/animation.dart';
|
||||
|
@ -116,7 +117,7 @@ class RenderView extends RenderObject with RenderObjectWithChildMixin<RenderBox>
|
|||
///
|
||||
/// Actually causes the output of the rendering pipeline to appear on screen.
|
||||
void compositeFrame() {
|
||||
ui.tracing.begin('RenderView.compositeFrame');
|
||||
Timeline.startSync('Composite');
|
||||
try {
|
||||
(layer as TransformLayer).transform = _logicalToDeviceTransform;
|
||||
Rect bounds = Point.origin & (size * ui.window.devicePixelRatio);
|
||||
|
@ -126,7 +127,7 @@ class RenderView extends RenderObject with RenderObjectWithChildMixin<RenderBox>
|
|||
ui.window.render(scene);
|
||||
scene.dispose();
|
||||
} finally {
|
||||
ui.tracing.end('RenderView.compositeFrame');
|
||||
Timeline.finishSync();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -2,6 +2,8 @@
|
|||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
|
||||
import 'dart:developer';
|
||||
|
||||
import 'package:flutter/animation.dart';
|
||||
import 'package:flutter/rendering.dart';
|
||||
|
||||
|
@ -47,6 +49,7 @@ class WidgetFlutterBinding extends FlutterBinding {
|
|||
void buildDirtyElements() {
|
||||
if (_dirtyElements.isEmpty)
|
||||
return;
|
||||
Timeline.startSync('Build');
|
||||
BuildableElement.lockState(() {
|
||||
_dirtyElements.sort((BuildableElement a, BuildableElement b) => a.depth - b.depth);
|
||||
int dirtyCount = _dirtyElements.length;
|
||||
|
@ -63,6 +66,7 @@ class WidgetFlutterBinding extends FlutterBinding {
|
|||
_dirtyElements.clear();
|
||||
}, building: true);
|
||||
assert(_dirtyElements.isEmpty);
|
||||
Timeline.finishSync();
|
||||
}
|
||||
|
||||
/// The [Element] that is at the root of the hierarchy (and which wraps the
|
||||
|
|
Loading…
Reference in a new issue