如何在Bootstrap 4 Sass媒体查询中添加“方向媒体查询”

4
我在我的SCSS文件中使用了"纯净版"Bootstrap 4的SASS媒体查询:
@include media-breakpoint-up(xs){}
@include media-breakpoint-up(sm){}
@include media-breakpoint-up(lg){}
@include media-breakpoint-up(xl){}

我知道如果我使用CSS宽度媒体查询,就可以将其与方向媒体查询结合使用,但我想使用SASS框架。我想在其中一个媒体查询中添加方向媒体查询,即 XS 查询。因此它是具体的。因为如你所知,Bootstrap 4目前不支持方向查询(奇怪的是)。
我尝试以不同的方式将 "方向查询" 与 "SASS Bootstrap 媒体查询 (XS)" 连接起来,但我总是遇到一个SASS错误。
因此,我做的是将其嵌套在 SASS Bootstrap 媒体查询 (XS) 中:
@include media-breakpoint-up(xs){

... some SCSS rules

  @media (orientation: landscape){
     header{
     display:none !important;   
     } 
     .navbar{ 
     display:none !important;   
     } 
  }
}

我有一个问题,尽管它被嵌套到XS查询中,但它适用于所有断点。就像它没有考虑到被嵌套的情况。

我的问题是:如何将“方向查询”与“SASS引导程序媒体查询(xs)”连接起来?或者如何通过嵌套使其特定于XS断点。

谢谢您


要将您的答案标记为解决方案,无需在标题中添加[solved]。相反,应使用答案接受系统 - 当系统允许时,单击与您的答案相邻的勾选/检查标记。 - halfer
2个回答

5

我找到了解决方案。

可以通过嵌套组合sass mixin,因此我在我的_mixins.scss文件中创建了以下mixin:

@mixin orientation($direction) { 

  $orientation-landscape: "(orientation:landscape)"; 
  $orientation-portrait: "(orientation:portrait)";

  @if $direction == landscape {
    @media #{$orientation-landscape} { @content; } 
  }
  @if $direction == portrait {
    @media #{$orientation-portrait} { @content; } 
  }
} 

请注意:我没有将“and”放入变量值,“and(orientation:landscape)”。我想SASS或bootstrap自动添加它。
然后,在我的SCCS文件中,我添加了以下规则:
@include media-breakpoint-down(sm) {
  @include orientation(landscape) {
    .path-frontpage header {
      display: none !important;
    }
    .path-frontpage .navbar {
      display: none !important;
    }
  }
}

注意:在我的第一篇文章中,我说嵌套的CSS规则适用于所有断点,这是因为生成CSS时,SASS Bootstrap 4 XS断点没有被编写,我认为这是因为该值为0。因此,方向媒体查询没有与min-width值结合。所以,我将值更改为max-width而不是min-width,因为Bootstrap 4 SM断点具有576px值。
CSS文件中的结果正是我想要的:
@media (max-width: 767.98px) and (orientation: landscape) {
  .path-frontpage header {
    display: none !important;
  }
  .path-frontpage .navbar {
    display: none !important;
  }
}

我希望这将有助于社区。


有没有办法设置$direction的默认值? - Usman Iqbal

1

我在Bootstrap之外使用这个。你应该可以在Bootstrap或任何其他框架中使用它,从而使你的媒体查询更加灵活。

// Extra map functions by Hugo Giraudel
@function map-deep-get($map, $keys...) {
  @each $key in $keys {
    $map: map-get($map, $key);
  }
  @return $map;
}

@function map-has-keys($map, $keys...) {
  @each $key in $keys {
    @if not map-has-key($map, $key) {
      @return false;
    }
  }
  @return true;
}

@function map-has-nested-keys($map, $keys...) {
  @each $key in $keys {
    @if not map-has-key($map, $key) {
      @return false;
    }
    $map: map-get($map, $key);
  }
  @return true;
}

这些是Hugo Giraudel编写的额外地图函数。map-deep-get基本上是一个简化的嵌套map-get函数。map-has-keys类似于sass内置的map-has-key,但会检查多个键。map-has-nested-keys在此基础上扩展,检查嵌套键。这对于该方法至关重要。我肯定会研究他构建的额外Sass函数。我已经很容易地找到了它们的用途。

// Map
$sizes: (
  null: (
    breakpoint: 0,
    container: 100%
  ),
  xs: (
    breakpoint: 480px,
    container: 464px
  ),
  sm: (
    breakpoint: 768px,
    container: 750px
  ),
  md: (
    breakpoint: 992px,
    container: 970px
  ),
  lg: (
    breakpoint: 1200px,
    container: 1170px
  )
);


这是一个简单的断点地图。我通常将其用作项目中所有设置的基础地图,因此会在其中包含基本字体大小等内容。
// Breakpoint mixin
@mixin break($screen-min: null, $screen-max: null, $orientation: null) {
  $min: $screen-min;
  $max: $screen-max;
  $o: $orientation;
  $query: unquote("only screen");
  @if $min != null and $min != "" {
    @if map-has-nested-keys($base, sizes, $screen-min) {
      $min: map-deep-get($base, sizes, $screen-min, breakpoint);
    }
    @else {
      $min: $screen-min;
    }
    @if is-number($min) {
      $query: append($query, unquote("and (min-width: #{$min})"));
    }
  }
  @if $max != null and $max != "" {
    @if map-has-nested-keys($base, sizes, $screen-max) {
      $max: map-deep-get($base, sizes, $screen-max, breakpoint);
    }
    @else {
      $max: $screen-max;
    }
    @if is-number($max) {
      $query: append($query, unquote("and (max-width: #{$max})"));
    }
  }
  @if $orientation == landscape or $orientation == portrait {
    $o: $orientation;
    $query: append($query, unquote("and (orientation: #{$o})"));
  }
  @else {
    $o: null;
  }
  @media #{$query} {
    @content;
  }
};

这是一个混合器。您可以使用尺寸映射中的键(xs,sm,md,lg)作为前两个参数,或者您可以使用自定义值(例如30em)。第三个参数接受横向或纵向。您甚至可以自定义混合器,将l = landscape和p = portrait。
此外,如果您只想要一个方向,例如,您可以传递参数(null,null,landscape)。
为了清晰起见,这里有一些示例:
@include break(null, md, landscape) {
  ...
}

@include break(null, null, landscape) {
  ...
}

@include break(md) {
  ...
}

@include break(null, md) {
  ...
}

@include break(480px) {
  ...
}

输出:

@media only screen and (max-width: 992px) and (orientation: landscape) {
  ...
}
@media only screen and (orientation: landscape) {
  ...
}
@media only screen and (min-width: 992px) {
  ...
}
@media only screen and (max-width: 992px) {
  ...
}
@media only screen and (min-width: 480px) {
  ...
}

1
您好,感谢您的回答。正如您所说,您提出的解决方案并不是基于Bootstrap 4的,因此它并不是我问题的合适解决方案。请注意,我已经自己找到了解决方案,并在以下帖子中发布了。然而,map函数看起来很有趣、功能强大,如果您没有使用像Bootstrap这样的框架,那么它是必要的。顺便说一句,Bootstrap也使用这种类型的map来进行媒体查询。 - octogone.dev

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接