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

create a DropShadow behind a control #10295

Closed
tpoint75 opened this issue Jan 10, 2025 · 8 comments
Closed

create a DropShadow behind a control #10295

tpoint75 opened this issue Jan 10, 2025 · 8 comments
Labels
needs-triage Issue needs to be triaged by the area owners

Comments

@tpoint75
Copy link

Describe the bug

I cant create a DropShadow behind a control. The shadow is always in front of it!

void ApplyDropShadow(FrameworkElement const& element) {

        // Get the Compositor and Visual for the element
        auto visual = ElementCompositionPreview::GetElementVisual(element);
        auto compositor = visual.Compositor();

        // Create a DropShadow
        DropShadow dropShadow = compositor.CreateDropShadow();
        dropShadow.Color(winrt::Windows::UI::ColorHelper::FromArgb(255, 0, 255, 255)); 
        dropShadow.BlurRadius(30.0f);
        dropShadow.Opacity(0.8f);
        dropShadow.Offset({ -5.0f, -5.0f, 0.0f });

        // Create a SpriteVisual and set the shadow
        SpriteVisual shadowVisual = compositor.CreateSpriteVisual();
        shadowVisual.Shadow(dropShadow);

        // Set the size of the shadow to match the element
        shadowVisual.Size({ element.ActualSize().x + 10, element.ActualSize().y + 10 });

        // Place the container visual behind the XAML element
        ElementCompositionPreview::SetElementChildVisual(element, shadowVisual);
}

Steps to reproduce the bug

execute code

Expected behavior

No response

Screenshots

No response

NuGet package version

None

Packaging type

No response

Windows version

No response

IDE

No response

Additional context

No response

@microsoft-github-policy-service microsoft-github-policy-service bot added the needs-triage Issue needs to be triaged by the area owners label Jan 10, 2025
@tpoint75 tpoint75 changed the title Bug title create a DropShadow behind a control Jan 10, 2025
@RDMacLachlan RDMacLachlan transferred this issue from microsoft/WindowsAppSDK Jan 13, 2025
@castorix
Copy link

I cannot test in C++, but it is the same code as in C#; a way is to render the control with RenderTargetBitmap (similar to in this test #10062), then add the shadow (and Mask depending on the control (GetAlphaMask))
A test with an Image control, by adapting your code :

Image

I also found other methods with another control, like at https://github.com/microsoft/uwp-experiences/blob/master/apps/News/News/Helpers/Composition/CompositionShadow.xaml.cs

@tpoint75
Copy link
Author

Yeah, how to get the mask for each control? The most doesn't have it (Can mask images, text, and shapes do) and if I understand it right, the https://github.com/CommunityToolkit/WindowsCommunityToolkit/blob/main/Microsoft.Toolkit.Uwp.UI.Controls.Core/DropShadowPanel/DropShadowPanel.xaml
puts a Border around the element, and paint the shadow over the border to get the element over the shadow.

@castorix
Copy link

Without mask, the shadow will be rectangular.
But simple controls like Buttons use transparency, so alpha must be changed and it is not great :
Image
MS also uses a Border in CompositionShadow.xaml. Maybe it is the best method.
There is also this, but not tested : https://learn.microsoft.com/en-us/windows/communitytoolkit/helpers/attachedshadows

@niels9001
Copy link
Contributor

@karkarl karkarl added needs-author-feedback Asked author to supply more information. and removed needs-triage Issue needs to be triaged by the area owners labels Jan 16, 2025
@marcelwgn
Copy link
Collaborator

@tpoint75 Have you tried using a negative z-index for the shadow offset?

@tpoint75
Copy link
Author

Ok, as I figured out:
https://stackoverflow.com/questions/58235566/how-to-create-themeshadow-programmatically-c-uwp-1903
and
https://learn.microsoft.com/en-us/windows/windows-app-sdk/api/winrt/microsoft.ui.xaml.media.themeshadow.receivers?view=windows-app-sdk-1.6

The main problem is that: "Receivers cannot be an ancestor of the caster in the visual tree."

You always need something that receives the shadow and this must be a sibling of the element and be above it in the XAML tree.
So it must be a child of an grid, because other elements doesn't allow multiple content.
Then it's easy with:

ThemeShadow shadow;
MeasClass().Shadow(shadow);
shadow.Receivers().Append(ReceivingGrid().as());
ReceivingGrid().as().Translation({ 0, 0, 100 });

But this limitation is a no go, because I can't build that stuff around each element.

So the only way could be to get the alpha mask for every element. (How?)
//Create surface brush and load image
CompositionSurfaceBrush surfaceBrush = compositor.CreateSurfaceBrush();
surfaceBrush.Surface(there is no function to get);

// Create a SpriteVisual and set the shadow
SpriteVisual shadowVisual = compositor.CreateSpriteVisual();
shadowVisual.Brush(surfaceBrush);
shadowVisual.Shadow(dropShadow);

Or to create this dynamically with visuals. I tried this with visual containers and appending childs, but on the one hand the shadow is visible on the other the element was gone..

@microsoft-github-policy-service microsoft-github-policy-service bot added needs-triage Issue needs to be triaged by the area owners and removed needs-author-feedback Asked author to supply more information. labels Jan 17, 2025
@tpoint75
Copy link
Author

tpoint75 commented Jan 17, 2025

Crazy, this 3 lines are working

ThemeShadow ts;
MeasClass().Translation({ 0,0,10 });
MeasClass().Shadow(ts);

@microsoft-github-policy-service microsoft-github-policy-service bot added needs-triage Issue needs to be triaged by the area owners and removed needs-triage Issue needs to be triaged by the area owners labels Jan 17, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
needs-triage Issue needs to be triaged by the area owners
Projects
None yet
Development

No branches or pull requests

5 participants