Skip to content
This repository has been archived by the owner on Jan 1, 2025. It is now read-only.

Commit

Permalink
feat: rendering windows
Browse files Browse the repository at this point in the history
  • Loading branch information
RossComputerGuy committed May 8, 2024
1 parent 0f8580b commit cce63e8
Show file tree
Hide file tree
Showing 9 changed files with 494 additions and 23 deletions.
42 changes: 41 additions & 1 deletion lib/logic/display.dart
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import 'dart:async';
import 'dart:collection';

import 'package:flutter/foundation.dart';
import 'package:flutter/services.dart';
Expand Down Expand Up @@ -35,10 +36,37 @@ class DisplayManager extends ChangeNotifier {
case 'map':
toplevel.sync();
break;
case 'commit':
toplevel.notifyListeners();
break;
}
break;
case 'notifyToplevel':
print(call.arguments);
final server = find(call.arguments['name']);
if (server == null) break;

final toplevel = server._toplevels.firstWhere((item) => item.id == call.arguments['id']);

switch (call.arguments['propName']) {
case 'appId':
toplevel.appId = call.arguments['propValue'];
toplevel.notifyListeners();
break;
case 'title':
toplevel.title = call.arguments['propValue'];
toplevel.notifyListeners();
break;
case 'texture':
toplevel.texture = call.arguments['propValue'];
toplevel.notifyListeners();
break;
case 'parent':
toplevel._parent = call.arguments['propValue'];
toplevel.notifyListeners();
break;
default:
throw MissingPluginException();
}
break;
default:
throw MissingPluginException();
Expand Down Expand Up @@ -86,6 +114,7 @@ class DisplayServer extends ChangeNotifier {
final String name;

List<DisplayServerToplevel> _toplevels = [];
UnmodifiableListView<DisplayServerToplevel> get toplevels => UnmodifiableListView(_toplevels);

Future<void> stop() async {
await DisplayManager.channel.invokeMethod('stop', name);
Expand All @@ -109,6 +138,7 @@ class DisplayServerToplevel extends ChangeNotifier {

String? appId;
String? title;
int? texture;

int? _parent;
DisplayServerToplevel? get parent {
Expand All @@ -124,7 +154,17 @@ class DisplayServerToplevel extends ChangeNotifier {

appId = data['appId'];
title = data['title'];
texture = data['texture'];
_parent = data['parent'];
notifyListeners();
}

Future<void> setSize(int width, int height) async {
await DisplayManager.channel.invokeMethod('setToplevelSize', <String, dynamic>{
'name': _server.name,
'id': id,
'width': width,
'height': height,
});
}
}
18 changes: 17 additions & 1 deletion lib/views/desktop.dart
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import '../logic/wallpaper.dart';

import '../widgets/system_layout.dart';
import '../widgets/system_navbar.dart';
import '../widgets/toplevel.dart';

class DesktopView extends StatefulWidget {
const DesktopView({
Expand Down Expand Up @@ -110,8 +111,23 @@ class _DesktopViewState extends State<DesktopView> {
image: getWallpaper(
path: (Breakpoints.small.isActive(context) ? widget.mobileWallpaper : widget.desktopWallpaper) ?? widget.wallpaper,
fallback: AssetImage('assets/wallpaper/${Breakpoints.small.isActive(context) ? 'mobile' : 'desktop'}/default.jpg'),
),
)
),
child: _displayServer != null
? ChangeNotifierProvider(
create: (_) => _displayServer!,
child: Consumer<DisplayServer>(
builder: (context, server, _) =>
Stack(
children: server.toplevels.map(
(toplevel) =>
Toplevel(
toplevel: toplevel,
)
).toList(),
),
),
) : null,
),
bottomNavigationBar: Breakpoints.small.isActive(context)
? SystemNavbar() : null,
Expand Down
48 changes: 48 additions & 0 deletions lib/widgets/toplevel.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
import 'package:flutter/scheduler.dart';
import 'package:libtokyo_flutter/libtokyo.dart' hide ColorScheme;
import 'package:libtokyo/libtokyo.dart' hide TokyoApp;
import 'package:provider/provider.dart';

import '../logic/display.dart';

class Toplevel extends StatefulWidget {
const Toplevel({
super.key,
required this.toplevel,
});

final DisplayServerToplevel toplevel;

@override
State<Toplevel> createState() => _ToplevelState();
}

class _ToplevelState extends State<Toplevel> {
GlobalKey key = GlobalKey();

@override
void initState() {
super.initState();

SchedulerBinding.instance.addPostFrameCallback((_) {
if (key.currentContext != null && widget.toplevel.texture != null) {
final box = key.currentContext!.findRenderObject() as RenderBox;
widget.toplevel.setSize(box.size.width.toInt(), box.size.height.toInt());
}
});
}

@override
Widget build(BuildContext context) =>
ChangeNotifierProvider(
key: key,
create: (_) => widget.toplevel,
child: Consumer<DisplayServerToplevel>(
builder: (context, toplevel, _) =>
toplevel.texture == null
? SizedBox() : Texture(
textureId: toplevel.texture!,
),
),
);
}
1 change: 1 addition & 0 deletions linux/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -121,6 +121,7 @@ add_executable(${BINARY_NAME}
"channels/display/backend/dummy.c"
"channels/display/backend/wayland.c"
"channels/display/backend.c"
"channels/display/pixel-format.c"
"channels/display/texture.c"
"channels/display/toplevel.c"
"channels/display.c"
Expand Down
28 changes: 28 additions & 0 deletions linux/channels/display.c
Original file line number Diff line number Diff line change
Expand Up @@ -200,7 +200,35 @@ static void method_call_handler(FlMethodChannel* channel, FlMethodCall* method_c
fl_value_set(value, fl_value_new_string("parent"), fl_value_new_null());
}

if (toplevel->texture != NULL) {
fl_value_set(value, fl_value_new_string("texture"), fl_value_new_int((uintptr_t)FL_TEXTURE(toplevel->texture)));
} else {
fl_value_set(value, fl_value_new_string("texture"), fl_value_new_null());
}

response = FL_METHOD_RESPONSE(fl_method_success_response_new(value));
} else if (strcmp(fl_method_call_get_name(method_call), "setToplevelSize") == 0) {
FlValue* args = fl_method_call_get_args(method_call);
const gchar* name = fl_value_get_string(fl_value_lookup_string(args, "name"));
int id = fl_value_get_int(fl_value_lookup_string(args, "id"));

if (!g_hash_table_contains(self->displays, name)) {
fl_method_call_respond_error(method_call, "Linux", "Display server does not exist", NULL, NULL);
return;
}

DisplayChannelDisplay* disp = g_hash_table_lookup(self->displays, name);

if (!g_hash_table_contains(disp->toplevels, &id)) {
fl_method_call_respond_error(method_call, "Linux", "Toplevel does not exist", NULL, NULL);
return;
}

DisplayChannelToplevel* toplevel = g_hash_table_lookup(disp->toplevels, &id);
g_assert(toplevel->id == id);

wlr_xdg_toplevel_set_size(toplevel->xdg, fl_value_get_int(fl_value_lookup_string(args, "width")), fl_value_get_int(fl_value_lookup_string(args, "height")));
response = FL_METHOD_RESPONSE(fl_method_success_response_new(NULL));
} else {
response = FL_METHOD_RESPONSE(fl_method_not_implemented_response_new());
}
Expand Down
Loading

0 comments on commit cce63e8

Please sign in to comment.