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

Visual States Question #99

Open
SandTechStuff opened this issue Sep 15, 2024 · 14 comments
Open

Visual States Question #99

SandTechStuff opened this issue Sep 15, 2024 · 14 comments

Comments

@SandTechStuff
Copy link

I am currently making a modern Windows 7/8 taskbar design, which uses different backgrounds in place of the running indicators. To change the background when the program is active, inactive, or requesting attention, I am using RunningIndicatorStates as the Visual State.

taskbar

This causes the issue that I cannot use the regular CommonStates to change the background on hover, when pressed, etc. I tried to switch from using RunningIndicatorStates to CommonStates, but there is no state for when the program is not running. The InactiveNormal state is not equal to the InactiveRunningIndicator state, as InactiveNormal is applied whether a program is running or not. This causes all taskbar buttons to look like they are running.

CommonStates
Only Firefox and Windhawk are running in this screenshot

I want to be able to make use of CommonStates more versatile states while also excluding non-running programs from having a background when not hovered over or pressed. I couldn't find a way to make this work, as you can only use one visual state per object, so I thought to ask the experts ;)

@bbmaster123
Copy link
Collaborator

Use UWPSpy to find another target you can use when needed, and also to find whatever visual states that target supports. Not every target supports common states, and some have their own unique visual states.
For running indicators, I believe you'd want NoRunningIndicator but I can check that

@SandTechStuff
Copy link
Author

@bbmaster123 Thanks for your reply. I already am using NoRunningIndicator, the problem is I want to use CommonStates as RunningIndicatorStates is very limited. CommonStates would allow me to add hover effects, pressed effects, etc.

Written in green are the visual states that can be achieved using either CommonStates or RunningIndicatorStates, they can be easily swapped from the current RunningIndicatorStates to work with CommonStates.

Written in red are the visual states that can ONLY be achieved using one of the visual states or another. They are mutually exclusive. There is no equivalent to NoRunningIndicator in common states that I am aware of, and you cannot use multiple visual states at once, which is what I am inquiring about.

visualStates

@m417z
Copy link
Member

m417z commented Sep 17, 2024

you can only use one visual state per object

To be more precise, you can only use one visual state per object and property. For example, Opacity and Width here are defined for the same Image#Icon object and different visual states:

image

This can provide more room for creative solutions.

The problem with defining the same object and property for different visual states is that they'll override each other. For example, if you define a red border for ActiveNormal and a green border for ActiveRunningIndicator, what should happen? There could be some priority mechanism (last defined match wins?), but currently it's not implemented. Let me know if you think it can work in your case and I can try to implement it.

@SandTechStuff
Copy link
Author

@m417z Thanks for the idea! I was able to adjust Background using RunningIndicatorStates and Opacity using CommonStates.

Background color is "enabled" by ActiveRunningIndicator & InactiveRunningIndicator, and set to transparent by NoRunningIndicator.

Opacity is increased and decreased on different states of CommonStates to make it look like the background color is changing.

visualStates2.mp4

It's still not perfect, not sure how I feel about the current opacity values. Multi-Window programs do not have a distinct active vs. inactive visual state for hovered & pressed, which makes it difficult to have consistency with the other programs without removing the distinction between active vs. inactive in all programs, regardless if it is multi-window or not. (You can see how ActivePointerOver and InactivePointerOver have the same opacity, for example, to compensate for multi-window programs' lack of inactive vs. active.)

VisualStatesEverywhere

I would appreciate some feedback on how it looks so far.

@m417z
Copy link
Member

m417z commented Oct 12, 2024

Looks like I never replied. I think it looks great! If you're considering to submit it, go ahead, it'll also be an opportunity for a mod update after adding your theme.

@SandTechStuff
Copy link
Author

I would submit it, but how would it work since it requires multiple mods and configurations? If you only use "Windows 11 Taskbar Styler" and not "Taskbar height and icon size", it looks like this:

image

For people selecting the theme through the integrated list in the mod, there is no way to communicate that another mod is needed for the correct look.

@SandTechStuff
Copy link
Author

I also have a version for the vertical taskbar, but that's another can of worms.

@m417z
Copy link
Member

m417z commented Oct 17, 2024

Looks pretty good to me. In any case, you can specify additional requirements or recommendations in the theme's readme page, for example:
https://github.com/ramensoftware/windows-11-taskbar-styling-guide/blob/main/Themes/RosePine/README.md

Not all users will notice it or will go read it, but some will. I can also append something like "ThemeName (see readme for recommended configuration)" to the name that's displayed in the mod's combobox if you prefer.

Regarding vertical taskbar, yeah, I assume it's a different set of styles. It can be included as a variant to be imported manually in the readme, like it's done here:
https://github.com/ramensoftware/windows-11-taskbar-styling-guide/blob/main/Themes/Squircle/README.md#manual-installation

@SandTechStuff
Copy link
Author

Something strange is happening, a border is being applied when a non running program is hovered over. I think its the border applied by default, but I cannot figure out how to change it besides getting rid of it entirely or changing its BorderThickness (I increased it for this demo).

I originally made the guess that it is applied by the InactivePointerOver visual state. I realized that didn't seem to make much sense given that I edited border styles using a different visual state in another part of the styles, and as discussed you cannot use multiple visual states for one property.

I tried to experiment with UWPSpy but I couldn't figure out a way to modify this border. I wanted to have the border appear when non running programs are hovered, since changing the background color would not be possible given visual state limitations. The border looks mediocre right now though, and I wanted to figure out how to change its color or something.

Styles.mp4

@SandTechStuff
Copy link
Author

I also changed the start button size to be 24px, not sure if it looks better compared to the previous 32px.

@m417z
Copy link
Member

m417z commented Oct 19, 2024

That's Border#BackgroundElement, I assume.

I originally made the guess that it is applied by the InactivePointerOver visual state. I realized that didn't seem to make much sense given that I edited border styles using a different visual state in another part of the styles, and as discussed you cannot use multiple visual states for one property.

You can't with the styler rules, but the taskbar might have its own logic.

@SandTechStuff
Copy link
Author

Can you use visual states if they are unnamed? If it is possible I cannot figure out how. Tray icon element in UWPSpy for reference.

image

That's Border#BackgroundElement, I assume.

Yeah, it appears to be. I cannot find a way to style it without overriding borders set by visual state styles, so I guess I'll leave it be.

@m417z
Copy link
Member

m417z commented Oct 24, 2024

Can you use visual states if they are unnamed?

I didn't know there can be more than one. It's supported, but only the first one will be picked up. For example:

Grid@ > Border#BackgroundBorder

I hope that the iteration order is consistent, and that the visual state group that you need is the first one. Otherwise, it's not supported and it's also not straightforward to add support to it, as there's no straightforward way to identify each visual state.

@SandTechStuff
Copy link
Author

The first one is the one I need, looks like I got lucky. I'll try it when I get the chance.

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