微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

在 Xamarin.Forms 中序列化 ImageSource

如何解决在 Xamarin.Forms 中序列化 ImageSource

我正在尝试序列化一个成员为 ImageSource 类型的类。 类是:

    public class AppInfo
    {
        public string Name { get; set; }
        public ImageSource Icon { get; set; }
        public bool Is90Hz { get; set; }
    }

我像这样获取类的数据:

        private static IList<AppInfo> GetAppInfos()
        {
            var localAppInfo = new List<AppInfo>();
            var allAppsRaw = DependencyService.Get<IGetAllApps>().GetApps();

            var pm = Android.App.Application.Context.PackageManager;
            if (pm == null)
                return null;

            foreach (var info in allAppsRaw)
            {
                var bitmap = DependencyService.Get<IGetAllApps>().DrawabletoBitmap(info.LoadIcon(pm));
                byte[] bitmapData;

                using (var stream = new MemoryStream())
                {
                    bitmap.Compress(Bitmap.CompressFormat.Png,stream);
                    bitmapData = stream.ToArray();
                }

                var imageSource = ImageSource.FromStream(() => new MemoryStream(bitmapData,bitmapData.Length));

                localAppInfo.Add(new AppInfo { Name = info.LoadLabel(pm),Icon = imageSource,Is90Hz = true });
            }

            return localAppInfo;
        }

问题在于 System.Text.Json 无法序列化该类型。我反复搜索如何将其转换为字节数组或 Base64 字符串,但我有点迷茫。

我向成员添加[JsonConverter(typeof(ImageSourceConverter))] 并声明了我的转换器类,如下所示:

    public class ImageSourceConverter : JsonConverter<ImageSource>
    {
        public override ImageSource Read(ref Utf8JsonReader reader,Type typetoConvert,JsonSerializerOptions options)
        {
        }

        public override void Write(Utf8JsonWriter writer,ImageSource value,JsonSerializerOptions options)
        {
        }
    }

但我现在有点迷茫......只是无法弄清楚读写方法的逻辑。

*编辑: 最终目标是展示它,目前的做法是:

        <ListView Grid.Column="3" x:Name="AppsView" CachingStrategy="RecycleElement" Margin="10,10,10">
            <ListView.ItemTemplate>
                <DataTemplate>
                    <ViewCell>
                        <StackLayout Orientation="Horizontal" CompressedLayout.IsHeadless="true">
                            <Image Source="{Binding Icon,Mode=TwoWay}" WidthRequest="40" HeightRequest="40" HorizontalOptions="StartAndExpand"/>
                            <Label Text="{Binding Name,Mode=TwoWay}" VerticalOptions="CenterandExpand" HorizontalOptions="CenterandExpand"/>
                            <Switch IsToggled="{Binding Is90Hz,Mode=TwoWay}" HorizontalOptions="EndAndExpand"/>
                        </StackLayout>
                    </ViewCell>
                </DataTemplate>
            </ListView.ItemTemplate>
        </ListView>
    </ContentPage.Content>

解决方法

Xamarin.Forms 使用 Image 视图在页面上显示图像。它有几个重要的属性:

Source - 一个 ImageSource 实例,可以是 File、Uri 或 Resource,用于设置要显示的图像。

ImageSource 可以使用每种类型的图像源的静态方法获取实例:

  • FromFile - 需要可以在每个平台上解析的文件名或文件路径。

  • FromUri - 需要一个 Uri 对象,例如。 new Uri("http://....") .

  • FromResource - 需要嵌入在应用程序或 .NET Standard 库项目中的图像文件的资源标识符,并带有 构建操作:EmbeddedResource。

  • FromStream - 需要提供图像数据的流。

所以你可以尝试绑定流:

改变

public ImageSource Icon { get; set; }

public Stream Icon { get; set; }

然后添加流:

var imageSource = new MemoryStream(bitmapData,bitmapData.Length);

localAppInfo.Add(new AppInfo { Name = info.LoadLabel(pm),Icon = imageSource,Is90Hz = true });

在您的 xaml 中:

<Image>
    <Image.Source>
       <StreamImageSource Stream="{Binding Icon}"
    </Image.Source>
</Image>
,

谢谢,我最终用转换器做了类似的事情。 在我的 xaml 中:

    <ContentPage.Resources>
         <ResourceDictionary>
              <api:ByteArrayToImageConverter x:Key="Bti"/>
         </ResourceDictionary>
    </ContentPage.Resources>
<Image Source="{Binding Icon,Converter={StaticResource Bti},Mode=Default}" WidthRequest="37" HeightRequest="37" HorizontalOptions="StartAndExpand"/>

转换器类:

    public class ByteArrayToImageConverter : IValueConverter
    {
        public object Convert(object value,Type targetType,object parameter,System.Globalization.CultureInfo culture)
        {
            if (value == null)
                return null;

            var imageAsBytes = (byte[])value;
            return ImageSource.FromStream(() => new MemoryStream(imageAsBytes));
        }

        public object ConvertBack(object value,System.Globalization.CultureInfo culture) =>
                throw new NotImplementedException();
    }

我只是将照片保存为 byte[] :

                var bitmap = DependencyService.Get<IGetAllApps>().DrawableToBitmap(info.LoadIcon(pm));
                byte[] bitmapData;

                using (var stream = new MemoryStream())
                {
                    bitmap.Compress(Bitmap.CompressFormat.Png,stream);
                    bitmapData = stream.ToArray();
                }

                localAppInfo.Add(new AppInfo
                    {Name = info.LoadLabel(pm),PackageName = info.PackageName,Icon = bitmapData,Is90Hz = true});

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。