8

我的样式表如下所示:

.thing-1 { background-image: url('top.png'); }
.thing-2 { background-image: url('top.png'); }
.thing-3 { background-image: url('top.png'); }
/* etc... */

紧随其后的是:

.thing-20 { background-image: url('bottom.png'); }
.thing-21 { background-image: url('bottom.png'); }
.thing-22 { background-image: url('bottom.png'); }
/* etc... */

我正在寻找一种方法来用 LESS 或类似的东西来简化我的样式表。这是我想做的:

.thing-[i < 15] { background-image: url('top.png'); }
.thing-[i >= 15] { background-image: url('bottom.png'); }

有没有办法用LESS做这样的事情?如果不是 LESS,也许是 SASS?

4

4 回答 4

12

当您要求 LESS 和 Sass 时,这里有一些解决方案。你可以通过值循环来实现它——但是 Sass 在这个领域更强大一些,因为它有内置的控制指令,比如@for,和。当然有多种实现方式,但这是首先想到的:@if@while@each

较少的:

.bg (@i) when (@i < 15) { background-image: url('top.png'); }
.bg (@i) when (@i >= 15) { background-image: url('bottom.png'); }

.things (@max, @i: 1) when (@i < @max) {
  .thing-@{i} { .bg (@i); }
  .things (@max, (@i + 1));
}

.things(50);

SCSS:

@function bg($i) {
  @if $i < 15 { @return 'top.png' }
  @else { @return 'bottom.png' }
}

@for $i from 1 through 50 {
  .thing-#{$i} { background-image: url(bg($i)); }
}

您可以在哪里获得确切的输出。

但是通过以下方式可以实现更干燥的输出:

少:@seven-phases-max 的答案.thing-15但是,如果您只有少于 15 个项目,也总是必须打印出来的问题。除非您添加另一个.thing-15仅在需要时添加的守卫,如下所示:

.thing(@i) when (@i = 15) {
    .thing-15 {background-image: url('bottom.png')}
}

您可以在less2css.org上试用 Less 解决方案

SCSS:

%bg-top { background-image: url('top.png'); }
%bg-bottom { background-image: url('bottom.png'); }

@for $i from 1 through 50 {
  .thing-#{$i} {
    @if $i < 15 { @extend %bg-top; }
    @else { @extend %bg-bottom; }
  }
}

我认为最后一个是最优雅的解决方案。

演示

于 2013-11-02T00:10:59.800 回答
5

在某些情况下不需要预处理器

更新:使解决方案完全通用,以允许在类的任一侧添加额外的thing-#类。

这对于您正在处理的数字是相当实用的。基本上该技术类似于我为这个问题回答的技术,但在您的情况下,代码如下(这是一个仅使用背景颜色的调整示例):

[class*="thing-"] {
    background-image: url('top.png');
}

[class*="thing-1"]:not(.thing-1):not(.thing-10):not(.thing-11):not(.thing-12):not(.thing-13):not(.thing-14),
[class*="thing-2"]:not(.thing-2),
[class*="thing-3"]:not(.thing-3),
[class*="thing-4"]:not(.thing-4),
[class*="thing-5"]:not(.thing-5),
[class*="thing-6"]:not(.thing-6),
[class*="thing-7"]:not(.thing-7),
[class*="thing-8"]:not(.thing-8),
[class*="thing-9"]:not(.thing-9) {
    background-image: url('bottom.png');
}

它在跨多个数字进行“一般”选择时使用属性选择器,然后过滤掉一般不应适用的特定类。

您可以进一步减少 CSS

如果您将1-9类更改为具有前面的零(thing-01thing-02),则可以将一般 css进一步简化为

[class*="thing-"] {
    background-image: url('top.png');
}

[class*="thing-"]:not([class*="thing-0"]):not(.thing-10):not(.thing-11):not(.thing-12):not(.thing-13):not(.thing-14) {
    background-image: url('bottom.png');
}

实际限制

如果需要一个非常大的断点,这一切都会变得非常麻烦,因为需要进行更多的过滤。但是,正如我对另一个问题的原始答案所展示的那样,仍然可以实现一些更大的中断级别,并且在那时,也许使用 LESS 或 SCSS 以某种方式进行断点是可能的,同时仍然保持输出 CSS 较低。

于 2013-11-02T01:46:43.440 回答
4

是的,你可以在 LESS 中做到这一点。但是代码有点吓人(基本上它需要您学习一些高级 LESS 概念),所以如果您的用例如此简单,我想您更愿意手动编写这些东西(如@Ashkan 所建议的那样)。


更少的代码:

.thing-1  {background-image: url('top.png')}
.thing-15 {background-image: url('bottom.png')}

.thing(@i) when (@i < 15) {
    .thing-@{i} {&:extend(.thing-1);}
}
.thing(@i) when (@i > 15) {
    .thing-@{i} {&:extend(.thing-15);}
}

.generate-things(@i) when (@i > 1) {
    .generate-things((@i - 1));
    .thing(@i);
}

.generate-things(30);
于 2013-11-02T00:09:47.943 回答
2

你可以做

.thing-1,.thing-2,.thing-3,... { background-image: url('top.png'); }
.thing-20,.thing-21,.thing-22,... { background-image: url('bottom.png'); }

你们中的一些人可以为您的元素使用多个类:

.top { background-image: url('top.png'); }
.bottom { background-image: url('bottom.png'); }
.thing-1 { /*only thing-1 related css code*/}
.thing-2 { /*only thing-2 related css code*/}

并像这样使用它:

<div class="top thing-1"></div>
<div class="bottom thing-1"></div>
于 2013-11-01T23:41:09.393 回答