Files
2025-08-02 16:30:27 +02:00

1201 lines
36 KiB
PHP

<?php
namespace KupShop\AdminBundle\AdminList;
use DatabaseCommunication;
use Frame;
use KupShop\AdminBundle\Util\ListColumns;
use KupShop\AdminBundle\Util\ListExporter;
use KupShop\KupShopBundle\Context\CurrencyContext;
use KupShop\KupShopBundle\Util\Compat\ServiceContainer;
use KupShop\KupShopBundle\Util\HtmlBuilder\HTML;
use KupShop\KupShopBundle\Util\StringUtil;
use KupShop\KupShopBundle\Util\System\UrlFinder;
use Pager;
use Query\Operator;
use Query\QueryBuilder;
#[\AllowDynamicProperties]
class BaseList extends Frame
{
use DatabaseCommunication;
use FiltersStorage;
protected $tableDef = ['fields' => []];
protected $pageDivide;
protected $template = 'list.tpl';
protected $showAddItem = false;
protected $showExport = true;
protected $showMassEdit = false;
private $massEditActive = false;
protected $tableName;
/**
* Must be set when $tableName is defined.
*/
protected ?string $tableAlias = null;
protected $orderParam = [];
protected $tableDefLoaded;
protected bool $useFilterQuery = false;
protected bool $useLazyNumberOfPages = false;
protected ?int $totalObjectsCount = null;
protected bool $useFiltersStorage = true;
protected bool $hasStringId = false;
// Column types
public const TYPE_STRING = 'string';
public const TYPE_DATE = 'date';
public const TYPE_DATETIME = 'datetime';
public const TYPE_FLOAT = 'float';
public const TYPE_INT = 'int';
public const TYPE_PRICE = 'price';
public const TYPE_PRICE_WITH_CURRENCY = 'priceWithCurrency';
public const TYPE_FLOAT_WITH_CURRENCY = 'floatWithCurrency';
public const TYPE_BOOL = 'bool';
public const TYPE_LIST = 'list';
public const TYPE_LIST_MULTISELECT = 'listMultiselect';
public const TYPE_LIST_AUTOCOMPLETE = 'autocomplete';
public const TYPE_LIST_ACTIONS = 'actions';
public const TYPE_LIST_MULTISELECT_AUTOCOMPLETE = 'multiselectAutocomplete';
public const TYPE_POSITION = 'position';
protected function getOrder($type)
{
$cookieName = 'adminList_'.$type;
if (!empty($_GET['window'])) {
$cookieName .= 'window';
}
if (!empty($_GET['order'])) {
// pokud ma starou formu
if (preg_match('/^([0-9]+)(a|d)$/i', $_GET['order'], $matches)) {
$orderParam = $this->createOrderParamFromOldStyle($matches);
} else {
$orderParam = [
'direction' => StringUtil::startsWith($_GET['order'], '-') ? 'DESC' : 'ASC',
'sort' => trim($_GET['order'], '-'),
];
}
} else {
$orderParam = $this->orderParam;
// fallback na cookie
if (!empty($_COOKIE[$cookieName])) {
// pokud je z cookie, tak musi mit starou formu
$orderParam = $this->createOrderParamFromOldStyle(unserialize($_COOKIE[$cookieName]));
}
if ($this->filterStorageReady()) {
if (isset($this->activeFilter)) {
$orderParam = json_decode($this->activeFilter['sort'] ?? '', true);
} else {
$defaultFilter = $this->getDefaultFilter();
if ($defaultFilter && !empty($defaultFilter['sort'])) {
$orderParam = $defaultFilter['sort'];
}
}
}
}
// pokud je orderParam porad prazdny / neni nastaveny, tak pouzij default
if (empty($orderParam)) {
return $this->getDefaultOrder();
} else {
// fallback pokud se upravil key ve fields kvuli prekladum
if (!array_key_exists($orderParam['sort'], $this->getTableDef()['fields'])) {
foreach ($this->getTableDef()['fields'] as $key => $field) {
if ($field['title'] == $orderParam['sort']) {
$orderParam['sort'] = $key;
break;
}
}
}
if ($this->getTableDef()['fields'][$orderParam['sort']]['visible'] == 'N') {
return $this->getDefaultOrder();
}
}
return $orderParam;
}
protected function getDefaultOrder()
{
if ($this->orderParam) {
return $this->orderParam;
}
$fields = array_keys($this->getTableDef()['fields']);
return [
'sort' => reset($fields),
'direction' => 'ASC',
];
}
private function createOrderParamFromOldStyle($old)
{
$tableDef = $this->getTableDef();
$fields = $tableDef['fields'];
$index = $old[1] ?? 0;
if ($index > 0) {
$index--;
}
$names = array_keys($fields);
return [
'sort' => $names[$index] ?? reset($names),
'direction' => ($old[2] ?? 'a') == 'a' ? 'ASC' : 'DESC',
];
}
public function &getTableDef()
{
// tableAlias can't be NULL when tableName is defined
assert(
!(!is_null($this->tableName) && is_null($this->tableAlias)),
'tableAlias can not be NULL when tableName is defined in '.static::class
);
if (!$this->tableDefLoaded) {
// customize
$this->tableDef = $this->customizeTableDef($this->tableDef);
if ($this->massEditActive) {
$this->tableDef = $this->customizeMassTableDef($this->tableDef);
}
$this->tableDef = $this->translateTableDef($this->tableDef);
/** @var ListColumns $listColumn */
$listColumn = ServiceContainer::getService(ListColumns::class);
$tableDef = $listColumn->orderTableDef($this->tableDef, getVal('type'), getVal('adminFilter'));
$this->tableDef = $tableDef;
$this->tableDefLoaded = true;
}
return $this->tableDef;
}
private function translateTableDef($tableDef)
{
$fields = $tableDef['fields'] ?? [];
// translate
foreach ($fields as $key => &$field) {
if (isset($field['translate'])) {
$translation_section = $field['translation_section'] ?? $tableDef['translation_section'] ?? getVal('type');
if ($field['translate'] === true) {
$label = translate($key, $translation_section);
} elseif (is_callable($field['translate'])) {
$label = $field['translate']($key, $translation_section);
} else {
$label = translate($field['translate'], $translation_section);
}
$field['title'] = $label;
} else {
$field['title'] = $key;
}
}
$tableDef['fields'] = $fields;
return $tableDef;
}
public function customizeTableDef($tableDef)
{
return $tableDef;
}
public function customizeMassTableDef($tableDef)
{
return $tableDef;
}
public function getTableIdColumn(): string
{
return $this->getTableDef()['id'];
}
/**
* @return \Query\QueryBuilder
*/
public function getQuery()
{
return sqlQueryBuilder()
->select($this->tableAlias ? "{$this->tableAlias}.*" : '*')
->from($this->getTableName(), $this->tableAlias)
->where(
$this->hasStringId ? Operator::inStringArray($this->getFilterIds(), $this->getTableIdColumn()) :
Operator::inIntArray($this->getFilterIds(), $this->getTableIdColumn())
)
->groupBy($this->getTableIdColumn());
}
public function getFilterIds(): array
{
// Jakmile volám getFilterIds(), používám filter query
$this->useFilterQuery = true;
$page = $this->getPage();
$divide = $this->getPageDivide();
$qb = $this->getFilterQuery();
if ($divide > 0) {
$qb->setFirstResult(ceil(($page - 1) * $divide))
->setMaxResults($divide);
}
// Ordering
$vars = [];
$vars['orderParam'] = $this->getOrder(
$this->getListName()
);
$this->applyOrder($qb, $vars);
if (!$this->useLazyNumberOfPages) {
$this->addSQLCalcFoundRows($qb);
}
$IDs = sqlFetchAll($qb->execute(), ['id' => 'id']);
if (!$this->useLazyNumberOfPages) {
$this->totalObjectsCount = returnSQLResult('SELECT FOUND_ROWS()');
}
return $IDs;
}
public function getFilterQuery(): QueryBuilder
{
return sqlQueryBuilder()
->select($this->getTableIdColumn().' as id')
->from($this->getTableName(), $this->tableAlias)
->groupBy($this->getTableIdColumn());
}
public function addSQLCalcFoundRows(QueryBuilder $qb): void
{
$selectPart = $qb->getQueryPart('select');
$selectPart[0] = 'SQL_CALC_FOUND_ROWS '.$selectPart[0];
$qb->select($selectPart);
}
private function getCountQuery(): QueryBuilder
{
if (!$this->useFilterQuery) {
// pokud jeste nepouzivam filter query, tak potrebuju nejak nacist IDcka vcetne aplikovanych filtru
// takze pouziju standardni `getQuery` a selectnu pouze idcka a podle toho zafiltruju, abych nacetl pocet
$qb = $this->getQuery();
if (is_array($qb)) {
$qb = $query['qb'] ?? null;
}
$subquery = $qb
->select($this->getTableIdColumn());
} else {
// pokud pouzivam filter query, tak jen nactu filter query a ten pouziju
$subquery = $this->getFilterQuery();
}
assert(!is_null($this->getTableName()), 'tableName can not be NULL in '.static::class);
return sqlQueryBuilder()
->select('COUNT('.$this->getTableIdColumn().')')
->from($this->getTableName(), $this->tableAlias)
->where(Operator::inSubQuery($this->getTableIdColumn(), $subquery));
}
public function getFilters()
{
return null;
}
public function getListName()
{
$fullName = explode('\\', $this->getClassName());
$name = end($fullName);
return lcfirst(preg_replace('/List/', '', $name));
}
public function getPageDivide()
{
if (isset($this->pageDivide)) {
return $this->pageDivide;
}
global $dbcfg;
return $dbcfg['page_divide'];
}
public function setPageDivide($pageDivide): void
{
$this->pageDivide = $pageDivide;
}
public function handleExport()
{
$listExporter = ServiceContainer::getService(ListExporter::class);
$this->setPageDivide(0);
$listExporter->setListObject($this);
$listExporter->listExport();
exit;
}
public function get_vars()
{
$vars = parent::get_vars();
$this->tryRights();
$qb = $this->getFinalQueryBuilder($vars);
$sql = $this->getSQL($qb);
$vars['SQL'] = $sql['SQL'];
$vars['pageCount'] = is_array($sql['SQL']) || $sql['SQL'] instanceof \Countable ? count($sql['SQL']) : $sql['SQL']->rowCount();
if (isset($sql['pages'])) {
$vars['pager'] = $this->createPager($sql);
}
$vars['columns'] = $this->getColumns();
$vars['searchWnd'] = getVal('searchWnd');
if ($this->getFilters() != null) {
$filters = $this->getFilters();
$vars['filtersValue'] = $this->getFiltersData($qb, $filters);
// $vars['filtersValue'] = $this->getFiltersData($vars['var'], $filters);
}
$vars['showExport'] = $this->showExport;
$vars['showMassEdit'] = $this->showMassEdit;
return $vars;
}
protected function evaluateColumnClosures(QueryBuilder $qb)
{
foreach ($this->getTableDef()['fields'] as $key => $field) {
if (isset($field['spec']) && $field['visible'] == 'Y') {
// pokud ma mit specku, ale nema ji definovanou
if (is_array($field['spec'])) {
throw new \RuntimeException(
sprintf('Missing field query spec for field: "%s"!', $key)
);
}
$qb->addSelect($field['spec']);
}
}
return $qb;
}
private function filtersActive()
{
$get = $_REQUEST;
unset($get['s'], $get['type'], $get['page'], $get['loadTotalCount'], $get['acn'], $get['OkStr'], $get['ErrStr'], $get['refresh']);
return count($get) > 0 || !empty($_GET['adminFilter']);
}
private function filterStorageReady(): bool
{
return $this->useFiltersStorage;
}
public function activateFilter($filter)
{
if (!$filter) {
return;
}
$this->activeFilter = $filter;
parse_str($filter['list'] ?? '', $output);
foreach ($output as $key => $filter) {
if (is_string($filter) && StringUtil::startsWith($filter, '{DATE:')) {
$date = new \DateTime();
$filter = str_replace('DATE:', '', trim($filter, '{}'));
if ($filter = intval($filter)) {
$date = $date->modify($filter.' day');
}
$filter = $date->format(\Settings::getDateFormat());
}
$_GET[$key] = $filter;
$_REQUEST[$key] = $filter;
}
}
public function activateDefaultFilter()
{
if ($this->filterStorageReady()) {
$default = $this->getDefaultFilter();
$this->activateFilter($default);
if (!empty($default['id'])) {
$_GET['adminFilter'] = $default['id'];
}
}
}
public function createPager($sql)
{
$pager = new Pager($sql['pages'], $sql['pageNumber']);
$pager->setPageInside($sql['pageNumber'] < 5 ? 5 : 3);
$pager->setPageSide(1);
$pager->setTotal($sql['totalCount']);
$pager->setOnPage($this->getPageDivide());
$pager->setUrl(
$this->getCurrentUri()
);
return $pager;
}
public function applyOrder(QueryBuilder $qb, &$vars)
{
$this->getSQLOrdering($vars, $vars['orderParam']);
if (!empty($vars['orderSpec'])) {
$qb->addSelect($vars['orderSpec']);
}
if (!empty($vars['orderField'])) {
$qb->orderBy($vars['orderField'], $vars['orderDir']);
}
return $qb;
}
public function getColumns()
{
$first = true;
$table = &$this->getTableDef();
foreach ($table['fields'] as $label => &$column) {
if ($first && $column['visible'] == 'Y') {
$idField = $this->getFieldArrayName(getVal('id', $table, 'id'));
if ($idField) {
if (!isset($column['type_id'])) {
$column['type_id'] = $idField;
}
if (!isset($column['type'])) {
$column['type'] = $GLOBALS['type'];
}
}
$first = false;
} else {
if (isset($column['type'])) {
$idField = $this->getFieldArrayName(getVal('id', $table, 'id'));
if ($idField && !isset($column['type_id'])) {
$column['type_id'] = $idField;
}
}
}
if (!isset($column['size'])) {
$column['size'] = 1;
}
}
return $table;
}
public static function getClassName()
{
return get_called_class();
}
public function getSQLOrdering(&$var, &$orderParam)
{
if (empty($var['orderField'])) {
$table = &$this->getTableDef();
$fields = $table['fields'];
$column = $orderParam['sort'];
if (isset($fields[$column])) {
$field = $fields[$column];
$var['orderField'] = !empty($field['raw_field']) ? $field['raw_field'] : $field['field'];
$var['orderDir'] = $orderParam['direction'];
// Používám spec pouze pokud používáme filterQuery
if ($field['spec'] ?? null && $this->useFilterQuery) {
$var['orderSpec'] = $field['spec'];
}
}
}
}
public function getPage(): int
{
$page = getVal('page');
if (empty($page)) {
$page = 1;
}
return (int) $page;
}
public function getSQL(QueryBuilder $qb)
{
if (!$this->useLazyNumberOfPages) {
$this->addSQLCalcFoundRows($qb);
}
// ################################################
$page = $this->getPage();
$divide = $this->getPageDivide();
$noPages = 0;
if (!$this->useFilterQuery && $divide > 0) {
$qb->setFirstResult(ceil(($page - 1) * $divide))->setMaxResults($divide);
}
// SQL prikaz na databazi
$SQL = $qb->execute();
if ($this->useLazyNumberOfPages) {
$totalCountCacheKey = $this->getListName().'-'.md5(json_encode($this->getCurrentFilterParams()));
$this->totalObjectsCount = getCache($totalCountCacheKey, $found);
if (!$found) {
$this->totalObjectsCount = null;
}
// loadnu totalCount a cachnu ho na 10 minut
if (getVal('loadTotalCount')) {
$this->totalObjectsCount = $this->getCountQuery()->execute()->fetchOne();
setCache($totalCountCacheKey, $this->totalObjectsCount, 600);
}
} elseif (!$this->useFilterQuery) {
// Když používám filter query, už jsem si počet objektů načetl při fetchování IDček
$this->totalObjectsCount = returnSQLResult('SELECT FOUND_ROWS()');
}
if ($divide > 0) {
// spocitat stranky
$noPages = $this->totalObjectsCount === null ? Pager::INFINITE_PAGE_COUNT : ceil($this->totalObjectsCount / $divide);
}
return [
'SQL' => $SQL,
'pages' => $noPages,
'pageNumber' => $page,
'totalCount' => $this->totalObjectsCount,
];
}
protected function getCurrentFilterParams(): array
{
$params = array_filter($_GET, function ($x) {
if ($x === '0') {
return true;
}
return !empty($x);
});
unset($params['s'], $params['type'], $params['page'], $params['order'], $params['loadTotalCount']);
return $params;
}
protected function getCurrentUri(): string
{
$uri = $_SERVER['REQUEST_URI'];
$parsed = parse_url($uri);
if (!empty($parsed['query'])) {
parse_str($parsed['query'], $query);
unset($query['loadTotalCount']);
$uri = $parsed['path'];
if (!empty($query)) {
$uri .= '?'.http_build_query($query);
}
}
return $uri;
}
public function printHeaderLabel($label, $column)
{
if (!empty($column['label'])) {
return $this->resolveCallable($column['label'], $column, $label);
}
return $label;
}
public function getListRowValue($values, $field, $default = null)
{
$field_name = $this->getFieldArrayName($field);
if (!isset($values[$field_name])) {
return $default;
}
return $values[$field_name];
}
public function printListRowLabel($column, &$values)
{
$render = getVal('render', $column);
if (is_callable($render)) {
$result = $render($this, $values);
} elseif (!empty($render)) {
$result = $this->$render($values, $column);
} else {
$result = $this->renderCell($values, $column);
}
$output = function ($snippet) {
echo $snippet instanceof HTML ? (string) $snippet : htmlspecialchars($snippet ?? '');
};
if (is_array($result)) {
foreach ($result as $part) {
$output($part);
}
} else {
$output($result);
}
}
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++//
public function printListRowItem($column, &$values)
{
$type = getVal('type', $column);
if (!$type) {
return $this->printListRowLabel($column, $values);
}
$params = getVal('params', $column);
$id = $values[$this->getFieldArrayName($column['type_id'])]; ?>
<a href="javascript:<?php if (getVal('searchWnd')) { ?>searchResult('<?php echo $id; ?>', '<?php echo base64_encode(json_encode($values)); ?>')<?php } else { ?>nw('<?php echo $type; ?>', '<?php echo $id; ?>', '<?php echo ($params) ? $params : ''; ?>')<?php } ?>;">
<?php $this->printListRowLabel($column, $values); ?>
</a>
<?php
}
/**
* @deprecated
*/
public function printListRow(&$values)
{
$table = &$this->getTableDef();
if ($class = getVal('class', $table, '')) {
$class = $this->resolveCallable($class, $values);
} ?>
<tr class="<?php echo $class; ?>">
<?php foreach ($table['fields'] as $name => $column) {
$class = getVal('class', $column, '');
if ((getVal('wpjAdmin', $column) and !isSuperuser()) || ($column['visible'] == 'N')) {
continue;
}
if (is_callable($class)) {
$class = $class($values);
} elseif (method_exists($this, $class)) {
$class = $this->$class($values);
} ?>
<td>
<div class="list_item <?php echo $class; ?>">
<?php echo $this->printListRowItem($column, $values); ?>
</div>
</td>
<?php
} ?>
</tr>
<?php
}
public function getItemClass($class, $values)
{
if (is_callable($class)) {
$class = $class($values);
} elseif ($class && method_exists($this, $class)) {
$class = $this->$class($values);
}
return $class;
}
public function resolveCallable($class, ...$values)
{
if (empty($class)) {
return null;
}
if (is_callable($class)) {
$class = $class(...$values);
} elseif (method_exists($this, $class)) {
$class = $this->$class(...$values);
}
return $class;
}
public function printTreeRow(&$values)
{
$table = &$this->getTableDef();
$class = $this->resolveCallable(getVal('class', $table, ''), $values); ?>
<li class="<?php echo $class; ?>" data-id="<?php echo $this->getListRowValue($values, getVal('id', $table, 'id')); ?>">
<?php foreach ($table['fields'] as $name => $column) {
$class = $this->resolveCallable(getVal('class', $column, ''), $values); ?>
<div class="list_item <?php echo $class; ?>">
<?php echo $this->printListRowItem($column, $values); ?>
</div>
<?php
} ?>
</li>
<?php
}
public function getFieldArrayName($field)
{
$pos = strpos($field, '.');
if ($pos === false) {
return $field;
}
return substr($field, $pos + 1);
}
public function getFiltersData(QueryBuilder $qb, $filters)
{
$filterValues = [];
foreach ($filters as $name => $filter) {
$choiced = false;
if (getVal($name, null, '0') == '0') {
$choiced = true;
}
$values = [
'0' => [
'name' => $filter['title'],
'choiced' => $choiced,
],
];
$from = getVal('from', $filter);
$leftJoin = getVal('leftJoin', $filter);
$nameField = getVal('name', $filter, $filter['field']);
$orderField = getVal('order', $filter, 'name');
$qb->resetQueryPart('select');
$qb->select('DISTINCT '.$filter['field'].' as value', $nameField.' as name')
->leftJoin($leftJoin['fromAlias'], $leftJoin['table'], $leftJoin['alias'], $leftJoin['condition'])
->orderBy($orderField)
->setMaxResults(100);
$SQL = $qb->execute();
while (($row = sqlFetchAssoc($SQL)) !== false) {
$choiced = false;
if (getVal($name, null, '0') == $row['value']) {
$choiced = true;
}
$values[$row['value']]['name'] = $row['name'];
$values[$row['value']]['choiced'] = $choiced;
}
$filterValues[$filter['title']] = $values;
}
return $filterValues;
}
public function printMenuRow($title, $type, $params)
{
?>
<img src="<?php echo $GLOBALS['cfg']['Path']['admin_images']; ?>xp_icon_16x16_arrow1.gif" width="16" height="16" border="0" alt=""/>
<a href="javascript:nw('<?php echo $type; ?>', '0', '<?php echo $params; ?>');"><?php echo $title; ?></a>
<?php
}
public function printAddItem($params)
{
$this->printMenuRow('Přidat položku', $GLOBALS['type'], $params);
}
public function getAddItem()
{
if (!getVal('window')) {
return false;
}
if ($this->showAddItem === false) {
return false;
}
$replace = array_merge(['ID' => $this->getID()], $_GET);
$params = str_replace(array_map(function ($x) {
return '{'.$x.'}';
}, array_keys($replace)), array_values($replace), $this->showAddItem);
$params = preg_replace('/\{[^\{]+\}/i', '', $params);
return ['type' => $GLOBALS['type'], 'params' => $params];
}
/* Renderers */
public function renderCell($values, $column)
{
return $this->getListRowValue($values, $column['field']);
}
public function renderBoolean($values, $column, $tooltip = '')
{
$value = $this->renderCell($values, $column);
if ($value == 'Y' || $value == '1' || $value === true) {
return $this->renderIcon('success', 'Ano', $tooltip);
} else {
return $this->renderIcon('error', 'Ne', $tooltip);
}
}
protected function renderIcon($icon, $text = '', $tooltip = '')
{
switch ($icon) {
case 'warning':
return $this->renderFontIcon('list-warn bi bi-exclamation-triangle', $text, $tooltip);
case 'success':
return $this->renderFontIcon('list-yes bi bi-check-circle', $text, $tooltip);
case 'error':
return $this->renderFontIcon('list-no bi bi-x-circle', $text, $tooltip);
}
}
protected function renderFontIcon($class, $text, $tooltip = '')
{
$tag = HTML::create('span')
->class($class);
if (!empty($tooltip)) {
$tag->attr('title', $tooltip);
}
return $tag->tag('i')->text($text)->end();
}
public function renderIsSet($values, $column)
{
$value = $this->renderCell($values, $column);
if ($value) {
return $this->renderIcon('success', 'Ano');
} else {
return '';
}
}
public function renderFloat($values, $column)
{
$value = $this->renderCell($values, $column);
if ($value === null) {
return '-';
}
return floatval($value);
}
public function renderPrice($values, $column)
{
$value = $this->renderCell($values, $column);
if ($value === null) {
return '-';
}
return $this->renderFormatPrice($values, $column);
}
public function renderFormatPrice($values, $column)
{
$value = $this->renderCell($values, $column);
$params = ['printcurrency' => false];
if (!empty($column['price_params'])) {
$params += $column['price_params'];
}
$currencyContext = ServiceContainer::getService(CurrencyContext::class);
$currency = $currencyContext->getActive();
if (!empty($values['currency'])) {
$currency = $currencyContext->getAll()[$values['currency']];
$params['currency'] = $currency;
}
return [
printPrice($value, $params).' ',
HTML::create('span')->class('currency')->text($currency->getSymbol()),
];
}
public function renderPriceVAT($values, $column)
{
$value = $this->renderCell($values, $column);
$vat = $this->getListRowValue($values, 'vat', getAdminVat()['id']);
$values[$this->getFieldArrayName($column['field'])] = calcPrice($value, getVat($vat), 0);
return $this->renderFormatPrice($values, $column);
}
public function renderPriceFinal($values, $column)
{
$value = $this->renderCell($values, $column);
$vat = $this->getListRowValue($values, 'vat', getAdminVat()['id']);
$discount = $this->getListRowValue($values, 'discount', null);
$values[$this->getFieldArrayName($column['field'])] = calcPrice($value, getVat($vat), $discount);
return $this->renderFormatPrice($values, $column);
}
public function renderPricePreferred($values, $column)
{
switch (\Settings::getDefault()->prod_prefer_price_vat) {
case 'Y':
return $this->renderPriceVAT($values, $column);
case 'F':
return $this->renderPriceFinal($values, $column);
default:
case 'N':
return $this->renderPrice($values, $column);
}
}
public function renderHTML($values, $column)
{
$value = $this->renderCell($values, $column);
if (!$value) {
return '';
}
return HTML::create('span')->attr('class', 'text-dark')->text(strip_tags($value));
}
public function renderDate($values, $column)
{
$value = $this->renderCell($values, $column);
if (!$value || substr($value, 0, 10) == '0000-00-00') {
return '';
}
$date = new \DateTime($value);
$format = \Settings::getDateFormat();
return $date->format($format);
}
public function renderDateTime($values, $column)
{
$value = $this->renderCell($values, $column);
if (!$value || substr($value, 0, 19) == '0000-00-00 00:00:00') {
return '';
}
$date = new \DateTime($value);
$format = \Settings::getDateFormat().' '.\Settings::getTimeFormat();
return $date->format($format);
}
public function renderPosition($values)
{
return [
HTML::create('span')
->class('drag-drop-mover pull-right')
->tag('i')
->class('bi bi-arrows-move handle')
->end(),
HTML::create('input')
->class('sort')
->attr('type', 'hidden')
->attr('data-sort', '')
->attr('name', $values['id'])
->attr('value', $values['position'] ?? ''),
];
}
public function renderPercents($values, $column)
{
$value = $this->getListRowValue($values, $column['field']);
if (is_null($value)) {
return \KupShop\KupShopBundle\Util\HtmlBuilder\HTML::create('span')
->text('-')
->attr('style', 'font-size: 140%');
}
return round($value, 1).' %';
}
public function renderBadge($title, $badgeClass, $icon)
{
if ($icon) {
return HTML::create('span')->class('badge '.$badgeClass)
->tag('span')->class('bi bi-'.$icon)->end()
->attr('title', $title)
->tag('span')->class('tooltip-text m-l-1')->text($title)->end();
} else {
return HTML::create('span')->class('badge '.$badgeClass)
->attr('title', $title)
->text($title);
}
}
public function renderImage($values, $column)
{
$img = getImage($values['id_image'] ?? null, $values['image_2'] ?? null, $values['image_source'] ?? null, $values['image_type'] ?? null);
if (empty($img)) {
$path = '/admin/static/images/no-image.png';
} else {
$path = $this->getUrlFinder()->staticUrl($img['source']);
}
return HTML::create('img')
->class('img img-rounded')
->attr('src', $path);
}
public function exportArray($array, $separator = ', ')
{
return implode($separator, $array);
}
public function getCheckbox($name, $value, $checked = true)
{
return HTML::create('input')
->attr('type', 'checkbox')
->attr('style', 'margin: 0 10px 0 0; float:left;')
->attr($checked ? 'checked' : '', $checked ? 'checked' : '')
->attr('name', 'data['.$name.'][]')
->attr('value', $value);
}
// Label functions
public function labelPricePreferred($column)
{
switch (\Settings::getDefault()->prod_prefer_price_vat) {
case 'Y':
return 'Cena s DPH';
case 'F':
return 'Cena finální';
default:
case 'N':
return 'Cena bez DPH';
}
}
public function getFinalQueryBuilder(array &$vars): QueryBuilder
{
$vars['filtersStorage'] = $this->activateFilters();
$this->getTableDef();
$qb = $this->getQuery();
if (is_array($qb)) {
foreach ($qb as $key => $data) {
if ($key == 'qb') {
$qb = $data;
}
$vars['var'][$key] = $data;
}
}
if (isset($vars['var']['divide'])) {
$this->pageDivide = $vars['var']['divide'];
}
$vars['object'] = $this;
$name = $this->getListName();
$vars['orderParam'] = $this->getOrder($name);
$qb = $this->evaluateColumnClosures($qb);
$qb = $this->applyOrder($qb, $vars);
return $qb;
}
public function activateFilters(): ?array
{
$filtersStorage = null;
if ($this->filterStorageReady()) {
$filtersStorage = $this->getFiltersStorage();
if (!$this->filtersActive()) {
$default = $this->getDefaultFilter();
if (!empty($default['id'])) {
$_GET['adminFilter'] = $default['id'];
}
}
if (!empty($filtersStorage['storage']) && !empty($_GET['adminFilter'])) {
$filterID = $_GET['adminFilter'];
$filter = null;
foreach ($filtersStorage['storage'] as $f) {
if ($f['id'] == $filterID) {
$filter = $f;
break;
}
}
$this->activateFilter($filter);
}
}
return $filtersStorage;
}
/**
* @return string|null
*/
public function getTableName()
{
return $this->tableName;
}
public function setMassEditActive(bool $massEditActive): void
{
$this->massEditActive = $massEditActive;
}
protected function getUrlFinder(): UrlFinder
{
static $urlFinder = null;
if (!$urlFinder) {
$urlFinder = ServiceContainer::getService(UrlFinder::class);
}
return $urlFinder;
}
}