# Свойства блоков

## Вид

### Текстура - *texture*

Название текстуры блока (указывается только имя, без расширения или пути к файлу)

Файл текстуры должен находиться в `res/textures/blocks/` и иметь формат **png**

### Текстурирование сторон - *texture-faces*

>[!IMPORTANT]
> Не может использоваться одновременно с *texture*

Массив из 6 названий текстур, позволяющих указать их для каждой из сторон отдельно.

Пример: 
```json
"texture-faces": [
    "grass_side",
    "grass_side",
    "dirt",
    "grass_top",
    "grass_side",
    "grass_side"
]
```

### Модель - *model*

Модель блока из списка:
- "block" - используется по-умолчанию для всех обычных блоков
- "none" - невидимый блок (пример: воздух)
- "X" - модель травы (крест из двух спрайтов)
- "aabb" - модель, соответствующая хитбоксу блока (составной хитбокс будет объединен в один). Примеры: трубы, лампочки, панели.

### Имя модели - *model-name*

Кроме встроенных типов моделей, можно использовать собственные, загружаемые из файлов.

В свойстве указывается имя модели без `точка_входа:models/` и расширения.

> [!WARNING]
> Текстуры (материалы), использующиеся в модели, должны находиться в атласе `blocks` и указываться в соответствующем формате:
> `blocks:имя_текстуры`

### Группа отрисовки - *draw-group*

Целое число определяющее номер группы отрисовки данного блока. 
Актуально для полупрозрачных блоков - решает проблемы невидимых сторон блоков за этим блоком.

### Полупрозрачность - *translucent*

Включает поддержку полупрозрачности в текстурах блока (примеры: вода, лёд).
Следует использовать только при надобности, так как влияет на производительность.
Не требуется для полной прозрачности (трава, цветы).

### Вращение - *rotation*

Профиль вращения (набор положений, в которые можно установить блок) из списка:

- "none" - вращение блока отключено (по-умолчанию)
- "pipe" - профиль "труба". Примеры блоков: бревно, труба, лампочка
- "pane" - профиль "панель". Примеры блоков: панель, дверь, табличка

### Испускаемые частицы - *particles*

Частицы указываются в виде JSON объекта. Имена свойств можно найти [в разделе, посвященном частицам](particles.md).

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

## Освещение

### Излучение - *emission*:

Массив из трех целых чисел - R, G, B освещения от 0 до 15.

Примеры:

- `[15, 15, 15]` - самый яркий белый свет
- `[7, 0, 0]` - слабый красный свет
- `[0, 0, 0]` - блок не излучает свет (по-умолчанию)


### Светопроводимость - *light-passing*

При значении `true` блок проводит свет от излучающих блоков.

### Солнечная светопроводимость - *sky-light-passing*

При значении `true` блок не препятствует прохождению вертикального луча солнечного света.

### Без освещения - *shadeless*

Выключает освещение на модели блока.

### Вершинный Ambient-Occlusion - *ambient-occlusion*

Определяет наличие эффекта вершинного AO. Включен по-умолчанию.

### Отсечение - *culling*

Режим отсечения граней:
- **default** - обычное отсечение граней
- **optional** - отсечение граней среди блоков одной группы отрисовки можно отключить через настройку `graphics.dense-render` (Плотный рендер блоков).
- **disabled** - отсечение граней среди блоков одной группы отрисовки отключено.

## Физика

### Препятствие - *obstacle*

Значение false отключает хитбокс у блока (позволяет игроку проходить сквозь блок)

### Хитбокс - *hitbox*

Массив из 6 чисел описывающих смещение и размер хитбокса блока.

Числа указываются в диапазоне [0.0, 1.0] - т.е в пределах блока.

Массив `[0.25, 0.0, 0.5,  0.75, 0.4, 0.3]` описывает хитбокс:
- смещен на 0.25 м на запад
- смещен на 0.0 м вверх
- смещен на 0.5 м на север
- шириной (с востока на запад) 0.75 м
- высотой 0.4 м
- длиной (с юга на север) 0.3 м

### Приземленность - *grounded*

Блок может быть установлен только на полный блок.
Разрушается при разрушении блока под ним.

### Выделяемость - *selectable*

При значении в `false` курсор будет игнорировать блок, выделяя тот, что находится за ним.

### Заменяемость - *replaceable*

При значении в `true` на месте блока можно установить любой другой блок. Пример: вода, трава, цветок.

### Разрушаемость - *breakable*

При значении в `false` блок нельзя сломать.

## Инвентарь

### Скрытый блок - *hidden*

При значении в `true` блок не появляется в инвентаре и для него не генерируется предмет, поэтому c 0.17 требуется указать свойство *picking-item*

### Подбираемый предмет - *picking-item*

Предмет, который будет выбран при нажатии средней кнопкой мыши на блок.

Пример: блок `door:door_open` скрыт (hidden) поэтому указывается `picking-item: "door:door.item"`

### Имя скрипта - *script-name*

Позволяет указать название скрипта блока. Свойство обеспечивает возможность использования одного скрипта для нескольких блоков.
Название указывается без `пак:scripts/` и расширения.

### Имя макета UI - *ui-layout*

Позволяет указать id XML-макета интерфейса блока. По-умолчанию используется строковый id блока.

### Размер инвентаря - *inventory-size*

Число слотов инвентаря блока. По-умолчанию - 0 (инвентарь отсутствует)

## Расширенные блоки

### Размер блока - *size*

Массив из трех целых чисел. Значение по-умолчанию - `[1, 1, 1]`.

## Поля блока

Поля блоков позволяет записывать больше уникальных для конкретного блока данных, чем это позволяют пользовательские биты.

Поля блока объявляются в следующем формате:

```json
"fields": {
    "имя": {"type": "тип_данных"},
    "имя_массива": {"type": "тип_данных", "length": "длина_массива"}
}
```

Кроме `type` и `length` доступен параметр `convert-strategy` определяющий
стратегию конвертации значения при сужении типа данных.

Параметр принимает одно из двух значений:
- `reset` - значение, не попадающее в новый диапазон, будет сброшено до 0
- `clamp` - значение будет сведено к ближайшему в новом диапазоне

Пример: число 231 при изменении типа поля с int16 до int8:
- в режиме `reset` превратится в 0
- в режиме `clamp` превратится в 127


Доступные типы данных:

| Тип     | Размер   | Описание                      |
| ------- | -------- | ----------------------------- |
| int8    | 1 байт   | целочисленный знаковый 8 бит  |
| int16   | 2 байта  | целочисленный знаковый 16 бит |
| int32   | 4 байта  | целочисленный знаковый 32 бит |
| int64   | 8 байт   | целочисленный знаковый 64 бит |
| float32 | 4 байта  | вещественный 32 бит           |
| float64 | 8 байт   | вещественный 64 бит           |
| char    | 1 байт   | символьный                    |

- На данный момент общая сумма размеров полей не может превышать 240 байт.
- Поле без указания длины массива эквивалентно массиву из 1 элемента.
- Массив символьного типа может использоваться для хранения UTF-8 строк.

## Пользовательские свойства

Доступ к пользовательским свойствам производится через таблицу `block.properties[id]["свойство"]` где id - числовой id (индекс) блока.

Пользовательские свойства должны быть объявляены в файле `пак:config/user-props.toml`:
```toml
"пак:имя_свойства" = {}
```

Пример: [пользовательские свойства пака **base**](../../res/content/base/config/user-props.toml).

## Свойства, вводимые паком `base`

### Прочность - *base:durability*

Время разрушения блока без инструментов и эффектов в секундах.

### Лут - *base:loot*

Список таблиц со свойствами:

```json
{
    "item": "пак:предмет",
    "min": 1,
    "max": 3,
    "chance": 0.5
}
```

- count равен 1 по-умолчанию. Не нужно указывать если указаны `min` и `max`.
- min, max - минимальное и максимальное количество предмета.
- chance - вероятность выпадения предмета. По-умолчанию: 1.0.

Следует учитывать, что в item указывается именно предмет. Т.е. чтобы указать предмет блока, нужно добавить `.item` после имени блока.
Пример: `base:dirt.item`.

Для генерации лута следует использовать функцию `block_loot(block_id: int)` в модуле `base:util`.

## Методы

Методы используются для управлением перезаписью свойств при расширении блока другими паками.

### `имя_свойства@append`

Добавляет элементы в конец списка, вместо его полной перезаписи.
