include-media icon indicating copy to clipboard operation
include-media copied to clipboard

Container Queries?

Open andreimoment opened this issue 1 year ago • 10 comments

@container queries just landed in Chromium and Firefox, now covering most evergreen browsers. https://caniuse.com/?search=container

Does include-media provide a facility for using them? If not yet, would you consider adding it?

andreimoment avatar Feb 20 '23 20:02 andreimoment

@andreimoment Its just unit support for cqw, cqh, cqi, cqb, cqmin, cqmax right? any others we need to consider?

jackmcpickle avatar Feb 21 '23 01:02 jackmcpickle

@jackmcpickle I think the main addition is the @container query - I don't think this is related to specific units.

@container query is the equivalent of an @media query but based on the size of an ancestor div / containing element and not on the browser's windows size.

A good example by Rachel Andrew - shows the same card displayed in two places - and the card reflows based on the parent element width, not the screen width: https://codepen.io/rachelandrew/pen/NWdaxde

One more nuance of container queries is that the @container query can specify a named ancestor (to overcome the limit of only working with the immediate ancestor). The name of the ancestor is specified in the ancestor's CSS.

I think it would be great to be able to specify dimensions for @container in a format similar to @include media(">phone", "<=tablet") - that would probably be something like @include container(">33ch", "<=60ch") - and now that I think about it, might be a separate library?

I'll be happy to contribute - let me know how I can help.

Details:

https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_Container_Queries https://developer.mozilla.org/en-US/docs/Web/CSS/@container https://developer.mozilla.org/en-US/docs/Web/CSS/container-name

andreimoment avatar Feb 21 '23 19:02 andreimoment

Yes you're right. I think it makes sense to add it in here. I can look at over the weekend, or feel free to have a crack and submit a PR. 😉

jackmcpickle avatar Feb 21 '23 22:02 jackmcpickle

We are speaking of creating @mixin container($conditions...) { , correct?

andreimoment avatar Feb 21 '23 22:02 andreimoment

Yes probably initially just to @container (width > 400px) {}

and a part 2 to support the named containers @container sidebar (width > 400px) {}

jackmcpickle avatar Feb 23 '23 06:02 jackmcpickle

How would you approach the named container api? A mixin needs all of its variables in the variables section.

I was thinking along the by lines of (… “named: thename”) as a parameter.

andreimoment avatar Feb 24 '23 18:02 andreimoment

Yeah lets start with that.

Input

@include container(">=tablet") {
  width: 50%;
}

output

@container (min-width: 768px) {
    width: 50%;
}

and named

Input

@include container("named: sidebar", ">=tablet") {
  width: 50%;
}

output

@container sidebar (min-width: 768px) {
    width: 50%;
}

ideally we can drop the named: part and just treat as special case.

jackmcpickle avatar Feb 24 '23 23:02 jackmcpickle

@andreimoment added PR for initial container queries. Basically the same as media, since is does all the same stuff. If you could have a look and test on your end that would be great.

jackmcpickle avatar Feb 27 '23 21:02 jackmcpickle

there is probably a better way, but this seems to work as a draft. @andreimoment , could you test please? You should be able to patch it into your _include-media.scss:

/// @example scss - Mixing everything
/// @include container('>=350px', '<tablet') { }
/// 
/// or the first argument can be the named container
/// @include container(':named-container', '>=350px', '<tablet') { }
///  
@mixin container($conditions...) {
  @if ($im-media-support and list.length($conditions)==0) {
    @content;
  }

  @else if (not $im-media-support and im-intercepts-static-breakpoint($conditions...)) {
    @content;
  }

  @else if ($im-media-support and list.length($conditions) > 0) {
    $first-condition: list.nth($conditions, 1);
    $first-character: string.slice($first-condition, 1, 1);
    $container-name: "" !default;

    @if ($first-character ==':') {
      $container-name : str-slice($first-condition, 2, -1);
    }

    @if ($container-name =="") {
      @container #{string.unquote(parse-expression($first-condition))} {
        $actual_conditions: slice($conditions, 2);

        @include container($actual_conditions...) {
          @content;
        }
      }
    }

    @else {
      @container #{string.unquote($container-name)} #{string.unquote(parse-expression(list.nth($conditions, 2)))} {
        $actual_conditions: slice($conditions, 3);

        @if (list.length($actual_conditions) > 0) {
          @include container($first-condition, $actual_conditions...) {
            @content;
          }
        }

        @else {
          @content;
        }
      }
    }
  }
}

basaran avatar Jan 16 '24 13:01 basaran

I have a fork here as well @eduardoboucas , please let me know if this is okay to send as PR.

https://github.com/basaran/include-media

basaran avatar Jan 18 '24 07:01 basaran