Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fonts loaded from memory (byte[] and Streams) disappear after some usage #282

Open
ZedDevStuff opened this issue Jan 17, 2025 · 2 comments
Milestone

Comments

@ZedDevStuff
Copy link

Fonts Loaded via the Font(byte[] bytes) constructor disappear after a certain time/memory usage. Take the following example

using SFML.Audio;
using SFML.Graphics;
using SFML.System;
using SFML.Window;
using System;
using System.Collections.Generic;

public class Program
{
    public static void Main(string[] args)
    {
        RenderWindow window = new RenderWindow(new VideoMode(800, 600), "SFML.net");
        window.Closed += (sender, e) => window.Close();
        List<CircleShape> shapes = new List<CircleShape>();
        // Replace with one of your fonts if you don't like me embedding one
        Text shapeCount = new Text("Shapes: 0", new Font(File.ReadAllBytes("path/to/your/font")), 18) 
        {
            Style = Text.Styles.Bold,
            FillColor = Color.Green,
            OutlineThickness = 1,
            OutlineColor = Color.Black
        };
        while (window.IsOpen)
        {
            window.DispatchEvents();
            window.Clear(Color.Black);
            foreach(CircleShape shape in shapes)
            {
                window.Draw(shape);
            }
            shapeCount.DisplayedString = $"Time: {DateTime.Now}";
            window.Draw(shapeCount);
            shapes.Add(new CircleShape(50) 
            { 
                Position = new Vector2f(Random.Shared.Next(0, 800), Random.Shared.Next(0, 600)),
                FillColor = new Color((byte)Random.Shared.Next(0, 255), (byte)Random.Shared.Next(0, 255), (byte)Random.Shared.Next(0, 255))
            });
            shapes.Add(new CircleShape(50)
            {
                Position = new Vector2f(Random.Shared.Next(0, 800), Random.Shared.Next(0, 600)),
                FillColor = new Color((byte)Random.Shared.Next(0, 255), (byte)Random.Shared.Next(0, 255), (byte)Random.Shared.Next(0, 255))
            });
            window.Display();
        }
    }
}

On my machine, the font disappears when the program reaches around 207MB of memory usage (according to Visual Studio's debugger)
Streams are unpredictable. In another project i have, loading the same font used in this example will result in a System.EngineExecutionException if i load it from the assembly resource manifest but works fine if i load it using the file path

@eXpl0it3r eXpl0it3r added this to the 2.6.1 milestone Jan 17, 2025
@eXpl0it3r
Copy link
Member

Regression introduced in #253

The font doesn't load the whole font data into memory, but goes back and tries to reload certain glyphs at times, but we're pinning the memory and freeing it after, which eventually causes issues.

@FRex
Copy link

FRex commented Jan 17, 2025

Here's a bit more info.

This was previously reported and later fixed by using a memory stream (so all reads from C++ go through C# read callback that doesn't care memory was moved around):
https://en.sfml-dev.org/forums/index.php?topic=24650
#156
388bf9b

Later during clean up the same bug was reintroduced with similar code (pin + create from memory), later changed a bit to fixed keyword but the problem remains:
1dfc5db

Music has the same problem, and it was never reported/fixed.

In the past, a workaround (before byte constructor was fixed) was to use a Stream constructor yourself. But now I think this is broken too, due to StreamAdaptor that is Disposed after creating the Font/Music which keep pointer from it (same style issue as pin + construct + use pointer from C++ after it's unpinned in C#).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants