Merge branch 'master' of https://git.micazi.dev/micazi/astromic_elements
This commit is contained in:
@@ -1 +1 @@
|
|||||||
{"info":"This is a generated file; do not edit or check into version control.","plugins":{"ios":[{"name":"path_provider_foundation","path":"C:\\\\Users\\\\micwa\\\\AppData\\\\Local\\\\Pub\\\\Cache\\\\hosted\\\\pub.dev\\\\path_provider_foundation-2.4.1\\\\","shared_darwin_source":true,"native_build":true,"dependencies":[],"dev_dependency":false},{"name":"sqflite_darwin","path":"C:\\\\Users\\\\micwa\\\\AppData\\\\Local\\\\Pub\\\\Cache\\\\hosted\\\\pub.dev\\\\sqflite_darwin-2.4.1+1\\\\","shared_darwin_source":true,"native_build":true,"dependencies":[],"dev_dependency":false}],"android":[{"name":"path_provider_android","path":"C:\\\\Users\\\\micwa\\\\AppData\\\\Local\\\\Pub\\\\Cache\\\\hosted\\\\pub.dev\\\\path_provider_android-2.2.15\\\\","native_build":true,"dependencies":[],"dev_dependency":false},{"name":"sqflite_android","path":"C:\\\\Users\\\\micwa\\\\AppData\\\\Local\\\\Pub\\\\Cache\\\\hosted\\\\pub.dev\\\\sqflite_android-2.4.0\\\\","native_build":true,"dependencies":[],"dev_dependency":false}],"macos":[{"name":"path_provider_foundation","path":"C:\\\\Users\\\\micwa\\\\AppData\\\\Local\\\\Pub\\\\Cache\\\\hosted\\\\pub.dev\\\\path_provider_foundation-2.4.1\\\\","shared_darwin_source":true,"native_build":true,"dependencies":[],"dev_dependency":false},{"name":"sqflite_darwin","path":"C:\\\\Users\\\\micwa\\\\AppData\\\\Local\\\\Pub\\\\Cache\\\\hosted\\\\pub.dev\\\\sqflite_darwin-2.4.1+1\\\\","shared_darwin_source":true,"native_build":true,"dependencies":[],"dev_dependency":false}],"linux":[{"name":"path_provider_linux","path":"C:\\\\Users\\\\micwa\\\\AppData\\\\Local\\\\Pub\\\\Cache\\\\hosted\\\\pub.dev\\\\path_provider_linux-2.2.1\\\\","native_build":false,"dependencies":[],"dev_dependency":false}],"windows":[{"name":"path_provider_windows","path":"C:\\\\Users\\\\micwa\\\\AppData\\\\Local\\\\Pub\\\\Cache\\\\hosted\\\\pub.dev\\\\path_provider_windows-2.3.0\\\\","native_build":false,"dependencies":[],"dev_dependency":false}],"web":[]},"dependencyGraph":[{"name":"path_provider","dependencies":["path_provider_android","path_provider_foundation","path_provider_linux","path_provider_windows"]},{"name":"path_provider_android","dependencies":[]},{"name":"path_provider_foundation","dependencies":[]},{"name":"path_provider_linux","dependencies":[]},{"name":"path_provider_windows","dependencies":[]},{"name":"sqflite","dependencies":["sqflite_android","sqflite_darwin"]},{"name":"sqflite_android","dependencies":[]},{"name":"sqflite_darwin","dependencies":[]}],"date_created":"2025-03-19 12:37:24.992698","version":"3.29.0","swift_package_manager_enabled":{"ios":false,"macos":false}}
|
{"info":"This is a generated file; do not edit or check into version control.","plugins":{"ios":[{"name":"path_provider_foundation","path":"/Users/micazi/.pub-cache/hosted/pub.dev/path_provider_foundation-2.4.1/","shared_darwin_source":true,"native_build":true,"dependencies":[],"dev_dependency":false},{"name":"sqflite_darwin","path":"/Users/micazi/.pub-cache/hosted/pub.dev/sqflite_darwin-2.4.2/","shared_darwin_source":true,"native_build":true,"dependencies":[],"dev_dependency":false}],"android":[{"name":"path_provider_android","path":"/Users/micazi/.pub-cache/hosted/pub.dev/path_provider_android-2.2.17/","native_build":true,"dependencies":[],"dev_dependency":false},{"name":"sqflite_android","path":"/Users/micazi/.pub-cache/hosted/pub.dev/sqflite_android-2.4.1/","native_build":true,"dependencies":[],"dev_dependency":false}],"macos":[{"name":"path_provider_foundation","path":"/Users/micazi/.pub-cache/hosted/pub.dev/path_provider_foundation-2.4.1/","shared_darwin_source":true,"native_build":true,"dependencies":[],"dev_dependency":false},{"name":"sqflite_darwin","path":"/Users/micazi/.pub-cache/hosted/pub.dev/sqflite_darwin-2.4.2/","shared_darwin_source":true,"native_build":true,"dependencies":[],"dev_dependency":false}],"linux":[{"name":"path_provider_linux","path":"/Users/micazi/.pub-cache/hosted/pub.dev/path_provider_linux-2.2.1/","native_build":false,"dependencies":[],"dev_dependency":false}],"windows":[{"name":"path_provider_windows","path":"/Users/micazi/.pub-cache/hosted/pub.dev/path_provider_windows-2.3.0/","native_build":false,"dependencies":[],"dev_dependency":false}],"web":[]},"dependencyGraph":[{"name":"path_provider","dependencies":["path_provider_android","path_provider_foundation","path_provider_linux","path_provider_windows"]},{"name":"path_provider_android","dependencies":[]},{"name":"path_provider_foundation","dependencies":[]},{"name":"path_provider_linux","dependencies":[]},{"name":"path_provider_windows","dependencies":[]},{"name":"sqflite","dependencies":["sqflite_android","sqflite_darwin"]},{"name":"sqflite_android","dependencies":[]},{"name":"sqflite_darwin","dependencies":[]}],"date_created":"2025-09-12 18:26:52.817927","version":"3.32.4","swift_package_manager_enabled":{"ios":false,"macos":false}}
|
||||||
@@ -1,8 +1,10 @@
|
|||||||
//s1 Imports
|
//s1 Imports
|
||||||
//s2 Core Package Imports
|
//s2 Core Package Imports
|
||||||
|
import 'dart:ui';
|
||||||
|
|
||||||
|
import 'package:flutter/services.dart';
|
||||||
import 'package:flutter/widgets.dart';
|
import 'package:flutter/widgets.dart';
|
||||||
import 'dart:convert';
|
import 'dart:convert';
|
||||||
import 'dart:typed_data';
|
|
||||||
//s2 1st-party Package Imports
|
//s2 1st-party Package Imports
|
||||||
//s2 3rd-party Package Imports
|
//s2 3rd-party Package Imports
|
||||||
import 'package:cached_network_image/cached_network_image.dart';
|
import 'package:cached_network_image/cached_network_image.dart';
|
||||||
@@ -34,11 +36,10 @@ _DeclaredAssetType _parseAssetType(
|
|||||||
Uint8List? bytes,
|
Uint8List? bytes,
|
||||||
String? fallback,
|
String? fallback,
|
||||||
) {
|
) {
|
||||||
bool fromPath = (path != null && path != '');
|
final bool fromPath = (path != null && path.isNotEmpty);
|
||||||
bool fromBytes = (bytes != null && bytes.isNotEmpty);
|
final bool fromBytes = (bytes != null && bytes.isNotEmpty);
|
||||||
bool fromNetwork = (url != null && url.isNotEmpty && Uri.tryParse(url)?.hasAbsolutePath == true && (url.startsWith('http://') || url.startsWith('https://')));
|
final bool fromNetwork = (url != null && url.isNotEmpty && Uri.tryParse(url)?.hasAbsolutePath == true && (url.startsWith('http://') || url.startsWith('https://')));
|
||||||
|
|
||||||
//
|
|
||||||
return fromPath
|
return fromPath
|
||||||
? _DeclaredAssetType.path
|
? _DeclaredAssetType.path
|
||||||
: fromBytes
|
: fromBytes
|
||||||
@@ -49,8 +50,6 @@ _DeclaredAssetType _parseAssetType(
|
|||||||
}
|
}
|
||||||
|
|
||||||
class AstromicImage extends StatelessWidget {
|
class AstromicImage extends StatelessWidget {
|
||||||
//!SECTION
|
|
||||||
//
|
|
||||||
AstromicImage({
|
AstromicImage({
|
||||||
super.key,
|
super.key,
|
||||||
//
|
//
|
||||||
@@ -79,6 +78,7 @@ class AstromicImage extends StatelessWidget {
|
|||||||
this.blendMode,
|
this.blendMode,
|
||||||
this.fadeInCurve,
|
this.fadeInCurve,
|
||||||
this.fadeInDuration,
|
this.fadeInDuration,
|
||||||
|
this.imageQuality = 0.5,
|
||||||
//
|
//
|
||||||
this.svgColor,
|
this.svgColor,
|
||||||
//
|
//
|
||||||
@@ -103,6 +103,7 @@ class AstromicImage extends StatelessWidget {
|
|||||||
(sizingMaster == ImageSizingMaster.w && (widthSizing != null || fixedWidth != null)) || (sizingMaster == ImageSizingMaster.h && (heightSizing != null || fixedHeight != null)),
|
(sizingMaster == ImageSizingMaster.w && (widthSizing != null || fixedWidth != null)) || (sizingMaster == ImageSizingMaster.h && (heightSizing != null || fixedHeight != null)),
|
||||||
'Please provide the correct sizing configurations based on the SizingMaster chosen.',
|
'Please provide the correct sizing configurations based on the SizingMaster chosen.',
|
||||||
);
|
);
|
||||||
|
|
||||||
// SECTION - Widget Arguments
|
// SECTION - Widget Arguments
|
||||||
// S1 -- Assets
|
// S1 -- Assets
|
||||||
final String? assetPath;
|
final String? assetPath;
|
||||||
@@ -134,6 +135,7 @@ class AstromicImage extends StatelessWidget {
|
|||||||
final BlendMode? blendMode;
|
final BlendMode? blendMode;
|
||||||
final Curve? fadeInCurve;
|
final Curve? fadeInCurve;
|
||||||
final Duration? fadeInDuration;
|
final Duration? fadeInDuration;
|
||||||
|
final double? imageQuality; // 0.0 = very blurry, 1.0 = full quality
|
||||||
// S1 -- SVG FILTERS
|
// S1 -- SVG FILTERS
|
||||||
final Color? svgColor;
|
final Color? svgColor;
|
||||||
// S1 -- STATE WIDGETS
|
// S1 -- STATE WIDGETS
|
||||||
@@ -143,22 +145,20 @@ class AstromicImage extends StatelessWidget {
|
|||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
// SECTION - Build Setup
|
// SECTION - Build Setup
|
||||||
//s1 -Values
|
final _DeclaredAssetType assetType = _parseAssetType(assetPath, assetURL, assetBytes, assetFallback);
|
||||||
_DeclaredAssetType assetType = _parseAssetType(assetPath, assetURL, assetBytes, assetFallback);
|
final dynamic assetRef = _getAssetRef(assetType);
|
||||||
dynamic assetRef = _getAssetRef(assetType);
|
final bool isSVG = _isSVG(assetType, assetRef);
|
||||||
bool isSVG = _isSVG(assetType, assetRef);
|
|
||||||
//s1 -Values
|
|
||||||
//
|
|
||||||
//s1 -Widgets
|
|
||||||
// Default Loading Widget
|
// Default Loading Widget
|
||||||
Widget defaultLoadingWidget = const Text('Loading...');
|
final Widget defaultLoadingWidget = const Text('Loading...');
|
||||||
|
|
||||||
// Default Error Widget
|
// Default Error Widget
|
||||||
Widget defaultErrorWidget(dynamic error) => Text('An error has happened: $error');
|
Widget defaultErrorWidget(dynamic error) => Text('An error has happened: $error');
|
||||||
|
|
||||||
// Get final svg widget
|
// final svg widget (SVGs already handle width/height)
|
||||||
Widget? finalSVGWidget(Size size, Widget? loadingWidget) => assetType == _DeclaredAssetType.path
|
Widget? finalSVGWidget(Size size, Widget? loadingWidget) {
|
||||||
? SvgPicture.asset(
|
if (assetType == _DeclaredAssetType.path && assetRef is String) {
|
||||||
|
return SvgPicture.asset(
|
||||||
assetRef,
|
assetRef,
|
||||||
key: ValueKey<String>(assetRef),
|
key: ValueKey<String>(assetRef),
|
||||||
width: size.width,
|
width: size.width,
|
||||||
@@ -171,9 +171,9 @@ class AstromicImage extends StatelessWidget {
|
|||||||
),
|
),
|
||||||
alignment: alignment!,
|
alignment: alignment!,
|
||||||
colorFilter: svgColor != null ? ColorFilter.mode(svgColor!, blendMode ?? BlendMode.srcATop) : null,
|
colorFilter: svgColor != null ? ColorFilter.mode(svgColor!, blendMode ?? BlendMode.srcATop) : null,
|
||||||
)
|
);
|
||||||
: assetType == _DeclaredAssetType.url
|
} else if (assetType == _DeclaredAssetType.url && assetRef is String) {
|
||||||
? SvgPicture.network(
|
return SvgPicture.network(
|
||||||
assetRef,
|
assetRef,
|
||||||
key: ValueKey<String>(assetRef),
|
key: ValueKey<String>(assetRef),
|
||||||
width: size.width,
|
width: size.width,
|
||||||
@@ -186,23 +186,28 @@ class AstromicImage extends StatelessWidget {
|
|||||||
),
|
),
|
||||||
alignment: alignment!,
|
alignment: alignment!,
|
||||||
colorFilter: svgColor != null ? ColorFilter.mode(svgColor!, blendMode ?? BlendMode.srcATop) : null,
|
colorFilter: svgColor != null ? ColorFilter.mode(svgColor!, blendMode ?? BlendMode.srcATop) : null,
|
||||||
)
|
);
|
||||||
: null;
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
Widget buildImage(Size size) {
|
Widget buildImage(Size size) {
|
||||||
|
// choose filter quality from imageQuality for paint-time interpolation
|
||||||
|
final FilterQuality filterQuality = _filterQualityFromImageQuality(imageQuality ?? 1.0);
|
||||||
|
|
||||||
return Stack(
|
return Stack(
|
||||||
children: <Widget>[
|
children: <Widget>[
|
||||||
OctoImage(
|
OctoImage(
|
||||||
key: ValueKey<String>(assetType == _DeclaredAssetType.bytes ? (assetRef as Uint8List).length.toString() : assetRef),
|
key: ValueKey<String>(
|
||||||
//
|
assetType == _DeclaredAssetType.bytes ? 'bytes-${(assetRef as Uint8List).lengthInBytes}' : (assetRef?.toString() ?? 'unknown'),
|
||||||
|
),
|
||||||
width: size.width,
|
width: size.width,
|
||||||
height: size.height == double.infinity ? null : size.height,
|
height: size.height == double.infinity ? null : size.height,
|
||||||
fit: fit,
|
fit: fit,
|
||||||
alignment: alignment,
|
alignment: alignment,
|
||||||
filterQuality: FilterQuality.none,
|
filterQuality: filterQuality,
|
||||||
color: svgColor,
|
color: svgColor,
|
||||||
colorBlendMode: blendMode ?? (isSVG ? BlendMode.srcATop : null),
|
colorBlendMode: blendMode ?? (isSVG ? BlendMode.srcATop : null),
|
||||||
//
|
|
||||||
errorBuilder: (BuildContext context, Object error, StackTrace? stackTrace) {
|
errorBuilder: (BuildContext context, Object error, StackTrace? stackTrace) {
|
||||||
return errorWidget != null
|
return errorWidget != null
|
||||||
? errorWidget!(error, stackTrace)
|
? errorWidget!(error, stackTrace)
|
||||||
@@ -210,13 +215,11 @@ class AstromicImage extends StatelessWidget {
|
|||||||
? Image.asset(assetFallback!)
|
? Image.asset(assetFallback!)
|
||||||
: defaultErrorWidget(error);
|
: defaultErrorWidget(error);
|
||||||
},
|
},
|
||||||
//
|
|
||||||
progressIndicatorBuilder: (_, ImageChunkEvent? bytes) => SizedBox(
|
progressIndicatorBuilder: (_, ImageChunkEvent? bytes) => SizedBox(
|
||||||
width: size.width,
|
width: size.width,
|
||||||
height: size.height == double.infinity ? null : size.height,
|
height: size.height == double.infinity ? null : size.height,
|
||||||
child: loadingWidget != null ? loadingWidget!(bytes?.cumulativeBytesLoaded, bytes?.expectedTotalBytes) : defaultLoadingWidget,
|
child: loadingWidget != null ? loadingWidget!(bytes?.cumulativeBytesLoaded, bytes?.expectedTotalBytes) : defaultLoadingWidget,
|
||||||
),
|
),
|
||||||
// placeholderBuilder: (BuildContext context) => loadingWidget != null ? loadingWidget!(null, null) : defaultLoadingWidget,
|
|
||||||
fadeInCurve: fadeInCurve,
|
fadeInCurve: fadeInCurve,
|
||||||
fadeInDuration: fadeInDuration,
|
fadeInDuration: fadeInDuration,
|
||||||
imageBuilder: (BuildContext context, Widget image) => Container(
|
imageBuilder: (BuildContext context, Widget image) => Container(
|
||||||
@@ -225,12 +228,7 @@ class AstromicImage extends StatelessWidget {
|
|||||||
padding: borderPadding ?? EdgeInsets.zero,
|
padding: borderPadding ?? EdgeInsets.zero,
|
||||||
margin: EdgeInsets.zero,
|
margin: EdgeInsets.zero,
|
||||||
decoration: BoxDecoration(
|
decoration: BoxDecoration(
|
||||||
border: borderWidth != null
|
border: borderWidth != null ? Border.all(width: borderWidth!, color: borderColor ?? const Color(0xff000000)) : null,
|
||||||
? Border.all(
|
|
||||||
width: borderWidth!,
|
|
||||||
color: borderColor ?? const Color(0xff000000),
|
|
||||||
)
|
|
||||||
: null,
|
|
||||||
borderRadius: isCircular! ? BorderRadius.circular(10000000) : ((radius as BorderRadius).addToAll((borderWidth ?? 0))),
|
borderRadius: isCircular! ? BorderRadius.circular(10000000) : ((radius as BorderRadius).addToAll((borderWidth ?? 0))),
|
||||||
boxShadow: shadow,
|
boxShadow: shadow,
|
||||||
),
|
),
|
||||||
@@ -243,7 +241,9 @@ class AstromicImage extends StatelessWidget {
|
|||||||
child: isSVG ? finalSVGWidget(size, loadingWidget != null ? loadingWidget!(null, null) : defaultLoadingWidget) : image,
|
child: isSVG ? finalSVGWidget(size, loadingWidget != null ? loadingWidget!(null, null) : defaultLoadingWidget) : image,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
image: isSVG ? MemoryImage(kTransparentImage) : _imageProvider(assetType, assetRef),
|
// Provide transparent image placeholder for Octo when rendering raster images;
|
||||||
|
// real provider is created via _imageProvider which uses ResizeImage
|
||||||
|
image: isSVG ? MemoryImage(kTransparentImage) : _imageProvider(assetType, assetRef, size, imageQuality ?? 1.0),
|
||||||
),
|
),
|
||||||
if (overlayColor != null || overlayGradient != null)
|
if (overlayColor != null || overlayGradient != null)
|
||||||
Container(
|
Container(
|
||||||
@@ -252,15 +252,16 @@ class AstromicImage extends StatelessWidget {
|
|||||||
],
|
],
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
//s1 -Widgets
|
|
||||||
//!SECTION
|
|
||||||
|
|
||||||
// SECTION - Build Return
|
// SECTION - Build Return
|
||||||
return LayoutBuilder(builder: (BuildContext context, BoxConstraints constraints) {
|
return LayoutBuilder(builder: (BuildContext context, BoxConstraints constraints) {
|
||||||
Size size = _calculateSize(constraints);
|
Size size = _calculateSize(constraints);
|
||||||
return SizedBox(width: size.width == double.infinity ? null : size.width, height: size.height == double.infinity ? null : size.height, child: buildImage(size));
|
return SizedBox(
|
||||||
|
width: size.width == double.infinity ? null : size.width,
|
||||||
|
height: size.height == double.infinity ? null : size.height,
|
||||||
|
child: buildImage(size),
|
||||||
|
);
|
||||||
});
|
});
|
||||||
//!SECTION
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// SECTION - Helper Functions
|
// SECTION - Helper Functions
|
||||||
@@ -279,43 +280,97 @@ class AstromicImage extends StatelessWidget {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Detect if asset is an SVG...
|
// Detect if asset is an SVG...
|
||||||
bool _isSVG(_DeclaredAssetType type, dynamic ref) =>
|
bool _isSVG(_DeclaredAssetType type, dynamic ref) {
|
||||||
type == _DeclaredAssetType.bytes ? utf8.decode(ref.sublist(0, ref.length > 10 ? 10 : ref.length), allowMalformed: true).trimLeft().startsWith('<svg') : (ref?.endsWith('.svg') ?? false);
|
try {
|
||||||
|
if (type == _DeclaredAssetType.bytes && ref is Uint8List) {
|
||||||
// Get image provider based on type
|
final String prefix = utf8.decode(ref.sublist(0, ref.length > 10 ? 10 : ref.length), allowMalformed: true).trimLeft();
|
||||||
ImageProvider _imageProvider(_DeclaredAssetType type, dynamic ref) {
|
return prefix.startsWith('<svg');
|
||||||
switch (type) {
|
|
||||||
case _DeclaredAssetType.fallback:
|
|
||||||
return AssetImage(ref);
|
|
||||||
case _DeclaredAssetType.path:
|
|
||||||
return AssetImage(ref);
|
|
||||||
case _DeclaredAssetType.bytes:
|
|
||||||
return MemoryImage(ref);
|
|
||||||
case _DeclaredAssetType.url:
|
|
||||||
return CachedNetworkImageProvider(ref, cacheKey: ref);
|
|
||||||
}
|
}
|
||||||
|
if (ref is String) return ref.toLowerCase().endsWith('.svg');
|
||||||
|
return false;
|
||||||
|
} catch (_) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Build image provider and ensure it's resized to (or near) the rendering size.
|
||||||
|
ImageProvider _imageProvider(
|
||||||
|
_DeclaredAssetType type,
|
||||||
|
dynamic ref,
|
||||||
|
Size size,
|
||||||
|
double imageQuality,
|
||||||
|
) {
|
||||||
|
// imageQuality is used as a downscale factor: 1.0 -> full target resolution, 0.5 -> half resolution
|
||||||
|
final double factor = imageQuality.clamp(0.1, 1.0);
|
||||||
|
|
||||||
|
final double dpr = PlatformDispatcher.instance.views.first.devicePixelRatio;
|
||||||
|
|
||||||
|
final int? targetWidth = size.width.isFinite ? (size.width * factor * dpr).clamp(1, 4096).toInt() : null;
|
||||||
|
final int? targetHeight = size.height.isFinite ? (size.height * factor * dpr).clamp(1, 4096).toInt() : null;
|
||||||
|
|
||||||
|
ImageProvider baseProvider;
|
||||||
|
switch (type) {
|
||||||
|
case _DeclaredAssetType.url:
|
||||||
|
baseProvider = CachedNetworkImageProvider(ref as String, cacheKey: ref);
|
||||||
|
break;
|
||||||
|
case _DeclaredAssetType.bytes:
|
||||||
|
baseProvider = MemoryImage(ref as Uint8List);
|
||||||
|
break;
|
||||||
|
case _DeclaredAssetType.path:
|
||||||
|
case _DeclaredAssetType.fallback:
|
||||||
|
baseProvider = AssetImage(ref as String);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// ✅ Skip resizing for AssetImage (Flutter handles resolution variants)
|
||||||
|
if (baseProvider is AssetImage) {
|
||||||
|
return baseProvider;
|
||||||
|
}
|
||||||
|
|
||||||
|
// If both target dims are null (infinite), return base provider (no resize).
|
||||||
|
if (targetWidth == null && targetHeight == null) {
|
||||||
|
return baseProvider;
|
||||||
|
}
|
||||||
|
|
||||||
|
// If one of them is null, supply 0 for that dim (ResizeImage respects non-zero dim).
|
||||||
|
final int w = targetWidth ?? 0;
|
||||||
|
final int h = targetHeight ?? 0;
|
||||||
|
|
||||||
|
// Wrap in ResizeImage so decoding happens closer to desired size.
|
||||||
|
return ResizeImage.resizeIfNeeded(w, h, baseProvider);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Calculate the sizing of the image...
|
// Calculate the sizing of the image...
|
||||||
Size _calculateSize(BoxConstraints constraints) {
|
Size _calculateSize(BoxConstraints constraints) {
|
||||||
double? maxAvailablewidth = constraints.maxWidth;
|
final double maxAvailableWidth = constraints.maxWidth;
|
||||||
double? maxAvailableheight = constraints.maxHeight;
|
final double maxAvailableHeight = constraints.maxHeight;
|
||||||
Size finalSize;
|
Size finalSize;
|
||||||
switch (sizingMaster!) {
|
switch (sizingMaster!) {
|
||||||
case ImageSizingMaster.w:
|
case ImageSizingMaster.w:
|
||||||
{
|
finalSize = Size(
|
||||||
finalSize = Size(fixedWidth ?? (widthSizing!.$1 * maxAvailablewidth).clamp(widthSizing!.$2 ?? 0, widthSizing!.$3 ?? double.infinity), fixedHeight ?? maxAvailableheight);
|
fixedWidth ?? (widthSizing!.$1 * maxAvailableWidth).clamp(widthSizing!.$2 ?? 0, widthSizing!.$3 ?? double.infinity),
|
||||||
}
|
fixedHeight ?? maxAvailableHeight,
|
||||||
|
);
|
||||||
|
break;
|
||||||
case ImageSizingMaster.h:
|
case ImageSizingMaster.h:
|
||||||
{
|
finalSize = Size(
|
||||||
finalSize = Size(fixedWidth ?? maxAvailablewidth, fixedHeight ?? (heightSizing!.$1 * maxAvailableheight).clamp(heightSizing!.$2 ?? 0, heightSizing!.$3 ?? double.infinity));
|
fixedWidth ?? maxAvailableWidth,
|
||||||
}
|
fixedHeight ?? (heightSizing!.$1 * maxAvailableHeight).clamp(heightSizing!.$2 ?? 0, heightSizing!.$3 ?? double.infinity),
|
||||||
|
);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
return finalSize;
|
return finalSize;
|
||||||
}
|
}
|
||||||
//!SECTION
|
|
||||||
|
// Map imageQuality to a reasonable FilterQuality for paint-time resampling
|
||||||
|
FilterQuality _filterQualityFromImageQuality(double q) {
|
||||||
|
if (q >= 0.85) return FilterQuality.high;
|
||||||
|
if (q >= 0.5) return FilterQuality.medium;
|
||||||
|
return FilterQuality.low;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Transparent png for svg placeholder
|
||||||
final Uint8List kTransparentImage = Uint8List.fromList(<int>[
|
final Uint8List kTransparentImage = Uint8List.fromList(<int>[
|
||||||
0x89,
|
0x89,
|
||||||
0x50,
|
0x50,
|
||||||
|
|||||||
@@ -46,6 +46,7 @@ class AstromicWidgets {
|
|||||||
Color? svgColor,
|
Color? svgColor,
|
||||||
Widget Function(int? loadedBytes, int? totalBytesToLoad)? loadingWidget,
|
Widget Function(int? loadedBytes, int? totalBytesToLoad)? loadingWidget,
|
||||||
Widget Function(dynamic error, StackTrace? stackTrace)? errorWidget,
|
Widget Function(dynamic error, StackTrace? stackTrace)? errorWidget,
|
||||||
|
double? imageQuality,
|
||||||
}) =>
|
}) =>
|
||||||
AstromicImage(
|
AstromicImage(
|
||||||
assetPath: assetPath,
|
assetPath: assetPath,
|
||||||
@@ -77,6 +78,7 @@ class AstromicWidgets {
|
|||||||
svgColor: svgColor,
|
svgColor: svgColor,
|
||||||
loadingWidget: loadingWidget,
|
loadingWidget: loadingWidget,
|
||||||
errorWidget: errorWidget,
|
errorWidget: errorWidget,
|
||||||
|
imageQuality: imageQuality,
|
||||||
);
|
);
|
||||||
|
|
||||||
/// Customized Blur widget for the Astromic system.
|
/// Customized Blur widget for the Astromic system.
|
||||||
|
|||||||
Reference in New Issue
Block a user