pse and combi loops

This commit is contained in:
Etienne Roudeix
2013-08-21 12:50:49 +02:00
parent 3d0c7d6773
commit 9dbd8a283b
8 changed files with 324 additions and 336 deletions

View File

@@ -9,6 +9,7 @@
<loop class="Thelia\Core\Template\Loop\Address" name="address"/>
<loop class="Thelia\Core\Template\Loop\Attribute" name="attribute"/>
<loop class="Thelia\Core\Template\Loop\AttributeAvailability" name="attribute_availability"/>
<loop class="Thelia\Core\Template\Loop\AttributeCombination" name="attribute_combination"/>
<loop class="Thelia\Core\Template\Loop\Auth" name="auth"/>
<loop class="Thelia\Core\Template\Loop\Category" name="category"/>
<loop class="Thelia\Core\Template\Loop\Content" name="content"/>
@@ -22,7 +23,7 @@
<loop class="Thelia\Core\Template\Loop\OrderStatus" name="order-status"/>
<loop class="Thelia\Core\Template\Loop\CategoryPath" name="category-path"/>
<loop class="Thelia\Core\Template\Loop\Product" name="product"/>
<loop class="Thelia\Core\Template\Loop\ProductSaleElement" name="product_sale_element"/>
<loop class="Thelia\Core\Template\Loop\ProductSaleElements" name="product_sale_elements"/>
<loop class="Thelia\Core\Template\Loop\Feed" name="feed"/>
<loop class="Thelia\Core\Template\Loop\Title" name="title"/>
<loop class="Thelia\Core\Template\Loop\Lang" name="lang"/>

View File

@@ -0,0 +1,125 @@
<?php
/*************************************************************************************/
/* */
/* Thelia */
/* */
/* Copyright (c) OpenStudio */
/* email : info@thelia.net */
/* web : http://www.thelia.net */
/* */
/* This program is free software; you can redistribute it and/or modify */
/* it under the terms of the GNU General Public License as published by */
/* the Free Software Foundation; either version 3 of the License */
/* */
/* This program is distributed in the hope that it will be useful, */
/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
/* GNU General Public License for more details. */
/* */
/* You should have received a copy of the GNU General Public License */
/* along with this program. If not, see <http://www.gnu.org/licenses/>. */
/* */
/*************************************************************************************/
namespace Thelia\Core\Template\Loop;
use Propel\Runtime\ActiveQuery\Criteria;
use Propel\Runtime\ActiveQuery\Join;
use Thelia\Core\Template\Element\BaseLoop;
use Thelia\Core\Template\Element\LoopResult;
use Thelia\Core\Template\Element\LoopResultRow;
use Thelia\Core\Template\Loop\Argument\ArgumentCollection;
use Thelia\Core\Template\Loop\Argument\Argument;
use Thelia\Log\Tlog;
use Thelia\Model\Base\AttributeCombinationQuery;
use Thelia\Model\ConfigQuery;
use Thelia\Type\TypeCollection;
use Thelia\Type;
/**
*
* Attribute Combination loop
*
* Class AttributeCombination
* @package Thelia\Core\Template\Loop
* @author Etienne Roudeix <eroudeix@openstudio.fr>
*/
class AttributeCombination extends BaseLoop
{
/**
* @return ArgumentCollection
*/
protected function getArgDefinitions()
{
return new ArgumentCollection(
Argument::createIntTypeArgument('product_sale_element', null, true),
new Argument(
'order',
new TypeCollection(
new Type\EnumListType(array('attribute_availability', 'attribute_availability_reverse', 'attribute', 'attribute_reverse'))
),
'attribute'
)
);
}
/**
* @param $pagination
*
* @return \Thelia\Core\Template\Element\LoopResult
*/
public function exec(&$pagination)
{
$search = AttributeCombinationQuery::create();
$productSaleElement = $this->getProduct_sale_element();
$search->filterByProductSaleElementsId($productSaleElement, Criteria::EQUAL);
$orders = $this->getOrder();
foreach($orders as $order) {
switch ($order) {
case "attribute_availability":
//$search->addAscendingOrderByColumn(\Thelia\Model\Map\AttributeI18nTableMap::TITLE);
break;
case "attribute_availability_reverse":
//$search->addDescendingOrderByColumn(\Thelia\Model\Map\AttributeI18nTableMap::TITLE);
break;
case "attribute":
//$search->orderByPosition(Criteria::ASC);
break;
case "attribute_reverse":
//$search->orderByPosition(Criteria::DESC);
break;
}
}
$attributeCombinations = $this->search($search, $pagination);
$loopResult = new LoopResult();
foreach ($attributeCombinations as $attributeCombination) {
$loopResultRow = new LoopResultRow();
$attribute = $attributeCombination->getAttribute();
$attributeAvailability = $attributeCombination->getAttributeAv();
$loopResultRow
->set("ATTRIBUTE_TITLE", $attribute->getTitle())
->set("ATTRIBUTE_CHAPO", $attribute->getChapo())
->set("ATTRIBUTE_DESCRIPTION", $attribute->getDescription())
->set("ATTRIBUTE_POSTSCRIPTUM", $attribute->getPostscriptum())
->set("ATTRIBUTE_AVAILABILITY_TITLE", $attributeAvailability->getTitle())
->set("ATTRIBUTE_AVAILABILITY_CHAPO", $attributeAvailability->getChapo())
->set("ATTRIBUTE_AVAILABILITY_DESCRIPTION", $attributeAvailability->getDescription())
->set("ATTRIBUTE_AVAILABILITY_POSTSCRIPTUM", $attributeAvailability->getPostscriptum());
$loopResult->addRow($loopResultRow);
}
return $loopResult;
}
}

View File

@@ -35,7 +35,6 @@ use Thelia\Log\Tlog;
use Thelia\Model\Base\FeatureProductQuery;
use Thelia\Model\ConfigQuery;
use Thelia\Model\FeatureAvQuery;
use Thelia\Type\TypeCollection;
use Thelia\Type;
@@ -58,8 +57,8 @@ class FeatureValue extends BaseLoop
return new ArgumentCollection(
Argument::createIntTypeArgument('feature', null, true),
Argument::createIntTypeArgument('product', null, true),
Argument::createIntListTypeArgument('feature_available'),
Argument::createBooleanTypeArgument('exclude_feature_available', 0),
Argument::createIntListTypeArgument('feature_availability'),
Argument::createBooleanTypeArgument('exclude_feature_availability', 0),
Argument::createBooleanTypeArgument('exclude_default_values', 0),
new Argument(
'order',
@@ -88,14 +87,14 @@ class FeatureValue extends BaseLoop
$search->filterByProductId($product, Criteria::EQUAL);
$featureAvailable = $this->getFeature_available();
$featureAvailability = $this->getFeature_availability();
if (null !== $featureAvailable) {
$search->filterByFeatureAvId($featureAvailable, Criteria::IN);
if (null !== $featureAvailability) {
$search->filterByFeatureAvId($featureAvailability, Criteria::IN);
}
$excludeFeatureAvailable = $this->getExclude_feature_available();
if($excludeFeatureAvailable == true) {
$excludeFeatureAvailability = $this->getExclude_feature_availability();
if($excludeFeatureAvailability == true) {
$search->filterByFeatureAvId(null, Criteria::NULL);
}

View File

@@ -93,7 +93,7 @@ class Product extends BaseLoop
Argument::createIntListTypeArgument('exclude'),
Argument::createIntListTypeArgument('exclude_category'),
new Argument(
'feature_available',
'feature_availability',
new TypeCollection(
new Type\IntToCombinedIntsListType()
)
@@ -317,7 +317,7 @@ class Product extends BaseLoop
/*
* we need to test all promo field from our previous conditions. Indeed ie:
* product P0, attributes color : red
* P0red is in promo and is the only attribute combinaton available.
* P0red is in promo and is the only attribute combinaton availability.
* so the product might be consider as in promo (in outputs and ordering)
* We got the following loop to display in promo AND new product but we don't care it's the same attribute which is new and in promo :
* {loop type="product" promo="1" new="1" attribute_non_strict_match="promo,new"} {/loop}
@@ -397,10 +397,10 @@ class Product extends BaseLoop
);
}
$feature_available = $this->getFeature_available();
$feature_availability = $this->getFeature_availability();
if(null !== $feature_available) {
foreach($feature_available as $feature => $feature_choice) {
if(null !== $feature_availability) {
foreach($feature_availability as $feature => $feature_choice) {
foreach($feature_choice['values'] as $feature_av) {
$featureAlias = 'fa_' . $feature;
if($feature_av != '*')
@@ -520,8 +520,8 @@ class Product extends BaseLoop
->set("DESCRIPTION", $product->getDescription())
->set("POSTSCRIPTUM", $product->getPostscriptum())
->set("BEST_PRICE", $product->getVirtualColumn('real_lowest_price'))
->set("PROMO", $product->getVirtualColumn('main_product_is_promo'))
->set("NEW", $product->getVirtualColumn('main_product_is_new'))
->set("IS_PROMO", $product->getVirtualColumn('main_product_is_promo'))
->set("IS_NEW", $product->getVirtualColumn('main_product_is_new'))
->set("POSITION", $product->getPosition())
;

View File

@@ -33,29 +33,22 @@ use Thelia\Core\Template\Loop\Argument\ArgumentCollection;
use Thelia\Core\Template\Loop\Argument\Argument;
use Thelia\Log\Tlog;
use Thelia\Model\Base\FeatureProductQuery;
use Thelia\Model\CategoryQuery;
use Thelia\Model\FeatureAvQuery;
use Thelia\Model\FeatureQuery;
use Thelia\Model\Map\FeatureProductTableMap;
use Thelia\Model\Map\ProductTableMap;
use Thelia\Model\ProductCategoryQuery;
use Thelia\Model\ProductQuery;
use Thelia\Model\Base\ProductSaleElementsQuery;
use Thelia\Model\ConfigQuery;
use Thelia\Type\TypeCollection;
use Thelia\Type;
use Thelia\Type\BooleanOrBothType;
/**
*
* Product loop
* Product Sale Elements loop
*
* @todo : manage currency
*
* Class Product
* Class ProductSaleElements
* @package Thelia\Core\Template\Loop
* @author Etienne Roudeix <eroudeix@openstudio.fr>
*/
class Product extends BaseLoop
class ProductSaleElements extends BaseLoop
{
/**
* @return ArgumentCollection
@@ -63,45 +56,20 @@ class Product extends BaseLoop
protected function getArgDefinitions()
{
return new ArgumentCollection(
Argument::createIntListTypeArgument('id'),
Argument::createIntTypeArgument('devise'),
Argument::createIntTypeArgument('product', null, true),
new Argument(
'ref',
new TypeCollection(
new Type\AlphaNumStringListType()
)
),
Argument::createIntListTypeArgument('category'),
//Argument::createBooleanTypeArgument('new'),
//Argument::createBooleanTypeArgument('promo'),
//Argument::createFloatTypeArgument('min_price'),
//Argument::createFloatTypeArgument('max_price'),
//Argument::createIntTypeArgument('min_stock'),
//Argument::createFloatTypeArgument('min_weight'),
//Argument::createFloatTypeArgument('max_weight'),
Argument::createBooleanTypeArgument('current'),
Argument::createBooleanTypeArgument('current_category'),
Argument::createIntTypeArgument('depth', 1),
Argument::createBooleanOrBothTypeArgument('visible', 1),
new Argument(
'order',
new TypeCollection(
new Type\EnumListType(array('alpha', 'alpha_reverse', /*'min_price', 'max_price',*/ 'manual', 'manual_reverse', 'ref', /*'promo', 'new',*/ 'random', 'given_id'))
),
'alpha'
),
Argument::createIntListTypeArgument('exclude'),
Argument::createIntListTypeArgument('exclude_category'),
new Argument(
'feature_available',
'attribute_availability',
new TypeCollection(
new Type\IntToCombinedIntsListType()
)
),
new Argument(
'feature_values',
'order',
new TypeCollection(
new Type\IntToCombinedStringsListType()
)
new Type\EnumListType(array('alpha', 'alpha_reverse', 'attribute', 'attribute_reverse'))
),
'attribute'
)
);
}
@@ -110,311 +78,73 @@ class Product extends BaseLoop
* @param $pagination
*
* @return \Thelia\Core\Template\Element\LoopResult
* @throws \InvalidArgumentException
*/
public function exec(&$pagination)
{
$search = ProductQuery::create();
$search = ProductSaleElementsQuery::create();
//$search->withColumn('CASE WHEN ' . ProductTableMap::PROMO . '=1 THEN ' . ProductTableMap::PRICE2 . ' ELSE ' . ProductTableMap::PRICE . ' END', 'real_price');
$product = $this->getProduct();
$id = $this->getId();
if (!is_null($id)) {
$search->filterById($id, Criteria::IN);
}
$ref = $this->getRef();
if (!is_null($ref)) {
$search->filterByRef($ref, Criteria::IN);
}
$category = $this->getCategory();
if (!is_null($category)) {
$categories = CategoryQuery::create()->filterById($category, Criteria::IN)->find();
$depth = $this->getDepth();
if(null !== $depth) {
foreach(CategoryQuery::findAllChild($category, $depth) as $subCategory) {
$categories->prepend($subCategory);
}
}
$search->filterByCategory(
$categories,
Criteria::IN
);
}
/*$new = $this->getNew();
if ($new === true) {
$search->filterByNewness(1, Criteria::EQUAL);
} else if($new === false) {
$search->filterByNewness(0, Criteria::EQUAL);
}
$promo = $this->getPromo();
if ($promo === true) {
$search->filterByPromo(1, Criteria::EQUAL);
} else if($promo === false) {
$search->filterByNewness(0, Criteria::EQUAL);
}
$min_stock = $this->getMin_stock();
if (null != $min_stock) {
$search->filterByQuantity($min_stock, Criteria::GREATER_EQUAL);
}
$min_price = $this->getMin_price();*/
//if(null !== $min_price) {
/**
* Following should work but does not :
*
* $search->filterBy('real_price', $max_price, Criteria::GREATER_EQUAL);
*/
/*$search->condition('in_promo', ProductTableMap::PROMO . Criteria::EQUAL . '1')
->condition('not_in_promo', ProductTableMap::PROMO . Criteria::NOT_EQUAL . '1')
->condition('min_price2', ProductTableMap::PRICE2 . Criteria::GREATER_EQUAL . '?', $min_price)
->condition('min_price', ProductTableMap::PRICE . Criteria::GREATER_EQUAL . '?', $min_price)
->combine(array('in_promo', 'min_price2'), Criteria::LOGICAL_AND, 'in_promo_min_price')
->combine(array('not_in_promo', 'min_price'), Criteria::LOGICAL_AND, 'not_in_promo_min_price')
->where(array('not_in_promo_min_price', 'in_promo_min_price'), Criteria::LOGICAL_OR);
}
$max_price = $this->getMax_price();*/
//if(null !== $max_price) {
/**
* Following should work but does not :
*
* $search->filterBy('real_price', $max_price, Criteria::LESS_EQUAL);
*/
/*$search->condition('in_promo', ProductTableMap::PROMO . Criteria::EQUAL . '1')
->condition('not_in_promo', ProductTableMap::PROMO . Criteria::NOT_EQUAL . '1')
->condition('max_price2', ProductTableMap::PRICE2 . Criteria::LESS_EQUAL . '?', $max_price)
->condition('max_price', ProductTableMap::PRICE . Criteria::LESS_EQUAL . '?', $max_price)
->combine(array('in_promo', 'max_price2'), Criteria::LOGICAL_AND, 'in_promo_max_price')
->combine(array('not_in_promo', 'max_price'), Criteria::LOGICAL_AND, 'not_in_promo_max_price')
->where(array('not_in_promo_max_price', 'in_promo_max_price'), Criteria::LOGICAL_OR);
}*/
/*$min_weight = $this->getMin_weight();
if(null !== $min_weight) {
$search->filterByWeight($min_weight, Criteria::GREATER_EQUAL);
}
$max_weight = $this->getMax_weight();
if(null !== $max_weight) {
$search->filterByWeight($max_weight, Criteria::LESS_EQUAL);
}*/
$current = $this->getCurrent();
if ($current === true) {
$search->filterById($this->request->get("product_id"));
} elseif($current === false) {
$search->filterById($this->request->get("product_id"), Criteria::NOT_IN);
}
$current_category = $this->getCurrent_category();
if ($current_category === true) {
$search->filterByCategory(
CategoryQuery::create()->filterByProduct(
ProductCategoryQuery::create()->filterByProductId(
$this->request->get("product_id"),
Criteria::EQUAL
)->find(),
Criteria::IN
)->find(),
Criteria::IN
);
} elseif($current_category === false) {
$search->filterByCategory(
CategoryQuery::create()->filterByProduct(
ProductCategoryQuery::create()->filterByProductId(
$this->request->get("product_id"),
Criteria::EQUAL
)->find(),
Criteria::IN
)->find(),
Criteria::NOT_IN
);
}
$visible = $this->getVisible();
if ($visible != BooleanOrBothType::ANY) $search->filterByVisible($visible ? 1 : 0);
$search->filterByProductId($product, Criteria::EQUAL);
$orders = $this->getOrder();
foreach($orders as $order) {
switch ($order) {
case "alpha":
$search->addAscendingOrderByColumn(\Thelia\Model\Map\ProductI18nTableMap::TITLE);
//$search->addAscendingOrderByColumn(\Thelia\Model\Map\AttributeI18nTableMap::TITLE);
break;
case "alpha_reverse":
$search->addDescendingOrderByColumn(\Thelia\Model\Map\ProductI18nTableMap::TITLE);
//$search->addDescendingOrderByColumn(\Thelia\Model\Map\AttributeI18nTableMap::TITLE);
break;
/*case "min_price":
$search->orderBy('real_price', Criteria::ASC);
case "attribute":
//$search->orderByPosition(Criteria::ASC);
break;
case "max_price":
$search->orderBy('real_price', Criteria::DESC);
break;*/
case "manual":
if(null === $category || count($category) != 1)
throw new \InvalidArgumentException('Manual order cannot be set without single category argument');
$search->orderByPosition(Criteria::ASC);
case "attribute_reverse":
//$search->orderByPosition(Criteria::DESC);
break;
case "manual_reverse":
if(null === $category || count($category) != 1)
throw new \InvalidArgumentException('Manual order cannot be set without single category argument');
$search->orderByPosition(Criteria::DESC);
break;
case "ref":
$search->orderByRef(Criteria::ASC);
break;
/*case "promo":
$search->orderByPromo(Criteria::DESC);
break;
case "new":
$search->orderByNewness(Criteria::DESC);
break;*/
case "given_id":
if(null === $id)
throw new \InvalidArgumentException('Given_id order cannot be set without `id` argument');
foreach($id as $singleId) {
$givenIdMatched = 'given_id_matched_' . $singleId;
$search->withColumn(ProductTableMap::ID . "='$singleId'", $givenIdMatched);
$search->orderBy($givenIdMatched, Criteria::DESC);
}
break;
case "random":
$search->clearOrderByColumns();
$search->addAscendingOrderByColumn('RAND()');
break(2);
}
}
$exclude = $this->getExclude();
$devise = $this->getDevise();
if (!is_null($exclude)) {
$search->filterById($exclude, Criteria::NOT_IN);
}
$search->joinProductPrice('price', Criteria::INNER_JOIN);
//->addJoinCondition('price', '');
$exclude_category = $this->getExclude_category();
$search->withColumn('`price`.CURRENCY_ID', 'price_CURRENCY_ID')
->withColumn('`price`.PRICE', 'price_PRICE')
->withColumn('`price`.PROMO_PRICE', 'price_PROMO_PRICE');
if (!is_null($exclude_category)) {
$search->filterByCategory(
CategoryQuery::create()->filterById($exclude_category, Criteria::IN)->find(),
Criteria::NOT_IN
);
}
$feature_available = $this->getFeature_available();
if(null !== $feature_available) {
foreach($feature_available as $feature => $feature_choice) {
foreach($feature_choice['values'] as $feature_av) {
$featureAlias = 'fa_' . $feature;
if($feature_av != '*')
$featureAlias .= '_' . $feature_av;
$search->joinFeatureProduct($featureAlias, Criteria::LEFT_JOIN)
->addJoinCondition($featureAlias, "`$featureAlias`.FEATURE_ID = ?", $feature, null, \PDO::PARAM_INT);
if($feature_av != '*')
$search->addJoinCondition($featureAlias, "`$featureAlias`.FEATURE_AV_ID = ?", $feature_av, null, \PDO::PARAM_INT);
}
/* format for mysql */
$sqlWhereString = $feature_choice['expression'];
if($sqlWhereString == '*') {
$sqlWhereString = 'NOT ISNULL(`fa_' . $feature . '`.ID)';
} else {
$sqlWhereString = preg_replace('#([0-9]+)#', 'NOT ISNULL(`fa_' . $feature . '_' . '\1`.ID)', $sqlWhereString);
$sqlWhereString = str_replace('&', ' AND ', $sqlWhereString);
$sqlWhereString = str_replace('|', ' OR ', $sqlWhereString);
}
$search->where("(" . $sqlWhereString . ")");
}
}
$feature_values = $this->getFeature_values();
if(null !== $feature_values) {
foreach($feature_values as $feature => $feature_choice) {
foreach($feature_choice['values'] as $feature_value) {
$featureAlias = 'fv_' . $feature;
if($feature_value != '*')
$featureAlias .= '_' . $feature_value;
$search->joinFeatureProduct($featureAlias, Criteria::LEFT_JOIN)
->addJoinCondition($featureAlias, "`$featureAlias`.FEATURE_ID = ?", $feature, null, \PDO::PARAM_INT);
if($feature_value != '*')
$search->addJoinCondition($featureAlias, "`$featureAlias`.BY_DEFAULT = ?", $feature_value, null, \PDO::PARAM_STR);
}
/* format for mysql */
$sqlWhereString = $feature_choice['expression'];
if($sqlWhereString == '*') {
$sqlWhereString = 'NOT ISNULL(`fv_' . $feature . '`.ID)';
} else {
$sqlWhereString = preg_replace('#([a-zA-Z0-9_\-]+)#', 'NOT ISNULL(`fv_' . $feature . '_' . '\1`.ID)', $sqlWhereString);
$sqlWhereString = str_replace('&', ' AND ', $sqlWhereString);
$sqlWhereString = str_replace('|', ' OR ', $sqlWhereString);
}
$search->where("(" . $sqlWhereString . ")");
}
}
/**
* Criteria::INNER_JOIN in second parameter for joinWithI18n exclude query without translation.
*
* @todo : verify here if we want results for row without translations.
*/
$search->joinWithI18n(
$this->request->getSession()->getLocale(),
(ConfigQuery::read("default_lang_without_translation", 1)) ? Criteria::LEFT_JOIN : Criteria::INNER_JOIN
);
$search->groupBy(ProductTableMap::ID);
$products = $this->search($search, $pagination);
$PSEValues = $this->search($search, $pagination);
$loopResult = new LoopResult();
foreach ($products as $product) {
foreach ($PSEValues as $PSEValue) {
$loopResultRow = new LoopResultRow();
$loopResultRow->set("ID", $product->getId())
->set("REF",$product->getRef())
->set("TITLE",$product->getTitle())
->set("CHAPO", $product->getChapo())
->set("DESCRIPTION", $product->getDescription())
->set("POSTSCRIPTUM", $product->getPostscriptum())
//->set("PRICE", $product->getPrice())
//->set("PROMO_PRICE", $product->getPrice2())
//->set("WEIGHT", $product->getWeight())
//->set("PROMO", $product->getPromo())
//->set("NEW", $product->getNewness())
->set("POSITION", $product->getPosition())
;
$loopResultRow->set("ID", $PSEValue->getId())
->set("QUANTITY", $PSEValue->getQuantity())
->set("IS_PROMO", $PSEValue->getPromo() === 1 ? 1 : 0)
->set("IS_NEW", $PSEValue->getNewness() === 1 ? 1 : 0)
->set("WEIGHT", $PSEValue->getWeight())
->set("CURRENCY", $PSEValue->getVirtualColumn('price_CURRENCY_ID'))
->set("PRICE", $PSEValue->getVirtualColumn('price_PRICE'))
->set("PROMO_PRICE", $PSEValue->getVirtualColumn('price_PROMO_PRICE'));
//$price = $PSEValue->getAttributeAv();
/*
$attributeAvailability = $PSEValue->getAttributeAv();
$loopResultRow->set("TITLE", ($attributeAvailability === null ? '' : $attributeAvailability->getTitle()));
$loopResultRow->set("CHAPO", ($attributeAvailability === null ? '' : $attributeAvailability->getChapo()));
$loopResultRow->set("DESCRIPTION", ($attributeAvailability === null ? '' : $attributeAvailability->getDescription()));
$loopResultRow->set("POSTSCRIPTUM", ($attributeAvailability === null ? '' : $attributeAvailability->getPostscriptum()));*/
$loopResult->addRow($loopResultRow);
}
return $loopResult;
}
}
}

View File

@@ -0,0 +1,51 @@
<?php
/*************************************************************************************/
/* */
/* Thelia */
/* */
/* Copyright (c) OpenStudio */
/* email : info@thelia.net */
/* web : http://www.thelia.net */
/* */
/* This program is free software; you can redistribute it and/or modify */
/* it under the terms of the GNU General Public License as published by */
/* the Free Software Foundation; either version 3 of the License */
/* */
/* This program is distributed in the hope that it will be useful, */
/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
/* GNU General Public License for more details. */
/* */
/* You should have received a copy of the GNU General Public License */
/* along with this program. If not, see <http://www.gnu.org/licenses/>. */
/* */
/*************************************************************************************/
namespace Thelia\Tests\Core\Template\Loop;
use Thelia\Tests\Core\Template\Element\BaseLoopTestor;
use Thelia\Core\Template\Loop\AttributeCombination;
/**
*
* @author Etienne Roudeix <eroudeix@openstudio.fr>
*
*/
class AttributeCombinationTest extends BaseLoopTestor
{
public function getTestedClassName()
{
return 'Thelia\Core\Template\Loop\AttributeCombination';
}
public function getTestedInstance()
{
return new AttributeCombination($this->request, $this->dispatcher, $this->securityContext);
}
public function getMandatoryArguments()
{
return array('product_sale_element' => 1);
}
}

View File

@@ -0,0 +1,51 @@
<?php
/*************************************************************************************/
/* */
/* Thelia */
/* */
/* Copyright (c) OpenStudio */
/* email : info@thelia.net */
/* web : http://www.thelia.net */
/* */
/* This program is free software; you can redistribute it and/or modify */
/* it under the terms of the GNU General Public License as published by */
/* the Free Software Foundation; either version 3 of the License */
/* */
/* This program is distributed in the hope that it will be useful, */
/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
/* GNU General Public License for more details. */
/* */
/* You should have received a copy of the GNU General Public License */
/* along with this program. If not, see <http://www.gnu.org/licenses/>. */
/* */
/*************************************************************************************/
namespace Thelia\Tests\Core\Template\Loop;
use Thelia\Tests\Core\Template\Element\BaseLoopTestor;
use Thelia\Core\Template\Loop\ProductSaleElements;
/**
*
* @author Etienne Roudeix <eroudeix@openstudio.fr>
*
*/
class ProductSaleElementsTest extends BaseLoopTestor
{
public function getTestedClassName()
{
return 'Thelia\Core\Template\Loop\ProductSaleElements';
}
public function getTestedInstance()
{
return new ProductSaleElements($this->request, $this->dispatcher, $this->securityContext);
}
public function getMandatoryArguments()
{
return array('product' => 1);
}
}

View File

@@ -40,6 +40,32 @@
{elseloop rel="ft"}
<h5>No feature</h5>
{/elseloop}
{ifloop rel="pse"}
<h5>Product sale elements</h5>
{assign var=current_product value=#ID}
{loop name="pse" type="product_sale_elements" product="#ID"}
<div style="border: solid 2px darkorange; padding: 5px; margin: 5px;">
{loop name="combi" type="attribute_combination" product_sale_element="#ID"}
#ATTRIBUTE_TITLE = #ATTRIBUTE_AVAILABILITY_TITLE<br />
{/loop}
<br />#WEIGHT g
<br /><strong>{if #IS_PROMO == 1} #PROMO_PRICE € (instead of #PRICE) {else} #PRICE € {/if}</strong>
<br /><br />
Add
<select>
{for $will=1 to #QUANTITY}
<option>{$will}</option>
{/for}
</select>
to my cart
</ul>
</div>
{/loop}
{/ifloop}
{elseloop rel="ft"}
<h5>No feature</h5>
{/elseloop}
</div>
{/loop}
{loop name="catgory1" type="category" parent="#ID"}
@@ -65,7 +91,12 @@
<h5>Features</h5>
<ul>
{loop name="ft" type="feature" order="manual" product="#ID"}
<li>#TITLE</li>
<li>
<strong>#TITLE</strong> :
{loop name="ft_v" type="feature_value" product="{$current_product}" feature="#ID"}
#TITLE / #PERSONAL_VALUE
{/loop}
</li>
{/loop}
</ul>
{/ifloop}