简体   繁体   English

在 Angular 2 中使用全局 CSS 设置子元素样式

[英]Styling child elements using global CSS in Angular 2

I'm starting to use Angular 2 and I am using an admin template from Themeforest for styling.我开始使用 Angular 2,并且我正在使用 Themeforest 的管理模板进行样式设置。 I want my component to take the styles defined on the index.html, which should be global.我希望我的组件采用 index.html 上定义的样式,它应该是全局的。 The problem is that the elements inside a components html file are not finding these styles, and I think that it is because somehow the parent-child relationship is broken.问题是组件html文件中的元素没有找到这些样式,我认为这是因为不知何故父子关系被破坏了。 Here's an example:下面是一个例子:

In the index.html file, I have the following:在 index.html 文件中,我有以下内容:

...
<!-- This is my Component -->
<sidebar-menu></sidebar-menu>

<!-- This is coded directly on the index.html -->
<li class="m-t-30">
    <a href="#" class="detailed">
        <span class="title">Page 1</span>
        <span class="details">234 notifications</span>
    </a>
    <span class="icon-thumbnail "><i class="pg-mail"></i></span>
</li>
...

My <sidebar-menu> component has this on it's .html file:我的<sidebar-menu>组件在它的 .html 文件中有这个:

<li class="m-t-30">
  <a href="#" class="detailed">
    <span class="title">Page 1</span>
    <span class="details">234 notifications</span>
  </a>
  <span class="icon-thumbnail "><i class="pg-mail"></i></span>
</li>

Which is exactly the same as what is present on the index.html file.这与 index.html 文件中的内容完全相同。 So, I should see the two items displayed in the same way.所以,我应该看到这两个项目以相同的方式显示。 But this is what I see:但这就是我所看到的:

在此处输入图片说明

Clearly, the styling is broken, even though that both the component's html and the element's html are the same.显然,样式被破坏了,即使组件的 html 和元素的 html 是相同的。 Using the inspector, I can see that the component's html is not using the same styling as the second element:使用检查器,我可以看到组件的 html 没有使用与第二个元素相同的样式:

Component's inspected title:组件的检查标题: 组件的检查标题

Second element's inspected title:第二个元素的检查标题: 在此处输入图片说明

I tried defining encapsulation: ViewEncapsulation.None on my Component, but it doesn't do anything.我尝试在我的组件上定义encapsulation: ViewEncapsulation.None ,但它没有做任何事情。 Any ideas on how to solve this?关于如何解决这个问题的任何想法? Thanks!谢谢!

I use the styles metadata to add all the css files I need for a given component.我使用样式元数据添加给定组件所需的所有 css 文件。 If you have access to the admin template css, you can reference it with a relative path to your component.如果您有权访问管理模板 css,则可以使用组件的相对路径引用它。 An example:一个例子:

@Component({
    selector: 'my-selector',
    template: require('./my-template.html'),
    styles: [
        require('./my-style.css'),
        require('../some-other-folder/some-other-style.css')
    ]
})

Due to view encapsulation being Emulated by default, other styles to do not bleed into your component this way and you have to explicitly declare the css files you want to be included for this component.由于默认情况下模拟视图封装,因此其他样式不会以这种方式渗透到您的组件中,您必须明确声明要包含在该组件中的 css 文件。

FYI, another way to have a style exposed globally is by adding :host >>> to the beginning of the style that's in the external css file.仅供参考,另一种在全局公开样式的方法是将:host >>>添加到外部 css 文件中样式的开头。 Example:例子:

:host >>> .no-margin {
    margin: 0;
}

(As you said you can't change the admin template, this option wouldn't work for you but I'm putting it out here for anyone interested). (正如您所说,您无法更改管理模板,此选项对您不起作用,但我将其放在这里供任何感兴趣的人使用)。 With this approach, you do not have to include the style in your styles array.通过这种方法,你不必在您的风格排列的风格。

Yet another thing to look at is the different types of view encapsulation: Emulated (default), Native, and None.另一个需要注意的是不同类型的视图封装:Emulated(默认)、Native 和 None。 https://angular.io/docs/ts/latest/guide/component-styles.html#view-encapsulation https://angular.io/docs/ts/latest/guide/component-styles.html#view-encapsulation

Just set the view encapulation to "none":只需将视图封装设置为“无”:

@Component({
    ....
    encapsulation: ViewEncapsulation.None
})

The way I managed to work around this limitation was to change the way my component's directive is called.我设法解决这个限制的方法是改变我的组件指令的调用方式。 Normally, you would define the selector like this:通常,您会像这样定义选择器:

@Component({
  moduleId: module.id,
  selector: 'sidebar-menu',
  ...
})

And call it using <sidebar-menu></sidebar-menu> .并使用<sidebar-menu></sidebar-menu>调用它。 Instead, I defined the selector like this:相反,我像这样定义了选择器:

@Component({
  moduleId: module.id,
  selector: '[sidebar-menu]',
  ...
})

And call it as a directive inside a div , a li or any DOM element for that matter.并将其称为divli或任何 DOM 元素内的指令。

<ul class="menu-items" sidebar-menu></ul>

This way, I can still use the styling from my Themeforest template and use components.这样,我仍然可以使用我的 Themeforest 模板中的样式并使用组件。 I figured that it broke because normally I would have something like this:我认为它坏了,因为通常我会有这样的事情:

<div class="parent-class">
    <div class="child-class">
        ... styles applied to ".parent-class.child-class"
    </div>
</div>

And with components, I got something like this:对于组件,我得到了这样的东西:

<div class="parent-class">
    <sidebar-menu>
        <div class="child-class">
            ... CSS can't find ".parent-class.child-class" anymore, as it has a sidebar-menu element in the middle!
        </div>
    </sidebar-menu>
</div>

With the workaround, you end up with this:通过解决方法,您最终会得到以下结果:

<div class="parent-class">
    <div class="child-class" sidebar-menu>
        ... CSS can still find ".parent-class.child-class", all good!
    </div>
</div>

Hopefully this will help someone.希望这会帮助某人。 Thanks for your answers!感谢您的回答!

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM