work
@ -46,7 +46,7 @@ android {
|
|||||||
|
|
||||||
defaultConfig {
|
defaultConfig {
|
||||||
// TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html).
|
// TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html).
|
||||||
applicationId "com.vekoni.veilidchat.veilidchat"
|
applicationId "com.veilid.veilidchat"
|
||||||
// You can update the following values to match your application needs.
|
// You can update the following values to match your application needs.
|
||||||
// For more information, see: https://docs.flutter.dev/deployment/android#reviewing-the-build-configuration.
|
// For more information, see: https://docs.flutter.dev/deployment/android#reviewing-the-build-configuration.
|
||||||
minSdkVersion Math.max(flutter.minSdkVersion, 24)
|
minSdkVersion Math.max(flutter.minSdkVersion, 24)
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
|
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
package="com.vekoni.veilidchat.veilidchat">
|
package="com.veilid.veilidchat">
|
||||||
<application
|
<application
|
||||||
android:label="veilidchat"
|
android:label="VeilidChat"
|
||||||
android:name="${applicationName}"
|
android:name="${applicationName}"
|
||||||
android:icon="@mipmap/ic_launcher">
|
android:icon="@mipmap/ic_launcher">
|
||||||
<activity
|
<activity
|
||||||
|
Before Width: | Height: | Size: 544 B After Width: | Height: | Size: 7.9 KiB |
Before Width: | Height: | Size: 442 B After Width: | Height: | Size: 4.8 KiB |
Before Width: | Height: | Size: 721 B After Width: | Height: | Size: 11 KiB |
Before Width: | Height: | Size: 1.0 KiB After Width: | Height: | Size: 19 KiB |
Before Width: | Height: | Size: 1.4 KiB After Width: | Height: | Size: 28 KiB |
@ -1,7 +1,21 @@
|
|||||||
{
|
{
|
||||||
"app_bar": {
|
"app": {
|
||||||
"title": "VeilidChat"
|
"title": "VeilidChat"
|
||||||
},
|
},
|
||||||
|
"app_bar": {
|
||||||
|
"settings_tooltip": "Settings"
|
||||||
|
},
|
||||||
|
"new_account_page": {
|
||||||
|
"title": "Create a new account",
|
||||||
|
"header": "Account Profile",
|
||||||
|
"import": "Import an existing account"
|
||||||
|
},
|
||||||
|
"new_account_form": {
|
||||||
|
"name": "Name",
|
||||||
|
"title": "Title (optional)",
|
||||||
|
"create": "Create",
|
||||||
|
"instructions": "This information will be shared with the people you invite to connect with you on VeilidChat."
|
||||||
|
},
|
||||||
"button": {
|
"button": {
|
||||||
"cancel": "Cancel",
|
"cancel": "Cancel",
|
||||||
"change_language": "Change Language"
|
"change_language": "Change Language"
|
||||||
|
50
assets/images/vlogo.svg
Normal file
After Width: | Height: | Size: 23 KiB |
BIN
assets/launcher/icon.png
Normal file
After Width: | Height: | Size: 260 KiB |
BIN
assets/sources/vlogo.afdesign
Normal file
@ -1,34 +1,57 @@
|
|||||||
PODS:
|
PODS:
|
||||||
- Flutter (1.0.0)
|
- Flutter (1.0.0)
|
||||||
- path_provider_ios (0.0.1):
|
- FMDB (2.7.5):
|
||||||
|
- FMDB/standard (= 2.7.5)
|
||||||
|
- FMDB/standard (2.7.5)
|
||||||
|
- path_provider_foundation (0.0.1):
|
||||||
- Flutter
|
- Flutter
|
||||||
- shared_preferences_ios (0.0.1):
|
- FlutterMacOS
|
||||||
|
- shared_preferences_foundation (0.0.1):
|
||||||
|
- Flutter
|
||||||
|
- FlutterMacOS
|
||||||
|
- sqflite (0.0.3):
|
||||||
|
- Flutter
|
||||||
|
- FMDB (>= 2.7.5)
|
||||||
|
- system_info_plus (0.0.1):
|
||||||
- Flutter
|
- Flutter
|
||||||
- veilid (0.0.1):
|
- veilid (0.0.1):
|
||||||
- Flutter
|
- Flutter
|
||||||
|
|
||||||
DEPENDENCIES:
|
DEPENDENCIES:
|
||||||
- Flutter (from `Flutter`)
|
- Flutter (from `Flutter`)
|
||||||
- path_provider_ios (from `.symlinks/plugins/path_provider_ios/ios`)
|
- path_provider_foundation (from `.symlinks/plugins/path_provider_foundation/darwin`)
|
||||||
- shared_preferences_ios (from `.symlinks/plugins/shared_preferences_ios/ios`)
|
- shared_preferences_foundation (from `.symlinks/plugins/shared_preferences_foundation/darwin`)
|
||||||
|
- sqflite (from `.symlinks/plugins/sqflite/ios`)
|
||||||
|
- system_info_plus (from `.symlinks/plugins/system_info_plus/ios`)
|
||||||
- veilid (from `.symlinks/plugins/veilid/ios`)
|
- veilid (from `.symlinks/plugins/veilid/ios`)
|
||||||
|
|
||||||
|
SPEC REPOS:
|
||||||
|
trunk:
|
||||||
|
- FMDB
|
||||||
|
|
||||||
EXTERNAL SOURCES:
|
EXTERNAL SOURCES:
|
||||||
Flutter:
|
Flutter:
|
||||||
:path: Flutter
|
:path: Flutter
|
||||||
path_provider_ios:
|
path_provider_foundation:
|
||||||
:path: ".symlinks/plugins/path_provider_ios/ios"
|
:path: ".symlinks/plugins/path_provider_foundation/darwin"
|
||||||
shared_preferences_ios:
|
shared_preferences_foundation:
|
||||||
:path: ".symlinks/plugins/shared_preferences_ios/ios"
|
:path: ".symlinks/plugins/shared_preferences_foundation/darwin"
|
||||||
|
sqflite:
|
||||||
|
:path: ".symlinks/plugins/sqflite/ios"
|
||||||
|
system_info_plus:
|
||||||
|
:path: ".symlinks/plugins/system_info_plus/ios"
|
||||||
veilid:
|
veilid:
|
||||||
:path: ".symlinks/plugins/veilid/ios"
|
:path: ".symlinks/plugins/veilid/ios"
|
||||||
|
|
||||||
SPEC CHECKSUMS:
|
SPEC CHECKSUMS:
|
||||||
Flutter: f04841e97a9d0b0a8025694d0796dd46242b2854
|
Flutter: f04841e97a9d0b0a8025694d0796dd46242b2854
|
||||||
path_provider_ios: 14f3d2fd28c4fdb42f44e0f751d12861c43cee02
|
FMDB: 2ce00b547f966261cd18927a3ddb07cb6f3db82a
|
||||||
shared_preferences_ios: 548a61f8053b9b8a49ac19c1ffbc8b92c50d68ad
|
path_provider_foundation: 29f094ae23ebbca9d3d0cec13889cd9060c0e943
|
||||||
|
shared_preferences_foundation: 5b919d13b803cadd15ed2dc053125c68730e5126
|
||||||
|
sqflite: 31f7eba61e3074736dff8807a9b41581e4f7f15a
|
||||||
|
system_info_plus: 5393c8da281d899950d751713575fbf91c7709aa
|
||||||
veilid: f5c2e662f91907b30cf95762619526ac3e4512fd
|
veilid: f5c2e662f91907b30cf95762619526ac3e4512fd
|
||||||
|
|
||||||
PODFILE CHECKSUM: fcab1959fbc0528061dce4ed4f921740dc46f1e5
|
PODFILE CHECKSUM: fcab1959fbc0528061dce4ed4f921740dc46f1e5
|
||||||
|
|
||||||
COCOAPODS: 1.11.3
|
COCOAPODS: 1.12.1
|
||||||
|
@ -3,7 +3,7 @@
|
|||||||
archiveVersion = 1;
|
archiveVersion = 1;
|
||||||
classes = {
|
classes = {
|
||||||
};
|
};
|
||||||
objectVersion = 51;
|
objectVersion = 54;
|
||||||
objects = {
|
objects = {
|
||||||
|
|
||||||
/* Begin PBXBuildFile section */
|
/* Begin PBXBuildFile section */
|
||||||
@ -216,10 +216,12 @@
|
|||||||
};
|
};
|
||||||
3B06AD1E1E4923F5004D2608 /* Thin Binary */ = {
|
3B06AD1E1E4923F5004D2608 /* Thin Binary */ = {
|
||||||
isa = PBXShellScriptBuildPhase;
|
isa = PBXShellScriptBuildPhase;
|
||||||
|
alwaysOutOfDate = 1;
|
||||||
buildActionMask = 2147483647;
|
buildActionMask = 2147483647;
|
||||||
files = (
|
files = (
|
||||||
);
|
);
|
||||||
inputPaths = (
|
inputPaths = (
|
||||||
|
"${TARGET_BUILD_DIR}/${INFOPLIST_PATH}",
|
||||||
);
|
);
|
||||||
name = "Thin Binary";
|
name = "Thin Binary";
|
||||||
outputPaths = (
|
outputPaths = (
|
||||||
@ -230,6 +232,7 @@
|
|||||||
};
|
};
|
||||||
9740EEB61CF901F6004384FC /* Run Script */ = {
|
9740EEB61CF901F6004384FC /* Run Script */ = {
|
||||||
isa = PBXShellScriptBuildPhase;
|
isa = PBXShellScriptBuildPhase;
|
||||||
|
alwaysOutOfDate = 1;
|
||||||
buildActionMask = 2147483647;
|
buildActionMask = 2147483647;
|
||||||
files = (
|
files = (
|
||||||
);
|
);
|
||||||
|
Before Width: | Height: | Size: 11 KiB After Width: | Height: | Size: 246 KiB |
Before Width: | Height: | Size: 564 B After Width: | Height: | Size: 1.4 KiB |
Before Width: | Height: | Size: 1.3 KiB After Width: | Height: | Size: 3.3 KiB |
Before Width: | Height: | Size: 1.6 KiB After Width: | Height: | Size: 5.6 KiB |
Before Width: | Height: | Size: 1.0 KiB After Width: | Height: | Size: 2.2 KiB |
Before Width: | Height: | Size: 1.7 KiB After Width: | Height: | Size: 5.4 KiB |
Before Width: | Height: | Size: 1.9 KiB After Width: | Height: | Size: 8.9 KiB |
Before Width: | Height: | Size: 1.3 KiB After Width: | Height: | Size: 3.3 KiB |
Before Width: | Height: | Size: 1.9 KiB After Width: | Height: | Size: 8.0 KiB |
Before Width: | Height: | Size: 2.6 KiB After Width: | Height: | Size: 14 KiB |
After Width: | Height: | Size: 4.5 KiB |
After Width: | Height: | Size: 10 KiB |
After Width: | Height: | Size: 5.2 KiB |
After Width: | Height: | Size: 13 KiB |
Before Width: | Height: | Size: 2.6 KiB After Width: | Height: | Size: 14 KiB |
Before Width: | Height: | Size: 3.7 KiB After Width: | Height: | Size: 22 KiB |
After Width: | Height: | Size: 7.0 KiB |
After Width: | Height: | Size: 17 KiB |
Before Width: | Height: | Size: 1.8 KiB After Width: | Height: | Size: 7.5 KiB |
Before Width: | Height: | Size: 3.2 KiB After Width: | Height: | Size: 18 KiB |
Before Width: | Height: | Size: 3.5 KiB After Width: | Height: | Size: 20 KiB |
@ -27,7 +27,7 @@ class VeilidChatApp extends ConsumerWidget {
|
|||||||
child: MaterialApp.router(
|
child: MaterialApp.router(
|
||||||
debugShowCheckedModeBanner: false,
|
debugShowCheckedModeBanner: false,
|
||||||
routerConfig: router,
|
routerConfig: router,
|
||||||
title: 'VeilidChat',
|
title: translate("app.title"),
|
||||||
theme: theme,
|
theme: theme,
|
||||||
localizationsDelegates: [
|
localizationsDelegates: [
|
||||||
GlobalMaterialLocalizations.delegate,
|
GlobalMaterialLocalizations.delegate,
|
||||||
|
@ -1,10 +1,10 @@
|
|||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter/widgets.dart';
|
import 'package:flutter/widgets.dart';
|
||||||
|
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
import 'package:window_manager/window_manager.dart';
|
import 'package:window_manager/window_manager.dart';
|
||||||
import 'package:circular_profile_avatar/circular_profile_avatar.dart';
|
import 'package:circular_profile_avatar/circular_profile_avatar.dart';
|
||||||
import 'package:badges/badges.dart';
|
import 'package:badges/badges.dart';
|
||||||
|
import 'package:awesome_extensions/awesome_extensions.dart';
|
||||||
|
|
||||||
import '../entities/local_account.dart';
|
import '../entities/local_account.dart';
|
||||||
import '../providers/logins.dart';
|
import '../providers/logins.dart';
|
||||||
@ -30,3 +30,22 @@ class AccountBubble extends ConsumerWidget {
|
|||||||
]));
|
]));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class AddAccountBubble extends ConsumerWidget {
|
||||||
|
const AddAccountBubble({super.key});
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context, WidgetRef ref) {
|
||||||
|
windowManager.setTitleBarStyle(TitleBarStyle.normal);
|
||||||
|
final logins = ref.watch(loginsProvider);
|
||||||
|
|
||||||
|
return Column(mainAxisAlignment: MainAxisAlignment.center, children: [
|
||||||
|
CircularProfileAvatar("",
|
||||||
|
borderWidth: 4,
|
||||||
|
borderColor: Theme.of(context).unselectedWidgetColor,
|
||||||
|
child: Container(
|
||||||
|
color: Colors.blue, child: const Icon(Icons.add, size: 50))),
|
||||||
|
const Text("Add Account").paddingLTRB(0, 4, 0, 0)
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -1,9 +1,8 @@
|
|||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
|
|
||||||
class ChatPage extends ConsumerWidget {
|
class Chat extends ConsumerWidget {
|
||||||
const ChatPage({super.key});
|
const Chat({super.key});
|
||||||
static const path = '/chat';
|
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context, WidgetRef ref) {
|
Widget build(BuildContext context, WidgetRef ref) {
|
@ -1,9 +1,8 @@
|
|||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
|
|
||||||
class ContactsPage extends ConsumerWidget {
|
class ChatIndex extends ConsumerWidget {
|
||||||
const ContactsPage({super.key});
|
const ChatIndex({super.key});
|
||||||
static const path = '/contacts';
|
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context, WidgetRef ref) {
|
Widget build(BuildContext context, WidgetRef ref) {
|
29
lib/components/default_app_bar.dart
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:flutter_svg/flutter_svg.dart';
|
||||||
|
import 'package:flutter_translate/flutter_translate.dart';
|
||||||
|
|
||||||
|
class DefaultAppBar extends AppBar {
|
||||||
|
DefaultAppBar(BuildContext context,
|
||||||
|
{super.key, required super.title, Widget? leading, List<Widget>? actions})
|
||||||
|
: super(
|
||||||
|
leading: leading ??
|
||||||
|
Container(
|
||||||
|
margin: const EdgeInsets.all(4),
|
||||||
|
decoration: BoxDecoration(
|
||||||
|
color: Colors.black.withAlpha(32),
|
||||||
|
shape: BoxShape.circle),
|
||||||
|
child: SvgPicture.asset("assets/images/vlogo.svg",
|
||||||
|
height: 48)),
|
||||||
|
actions: (actions ?? <Widget>[])
|
||||||
|
..add(
|
||||||
|
IconButton(
|
||||||
|
icon: const Icon(Icons.settings),
|
||||||
|
tooltip: translate('app_bar.settings_tooltip'),
|
||||||
|
onPressed: () {
|
||||||
|
ScaffoldMessenger.of(context).showSnackBar(const SnackBar(
|
||||||
|
content: Text(
|
||||||
|
'Accessibility and language options coming soon')));
|
||||||
|
},
|
||||||
|
),
|
||||||
|
));
|
||||||
|
}
|
71
lib/components/new_account_form.dart
Normal file
@ -0,0 +1,71 @@
|
|||||||
|
import 'package:awesome_extensions/awesome_extensions.dart';
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
|
import 'package:flutter_translate/flutter_translate.dart';
|
||||||
|
|
||||||
|
import '../components/default_app_bar.dart';
|
||||||
|
import '../tools/desktop_control.dart';
|
||||||
|
|
||||||
|
class NewAccountForm extends ConsumerStatefulWidget {
|
||||||
|
const NewAccountForm({super.key});
|
||||||
|
|
||||||
|
@override
|
||||||
|
NewAccountFormState createState() {
|
||||||
|
return NewAccountFormState();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class NewAccountFormState extends ConsumerState<NewAccountForm> {
|
||||||
|
final _formKey = GlobalKey<FormState>();
|
||||||
|
|
||||||
|
@override
|
||||||
|
Widget build(BuildContext context) {
|
||||||
|
return Form(
|
||||||
|
key: _formKey,
|
||||||
|
child: Column(
|
||||||
|
children: [
|
||||||
|
TextFormField(
|
||||||
|
key: const ValueKey("name"),
|
||||||
|
autofocus: true,
|
||||||
|
decoration:
|
||||||
|
InputDecoration(hintText: translate("new_account_form.name")),
|
||||||
|
maxLength: 64,
|
||||||
|
// The validator receives the text that the user has entered.
|
||||||
|
validator: (value) {
|
||||||
|
if (value == null || value.isEmpty) {
|
||||||
|
return 'Name is required';
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
},
|
||||||
|
),
|
||||||
|
TextFormField(
|
||||||
|
key: const ValueKey("title"),
|
||||||
|
maxLength: 64,
|
||||||
|
decoration:
|
||||||
|
InputDecoration(hintText: translate("new_account_form.title")),
|
||||||
|
),
|
||||||
|
Row(children: [
|
||||||
|
const Spacer(),
|
||||||
|
Text(translate("new_account_form.instructions"))
|
||||||
|
.toCenter()
|
||||||
|
.flexible(flex: 4),
|
||||||
|
const Spacer(),
|
||||||
|
]).paddingSymmetric(vertical: 24),
|
||||||
|
ElevatedButton(
|
||||||
|
onPressed: () {
|
||||||
|
// Validate returns true if the form is valid, or false otherwise.
|
||||||
|
if (_formKey.currentState!.validate()) {
|
||||||
|
// If the form is valid, display a snackbar. In the real world,
|
||||||
|
// you'd often call a server or save the information in a database.
|
||||||
|
ScaffoldMessenger.of(context).showSnackBar(
|
||||||
|
const SnackBar(content: Text('Processing Data')),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
child: Text(translate('new_account_form.create')),
|
||||||
|
).paddingSymmetric(vertical: 16).toCenter(),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
@ -4,7 +4,6 @@ import 'package:flutter/foundation.dart';
|
|||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
import 'package:flutter_translate/flutter_translate.dart';
|
import 'package:flutter_translate/flutter_translate.dart';
|
||||||
import 'package:window_manager/window_manager.dart';
|
|
||||||
|
|
||||||
import 'log/log.dart';
|
import 'log/log.dart';
|
||||||
import 'veilid_support/veilid_support.dart';
|
import 'veilid_support/veilid_support.dart';
|
||||||
@ -12,6 +11,8 @@ import 'theming/theming.dart';
|
|||||||
import 'app.dart';
|
import 'app.dart';
|
||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
|
|
||||||
|
import '../tools/desktop_control.dart';
|
||||||
|
|
||||||
void main() async {
|
void main() async {
|
||||||
// Disable all debugprints in release mode
|
// Disable all debugprints in release mode
|
||||||
if (kReleaseMode) {
|
if (kReleaseMode) {
|
||||||
@ -32,21 +33,7 @@ void main() async {
|
|||||||
var initTheme = themeService.initial;
|
var initTheme = themeService.initial;
|
||||||
|
|
||||||
// Manage window on desktop platforms
|
// Manage window on desktop platforms
|
||||||
if (Platform.isWindows || Platform.isLinux || Platform.isMacOS) {
|
await setupDesktopWindow();
|
||||||
await windowManager.ensureInitialized();
|
|
||||||
|
|
||||||
const windowOptions = WindowOptions(
|
|
||||||
size: Size(768, 1024),
|
|
||||||
center: true,
|
|
||||||
backgroundColor: Colors.transparent,
|
|
||||||
skipTaskbar: false,
|
|
||||||
titleBarStyle: TitleBarStyle.hidden,
|
|
||||||
);
|
|
||||||
windowManager.waitUntilReadyToShow(windowOptions, () async {
|
|
||||||
await windowManager.show();
|
|
||||||
await windowManager.focus();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
// Make localization delegate
|
// Make localization delegate
|
||||||
var delegate = await LocalizationDelegate.create(
|
var delegate = await LocalizationDelegate.create(
|
||||||
|
@ -1,7 +1,8 @@
|
|||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:radix_colors/radix_colors.dart';
|
import 'package:radix_colors/radix_colors.dart';
|
||||||
import 'package:flutter_svg/flutter_svg.dart';
|
import 'package:flutter_svg/flutter_svg.dart';
|
||||||
import 'package:window_manager/window_manager.dart';
|
|
||||||
|
import '../tools/desktop_control.dart';
|
||||||
|
|
||||||
class IndexPage extends StatelessWidget {
|
class IndexPage extends StatelessWidget {
|
||||||
const IndexPage({super.key});
|
const IndexPage({super.key});
|
||||||
@ -9,7 +10,7 @@ class IndexPage extends StatelessWidget {
|
|||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
windowManager.setTitleBarStyle(TitleBarStyle.hidden);
|
enableTitleBar(false);
|
||||||
return Scaffold(
|
return Scaffold(
|
||||||
body: DecoratedBox(
|
body: DecoratedBox(
|
||||||
decoration: BoxDecoration(
|
decoration: BoxDecoration(
|
||||||
|
@ -39,27 +39,30 @@ class LoginPage extends ConsumerWidget {
|
|||||||
),
|
),
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
body: Center(
|
body: Column(
|
||||||
child: Column(
|
|
||||||
mainAxisAlignment: MainAxisAlignment.center,
|
mainAxisAlignment: MainAxisAlignment.center,
|
||||||
crossAxisAlignment: CrossAxisAlignment.center,
|
crossAxisAlignment: CrossAxisAlignment.center,
|
||||||
children: [
|
children: [
|
||||||
const Spacer(),
|
Container(height: 100, color: Color.fromARGB(255, 255, 0, 0)),
|
||||||
accounts.when(
|
Spacer(),
|
||||||
error: (obj, err) => Text("error loading accounts: $err"),
|
// accounts.when(
|
||||||
loading: () => CircularProgressIndicator(),
|
// error: (obj, err) => Text("error loading accounts: $err"),
|
||||||
data: (accountList) => ReorderableGridView.extent(
|
// loading: () => CircularProgressIndicator(),
|
||||||
maxCrossAxisExtent: 128,
|
// data: (accountList) => ReorderableGridView.extent(
|
||||||
onReorder: (oldIndex, newIndex) =>
|
// maxCrossAxisExtent: 128,
|
||||||
_onReorder(ref, oldIndex, newIndex),
|
// onReorder: (oldIndex, newIndex) =>
|
||||||
children: accountList.map((account) {
|
// _onReorder(ref, oldIndex, newIndex),
|
||||||
return AccountBubble(account: account);
|
// children: accountList.map<Widget>((account) {
|
||||||
}).toList(),
|
// return AccountBubble(
|
||||||
)),
|
// key: ValueKey(account.identityMaster.masterRecordKey),
|
||||||
const Spacer(),
|
// account: account);
|
||||||
|
// }).toList(),
|
||||||
|
// )),
|
||||||
|
AddAccountBubble(key: ValueKey("+")),
|
||||||
|
Spacer(),
|
||||||
|
Container(height: 100, color: Color.fromARGB(255, 0, 255, 0)),
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
),
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,11 @@
|
|||||||
|
import 'package:awesome_extensions/awesome_extensions.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||||
|
import 'package:flutter_translate/flutter_translate.dart';
|
||||||
|
|
||||||
|
import '../components/default_app_bar.dart';
|
||||||
|
import '../components/new_account_form.dart';
|
||||||
|
import '../tools/tools.dart';
|
||||||
|
|
||||||
class NewAccountPage extends ConsumerWidget {
|
class NewAccountPage extends ConsumerWidget {
|
||||||
const NewAccountPage({super.key});
|
const NewAccountPage({super.key});
|
||||||
@ -7,26 +13,25 @@ class NewAccountPage extends ConsumerWidget {
|
|||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context, WidgetRef ref) {
|
Widget build(BuildContext context, WidgetRef ref) {
|
||||||
|
enableTitleBar(true);
|
||||||
|
|
||||||
return Scaffold(
|
return Scaffold(
|
||||||
appBar: null,
|
resizeToAvoidBottomInset: false,
|
||||||
body: Center(
|
appBar: DefaultAppBar(context,
|
||||||
|
title: Text(translate("new_account_page.title"))),
|
||||||
|
body: Container(
|
||||||
|
padding: const EdgeInsets.all(24),
|
||||||
child: Column(
|
child: Column(
|
||||||
mainAxisAlignment: MainAxisAlignment.center,
|
mainAxisAlignment: MainAxisAlignment.start,
|
||||||
crossAxisAlignment: CrossAxisAlignment.center,
|
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||||
children: [
|
children: [
|
||||||
const Text("New Account Page"),
|
Text(translate("new_account_page.header"))
|
||||||
// ElevatedButton(
|
.textStyle(context.headlineSmall)
|
||||||
// onPressed: () async {
|
.paddingSymmetric(vertical: 16),
|
||||||
// ref.watch(authNotifierProvider.notifier).login(
|
const NewAccountForm().flexible(),
|
||||||
// "myEmail",
|
Text(translate("new_account_page.import"))
|
||||||
// "myPassword",
|
|
||||||
// );
|
|
||||||
// },
|
|
||||||
// child: const Text("Login"),
|
|
||||||
// ),
|
|
||||||
],
|
],
|
||||||
),
|
),
|
||||||
),
|
));
|
||||||
);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -6,7 +6,7 @@ part of 'local_accounts.dart';
|
|||||||
// RiverpodGenerator
|
// RiverpodGenerator
|
||||||
// **************************************************************************
|
// **************************************************************************
|
||||||
|
|
||||||
String _$localAccountsHash() => r'694236fa91156c00b3f7d6985fbc55b8871646ab';
|
String _$localAccountsHash() => r'1faa6b22284a402e4f47b2629e54a39ffda9a4ad';
|
||||||
|
|
||||||
/// See also [LocalAccounts].
|
/// See also [LocalAccounts].
|
||||||
@ProviderFor(LocalAccounts)
|
@ProviderFor(LocalAccounts)
|
||||||
|
@ -5,12 +5,14 @@ import 'package:riverpod_annotation/riverpod_annotation.dart';
|
|||||||
import '../pages/pages.dart';
|
import '../pages/pages.dart';
|
||||||
import 'router_notifier.dart';
|
import 'router_notifier.dart';
|
||||||
|
|
||||||
|
part 'router.g.dart';
|
||||||
|
|
||||||
final _key = GlobalKey<NavigatorState>(debugLabel: 'routerKey');
|
final _key = GlobalKey<NavigatorState>(debugLabel: 'routerKey');
|
||||||
|
|
||||||
/// This simple provider caches our GoRouter.
|
/// This simple provider caches our GoRouter.
|
||||||
final routerProvider = Provider.autoDispose<GoRouter>((ref) {
|
@riverpod
|
||||||
|
GoRouter router(RouterRef ref) {
|
||||||
final notifier = ref.watch(routerNotifierProvider.notifier);
|
final notifier = ref.watch(routerNotifierProvider.notifier);
|
||||||
|
|
||||||
return GoRouter(
|
return GoRouter(
|
||||||
navigatorKey: _key,
|
navigatorKey: _key,
|
||||||
refreshListenable: notifier,
|
refreshListenable: notifier,
|
||||||
@ -19,4 +21,4 @@ final routerProvider = Provider.autoDispose<GoRouter>((ref) {
|
|||||||
routes: notifier.routes,
|
routes: notifier.routes,
|
||||||
redirect: notifier.redirect,
|
redirect: notifier.redirect,
|
||||||
);
|
);
|
||||||
});
|
}
|
||||||
|
25
lib/router/router.g.dart
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
// GENERATED CODE - DO NOT MODIFY BY HAND
|
||||||
|
|
||||||
|
part of 'router.dart';
|
||||||
|
|
||||||
|
// **************************************************************************
|
||||||
|
// RiverpodGenerator
|
||||||
|
// **************************************************************************
|
||||||
|
|
||||||
|
String _$routerHash() => r'2273f69a347c52bbb53358ac9034ab0ea760ecce';
|
||||||
|
|
||||||
|
/// This simple provider caches our GoRouter.
|
||||||
|
///
|
||||||
|
/// Copied from [router].
|
||||||
|
@ProviderFor(router)
|
||||||
|
final routerProvider = AutoDisposeProvider<GoRouter>.internal(
|
||||||
|
router,
|
||||||
|
name: r'routerProvider',
|
||||||
|
debugGetCreateSourceHash:
|
||||||
|
const bool.fromEnvironment('dart.vm.product') ? null : _$routerHash,
|
||||||
|
dependencies: null,
|
||||||
|
allTransitiveDependencies: null,
|
||||||
|
);
|
||||||
|
|
||||||
|
typedef RouterRef = AutoDisposeProviderRef<GoRouter>;
|
||||||
|
// ignore_for_file: unnecessary_raw_strings, subtype_of_sealed_class, invalid_use_of_internal_member, do_not_use_environment, prefer_const_constructors, public_member_api_docs, avoid_private_typedef_functions
|
@ -1,23 +1,25 @@
|
|||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
|
||||||
import 'package:go_router/go_router.dart';
|
import 'package:go_router/go_router.dart';
|
||||||
|
import 'package:riverpod_annotation/riverpod_annotation.dart';
|
||||||
|
|
||||||
import '../pages/pages.dart';
|
import '../pages/pages.dart';
|
||||||
import '../providers/logins.dart';
|
import '../providers/local_accounts.dart';
|
||||||
|
|
||||||
class RouterNotifier extends AutoDisposeAsyncNotifier<void>
|
part 'router_notifier.g.dart';
|
||||||
implements Listenable {
|
|
||||||
|
@riverpod
|
||||||
|
class RouterNotifier extends _$RouterNotifier implements Listenable {
|
||||||
/// GoRouter listener
|
/// GoRouter listener
|
||||||
VoidCallback? routerListener;
|
VoidCallback? routerListener;
|
||||||
|
|
||||||
/// Router state for redirect
|
/// Do we need to make or import an account immediately?
|
||||||
bool hasActiveUserLogin = false;
|
bool hasAnyAccount = false;
|
||||||
|
|
||||||
/// AsyncNotifier build
|
/// AsyncNotifier build
|
||||||
@override
|
@override
|
||||||
Future<void> build() async {
|
Future<void> build() async {
|
||||||
hasActiveUserLogin = await ref.watch(
|
hasAnyAccount = await ref.watch(
|
||||||
loginsProvider.selectAsync((data) => data.activeUserLogin != null),
|
localAccountsProvider.selectAsync((data) => data.isNotEmpty),
|
||||||
);
|
);
|
||||||
|
|
||||||
// When this notifier's state changes, inform GoRouter
|
// When this notifier's state changes, inform GoRouter
|
||||||
@ -33,11 +35,9 @@ class RouterNotifier extends AutoDisposeAsyncNotifier<void>
|
|||||||
|
|
||||||
switch (state.location) {
|
switch (state.location) {
|
||||||
case IndexPage.path:
|
case IndexPage.path:
|
||||||
return hasActiveUserLogin ? HomePage.path : LoginPage.path;
|
return hasAnyAccount ? HomePage.path : NewAccountPage.path;
|
||||||
case LoginPage.path:
|
|
||||||
return hasActiveUserLogin ? HomePage.path : null;
|
|
||||||
default:
|
default:
|
||||||
return hasActiveUserLogin ? null : LoginPage.path;
|
return hasAnyAccount ? null : NewAccountPage.path;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -50,38 +50,6 @@ class RouterNotifier extends AutoDisposeAsyncNotifier<void>
|
|||||||
GoRoute(
|
GoRoute(
|
||||||
path: HomePage.path,
|
path: HomePage.path,
|
||||||
builder: (context, state) => const HomePage(),
|
builder: (context, state) => const HomePage(),
|
||||||
// redirect: (context, state) async {
|
|
||||||
// if (state.location == HomePage.path) return null;
|
|
||||||
|
|
||||||
// // final roleListener = ProviderScope.containerOf(context).listen(
|
|
||||||
// // permissionsProvider.select((value) => value.valueOrNull),
|
|
||||||
// // (previous, next) {},
|
|
||||||
// // );
|
|
||||||
|
|
||||||
// // final userRole = roleListener.read();
|
|
||||||
// // final redirectTo = userRole?.redirectBasedOn(state.location);
|
|
||||||
|
|
||||||
// // roleListener.close();
|
|
||||||
// // return redirectTo;
|
|
||||||
// },
|
|
||||||
// routes: [
|
|
||||||
// GoRoute(
|
|
||||||
// path: AdminPage.path,
|
|
||||||
// builder: (context, state) => const AdminPage(),
|
|
||||||
// ),
|
|
||||||
// GoRoute(
|
|
||||||
// path: UserPage.path,
|
|
||||||
// builder: (context, state) => const UserPage(),
|
|
||||||
// ),
|
|
||||||
// GoRoute(
|
|
||||||
// path: GuestPage.path,
|
|
||||||
// builder: (context, state) => const GuestPage(),
|
|
||||||
// )
|
|
||||||
// ]
|
|
||||||
),
|
|
||||||
GoRoute(
|
|
||||||
path: LoginPage.path,
|
|
||||||
builder: (context, state) => const LoginPage(),
|
|
||||||
),
|
),
|
||||||
GoRoute(
|
GoRoute(
|
||||||
path: NewAccountPage.path,
|
path: NewAccountPage.path,
|
||||||
@ -112,27 +80,3 @@ class RouterNotifier extends AutoDisposeAsyncNotifier<void>
|
|||||||
routerListener = null;
|
routerListener = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
final routerNotifierProvider =
|
|
||||||
AutoDisposeAsyncNotifierProvider<RouterNotifier, void>(() {
|
|
||||||
return RouterNotifier();
|
|
||||||
});
|
|
||||||
|
|
||||||
/// A simple extension to determine wherever should we redirect our users
|
|
||||||
// extension RedirecttionBasedOnRole on UserRole {
|
|
||||||
// /// Redirects the users based on [this] and its current [location]
|
|
||||||
// String? redirectBasedOn(String location) {
|
|
||||||
// switch (this) {
|
|
||||||
// case UserRole.admin:
|
|
||||||
// return null;
|
|
||||||
// case UserRole.verifiedUser:
|
|
||||||
// case UserRole.unverifiedUser:
|
|
||||||
// if (location == AdminPage.path) return HomePage.path;
|
|
||||||
// return null;
|
|
||||||
// case UserRole.guest:
|
|
||||||
// case UserRole.none:
|
|
||||||
// if (location != HomePage.path) return HomePage.path;
|
|
||||||
// return null;
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
|
25
lib/router/router_notifier.g.dart
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
// GENERATED CODE - DO NOT MODIFY BY HAND
|
||||||
|
|
||||||
|
part of 'router_notifier.dart';
|
||||||
|
|
||||||
|
// **************************************************************************
|
||||||
|
// RiverpodGenerator
|
||||||
|
// **************************************************************************
|
||||||
|
|
||||||
|
String _$routerNotifierHash() => r'00de1dd715945e96b49507ea55d7b97a78366adc';
|
||||||
|
|
||||||
|
/// See also [RouterNotifier].
|
||||||
|
@ProviderFor(RouterNotifier)
|
||||||
|
final routerNotifierProvider =
|
||||||
|
AutoDisposeAsyncNotifierProvider<RouterNotifier, void>.internal(
|
||||||
|
RouterNotifier.new,
|
||||||
|
name: r'routerNotifierProvider',
|
||||||
|
debugGetCreateSourceHash: const bool.fromEnvironment('dart.vm.product')
|
||||||
|
? null
|
||||||
|
: _$routerNotifierHash,
|
||||||
|
dependencies: null,
|
||||||
|
allTransitiveDependencies: null,
|
||||||
|
);
|
||||||
|
|
||||||
|
typedef _$RouterNotifier = AutoDisposeAsyncNotifier<void>;
|
||||||
|
// ignore_for_file: unnecessary_raw_strings, subtype_of_sealed_class, invalid_use_of_internal_member, do_not_use_environment, prefer_const_constructors, public_member_api_docs, avoid_private_typedef_functions
|
32
lib/tools/desktop_control.dart
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
import 'dart:io';
|
||||||
|
import 'package:window_manager/window_manager.dart';
|
||||||
|
import 'package:flutter/material.dart';
|
||||||
|
|
||||||
|
Future<void> setupDesktopWindow() async {
|
||||||
|
if (Platform.isWindows || Platform.isLinux || Platform.isMacOS) {
|
||||||
|
await windowManager.ensureInitialized();
|
||||||
|
|
||||||
|
const windowOptions = WindowOptions(
|
||||||
|
size: Size(768, 1024),
|
||||||
|
minimumSize: Size(480, 640),
|
||||||
|
center: true,
|
||||||
|
backgroundColor: Colors.transparent,
|
||||||
|
skipTaskbar: false,
|
||||||
|
titleBarStyle: TitleBarStyle.hidden,
|
||||||
|
);
|
||||||
|
windowManager.waitUntilReadyToShow(windowOptions, () async {
|
||||||
|
await windowManager.show();
|
||||||
|
await windowManager.focus();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void enableTitleBar(bool enabled) {
|
||||||
|
if (Platform.isWindows || Platform.isLinux || Platform.isMacOS) {
|
||||||
|
if (enabled) {
|
||||||
|
windowManager.setTitleBarStyle(TitleBarStyle.normal);
|
||||||
|
} else {
|
||||||
|
windowManager.setTitleBarStyle(TitleBarStyle.hidden);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -2,3 +2,5 @@ export 'external_stream_state.dart';
|
|||||||
export 'json_tools.dart';
|
export 'json_tools.dart';
|
||||||
export 'phono_byte.dart';
|
export 'phono_byte.dart';
|
||||||
export 'protobuf_tools.dart';
|
export 'protobuf_tools.dart';
|
||||||
|
export 'widget_helpers.dart';
|
||||||
|
export 'desktop_control.dart';
|
||||||
|
9
lib/tools/widget_helpers.dart
Normal file
@ -0,0 +1,9 @@
|
|||||||
|
import 'package:flutter/material.dart';
|
||||||
|
|
||||||
|
extension BorderExt on Widget {
|
||||||
|
Container debugBorder() {
|
||||||
|
return Container(
|
||||||
|
decoration: BoxDecoration(border: Border.all(color: Colors.redAccent)),
|
||||||
|
child: this);
|
||||||
|
}
|
||||||
|
}
|
@ -43,7 +43,7 @@ void _initVeilid() {
|
|||||||
otlp: VeilidFFIConfigLoggingOtlp(
|
otlp: VeilidFFIConfigLoggingOtlp(
|
||||||
enabled: false,
|
enabled: false,
|
||||||
level: VeilidConfigLogLevel.trace,
|
level: VeilidConfigLogLevel.trace,
|
||||||
grpcEndpoint: "localhost:4317",
|
grpcEndpoint: "192.168.1.40:4317",
|
||||||
serviceName: "VeilidChat"),
|
serviceName: "VeilidChat"),
|
||||||
api: VeilidFFIConfigLoggingApi(
|
api: VeilidFFIConfigLoggingApi(
|
||||||
enabled: true, level: VeilidConfigLogLevel.info)));
|
enabled: true, level: VeilidConfigLogLevel.info)));
|
||||||
|
@ -1,4 +1,8 @@
|
|||||||
{
|
{
|
||||||
|
"info": {
|
||||||
|
"version": 1,
|
||||||
|
"author": "xcode"
|
||||||
|
},
|
||||||
"images": [
|
"images": [
|
||||||
{
|
{
|
||||||
"size": "16x16",
|
"size": "16x16",
|
||||||
@ -60,9 +64,5 @@
|
|||||||
"filename": "app_icon_1024.png",
|
"filename": "app_icon_1024.png",
|
||||||
"scale": "2x"
|
"scale": "2x"
|
||||||
}
|
}
|
||||||
],
|
]
|
||||||
"info" : {
|
|
||||||
"version" : 1,
|
|
||||||
"author" : "xcode"
|
|
||||||
}
|
|
||||||
}
|
}
|
Before Width: | Height: | Size: 101 KiB After Width: | Height: | Size: 268 KiB |
Before Width: | Height: | Size: 5.5 KiB After Width: | Height: | Size: 16 KiB |
Before Width: | Height: | Size: 520 B After Width: | Height: | Size: 1.2 KiB |
Before Width: | Height: | Size: 14 KiB After Width: | Height: | Size: 40 KiB |
Before Width: | Height: | Size: 1.0 KiB After Width: | Height: | Size: 2.8 KiB |
Before Width: | Height: | Size: 36 KiB After Width: | Height: | Size: 95 KiB |
Before Width: | Height: | Size: 2.2 KiB After Width: | Height: | Size: 6.8 KiB |
48
pubspec.lock
@ -41,6 +41,14 @@ packages:
|
|||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.0.1"
|
version: "2.0.1"
|
||||||
|
archive:
|
||||||
|
dependency: transitive
|
||||||
|
description:
|
||||||
|
name: archive
|
||||||
|
sha256: "0c8368c9b3f0abbc193b9d6133649a614204b528982bebc7026372d61677ce3a"
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "3.3.7"
|
||||||
args:
|
args:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -57,6 +65,14 @@ packages:
|
|||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.11.0"
|
version: "2.11.0"
|
||||||
|
awesome_extensions:
|
||||||
|
dependency: "direct main"
|
||||||
|
description:
|
||||||
|
name: awesome_extensions
|
||||||
|
sha256: "6b9c6a5f70d17959ace71d649d3b816b13b73267196035d431ff17e65a228608"
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "2.0.9"
|
||||||
badges:
|
badges:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
@ -374,6 +390,14 @@ packages:
|
|||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.18.6"
|
version: "0.18.6"
|
||||||
|
flutter_launcher_icons:
|
||||||
|
dependency: "direct dev"
|
||||||
|
description:
|
||||||
|
name: flutter_launcher_icons
|
||||||
|
sha256: "526faf84284b86a4cb36d20a5e45147747b7563d921373d4ee0559c54fcdbcea"
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "0.13.1"
|
||||||
flutter_lints:
|
flutter_lints:
|
||||||
dependency: "direct dev"
|
dependency: "direct dev"
|
||||||
description:
|
description:
|
||||||
@ -509,6 +533,14 @@ packages:
|
|||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "4.0.2"
|
version: "4.0.2"
|
||||||
|
image:
|
||||||
|
dependency: transitive
|
||||||
|
description:
|
||||||
|
name: image
|
||||||
|
sha256: a72242c9a0ffb65d03de1b7113bc4e189686fc07c7147b8b41811d0dd0e0d9bf
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "4.0.17"
|
||||||
intl:
|
intl:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
@ -709,6 +741,14 @@ packages:
|
|||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.1.4"
|
version: "2.1.4"
|
||||||
|
pointycastle:
|
||||||
|
dependency: transitive
|
||||||
|
description:
|
||||||
|
name: pointycastle
|
||||||
|
sha256: "7c1e5f0d23c9016c5bbd8b1473d0d3fb3fc851b876046039509e18e0c7485f2c"
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "3.7.3"
|
||||||
pool:
|
pool:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
@ -978,6 +1018,14 @@ packages:
|
|||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "3.0.2"
|
version: "3.0.2"
|
||||||
|
system_info_plus:
|
||||||
|
dependency: transitive
|
||||||
|
description:
|
||||||
|
name: system_info_plus
|
||||||
|
sha256: b915c811c6605b802f3988859bc2bb79c95f735762a75b5451741f7a2b949d1b
|
||||||
|
url: "https://pub.dev"
|
||||||
|
source: hosted
|
||||||
|
version: "0.0.5"
|
||||||
term_glyph:
|
term_glyph:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
23
pubspec.yaml
@ -44,6 +44,7 @@ dependencies:
|
|||||||
reorderable_grid: ^1.0.7
|
reorderable_grid: ^1.0.7
|
||||||
circular_profile_avatar: ^2.0.5
|
circular_profile_avatar: ^2.0.5
|
||||||
badges: ^3.1.1
|
badges: ^3.1.1
|
||||||
|
awesome_extensions: ^2.0.9
|
||||||
|
|
||||||
dev_dependencies:
|
dev_dependencies:
|
||||||
flutter_test:
|
flutter_test:
|
||||||
@ -53,14 +54,36 @@ dev_dependencies:
|
|||||||
freezed: ^2.3.5
|
freezed: ^2.3.5
|
||||||
json_serializable: ^6.7.1
|
json_serializable: ^6.7.1
|
||||||
riverpod_generator: ^2.2.3
|
riverpod_generator: ^2.2.3
|
||||||
|
flutter_launcher_icons: "^0.13.1"
|
||||||
|
|
||||||
|
flutter_launcher_icons:
|
||||||
|
image_path: "assets/launcher/icon.png"
|
||||||
|
android: true
|
||||||
|
ios: true
|
||||||
|
remove_alpha_ios: true
|
||||||
|
min_sdk_android: 24 # android min sdk min:16, default 21
|
||||||
|
web:
|
||||||
|
generate: true
|
||||||
|
background_color: "#33183f"
|
||||||
|
theme_color: "#863fa6"
|
||||||
|
windows:
|
||||||
|
generate: true
|
||||||
|
icon_size: 48 # min:48, max:256, default: 48
|
||||||
|
macos:
|
||||||
|
generate: true
|
||||||
|
|
||||||
flutter:
|
flutter:
|
||||||
uses-material-design: true
|
uses-material-design: true
|
||||||
assets:
|
assets:
|
||||||
|
# Translations
|
||||||
- assets/i18n/en.json
|
- assets/i18n/en.json
|
||||||
|
# Launcher icon
|
||||||
|
- assets/launcher/icon.png
|
||||||
|
# Images
|
||||||
- assets/images/splash.svg
|
- assets/images/splash.svg
|
||||||
- assets/images/icon.svg
|
- assets/images/icon.svg
|
||||||
- assets/images/title.svg
|
- assets/images/title.svg
|
||||||
|
- assets/images/vlogo.svg
|
||||||
|
|
||||||
# An image asset can refer to one or more resolution-specific "variants", see
|
# An image asset can refer to one or more resolution-specific "variants", see
|
||||||
# https://flutter.dev/assets-and-images/#resolution-aware
|
# https://flutter.dev/assets-and-images/#resolution-aware
|
||||||
|
2
update_icons.sh
Executable file
@ -0,0 +1,2 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
dart run flutter_launcher_icons
|
BIN
web/favicon.png
Before Width: | Height: | Size: 917 B After Width: | Height: | Size: 1.2 KiB |
Before Width: | Height: | Size: 5.2 KiB After Width: | Height: | Size: 28 KiB |
Before Width: | Height: | Size: 8.1 KiB After Width: | Height: | Size: 95 KiB |
Before Width: | Height: | Size: 5.5 KiB After Width: | Height: | Size: 28 KiB |
Before Width: | Height: | Size: 20 KiB After Width: | Height: | Size: 95 KiB |
@ -3,8 +3,8 @@
|
|||||||
"short_name": "veilidchat",
|
"short_name": "veilidchat",
|
||||||
"start_url": ".",
|
"start_url": ".",
|
||||||
"display": "standalone",
|
"display": "standalone",
|
||||||
"background_color": "#0175C2",
|
"background_color": "#33183f",
|
||||||
"theme_color": "#0175C2",
|
"theme_color": "#863fa6",
|
||||||
"description": "VeilidChat",
|
"description": "VeilidChat",
|
||||||
"orientation": "portrait-primary",
|
"orientation": "portrait-primary",
|
||||||
"prefer_related_applications": false,
|
"prefer_related_applications": false,
|
||||||
|
Before Width: | Height: | Size: 33 KiB After Width: | Height: | Size: 4.8 KiB |