Symbol zastępczy Mixin SCSS / CSS

122

Próbuję utworzyć mixin dla symboli zastępczych w sassie.

To jest mixin, który stworzyłem.

@mixin placeholder ($css) {
  ::-webkit-input-placeholder {$css}
  :-moz-placeholder           {$css}
  ::-moz-placeholder          {$css}
  :-ms-input-placeholder      {$css}  
}

Oto, w jaki sposób chciałbym dołączyć ten miks:

@include placeholder(font-style:italic; color: white; font-weight:100;);

Oczywiście to nie zadziała z powodu wszystkich dwukropków i średników, które są przekazywane do miksera, ale ... naprawdę chciałbym po prostu wprowadzić statyczny css i przepuścić go dokładnie tak, jak powyższa funkcja.

czy to możliwe?

Shannon Hochkins
źródło

Odpowiedzi:

254

Szukasz @contentdyrektywy:

@mixin placeholder {
  ::-webkit-input-placeholder {@content}
  :-moz-placeholder           {@content}
  ::-moz-placeholder          {@content}
  :-ms-input-placeholder      {@content}  
}

@include placeholder {
    font-style:italic;
    color: white;
    font-weight:100;
}

Więcej informacji można znaleźć tutaj: http://sass-lang.com/docs/yardoc/file.SASS_REFERENCE.html#mixin-content


Począwszy od Sass 3.4, ten mixin można napisać tak, aby działał zarówno zagnieżdżony, jak i niezagnieżdżony:

@mixin optional-at-root($sel) {
  @at-root #{if(not &, $sel, selector-append(&, $sel))} {
    @content;
  }
}

@mixin placeholder {
  @include optional-at-root('::-webkit-input-placeholder') {
    @content;
  }

  @include optional-at-root(':-moz-placeholder') {
    @content;
  }

  @include optional-at-root('::-moz-placeholder') {
    @content;
  }

  @include optional-at-root(':-ms-input-placeholder') {
    @content;
  }
}

Stosowanie:

.foo {
  @include placeholder {
    color: green;
  }
}

@include placeholder {
  color: red;
}

Wynik:

.foo::-webkit-input-placeholder {
  color: green;
}
.foo:-moz-placeholder {
  color: green;
}
.foo::-moz-placeholder {
  color: green;
}
.foo:-ms-input-placeholder {
  color: green;
}

::-webkit-input-placeholder {
  color: red;
}
:-moz-placeholder {
  color: red;
}
::-moz-placeholder {
  color: red;
}
:-ms-input-placeholder {
  color: red;
}
cimmanon
źródło
1
Idealnie, dokładnie to, czego potrzebowałem.
Shannon Hochkins
4
Nie wiem, dlaczego to zostało cofnięte, ale odpowiedź jest nieprawidłowa. Potrzebujesz znaku „@” na początku każdego z prefiksów poszczególnych dostawców. Spójrz na odpowiedź napisaną dalej przez Dave'a Heina lub jeszcze lepiej - spróbuj uruchomić ten kod, a zobaczysz, że to nie zadziała.
Sk446,
1
@RickM Został cofnięty, ponieważ wprowadzone modyfikacje nie kompilują się (błąd: reguły na poziomie podstawowym nie mogą zawierać znaku „&” odwołującego się do selektora nadrzędnego). Tworzy to dokładny wynik, którego szuka OP, a odpowiedź, którą twierdzisz, jest „poprawna”, nie.
cimmanon
Ciekawe ... czy kompilujesz przez CLI? Wygląda na to, że musi istnieć konflikt wersji, ponieważ w moim przypadku dzieje się dokładnie odwrotnie, a sądząc po innych odpowiedziach, kilka innych też.
Sk446,
4
Tak, CLI: Sass 3.3.0.rc.3 przez Compass. Podwójnie sprawdzone za pomocą CodePen i Sassmeister . Jest &to konieczne, jeśli chcesz mieć selektor podobny input::-webkit-input-placeholderdo miksu, ale uniemożliwi to użycie go na poziomie root. sassmeister.com/gist/9469073 . Jeśli używasz LibSass, to inna historia.
cimmanon
168

Okazało się, że podejście podane przez cimmanona i Kurta Muellera prawie zadziałało, ale potrzebowałem odniesienia nadrzędnego (tj. Muszę dodać przedrostek „&” do każdego przedrostka dostawcy); lubię to:

@mixin placeholder {
    &::-webkit-input-placeholder {@content}
    &:-moz-placeholder           {@content}
    &::-moz-placeholder          {@content}
    &:-ms-input-placeholder      {@content}  
}

Używam miksu w ten sposób:

input {
    @include placeholder {
        font-family: $base-font-family;
        color: red;
    }
}

Po umieszczeniu referencji rodzica generowany jest poprawny css, np .:

input::-webkit-input-placeholder {
    font-family: Constantia, "Lucida Bright", Lucidabright, "Lucida Serif", Lucida, "DejaVu Serif", "Liberation Serif", Georgia, serif;
    color: red;
}

Bez odniesienia nadrzędnego (&) spacja jest wstawiana przed prefiksem dostawcy, a procesor CSS ignoruje deklarację; wygląda to tak:

input::-webkit-input-placeholder {
    font-family: Constantia, "Lucida Bright", Lucidabright, "Lucida Serif", Lucida, "DejaVu Serif", "Liberation Serif", Georgia, serif;
    color: red;
}
Dave Hein
źródło
9
Dziękuję Ci bardzo. Uratowałeś mi godzin prób i błędów w celu dokonania prac przyjętym odpowiedź / rozwiązanie ...
tmuecksch
Warto zauważyć, że twoje selektory są teraz nieco zawyżone (chyba że naprawdę nie chcesz, aby działały na wejściu lub wybieraniu elementów). Dodanie selektora nadrzędnego zapobiega używaniu miksera bez zagnieżdżania (czego szukał OP).
cimmanon
1
Jest &to całkowicie konieczne. Zredagował popularną odpowiedź, aby to odzwierciedlić.
AlexKempton
1
+1. Niektóre przeglądarki obsługują ::placeholderteraz oficjalną właściwość, więc polecam dodanie tego u góry:&::placeholder {@content}
Matt Browne,
11

To jest dla skróconej składni

=placeholder
  &::-webkit-input-placeholder
    @content
  &:-moz-placeholder
    @content
  &::-moz-placeholder
    @content
  &:-ms-input-placeholder
    @content

użyj go jak

input
  +placeholder
    color: red
igrossiter
źródło
4
Szczerze myślę, że jest to trudniejsze do odczytania, a także nie tak schludne, jak zwykła składnia
Shannon Hochkins,
Próbowałem to umieścić jako komentarz, ale jest za duży. Wolę używać tej składni i nie mogę sprawić, by wybrana odpowiedź działała zbyt łatwo. Pomyślałem, że to może być przydatne dla kogoś innego.
igrossiter
2
ten jest najlepszy, łatwy do zrozumienia i wdrożenia.
arslion
3

Dlaczego nie coś takiego?

Używa kombinacji list, iteracji i interpolacji.

@mixin placeholder ($rules) {

  @each $rule in $rules {
    ::-webkit-input-placeholder,
    :-moz-placeholder,
    ::-moz-placeholder,
    :-ms-input-placeholder {
      #{nth($rule, 1)}: #{nth($rule, 2)};
    }  
  }
}

$rules: (('border', '1px solid red'),
         ('color', 'green'));

@include placeholder( $rules );
Kurt Mueller
źródło
1
To trochę skomplikowane, szukałem dyrektywy dotyczącej treści, ale dziękuję!
Shannon Hochkins
3

Aby uniknąć błędów „Unclosed block: CssSyntaxError” wyrzucanych przez kompilatory sass, należy dodać znak „;” do końca @content.

@mixin placeholder {
   ::-webkit-input-placeholder { @content;}
   :-moz-placeholder           { @content;}
   ::-moz-placeholder          { @content;}
   :-ms-input-placeholder      { @content;}
}
Nie ma kierunku
źródło
0

Używam dokładnie tego samego symbolu zastępczego mixin sass, jak napisał NoDirection. Znajduję go w kolekcji miksów sassowych tutaj i jestem z niego bardzo zadowolony. Jest tekst, który wyjaśnia więcej opcji mieszania.

Nesha Zoric
źródło