betrayal 1.3.7 copy "betrayal: ^1.3.7" to clipboard
betrayal: ^1.3.7 copied to clipboard

PlatformWindows

A plugin to setup custom system tray icons through composable widgets.

example/README.md

How to use? #

To add an icon to your app, simply use the TrayIconWidget.

import 'package:betrayal/betrayal.dart';
import 'package:flutter/material.dart';

void main() {
  runApp(const MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) => MaterialApp(
    home: Scaffold(
      appBar: AppBar(
        title: const Text("Look at the system tray 👀")
      ),
      body: Center(
        child: TrayIconWidget(
          winIcon: WinIcon.application,
          tooltip: "Here I am!"
          child: FlutterLogo()
        )
      )
    )
  );
}

Check out the widgets api example to learn more about this approach and have a look at widgets_api for a small demo app that uses it.

skeleton_example is an abridged version of the Flutter skeleton template that persists an icon over multiple pages.

Ok, but I want to work with TrayIcons directly, please! #

Sure, you can use the imperative api to create and control TrayIcons directly.

final icon = TrayIcon();

await icon.setTooltip("🎭");
await icon.setImage(asset: "assets/dart.ico"));
await icon.show();

Just make sure to dispose of it and free its resources once you're done.

icon.dispose();

If you don't feel like managing an icon, you can still use a TrayIconWidget and get its underlying TrayIcon by calling TrayIcon.of(context).

@override
Widget build(BuildContext context) {
  return TrayIconWidget(
    child: 
      // .............
      Builder(
        builder: (BuildContext context) {
          // The BuildContext must be from a child of `TrayIconWidget`,
          // otherwise the icon may not be found.
          return IconButton(
            onPressed: () => TrayIcon.of(context).setTooltip("🙇‍♂️"),
            icon: Icon(Icons.add)
          );
        }
      )
  );
}

Check out the select_image example for a more complex app that uses the imperative api.

If you want to see how Betrayal can work with multiple icons and how to generate images at runtime through Canvas please look at the add_many

Is there a way to get rid of the log messages? #

Yeah, you can change the log level, as seen in the widgets_api example.

// sets `hierarchicalLoggingEnabled`
// from the `logging` package to `true`
BetrayalLogConfig.allowIndividualLevels();

// disables logging only for *betrayal*
BetrayalLogConfig.level = "OFF";

To learn more about logging in betrayal have a look at the implementation in logging.dart.

Why is there no built-in method for opening a context menu? #

Because it's unrelated from displaying and managing a tray icon.

There are already great plugins for doing so, such as leanflutter/contextual_menu!
In the select_image example you can see that it plays well with betrayal

Why are my icons still there after restarting the app? #

There is no hook for plugin devs to detect a hot restart. The best we can do is to reset state once the restarted app starts to interact with the library again and to provide an optional reset method users can call before runApp runs.

// hot restart is only possible in debug mode
if (kDebugMode) TrayIcon.clearAll();
runApp(const MyApp());
4
likes
130
pub points
38%
popularity

Publisher

verified publisherbent.party

A plugin to setup custom system tray icons through composable widgets.

Homepage
Repository (GitHub)
View/report issues

Documentation

Documentation
API reference

License

MIT (LICENSE)

Dependencies

flutter, logging, path, synchronized

More

Packages that depend on betrayal