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

fix: FluentBadge content alignment when component is static #1749

Closed
swegele opened this issue Mar 27, 2024 · 17 comments · Fixed by #1921
Closed

fix: FluentBadge content alignment when component is static #1749

swegele opened this issue Mar 27, 2024 · 17 comments · Fixed by #1921
Assignees
Labels
area:fluent-ui-web-components A FluentUI specific issue status:blocked Any issue blocked by another

Comments

@swegele
Copy link

swegele commented Mar 27, 2024

Love the controls!!

🐛 Bug Report

Counter page FluentBadge alignment is skewed when page is rendered statically

SERVER and WASM INTERACTIVE:
GoodLabel with ServerInteractive

STATIC:
BadLabel with ServerInteractive

💻 Repro or Code Sample

  1. Create Project "Auto" - mode declared on each page
  2. Create a copy of Counter.razor and call it CounterStatic.razor.
  3. Change route to "\counter_static"
  4. At top of page delete /@rendermode line to make it static
  5. Add to NavMenu
  6. Run and navigate

🤔 Expected Behavior

All 3 render modes should look the same

😯 Current Behavior

Static is different
Upon inspecting elements, it looks like the "0" div ends up outside the badge container.

🔦 Context

Latest version of controls/nuget

@oneolddev
Copy link
Contributor

InteractiveAuto rendermode

image

no rendermode specified

image

@vnbaaij
Copy link
Collaborator

vnbaaij commented Mar 27, 2024

So the div that contains the content is not placed in the shadow DOM in SSR mode. I don't think that's really strange but also don't know yet why that is the case.

@swegele 's assumption that all 3 render modes should look the same is a nice one but not necessariy true in practice. We have not claimed anywhere that all components work in SSR mode.

@swegele
Copy link
Author

swegele commented Mar 27, 2024

I actually thought about if the different behavior here was logical due to lack of interactivity (example: obviously the button doesn't do anything but that is expected). Couldn't think of a reason why it would render differently....so just passing it on. 😃

Thanks again for your work on this. I'm adopting it in upcoming projects.

@swegele
Copy link
Author

swegele commented Mar 28, 2024

@vnbaaij I just noticed something that maybe gives a hint. I deleted cache and loaded a counter page set for:
@rendermode InteractiveWebAssembly - thus it had a delay while loading the WASM (few seconds). While it was loading the div with "0" was underneath like in the screenshots in previous comments. But when the WASM loaded then the "0" value popped up where it was supposed to be.

So it does look like the "div" tag literally gets moved inside the badge component during subsequent rendering.

@oneolddev
Copy link
Contributor

It looks like the issue is in the underlying fluent-badge web component. Working on the repro now.

@oneolddev
Copy link
Contributor

@swegele

@vnbaaij I just noticed something that maybe gives a hint. I deleted cache and loaded a counter page set for: @rendermode InteractiveWebAssembly - thus it had a delay while loading the WASM (few seconds). While it was loading the div with "0" was underneath like in the screenshots in previous comments. But when the WASM loaded then the "0" value popped up where it was supposed to be.

So it does look like the "div" tag literally gets moved inside the badge component during subsequent rendering.

The flicker you are seeing is the transition from the initial static rendering generated by the server to the rendering generated by Blazor. All the interactive modes of Blazor Web Apps initially do a static render. This issue makes it more visually apparent.

@swegele
Copy link
Author

swegele commented Mar 28, 2024

The flicker you are seeing is the transition from the initial static rendering generated by the server to the rendering generated by Blazor. All the interactive modes of Blazor Web Apps initially do a static render. This issue makes it more visually apparent.

I downloaded the source and took a gander. I was unable to determine why it would ever render content outside the tag.

_P.S. I also realized how there are some very smart people out there! This is very well organized code with tests and auto-documenting etc. A little above my head too!

@oneolddev
Copy link
Contributor

oneolddev commented Mar 28, 2024

It appears the underlying issue is in the fluent-badge web component. If the fluent-badge component is enclosed in a p tag, this issue appears. The issue doesn't appear when enclosde in a div tag.

Repro

Code

@page "/staticcounter"
@* @rendermode InteractiveAuto *@

<PageTitle>Counter</PageTitle>

<h1>Counter</h1>

<p role="status">Current count: <FluentBadge Appearance="Appearance.Neutral">@currentCount</FluentBadge></p>

<FluentButton Appearance="Appearance.Accent" @onclick="IncrementCount">Click me</FluentButton>

<hr />

<h2>Repro</h2>

<p>Explicitly using fluent-badge</p>

<h3>Original</h3>
<p>
    Test #1:
    <fluent-badge>
        <div>@currentCount</div>
    </fluent-badge>
</p>

<h3>Workaround</h3>
<div>
    Test #2:
    <fluent-badge>
        <div>@currentCount</div>
    </fluent-badge>
</div>

@code {
    private int currentCount = 0;

    private void IncrementCount()
    {
        currentCount++;
    }
}

Results

image

As to why this doesn't appear when not statically rendered, I suspect it has something to do with the way Blazor DOM is created. I'm guessing the leaf nodes are created first.

@vnbaaij Is this a fluent-badge bug?

@oneolddev
Copy link
Contributor

The workaround would be replacing

<p role="status">Current count: <FluentBadge Appearance="Appearance.Neutral">@currentCount</FluentBadge></p>

with

<div role="status" style="padding-bottom: 1em;">
    Current count: <FluentBadge Appearance="Appearance.Neutral">@currentCount</FluentBadge>
</div>

@vnbaaij
Copy link
Collaborator

vnbaaij commented Mar 28, 2024

Great find Gary!

I'm not sue if this is really a web component bug.

Looking at the source at https://github.com/microsoft/fast/tree/archives/fast-element-1/packages/web-components/fast-foundation/src/badge, I can only conclude that this is about the simplest webcomponent of all of them. And besides, the web component has no influence on what it is surrounded with so I'm more inclined to think it is actually a Blazor thing.

@vnbaaij vnbaaij added this to the vNext milestone Mar 28, 2024
@vnbaaij vnbaaij self-assigned this Mar 28, 2024
@vnbaaij
Copy link
Collaborator

vnbaaij commented Mar 28, 2024

I've implemented the replacing of the p with a div in the template code. Will be in next release.

As we have a workaround with that, I'm closing this one for now.

@swegele
Copy link
Author

swegele commented Mar 28, 2024

thanks to you both!

@oneolddev
Copy link
Contributor

@vnbaaij

I was able to recreate the issue outside of Blazor in Codepen.

image

@vnbaaij
Copy link
Collaborator

vnbaaij commented Mar 28, 2024

Will you create an issue for it in the Fluent UI repo?

@oneolddev
Copy link
Contributor

@vnbaaij

Given that I filed this as an issue in the fluentui repo, can we re-open this and add labels area:fluent-ui-web-components and status:blocked?

@vnbaaij vnbaaij reopened this Apr 10, 2024
@vnbaaij vnbaaij added area:fluent-ui-web-components A FluentUI specific issue status:blocked Any issue blocked by another labels Apr 10, 2024
@vnbaaij vnbaaij modified the milestones: v4.6.0, v4.7.0 Apr 10, 2024
@vnbaaij vnbaaij removed this from the v4.7.0 milestone Apr 22, 2024
@vnbaaij
Copy link
Collaborator

vnbaaij commented Apr 23, 2024

Update on this one...I spoke with the Fluent team and it looks like the cause of this is using a div (which is a block element) into an inline element. An easy workaround is to use a span element inside the FluentBadge or, even better, don't wrap the text at all.
So approach to solve is:

  1. Don't wrap it, just pass the text...you don't need that div. Updated to illustrate that.
  2. Use an inline element like span
  3. Style the div to be an inline element

You can verify this works by altering the codepen link provided earlier. Also add appearance="accent" to the fluent-badge tags to make them better visible:
image

I'm changing the FluentBadge to use a span for wrapping the childcontent

Closing this as a good workaround is now available.

@vnbaaij vnbaaij closed this as completed Apr 23, 2024
vnbaaij added a commit that referenced this issue Apr 23, 2024

Unverified

This user has not yet uploaded their public signing key.
@MaRRiK74
Copy link

MaRRiK74 commented May 24, 2024

@vnbaaij

When using HorizontalPosition and/or VerticalPosition it still has an issue

<FluentCounterBadge Count="counter" Appearance="Appearance.Lightweight" HorizontalPosition="0" VerticalPosition="0">
    <FluentButton Appearance="Appearance.Accent" OnClick="@Increment">
        <FluentIcon Value="@(new Icons.Regular.Size24.Alert())" Color="@Color.Fill" />
    </FluentButton>
</FluentCounterBadge>

@code {
    int counter = 1;

    public void Increment()
    {
        counter++;
    }
}

Badge

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
area:fluent-ui-web-components A FluentUI specific issue status:blocked Any issue blocked by another
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants