Concrete Sass Examples

When I started using Sass I was mostly using  nesting and variables. In my own experience this is also what I’ve seen to be the most commonly used features.

I want to illustrate some of it’s other features and how they can be used with practical examples.

@for and @if rules

The @for and @if rules can be used to quickly generate a lot of CSS selectors. Things that would have been possible but impractical and would have been hard to maintain.

For example to make a CSS implementation of  a progress meter, I used the @for and @if rules.

@for $pct from 0 through 100 {
    .progress-#{$pct} {
      width: getWidth($pct);

      &.tresholds {
        @if $pct < 33 {
          background-color: greenyellow;
        } @else if $pct < 66 {
          background-color: yellow;
        } @else {
          background-color: red;
        }
      }
    }
}

This quickly generates all 100 CSS selectors with colours varying depending on the progress.

You can see the full example here: CSS Progress Meters CodePen.

Another good use of the @for rule is for creating multiple @keyframes in CSS animations.

@function

Functions can be used to return values which is useful when dealing with dynamic rules like those created with @for or to calculate a value using a variable. This way if this value changes in the future you only need to change the variable and not all of the derived values.

For example (this is taken from the same progress meters CodePen):

$meter-width: 120px;

@function getWidth($pct) {
  @return $meter-width / 100 * $pct;
}

In this case the getWidth function will return the width for a given percentage. In the previous progress meter example we use this to get the width at each iteration in our for loop.

Also if we change the value of the $meter-width variable we won’t have to change our scss file besides that single value change.

Using Sass variables with CSS’ calc

CSS’ calc function is great, particularly when doing things like:

width: calc(100% - 5em);

You can still use your Sass variables in the calc function by using the following syntax:

$meter-width: 120px;

width: calc(100% - #{$meter-width});

Mixins

Mixins allow you to include a bunch of rules at once in a selector. Similar to @extend but one of the things that differentiate them is the fact that mixins can have parameters.

The Sass website mentions vendor prefixes as a good use of mixins. In this CSS triangles CodePen, I demonstrate another use. I used mixins for creating triangles using the the CSS Triangle trick.

If you define these mixins in a base scss file, you can then easily create all kind of CSS triangles.

%arrow {
  height: 0;
  width: 0;
}

@mixin css-triangle-trick-up($size, $color) {
  border-bottom: $size solid $color;
  border-left: $size solid transparent;
  border-right: $size solid transparent;
}

@mixin css-triangle-trick-down($size, $color) {
  border-top: $size solid $color;
  border-left: $size solid transparent;
  border-right: $size solid transparent;
}

.arrow-up {
  @extend %arrow;
  @include css-triangle-trick-up(30px, white);
}

.arrow-red-down {
  @extend %arrow;
  @include css-triangle-trick-down(40px, red);
}

The CodePen also includes examples of the @for rule and @extend.

Conclusion

There is more to Sass than what I have shown here, but still Sass is one of those subjects where there aren’t a ton of things to master. It’s quick and easy to learn the different features it offers and well worth the effort.

Use TypeScript enum values in Angular HTML templates

You can use your enum values in your HTML templates. This comes in handy for cases like ngSwitch where it’s more readable to use the enum value than it’s underlying value.

There are many ways to do this but I like to use this technique which requires defining the enum in your component class:

  // Expose enum to HTML template.
  myEnum: typeof MyEnum = MyEnum;

And then using it in your component template:

*ngSwitchCase="myEnum.Done"

Making PDF.js work with digital signatures

Out of the box PDF.js doesn’t support displaying signatures on PDF files. This is strange since it’s such a common scenario and it’s been requested many times over the years.

Thankfully there’s a simple solution to this. You need to modify the pdf.worker.js file with the following modification.

In the var WidgetAnnotation = /*#__PURE__*/ function, look for the following code:

if (data.fieldType === 'Sig') {
  data.fieldValue = null;
  _this3.setFlags(_util.AnnotationFlag.HIDDEN);
}

And comment out the setFlags line like this:

if (data.fieldType === 'Sig') {
  data.fieldValue = null;
  // _this3.setFlags(_util.AnnotationFlag.HIDDEN);
}

You don’t need to make any modifications to the pdf.js file itself just the pdf.worker.js file.

To do this you download PDF.js from the project page. Take the pdf.worker.js file from the build folder and make the modification. In your web project, use the local modified version of this file but keep referencing the base file through a CDN (or locally if you wish).

Don’t forget to minify your modified worker file afterwards.

Of course, you’ll have to make this manual modification each time you update PDF.js.

Final Fantasy like screen transition effect

transition-effect

I’ve created a small project where I tried to produce an effect similar to the Final Fantasy 8 screen transition effect.

You can see a video of the original effect here and my project in action here.

The code is accessible through the GitHub repository.

Whilst I’m a Firefox user I had to resort to refreshing the page on Firefox as it leaked an amount of memory the size of the canvas’ image data. This leak wasn’t present on Chrome, Edge or Safari.

I’m writing directly to the image data like a buffer, which I found out is far from optimal. It’s far better to stick to drawing primitives from the API (much faster) but this ultimately limits what you can do which is why I stuck with direct operations on the image data.