如何使用自定义样式覆盖默认的 PrimeFaces CSS?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/8768317/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How do I override default PrimeFaces CSS with custom styles?
提问by Samuel Tian
I've created my own theme as a separate Maven project, and it is loaded correctly.
我已经将自己的主题创建为单独的 Maven 项目,并且已正确加载。
Now I want to change the size of an component. For example, a <p:orderList>
. It has a class called ui-orderlist-list
which is defined in primefaces.css
with a fixed 200x200 dimension. No matter what I do in my theme.css
, it is overwritten by this attribute and there is no way I can make the content part of a <p:orderList>
wider.
现在我想更改组件的大小。例如,一个<p:orderList>
. 它有一个名为的类ui-orderlist-list
,定义primefaces.css
为固定的 200x200 尺寸。不管是什么我在做的theme.css
,是覆盖该属性,也没有办法,我可以做的内容部分<p:orderList>
宽。
For other components I might want to override just one instance of a component, not all.
对于其他组件,我可能只想覆盖组件的一个实例,而不是全部。
Can anyone please tell me how can I do all this?
谁能告诉我我该怎么做这一切?
回答by BalusC
There are several things you need to take into account of which one or more might be relevant you your specific case
您需要考虑几件事,其中一项或多项可能与您的具体情况相关
Load your CSS afterPrimeFaces one
在PrimeFaces之后加载您的 CSS
You need to ensure that your CSS is loaded afterthe PrimeFaces one. You can achieve this by placing the <h:outputStylesheet>
referencing your CSS file inside <h:body>
instead of <h:head>
:
您需要确保在 PrimeFaces之后加载您的 CSS 。您可以通过将<h:outputStylesheet>
引用您的 CSS 文件放在里面<h:body>
而不是<h:head>
:
<h:head>
...
</h:head>
<h:body>
<h:outputStylesheet name="style.css" />
...
</h:body>
JSF will automatically relocate the stylesheet to the endof the generated HTML <head>
and this will thus ensure that the stylesheet is loaded afterthe PrimeFaces' default styles. This way the selectors in your CSS file which are exactly the same as in PrimeFaces CSS file will get precedence over the PrimeFaces one.
JSF 会自动将样式表重新定位到生成的 HTML的末尾,<head>
从而确保在 PrimeFaces 的默认样式之后加载样式表。这样,CSS 文件中与 PrimeFaces CSS 文件中完全相同的选择器将优先于 PrimeFaces 选择器。
You'll probably also see suggestions to put it in <f:facet name="last">
of <h:head>
which is understood by PrimeFaces-specific HeadRenderer
, but this is unnecessarily clumsy and would break when you have your own HeadRenderer
.
你可能也看到建议把它<f:facet name="last">
的<h:head>
这是由PrimeFaces特定的理解HeadRenderer
,但这是不必要的笨拙,当你有你自己会打破HeadRenderer
。
Understand CSS specificity
了解 CSS 特性
You also need to ensure that your CSS selector is at leastas specific as the PrimeFaces' default CSS selector on the particular element. You need to understand CSS Specificityand Cascading and Inheritance rules. For example, if PrimeFaces declares a style by default as follows
您还需要确保您的 CSS 选择器至少与特定元素上 PrimeFaces 的默认 CSS 选择器一样具体。您需要了解CSS 特异性和级联和继承规则。例如,如果 PrimeFaces 默认声明一个样式如下
.ui-foo .ui-bar {
color: pink;
}
and you declare it as
你把它声明为
.ui-bar {
color: purple;
}
and the particular element with class="ui-bar"
happen to have a parent element with class="ui-foo"
, then the PrimeFaces' one will still get precedence because that's the most specific match!
并且特定元素 withclass="ui-bar"
碰巧有一个父元素 with class="ui-foo"
,那么 PrimeFaces的父元素仍将获得优先级,因为这是最具体的匹配!
You can use the webbrowser developer tools to find the exact CSS selector. Rightclick the element in question in the webbrowser (IE9/Chrome/Firefox+Firebug) and choose Inspect Elementto see it.
您可以使用 webbrowser 开发人员工具来查找确切的 CSS 选择器。在网络浏览器(IE9/Chrome/Firefox+Firebug)中右键单击有问题的元素,然后选择“检查元素”以查看它。
Partial overriding
部分覆盖
If you need to override a style for only a specific instance of the component and not all instances of the same component, then add a custom styleClass
and hook on that instead. It is another case where specificity is used/applied. For example:
如果您只需要为组件的特定实例而不是同一组件的所有实例覆盖样式,请添加自定义styleClass
和钩子。这是使用/应用特异性的另一种情况。例如:
<p:dataTable styleClass="borderless">
.ui-datatable.borderless tbody,
.ui-datatable.borderless th
.ui-datatable.borderless td {
border-style: none;
}
If a component does not support a styleClass
and you are on jsf 2.2 or up, you can also use passtrough attributesand add a pt:class
and have it end-up on the output.
如果组件不支持 astyleClass
并且您使用的是 jsf 2.2 或更高版本,您还可以使用passtrough 属性并添加 apt:class
并使其最终出现在输出中。
<p:clock pt:class="borderless" />
Never use !important
永远不要使用 !important
In case you fail to properly load the CSS file in order or to figure the right CSS selector, you'll probably grab the !important
workaround. This is Plain Wrong. It's an ugly workaround and not a real solution. It only confuses your style rules and yourself more in long term. The !important
should onlybe used in order to override the values hardcoded in HTML element's style
attribute from a CSS stylesheet file on (which is in turn also a bad practice, but in some rare cases unfortunately unavoidable).
如果您未能按顺序正确加载 CSS 文件或找出正确的 CSS 选择器,您可能会抓住!important
解决方法。这是完全错误的。这是一个丑陋的解决方法,而不是一个真正的解决方案。从长远来看,它只会混淆你的风格规则和你自己。本!important
应只以覆盖HTML元素的硬编码值被用来style
从一个CSS样式表文件属性(这反过来也是一个不好的做法,但在某些罕见的情况下不幸的是不可避免的)。
See also:
也可以看看:
回答by Daniel
you can create a new css file for example cssOverrides.css
您可以创建一个新的 css 文件,例如 cssOverrides.css
and place all the overrides you want inside it, that way upgrading the primefaces version wont affect you ,
并将所有你想要的覆盖放在里面,这样升级primefaces版本不会影响你,
and in your h:head add something like that
在你的 h:head 添加类似的东西
<link href="../../css/cssOverrides.css" rel="stylesheet" type="text/css" />
if it wont work try adding it to the h:body
如果它不起作用,请尝试将其添加到 h:body
in order to check if its working try this simple example inside the css file
为了检查它是否工作在 css 文件中尝试这个简单的例子
.ui-widget {
font-size: 90% !important;
}
this will reduce the size of all primefaces components /text
这将减少所有primefaces组件/text的大小
回答by Andrew
I'm using PrimeFaces 6.0. Here's some information I would have liked to have regarding this:
我正在使用 PrimeFaces 6.0。以下是我希望获得的关于此的一些信息:
If you use <h:outputStylesheet/>
, it will work, but your CSS will not be loaded last even if it's last in the <h:head></h:head>
tags (other CSS files will be included afterwards). A trick you can do which I learned from hereis to place it inside <f:facet name="last"></f:facet>
, which must go inside the body, like so:
如果您使用<h:outputStylesheet/>
,它将起作用,但即使您的 CSS 位于<h:head></h:head>
标签的最后,也不会最后加载(其他 CSS 文件将在之后包含)。我从这里学到的一个技巧是将它放入 inside <f:facet name="last"></f:facet>
,它必须进入 body,如下所示:
<h:body>
<f:facet name="last">
<h:outputStylesheet name="css/MyCSS.css" />
</f:facet>
...
Then your CSS will be the last loaded. Note:you will still have to adhere to the specificity rules as BalusC outlined.
然后你的 CSS 将是最后加载的。注意:您仍然必须遵守 BalusC 概述的特异性规则。
I placed "MyCSS.css" in WebContent/resources/css/.
我将“MyCSS.css”放在 WebContent/resources/css/ 中。
More information on the resource loading order: http://www.mkyong.com/jsf2/primefaces/resource-ordering-in-primefaces
更多资源加载顺序信息:http: //www.mkyong.com/jsf2/primefaces/resource-ordering-in-primefaces
回答by Jasper de Vries
How to create more specific rules
如何创建更具体的规则
The style rules used by PrimeFaces can be quite complex. An element can receive its styling from multiple CSS rules. It's good to know you can use filtering in the DOM inspector's style tab to search on the property you want to customise:
PrimeFaces 使用的样式规则可能非常复杂。一个元素可以从多个 CSS 规则接收其样式。很高兴知道您可以在 DOM 检查器的样式选项卡中使用过滤来搜索要自定义的属性:
This screenshot was taken using Chrome, but filtering is also available in Firefox and Safari.
此屏幕截图是使用 Chrome 拍摄的,但过滤也可用于 Firefox 和 Safari。
When you have found the rule you want to customise, you can simply create a more specific rule by prefixing it with html
. For example, your could override .ui-corner-all
like:
找到要自定义的规则后,您可以简单地通过添加前缀来创建更具体的规则html
。例如,您可以.ui-corner-all
像这样覆盖:
html .ui-corner-all {
border-radius: 10px;
}
Replace theme values using a ResourceHandler
使用 a 替换主题值 ResourceHandler
I usually just want to replace some color with another value. As colors can be used in many different rules it can be useful to create a ResourceHandler
.
我通常只想用另一个值替换一些颜色。由于颜色可用于许多不同的规则,因此创建一个ResourceHandler
.
In the handler check for the PrimeFaces theme:
在处理程序中检查 PrimeFaces 主题:
@Override
public Resource createResource(String resourceName,
String libraryName) {
if (isPrimeFacesTheme(resourceName, libraryName)) {
return new MyResource(super.createResource(resourceName, libraryName), this);
}
else {
return getWrapped().createResource(resourceName, libraryName);
}
}
protected boolean isPrimeFacesTheme(final String resourceName,
final String libraryName) {
return libraryName != null
&& libraryName.startsWith("primefaces-")
&& "theme.css".equals(resourceName);
}
In the resource, replace the color:
在资源中,更换颜色:
private static String cache;
public MyResource(Resource wrapped, ResourceHandler handler) {
this.wrapped = wrapped;
this.handler = handler;
this.charset = Charset.forName(FacesContext.getCurrentInstance().getExternalContext().getResponseCharacterEncoding());
}
@Override
public InputStream getInputStream() throws IOException {
if (cache == null) {
cache = readInputStream(getWrapped().getInputStream());
// Replace values
cache = cache.replace("#007ad9", "#11dd99");
}
return new ByteArrayInputStream(cache.getBytes(charset));
}
And register it as follows in the faces-config.xml:
并在faces-config.xml中注册如下:
<application>
<resource-handler>com.example.MyResourceHandler</resource-handler>
</application>
For more information on resource handlers see:
有关资源处理程序的更多信息,请参阅: