mirror of
https://github.com/Yubico/yubioath-flutter.git
synced 2024-12-23 10:11:52 +03:00
import icon pack
This commit is contained in:
parent
b8580c0612
commit
494e99b36f
@ -17,6 +17,7 @@
|
||||
import 'dart:convert';
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:file_picker/file_picker.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_gen/gen_l10n/app_localizations.dart';
|
||||
import 'package:flutter_riverpod/flutter_riverpod.dart';
|
||||
@ -29,6 +30,7 @@ import 'app/message.dart';
|
||||
import 'app/state.dart';
|
||||
import 'core/state.dart';
|
||||
import 'desktop/state.dart';
|
||||
import 'oath/state.dart';
|
||||
import 'version.dart';
|
||||
import 'widgets/choice_filter_chip.dart';
|
||||
import 'widgets/responsive_dialog.dart';
|
||||
@ -191,6 +193,36 @@ class AboutPage extends ConsumerWidget {
|
||||
},
|
||||
),
|
||||
],
|
||||
|
||||
... [
|
||||
const SizedBox(height: 12.0,),
|
||||
FilterChip(
|
||||
label: const Text('Import icon pack'),
|
||||
onSelected: (value) async {
|
||||
final result = await FilePicker.platform.pickFiles(
|
||||
allowedExtensions: ['zip'],
|
||||
type: FileType.custom,
|
||||
allowMultiple: false,
|
||||
lockParentWindow: true,
|
||||
dialogTitle: 'Choose icon pack');
|
||||
if (result != null && result.files.isNotEmpty) {
|
||||
final importStatus = await ref
|
||||
.read(issuerIconProvider)
|
||||
.importPack(result.paths.first!);
|
||||
|
||||
await ref.read(withContextProvider)(
|
||||
(context) async {
|
||||
if (importStatus) {
|
||||
showMessage(context, 'Icon pack imported');
|
||||
} else {
|
||||
showMessage(context, 'Error importing icon pack');
|
||||
}
|
||||
},
|
||||
);
|
||||
}
|
||||
},
|
||||
),
|
||||
]
|
||||
],
|
||||
),
|
||||
),
|
||||
|
@ -2,6 +2,7 @@ import 'dart:convert';
|
||||
import 'dart:developer';
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:archive/archive.dart';
|
||||
import 'package:flutter/foundation.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:logging/logging.dart';
|
||||
@ -128,6 +129,12 @@ class IssuerIconProvider {
|
||||
|
||||
if (!await packFile.exists()) {
|
||||
_log.debug('Failed to find icons pack ${packFile.path}');
|
||||
_issuerIconPack = IssuerIconPack(
|
||||
uuid: '',
|
||||
name: '',
|
||||
version: 0,
|
||||
directory: Directory(''),
|
||||
icons: []);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -149,6 +156,91 @@ class IssuerIconProvider {
|
||||
'Parsed ${_issuerIconPack.name} with ${_issuerIconPack.icons.length} icons');
|
||||
}
|
||||
|
||||
Future<bool> _cleanTempDirectory(Directory tempDirectory) async {
|
||||
if (await tempDirectory.exists()) {
|
||||
await tempDirectory.delete(recursive: true);
|
||||
}
|
||||
|
||||
if (await tempDirectory.exists()) {
|
||||
_log.error('Failed to remove temp directory');
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
Future<bool> importPack(String filePath) async {
|
||||
|
||||
final packFile = File(filePath);
|
||||
if (!await packFile.exists()) {
|
||||
_log.error('Input file does not exist');
|
||||
return false;
|
||||
}
|
||||
|
||||
// copy input file to temporary folder
|
||||
final documentsDirectory = await getApplicationDocumentsDirectory();
|
||||
final tempDirectory = Directory('${documentsDirectory.path}${Platform.pathSeparator}temp${Platform.pathSeparator}');
|
||||
|
||||
if (!await _cleanTempDirectory(tempDirectory)) {
|
||||
_log.error('Failed to cleanup temp directory');
|
||||
return false;
|
||||
}
|
||||
|
||||
await tempDirectory.create(recursive: true);
|
||||
final tempCopy = await packFile.copy('${tempDirectory.path}${basename(packFile.path)}');
|
||||
final bytes = await File(tempCopy.path).readAsBytes();
|
||||
|
||||
final destination = Directory('${tempDirectory.path}ex${Platform.pathSeparator}');
|
||||
|
||||
final archive = ZipDecoder().decodeBytes(bytes);
|
||||
for (final file in archive) {
|
||||
final filename = file.name;
|
||||
if (file.isFile) {
|
||||
final data = file.content as List<int>;
|
||||
_log.debug('Writing file: ${destination.path}$filename');
|
||||
final extractedFile = File('${destination.path}$filename');
|
||||
final createdFile = await extractedFile.create(recursive: true);
|
||||
await createdFile.writeAsBytes(data);
|
||||
} else {
|
||||
_log.debug('Writing directory: ${destination.path}$filename');
|
||||
Directory('${destination.path}$filename')
|
||||
.createSync(recursive: true);
|
||||
}
|
||||
}
|
||||
|
||||
// check that there is pack.json
|
||||
final packJsonFile = File('${destination.path}pack.json');
|
||||
if (!await packJsonFile.exists()) {
|
||||
_log.error('File is not a icon pack.');
|
||||
//await _cleanTempDirectory(tempDirectory);
|
||||
return false;
|
||||
}
|
||||
|
||||
// remove old icons pack and icon pack cache
|
||||
final packDirectory = Directory(
|
||||
'${documentsDirectory.path}${Platform.pathSeparator}issuer_icons${Platform.pathSeparator}');
|
||||
if (!await _cleanTempDirectory(packDirectory)) {
|
||||
_log.error('Could not remove old pack directory');
|
||||
await _cleanTempDirectory(tempDirectory);
|
||||
return false;
|
||||
}
|
||||
|
||||
final packCacheDirectory = Directory(
|
||||
'${documentsDirectory.path}${Platform.pathSeparator}issuer_icons_cache${Platform.pathSeparator}');
|
||||
if (!await _cleanTempDirectory(packCacheDirectory)) {
|
||||
_log.error('Could not remove old cache directory');
|
||||
await _cleanTempDirectory(tempDirectory);
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
await destination.rename(packDirectory.path);
|
||||
readPack('issuer_icons');
|
||||
|
||||
await _cleanTempDirectory(tempDirectory);
|
||||
return true;
|
||||
}
|
||||
|
||||
VectorGraphic? issuerVectorGraphic(String issuer, Widget placeHolder) {
|
||||
final matching = _issuerIconPack.icons
|
||||
.where((element) => element.issuer.any((element) => element == issuer));
|
||||
|
18
pubspec.lock
18
pubspec.lock
@ -18,7 +18,7 @@ packages:
|
||||
source: hosted
|
||||
version: "5.5.0"
|
||||
archive:
|
||||
dependency: transitive
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: archive
|
||||
sha256: "80e5141fafcb3361653ce308776cfd7d45e6e9fbb429e14eec571382c0c5fecb"
|
||||
@ -217,6 +217,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "6.1.4"
|
||||
file_picker:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: file_picker
|
||||
sha256: d090ae03df98b0247b82e5928f44d1b959867049d18d73635e2e0bc3f49542b9
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "5.2.5"
|
||||
fixnum:
|
||||
dependency: transitive
|
||||
description:
|
||||
@ -248,6 +256,14 @@ packages:
|
||||
description: flutter
|
||||
source: sdk
|
||||
version: "0.0.0"
|
||||
flutter_plugin_android_lifecycle:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: flutter_plugin_android_lifecycle
|
||||
sha256: "60fc7b78455b94e6de2333d2f95196d32cf5c22f4b0b0520a628804cb463503b"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.0.7"
|
||||
flutter_riverpod:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
|
@ -57,6 +57,8 @@ dependencies:
|
||||
vector_graphics: ^1.0.1
|
||||
vector_graphics_compiler: ^1.0.1
|
||||
path: ^1.8.2
|
||||
file_picker: ^5.2.5
|
||||
archive: ^3.3.2
|
||||
|
||||
dev_dependencies:
|
||||
integration_test:
|
||||
|
Loading…
Reference in New Issue
Block a user