Created onboarding
This commit is contained in:
@@ -0,0 +1 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.1" width="24" height="24" viewBox="0 0 24 24"><path d="M12,2A10,10 0 0,0 2,12C2,16.42 4.87,20.17 8.84,21.5C9.34,21.58 9.5,21.27 9.5,21C9.5,20.77 9.5,20.14 9.5,19.31C6.73,19.91 6.14,17.97 6.14,17.97C5.68,16.81 5.03,16.5 5.03,16.5C4.12,15.88 5.1,15.9 5.1,15.9C6.1,15.97 6.63,16.93 6.63,16.93C7.5,18.45 8.97,18 9.54,17.76C9.63,17.11 9.89,16.67 10.17,16.42C7.95,16.17 5.62,15.31 5.62,11.5C5.62,10.39 6,9.5 6.65,8.79C6.55,8.54 6.2,7.5 6.75,6.15C6.75,6.15 7.59,5.88 9.5,7.17C10.29,6.95 11.15,6.84 12,6.84C12.85,6.84 13.71,6.95 14.5,7.17C16.41,5.88 17.25,6.15 17.25,6.15C17.8,7.5 17.45,8.54 17.35,8.79C18,9.5 18.38,10.39 18.38,11.5C18.38,15.32 16.04,16.16 13.81,16.41C14.17,16.72 14.5,17.33 14.5,18.26C14.5,19.6 14.5,20.68 14.5,21C14.5,21.27 14.66,21.59 15.17,21.5C19.14,20.16 22,16.42 22,12A10,10 0 0,0 12,2Z" /></svg>
|
||||
|
After Width: | Height: | Size: 1.0 KiB |
@@ -0,0 +1 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.1" width="24" height="24" viewBox="0 0 24 24"><path d="M3,20.5V3.5C3,2.91 3.34,2.39 3.84,2.15L13.69,12L3.84,21.85C3.34,21.6 3,21.09 3,20.5M16.81,15.12L6.05,21.34L14.54,12.85L16.81,15.12M20.16,10.81C20.5,11.08 20.75,11.5 20.75,12C20.75,12.5 20.53,12.9 20.18,13.18L17.89,14.5L15.39,12L17.89,9.5L20.16,10.81M6.05,2.66L16.81,8.88L14.54,11.15L6.05,2.66Z" /></svg>
|
||||
|
After Width: | Height: | Size: 588 B |
+86
-2
@@ -4,9 +4,9 @@
|
||||
/// To regenerate, run: `dart run slang`
|
||||
///
|
||||
/// Locales: 2
|
||||
/// Strings: 8 (4 per locale)
|
||||
/// Strings: 30 (15 per locale)
|
||||
///
|
||||
/// Built on 2024-02-21 at 23:50 UTC
|
||||
/// Built on 2024-02-22 at 01:09 UTC
|
||||
|
||||
// coverage:ignore-file
|
||||
// ignore_for_file: type=lint
|
||||
@@ -148,8 +148,28 @@ class Translations implements BaseTranslations<AppLocale, Translations> {
|
||||
late final Translations _root = this; // ignore: unused_field
|
||||
|
||||
// Translations
|
||||
late final _StringsOnboardingEn onboarding = _StringsOnboardingEn._(_root);
|
||||
late final _StringsConnectEn connect = _StringsConnectEn._(_root);
|
||||
late final _StringsLinksEn links = _StringsLinksEn._(_root);
|
||||
late final _StringsSettingsEn settings = _StringsSettingsEn._(_root);
|
||||
}
|
||||
|
||||
// Path: onboarding
|
||||
class _StringsOnboardingEn {
|
||||
_StringsOnboardingEn._(this._root);
|
||||
|
||||
final Translations _root; // ignore: unused_field
|
||||
|
||||
// Translations
|
||||
String get title => 'Welcome to My Linkding';
|
||||
String get subtitle => 'An application to manage your bookmarks.';
|
||||
String get start => 'Start';
|
||||
String get next => 'Next';
|
||||
String get previous => 'Previous';
|
||||
String get serverRequired => 'Servidor requerido';
|
||||
String get serverRequiredDescription => 'My Linkding it\'s not an standalone app, it requires the Linkding server to work.\nIn order to use this application, you must deploy Linkding on your home server, VPS or any other computer.';
|
||||
String get installationInstructions => 'Check the installation instructions on the official GitHub repository.';
|
||||
String get serverRunningConfirmation => 'I confirm that I have an instance of the Linkding server already running.';
|
||||
}
|
||||
|
||||
// Path: connect
|
||||
@@ -174,6 +194,17 @@ class _StringsLinksEn {
|
||||
String get links => 'Links';
|
||||
}
|
||||
|
||||
// Path: settings
|
||||
class _StringsSettingsEn {
|
||||
_StringsSettingsEn._(this._root);
|
||||
|
||||
final Translations _root; // ignore: unused_field
|
||||
|
||||
// Translations
|
||||
String get settings => 'Settings';
|
||||
String get disconnectFromServer => 'Disconnect from server';
|
||||
}
|
||||
|
||||
// Path: <root>
|
||||
class _StringsEs implements Translations {
|
||||
/// You can call this constructor and build your own translation instance of this locale.
|
||||
@@ -198,8 +229,28 @@ class _StringsEs implements Translations {
|
||||
@override late final _StringsEs _root = this; // ignore: unused_field
|
||||
|
||||
// Translations
|
||||
@override late final _StringsOnboardingEs onboarding = _StringsOnboardingEs._(_root);
|
||||
@override late final _StringsConnectEs connect = _StringsConnectEs._(_root);
|
||||
@override late final _StringsLinksEs links = _StringsLinksEs._(_root);
|
||||
@override late final _StringsSettingsEs settings = _StringsSettingsEs._(_root);
|
||||
}
|
||||
|
||||
// Path: onboarding
|
||||
class _StringsOnboardingEs implements _StringsOnboardingEn {
|
||||
_StringsOnboardingEs._(this._root);
|
||||
|
||||
@override final _StringsEs _root; // ignore: unused_field
|
||||
|
||||
// Translations
|
||||
@override String get title => 'Bienvenido a My Linkding';
|
||||
@override String get subtitle => 'Una aplicación para gestionar tus enlaces favoritos.';
|
||||
@override String get start => 'Comenzar';
|
||||
@override String get next => 'Siguiente';
|
||||
@override String get previous => 'Anterior';
|
||||
@override String get serverRequired => 'Servidor requerido';
|
||||
@override String get serverRequiredDescription => 'My Linkding no es una aplicación independiente, requiere el servidor Linkding para funcionar.\nPara utilizar esta aplicación, debe instalar Linkding en su servidor doméstico, VPS o cualquier otro ordenador.';
|
||||
@override String get installationInstructions => 'Mira las instrucciones de instalación en el repositorio oficial en GitHub.';
|
||||
@override String get serverRunningConfirmation => 'Confirmo que tengo una instancia del servidor Linkding ya en funcionamiento.';
|
||||
}
|
||||
|
||||
// Path: connect
|
||||
@@ -224,16 +275,38 @@ class _StringsLinksEs implements _StringsLinksEn {
|
||||
@override String get links => 'Enlaces';
|
||||
}
|
||||
|
||||
// Path: settings
|
||||
class _StringsSettingsEs implements _StringsSettingsEn {
|
||||
_StringsSettingsEs._(this._root);
|
||||
|
||||
@override final _StringsEs _root; // ignore: unused_field
|
||||
|
||||
// Translations
|
||||
@override String get settings => 'Ajustes';
|
||||
@override String get disconnectFromServer => 'Desconectar del servidor';
|
||||
}
|
||||
|
||||
/// Flat map(s) containing all translations.
|
||||
/// Only for edge cases! For simple maps, use the map function of this library.
|
||||
|
||||
extension on Translations {
|
||||
dynamic _flatMapFunction(String path) {
|
||||
switch (path) {
|
||||
case 'onboarding.title': return 'Welcome to My Linkding';
|
||||
case 'onboarding.subtitle': return 'An application to manage your bookmarks.';
|
||||
case 'onboarding.start': return 'Start';
|
||||
case 'onboarding.next': return 'Next';
|
||||
case 'onboarding.previous': return 'Previous';
|
||||
case 'onboarding.serverRequired': return 'Servidor requerido';
|
||||
case 'onboarding.serverRequiredDescription': return 'My Linkding it\'s not an standalone app, it requires the Linkding server to work.\nIn order to use this application, you must deploy Linkding on your home server, VPS or any other computer.';
|
||||
case 'onboarding.installationInstructions': return 'Check the installation instructions on the official GitHub repository.';
|
||||
case 'onboarding.serverRunningConfirmation': return 'I confirm that I have an instance of the Linkding server already running.';
|
||||
case 'connect.connect': return 'Connect';
|
||||
case 'connect.connecting': return 'Connecting...';
|
||||
case 'connect.cannotConnectToServer': return 'Cannot connect to the server.';
|
||||
case 'links.links': return 'Links';
|
||||
case 'settings.settings': return 'Settings';
|
||||
case 'settings.disconnectFromServer': return 'Disconnect from server';
|
||||
default: return null;
|
||||
}
|
||||
}
|
||||
@@ -242,10 +315,21 @@ extension on Translations {
|
||||
extension on _StringsEs {
|
||||
dynamic _flatMapFunction(String path) {
|
||||
switch (path) {
|
||||
case 'onboarding.title': return 'Bienvenido a My Linkding';
|
||||
case 'onboarding.subtitle': return 'Una aplicación para gestionar tus enlaces favoritos.';
|
||||
case 'onboarding.start': return 'Comenzar';
|
||||
case 'onboarding.next': return 'Siguiente';
|
||||
case 'onboarding.previous': return 'Anterior';
|
||||
case 'onboarding.serverRequired': return 'Servidor requerido';
|
||||
case 'onboarding.serverRequiredDescription': return 'My Linkding no es una aplicación independiente, requiere el servidor Linkding para funcionar.\nPara utilizar esta aplicación, debe instalar Linkding en su servidor doméstico, VPS o cualquier otro ordenador.';
|
||||
case 'onboarding.installationInstructions': return 'Mira las instrucciones de instalación en el repositorio oficial en GitHub.';
|
||||
case 'onboarding.serverRunningConfirmation': return 'Confirmo que tengo una instancia del servidor Linkding ya en funcionamiento.';
|
||||
case 'connect.connect': return 'Conectar';
|
||||
case 'connect.connecting': return 'Conectando...';
|
||||
case 'connect.cannotConnectToServer': return 'No se puede conectar con el servidor.';
|
||||
case 'links.links': return 'Enlaces';
|
||||
case 'settings.settings': return 'Ajustes';
|
||||
case 'settings.disconnectFromServer': return 'Desconectar del servidor';
|
||||
default: return null;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,4 +1,15 @@
|
||||
{
|
||||
"onboarding": {
|
||||
"title": "Welcome to My Linkding",
|
||||
"subtitle": "An application to manage your bookmarks.",
|
||||
"start": "Start",
|
||||
"next": "Next",
|
||||
"previous": "Previous",
|
||||
"serverRequired": "Servidor requerido",
|
||||
"serverRequiredDescription": "My Linkding it's not an standalone app, it requires the Linkding server to work.\nIn order to use this application, you must deploy Linkding on your home server, VPS or any other computer.",
|
||||
"installationInstructions": "Check the installation instructions on the official GitHub repository.",
|
||||
"serverRunningConfirmation": "I confirm that I have an instance of the Linkding server already running."
|
||||
},
|
||||
"connect": {
|
||||
"connect": "Connect",
|
||||
"connecting": "Connecting...",
|
||||
@@ -6,5 +17,9 @@
|
||||
},
|
||||
"links": {
|
||||
"links": "Links"
|
||||
},
|
||||
"settings": {
|
||||
"settings": "Settings",
|
||||
"disconnectFromServer": "Disconnect from server"
|
||||
}
|
||||
}
|
||||
@@ -1,4 +1,15 @@
|
||||
{
|
||||
"onboarding": {
|
||||
"title": "Bienvenido a My Linkding",
|
||||
"subtitle": "Una aplicación para gestionar tus enlaces favoritos.",
|
||||
"start": "Comenzar",
|
||||
"next": "Siguiente",
|
||||
"previous": "Anterior",
|
||||
"serverRequired": "Servidor requerido",
|
||||
"serverRequiredDescription": "My Linkding no es una aplicación independiente, requiere el servidor Linkding para funcionar.\nPara utilizar esta aplicación, debe instalar Linkding en su servidor doméstico, VPS o cualquier otro ordenador.",
|
||||
"installationInstructions": "Mira las instrucciones de instalación en el repositorio oficial en GitHub.",
|
||||
"serverRunningConfirmation": "Confirmo que tengo una instancia del servidor Linkding ya en funcionamiento."
|
||||
},
|
||||
"connect": {
|
||||
"connect": "Conectar",
|
||||
"connecting": "Conectando...",
|
||||
@@ -6,5 +17,9 @@
|
||||
},
|
||||
"links": {
|
||||
"links": "Enlaces"
|
||||
},
|
||||
"settings": {
|
||||
"settings": "Ajustes",
|
||||
"disconnectFromServer": "Desconectar del servidor"
|
||||
}
|
||||
}
|
||||
@@ -18,4 +18,9 @@ class ApiClientProvider extends _$ApiClientProvider {
|
||||
void setApiClient(ApiClient client) {
|
||||
state = client;
|
||||
}
|
||||
|
||||
void disconnectApiClient() {
|
||||
state = null;
|
||||
ref.read(serverInstancesProvider.notifier).removeServerInstances();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -6,7 +6,7 @@ part of 'api_client_provider.dart';
|
||||
// RiverpodGenerator
|
||||
// **************************************************************************
|
||||
|
||||
String _$apiClientProviderHash() => r'eff6aeacbfe369f2204d77f4884cc9d78ecf1e27';
|
||||
String _$apiClientProviderHash() => r'8c44873c4e0758acfcd64b181134b80a43327f46';
|
||||
|
||||
/// See also [ApiClientProvider].
|
||||
@ProviderFor(ApiClientProvider)
|
||||
|
||||
@@ -12,7 +12,7 @@ GoRouter router(RouterRef ref) {
|
||||
return GoRouter(
|
||||
redirect: (context, state) {
|
||||
if (ref.watch(apiClientProviderProvider) == null) {
|
||||
return RoutesPaths.connect;
|
||||
return RoutesPaths.onboarding;
|
||||
}
|
||||
return null;
|
||||
},
|
||||
|
||||
@@ -6,7 +6,7 @@ part of 'router_provider.dart';
|
||||
// RiverpodGenerator
|
||||
// **************************************************************************
|
||||
|
||||
String _$routerHash() => r'47e3f3d747dcb7b2543c73209f8a2f5561eb6ff7';
|
||||
String _$routerHash() => r'78eb4c32cddebb29e3029e0eeaeb0f4c40d77012';
|
||||
|
||||
/// See also [router].
|
||||
@ProviderFor(router)
|
||||
|
||||
@@ -4,8 +4,6 @@ import 'package:my_linkding/config/shared_preferences_keys.dart';
|
||||
import 'package:my_linkding/providers/shared_preferences_provider.dart';
|
||||
import 'package:riverpod_annotation/riverpod_annotation.dart';
|
||||
|
||||
import 'package:my_linkding/services/api_client.dart';
|
||||
import 'package:my_linkding/providers/api_client_provider.dart';
|
||||
import 'package:my_linkding/models/server_instance.dart';
|
||||
|
||||
part 'server_instances_provider.g.dart';
|
||||
@@ -45,4 +43,9 @@ class ServerInstances extends _$ServerInstances {
|
||||
final stringList = instances.map((i) => jsonEncode(i.toJson())).toList();
|
||||
ref.read(sharedPreferencesProvider).setStringList(SharedPreferencesKeys.serversInstances, stringList);
|
||||
}
|
||||
|
||||
void removeServerInstances() {
|
||||
state = [];
|
||||
ref.read(sharedPreferencesProvider).remove(SharedPreferencesKeys.serversInstances);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -6,7 +6,7 @@ part of 'server_instances_provider.dart';
|
||||
// RiverpodGenerator
|
||||
// **************************************************************************
|
||||
|
||||
String _$serverInstancesHash() => r'82b7d3367afbe5c19ad0238977e5df35fac3499b';
|
||||
String _$serverInstancesHash() => r'ee41f5a717b9f779aa4319cc711b479a47c1c9ef';
|
||||
|
||||
/// See also [ServerInstances].
|
||||
@ProviderFor(ServerInstances)
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
class RoutesPaths {
|
||||
static const connect = "/connect";
|
||||
static const onboarding = "/onboarding";
|
||||
static const links = "/links";
|
||||
static const search = "/search";
|
||||
static const settings = "/settings";
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:go_router/go_router.dart';
|
||||
|
||||
import 'package:my_linkding/screens/connect/ui/connect.dart';
|
||||
import 'package:my_linkding/screens/links/ui/links.dart';
|
||||
import 'package:my_linkding/screens/onboarding/ui/onboarding.dart';
|
||||
import 'package:my_linkding/screens/search/ui/search.dart';
|
||||
import 'package:my_linkding/screens/settings/ui/settings.dart';
|
||||
import 'package:my_linkding/widgets/layout.dart';
|
||||
@@ -16,8 +16,8 @@ final settingsNavigatorKey = GlobalKey<NavigatorState>();
|
||||
|
||||
final List<RouteBase> appRoutes = [
|
||||
GoRoute(
|
||||
path: RoutesPaths.connect,
|
||||
builder: (context, state) => const Connect(),
|
||||
path: RoutesPaths.onboarding,
|
||||
builder: (context, state) => const Onboarding(),
|
||||
),
|
||||
StatefulShellRoute.indexedStack(
|
||||
builder: (context, state, navigationShell) => Layout(
|
||||
|
||||
@@ -6,7 +6,7 @@ part of 'connect_provider.dart';
|
||||
// RiverpodGenerator
|
||||
// **************************************************************************
|
||||
|
||||
String _$connectToServerHash() => r'af66fee9a4bf26aba08b27ff5a7fe4643215117a';
|
||||
String _$connectToServerHash() => r'c40898fd5dd6dd7507140c7a69a6f336a56e30c0';
|
||||
|
||||
/// See also [connectToServer].
|
||||
@ProviderFor(connectToServer)
|
||||
|
||||
@@ -0,0 +1,16 @@
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
class OnboardingModel {
|
||||
final PageController pageController;
|
||||
final bool confirmServerRunning;
|
||||
|
||||
OnboardingModel({
|
||||
required this.pageController,
|
||||
required this.confirmServerRunning,
|
||||
});
|
||||
|
||||
OnboardingModel toggleConfirmServerRunning(bool newValue) => OnboardingModel(
|
||||
pageController: pageController,
|
||||
confirmServerRunning: newValue,
|
||||
);
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:riverpod_annotation/riverpod_annotation.dart';
|
||||
|
||||
import 'package:my_linkding/screens/onboarding/model/onboarding.model.dart';
|
||||
|
||||
part 'onboarding.provider.g.dart';
|
||||
|
||||
@riverpod
|
||||
class Onboarding extends _$Onboarding {
|
||||
@override
|
||||
OnboardingModel build() {
|
||||
return OnboardingModel(
|
||||
pageController: PageController(),
|
||||
confirmServerRunning: false,
|
||||
);
|
||||
}
|
||||
|
||||
void nextPage() {
|
||||
state.pageController.nextPage(
|
||||
duration: const Duration(milliseconds: 200),
|
||||
curve: Curves.ease,
|
||||
);
|
||||
}
|
||||
|
||||
void previousPage() {
|
||||
state.pageController.previousPage(
|
||||
duration: const Duration(milliseconds: 200),
|
||||
curve: Curves.ease,
|
||||
);
|
||||
}
|
||||
|
||||
void confirmServerRunning() {
|
||||
state = state.toggleConfirmServerRunning(!state.confirmServerRunning);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
// GENERATED CODE - DO NOT MODIFY BY HAND
|
||||
|
||||
part of 'onboarding.provider.dart';
|
||||
|
||||
// **************************************************************************
|
||||
// RiverpodGenerator
|
||||
// **************************************************************************
|
||||
|
||||
String _$onboardingHash() => r'5c876d53acbca92ab15630516099700609aa4f89';
|
||||
|
||||
/// See also [Onboarding].
|
||||
@ProviderFor(Onboarding)
|
||||
final onboardingProvider =
|
||||
AutoDisposeNotifierProvider<Onboarding, OnboardingModel>.internal(
|
||||
Onboarding.new,
|
||||
name: r'onboardingProvider',
|
||||
debugGetCreateSourceHash:
|
||||
const bool.fromEnvironment('dart.vm.product') ? null : _$onboardingHash,
|
||||
dependencies: null,
|
||||
allTransitiveDependencies: null,
|
||||
);
|
||||
|
||||
typedef _$Onboarding = AutoDisposeNotifier<OnboardingModel>;
|
||||
// ignore_for_file: type=lint
|
||||
// ignore_for_file: subtype_of_sealed_class, invalid_use_of_internal_member, invalid_use_of_visible_for_testing_member
|
||||
@@ -0,0 +1,29 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
|
||||
import 'package:my_linkding/screens/onboarding/provider/onboarding.provider.dart';
|
||||
import 'package:my_linkding/screens/onboarding/ui/server_required.dart';
|
||||
import 'package:my_linkding/screens/onboarding/ui/welcome.dart';
|
||||
import 'package:my_linkding/widgets/system_overlay_style.dart';
|
||||
|
||||
class Onboarding extends ConsumerWidget {
|
||||
const Onboarding({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return OverlayStyle(
|
||||
child: Scaffold(
|
||||
body: SafeArea(
|
||||
child: PageView(
|
||||
controller: ref.watch(onboardingProvider).pageController,
|
||||
physics: const NeverScrollableScrollPhysics(),
|
||||
children: const [
|
||||
OnboardingWelcome(),
|
||||
OnboardingServerRequired(),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,132 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:flutter_svg/flutter_svg.dart';
|
||||
|
||||
import 'package:my_linkding/screens/onboarding/provider/onboarding.provider.dart';
|
||||
|
||||
import 'package:my_linkding/i18n/strings.g.dart';
|
||||
|
||||
class OnboardingServerRequired extends ConsumerWidget {
|
||||
const OnboardingServerRequired({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return Padding(
|
||||
padding: const EdgeInsets.all(24),
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Expanded(
|
||||
child: ListView(
|
||||
children: [
|
||||
Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Icon(
|
||||
Icons.dns_rounded,
|
||||
size: 50,
|
||||
color: Theme.of(context).colorScheme.primary,
|
||||
),
|
||||
const SizedBox(height: 24),
|
||||
Text(
|
||||
t.onboarding.serverRequired,
|
||||
style: const TextStyle(fontSize: 28),
|
||||
),
|
||||
const SizedBox(height: 8),
|
||||
Text(
|
||||
t.onboarding.serverRequiredDescription,
|
||||
style: TextStyle(
|
||||
fontSize: 16,
|
||||
color: Theme.of(context).colorScheme.onSurfaceVariant,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
Container(height: 24),
|
||||
Card(
|
||||
child: InkWell(
|
||||
onTap: () => {},
|
||||
borderRadius: BorderRadius.circular(10),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(24),
|
||||
child: Row(
|
||||
children: [
|
||||
SvgPicture.asset(
|
||||
'assets/resources/github.svg',
|
||||
color: Theme.of(context).colorScheme.primary,
|
||||
width: 40,
|
||||
height: 40,
|
||||
),
|
||||
const SizedBox(width: 24),
|
||||
Flexible(
|
||||
child: Text(
|
||||
t.onboarding.installationInstructions,
|
||||
style: TextStyle(
|
||||
fontSize: 16,
|
||||
color: Theme.of(context).colorScheme.primary,
|
||||
fontWeight: FontWeight.w500,
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(height: 8),
|
||||
],
|
||||
),
|
||||
),
|
||||
Column(
|
||||
children: [
|
||||
ListTile(
|
||||
contentPadding: const EdgeInsets.all(8),
|
||||
leading: Checkbox(
|
||||
shape: RoundedRectangleBorder(
|
||||
borderRadius: BorderRadius.circular(5),
|
||||
),
|
||||
value: ref.watch(onboardingProvider).confirmServerRunning,
|
||||
onChanged: (_) => ref.read(onboardingProvider.notifier).confirmServerRunning(),
|
||||
),
|
||||
title: Text(
|
||||
t.onboarding.serverRunningConfirmation,
|
||||
style: const TextStyle(fontSize: 14),
|
||||
),
|
||||
onTap: () => ref.read(onboardingProvider.notifier).confirmServerRunning(),
|
||||
),
|
||||
const SizedBox(height: 8),
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
FilledButton(
|
||||
onPressed: () => ref.read(onboardingProvider.notifier).previousPage(),
|
||||
child: Row(
|
||||
children: [
|
||||
const Icon(Icons.arrow_back_rounded),
|
||||
const SizedBox(width: 8),
|
||||
Text(t.onboarding.previous),
|
||||
],
|
||||
),
|
||||
),
|
||||
FilledButton(
|
||||
onPressed: ref.watch(onboardingProvider).confirmServerRunning == true
|
||||
? () => ref.read(onboardingProvider.notifier).nextPage()
|
||||
: null,
|
||||
child: Row(
|
||||
children: [
|
||||
Text(t.onboarding.next),
|
||||
const SizedBox(width: 8),
|
||||
const Icon(Icons.arrow_forward_rounded),
|
||||
],
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,79 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
import 'package:my_linkding/i18n/strings.g.dart';
|
||||
import 'package:my_linkding/screens/onboarding/provider/onboarding.provider.dart';
|
||||
|
||||
class OnboardingWelcome extends ConsumerWidget {
|
||||
const OnboardingWelcome({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
final width = MediaQuery.of(context).size.width;
|
||||
final height = MediaQuery.of(context).size.height;
|
||||
|
||||
final iconSize = width > height ? height : width;
|
||||
|
||||
return Padding(
|
||||
padding: const EdgeInsets.all(24),
|
||||
child: Stack(
|
||||
children: [
|
||||
Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Container(
|
||||
width: 50,
|
||||
height: 50,
|
||||
color: Colors.red,
|
||||
),
|
||||
const SizedBox(height: 24),
|
||||
Text(
|
||||
t.onboarding.title,
|
||||
style: const TextStyle(fontSize: 28),
|
||||
),
|
||||
const SizedBox(height: 8),
|
||||
Text(
|
||||
t.onboarding.subtitle,
|
||||
style: TextStyle(
|
||||
fontSize: 16,
|
||||
color: Theme.of(context).colorScheme.onSurfaceVariant,
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
const SizedBox(),
|
||||
FilledButton(
|
||||
onPressed: () => ref.read(onboardingProvider.notifier).nextPage(),
|
||||
child: Row(
|
||||
children: [
|
||||
Text(t.onboarding.start),
|
||||
const SizedBox(width: 8),
|
||||
const Icon(Icons.arrow_forward_rounded),
|
||||
],
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
Center(
|
||||
child: Transform.rotate(
|
||||
angle: 0.7,
|
||||
child: Icon(
|
||||
Icons.link_rounded,
|
||||
size: iconSize - 48,
|
||||
color: Theme.of(context).colorScheme.secondary.withOpacity(0.2),
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -1,38 +1,28 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
|
||||
class Settings extends StatelessWidget {
|
||||
import 'package:my_linkding/i18n/strings.g.dart';
|
||||
import 'package:my_linkding/providers/api_client_provider.dart';
|
||||
|
||||
class Settings extends ConsumerWidget {
|
||||
const Settings({Key? key}) : super(key: key);
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Material(
|
||||
color: Colors.transparent,
|
||||
child: NestedScrollView(
|
||||
headerSliverBuilder: (context, innerBoxIsScrolled) => [
|
||||
SliverOverlapAbsorber(
|
||||
handle: NestedScrollView.sliverOverlapAbsorberHandleFor(context),
|
||||
sliver: SliverAppBar.large(
|
||||
pinned: true,
|
||||
floating: true,
|
||||
centerTitle: false,
|
||||
forceElevated: innerBoxIsScrolled,
|
||||
title: Text("Settings"),
|
||||
Widget build(BuildContext context, WidgetRef ref) {
|
||||
return Scaffold(
|
||||
appBar: AppBar(
|
||||
title: Text(t.settings.settings),
|
||||
),
|
||||
body: ListView(
|
||||
children: [
|
||||
FilledButton.icon(
|
||||
onPressed: () => ref.read(apiClientProviderProvider.notifier).disconnectApiClient(),
|
||||
icon: const Icon(Icons.clear_rounded),
|
||||
label: Text(
|
||||
t.settings.disconnectFromServer,
|
||||
),
|
||||
),
|
||||
],
|
||||
body: SafeArea(
|
||||
top: false,
|
||||
bottom: false,
|
||||
child: Builder(
|
||||
builder: (context) => CustomScrollView(
|
||||
slivers: [
|
||||
SliverOverlapInjector(
|
||||
handle: NestedScrollView.sliverOverlapAbsorberHandleFor(context),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
@@ -315,6 +315,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.4.10"
|
||||
flutter_svg:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: flutter_svg
|
||||
sha256: "7b4ca6cf3304575fe9c8ec64813c8d02ee41d2afe60bcfe0678bcb5375d596a2"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.0.10+1"
|
||||
flutter_test:
|
||||
dependency: "direct dev"
|
||||
description: flutter
|
||||
@@ -373,6 +381,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.2.0"
|
||||
http:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: http
|
||||
sha256: a2bbf9d017fcced29139daa8ed2bba4ece450ab222871df93ca9eec6f80c34ba
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.2.0"
|
||||
http_multi_server:
|
||||
dependency: transitive
|
||||
description:
|
||||
@@ -493,6 +509,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.8.3"
|
||||
path_parsing:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: path_parsing
|
||||
sha256: e3e67b1629e6f7e8100b367d3db6ba6af4b1f0bb80f64db18ef1fbabd2fa9ccf
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.0.1"
|
||||
path_provider_linux:
|
||||
dependency: transitive
|
||||
description:
|
||||
@@ -517,6 +541,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.2.1"
|
||||
petitparser:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: petitparser
|
||||
sha256: c15605cd28af66339f8eb6fbe0e541bfe2d1b72d5825efc6598f3e0a31b9ad27
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "6.0.2"
|
||||
platform:
|
||||
dependency: transitive
|
||||
description:
|
||||
@@ -882,6 +914,30 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.3.3"
|
||||
vector_graphics:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: vector_graphics
|
||||
sha256: "32c3c684e02f9bc0afb0ae0aa653337a2fe022e8ab064bcd7ffda27a74e288e3"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.1.11+1"
|
||||
vector_graphics_codec:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: vector_graphics_codec
|
||||
sha256: c86987475f162fadff579e7320c7ddda04cd2fdeffbe1129227a85d9ac9e03da
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.1.11+1"
|
||||
vector_graphics_compiler:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: vector_graphics_compiler
|
||||
sha256: "12faff3f73b1741a36ca7e31b292ddeb629af819ca9efe9953b70bd63fc8cd81"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.1.11+1"
|
||||
vector_math:
|
||||
dependency: transitive
|
||||
description:
|
||||
@@ -938,6 +994,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.0.4"
|
||||
xml:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: xml
|
||||
sha256: b015a8ad1c488f66851d762d3090a21c600e479dc75e68328c52774040cf9226
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "6.5.0"
|
||||
yaml:
|
||||
dependency: transitive
|
||||
description:
|
||||
|
||||
+4
-3
@@ -45,6 +45,7 @@ dependencies:
|
||||
uuid: ^4.3.3
|
||||
slang: ^3.29.0
|
||||
slang_flutter: ^3.29.0
|
||||
flutter_svg: ^2.0.9
|
||||
|
||||
dev_dependencies:
|
||||
build_runner: ^2.4.8
|
||||
@@ -64,9 +65,9 @@ flutter:
|
||||
uses-material-design: true
|
||||
|
||||
# To add assets to your application, add an assets section, like this:
|
||||
# assets:
|
||||
# - images/a_dot_burr.jpeg
|
||||
# - images/a_dot_ham.jpeg
|
||||
assets:
|
||||
- assets/resources/github.svg
|
||||
- assets/resources/google-play.svg
|
||||
|
||||
# An image asset can refer to one or more resolution-specific "variants", see
|
||||
# https://flutter.dev/assets-and-images/#resolution-aware
|
||||
|
||||
Reference in New Issue
Block a user