import 'dart:html'; import 'package:flutter/foundation.dart'; import 'package:flutter/material.dart'; import 'package:grpc/grpc_web.dart'; import 'package:softplayer_web/api/grpc/accounts.dart'; import 'package:softplayer_web/components/create_env_form.dart'; import 'package:softplayer_web/components/environments.dart'; import 'package:softplayer_web/components/login_form.dart'; void main() async { const String backendURL = String.fromEnvironment( 'SOFTPLAYER_BACKEND_URL', defaultValue: 'https://softplayer-backend.badhouseplants.net:8080', ); GrpcWebClientChannel grpcChannel = GrpcWebClientChannel.xhr(Uri.parse(backendURL)); runApp(MyApp(channel: grpcChannel)); } class MyApp extends StatelessWidget { MyApp({super.key, required this.channel}); final GrpcWebClientChannel channel; late final AccountsGrpc accountsGrpc = AccountsGrpc(channel: channel); @override Widget build(BuildContext context) { accountsGrpc.init(); return MaterialApp( debugShowCheckedModeBanner: false, title: 'Softplayer', home: RootWidget(channel: channel), theme: ThemeData( colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple), useMaterial3: true, ), ); } } class RootWidget extends StatefulWidget { final GrpcWebClientChannel channel; RootWidget({super.key, required this.channel}); late final AccountsGrpc accountsGrpc = AccountsGrpc(channel: channel); @override @override State createState() => _StateRootWidget(); } class _StateRootWidget extends State { refresh() { setState(() {}); } bool isSignedIn() { return window.localStorage.containsKey("token"); } @override Widget build(BuildContext context) { if (!isSignedIn()) { return Scaffold( body: Container( width: double.infinity, height: double.infinity, decoration: const BoxDecoration( image: DecorationImage( image: AssetImage("assets/login_background.jpg"), fit: BoxFit.cover, ), ), child: LoginForm( grpcChannel: widget.channel, notifyParent: refresh, ), )); } else { EnvirnomentList envList = EnvirnomentList(channel: widget.channel); return Scaffold( body: envList, appBar: AppBar( title: const Text("Softplayer"), actions: [ TextButton( onPressed: () { window.localStorage.remove("token"); window.localStorage.remove("uuid"); refresh(); }, child: const Text("sign out")) ], ), floatingActionButton: FloatingActionButton( child: const Icon(Icons.add), onPressed: () => showDialog( context: context, builder: (context) => CreateEnvForm(widget.channel), ), ), ); } } }