public override void Serialize(ContentSerializerContext context, SerializationStream stream, Image textureData) { if (context.Mode == ArchiveMode.Deserialize) { var isStreamable = stream.ReadBoolean(); if (!isStreamable) { var image = Image.Load(stream.NativeStream); textureData.InitializeFrom(image); } else { // Read image header var imageDescription = new ImageDescription(); ImageHelper.ImageDescriptionSerializer.Serialize(ref imageDescription, ArchiveMode.Deserialize, stream); // Read content storage header ContentStorageHeader storageHeader; ContentStorageHeader.Read(stream, out storageHeader); // Deserialize whole texture to image without streaming feature var contentSerializerContext = stream.Context.Get(ContentSerializerContext.ContentSerializerContextProperty); DeserializeImage(contentSerializerContext.ContentManager, textureData, ref imageDescription, ref storageHeader); } } else { textureData.Save(stream.NativeStream, ImageFileType.Xenko); } }
internal static void Serialize(ArchiveMode mode, SerializationStream stream, Texture texture, bool allowContentStreaming) { if (mode == ArchiveMode.Deserialize) { var services = stream.Context.Tags.Get(ServiceRegistry.ServiceRegistryKey); var graphicsDeviceService = services.GetSafeServiceAs <IGraphicsDeviceService>(); var texturesStreamingProvider = services.GetService <ITexturesStreamingProvider>(); var isStreamable = stream.ReadBoolean(); if (!isStreamable) { texturesStreamingProvider?.UnregisterTexture(texture); // TODO: Error handling? using (var textureData = Image.Load(stream.NativeStream)) { if (texture.GraphicsDevice != null) { texture.OnDestroyed(); //Allows fast reloading todo review maybe? } texture.AttachToGraphicsDevice(graphicsDeviceService.GraphicsDevice); texture.InitializeFrom(textureData.Description, new TextureViewDescription(), textureData.ToDataBox()); // Setup reload callback (reload from asset manager) var contentSerializerContext = stream.Context.Get(ContentSerializerContext.ContentSerializerContextProperty); if (contentSerializerContext != null) { var assetManager = contentSerializerContext.ContentManager; var url = contentSerializerContext.Url; texture.Reload = (graphicsResource) => { var textureDataReloaded = assetManager.Load <Image>(url); ((Texture)graphicsResource).Recreate(textureDataReloaded.ToDataBox()); assetManager.Unload(textureDataReloaded); }; } } } else { if (texture.GraphicsDevice != null) { texture.OnDestroyed(); } texture.AttachToGraphicsDevice(graphicsDeviceService.GraphicsDevice); texture.Reload = null; // Read image header var imageDescription = new ImageDescription(); ImageHelper.ImageDescriptionSerializer.Serialize(ref imageDescription, ArchiveMode.Deserialize, stream); // Read content storage header ContentStorageHeader storageHeader; ContentStorageHeader.Read(stream, out storageHeader); // Check if streaming service is available if (texturesStreamingProvider != null) { // Load initial texture (with limited number of mipmaps) if (storageHeader.InitialImage) { using (var textureData = Image.Load(stream.NativeStream)) { if (texture.GraphicsDevice != null) { texture.OnDestroyed(); //Allows fast reloading todo review maybe? } texture.InitializeFrom(textureData.Description, new TextureViewDescription(), textureData.ToDataBox()); } } if (allowContentStreaming) { // Register texture for streaming // NOTE: Here we don't load texture data and don't allocate GPU memory texturesStreamingProvider.RegisterTexture(texture, ref imageDescription, ref storageHeader); } else { // Request texture loading (should be fully loaded) texturesStreamingProvider.FullyLoadTexture(texture, ref imageDescription, ref storageHeader); } } else { // Load initial texture and discard it (we are going to load the full chunk texture right after) if (storageHeader.InitialImage) { using (var textureData = Image.Load(stream.NativeStream)) { } } // Deserialize whole texture without streaming feature var contentSerializerContext = stream.Context.Get(ContentSerializerContext.ContentSerializerContextProperty); DeserializeTexture(contentSerializerContext.ContentManager, texture, ref imageDescription, ref storageHeader); } } } else { var textureData = texture.GetSerializationData(); if (textureData is null) { throw new InvalidOperationException("Trying to serialize a Texture without CPU info."); } textureData.Write(stream); } }