Windi Lang Draft

Variables

@var width = 1px;
@var baseColor = #c6538c;
@var borderDark = rgba(base-color, 0.88);
@var borderWidth = width + 1px;
@var prop = 'color';

.alert {
  border: ${borderWidth + 4px} solid ${borderDark};
  ${prop}: red;
}

В черновике v1 мы думали об использовании $ аналогично sass. например, $width: 1px;, но в sass все еще есть очень неэлегантный оператор #{}, и при изменении переменной все равно нужно вызывать с символом $. Итак, наконец, мы решили включить указанную выше версию, вдохновленную строками шаблона JavaScript.

Alias

*btn: py-2 px-4 font-semibold rounded-lg;
*btn-green: text-white bg-green-500 hover:bg-green-700;

/* Псевдоним отличается от ярлыков тем, что он не будет компилироваться ни в какой css, псевдоним только определяет замену текста на основе текущей области. */

.button {
  @apply *btn *btn-green border-gray-200 !important;
}

Shortcuts

.btn: py-2 px-4 font-semibold rounded-lg;
.btn-green: btn text-white bg-green-500 hover:bg-green-700;

Apply

/* support omit @apply, when only using utilities */
.btn { p-4 rounded bg-green-500 hover:(bg-green-600) }
.container { max-w-60em py-8 }

@apply bg-white; /* global apply, generate .bg-white... */

.mixed {
  @apply max-w-60em py-8;
  border-radius: 50%;
}

Attributify

.btn {
	@attr[bg] red-500 opacity-30 lg:red-600;
}

@attr[bg] red-500 opacity-30 lg:red-600; /* global attributify */

Comments

support // this is a single line comment
and /* this is multi line comment */

Nesting

@screen sm {
  .clearfix {
    display: block;
    zoom: 1;
    &:after {
      content: " ";
      display: block;
      font-size: 0;
      height: 0;
      clear: both;
      visibility: hidden;
    }
  }
}

AutoEscape

/* input */
.sm:hover:bg-red-500 {

}
/* output */
.sm\:hover\:bg-red-500 {

}

Configuration

/* only works in the scope */
@config local {
	colors: {
		...
	}
}

/* set global config */
@config global {
  colors: {
    ...
  }
}

Layer

@layer base {

}
@layer components {

}
@layer utilities {

}

Important

/* input */
@important {
  .clearfix {
    display: block;
    zoom: 1;
  }
}
/* output */
.clearfix {
  display: block !important;
  zoom: 1 !important;
}

Data Types

boolean

@var open = True;
@var close = False;
@var none = None;

Обратитесь к python, начальные заглавные буквы легче определить.

string

@var color = 'blue';
@var color = "blue";
@var borderValue = `${borderWidth} solid ${borderDark}`; /* template string */

sizes

@var size = 1rem;
@var size = 1em;
@var size = 1px;
...

colors

@var color = #f2ece4; // #f2ece4
@var color = #b37399aa; // rgba(179, 115, 153, 67%)
@var color = midnightblue; // #191970
@var color = rgb(204, 102, 153); // #c69
@var color = rgba(107, 113, 127, 0.8); // rgba(107, 113, 127, 0.8)
@var color = hsl(228, 7%, 86%); // #dadbdf
@var color = hsla(20, 20%, 85%, 0.7); // rgb(225, 215, 210, 0.7)

number

@var width = 2;
@var height = 3.2;

dictionary

@var colors = {
  'primary': blue;
  'secondary': green;
}
/* set value */
colors['primary'] = red;
/* get value */
colors['primary'];

array

@var colors = [blue, gray, gray-200, 'test,comma'];

/* set value */
colors[2] = red;
colors.push(yellow);
colors.pop(yellow);

Operators

+ - * / ** == != ! > < >= <= and or not => new as in not in .

// числа преобразуются в одинаковые единицы
@var conversion-1 = 5cm + 10mm; // result is 6cm
@var conversion-2 = 2 - 3cm - 5mm; // result is -1.5cm

// преобразование невозможно
@var incompatibleUnits = 2 + 5px - 3cm; // result is 4px

// пример с переменными
@var base = 5%;
@var filler = base * 2; // result is 10%
@var other = base + filler; // result is 15%

Умножение и деление не преобразуют числа. В большинстве случаев это не имеет смысла - длина, умноженная на длину, дает площадь, а css не поддерживает указание областей. Less будет работать с числами как есть и назначить результату явно указанный тип единицы измерения.

@var base = 2cm * 3mm; // result is 6cm

Вы также можете выполнять арифметические операции с цветами:

@var color = #224488 / 2; //results in #112244
@var bg = #112244 + #111; // result is #223355

Functions

config()

theme()

range()

...

Statements

Каждое выражение на языке windi начинается с символа @.

Function

@func pow(base, exponent) {
  @var result = base ** exponent;
  @return result;
}

Loading

импорт javascript модуля

@load 'module1', 'module2', 'module3';
@load { export1 } from "module-name";
@load { export1 , export2 } from "module-name";
@load { export1 , export2 as alias2 , export3 as alias3 } from "module-name";
@load * from "module";
@load * as name from "module";
@load defaultExport from "module";
@load defaultExport, { export1, export2 } from "module-name";
@load defaultExport, * as name from 'module-name';

Importing

импорт css файлов

@import "typo.css";
@import "typo.windi";
@import "src/corners" as c;
@import "src/corners.windi" as c;

Console

@log 4rem + 3px;
@warn 'warn something';
@error 3rem * 2;
@assert 4 in [1, 2, 4];

Logic

If Statement
@var color = 'blue';

@if color == 'red' {
  .button {
    @apply btn btn-red border-gray-200 !important;
  }
} @elif color == 'green' {
  .button {
    @apply btn btn-green border-gray-200 !important;
  }
} @else {
  .button {
    @apply btn btn-blue border-gray-200 !important;
  }
}
For Statement
@for color in [red, blue, yellow] {
  .button-${color} {
    background: ${color};
  }
}

@for count, enum_days in enumerate(days, 5) {
  @log count, enum_days;
}
While Statement
@var i = 3;

@while i > 0 {
  @log i;
  i = i - 1;
} @else {
  @log i;
}

With

@with add(1,2) as c {
  c = c + 3;
  @log c;
}

Try

@var result;

@try {
  result = 10 / x;
} @except TypeError as error1 {
  @log \`Type Error \${error1.message}\`;
}

@try {
  result = 10 / x;
} @except Exception as error {
  @log 'Exceptions';
}

JS

@js {
  import { eval, rgba, get, set } from 'windi/lang';

  const a = get('width');
  set('width', eval('4px'));
  const width = eval('3px');
  export function add(a, b) {
    return a + b;
  }
}

@var c = add(1, 2);

Others

@break;
@continue;
@yield 123;
@return 'hello world';
@raise Error('msg);
@del a['key'];

Implementation

В настоящее время мы компилируем windi lang в JavaScript и запускаем его, как и TypeScript. Позже у нас также будет переводчик, чтобы сделать его независимым языком. В любом случае мы надеемся получить язык программирования, который хорошо взаимодействует с JavaScript и windi. Все зависимости пакетов windi будут построены с использованием TypeScript, что означает, что вы можете напрямую вызывать функции или классы JavaScript/TypeScript.

Кроме того, что касается построения css, у нас есть собственный движок сборки css, начиная с версии windi v1, а затем мы также реализовали вложенный css, поэтому я не буду здесь вдаваться в подробности. Короче верю, что с приведенной выше грамматикой windi станет более совершенной.

Пока что мы все еще находимся на стадии черновика, поэтому любые предложения приветствуются. Вы можете начать обсуждение в обсуждениях на github, и мы ответим вам в ближайшее время.