10
\$\begingroup\$

I am new to Unity. I have a problem where my game has good performance on my non-4k screen.

Bur when I play it on my 4k screen, the performance gets really bad.

It looks like the resolution is changing based on the resolution on the screen. I am also basing this on the fact that both my text and buttons are getting smaller.

Is it possible to set a maximum resolution?

\$\endgroup\$
11
\$\begingroup\$

One way to limit the resolution of your game is to have your camera render to a RenderTexture.

You can create a RenderTexture in script to match the current aspect ratio of your window/screen, or even adapt the resolution of the texture dynamically in response to performance measurements. Assign it to the target texture property of your camera to redirect your rendering to that texture.

When you first do this, you suddenly won't see anything in your game — all the content is being rendered to this off-screen texture instead of to the screen. So then we need to display that texture full-screen, which we can do in a couple of ways:

  • Add a UI canvas in ScreenSpace Overlay mode, and put a RawImage component under it that displays this texture. Or...

  • Add a textured quad to your scene, using an unlit material to display this texture. Put it in a layer your main camera doesn't see, then add a new camera that sees only that layer, framed to match the quad.

What this does is limit the expensive scene rendering steps to operate at the fixed resolution of your texture. Then at the end you do a cheap texture sampling operation to stretch that texture to the full output resolution. You'll get some blurring because of this stretching, of course — that's the trade off we're making to save rendering performance. But you can also use a custom shader in the last step to control the texture interpolation scheme used.

If you're using URP/LWRP, this technique is built in as the Render Scale parameter on the pipeline asset, under Quality. Set this to a value less than 1 to downscale the render target used for scene rendering, and automatically stretch it to the size of the screen, without needing to juggle the RenderTexture yourself. UI will still be rendered at full res on top of this stretched result.

\$\endgroup\$
7
  • \$\begingroup\$ Wow, that's an interesting idea @DMGregory. Combined with properly scaled UI overlay (where blurring and pixelation in many cases would be more egregious than the game art itself) that could work very well. \$\endgroup\$ Oct 5 at 12:17
  • 3
    \$\begingroup\$ I implemented this method with a current WebGL project this a.m. after reading this and indeed, I saw significant frame rate improvement during play on my Retina MBP, so thanks for opening my eyes to this. \$\endgroup\$ Oct 5 at 16:13
  • 2
    \$\begingroup\$ Glad to hear it was helpful in your case! And nice work securing that performance improvement! \$\endgroup\$
    – DMGregory
    Oct 5 at 16:14
  • \$\begingroup\$ Thank you for the tip! I am really new to Unity, so Im not sure where to start. Is it possible to get a step-by-step, on how to implement it? \$\endgroup\$
    – Kims
    Oct 8 at 16:11
  • \$\begingroup\$ What step is currently unclear to you? And which rendering pipeline are you using? \$\endgroup\$
    – DMGregory
    Oct 8 at 16:27
5
\$\begingroup\$

I know that you tagged the question as , but some people might find this question while developing a desktop game and might find this answer useful:

For a desktop game, you can use the method Screen.SetResolution(int width, int height, bool fullscreen) to change the resolution at runtime. Note that when you do not pass false for the third argument, then the game will run in a window which the player can then still resize themselves.

\$\endgroup\$
1
  • \$\begingroup\$ Thank you! I will try it out when Im making a desktop game \$\endgroup\$
    – Kims
    Oct 6 at 18:24
5
\$\begingroup\$

The text & button size issue can be addressed by changing the Canvas Scaler component on the canvas to a mode other than Constant Pixel Size:

canvas scaler

In Scale With Screen Size mode, you set a reference resolution that the UI elements are scaled to, regardless of the actual pixel dimensions of the running game canvas.

To restrict the WebGL to a certain resolution, choose your desired resolution in the player settings and be sure to choose an HTML template that supports that resolution (e.g. the Minimal template that ships will resize the game to fill the entire browser window, regardless of the default resolution specified.)

Edit: Note DMGregory's answer for an effective way to force resolution in a WebGL build regardless of HTML container size.

player settings

To diagnose your issues with poor performance, more information is needed. Generally when a game suffers when resolution increases it's due to GPU fillrate limitations. This page is always a good place to start when tackling performance issues: Unity: Optimizing Graphics Performance

\$\endgroup\$
2
  • \$\begingroup\$ Thank you! My UI looks much better now, and is scaling to screen. I think maybe it helped with the performance, but not in fullscreen mode. I am still getting bad framerates. \$\endgroup\$
    – Kims
    Oct 6 at 18:23
  • 1
    \$\begingroup\$ @Kims You're welcome. To diagnose the fullscreen performance issue, it would be useful to determine whether this is just happening in your WebGL build, or everywhere. In the Editor, do you get different (lower) framerates when you maximize the game pane? Try doing a native PC or Mac build and test in different resolutions. If resolution seems to affect framerate everywhere, start looking at ways to optimize GPU fillrate. The link in my answer has some ideas on places to start. If only in the WebGL build, try implementing DMGregory's solution. \$\endgroup\$ Oct 6 at 19:22

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.