Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(project): setting project icon #328

Open
wants to merge 2 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
38 changes: 37 additions & 1 deletion lib/src/modules/projects/components/project_list_item.dart
Original file line number Diff line number Diff line change
@@ -1,4 +1,7 @@
import 'package:file_selector/file_selector.dart';
import 'package:flutter/material.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:fvm/fvm.dart';
import 'package:hooks_riverpod/hooks_riverpod.dart';
import 'package:material_design_icons_flutter/material_design_icons_flutter.dart';
import 'package:sidekick/src/modules/common/utils/helpers.dart';
Expand All @@ -10,8 +13,10 @@ import '../../../components/molecules/version_install_button.dart';
import '../../releases/releases.provider.dart';
import '../../sandbox/sandbox.screen.dart';
import '../project.dto.dart';
import '../projects.provider.dart';
import 'project_actions.dart';
import 'project_release_select.dart';
import 'package:file_selector/file_selector.dart' as selector;

/// Project list item
class ProjectListItem extends ConsumerWidget {
Expand All @@ -30,6 +35,8 @@ class ProjectListItem extends ConsumerWidget {

@override
Widget build(BuildContext context, WidgetRef ref) {
final notifier = ref.watch(projectsProvider.notifier);

final cachedVersions = ref.watch(releasesStateProvider).all;

final version = ref.watch(getVersionProvider(project.pinnedVersion));
Expand Down Expand Up @@ -62,14 +69,37 @@ class ProjectListItem extends ConsumerWidget {
);
}

Future<void> handleChangeProjectIcon(Project project) async {
const XTypeGroup typeGroup = XTypeGroup(
label: 'images',
extensions: <String>['svg'],
);

final XFile? iconFile = await selector.openFile(
confirmButtonText: context.i18n('modules:projects.choose'),
acceptedTypeGroups: <XTypeGroup>[typeGroup]);
if (iconFile == null) {
// Operation was canceled by the user.
return;
}
// ignore: use_build_context_synchronously
await notifier.changeProjectIcon(context, project, iconFile);
}

return SizedBox(
height: 170,
child: Center(
child: Card(
child: Column(
children: [
ListTile(
leading: const Icon(MdiIcons.alphaPBox),
leading: project.projectIcon != ""
? SvgPicture.string(
project.projectIcon,
width: 24,
height: 24,
)
: const Icon(MdiIcons.alphaPBox),
title: Subheading(project.name),
trailing: ProjectActions(project),
),
Expand Down Expand Up @@ -122,6 +152,12 @@ class ProjectListItem extends ConsumerWidget {
),
),
const Spacer(),

/// TODO: Need Update UI
TextButton(
onPressed: () => handleChangeProjectIcon(project),
child: Text("Change Icon"),
),
versionSelect
? Row(
children: [
Expand Down
26 changes: 17 additions & 9 deletions lib/src/modules/projects/project.dto.dart
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ class FlutterProject extends Project {
required Directory projectDir,
required this.pubspec,
this.invalid = false,
this.projectIcon = "",
}) : super(
name: name,
config: config,
Expand All @@ -27,12 +28,14 @@ class FlutterProject extends Project {
final bool invalid;

/// Create Flutter project from project
factory FlutterProject.fromProject(Project project, Pubspec pubspec) {
factory FlutterProject.fromProject(Project project, Pubspec pubspec,
{String projectIcon = ""}) {
return FlutterProject._(
name: project.name ?? pubspec.name,
config: project.config,
projectDir: project.projectDir,
pubspec: pubspec,
projectIcon: projectIcon,
);
}

Expand All @@ -44,6 +47,7 @@ class FlutterProject extends Project {
projectDir: project.projectDir,
pubspec: null,
invalid: true,
projectIcon: "",
);
}

Expand All @@ -54,13 +58,17 @@ class FlutterProject extends Project {
String get description {
return pubspec?.description ?? '';
}

/// Project Icon Raw String Data
late String projectIcon;
}

/// Ref to project path
class ProjectRef {
/// Constructor
const ProjectRef({
ProjectRef({
required this.name,
required this.projectIcon,
required this.path,
});

Expand All @@ -70,20 +78,20 @@ class ProjectRef {
/// Project path
final String path;

/// Project Icon
final String projectIcon;

/// Creates a project path from map
factory ProjectRef.fromMap(Map<String, String> map) {
return ProjectRef(
name: map['name'] ?? '',
path: map['path'] ?? '',
);
name: map['name'] ?? '',
path: map['path'] ?? '',
projectIcon: map['projectIcon'] ?? '');
}

/// Returns project path as a map
Map<String, String> toMap() {
return {
'name': name,
'path': path,
};
return {'name': name, 'path': path, 'projectIcon': projectIcon};
}
}

Expand Down
26 changes: 25 additions & 1 deletion lib/src/modules/projects/projects.provider.dart
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,10 @@
// ignore_for_file: top_level_function_literal_block

import 'dart:async';
import 'dart:developer';
import 'dart:io';

import 'package:file_selector/file_selector.dart';
import 'package:flutter/widgets.dart';
import 'package:fvm/fvm.dart';
import 'package:hooks_riverpod/hooks_riverpod.dart';
Expand Down Expand Up @@ -80,7 +82,8 @@ class ProjectsStateNotifier extends StateNotifier<List<FlutterProject>> {
Future<void> addProject(BuildContext context, String path) async {
final project = await FVMClient.getProjectByDirectory(Directory(path));
if (project.isFlutterProject) {
final ref = ProjectRef(name: path.split('/').last, path: path);
final ref =
ProjectRef(name: path.split('/').last, path: path, projectIcon: "");
await ProjectsService.box.put(path, ref);
await load();
} else {
Expand All @@ -89,6 +92,27 @@ class ProjectsStateNotifier extends StateNotifier<List<FlutterProject>> {
}
}

/// Adds a project
Future<void> changeProjectIcon(
BuildContext context, Project project, XFile file) async {
// TODO: File should handle
// 1. handle svg size
// 2. handle svg unsupported element https://pub.dev/packages/flutter_svg#precompiling-and-optimizing-svgs
if (project.isFlutterProject) {
project as FlutterProject;
await ProjectsService.box.put(
project.projectDir.path,
ProjectRef(
name: project.name,
path: project.projectDir.path,
projectIcon: await file.readAsString()));
await load();
} else {
// ignore: use_build_context_synchronously
notify(context.i18n('modules:projects.notAFlutterProject'));
}
}

/// Removes a project
void removeProject(Directory projectDir) {
ProjectsService.box.delete(projectDir.path);
Expand Down
15 changes: 11 additions & 4 deletions lib/src/modules/projects/projects.service.dart
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import 'dart:developer';
import 'dart:io';

import 'package:collection/collection.dart';
Expand Down Expand Up @@ -35,24 +36,30 @@ class ProjectsService {
final projects = await FVMClient.fetchProjects(directories);

/// Check if its flutter project
final projectsWithFlutter = projects.where((p) => p.isFlutterProject);
final Iterable<Project> projectsWithFlutter =
projects.where((p) => p.isFlutterProject);

/// Return flutter projects
final flutterProjects = projectsWithFlutter.map((project) async {
final pubspecFile = project.pubspecFile;
if (box.get(project.projectDir.path) == null) {
await box.delete(project.projectDir.path);
}

final pubspecFile = project.pubspecFile;
if (await pubspecFile.exists()) {
final yaml = await pubspecFile.readAsString();
final pubspec = Pubspec.parse(yaml);

return FlutterProject.fromProject(project, pubspec);
log(project.projectDir.path);
return FlutterProject.fromProject(project, pubspec,
projectIcon: box.get(project.projectDir.path)!.projectIcon);
} else {
/// If it does not exist should be removed
await box.delete(project.projectDir.path);
}
});

final results = await Future.wait(flutterProjects);
log(results.length.toString());
return results.whereNotNull();
}

Expand Down
40 changes: 40 additions & 0 deletions pubspec.lock
Original file line number Diff line number Diff line change
Expand Up @@ -472,6 +472,14 @@ packages:
url: "https://pub.flutter-io.cn"
source: hosted
version: "5.2.1"
flutter_svg:
dependency: "direct main"
description:
name: flutter_svg
sha256: "7b4ca6cf3304575fe9c8ec64813c8d02ee41d2afe60bcfe0678bcb5375d596a2"
url: "https://pub.flutter-io.cn"
source: hosted
version: "2.0.10+1"
flutter_test:
dependency: "direct dev"
description: flutter
Expand Down Expand Up @@ -852,6 +860,14 @@ packages:
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.9.0"
path_parsing:
dependency: transitive
description:
name: path_parsing
sha256: e3e67b1629e6f7e8100b367d3db6ba6af4b1f0bb80f64db18ef1fbabd2fa9ccf
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.0.1"
path_provider:
dependency: "direct main"
description:
Expand Down Expand Up @@ -1281,6 +1297,30 @@ packages:
url: "https://pub.flutter-io.cn"
source: hosted
version: "3.1.2"
vector_graphics:
dependency: transitive
description:
name: vector_graphics
sha256: "32c3c684e02f9bc0afb0ae0aa653337a2fe022e8ab064bcd7ffda27a74e288e3"
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.1.11+1"
vector_graphics_codec:
dependency: transitive
description:
name: vector_graphics_codec
sha256: c86987475f162fadff579e7320c7ddda04cd2fdeffbe1129227a85d9ac9e03da
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.1.11+1"
vector_graphics_compiler:
dependency: transitive
description:
name: vector_graphics_compiler
sha256: "12faff3f73b1741a36ca7e31b292ddeb629af819ca9efe9953b70bd63fc8cd81"
url: "https://pub.flutter-io.cn"
source: hosted
version: "1.1.11+1"
vector_math:
dependency: transitive
description:
Expand Down
1 change: 1 addition & 0 deletions pubspec.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ dependencies:
sdk: flutter
flutter_spinkit: ^5.0.0
fvm: ^2.4.1
flutter_svg: ^2.0.10+1
google_fonts: ^6.2.1
hive: ^2.0.4
hive_flutter: ^1.0.0
Expand Down
Loading