-
Notifications
You must be signed in to change notification settings - Fork 324
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
0dfdc8e
commit 2308099
Showing
11 changed files
with
470 additions
and
55 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,67 @@ | ||
// Copyright 2023 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. | ||
|
||
// ignore_for_file: unused_local_variable | ||
|
||
import 'dart:async'; | ||
|
||
import 'package:devtools_app_shared/service.dart'; | ||
import 'package:devtools_app_shared/service_extensions.dart' as extensions; | ||
import 'package:devtools_shared/service.dart'; | ||
import 'package:flutter/foundation.dart'; | ||
import 'package:vm_service/vm_service.dart'; | ||
|
||
void main() async { | ||
final serviceManager = ServiceManager(); | ||
|
||
// Example: use [connectedState] to listen for connection updates. | ||
serviceManager.connectedState.addListener(() { | ||
if (serviceManager.connectedState.value.connected) { | ||
print('Manager connected to VM service'); | ||
} else { | ||
print('Manager not connected to VM service'); | ||
} | ||
}); | ||
|
||
// Example: establish a vm service connection. | ||
// To get a [VmService] object from a vm service URI, consider importing | ||
// `package:devtools_shared/service.dart` from `package:devtools_shared`. | ||
const someVmServiceUri = 'http://127.0.0.1:60851/fH-kAEXc7MQ=/'; | ||
final finishedCompleter = Completer<void>(); | ||
final vmService = await connect<VmService>( | ||
uri: Uri.parse(someVmServiceUri), | ||
finishedCompleter: finishedCompleter, | ||
createService: ({ | ||
// ignore: avoid-dynamic, code needs to match API from VmService. | ||
required Stream<dynamic> /*String|List<int>*/ inStream, | ||
required void Function(String message) writeMessage, | ||
required Uri connectedUri, | ||
}) { | ||
return VmService(inStream, writeMessage); | ||
}, | ||
); | ||
|
||
await serviceManager.vmServiceOpened( | ||
vmService, | ||
onClosed: finishedCompleter.future, | ||
); | ||
|
||
/// Example: Get a service extension state. | ||
final ValueListenable<ServiceExtensionState> performanceOverlayEnabled = | ||
serviceManager.serviceExtensionManager.getServiceExtensionState( | ||
extensions.performanceOverlay.extension, | ||
); | ||
|
||
// Example: Set a service extension state. | ||
await serviceManager.serviceExtensionManager.setServiceExtensionState( | ||
extensions.performanceOverlay.extension, | ||
enabled: true, | ||
value: true, | ||
); | ||
|
||
// Example: Access isolates. | ||
final myIsolate = serviceManager.isolateManager.mainIsolate.value; | ||
|
||
// Etc. | ||
} |
31 changes: 31 additions & 0 deletions
31
packages/devtools_app_shared/example/ui/common_example.dart
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,31 @@ | ||
// Copyright 2023 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:devtools_app_shared/ui.dart' as devtools_shared_ui; | ||
import 'package:flutter/material.dart'; | ||
|
||
class ExampleWidget extends StatelessWidget { | ||
const ExampleWidget({super.key}); | ||
|
||
@override | ||
Widget build(BuildContext context) { | ||
return devtools_shared_ui.RoundedOutlinedBorder( | ||
child: Column( | ||
children: [ | ||
const devtools_shared_ui.AreaPaneHeader( | ||
roundedTopBorder: false, | ||
includeTopBorder: false, | ||
title: Text('This is a section header'), | ||
), | ||
Expanded( | ||
child: Text( | ||
'Foo', | ||
style: Theme.of(context).subtleTextStyle, // Shared style | ||
), | ||
), | ||
], | ||
), | ||
); | ||
} | ||
} |
38 changes: 38 additions & 0 deletions
38
packages/devtools_app_shared/example/ui/dialog_example.dart
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,38 @@ | ||
// Copyright 2023 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:devtools_app_shared/ui.dart' as devtools_shared_ui; | ||
import 'package:flutter/material.dart'; | ||
|
||
/// Example of using a [DevToolsDialog] widget from | ||
/// 'package:devtools_app_shared/ui.dart'. | ||
class MyDialog extends StatelessWidget { | ||
const MyDialog({super.key}); | ||
|
||
@override | ||
Widget build(BuildContext context) { | ||
return devtools_shared_ui.DevToolsDialog( | ||
title: const devtools_shared_ui.DialogTitleText('My Cool Dialog'), | ||
content: const Column( | ||
mainAxisSize: MainAxisSize.min, | ||
crossAxisAlignment: CrossAxisAlignment.start, | ||
children: [ | ||
Text('Here is the body of my dialog.'), | ||
SizedBox(height: devtools_shared_ui.denseSpacing), | ||
Text('It communicates something important'), | ||
], | ||
), | ||
actions: [ | ||
devtools_shared_ui.DialogTextButton( | ||
onPressed: () { | ||
// Do someting and then remove the dialog. | ||
Navigator.of(context).pop(devtools_shared_ui.dialogDefaultContext); | ||
}, | ||
child: const Text('DO SOMETHING'), | ||
), | ||
const devtools_shared_ui.DialogCancelButton(), | ||
], | ||
); | ||
} | ||
} |
73 changes: 73 additions & 0 deletions
73
packages/devtools_app_shared/example/ui/split_example.dart
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,73 @@ | ||
// Copyright 2023 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:devtools_app_shared/ui.dart' as devtools_shared_ui; | ||
import 'package:flutter/material.dart'; | ||
|
||
/// Example of using the [Split] widget from | ||
/// 'package:devtools_app_shared/ui.dart' with two children laid across a | ||
/// horizontal axis. | ||
/// | ||
/// This example does not specify the [Split.splitters] parameter, so a | ||
/// default splitter is used. | ||
class SplitExample extends StatelessWidget { | ||
const SplitExample({super.key}); | ||
|
||
@override | ||
Widget build(BuildContext context) { | ||
return devtools_shared_ui.Split( | ||
axis: Axis.horizontal, | ||
initialFractions: const [0.3, 0.7], | ||
minSizes: const [50.0, 100.0], | ||
children: const [ | ||
Text('Left side'), | ||
Text('Right side'), | ||
], | ||
); | ||
} | ||
} | ||
|
||
/// Example of using the [Split] widget from | ||
/// 'package:devtools_app_shared/ui.dart' with three children laid across a | ||
/// vertical axis. | ||
/// | ||
/// This example uses custom splitters. | ||
class MultiSplitExample extends StatelessWidget { | ||
const MultiSplitExample({super.key}); | ||
|
||
@override | ||
Widget build(BuildContext context) { | ||
return devtools_shared_ui.Split( | ||
axis: Axis.vertical, | ||
initialFractions: const [0.3, 0.3, 0.4], | ||
minSizes: const [50.0, 50.0, 100.0], | ||
splitters: const [ | ||
CustomSplitter(), | ||
CustomSplitter(), | ||
], | ||
children: const [ | ||
Text('Top'), | ||
Text('Middle'), | ||
Text('Bottom'), | ||
], | ||
); | ||
} | ||
} | ||
|
||
class CustomSplitter extends StatelessWidget implements PreferredSizeWidget { | ||
const CustomSplitter({super.key}); | ||
|
||
static const _size = 50.0; | ||
|
||
@override | ||
Widget build(BuildContext context) { | ||
return const SizedBox( | ||
height: _size, | ||
child: Icon(Icons.front_hand), | ||
); | ||
} | ||
|
||
@override | ||
Size get preferredSize => const Size.fromHeight(_size); | ||
} |
91 changes: 91 additions & 0 deletions
91
packages/devtools_app_shared/example/utils/auto_dispose_example.dart
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,91 @@ | ||
// Copyright 2023 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:devtools_app_shared/utils.dart'; | ||
import 'package:flutter/widgets.dart'; | ||
|
||
/// This is an example of a [StatefulWidget] that uses the [AutoDisposeMixin] on | ||
/// its state. | ||
/// | ||
/// [AutoDisposeMixin] is exposed by 'package:devtools_app_shared/utils.dart'. | ||
class MyStatefulWidget extends StatefulWidget { | ||
const MyStatefulWidget({super.key, required this.someNotifier}); | ||
|
||
final ValueNotifier<String> someNotifier; | ||
|
||
@override | ||
State<MyStatefulWidget> createState() => _MyStatefulWidgetState(); | ||
} | ||
|
||
// This is a State class that mixes in [AutoDisoposeMixin]. | ||
class _MyStatefulWidgetState extends State<MyStatefulWidget> | ||
with AutoDisposeMixin { | ||
late final MyController controller; | ||
late String foo; | ||
|
||
@override | ||
void initState() { | ||
super.initState(); | ||
_init(); | ||
} | ||
|
||
@override | ||
void didUpdateWidget(MyStatefulWidget oldWidget) { | ||
super.didUpdateWidget(oldWidget); | ||
if (oldWidget.someNotifier != widget.someNotifier) { | ||
_init(); | ||
} | ||
} | ||
|
||
@override | ||
void dispose() { | ||
controller.dispose(); | ||
super.dispose(); | ||
} | ||
|
||
void _init() { | ||
// This kicks off initialization in [controller] which uses the | ||
// [AutoDisposeControllerMixin]. | ||
controller = MyController(widget.someNotifier)..init(); | ||
|
||
// Cancel any existing listeners in situations like this where we could be | ||
// "re-initializing" in [didUpdateWidget]. | ||
cancelListeners(); | ||
|
||
foo = widget.someNotifier.value; | ||
|
||
// Adds a listener to [widget.someNotifier] that will be automatically | ||
// disposed as part of this stateful widget lifecycle. | ||
addAutoDisposeListener(widget.someNotifier, () { | ||
setState(() { | ||
foo = widget.someNotifier.value; | ||
}); | ||
}); | ||
} | ||
|
||
@override | ||
Widget build(BuildContext context) { | ||
return Text(foo); | ||
} | ||
} | ||
|
||
/// This is an example of a controller that uses the | ||
/// [AutoDisposeControllerMixin] exposed by | ||
/// 'package:devtools_app_shared/utils.dart'. | ||
/// | ||
/// When [dispose] is called on this controller, any listeners or stream | ||
/// subscriptions added using the [AutoDisposeControllerMixin] will be disposed | ||
/// or canceled. | ||
class MyController extends DisposableController | ||
with AutoDisposeControllerMixin { | ||
MyController(this.notifier); | ||
|
||
final ValueNotifier<String> notifier; | ||
|
||
void init() { | ||
addAutoDisposeListener(notifier, () { | ||
// Do something. | ||
}); | ||
} | ||
} |
30 changes: 30 additions & 0 deletions
30
packages/devtools_app_shared/example/utils/globals_example.dart
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
// Copyright 2023 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:devtools_app_shared/utils.dart'; | ||
|
||
void main() { | ||
setAndAccessGlobal(); | ||
} | ||
|
||
/// This method demonstrates setting and accessing globals, which is | ||
/// functionality exposed by 'package:devtools_app_shared/utils.dart'. | ||
void setAndAccessGlobal() { | ||
// Creates a globally accessible variable (`globals[ServiceManager]`); | ||
setGlobal(MyCoolClass, MyCoolClass()); | ||
// Access the variable directory from [globals]. | ||
final coolClassFromGlobals = globals[MyCoolClass] as MyCoolClass; | ||
coolClassFromGlobals.foo(); | ||
|
||
// OR (recommended) access the global from a top level getter. | ||
coolClass.foo(); | ||
} | ||
|
||
MyCoolClass get coolClass => globals[MyCoolClass] as MyCoolClass; | ||
|
||
class MyCoolClass { | ||
void foo() { | ||
print('foo'); | ||
} | ||
} |
35 changes: 35 additions & 0 deletions
35
packages/devtools_app_shared/example/utils/list_example.dart
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,35 @@ | ||
// Copyright 2023 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:devtools_app_shared/utils.dart'; | ||
import 'package:flutter/widgets.dart'; | ||
|
||
void main() { | ||
useListValueNotifier(); | ||
} | ||
|
||
/// This is an example of using the [ListValueNotifier] that is exposed from | ||
/// 'package:devtools_app_shared/utils.dart'. | ||
/// | ||
/// A [ListValueNotifier] will holds a list object, and will notify listeners | ||
/// on modifications to the list. | ||
/// | ||
/// This should be used in place of ValueNotifier<List<Object>> when list | ||
/// updates should notify listeners, and not just changing the notifier's value | ||
/// with a new list. | ||
void useListValueNotifier() { | ||
final myListNotifier = ListValueNotifier<int>([1, 2, 3]); | ||
|
||
// These calls will notify all listeners of [myListNotifier]. | ||
myListNotifier.add(4); | ||
myListNotifier.removeAt(0); | ||
// ... | ||
|
||
// As opposed to: | ||
final myValueNotifierWithAList = ValueNotifier<List<int>>([1, 2, 3]); | ||
|
||
// These calls will not notify listeners of [myValueNotifierWithAList] | ||
myValueNotifierWithAList.value.add(4); | ||
myValueNotifierWithAList.value.removeAt(0); | ||
} |
Oops, something went wrong.