l10n: number format
This commit is contained in:
parent
2628192e06
commit
94659ae8af
14 changed files with 105 additions and 102 deletions
|
@ -1,20 +1,23 @@
|
||||||
|
import 'package:equatable/equatable.dart';
|
||||||
import 'package:flutter/foundation.dart';
|
import 'package:flutter/foundation.dart';
|
||||||
import 'package:intl/intl.dart';
|
|
||||||
|
|
||||||
class OverlayMetadata {
|
@immutable
|
||||||
final String? aperture, exposureTime, focalLength, iso;
|
class OverlayMetadata extends Equatable {
|
||||||
|
final double? aperture, focalLength;
|
||||||
|
final String? exposureTime;
|
||||||
|
final int? iso;
|
||||||
|
|
||||||
static final apertureFormat = NumberFormat('0.0', 'en_US');
|
@override
|
||||||
static final focalLengthFormat = NumberFormat('0.#', 'en_US');
|
List<Object?> get props => [aperture, exposureTime, focalLength, iso];
|
||||||
|
|
||||||
OverlayMetadata({
|
bool get isEmpty => aperture == null && exposureTime == null && focalLength == null && iso == null;
|
||||||
double? aperture,
|
|
||||||
|
const OverlayMetadata({
|
||||||
|
this.aperture,
|
||||||
this.exposureTime,
|
this.exposureTime,
|
||||||
double? focalLength,
|
this.focalLength,
|
||||||
int? iso,
|
this.iso,
|
||||||
}) : aperture = aperture != null ? 'ƒ/${apertureFormat.format(aperture)}' : null,
|
});
|
||||||
focalLength = focalLength != null ? '${focalLengthFormat.format(focalLength)} mm' : null,
|
|
||||||
iso = iso != null ? 'ISO$iso' : null;
|
|
||||||
|
|
||||||
factory OverlayMetadata.fromMap(Map map) {
|
factory OverlayMetadata.fromMap(Map map) {
|
||||||
return OverlayMetadata(
|
return OverlayMetadata(
|
||||||
|
@ -24,9 +27,4 @@ class OverlayMetadata {
|
||||||
iso: map['iso'] as int?,
|
iso: map['iso'] as int?,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool get isEmpty => aperture == null && exposureTime == null && focalLength == null && iso == null;
|
|
||||||
|
|
||||||
@override
|
|
||||||
String toString() => '$runtimeType#${shortHash(this)}{aperture=$aperture, exposureTime=$exposureTime, focalLength=$focalLength, iso=$iso}';
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,6 +2,7 @@ import 'package:aves/utils/geo_utils.dart';
|
||||||
import 'package:aves/widgets/common/extensions/build_context.dart';
|
import 'package:aves/widgets/common/extensions/build_context.dart';
|
||||||
import 'package:flutter/widgets.dart';
|
import 'package:flutter/widgets.dart';
|
||||||
import 'package:flutter_gen/gen_l10n/app_localizations.dart';
|
import 'package:flutter_gen/gen_l10n/app_localizations.dart';
|
||||||
|
import 'package:intl/intl.dart';
|
||||||
import 'package:latlong2/latlong.dart';
|
import 'package:latlong2/latlong.dart';
|
||||||
|
|
||||||
import 'enums.dart';
|
import 'enums.dart';
|
||||||
|
@ -16,24 +17,36 @@ extension ExtraCoordinateFormat on CoordinateFormat {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static const _separator = ', ';
|
||||||
|
|
||||||
String format(AppLocalizations l10n, LatLng latLng, {bool minuteSecondPadding = false, int dmsSecondDecimals = 2}) {
|
String format(AppLocalizations l10n, LatLng latLng, {bool minuteSecondPadding = false, int dmsSecondDecimals = 2}) {
|
||||||
switch (this) {
|
switch (this) {
|
||||||
case CoordinateFormat.dms:
|
case CoordinateFormat.dms:
|
||||||
return toDMS(l10n, latLng, minuteSecondPadding: minuteSecondPadding, secondDecimals: dmsSecondDecimals).join(', ');
|
return toDMS(l10n, latLng, minuteSecondPadding: minuteSecondPadding, secondDecimals: dmsSecondDecimals).join(_separator);
|
||||||
case CoordinateFormat.decimal:
|
case CoordinateFormat.decimal:
|
||||||
return [latLng.latitude, latLng.longitude].map((n) => n.toStringAsFixed(6)).join(', ');
|
return _toDecimal(l10n, latLng).join(_separator);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// returns coordinates formatted as DMS, e.g. ['41° 24′ 12.2″ N', '2° 10′ 26.5″ E']
|
// returns coordinates formatted as DMS, e.g. ['41° 24′ 12.2″ N', '2° 10′ 26.5″ E']
|
||||||
static List<String> toDMS(AppLocalizations l10n, LatLng latLng, {bool minuteSecondPadding = false, int secondDecimals = 2}) {
|
static List<String> toDMS(AppLocalizations l10n, LatLng latLng, {bool minuteSecondPadding = false, int secondDecimals = 2}) {
|
||||||
|
final locale = l10n.localeName;
|
||||||
final lat = latLng.latitude;
|
final lat = latLng.latitude;
|
||||||
final lng = latLng.longitude;
|
final lng = latLng.longitude;
|
||||||
final latSexa = GeoUtils.decimal2sexagesimal(lat, minuteSecondPadding, secondDecimals);
|
final latSexa = GeoUtils.decimal2sexagesimal(lat, minuteSecondPadding, secondDecimals, locale);
|
||||||
final lngSexa = GeoUtils.decimal2sexagesimal(lng, minuteSecondPadding, secondDecimals);
|
final lngSexa = GeoUtils.decimal2sexagesimal(lng, minuteSecondPadding, secondDecimals, locale);
|
||||||
return [
|
return [
|
||||||
l10n.coordinateDms(latSexa, lat < 0 ? l10n.coordinateDmsSouth : l10n.coordinateDmsNorth),
|
l10n.coordinateDms(latSexa, lat < 0 ? l10n.coordinateDmsSouth : l10n.coordinateDmsNorth),
|
||||||
l10n.coordinateDms(lngSexa, lng < 0 ? l10n.coordinateDmsWest : l10n.coordinateDmsEast),
|
l10n.coordinateDms(lngSexa, lng < 0 ? l10n.coordinateDmsWest : l10n.coordinateDmsEast),
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static List<String> _toDecimal(AppLocalizations l10n, LatLng latLng) {
|
||||||
|
final locale = l10n.localeName;
|
||||||
|
final formatter = NumberFormat('0.000000°', locale);
|
||||||
|
return [
|
||||||
|
formatter.format(latLng.latitude),
|
||||||
|
formatter.format(latLng.longitude),
|
||||||
|
];
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -374,7 +374,7 @@ class VideoMetadataFormatter {
|
||||||
|
|
||||||
static String _formatFilesize(String value) {
|
static String _formatFilesize(String value) {
|
||||||
final size = int.tryParse(value);
|
final size = int.tryParse(value);
|
||||||
return size != null ? formatFilesize(size) : value;
|
return size != null ? formatFileSize('en_US', size) : value;
|
||||||
}
|
}
|
||||||
|
|
||||||
static String _formatLanguage(String value) {
|
static String _formatLanguage(String value) {
|
||||||
|
@ -399,20 +399,10 @@ class VideoMetadataFormatter {
|
||||||
if (parsed == null) return size;
|
if (parsed == null) return size;
|
||||||
size = parsed;
|
size = parsed;
|
||||||
}
|
}
|
||||||
|
|
||||||
const divider = 1000;
|
const divider = 1000;
|
||||||
|
|
||||||
if (size < divider) return '$size $unit';
|
if (size < divider) return '$size $unit';
|
||||||
|
if (size < divider * divider) return '${(size / divider).toStringAsFixed(round)} K$unit';
|
||||||
if (size < divider * divider && size % divider == 0) {
|
|
||||||
return '${(size / divider).toStringAsFixed(0)} K$unit';
|
|
||||||
}
|
|
||||||
if (size < divider * divider) {
|
|
||||||
return '${(size / divider).toStringAsFixed(round)} K$unit';
|
|
||||||
}
|
|
||||||
|
|
||||||
if (size < divider * divider * divider && size % divider == 0) {
|
|
||||||
return '${(size / (divider * divider)).toStringAsFixed(0)} M$unit';
|
|
||||||
}
|
|
||||||
return '${(size / divider / divider).toStringAsFixed(round)} M$unit';
|
return '${(size / divider / divider).toStringAsFixed(round)} M$unit';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,38 +1,16 @@
|
||||||
String formatFilesize(int size, {int round = 2}) {
|
import 'package:intl/intl.dart';
|
||||||
var divider = 1024;
|
|
||||||
|
|
||||||
if (size < divider) return '$size B';
|
const _kiloDivider = 1024;
|
||||||
|
const _megaDivider = _kiloDivider * _kiloDivider;
|
||||||
|
const _gigaDivider = _megaDivider * _kiloDivider;
|
||||||
|
const _teraDivider = _gigaDivider * _kiloDivider;
|
||||||
|
|
||||||
if (size < divider * divider && size % divider == 0) {
|
String formatFileSize(String locale, int size, {int round = 2}) {
|
||||||
return '${(size / divider).toStringAsFixed(0)} KB';
|
if (size < _kiloDivider) return '$size B';
|
||||||
}
|
|
||||||
if (size < divider * divider) {
|
|
||||||
return '${(size / divider).toStringAsFixed(round)} KB';
|
|
||||||
}
|
|
||||||
|
|
||||||
if (size < divider * divider * divider && size % divider == 0) {
|
final formatter = NumberFormat('0${round > 0 ? '.${'0' * round}' : ''}', locale);
|
||||||
return '${(size / (divider * divider)).toStringAsFixed(0)} MB';
|
if (size < _megaDivider) return '${formatter.format(size / _kiloDivider)} KB';
|
||||||
}
|
if (size < _gigaDivider) return '${formatter.format(size / _megaDivider)} MB';
|
||||||
if (size < divider * divider * divider) {
|
if (size < _teraDivider) return '${formatter.format(size / _gigaDivider)} GB';
|
||||||
return '${(size / divider / divider).toStringAsFixed(round)} MB';
|
return '${formatter.format(size / _teraDivider)} TB';
|
||||||
}
|
|
||||||
|
|
||||||
if (size < divider * divider * divider * divider && size % divider == 0) {
|
|
||||||
return '${(size / (divider * divider * divider)).toStringAsFixed(0)} GB';
|
|
||||||
}
|
|
||||||
if (size < divider * divider * divider * divider) {
|
|
||||||
return '${(size / divider / divider / divider).toStringAsFixed(round)} GB';
|
|
||||||
}
|
|
||||||
|
|
||||||
if (size < divider * divider * divider * divider * divider && size % divider == 0) {
|
|
||||||
return '${(size / divider / divider / divider / divider).toStringAsFixed(0)} TB';
|
|
||||||
}
|
|
||||||
if (size < divider * divider * divider * divider * divider) {
|
|
||||||
return '${(size / divider / divider / divider / divider).toStringAsFixed(round)} TB';
|
|
||||||
}
|
|
||||||
|
|
||||||
if (size < divider * divider * divider * divider * divider * divider && size % divider == 0) {
|
|
||||||
return '${(size / divider / divider / divider / divider / divider).toStringAsFixed(0)} PB';
|
|
||||||
}
|
|
||||||
return '${(size / divider / divider / divider / divider / divider).toStringAsFixed(round)} PB';
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,33 +1,23 @@
|
||||||
import 'dart:math';
|
import 'dart:math';
|
||||||
|
|
||||||
import 'package:aves/utils/math_utils.dart';
|
|
||||||
import 'package:intl/intl.dart';
|
import 'package:intl/intl.dart';
|
||||||
import 'package:latlong2/latlong.dart';
|
import 'package:latlong2/latlong.dart';
|
||||||
|
|
||||||
class GeoUtils {
|
class GeoUtils {
|
||||||
static String decimal2sexagesimal(final double degDecimal, final bool minuteSecondPadding, final int secondDecimals) {
|
static String decimal2sexagesimal(
|
||||||
List<int> _split(final double value) {
|
double degDecimal,
|
||||||
// NumberFormat is necessary to create digit after comma if the value
|
bool minuteSecondPadding,
|
||||||
// has no decimal point (only necessary for browser)
|
int secondDecimals,
|
||||||
final tmp = NumberFormat('0.0#####').format(roundToPrecision(value, decimals: 10)).split('.');
|
String locale,
|
||||||
return <int>[
|
) {
|
||||||
int.parse(tmp[0]).abs(),
|
final degAbs = degDecimal.abs();
|
||||||
int.parse(tmp[1]),
|
final deg = degAbs.toInt();
|
||||||
];
|
final minDecimal = (degAbs - deg) * 60;
|
||||||
}
|
final min = minDecimal.toInt();
|
||||||
|
|
||||||
final deg = _split(degDecimal)[0];
|
|
||||||
final minDecimal = (degDecimal.abs() - deg) * 60;
|
|
||||||
final min = _split(minDecimal)[0];
|
|
||||||
final sec = (minDecimal - min) * 60;
|
final sec = (minDecimal - min) * 60;
|
||||||
|
|
||||||
final secRounded = roundToPrecision(sec, decimals: secondDecimals);
|
var minText = NumberFormat('0' * (minuteSecondPadding ? 2 : 1), locale).format(min);
|
||||||
var minText = '$min';
|
var secText = NumberFormat('${'0' * (minuteSecondPadding ? 2 : 1)}${secondDecimals > 0 ? '.${'0' * secondDecimals}' : ''}', locale).format(sec);
|
||||||
var secText = secRounded.toStringAsFixed(secondDecimals);
|
|
||||||
if (minuteSecondPadding) {
|
|
||||||
minText = minText.padLeft(2, '0');
|
|
||||||
secText = secText.padLeft(secondDecimals > 0 ? 3 + secondDecimals : 2, '0');
|
|
||||||
}
|
|
||||||
|
|
||||||
return '$deg° $minText′ $secText″';
|
return '$deg° $minText′ $secText″';
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,6 +3,7 @@ import 'package:aves/model/source/collection_lens.dart';
|
||||||
import 'package:aves/model/source/collection_source.dart';
|
import 'package:aves/model/source/collection_source.dart';
|
||||||
import 'package:aves/model/source/enums.dart';
|
import 'package:aves/model/source/enums.dart';
|
||||||
import 'package:aves/utils/file_utils.dart';
|
import 'package:aves/utils/file_utils.dart';
|
||||||
|
import 'package:aves/widgets/common/extensions/build_context.dart';
|
||||||
import 'package:aves/widgets/common/grid/draggable_thumb_label.dart';
|
import 'package:aves/widgets/common/grid/draggable_thumb_label.dart';
|
||||||
import 'package:aves/widgets/common/grid/section_layout.dart';
|
import 'package:aves/widgets/common/grid/section_layout.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
|
@ -48,7 +49,7 @@ class CollectionDraggableThumbLabel extends StatelessWidget {
|
||||||
];
|
];
|
||||||
case EntrySortFactor.size:
|
case EntrySortFactor.size:
|
||||||
return [
|
return [
|
||||||
if (entry.sizeBytes != null) formatFilesize(entry.sizeBytes!, round: 0),
|
if (entry.sizeBytes != null) formatFileSize(context.l10n.localeName, entry.sizeBytes!, round: 0),
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
|
@ -75,13 +75,15 @@ mixin SizeAwareMixin {
|
||||||
await showDialog(
|
await showDialog(
|
||||||
context: context,
|
context: context,
|
||||||
builder: (context) {
|
builder: (context) {
|
||||||
final neededSize = formatFilesize(needed);
|
final l10n = context.l10n;
|
||||||
final freeSize = formatFilesize(free);
|
final locale = l10n.localeName;
|
||||||
|
final neededSize = formatFileSize(locale, needed);
|
||||||
|
final freeSize = formatFileSize(locale, free);
|
||||||
final volume = destinationVolume.getDescription(context);
|
final volume = destinationVolume.getDescription(context);
|
||||||
return AvesDialog(
|
return AvesDialog(
|
||||||
context: context,
|
context: context,
|
||||||
title: context.l10n.notEnoughSpaceDialogTitle,
|
title: l10n.notEnoughSpaceDialogTitle,
|
||||||
content: Text(context.l10n.notEnoughSpaceDialogMessage(neededSize, freeSize, volume)),
|
content: Text(l10n.notEnoughSpaceDialogMessage(neededSize, freeSize, volume)),
|
||||||
actions: [
|
actions: [
|
||||||
TextButton(
|
TextButton(
|
||||||
onPressed: () => Navigator.pop(context),
|
onPressed: () => Navigator.pop(context),
|
||||||
|
|
|
@ -25,7 +25,7 @@ class _DebugCacheSectionState extends State<DebugCacheSection> with AutomaticKee
|
||||||
Row(
|
Row(
|
||||||
children: [
|
children: [
|
||||||
Expanded(
|
Expanded(
|
||||||
child: Text('Image cache:\n\t${imageCache!.currentSize}/${imageCache!.maximumSize} items\n\t${formatFilesize(imageCache!.currentSizeBytes)}/${formatFilesize(imageCache!.maximumSizeBytes)}'),
|
child: Text('Image cache:\n\t${imageCache!.currentSize}/${imageCache!.maximumSize} items\n\t${formatFileSize('en_US', imageCache!.currentSizeBytes)}/${formatFileSize('en_US', imageCache!.maximumSizeBytes)}'),
|
||||||
),
|
),
|
||||||
const SizedBox(width: 8),
|
const SizedBox(width: 8),
|
||||||
ElevatedButton(
|
ElevatedButton(
|
||||||
|
|
|
@ -53,7 +53,7 @@ class _DebugAppDatabaseSectionState extends State<DebugAppDatabaseSection> with
|
||||||
return Row(
|
return Row(
|
||||||
children: [
|
children: [
|
||||||
Expanded(
|
Expanded(
|
||||||
child: Text('DB file size: ${formatFilesize(snapshot.data!)}'),
|
child: Text('DB file size: ${formatFileSize('en_US', snapshot.data!)}'),
|
||||||
),
|
),
|
||||||
const SizedBox(width: 8),
|
const SizedBox(width: 8),
|
||||||
ElevatedButton(
|
ElevatedButton(
|
||||||
|
|
|
@ -46,7 +46,7 @@ class _DebugStorageSectionState extends State<DebugStorageSection> with Automati
|
||||||
'isPrimary': '${v.isPrimary}',
|
'isPrimary': '${v.isPrimary}',
|
||||||
'isRemovable': '${v.isRemovable}',
|
'isRemovable': '${v.isRemovable}',
|
||||||
'state': v.state,
|
'state': v.state,
|
||||||
if (freeSpace != null) 'freeSpace': formatFilesize(freeSpace),
|
if (freeSpace != null) 'freeSpace': formatFileSize('en_US', freeSpace),
|
||||||
},
|
},
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
|
|
@ -60,7 +60,7 @@ class BasicSection extends StatelessWidget {
|
||||||
final date = entry.bestDate;
|
final date = entry.bestDate;
|
||||||
final dateText = date != null ? formatDateTime(date, locale, use24hour) : infoUnknown;
|
final dateText = date != null ? formatDateTime(date, locale, use24hour) : infoUnknown;
|
||||||
final showResolution = !entry.isSvg && entry.isSized;
|
final showResolution = !entry.isSvg && entry.isSized;
|
||||||
final sizeText = entry.sizeBytes != null ? formatFilesize(entry.sizeBytes!) : infoUnknown;
|
final sizeText = entry.sizeBytes != null ? formatFileSize(locale, entry.sizeBytes!) : infoUnknown;
|
||||||
final path = entry.path;
|
final path = entry.path;
|
||||||
|
|
||||||
return Column(
|
return Column(
|
||||||
|
|
|
@ -20,6 +20,7 @@ import 'package:aves/widgets/viewer/page_entry_builder.dart';
|
||||||
import 'package:decorated_icon/decorated_icon.dart';
|
import 'package:decorated_icon/decorated_icon.dart';
|
||||||
import 'package:flutter/foundation.dart';
|
import 'package:flutter/foundation.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:intl/intl.dart';
|
||||||
import 'package:provider/provider.dart';
|
import 'package:provider/provider.dart';
|
||||||
import 'package:tuple/tuple.dart';
|
import 'package:tuple/tuple.dart';
|
||||||
|
|
||||||
|
@ -423,14 +424,25 @@ class _ShootingRow extends StatelessWidget {
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
|
final locale = context.l10n.localeName;
|
||||||
|
|
||||||
|
final aperture = details.aperture;
|
||||||
|
final apertureText = aperture != null ? 'ƒ/${NumberFormat('0.0', locale).format(aperture)}' : Constants.overlayUnknown;
|
||||||
|
|
||||||
|
final focalLength = details.focalLength;
|
||||||
|
final focalLengthText = focalLength != null ? '${NumberFormat('0.#', locale).format(focalLength)} mm' : Constants.overlayUnknown;
|
||||||
|
|
||||||
|
final iso = details.iso;
|
||||||
|
final isoText = iso != null ? 'ISO$iso' : Constants.overlayUnknown;
|
||||||
|
|
||||||
return Row(
|
return Row(
|
||||||
children: [
|
children: [
|
||||||
const DecoratedIcon(AIcons.shooting, shadows: Constants.embossShadows, size: _iconSize),
|
const DecoratedIcon(AIcons.shooting, shadows: Constants.embossShadows, size: _iconSize),
|
||||||
const SizedBox(width: _iconPadding),
|
const SizedBox(width: _iconPadding),
|
||||||
Expanded(child: Text(details.aperture ?? Constants.overlayUnknown, strutStyle: Constants.overflowStrutStyle)),
|
Expanded(child: Text(apertureText, strutStyle: Constants.overflowStrutStyle)),
|
||||||
Expanded(child: Text(details.exposureTime ?? Constants.overlayUnknown, strutStyle: Constants.overflowStrutStyle)),
|
Expanded(child: Text(details.exposureTime ?? Constants.overlayUnknown, strutStyle: Constants.overflowStrutStyle)),
|
||||||
Expanded(child: Text(details.focalLength ?? Constants.overlayUnknown, strutStyle: Constants.overflowStrutStyle)),
|
Expanded(child: Text(focalLengthText, strutStyle: Constants.overflowStrutStyle)),
|
||||||
Expanded(child: Text(details.iso ?? Constants.overlayUnknown, strutStyle: Constants.overflowStrutStyle)),
|
Expanded(child: Text(isoText, strutStyle: Constants.overflowStrutStyle)),
|
||||||
],
|
],
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
16
test/utils/file_utils_test.dart
Normal file
16
test/utils/file_utils_test.dart
Normal file
|
@ -0,0 +1,16 @@
|
||||||
|
import 'package:aves/model/settings/coordinate_format.dart';
|
||||||
|
import 'package:aves/utils/file_utils.dart';
|
||||||
|
import 'package:aves/utils/geo_utils.dart';
|
||||||
|
import 'package:flutter_gen/gen_l10n/app_localizations.dart';
|
||||||
|
import 'package:latlong2/latlong.dart';
|
||||||
|
import 'package:test/test.dart';
|
||||||
|
|
||||||
|
void main() {
|
||||||
|
test('format file size', () {
|
||||||
|
final l10n = lookupAppLocalizations(AppLocalizations.supportedLocales.first);
|
||||||
|
final locale = l10n.localeName;
|
||||||
|
expect(formatFileSize(locale, 1024), '1.00 KB');
|
||||||
|
expect(formatFileSize(locale, 1536), '1.50 KB');
|
||||||
|
expect(formatFileSize(locale, 1073741824), '1.00 GB');
|
||||||
|
});
|
||||||
|
}
|
|
@ -12,6 +12,9 @@ void main() {
|
||||||
expect(ExtraCoordinateFormat.toDMS(l10n, LatLng(-38.6965891, 175.9830047)), ['38° 41′ 47.72″ S', '175° 58′ 58.82″ E']); // Taupo
|
expect(ExtraCoordinateFormat.toDMS(l10n, LatLng(-38.6965891, 175.9830047)), ['38° 41′ 47.72″ S', '175° 58′ 58.82″ E']); // Taupo
|
||||||
expect(ExtraCoordinateFormat.toDMS(l10n, LatLng(-64.249391, -56.6556145)), ['64° 14′ 57.81″ S', '56° 39′ 20.21″ W']); // Marambio
|
expect(ExtraCoordinateFormat.toDMS(l10n, LatLng(-64.249391, -56.6556145)), ['64° 14′ 57.81″ S', '56° 39′ 20.21″ W']); // Marambio
|
||||||
expect(ExtraCoordinateFormat.toDMS(l10n, LatLng(0, 0)), ['0° 0′ 0.00″ N', '0° 0′ 0.00″ E']);
|
expect(ExtraCoordinateFormat.toDMS(l10n, LatLng(0, 0)), ['0° 0′ 0.00″ N', '0° 0′ 0.00″ E']);
|
||||||
|
expect(ExtraCoordinateFormat.toDMS(l10n, LatLng(0, 0), minuteSecondPadding: true), ['0° 00′ 00.00″ N', '0° 00′ 00.00″ E']);
|
||||||
|
expect(ExtraCoordinateFormat.toDMS(l10n, LatLng(0, 0), secondDecimals: 0), ['0° 0′ 0″ N', '0° 0′ 0″ E']);
|
||||||
|
expect(ExtraCoordinateFormat.toDMS(l10n, LatLng(0, 0), secondDecimals: 4), ['0° 0′ 0.0000″ N', '0° 0′ 0.0000″ E']);
|
||||||
});
|
});
|
||||||
|
|
||||||
test('bounds center', () {
|
test('bounds center', () {
|
||||||
|
|
Loading…
Reference in a new issue