containerSelector = $containerSelector;
# добавление мастер поля
$masterAdd = function ($id) use (&$settings) {
$this->masters[$id] = [
'd' => isset($settings[$id]['data']) ? $settings[$id]['data'] : 0,
];
};
# добавление поля с условием
$toggleAdd = function (&$arr, $k, $kk, $vv) {
$arr[] = [
'k' => $k,
'm' => $kk,
'v' => is_array($vv) ? $vv : [$vv],
];
};
# обрабатываем табы
if (! empty($options['tabs']) && is_array($options['tabs'])) {
foreach ($options['tabs'] as $k => $v) {
$this->tabs[$k] = [];
# добавляем табы с условием для видимости
if (isset($v['visibleIf']) && is_array($v['visibleIf'])) {
foreach ($v['visibleIf'] as $kk => $vv) {
if (! isset($settings[$kk])) {
continue;
}
$masterAdd($kk);
$toggleAdd($this->visibleTabs, $k, $kk, $vv);
}
}
# добавляем табы с условием для скрытности
if (isset($v['hiddenIf']) && is_array($v['hiddenIf'])) {
foreach ($v['hiddenIf'] as $kk => $vv) {
if (! isset($settings[$kk])) {
continue;
}
$masterAdd($kk);
$toggleAdd($this->hiddenTabs, $k, $kk, $vv);
}
}
}
}
# обрабатываем поля
foreach ($settings as $k => $v) {
# добавляем поля с условием для видимости
if (isset($v['visibleIf']) && is_array($v['visibleIf'])) {
foreach ($v['visibleIf'] as $kk => $vv) {
if (! isset($settings[$kk])) {
continue;
}
$masterAdd($kk);
$toggleAdd($this->visible, $k, $kk, $vv);
}
}
# добавляем поля с условием для скрытности
if (isset($v['hiddenIf']) && is_array($v['hiddenIf'])) {
foreach ($v['hiddenIf'] as $kk => $vv) {
if (! isset($settings[$kk])) {
continue;
}
$masterAdd($kk);
$toggleAdd($this->hidden, $k, $kk, $vv);
}
}
}
# нумеруем табы
$i = 1;
foreach ($this->tabs as & $v) {
$v['id'] = $i;
$i++;
}
# нумеруем мастер поля
$i = 1;
foreach ($this->masters as & $v) {
$v['id'] = $i;
$i++;
}
}
/**
* Генерация css класов для скрывания блоков
* @return string
*/
public function css(): string
{
$selector = $this->containerSelector;
$result = '';
if (! empty($this->tabs)) {
$result .= $selector . ' .j-hide-t{display: none;} ';
}
foreach ($this->masters as $v) {
$result .= $selector . ' .j-hide-' . $v['id'] . '{display: none;} ';
}
return $result ? '' : '';
}
/**
* Генерация атрибутов для тегов TR
* @param string $key ключ настройки
* @param array $field значение настройки
* @param array $attr @ref атрибуты тега TR
* @return void
*/
public function trAttributes(string $key, $field, array &$attr)
{
$classes = [];
# проверим присутствие поля в условиях для видимости
foreach ($this->visible as $v) {
if ($v['k'] !== $key) {
continue;
}
if (isset($this->masters[ $v['m'] ])) {
$m = $this->masters[ $v['m'] ]; # мастер от которого зависит
$classes[] = 'j-visible-' . $m['id']; # класс зависимости от мастера
foreach ($v['v'] as $vv) {
$classes[] = 'j-visible-' . $m['id'] . '-' . $vv; # класс зависимости от значения
}
if (! in_array($m['d'], $v['v'])) {
$classes[] = 'j-hide-' . $m['id']; # скрываем при необходимости от текущего значения мастера
}
}
}
# проверим присутствие поля в условиях для скрытности
foreach ($this->hidden as $v) {
if ($v['k'] !== $key) {
continue;
}
if (isset($this->masters[ $v['m'] ])) {
$m = $this->masters[ $v['m'] ]; # мастер от которого зависит
$classes[] = 'j-hidden-' . $m['id']; # класс зависимости от мастера
foreach ($v['v'] as $vv) {
$classes[] = 'j-hidden-' . $m['id'] . '-' . $vv; # класс зависимости от значения
}
if (in_array($m['d'], $v['v'])) {
$classes[] = 'j-hide-' . $m['id']; # скрываем при необходимости от текущего значения мастера
}
}
}
# проверим присутствие поля внутри таба
if (isset($field['tab'])) {
$t = $field['tab'];
if (isset($this->tabs[$t])) {
$tab = $this->tabs[$t];
$classes[] = 'j-extension-settings-tab'; # класс зависимости от табов
$classes[] = 'j-extension-settings-tab-' . $tab['id']; # класс зависимости от конкретного таба
if ($tab['id'] != 1) {
$classes[] = 'j-hide-t'; # скрываем если не в первом табе
}
}
}
if (empty($classes)) {
return;
}
HTML::attributeAdd($attr, 'class', $classes);
}
/**
* Генерация атрибутов для мастер инпутов
* @param string $key ключ настройки
* @param array $attr @ref атрибуты тега input
* @return void
*/
public function inputAttributes(string $key, array &$attr)
{
$classes = [];
if (isset($this->masters[$key])) { # если настройка определена как мастер
$classes[] = 'j-toggle-if'; # класс для события onchange
$attr['data-toggle'] = $this->masters[$key]['id']; # установим id мастера
}
if (empty($classes)) {
return;
}
HTML::attributeAdd($attr, 'class', $classes);
}
/**
* Генерация атрибутов для табов
* @param string $key ключ таба
* @param array $attr @ref атрибуты таба
* @return void
*/
public function tabAttributes(string $key, array &$attr)
{
$classes = [];
if (isset($this->tabs[$key])) {
$t = $this->tabs[$key];
$classes[] = 'j-toggle-tab'; # класс для события onclick
$attr['data-id'] = $t['id']; # установим id таба
}
# проверим присутствие таба в условиях для видимости
foreach ($this->visibleTabs as $v) {
if ($v['k'] !== $key) {
continue;
}
if (isset($this->masters[ $v['m'] ])) {
$m = $this->masters[ $v['m'] ]; # мастер от которого зависит
$classes[] = 'j-visible-' . $m['id']; # класс зависимости от мастера
foreach ($v['v'] as $vv) {
$classes[] = 'j-visible-' . $m['id'] . '-' . $vv; # класс зависимости от значения
}
if (! in_array($m['d'], $v['v'])) {
$classes[] = 'j-hide-' . $m['id']; # скрываем при необходимости от текущего значения мастера
}
}
}
# проверим присутствие поля в условиях для скрытности
foreach ($this->hiddenTabs as $v) {
if ($v['k'] !== $key) {
continue;
}
if (isset($this->masters[ $v['m'] ])) {
$m = $this->masters[ $v['m'] ]; # мастер от которого зависит
$classes[] = 'j-hidden-' . $m['id']; # класс зависимости от мастера
foreach ($v['v'] as $vv) {
$classes[] = 'j-hidden-' . $m['id'] . '-' . $vv; # класс зависимости от значения
}
if (in_array($m['d'], $v['v'])) {
$classes[] = 'j-hide-' . $m['id']; # скрываем при необходимости от текущего значения мастера
}
}
}
if (empty($classes)) {
return;
}
HTML::attributeAdd($attr, 'class', $classes);
}
/**
* Формирование javascript кода для переключения видимости полей
* @return string
*/
public function js(): string
{
if (empty($this->tabs) && empty($this->masters)) {
return '';
}
tpl::start();
$selector = $this->containerSelector;
?>