import 'dart:html'; import 'package:flutter/material.dart'; import 'package:grpc/grpc_web.dart'; import 'package:softplayer_web/api/grpc/accounts.dart'; class SignInForm extends StatefulWidget { const SignInForm({ super.key, required this.accountsGrpc, }); final AccountsGrpc accountsGrpc; @override State createState() => _SignInFormState(); } class _SignInFormState extends State { final _formKey = GlobalKey(); final usernameCtrl = TextEditingController(); final passwordCtrl = TextEditingController(); static const dialogName = "Sign In"; void submitForm() { // Validate returns true if the form is valid, or false otherwise. if (_formKey.currentState!.validate()) { final username = usernameCtrl.text; final password = passwordCtrl.text; widget.accountsGrpc.signIn(username, "", password).then((rs) { window.localStorage["token"] = rs.token; window.localStorage["uuid"] = rs.uuid; Navigator.of(context, rootNavigator: true).pop(); }).catchError((e) { GrpcError error = e; String msg; if (error.message != null) { msg = error.message!; } else { msg = error.toString(); } ScaffoldMessenger.of(context).showSnackBar(SnackBar( content: Text(msg), backgroundColor: Colors.red, showCloseIcon: true, behavior: SnackBarBehavior.floating, )); passwordCtrl.clear(); }); } } @override Widget build(BuildContext context) => AlertDialog( title: const Text(dialogName), content: SizedBox( width: 420, height: 140, child: Form( key: _formKey, child: Center( child: Column(children: [ TextFormField( controller: usernameCtrl, autofocus: true, decoration: const InputDecoration( hintText: "Enter your username or email", icon: Icon(Icons.account_circle), label: Text("Username"), ), cursorWidth: 1, cursorHeight: 18, cursorRadius: const Radius.circular(10), ), TextFormField( controller: passwordCtrl, obscureText: true, decoration: const InputDecoration( hintText: "Enter your password", icon: Icon(Icons.password), label: Text("Password")), cursorWidth: 1, cursorHeight: 18, cursorRadius: const Radius.circular(10), onFieldSubmitted: (v) { if (usernameCtrl.text.isEmpty) { FocusScope.of(context).nextFocus(); } else { submitForm(); } }, ), ])))), actions: [ TextButton( onPressed: () => Navigator.pop(context, 'Cancel'), child: const Text('Cancel'), ), TextButton( onPressed: submitForm, child: const Text('OK'), ), ], ); }