-
- Nir Hasson
- Posts: 71
- Joined:
- Contact:
Predict Off-screen Render Target Size
Hi,
I'm getting the following error on several controls I created:
I would like to make sure that our application won't get any error of this kind during it's runtime.
What is the best way to deal with this error ?
SImply increase the offscreen size of any control I created ? (That sounds like a waste of resources)
Testing every control until we get no errors ?
Can I compute the needed offscreen size and apply it to each renderer ?
Regards,
Nir
I'm getting the following error on several controls I created:
So far I solved this issue by increasing the offscreen render target size using the IRenderere::SetOffscreenSize method.Offscreen atlas texture is full. Can't find space for 776x301 rectangle. Please increase Offscreen size in renderer
I would like to make sure that our application won't get any error of this kind during it's runtime.
What is the best way to deal with this error ?
SImply increase the offscreen size of any control I created ? (That sounds like a waste of resources)
Testing every control until we get no errors ?
Can I compute the needed offscreen size and apply it to each renderer ?
Regards,
Nir
-
-
sfernandez
Site Admin
- Posts: 3222
- Joined:
Re: Predict Off-screen Render Target Size
Offscreen render target is used to render opacity groups (element trees with an Opacity < 1.0 or using an OpacityMask). This render target is used as a texture atlas that is filled each frame with the rects needed to render each opacity group at one level (level known as all the opacity groups that should be generated at the same time because they are siblings).
The following example will require that your offscreen render target has space for 2 rects (100x50 and 200x100) that are generated at the same time because they are siblings. Requiring a total space of 300x100 or 200x150.
However, the following example will only require an offscreen render target of 200x100 (the bigger rect), because only one opacity group is rendered at a time.
So, to predict the size of the offscreen render target, you have to know how many UI elements with Opacity/OpacityGroup in your XAML will be rendered at the same time (not nested).
NOTE: Offscreen size is specified relative to the size of the main render target (window/screen). An offscreen size of 1,1 creates an offscreen render target with the same size than the main render target.
The following example will require that your offscreen render target has space for 2 rects (100x50 and 200x100) that are generated at the same time because they are siblings. Requiring a total space of 300x100 or 200x150.
Code: Select all
<Grid
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<StackPanel HorizontalAlignment="Center" VerticalAlignment="Center">
<Border Background="Red" Width="100" Height="50" Opacity="0.5"/>
<Border Background="Green" Width="200" Height="100" Opacity="0.5"/>
</StackPanel>
</Grid>
Code: Select all
<Grid
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<Border Background="Red" Width="200" Height="100" Opacity="0.5">
<Border Background="Green" Width="150" Height="75" Opacity="0.5">
<Border Background="Blue" Width="100" Height="50" Opacity="0.5"/>
</Border>
</Border>
</Grid>
NOTE: Offscreen size is specified relative to the size of the main render target (window/screen). An offscreen size of 1,1 creates an offscreen render target with the same size than the main render target.
Re: Predict Off-screen Render Target Size
Note that the offscreen must be set by application (in fact, per renderer, but usually you only have one per camera) not by control.
In previous version of Noesis this setup was done automatically behind the walls but it was giving performance problems (we had to create rendertargets in the middle of the execution which is a bad idea if you want to avoid spikes). So now setting the offscreen is like setting the max memory avaliable to your application. You have to test it to be sure that there is enough memory. But at least the results are deterministics.
Anyway, our advice: try to minimize these numbers as much as possible (more than 100% is probably a bad number) because many cases of opacity groups can be avoided. Of course 0% is the best, although even our themes aren't yet optimized to that level.
In previous version of Noesis this setup was done automatically behind the walls but it was giving performance problems (we had to create rendertargets in the middle of the execution which is a bad idea if you want to avoid spikes). So now setting the offscreen is like setting the max memory avaliable to your application. You have to test it to be sure that there is enough memory. But at least the results are deterministics.
Anyway, our advice: try to minimize these numbers as much as possible (more than 100% is probably a bad number) because many cases of opacity groups can be avoided. Of course 0% is the best, although even our themes aren't yet optimized to that level.
-
- Nir Hasson
- Posts: 71
- Joined:
- Contact:
Re: Predict Off-screen Render Target Size
In my case I'm creating elements dynamically and add them to some ItemsControl so I can't calculate a static size before execution - Am I wrong ?
In my opinion the automatic approach is better but the offscreen size API should be kept and it will determine the quality of the output result. Your renderer will have to fit all needed elements into the given offscreen texture atlas.
In this way the application will always work, and the developer will have full control over how much GPU resources he would like to allocate. You can pre-allocate these resources in order to avoid runtime spikes.
Beside that - can't you use staright forward rendering to accomplish the UI rendering in one pass ? I guess you'll have the overhead of changing states (Alpha blend/test ) and maybe some kind of sorting but it might worth the effort. If you can do that you'll have a fallback when the offsreen target is not suitable.
In my opinion the automatic approach is better but the offscreen size API should be kept and it will determine the quality of the output result. Your renderer will have to fit all needed elements into the given offscreen texture atlas.
In this way the application will always work, and the developer will have full control over how much GPU resources he would like to allocate. You can pre-allocate these resources in order to avoid runtime spikes.
Beside that - can't you use staright forward rendering to accomplish the UI rendering in one pass ? I guess you'll have the overhead of changing states (Alpha blend/test ) and maybe some kind of sorting but it might worth the effort. If you can do that you'll have a fallback when the offsreen target is not suitable.
-
-
sfernandez
Site Admin
- Posts: 3222
- Joined:
Re: Predict Off-screen Render Target Size
Opacity groups is a complex problem (specially nested opacity groups) that requires the use of extra buffers to achieve a correct result.
Imagine the following scenarios (using pseudo code):
Using a straight forward solution does not solve nested opacities correctly, because blending is not solved in the correct order. You would get something like this:
The expected and visually correct result should be:
About managing the offscreen buffers automatically, in dynamic scenarios (like the one you are describing), we cannot pre-allocate to avoid runtime spikes. An automatic solution will require to create a new extra buffer when the previous one becomes full. Maybe is the only solution to avoid runtime crashes, but we need to think about it and evaluate the pros and cons.
I want to remark the following: the rule is, the more 'opacity' attributes you have in your document, the more it's going to hurt performance. You should think carefully before using this attribute, and make absolutely sure that you can't achieve the same effect using the brush-opacity attributes.
Imagine the following scenarios (using pseudo code):
Code: Select all
<page bg=white>
<rect bg=red opacity=0.5>
<rect bg=blue opacity=0.5/>
</rect>
</page>
<page bg=white>
<ellipse bg=red opacity=0.5>
<ellipse bg=red opacity=0.5/>
</ellipse>
</page>
I want to remark the following: the rule is, the more 'opacity' attributes you have in your document, the more it's going to hurt performance. You should think carefully before using this attribute, and make absolutely sure that you can't achieve the same effect using the brush-opacity attributes.
-
- Nir Hasson
- Posts: 71
- Joined:
- Contact:
Re: Predict Off-screen Render Target Size
Thanks for the detailed explanation and examples.. I see the problem now.
As for my case - I didn't use any opacity groups explicitly in the source XAML file, but I guess they are coming from my custom Theme that is based on your own provided Theme.
These themes contain multiple references to Opacity property that are activated on visual state transitions..
I guess that in case I'll eliminate their usage I could reduce the offscreen usage dramatically.
Beside performance issues that you've mentioned, the application stability is much more important to me so please consider an alternative approach to this issue. Even unexpected visual rendering is preferred over runtime crash on our customers sites...
As for my case - I didn't use any opacity groups explicitly in the source XAML file, but I guess they are coming from my custom Theme that is based on your own provided Theme.
These themes contain multiple references to Opacity property that are activated on visual state transitions..
I guess that in case I'll eliminate their usage I could reduce the offscreen usage dramatically.
Beside performance issues that you've mentioned, the application stability is much more important to me so please consider an alternative approach to this issue. Even unexpected visual rendering is preferred over runtime crash on our customers sites...
-
-
sfernandez
Site Admin
- Posts: 3222
- Joined:
Re: Predict Off-screen Render Target Size
Our NoesisStyle contains lots of element opacity animations we want to change, because most of them can be brush opacity animations that are more efficient.
We will consider an alternative approach for the offscreen render targets, runtime crashes should not happen.
We will consider an alternative approach for the offscreen render targets, runtime crashes should not happen.
-
- ai_enabled
- Posts: 231
- Joined:
- Contact:
Re: Predict Off-screen Render Target Size
This is really annoying problem. In the our project we have already minimized using of opacity groups, but knowledge that our game can crash in any time just because we was wrong when set the offscreen render size is terrifying. So I vote for automatically increasing of the off-screen size when it's required (with error notification to editor log, or warning notification to game log) in the future versions of the NoesisGUI.
sfernandez, "Our NoesisStyle contains lots of element opacity animations we want to change, because most of them can be brush opacity animations that are more efficient."
Is not the brush opacity also uses off-screen render? I'm little bit confused with it.
And what is better approach to animate solid color brush - by changing it's Alpha color or by changing the Opacity property?
sfernandez, "Our NoesisStyle contains lots of element opacity animations we want to change, because most of them can be brush opacity animations that are more efficient."
Is not the brush opacity also uses off-screen render? I'm little bit confused with it.
And what is better approach to animate solid color brush - by changing it's Alpha color or by changing the Opacity property?
AtomicTorch Studio Pte. Ltd. http://atomictorch.com
-
-
sfernandez
Site Admin
- Posts: 3222
- Joined:
Re: Predict Off-screen Render Target Size
The only properties that start an opacity group (which uses off-screen render) are UIElement.Opacity and UIElement.OpacityMask, because they apply to the whole element subtree.sfernandez, "Our NoesisStyle contains lots of element opacity animations we want to change, because most of them can be brush opacity animations that are more efficient."
Is not the brush opacity also uses off-screen render? I'm little bit confused with it.
And what is better approach to animate solid color brush - by changing it's Alpha color or by changing the Opacity property?
Setting Brush.Opacity or the alpha channel of the color of any Brush only affects that Brush resource.
So, avoid:
Code: Select all
<Rectangle Fill="Red" Opacity="0.5"/>
Code: Select all
<Rectangle Fill="#80FF0000"/>
Code: Select all
<Rectangle>
<Rectangle.Fill>
<SolidColorBrush Color="Red" Opacity="0.5"/>
</Rectangle.Fill>
</Rectangle>
Code: Select all
<Grid Opacity="0.5">
<Rectangle Fill="Red"/>
<Ellipse Fill="Blue"/>
</Grid>

Re: Predict Off-screen Render Target Size
It won't crash if you tested all states of your gui. The behaviour is deterministic, it won't randomly crash. I see it very similar to being constrained by a limited size of memory.This is really annoying problem. In the our project we have already minimized using of opacity groups, but knowledge that our game can crash in any time just because we was wrong when set the offscreen render size is terrifying. So I vote for automatically increasing of the off-screen size when it's required (with error notification to editor log, or warning notification to game log) in the future versions of the NoesisGUI.
Anyway, our current implementation can be improved. For example:
- Detect cases where the opacity is not needed and generate a warning in the log or even being smart and try to carry the opacity to the brush of the internal node. I would say this will eliminate a very high percentage of offscreen uses.
- If there is not enough space in the offscreen texture instead of giving an error we could render the node without opacity with straight forward render. Although this will render the xaml incorrectly.