Resolution Solution [library]

Showcase your libraries, tools and other projects that help your fellow love users.
User avatar
GVovkiv
Party member
Posts: 668
Joined: Fri Jan 15, 2021 7:29 am

Re: Resolution Solution [library]

Post by GVovkiv »

This library can scale with 3 different methods. It can scale to specified by you size (so, for example, 1920x1080). It works nice for games, where all what you intendent to support is this one 1920x1080. But what about situations when you need support several resolutions? You need to store somewhere list of available resolutions, manually implement function that will decide best resolution, based on monitor size (for example, if you support 1920x1080 and 1280x720, it would be nice for end user to get 1280x720 resolution, if their monitor use it, instead of 1920x1080, so less reasons to go into options screen to fix that), and if you want to implement options screen, where user could change resolution, you should manually implement all of that.

My proposal is implement full featured resolutions handling system, that will take care for most of this problems for you. If there will be any updates, i will post it in https://github.com/Vovkiv/resolution_solution/issues/6, so if anyone interested on this, go check issues on github. Maybe eventually i implement this, who knows?
User avatar
GVovkiv
Party member
Posts: 668
Joined: Fri Jan 15, 2021 7:29 am

Re: Resolution Solution [library]

Post by GVovkiv »

GVovkiv wrote: Fri Dec 30, 2022 4:40 pm This library can scale with 3 different methods. It can scale to specified by you size (so, for example, 1920x1080). It works nice for games, where all what you intendent to support is this one 1920x1080. But what about situations when you need support several resolutions? You need to store somewhere list of available resolutions, manually implement function that will decide best resolution, based on monitor size (for example, if you support 1920x1080 and 1280x720, it would be nice for end user to get 1280x720 resolution, if their monitor use it, instead of 1920x1080, so less reasons to go into options screen to fix that), and if you want to implement options screen, where user could change resolution, you should manually implement all of that.

My proposal is implement full featured resolutions handling system, that will take care for most of this problems for you. If there will be any updates, i will post it in https://github.com/Vovkiv/resolution_solution/issues/6, so if anyone interested on this, go check issues on github. Maybe eventually i implement this, who knows?
Is there anyone, who actually need something like this? I feel, like most of indie devs just slap 1 resolution (because they don't want to deal with several of them, since it can become hard to deal with ) and call it a day, haha
User avatar
GVovkiv
Party member
Posts: 668
Joined: Fri Jan 15, 2021 7:29 am

Re: Resolution Solution [library]

Post by GVovkiv »

Is anyone okay with some hacks?
I found out, that non even window size by width and height will result in non integer xOff and yOff values, which will result in pixel bleeding, which is might be noticeable. This hack can be turned of and on by switching rs.pixelPerfectOffsetsHack to false , and by default will be set to false. It will only affect 3rd pixel perfect scaling, even if hack active it will do nothing in other scaling methods.
I'l achieved this by simply rounding non even reported window size to even:
if rs.pixelPerfectOffsetsHack and rs.scaleMode == 3 then
if (windowWidth % 2 ~= 0) then
windowWidth = windowWidth + 1
end

if (gameHeight % 2 ~= 0) then
gameHeight = gameHeight + 1
end
end
I also tried to just ceil/floor offset values, which resulted in almost same behaviour, but it resulted on cut down 1 line of pixels on right/bottom sides, which is even worse/
The side effects of this:
1. If width/height of window non even, rs.windowWidth and rs.windowHeight will report wrong by 1 value. Workqround for this is to use love.graphics.getWidth/Height() instead.
2. On non even window, scaled game content will be moved to left/right by 1 pixel. It shouldn't be noticeable by user at all, because it can be moved only by 1 pixel, without croped content. It doesn't appear to mess up with precision, so rs.toGame/toScreen should report correct numbers, so cursor collision should work as it should.
I will upload update in next 1-2 days.

So, TL;DR
Set s.pixelPerfectOffsetsHack to true, if you noticing pixel bleeding in pixel perfect scaling mode, but this might come with some side effects, so use it on your own risk

But, apparently, none of existing scaling libraries that aims at pixel perfect scaling doesn't come up with good solution, so they just use non integer offsets...
Does that means that i'm trying to fix something that nobody cares about???
MAYBE I JUST LOSING MY DAMN MIND ON THIS??
MAYBE I TOOK PIXEL "PERFECT" SCALING TOO FAR???
AND I GOING INSANE FOR NOTHING???

Anyway, happy new year, i guess. Hope everyone have happy time (because, i surely don't) with their families and loved ones, and you got good presents under your christmas tree.
User avatar
GVovkiv
Party member
Posts: 668
Joined: Fri Jan 15, 2021 7:29 am

Re: Resolution Solution [library]

Post by GVovkiv »

https://github.com/Vovkiv/resolution_so ... /tag/v2001

Version v2001 31 december 2022
Small update, that add some QoL features, and hack for Pixel Pefrect Scaling. Check source code (specifically
rs.pixelPerfectOffsetsHack and rs.resize) and this update log for more info.
Happy new year!

New:
* nearestFilter(filter, anisotropy) - this function is easier to use wrapper for love.graphics.setDefaultFilter()
It expects 2 optional arguments:
1st in true/false or nil (which is esentially nothing). true/nil results in nearest filtering, while false is linear.
2nd is anisotropy. It can be number or nil. If number, function will simply use it to slap into love.graphics.setDefaultFilter(),
but if nil, then library will simply get anisotropy value from love.graphics.getDefaultFilter() and will use it instead. Current love uses 1 as default.
If this function was never run, library will never touch or edit love.graphics.setDefaultFilter()

* rs.pixelPerfectOffsetsHack = false/true - very experimental feature, that aim to fix pixel bleeding in perfect scaling mode
when window size is not even. It result in always "clean" pixels, byt comes with side effects such as:
1. rs.windowWidth and rs.windowHeight will be wrong by 1 if window is non even. The workaround is to use love.graphics.getWidth/Height instead.
2. On non even window size, offset from left and top will place game content on 1 pixel left/upper.
It shouldn't be problem for end user tho.

But if you never ever draw anything inside rs.unscaleStart() and rs.unscaleStop() and outside of rs.start() and stop(), then you should probably fine using this hack.

* rs.switchPixelHack() - turn on/off mentioned hack.
* rs.setMode() - wrapper around love.window.setMode(). You should use this functions instead, since using love.window.setMode() might
don't trigger love.resize and therefore rs.resize.

Updated:
* Updated demo to include all new functions and values
* Updated rs.debugFunc to include all new values and functions
User avatar
togFox
Party member
Posts: 764
Joined: Sat Jan 30, 2021 9:46 am
Location: Brisbane, Oztralia

Re: Resolution Solution [library]

Post by togFox »

I'd like to develop to my desktop (1920 / 1080) but also scale correctly when on laptops and smaller monitors.

I haven't looked at the code yet - just the wiki page - would you suggest this the best setting:

Code: Select all

	res.init({width = 1920, height = 1080, mode = 3})
	res.setMode(1920, 1080, {resizable = true})
	
Again, without looking, it is unclear the purpose of init and setMode and why call one after the other. Should init just call setMode or or init do what setMode does?

Code: Select all

res.init({width = 1920, height = 1080, mode = 3, resizable = true})
Current project:
https://togfox.itch.io/backyard-gridiron-manager
American football manager/sim game - build and manage a roster and win season after season
User avatar
GVovkiv
Party member
Posts: 668
Joined: Fri Jan 15, 2021 7:29 am

Re: Resolution Solution [library]

Post by GVovkiv »

togFox wrote: Sun Jan 22, 2023 12:36 pm I'd like to develop to my desktop (1920 / 1080) but also scale correctly when on laptops and smaller monitors.

I haven't looked at the code yet - just the wiki page - would you suggest this the best setting:

Code: Select all

	res.init({width = 1920, height = 1080, mode = 3})
	res.setMode(1920, 1080, {resizable = true})
Again, without looking, it is unclear the purpose of init and setMode and why call one after the other. Should init just call setMode or or init do what setMode does?

Code: Select all

res.init({width = 1920, height = 1080, mode = 3, resizable = true})
tl;dr: bug was discovered with love.window.setMode so rs.setMode was made to workaround it.

"res.setMode" is just wrap for love's "love.window.setMode" and it was added when i discovered that love.window.setMode, apparently, sometimes fail to call love.resize, so if you change window size via love's setMode, library fail to get new window size until you resize window manually. That's how this function was born. You can use:

Code: Select all

love.window.setMode(*something*)
rs.resize(love.graphics.getWidth(), love.graphics.getHeight())
Which results in same behaviour.
Maybe in future i will do something with it, but for now it's just wrap for setMode, so when you need it, call rs.setMode instead. Or just use conf.lua if you need change options once.

Right now, my life is not in position to change it. I mentioned it in issues, but i have actually plans to decouple changelogs, documentation, demo examples, etc in different files. Put documentation in some sort of "documentation.md", changelogs in "changelogs.md", etc. Right now, everything is included in library file itself. Every function was documented: what it does, why and when you should used, etc. And this was, probably, fine approach when library was small, but now there 1122 lines, where maybe ~50% of is changelogs, demo, documentation and navigating this mess is painful.
User avatar
togFox
Party member
Posts: 764
Joined: Sat Jan 30, 2021 9:46 am
Location: Brisbane, Oztralia

Re: Resolution Solution [library]

Post by togFox »

Interesting. Thanks.

And the way I call it above is the correct way when I design for desk top but want a good experience on laptops?
Current project:
https://togfox.itch.io/backyard-gridiron-manager
American football manager/sim game - build and manage a roster and win season after season
User avatar
GVovkiv
Party member
Posts: 668
Joined: Fri Jan 15, 2021 7:29 am

Re: Resolution Solution [library]

Post by GVovkiv »

togFox wrote: Sun Jan 22, 2023 10:59 pm Interesting. Thanks.

And the way I call it above is the correct way when I design for desk top but want a good experience on laptops?
Yes.
As i say, rs.setMode is wrap for love.window.setMode so there no "right" and "wrong" way to use it, lol. Tho, it's probably better to change first time settings (e.g, make window resizable) at conf.lua, instead of love.window.setMode, because everytime window will flash when you use it, which is might be not desired behaviour.
User avatar
togFox
Party member
Posts: 764
Joined: Sat Jan 30, 2021 9:46 am
Location: Brisbane, Oztralia

Re: Resolution Solution [library]

Post by togFox »

Intentionally bumping this thread as I constantly have this problem which demonstrates I'm not understanding something.

I use this code on my desktop (1920 x 100) and it works fine:

Code: Select all

function love.load()

	res.init({width = 1920, height = 1080, mode = 3})
	res.setMode(1920, 1080, {resizable = true})
	...


function love.draw()
    res.start()

	if currentscene == enum.sceneMainMenu then
		mainmenu.draw()
		...
		

I run the same code on my laptop (1366 x 768) and it doesn't scale as I was expecting:

Image

That's my main menu being drawn off the screen.

I don't have a config file but happy to use one if that will help. I must be misunderstanding something. Thanks for any tips.
Current project:
https://togfox.itch.io/backyard-gridiron-manager
American football manager/sim game - build and manage a roster and win season after season
User avatar
GVovkiv
Party member
Posts: 668
Joined: Fri Jan 15, 2021 7:29 am

Re: Resolution Solution [library]

Post by GVovkiv »

togFox wrote: Sat Mar 18, 2023 3:59 am Intentionally bumping this thread as I constantly have this problem which demonstrates I'm not understanding something.

I use this code on my desktop (1920 x 100) and it works fine:

Code: Select all

function love.load()

	res.init({width = 1920, height = 1080, mode = 3})
	res.setMode(1920, 1080, {resizable = true})
	...


function love.draw()
    res.start()

	if currentscene == enum.sceneMainMenu then
		mainmenu.draw()
		...
		

I run the same code on my laptop (1366 x 768) and it doesn't scale as I was expecting:

Image

That's my main menu being drawn off the screen.

I don't have a config file but happy to use one if that will help. I must be misunderstanding something. Thanks for any tips.
It's probably better to use github page, but, anyway:
Pixel perfect mode try to maintain 1, 2, 3, etc scale mode. You game is 1920x1080 and when you window width is >= 1920 or height is >= 1080 and less then 3840x2160 it will be impossible to get 2 scale factor. It will be something like float with 1.*float_part*. Which will be floored to 1.
If your window is less then 1920x1080, result of division will be less then 1, like 0.*float_part*. Which will be floored to 0. And as you might understand, scale == 0 means nothing to show. That's reason why at line https://github.com/Vovkiv/resolution_so ... n.lua#L438.
It will pick 1 if scale value will be less then 1, otherwise pick current scale value.

What you could do with it? I'm not sure. All this pixel perfect stuff is mostly for pixel art and pixel art is usually done in low res. For example, right now, i kinda work with game that will use pixel art. I want it to support 16:9 properly so i draw it in 960x540, which is x1. When game will be 1920x1080, it will be scale factor 2 so no pixel bleeds, etc.
If you will use low res, then game can be pretty much run on any resolution (since even 1366x768 become less and less used and 1080 and more become more used; and 960x540 window can feet anywhere).
You could at start of game (or any other moment) check current resolution of user screen, and if it less then your desired 1920x1080, then you could enforce different scaling method, with obvious downside that there will be no pixel perfect scaling. Or to achieve same effect, go to https://github.com/Vovkiv/resolution_so ... n.lua#L438 and replace

Code: Select all

scale = math.max(math.floor(scale), 1)
with:

Code: Select all

if scale > 1 then
scale = math.floor(scale)
end
It will looks like this:
test_demo.love
(try to resize window to be smaller)
(39.44 KiB) Downloaded 88 times
But i was not really sure how i was supposed to deal scale < 1, so i just slap 1 scale as minimum for pixel perfect.
Post Reply

Who is online

Users browsing this forum: No registered users and 16 guests