294 lines
11 KiB
PHP
294 lines
11 KiB
PHP
<?php
|
|
|
|
class AdvMenuLink extends ObjectModel {
|
|
|
|
public $id_link;
|
|
public $id_parent;
|
|
public $cta;
|
|
public $title;
|
|
public $url;
|
|
public $classbloc;
|
|
public $external;
|
|
public $position;
|
|
public $tree_categories;
|
|
public $liste_icons_menu;
|
|
|
|
public $has_error = FALSE;
|
|
|
|
public static $definition = array(
|
|
'table' => 'advmenu',
|
|
'primary' => 'id_link',
|
|
'multilang' => TRUE,
|
|
'fields' => array(
|
|
'id_link' => array('type' => self::TYPE_INT, 'validate' => 'isInt'),
|
|
'id_parent' => array('type' => self::TYPE_INT, 'validate' => 'isInt'),
|
|
'tree_categories' => array('type' => self::TYPE_INT, 'validate' => 'isInt'),
|
|
'liste_icons_menu' => array('type' => self::TYPE_STRING, 'validate' => 'isGenericName'),
|
|
'external' => array('type' => self::TYPE_BOOL, 'validate' => 'isBool'),
|
|
'position' => array('type' => self::TYPE_INT, 'validate' => 'isInt'),
|
|
'classbloc' => array('type' => self::TYPE_STRING, 'validate' => 'isGenericName'),
|
|
|
|
// Lang fields
|
|
'url' => array('type' => self::TYPE_STRING, 'lang' => TRUE, 'validate' => 'isUrl', 'required' => FALSE, 'size' => 255),
|
|
'title' => array('type' => self::TYPE_STRING, 'lang' => TRUE, 'validate' => 'isGenericName', 'required' => TRUE, 'size' => 255),
|
|
'cta' => array('type' => self::TYPE_HTML, 'lang' => TRUE, 'validate' => 'isCleanHtml')
|
|
)
|
|
);
|
|
|
|
public function add($null_values = false, $autodate = true)
|
|
{
|
|
$this->position = $this->getHigherPosition($this->id_parent)+1;
|
|
$result = parent::add($null_values, $autodate);
|
|
|
|
//Add and remove shop association
|
|
if($result && Shop::isFeatureActive()) {
|
|
//Delete record if shop has been removed from the list
|
|
$result &= Db::getInstance()->delete($this->def['table'].'_shop', '`'.$this->def['primary'].'` ='.(int)$this->id.' AND id_shop NOT IN ('.implode(', ', $this->id_shop_list).')');
|
|
|
|
// Insert new record if shop has been added in the list
|
|
$insert='';
|
|
foreach ($this->id_shop_list as $id_shop) {
|
|
if($insert != '')
|
|
$insert .= ', ';
|
|
$insert .= '('.(int)$this->id.' , '.$id_shop.') ';
|
|
}
|
|
$result &= Db::getInstance()->execute('
|
|
INSERT IGNORE INTO `'._DB_PREFIX_.$this->def['table'].'_shop` (`'.$this->def['primary'].'`, `id_shop`)
|
|
VALUES '.$insert
|
|
);
|
|
}
|
|
|
|
Hook::exec('actionSaveMenu');
|
|
return $result;
|
|
}
|
|
|
|
public function update($null_values = FALSE)
|
|
{
|
|
// check if the object has a different parent
|
|
$old_id_parent = -1;
|
|
$old_object = new AdvMenuLink((int)$this->id);
|
|
if (Validate::isLoadedObject($old_object)) {
|
|
$old_id_parent = $old_object->id_parent;
|
|
if ($old_id_parent != $this->id_parent) {
|
|
$this->position = $this->getHigherPosition($this->id_parent)+1;
|
|
}
|
|
}
|
|
|
|
// update the object
|
|
$result = parent::update($null_values);
|
|
|
|
//Add and remove shop association
|
|
if($result && Shop::isFeatureActive()) {
|
|
//Delete record if shop has been removed from the list
|
|
$result &= Db::getInstance()->delete($this->def['table'].'_shop', '`'.$this->def['primary'].'` ='.(int)$this->id.' AND id_shop NOT IN ('.implode(', ', $this->id_shop_list).')');
|
|
|
|
// Insert new record if shop has been added in the list
|
|
$insert='';
|
|
foreach ($this->id_shop_list as $id_shop) {
|
|
if($insert != '')
|
|
$insert .= ', ';
|
|
$insert .= '('.(int)$this->id.' , '.$id_shop.') ';
|
|
}
|
|
$result &= Db::getInstance()->execute('INSERT IGNORE INTO `'._DB_PREFIX_.$this->def['table'].'_shop` (`'.$this->def['primary'].'`, `id_shop`) VALUES '.$insert);
|
|
}
|
|
|
|
// update links position of previous parent and the new one
|
|
if ($result && $old_id_parent != -1) {
|
|
$this->refreshPositions($old_id_parent);
|
|
$this->refreshPositions();
|
|
}
|
|
|
|
Hook::exec('actionSaveMenu');
|
|
return $result;
|
|
}
|
|
|
|
public function delete()
|
|
{
|
|
$this->has_error = FALSE;
|
|
$nb_sublinks = $this->getNbSubLinks($this->id);
|
|
if ($nb_sublinks>0) {
|
|
$this->has_error = TRUE;
|
|
return FALSE;
|
|
}
|
|
|
|
if (parent::delete()) {
|
|
$this->refreshPositions();
|
|
return true;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
public function getNbSubLinks($id_link)
|
|
{
|
|
return Db::getInstance()->getValue(
|
|
'SELECT COUNT(*) FROM `'._DB_PREFIX_.'advmenu` WHERE `id_parent` = '.(int)$id_link
|
|
);
|
|
}
|
|
|
|
public function hasError()
|
|
{
|
|
return $this->has_error;
|
|
}
|
|
|
|
public static function getPath($id_parent, $id_lang)
|
|
{
|
|
$links = [];
|
|
while ($id_parent) {
|
|
$obj = new AdvMenuLink((int)$id_parent, (int)$id_lang);
|
|
$links[] = ['id_link' => $obj->id, 'title' => $obj->title ];
|
|
$id_parent = $obj->id_parent;
|
|
}
|
|
return array_reverse($links);
|
|
}
|
|
public static function getCategoryAssociates($id_link) {
|
|
$cat = Db::getInstance()->executeS('
|
|
SELECT adv.`tree_categories`
|
|
FROM `'._DB_PREFIX_.'advmenu` adv
|
|
WHERE `id_link` = ' . (int)$id_link . '
|
|
ORDER BY `position` ASC
|
|
');
|
|
return $cat;
|
|
}
|
|
public static function getMenu()
|
|
{
|
|
$context = Context::getContext();
|
|
$menuLinks = self::getLinks(0, $context);
|
|
|
|
foreach($menuLinks as $i => $link) {
|
|
$menuLinks[$i]['children'] = self::getLinks($link['id_link'], $context);
|
|
$menuLinks[$i]['nbChildren'] = count($menuLinks[$i]['children']);
|
|
|
|
foreach($menuLinks[$i]['children'] as $y => $children)
|
|
{
|
|
$menuLinks[$i]['children'][$y]['children'] = self::getLinks($children['id_link'], $context);
|
|
}
|
|
}
|
|
|
|
return $menuLinks;
|
|
}
|
|
|
|
public static function getLinks($id_parent, $context)
|
|
{
|
|
$links = Db::getInstance()->executeS('
|
|
SELECT adv.`id_link`, `title`, `url`, `classbloc`, `cta`, `external`, `tree_categories`, `liste_icons_menu`
|
|
FROM `'._DB_PREFIX_.'advmenu` adv
|
|
JOIN `'._DB_PREFIX_.'advmenu_lang` advl ON adv.`id_link` = advl.`id_link` AND id_lang = '. (int)($context->cookie->id_lang) . '
|
|
WHERE `id_parent` = ' . (int)$id_parent . '
|
|
ORDER BY `position` ASC
|
|
');
|
|
|
|
return $links;
|
|
}
|
|
|
|
public static function getLinksTree(&$links, $id_parent, $id_lang, $id_link_to_exclude=-1, $level=-1)
|
|
{
|
|
$level++;
|
|
|
|
$sql = '
|
|
SELECT adv.`id_link`, `title`, `id_parent`
|
|
FROM `'._DB_PREFIX_.'advmenu` adv
|
|
JOIN `'._DB_PREFIX_.'advmenu_lang` advl ON adv.`id_link` = advl.`id_link` AND id_lang = '. (int)($id_lang) . '
|
|
WHERE `id_parent` = ' . (int)$id_parent;
|
|
if ($id_link_to_exclude!=-1) {
|
|
$sql .= ' AND adv.`id_link` <> '.(int)$id_link_to_exclude;
|
|
|
|
}
|
|
$sql .= ' ORDER BY `position` ASC';
|
|
|
|
$rows = Db::getInstance()->executeS($sql);
|
|
foreach($rows as &$row) {
|
|
$row['level'] = $level;
|
|
$links[] = $row;
|
|
|
|
if ($row['id_link']!=$id_link_to_exclude) {
|
|
self::getLinksTree($links, $row['id_link'], $id_lang, $id_link_to_exclude, $level);
|
|
}
|
|
}
|
|
}
|
|
|
|
public function cleanPositions()
|
|
{
|
|
return Db::getInstance()->execute('UPDATE `'._DB_PREFIX_.'advmenu`
|
|
SET `position`= `position` - 1
|
|
WHERE `id_link` = '.(int)$this->id_link.'
|
|
AND `position` > '.(int)$this->position);
|
|
}
|
|
|
|
public function updatePosition($way, $position)
|
|
{
|
|
$sql = 'SELECT `position`, `id_link`
|
|
FROM `'._DB_PREFIX_.'advmenu`
|
|
WHERE `id_parent` = '.(int)$this->id_parent.'
|
|
ORDER BY `position` ASC';
|
|
if (!$res = Db::getInstance()->executeS($sql))
|
|
return false;
|
|
|
|
foreach ($res as $row)
|
|
if ((int)$row['id_link'] == (int)$this->id_link)
|
|
$moved_row = $row;
|
|
|
|
if (!isset($moved_row) || !isset($position))
|
|
return false;
|
|
|
|
// < and > statements rather than BETWEEN operator
|
|
// since BETWEEN is treated differently according to databases
|
|
$res = Db::getInstance()->execute('
|
|
UPDATE `'._DB_PREFIX_.'advmenu`
|
|
SET `position`= `position` '.($way ? '- 1' : '+ 1').'
|
|
WHERE `id_parent` = '.(int)$this->id_parent.'
|
|
AND `position`
|
|
'.($way
|
|
? '> '.(int)$moved_row['position'].' AND `position` <= '.(int)$position
|
|
: '< '.(int)$moved_row['position'].' AND `position` >= '.(int)$position)
|
|
)
|
|
&& Db::getInstance()->execute('
|
|
UPDATE `'._DB_PREFIX_.'advmenu`
|
|
SET `position` = '.(int)$position.'
|
|
WHERE `id_link`='.(int)$moved_row['id_link']
|
|
);
|
|
$this->refreshPositions();
|
|
|
|
Hook::exec('actionSaveMenu');
|
|
|
|
return $res;
|
|
}
|
|
|
|
public function refreshPositions($id_parent=-1)
|
|
{
|
|
$sql = 'SELECT `id_link`
|
|
FROM `'._DB_PREFIX_.'advmenu`
|
|
WHERE `id_parent` = '.($id_parent>-1 ? $id_parent : (int)$this->id_parent).'
|
|
ORDER BY `position` ASC';
|
|
if (!$blocks = Db::getInstance()->executeS($sql))
|
|
return false;
|
|
|
|
$pos=0;
|
|
foreach ($blocks as $block) {
|
|
Db::getInstance()->execute('
|
|
UPDATE `'._DB_PREFIX_.'advmenu`
|
|
SET `position` = '.(int)$pos.'
|
|
WHERE `id_link`='.(int)$block['id_link']);
|
|
$pos++;
|
|
}
|
|
}
|
|
|
|
public function getHigherPosition($id_parent)
|
|
{
|
|
$sql = 'SELECT MAX(`position`)
|
|
FROM `'._DB_PREFIX_.'advmenu`
|
|
WHERE `id_parent` = '.(int)$id_parent;
|
|
$position = DB::getInstance()->getValue($sql);
|
|
return (is_numeric($position)) ? $position : -1;
|
|
}
|
|
|
|
public static function refreshPositionsAll()
|
|
{
|
|
$obj = new AdvMenuLink(null);
|
|
|
|
$sql = 'SELECT DISTINCT id_parent FROM `'._DB_PREFIX_.'advmenu`';
|
|
$rows = Db::getInstance()->executeS($sql);
|
|
foreach ($rows as $row) {
|
|
$obj->refreshPositions($row['id_parent']);
|
|
}
|
|
}
|
|
} |