Blazor项目中,支持将CSS样式隔离到各个组件(也就是将指定的CSS样式只在作用在指定的组件上),以简化 CSS 并避免与其他组件或库发生冲突。
启用CSS隔离
若要定义组件特定的样式,可以在同一个文件夹中创建一个 .razor.css
文件,该文件与组件的 .razor
文件的名称相匹配。.razor.css
文件是限定范围的 CSS 文件。
例如,对于 Example.razor
文件中的 Example
组件,可以在同文件夹下创建一个名为 Example.razor.css
的文件。
-
Example.razor
csharp@page "/example" <h1>Scoped CSS Example</h1>
-
Example.razor.css
cssh1 { color: brown; font-family: Tahoma, Geneva, Verdana, sans-serif; }
Example.razor.css
中定义的样式仅应用于 Example
组件的渲染输出。 CSS 隔离适用于匹配的 Razor 文件中的 HTML 元素。 在应用的其他位置定义的任何 h1
CSS 声明都不会与 Example
组件的样式冲突。
CSS 隔离捆绑
当使用 Visual Studio 或 .NET CLI 通过 blazor
模板创建一个新的 Blazor 项目时,项目模板会默认在 App.razor
文件中自动添加一个特定的 <link>
标签,用来引用 Blazor 自动生成的 CSS 隔离文件。
- 其中
{ASSEMBLY NAME}
是项目程序集名称 - Blazor 在编译时会扫描每个组件的
.razor.css
文件(如Counter.razor.css
)。重写这些 CSS 选择器,使其仅作用于对应组件的 HTML 范围,然后将所有处理后的 CSS 合并到{ASSEMBLY NAME}.styles.css
文件中
css
<link href="{ASSEMBLY NAME}.styles.css" rel="stylesheet">
注意,为了保证发生捆绑时的样式隔离,不支持在 Razor 代码块中导入 CSS。
在捆绑的文件中,每个组件都与范围标识符关联,组件中所有的元素都会追加属性,即该组件对应的范围标识符b-{STRING}
,其中 {STRING}
占位符是框架生成的十个字符的字符串,标识符具有唯一性。
例如,对Counter.razor组件使用css样式隔离
-
Counter.razor.css
cssh1{ color: red } p{ color:blue }
渲染后,可以看到h1
和p
元素中自动追加了该组件的范围标识符

其项目捆绑包位于obj/{CONFIGURATION}/{TARGET FRAMEWORK}/scopedcss/projectbundle/{ASSEMBLY NAME}.bundle.scp.css
{CONFIGURATION}
:应用的生成配置(例如Debug
、Release
)。{TARGET FRAMEWORK}
:目标框架(例如net6.0
)。{ASSEMBLY NAME}
:应用的程序集名称(例如BlazorSample
)。
CSS隔离样式的传递
默认情况下,CSS 隔离仅应用于与 {COMPONENT NAME}.razor.css
格式关联的组件,若要让子组件也应用隔离的样式。可以在父组件的 .razor.css
文件中,对目标元素使用 ::deep
, ::deep
会选择具有范围标识符的元素的后代元素。
- 注意,
::deep
只作用于具有样式范围标识符元素的后代元素 - 限定范围的 CSS 仅适用于 HTML 元素,不适用于 Razor 组件或标记帮助程序,包括应用了标记帮助程序的元素
例如,有Parent.razor和Child.razor组件如下:
csharp
@page "/parent"
<h1>这里是爸爸</h1>
<Child />
csharp
<h1>我只是个孩子啊</h1>
现在,设置如下隔离样式,Parent.razor.css
css
::deep h1 {
color: red
}
由于::deep h1
只作用于具有样式范围标识符元素的后代元素,所以两个h1
元素都没有使用样式。

现在,将Parent.razor修改如下:
csharp
@page "/parent"
<div>
<h1>这里是爸爸</h1>
<Child />
</div>
此时,由于h1
和Child组件都属于div
的后代,而div
具有范围标识符,所以两个h1
都使用了样式。

选择器的范围
默认情况下,在隔离的CSS文件中定义选择器时,范围默认应用于最右侧的元素,例如div > a
转换为 div > a[b-{STRING}]
。如果希望规则应用于其他选择器,可以改为 div ::deep > a
转换为 div[b-{STRING}] > a
。
CSS 隔离配置
CSS 隔离开箱即用,也可在某些高级场景(例如依赖于现有工具或工作流)下进行配置。对于CSS隔离的配置,基本上都在项目文件中进行。
一、自定义范围标识符格式
默认情况下,范围标识符使用格式 b-{STRING}
,其中 {STRING}
占位符是框架生成的十个字符的字符串。 若要自定义范围标识符格式,可以将项目文件更新为所需模式:
指定单个CSS隔离文件的范围标识符
xml
<ItemGroup>
<None Update="Components/Pages/Example.razor.css" CssScope="custom-scope-identifier" />
</ItemGroup>
在上面的示例中,为 Example.razor.css
生成的 CSS 将其范围标识符从 b-{STRING}
更改为了 custom-scope-identifier
CSS隔离文件的继承
可以通过范围标识符实现CSS文件的继承,在下面的项目文件示例中,BaseComponent.razor.css
文件包含跨组件的通用样式, DerivedComponent.razor.css
文件继承了这些样式。
xml
<ItemGroup>
<None Update="Components/Pages/BaseComponent.razor.css" CssScope="custom-scope-identifier" />
<None Update="Components/Pages/DerivedComponent.razor.css" CssScope="custom-scope-identifier" />
</ItemGroup>
共享范围标识符
可以使用通配符 (*
) 运算符跨多个文件共享范围标识符
xml
<ItemGroup>
<None Update="Components/Pages/*.razor.css" CssScope="custom-scope-identifier" />
</ItemGroup>
二、更改静态 Web 资产的基路径
默认情况下,scoped.styles.css
文件在应用的根目录生成。 可以通过在项目文件中,使用 <StaticWebAssetBasePath>
属性来更改默认路径。 例如,将 scoped.styles.css
文件以及应用的其余资产放在 _content
路径:
xml
<PropertyGroup>
<StaticWebAssetBasePath>_content/$(PackageId)</StaticWebAssetBasePath>
</PropertyGroup>
三、禁用自动捆绑
若要禁用 Blazor 在运行时发布和加载限定范围的文件,可以使用 DisableScopedCssBundling
属性。 使用此属性时,意味着将由其他工具或进程从 obj
目录中捕获隔离的 CSS 文件,并在运行时发布和加载这些文件:
xml
<PropertyGroup>
<DisableScopedCssBundling>true</DisableScopedCssBundling>
</PropertyGroup>
四、禁用 CSS 隔离
可以通过在应用的项目文件中将 <ScopedCssEnabled>
属性设置为 false
来禁用项目的 CSS 隔离:
xml
<ScopedCssEnabled>false</ScopedCssEnabled>