Compare commits

...

19 Commits

Author SHA1 Message Date
Matej Bačo
a2314c8920
Merge pull request #7 from appwrite/fix-flutter-endpoint
Fix flutter endpoint
2025-08-11 12:30:53 +02:00
Khushboo Verma
f2caf6f028 Fix flutter endpoint 2025-08-11 15:52:36 +05:30
Matej Bačo
8aa2aec2d6
Merge pull request #6 from appwrite/fix-build-script
Simplify flutter starter by removing build script
2025-08-11 10:55:44 +02:00
Khushboo Verma
8e2361b825 Update placeholders 2025-08-08 19:34:58 +05:30
Khushboo Verma
9453e45ced Simplify flutter starter 2025-08-08 19:27:22 +05:30
Khushboo Verma
c0cae9fcb7 If no params passed, default to web 2025-08-08 18:29:14 +05:30
Khushboo Verma
fcc2384a5e Fix build script for flutter 2025-08-08 17:18:11 +05:30
Matej Bačo
774da7ad6c Avoid prepare sh 2025-05-20 11:34:27 +00:00
Matej Bačo
2d645274a9
Merge pull request #3 from appwrite/fix-cloud-build
Fix: Prepare for Cloud build
2025-05-20 10:39:32 +02:00
Matej Bačo
b3d927662c PR review improv 2025-05-20 08:39:21 +00:00
Matej Bačo
190cbcc0ea Prepare for Cloud build 2025-05-20 08:06:40 +00:00
Darshan
dfec3fd9e2 update: build.sh for manual runs. 2025-04-28 18:54:44 +05:30
Darshan
c23ce74bc4 fix: layout issues and add a nice spinner. 2025-04-28 18:47:10 +05:30
Matej Bačo
3ab962f00a
Fix build command 2025-03-12 10:53:22 +01:00
Matej Bačo
7174cea597
Add build command 2025-03-12 10:47:07 +01:00
Matej Bačo
0e067feb31 Downgrade dart 2025-03-11 13:28:51 +00:00
Matej Bačo
1ae5710a63
Merge pull request #2 from appwrite/env-support
Env support
2025-03-11 14:22:39 +01:00
Darshan
e314312082
Merge pull request #1 from appwrite/feat-starter-kit
Feat: Starter Kit for Flutter
2025-02-25 11:29:28 +05:30
Darshan
ff0c12e23d address comments. 2025-02-25 09:24:01 +05:30
17 changed files with 344 additions and 253 deletions

View File

@ -1,3 +0,0 @@
APPWRITE_PROJECT_ID=
APPWRITE_PROJECT_NAME=
APPWRITE_PUBLIC_ENDPOINT=

View File

@ -24,16 +24,39 @@ Alternatively, open the repository URL in `Android Studio` to clone it directly.
## 🛠️ Development Guide
1. **Configure Appwrite**
Navigate to `lib/data/repository/appwrite_repository.dart` and update the values to match your
Appwrite project credentials.
Open `lib/config/environment.dart` and update the values with your Appwrite project credentials:
```dart
class Environment {
static const String appwritePublicEndpoint = '[appwritePublicEndpoint]';
static const String appwriteProjectId = '[appwriteProjectId]';
static const String appwriteProjectName = '[appwriteProjectName]';
}
```
2. **Customize as Needed**
Modify the starter kit to suit your app's requirements. Adjust UI, features, or backend
integrations as per your needs.
3. **Run the App**
Select a target device (emulator or a connected physical device) in `Android Studio`, and
click **Run** to start the app.
Select a target device and run the app:
```bash
# List available devices
flutter devices
# Run on a specific device (replace 'device-id' with actual device)
flutter run -d device-id
# Examples:
flutter run -d chrome # Web
flutter run -d "iPhone 15" # iOS Simulator
flutter run -d emulator-5554 # Android Emulator
flutter run -d macos # macOS Desktop
```
**Build for Web:**
```bash
flutter build web
```
---
@ -46,5 +69,5 @@ production : https://docs.flutter.dev/deployment
## 💡 Additional Notes
- This starter project is designed to streamline your Android development with Appwrite.
- This starter project is designed to streamline your Flutter development with Appwrite.
- Refer to the [Appwrite Documentation](https://appwrite.io/docs) for detailed integration guidance.

19
lib/app.dart Normal file
View File

@ -0,0 +1,19 @@
import 'package:appwrite_flutter_starter_kit/home.dart';
import 'package:flutter/material.dart';
class AppwriteApp extends StatelessWidget {
const AppwriteApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Appwrite StarterKit',
debugShowCheckedModeBanner: false,
theme: ThemeData(
useMaterial3: true,
colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
),
home: const AppwriteStarterKit(),
);
}
}

View File

@ -0,0 +1,5 @@
class Environment {
static const String appwritePublicEndpoint = '[appwritePublicEndpoint]';
static const String appwriteProjectId = '[appwriteProjectId]';
static const String appwriteProjectName = '[appwriteProjectName]';
}

View File

@ -2,15 +2,16 @@ import 'package:intl/intl.dart';
import 'package:appwrite/appwrite.dart';
import 'package:appwrite_flutter_starter_kit/data/models/log.dart';
import 'package:appwrite_flutter_starter_kit/data/models/project_info.dart';
import 'package:appwrite_flutter_starter_kit/config/environment.dart';
/// A repository responsible for handling network interactions with the Appwrite server.
///
/// It provides a helper method to ping the server.
class AppwriteRepository {
static const String pingPath = "/ping";
static const String appwriteProjectId = String.fromEnvironment('APPWRITE_PROJECT_ID');
static const String appwriteProjectName = String.fromEnvironment('APPWRITE_PROJECT_NAME');
static const String appwritePublicEndpoint = String.fromEnvironment('APPWRITE_PUBLIC_ENDPOINT');
static const String appwriteProjectId = Environment.appwriteProjectId;
static const String appwriteProjectName = Environment.appwriteProjectName;
static const String appwritePublicEndpoint = Environment.appwritePublicEndpoint;
final Client _client = Client()
.setProject(appwriteProjectId)

80
lib/home.dart Normal file
View File

@ -0,0 +1,80 @@
import 'package:appwrite_flutter_starter_kit/data/models/log.dart';
import 'package:appwrite_flutter_starter_kit/data/models/status.dart';
import 'package:appwrite_flutter_starter_kit/data/repository/appwrite_repository.dart';
import 'package:appwrite_flutter_starter_kit/ui/components/checkered_background.dart';
import 'package:appwrite_flutter_starter_kit/ui/components/collapsible_bottomsheet.dart';
import 'package:appwrite_flutter_starter_kit/ui/components/connection_status_view.dart';
import 'package:appwrite_flutter_starter_kit/ui/components/getting_started_cards.dart';
import 'package:appwrite_flutter_starter_kit/ui/components/top_platform_view.dart';
import 'package:appwrite_flutter_starter_kit/utils/extensions/build_context.dart';
import 'package:flutter/material.dart';
class AppwriteStarterKit extends StatefulWidget {
const AppwriteStarterKit({super.key});
@override
State<AppwriteStarterKit> createState() => _AppwriteStarterKit();
}
class _AppwriteStarterKit extends State<AppwriteStarterKit> {
final List<Log> _logs = [];
Status _status = Status.idle;
final AppwriteRepository _repository = AppwriteRepository();
@override
Widget build(BuildContext context) {
return Scaffold(
body: CheckeredBackground(
child: SafeArea(
minimum: EdgeInsets.only(
top: context.isExtraWideScreen
? 156
: context.isLargeScreen
? 24
: 32),
child: Stack(
children: [
SingleChildScrollView(
child: Column(
spacing: 16,
children: [
TopPlatformView(status: _status),
ConnectionStatusView(
status: _status,
onButtonClick: () async {
setState(() => _status = Status.loading);
final log = await _repository.ping();
_logs.add(log);
await Future.delayed(
const Duration(milliseconds: 1250),
);
setState(
() => _status =
(200 <= log.status && log.status <= 399)
? Status.success
: Status.error,
);
},
),
GettingStartedCards()
],
),
),
// bottomsheet
Align(
alignment: Alignment.bottomCenter,
child: CollapsibleBottomSheet(
logs: _logs,
projectInfo: _repository.getProjectInfo(),
),
),
],
),
),
),
);
}
}

View File

@ -1,98 +1,8 @@
import 'package:appwrite_flutter_starter_kit/data/models/log.dart';
import 'package:appwrite_flutter_starter_kit/data/models/status.dart';
import 'package:appwrite_flutter_starter_kit/data/repository/appwrite_repository.dart';
import 'package:appwrite_flutter_starter_kit/ui/components/checkered_background.dart';
import 'package:appwrite_flutter_starter_kit/ui/components/collapsible_bottomsheet.dart';
import 'package:appwrite_flutter_starter_kit/ui/components/connection_status_view.dart';
import 'package:appwrite_flutter_starter_kit/ui/components/getting_started_cards.dart';
import 'package:appwrite_flutter_starter_kit/ui/components/top_platform_view.dart';
import 'package:appwrite_flutter_starter_kit/app.dart';
import 'package:appwrite_flutter_starter_kit/utils/app_initializer.dart';
import 'package:appwrite_flutter_starter_kit/utils/extensions/build_context.dart';
import 'package:flutter/material.dart';
void main() async {
await AppInitializer.initialize();
runApp(AppwriteApp());
}
class AppwriteApp extends StatelessWidget {
const AppwriteApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Appwrite StarterKit',
debugShowCheckedModeBanner: false,
theme: ThemeData(
useMaterial3: true,
colorScheme: ColorScheme.fromSeed(seedColor: Colors.deepPurple),
),
home: const AppwriteStarterKit(),
);
}
}
class AppwriteStarterKit extends StatefulWidget {
const AppwriteStarterKit({super.key});
@override
State<AppwriteStarterKit> createState() => _AppwriteStarterKit();
}
class _AppwriteStarterKit extends State<AppwriteStarterKit> {
final List<Log> _logs = [];
Status _status = Status.idle;
final AppwriteRepository _repository = AppwriteRepository();
@override
Widget build(BuildContext context) {
return Scaffold(
body: CheckeredBackground(
child: SafeArea(
minimum: EdgeInsets.only(top: context.isLargeScreen ? 24 : 16),
child: Stack(
children: [
SingleChildScrollView(
child: Column(
spacing: 16,
children: [
TopPlatformView(status: _status),
ConnectionStatusView(
status: _status,
onButtonClick: () async {
setState(() => _status = Status.loading);
final log = await _repository.ping();
_logs.add(log);
await Future.delayed(
const Duration(milliseconds: 1250),
);
setState(
() => _status =
(200 <= log.status && log.status <= 399)
? Status.success
: Status.error,
);
},
),
GettingStartedCards()
],
),
),
// bottomsheet
Align(
alignment: Alignment.bottomCenter,
child: CollapsibleBottomSheet(
logs: _logs,
projectInfo: _repository.getProjectInfo(),
),
),
],
),
),
),
);
}
}

View File

@ -491,7 +491,7 @@ class LogsTableRow extends StatelessWidget {
child: MouseRegion(
cursor: SystemMouseCursors.click,
child: Text(
response.substring(0, 50),
response.length >= 50 ? response.substring(0, 50) : response,
maxLines: 1,
overflow: TextOverflow.ellipsis,
style: const TextStyle(

View File

@ -15,7 +15,7 @@ class ConnectionLine extends StatelessWidget {
return SizedBox(
width: context.widthFactor(
mobileFactor: 0.25,
largeScreenFactor: 0.15,
largeScreenFactor: 0.1,
),
child: Flex(
direction: Axis.horizontal,

View File

@ -1,3 +1,4 @@
import 'package:appwrite_flutter_starter_kit/ui/components/responsive_layout.dart';
import 'package:appwrite_flutter_starter_kit/utils/extensions/build_context.dart';
import 'package:flutter/material.dart';
import 'package:url_launcher/url_launcher.dart';
@ -8,39 +9,85 @@ class GettingStartedCards extends StatelessWidget {
@override
Widget build(BuildContext context) {
return Padding(
padding: const EdgeInsets.symmetric(horizontal: 16.0, vertical: 16.0),
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
GeneralInfoCard(
title: "Edit your app",
link: null,
subtitle: const HighlightedText(),
),
GeneralInfoCard(
title: "Head to Appwrite Cloud",
link: "https://cloud.appwrite.io",
subtitle: const Text(
"Start managing your project from the Appwrite console",
style: TextStyle(
fontSize: 14,
color: Color(0xFF56565C),
return ResponsiveLayout(
smallDeviceLayout: Padding(
padding: const EdgeInsets.symmetric(horizontal: 16.0, vertical: 16.0),
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
GeneralInfoCard(
title: "Edit your app",
link: null,
subtitle: const HighlightedText(),
),
GeneralInfoCard(
title: "Head to Appwrite Cloud",
link: "https://cloud.appwrite.io",
subtitle: const Text(
"Start managing your project from the Appwrite console",
style: TextStyle(
fontSize: 14,
color: Color(0xFF56565C),
),
),
),
),
GeneralInfoCard(
title: "Explore docs",
link: "https://appwrite.io/docs",
subtitle: const Text(
"Discover the full power of Appwrite by diving into our documentation",
style: TextStyle(
fontSize: 14,
color: Color(0xFF56565C),
GeneralInfoCard(
title: "Explore docs",
link: "https://appwrite.io/docs",
subtitle: const Text(
"Discover the full power of Appwrite by diving into our documentation",
style: TextStyle(
fontSize: 14,
color: Color(0xFF56565C),
),
),
),
),
],
],
),
),
largeDeviceLayout: Padding(
padding: EdgeInsets.symmetric(
horizontal: context.isExtraWideScreen ? 64 : 16.0, vertical: 16.0),
child: Row(
mainAxisSize: MainAxisSize.min,
mainAxisAlignment: MainAxisAlignment.center,
spacing: 16,
children: [
Flexible(
child: GeneralInfoCard(
title: "Edit your app",
link: null,
subtitle: const HighlightedText(),
),
),
Flexible(
child: GeneralInfoCard(
title: "Head to Appwrite Cloud",
link: "https://cloud.appwrite.io",
subtitle: const Text(
"Start managing your project from the Appwrite console",
style: TextStyle(
fontSize: 14,
color: Color(0xFF56565C),
),
),
),
),
Flexible(
child: GeneralInfoCard(
title: "Explore docs",
link: "https://appwrite.io/docs",
subtitle: const Text(
"Discover the full power of Appwrite by diving into our documentation",
style: TextStyle(
fontSize: 14,
color: Color(0xFF56565C),
),
),
),
),
],
),
),
);
}
@ -68,9 +115,12 @@ class GeneralInfoCard extends StatelessWidget {
@override
Widget build(BuildContext context) {
return LayoutBuilder(builder: (context, constraints) {
final double cardWidth = context.isExtraWideScreen
? constraints.maxWidth.clamp(0, 350)
: constraints.maxWidth;
return SizedBox(
// `1` because we already have padding on sides.
width: constraints.maxWidth * (context.isExtraWideScreen ? 0.55 : 1),
width: cardWidth,
child: Card(
elevation: 0,
shape: RoundedRectangleBorder(

View File

@ -1,5 +1,6 @@
import 'package:appwrite_flutter_starter_kit/data/models/status.dart';
import 'package:appwrite_flutter_starter_kit/ui/icons/appwrite.dart';
import 'package:appwrite_flutter_starter_kit/utils/extensions/build_context.dart';
import 'package:flutter/material.dart';
import 'connection_line.dart';
@ -21,9 +22,15 @@ class TopPlatformView extends StatelessWidget {
return Row(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
PlatformIcon(child: FlutterLogo(size: 40)),
PlatformIcon(
size: context.isExtraWideScreen ? 142 : 100,
child: FlutterLogo(size: context.isExtraWideScreen ? 56 : 40),
),
ConnectionLine(show: status == Status.success),
PlatformIcon(child: AppwriteIcon(size: 40)),
PlatformIcon(
size: context.isExtraWideScreen ? 142 : 100,
child: AppwriteIcon(size: context.isExtraWideScreen ? 56 : 40),
),
],
);
}
@ -51,7 +58,7 @@ class PlatformIcon extends StatelessWidget {
height: size,
decoration: BoxDecoration(
color: const Color(0xFFFAFAFD),
borderRadius: BorderRadius.circular(24),
borderRadius: BorderRadius.circular(context.isExtraWideScreen ? size * 0.2 : 24),
border: Border.all(color: const Color(0x0A19191C), width: 1),
boxShadow: [
BoxShadow(
@ -65,9 +72,10 @@ class PlatformIcon extends StatelessWidget {
child: Container(
width: size * 0.86,
height: size * 0.86,
margin: context.isExtraWideScreen ? EdgeInsets.all(8) : null,
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.circular(16),
borderRadius: BorderRadius.circular(context.isExtraWideScreen ? size * 0.2: 16),
border: Border.all(color: const Color(0xFFFAFAFB), width: 1),
boxShadow: [
BoxShadow(

13
prepare-env.sh Normal file
View File

@ -0,0 +1,13 @@
#!/bin/sh
set -e
# Script used during deployment on Appwrite Sites
# Replace [appwritePublicEndpoint] with APPWRITE_PUBLIC_ENDPOINT in environment file
sed -i "s|\[appwritePublicEndpoint\]|$APPWRITE_PUBLIC_ENDPOINT|g" lib/config/environment.dart
# Replace [appwriteProjectId] with APPWRITE_PROJECT_ID in environment file
sed -i "s|\[appwriteProjectId\]|$APPWRITE_PROJECT_ID|g" lib/config/environment.dart
# Replace [appwriteProjectName] with APPWRITE_PROJECT_NAME in environment file
sed -i "s|\[appwriteProjectName\]|$APPWRITE_PROJECT_NAME|g" lib/config/environment.dart

View File

@ -45,10 +45,10 @@ packages:
dependency: transitive
description:
name: characters
sha256: f71061c654a3380576a52b451dd5532377954cf9dbd272a78fc8479606670803
sha256: "04a925763edad70e8443c99234dc3328f442e811f1d8fd1a72f1c8ad0f69a605"
url: "https://pub.dev"
source: hosted
version: "1.4.0"
version: "1.3.0"
checked_yaml:
dependency: transitive
description:
@ -77,10 +77,10 @@ packages:
dependency: transitive
description:
name: collection
sha256: "2f5709ae4d3d59dd8f7cd309b4e023046b57d8a6c82130785d2b0e5868084e76"
sha256: a1ace0a119f20aabc852d165077c036cd864315bd99b7eaa10a60100341941bf
url: "https://pub.dev"
source: hosted
version: "1.19.1"
version: "1.19.0"
cookie_jar:
dependency: transitive
description:
@ -271,10 +271,10 @@ packages:
dependency: transitive
description:
name: meta
sha256: e3641ec5d63ebf0d9b41bd43201a66e3fc79a65db5f61fc181f04cd27aab950c
sha256: bdb68674043280c3428e9ec998512fb681678676b3c54e773629ffe74419f8c7
url: "https://pub.dev"
source: hosted
version: "1.16.0"
version: "1.15.0"
package_info_plus:
dependency: transitive
description:
@ -625,5 +625,5 @@ packages:
source: hosted
version: "3.1.3"
sdks:
dart: ">=3.7.0-0 <4.0.0"
dart: ">=3.6.0 <4.0.0"
flutter: ">=3.27.0"

View File

@ -5,7 +5,7 @@ publish_to: 'none'
version: 1.0.0
environment:
sdk: ^3.6.0
sdk: ^3.5.4
dependencies:
flutter:

Binary file not shown.

Before

Width:  |  Height:  |  Size: 399 B

8
web/favicon.svg Normal file
View File

@ -0,0 +1,8 @@
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<path
d="M24.4429 16.4322V21.9096H10.7519C6.76318 21.9096 3.28044 19.7067 1.4171 16.4322C1.14622 15.9561 0.909137 15.4567 0.710264 14.9383C0.319864 13.9225 0.0744552 12.8325 0 11.6952V10.2143C0.0161646 9.96089 0.0416361 9.70942 0.0749451 9.46095C0.143032 8.95105 0.245898 8.45211 0.381093 7.96711C1.66006 3.36909 5.81877 0 10.7519 0C15.6851 0 19.8433 3.36909 21.1223 7.96711H15.2682C14.3072 6.4683 12.6437 5.4774 10.7519 5.4774C8.86017 5.4774 7.19668 6.4683 6.23562 7.96711C5.9427 8.42274 5.71542 8.92516 5.56651 9.46095C5.43425 9.93599 5.36371 10.4369 5.36371 10.9548C5.36371 12.5248 6.01324 13.94 7.05463 14.9383C8.01961 15.865 9.32061 16.4322 10.7519 16.4322H24.4429Z"
fill="#FD366E" />
<path
d="M24.4429 9.46094V14.9383H14.4492C15.4906 13.94 16.1401 12.5248 16.1401 10.9548C16.1401 10.4369 16.0696 9.93598 15.9373 9.46094H24.4429Z"
fill="#FD366E" />
</svg>

After

Width:  |  Height:  |  Size: 1012 B

View File

@ -1,4 +1,6 @@
<!DOCTYPE html><html><head>
<!DOCTYPE html>
<html>
<head>
<!--
If you are serving your web app in a path other than the root, change the
href value below to reflect the base path you are serving from.
@ -25,123 +27,98 @@
<link rel="apple-touch-icon" href="icons/Icon-192.png">
<!-- Favicon -->
<link rel="icon" type="image/png" href="favicon.png">
<link rel="icon" type="image/png" href="favicon.svg">
<title>AppwriteStarterKit</title>
<link rel="manifest" href="manifest.json">
<meta content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no"
name="viewport">
<meta content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no" name="viewport">
<style id="splash-screen-style">
html, body {
height: 100%;
margin: 0;
background-color: #EDEDF0;
}
.center {
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
width: 64px;
height: 64px;
display: flex;
align-items: center;
justify-content: center;
}
<style id="splash-screen-style">
html {
height: 100%
}
.bottom {
position: absolute;
bottom: 0;
left: 50%;
padding-bottom: 24px;
transform: translateX(-50%);
}
body {
margin: 0;
min-height: 100%;
background-color: #EDEDF0;
background-size: 100% 100%;
}
.center {
margin: 0;
position: absolute;
top: 50%;
left: 50%;
-ms-transform: translate(-50%, -50%);
transform: translate(-50%, -50%);
}
.contain {
display:block;
width:100%; height:100%;
object-fit: contain;
}
.stretch {
display:block;
width:100%; height:100%;
}
.cover {
display:block;
width:100%; height:100%;
object-fit: cover;
}
.bottom {
position: absolute;
bottom: 0;
left: 50%;
padding-bottom: 24px;
-ms-transform: translate(-50%, 0);
transform: translate(-50%, 0);
}
.bottomLeft {
position: absolute;
bottom: 0;
left: 0;
}
.bottomRight {
position: absolute;
bottom: 0;
right: 0;
}
@media (prefers-color-scheme: dark) {
body {
background-color: #19191D;
@keyframes rotate {
from {
transform: rotate(0deg);
}
}
</style>
<script id="splash-screen-script">
function removeSplashFromWeb() {
document.getElementById("splash")?.remove();
document.getElementById("splash-branding")?.remove();
document.body.style.background = "transparent";
}
</script>
to {
transform: rotate(360deg);
}
}
.rotate {
width: 100%;
height: 100%;
transform-origin: center center;
animation: rotate 1.5s infinite linear;
}
@media (prefers-color-scheme: dark) {
body {
background-color: #19191D;
}
}
@media (prefers-reduced-motion: reduce) {
.rotate {
animation: none;
}
}
</style>
<script id="splash-screen-script">
function removeSplashFromWeb() {
document.getElementById("splash")?.remove();
document.getElementById("splash-branding")?.remove();
document.body.style.background = "transparent";
}
</script>
</head>
<body>
<picture id="splash-branding">
<source srcset="splash/img/branding-1x.png 1x, splash/img/branding-2x.png 2x, splash/img/branding-3x.png 3x, splash/img/branding-4x.png 4x" media="(prefers-color-scheme: light)">
<source srcset="splash/img/branding-dark-1x.png 1x, splash/img/branding-dark-2x.png 2x, splash/img/branding-dark-3x.png 3x, splash/img/branding-dark-4x.png 4x" media="(prefers-color-scheme: dark)">
<picture id="splash-branding">
<source srcset="splash/img/branding-1x.png 1x, splash/img/branding-2x.png 2x, splash/img/branding-3x.png 3x, splash/img/branding-4x.png 4x"
media="(prefers-color-scheme: light)">
<source srcset="splash/img/branding-dark-1x.png 1x, splash/img/branding-dark-2x.png 2x, splash/img/branding-dark-3x.png 3x, splash/img/branding-dark-4x.png 4x"
media="(prefers-color-scheme: dark)">
<img class="bottom" aria-hidden="true" src="splash/img/branding-1x.png" alt="">
</picture>
<picture id="splash">
<source srcset="splash/img/light-1x.png 1x, splash/img/light-2x.png 2x, splash/img/light-3x.png 3x, splash/img/light-4x.png 4x" media="(prefers-color-scheme: light)">
<source srcset="splash/img/dark-1x.png 1x, splash/img/dark-2x.png 2x, splash/img/dark-3x.png 3x, splash/img/dark-4x.png 4x" media="(prefers-color-scheme: dark)">
<img class="center" aria-hidden="true" src="splash/img/light-1x.png" alt="">
</picture>
</picture>
<div id="splash" class="center">
<svg class="rotate" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="none">
<path opacity="0.2"
d="M24 12C24 18.6274 18.6274 24 12 24C5.37258 24 0 18.6274 0 12C0 5.37258 5.37258 0 12 0C18.6274 0 24 5.37258 24 12ZM2.4 12C2.4 17.3019 6.69807 21.6 12 21.6C17.3019 21.6 21.6 17.3019 21.6 12C21.6 6.69807 17.3019 2.4 12 2.4C6.69807 2.4 2.4 6.69807 2.4 12Z"
fill="#56565C"/>
<path d="M5.11708 2.17017C6.66833 1.08398 8.45463 0.380338 10.3299 0.116783C12.2052 -0.146772 14.1163 0.0372409 15.9068 0.653778C17.6974 1.27031 19.3166 2.30187 20.6321 3.6641C21.9476 5.02633 22.922 6.68056 23.4757 8.49154C24.0293 10.3025 24.1465 12.2188 23.8177 14.0838C23.4888 15.9487 22.7233 17.7094 21.5836 19.2218C20.444 20.7342 18.9625 21.9554 17.2605 22.7855C15.5584 23.6157 13.684 24.0312 11.7906 23.9982L11.8325 21.5985C13.3472 21.625 14.8467 21.2925 16.2084 20.6284C17.57 19.9643 18.7552 18.9873 19.6669 17.7774C20.5786 16.5675 21.1911 15.159 21.4542 13.667C21.7172 12.1751 21.6235 10.642 21.1805 9.19323C20.7376 7.74445 19.9581 6.42107 18.9057 5.33128C17.8533 4.2415 16.5579 3.41625 15.1255 2.92302C13.693 2.42979 12.1642 2.28258 10.6639 2.49343C9.1637 2.70427 7.73467 3.26718 6.49367 4.13614L5.11708 2.17017Z"
fill="#56565C"/>
</svg>
</div>
<script src="flutter_bootstrap.js" async=""></script>
</body></html>
</body>
</html>