Is it possible to create a Blazor scoped CSS file for multiple components without duplicating it?

Viewed 1866

Is it possible to create some sort of component scoped CSS file for multiple components without duplicating it? Is there any naming convention?

Lets assume there are three components which all use the same tags but a style should only be applied for components of naming scheme ComponentA . Other components should not be affected.

ComponentA_A.razor
ComponentA_B.razor
ComponentOther.razor

having

ComponentA.razor.css

instead of

ComponentA_A.razor.css
ComponentA_B.razor.css

If duplication is the only way, is it possible to use some kind of referencing in css file itself or referencing a specific css file in blazor component?

2 Answers

I've found a workaround for this, using custom scope identifier format.
It's not very elegant but you might consider it:

  • All .razor components need to have their respective .razor.css files:

    ComponentA.razor
      ↳ ComponentA.razor.css
    
    ComponentB.razor 
      ↳ ComponentB.razor.css
    
  • One of the .razor.css files contains the css styles, the others can stay empty.

  • In your .csproj file add the following item group:

    <ItemGroup>
        <None Update="Components\ComponentA.razor.css" CssScope="my-custom-scope" />
        <None Update="Components\ComponentB.razor.css" CssScope="my-custom-scope" />
    </ItemGroup>
    

This will create the same custom scope my-custom-scope for all components it's applied to, and thus will apply the same styles to them.

Another alternative (might not be applicable to the OP but it's a way) is to use a preprocessor like SASS then you can create mixins and variables that are shared across components but you can also use pure CSS solution nowadays using custom properties (variables).

So just to give an example using pure CSS you can do something like the following:

  1. In your _Host.cshtml file add a link to a global CSS file (in our example we gonna call it site.css) like so:
<head>
    ...
    <link href="css/site.css" rel="stylesheet" />
    <link href="BlazorWebApp.styles.css" rel="stylesheet" />
</head>

Note, that we added the link to site.css above BlazorWebApp.styles.css which is a generated file for the CSS, depends on the setup though.

  1. Then you can define a CSS variable preferably in the :root but it can be anywhere, you can even create a dummy class called .variables and declare it there (cascading rules applies) but for the example we gonna stick with :root like so:
:root {
    --primary-color: #ff0000
}
  1. And then we can use --primary-color across components and we can declare yet another variable say --component-a-color and use that for components related to ComponentA like so:

ComponentA_A.razor.css

div {
    --component-a-color: #00ff00
    color: var(--component-a-color);
    background-color: var(--primary-color);
}

ComponentA_B.razor.css

div {
    color: var(--component-a-color);
    background-color: var(--primary-color);
}

ComponentOther.razor.css

div {
    color: #0000ff;
    background-color: var(--primary-color);
}

p.s. I'm using separate files for the CSS here but this shouldn't matter.

Related