Зарегистрируйтесь, чтобы продолжить обучение

Функции SASS: Программирование

В одном из прошлых уроков мы научились использовать миксины как функции. Вспомним, что функции — участки кода, которые могут принимать аргументы и в конечном итоге возвращают результат своей работы. Таким образом мы можем совершать операции с разными числами множество раз. Можно привести простой пример получения квадрата любого числа. Для этого нам необходимо умножить число на само себя. Попробуем это сделать с помощью SASS.

Чтобы создать функцию в SASS используется ключевое слово @function, после которого идёт уникальное имя функции. Именно по этому имени мы и будем обращаться к функции впоследствии.

@function square

Теперь мы должны определить аргументы нашей функции. Аргумент — некая переменная, от которой зависит результат выполнения функции. Если вы разобрались с миксинами, то здесь проблем не возникнет. В отличие от миксинов, любая функция после имени имеет круглые скобки, даже в том случае, если никакие аргументы не передаются. Наша функция возведения в квадрат принимает один аргумент — число, которое возводится в квадрат. Не забудьте, что имена аргументов могут быть произвольными и обязательно указываются, как переменные.

@function square($number) {

}

Мы создали определение функции. Теперь настала очередь написать тело функции, в котором содержатся все необходимые вычисления.

@function square($number) {
  $result: $number * $number;
}

Что здесь произошло? Мы создали переменную $result в которую поместили результат перемножения числа на само себя. Создание переменной для результата — хорошая практика, которая помогает быстрее разобраться в коде.

При выборе имён переменных исходите из того, что имена должны быть понятными и нести смысловую нагрузку. Нет смысла создавать переменные с именами $abc, $lala и так далее. Да — это быстрый путь, но поверьте, что через неделю вы и сами не вспомните, что хранится в той или иной переменной. Вы можете прочитать про именование в программировании в нашем блоге.

С этого момента начинаются главные различия между созданием миксинов и использовании аргументов и созданием функции. Функция всегда что-то возвращает. Сейчас наша функция только считает, но ничего не возвращает. Это схоже с тем, как если вам зададут вопрос, вы найдёте ответ, но никому не расскажете. Чтобы функция могла рассказать, что она вычислила, используется конструкция @return. После неё указывается то, что мы хотим вернуть. В данном случае переменную $result.

@function square($number) {
  $result: $number * $number;
  @return $result;
}

Теперь наша функция полностью готова. У неё есть имя и аргументы, она делает операции внутри себя и возвращает какой-то результат. В этом достаточно просто убедиться — попробуем вызвать нашу функцию. Для этого достаточно указать её имя и аргументы, которые она принимает.

$side: 10;

@function square($number) {
  $result: $number * $number;
  @return $result;
}

.square {
  width: #{square($side)}px;
  height: #{square($side)}px;
}

Скомпилируем наш файл и получим следующий CSS-код:

.square {
  width: 100px;
  height: 100px;
}

Сейчас пример может казаться достаточно бесполезным, но со временем вы узнаете о различных конструкциях, которые возможно использовать в теле ваших функций. Это мощный инструмент, который сократит вам десятки часов при разработке.

Возвращение значения

В прошлом примере для возвращения результата мы использовали конструкцию @return и переменную $result, которая создавалась в самом начале тела нашей функции. При таких простых вычислениях можно не использовать дополнительную переменную, а подставлять необходимое выражение непосредственно в @return. Это сократит количество кода. Будьте аккуратны — используйте выражения в @return только при полностью понятной структуре того, что возвращается. Никогда не гонитесь за тем, чтобы написать максимально короткие функции. Впоследствии, возможно, их будет трудно поддерживать. Для простого перемножения можно использовать @return сразу. Тогда наша функция будет выглядеть следующим образом:

@function square($number) {
  @return $number * $number;
}

Возвращение другой функции

Помимо возвращения какого-то значения из функции, мы можем возвращать другие функции. В таком случае вначале функция, которую мы возвращаем, выполнится, и именно её значение будет возвращено. Это удобно в больших проектах, когда одна функция считает аргументы для второй функции и вызывает её. Таким образом можно писать достаточно короткие функции, которые легко читать и понимать.

Давайте представим, что мы хотим возвести в квадрат сумму переданных аргументов. При этом все аргументы должны браться по модулю, чтобы не было отрицательных значений. Если до этого у нас уже была функция возведения в квадрат, то нет никакого смысла вводить её в новой функции заново. Можно просто ей воспользоваться при возврате значения. А для того, что бы взять модуль числа воспользуемся встроенной функцией abs():

@function square($number) {
  @return $number * $number;
}

@function abs-square-sum($number-one, $number-two) {
  $number-one-modal: abs($number-one);
  $number-two-modal: abs($number-two);

  $sum: $number-one-modal + $number-two-modal;

  @return square($sum);
}

@debug abs-square-sum(-10, 5);

Результатом выполнения abs-square-sum(-10, 5) станет число 225.

Функция или миксин?

На первый взгляд может показаться, что нет особых отличий между использованием миксинов и функций. Тогда зачем нам это разделение? Используем миксины везде и живём спокойно. Используем один синтаксис и больше не путаемся.

Необходимо разграничить для себя, когда используются функции, а когда миксины. Миксины — это, в первую очередь, возможность переиспользования CSS-свойств. Не стоит пытаться использовать там логики больше, чем это необходимо. Функции используются для вычислений и зачастую не связаны непосредственно с CSS.

Рассмотрим это утверждение на примере увеличения размера шрифта в полтора раза. При использовании миксинов это может выглядеть следующим образом:

$font-size: 16;

@mixin big-text($size) {
  font-size: #{$size * 1.5}px;
}

.main {
  .error {
    @include big-text($font-size);
  }
}

После компиляции получим следующий код:

.main .error {
  font-size: 24px;
}

Выполним те же преобразования, но с использованием функций.

$font-size: 16;

@function multiply-by-one-and-half($number) {
  @return $number * 1.5;
}

.main {
  .error {
    font-size: #{multiply-by-one-and-half($font-size)}px;
  }
}

Результат выполнения этой функции будет точно таким же. Позволю себе его не копировать :) Как можно заметить, мы получили один и тот же результат, но с двумя разными подходами. Главный смысл функций в том, что нам не важно, где производить умножение на полтора. Эту функцию можно использовать и для вычисления отступов, высоты/ширины. Мы не завязаны на каком-то конкретном свойстве или единице измерения. В этом функции выигрывают у миксинов. Всегда учитывайте то, для чего используются вычисления. В зависимости от этого выбирайте использование или миксинов, или функций.


Аватары экспертов Хекслета

Остались вопросы? Задайте их в разделе «Обсуждение»

Вам ответят команда поддержки Хекслета или другие студенты

Для полного доступа к курсу нужен базовый план

Базовый план откроет полный доступ ко всем курсам, упражнениям и урокам Хекслета, проектам и пожизненный доступ к теории пройденных уроков. Подписку можно отменить в любой момент.

Получить доступ
1000
упражнений
2000+
часов теории
3200
тестов

Открыть доступ

Курсы программирования для новичков и опытных разработчиков. Начните обучение бесплатно

  • 130 курсов, 2000+ часов теории
  • 1000 практических заданий в браузере
  • 360 000 студентов
Отправляя форму, вы принимаете «Соглашение об обработке персональных данных» и условия «Оферты», а также соглашаетесь с «Условиями использования»

Наши выпускники работают в компаниях:

Логотип компании Альфа Банк
Логотип компании Aviasales
Логотип компании Yandex
Логотип компании Tinkoff

Используйте Хекслет по-максимуму!

  • Задавайте вопросы по уроку
  • Проверяйте знания в квизах
  • Проходите практику прямо в браузере
  • Отслеживайте свой прогресс

Зарегистрируйтесь или войдите в свой аккаунт

Отправляя форму, вы принимаете «Соглашение об обработке персональных данных» и условия «Оферты», а также соглашаетесь с «Условиями использования»