Welcome, Guest. Please login or register. Did you miss your activation email?

Author Topic: Crash during resize of UserControl with embedded RenderWindow  (Read 4139 times)

0 Members and 1 Guest are viewing this topic.

Conduit

  • Newbie
  • *
  • Posts: 30
    • View Profile
I'm creating a UserControl for use in a WinForms application which embeds and displays a RenderWindow using the method suggested in this forum post. Everything works well so far except when the control is resized. When the control is resized I want to recreate the embedded RenderWindow with a VideoMode that won't result in stretching, but this often results in the program crashing with no exceptions thrown... VS2013 gives me nothing to work with but a "vshost.exe has stopped working" message. I'm at a complete loss - any ideas for troubleshooting or fixing this are very, very welcome. The pertinent code is below.

(click to show/hide)

(click to show/hide)

(click to show/hide)
« Last Edit: April 07, 2015, 06:52:56 am by Conduit »

zsbzsb

  • Hero Member
  • *****
  • Posts: 1409
  • Active Maintainer of CSFML/SFML.NET
    • View Profile
    • My little corner...
    • Email
Re: Crash during resize of UserControl with embedded RenderWindow
« Reply #1 on: April 07, 2015, 01:16:35 pm »
Quote
I want to recreate the embedded RenderWindow with a VideoMode that won't result in stretching

Why don't you resize the view like you are supposed to do?

http://www.sfml-dev.org/tutorials/2.2/graphics-view.php#showing-more-when-the-window-is-resized

Recreating the window every time the control's size changes 1 pixel is not the way to do it and will make your application extremely slow. Not to mention SFML doesn't exactly play nicely with threads in some situations, so I don't understand why you have all these monitor calls all over. It is also well established multithreading your drawing calls won't help anything (OpenGL is single threaded).

Quote
this.m_Window = new RenderWindow(this.Handle, new ContextSettings(this.m_Depth, this.m_Stencil, this.m_Antialiasing, this.m_Major, this.m_Minor));

You never dispose the old window, which causes your memory usage to go through the roof considering you do this every time the size changes. Either way, you shouldn't recreate it as I said before, learn to do it right with the view.

private uint m_Depth = 0;
private uint m_Stencil = 0;
private uint m_Antialiasing = 0;
private uint m_Major = 2;
private uint m_Minor = 0;

Why don't you just store a context setting struct as a member variable?
Motion / MotionNET - Complete video / audio playback for SFML / SFML.NET

NetEXT - An SFML.NET Extension Library based on Thor

Conduit

  • Newbie
  • *
  • Posts: 30
    • View Profile
Re: Crash during resize of UserControl with embedded RenderWindow
« Reply #2 on: April 07, 2015, 08:01:50 pm »
Thanks for the tips!

Quote
Why don't you resize the view like you are supposed to do?
I don't know how I missed that section of the View tutorial, but that would probably do the trick. Ideally the RenderControl would work when its DockStyle was set to fill, but that caused a lot of trouble initially... I'll give this a try and report back.

Quote
You never dispose the old window
Good catch. Ran into trouble when testing before I'd finished the class, and must have missed that.

Quote
Not to mention SFML doesn't exactly play nicely with threads in some situations, so I don't understand why you have all these monitor calls all over
This control will eventually be incorporated into an application where rendering runs in a separate thread than the GUI, as is necessary to keep the GUI from hanging when using a rendering loop. After I shifted construction of all OpenGL-related objects to the rendering thread I haven't had any trouble when using SFML in my multithreaded app... if you have/know of any specific concerns, I'd be happy to hear them, though!

As for their purpose: if the GUI thread calls Destroy/Create at the same time the rendering thread calls Draw (or something) then we might have a race - if m_Window.Dispose had been called but m_Window hadn't yet been set to null, for example, we might try to draw to the disposed object (right...?). These will probably be converted into something more elegant, but during testing they will stay there.

Quote
Why don't you just store a context setting struct as a member variable
I had been considering making these changeable, but then I noticed that SFML doesn't let you do this and figured I shouldn't either. In retrospect I don't really know why you'd want to change them anyway. That will be fixed as soon as the more important bits are taken care of.



EDIT: Altering the view as suggested in that tutorial works wonderfully - thanks for the link.
At this point, zsbzsb, I practically owe you a co-author credit on my application ;)

As it stands I believe the class to be fully functional - if there are other concerns to be considered in a multithreaded application, though, I might need to make some changes (e.g. I am not entirely sure which of the built-in RenderWindow functions won't lead to a race, so some uses of Monitor might be unnecessary). I might just do away with the Monitor stuff entirely and assume that it will be handled externally (if needed), as this is more in line with what is expected of SFML.

Feel free to toss any other suggestions my way - revised code below.

(click to show/hide)
« Last Edit: April 07, 2015, 10:19:53 pm by Conduit »