<?php
namespace Plugin\ProductField\EventSubscriber;
use Eccube\Controller\AbstractController;
use Eccube\Event\TemplateEvent;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Plugin\ProductField\Repository\ConfigRepository;
use Plugin\ProductField\Repository\ProductFieldContentRepository;
use Plugin\ProductField\Common\CommonField;
use Plugin\ProductField\Common\CommonDefine;
use Eccube\Event\EccubeEvents;
use Eccube\Event\EventArgs;
use Eccube\Common\EccubeConfig;
use Plugin\ProductField\Service\ProductFileUploader;
use Symfony\Component\Form\Extension\Core\Type\HiddenType;
use Symfony\Component\Asset\Packages;
use Symfony\Component\Validator\Constraints\NotBlank;
class ProductSubscriber extends AbstractController implements EventSubscriberInterface
{
/**
* @var ConfigRepository
*/
protected $configRepository;
protected $ProductFieldContentRepository;
protected $eccubeConfig;
protected $productFileUploader;
protected $packages;
/**
* ConfigController constructor.
*
* @param ConfigRepository $configRepository
*/
public function __construct(
ConfigRepository $configRepository,
ProductFieldContentRepository $ProductFieldContentRepository,
EccubeConfig $eccubeConfig,
ProductFileUploader $productFileUploader,
Packages $packages
)
{
$this->configRepository = $configRepository;
$this->ProductFieldContentRepository = $ProductFieldContentRepository;
$this->eccubeConfig = $eccubeConfig;
$this->productFileUploader = $productFileUploader;
$this->packages = $packages;
}
protected function getProductFieldContent($product_id, $meta_key) {
$ProductFieldContent = $this->ProductFieldContentRepository->getProductFieldContent($product_id,$meta_key);
if(empty($ProductFieldContent)){
//無いとき
$ProductFieldContent = $this->ProductFieldContentRepository->newProductFieldContent($product_id,$meta_key);
}
return $ProductFieldContent;
}
/**
* @inheritDoc
*/
public static function getSubscribedEvents()
{
return [
'@admin/Product/product.twig' => 'onTemplateAdminProduct',
EccubeEvents::ADMIN_PRODUCT_EDIT_INITIALIZE => 'onAdminProductEditInit',
EccubeEvents::ADMIN_PRODUCT_EDIT_COMPLETE => 'onAdminProductEditComplete'
];
}
public function onAdminProductEditInit(EventArgs $event)
{
$Configs = $this->configRepository->joinMetaKey($event->getArguments()["Product"]["id"]);
$builder = $event->getArgument('builder');
//auto_render trueにすると製品に自動的に表示されるがhtmlを編集したいのでコメントアウト onTemplateAdminProductでtwig追加
if(!empty($Configs)){
foreach($Configs as $index => $Config){
$CommonField = new CommonField();
//関連商品で必要
$CommonField->setEntityManager($this->getDoctrine()->getManager());
$create = $CommonField->create([
"product_id" => $event->getArguments()["Product"]["id"],
"data" => $Config,
"eccube_save_image_dir" => $this->eccubeConfig["eccube_save_image_dir"],
]);
$validation = $CommonField->validation($Config);
if($Config["a_type"] === "select" || $Config["a_type"] === "radio" || $Config["a_type"] === "checkbox" || $Config["a_type"] === "relation_product" || $Config["a_type"] === "relation_product_multiple"){
//choicesがある場合、三項演算子などで空を含めるとエラーになるので分岐
$builder->add(CommonDefine::ADD_FIELD_NAME."_".$Config["a_meta_key"],$create["type"], [
'placeholder' => '選択して下さい',
'constraints' => $validation,
'mapped' => false,//フォームのプロパティでない場合
'attr' => $create["attr"],
// 'required' => !empty($Config["a_not_blank"]) ? true : false,
'required' => true,
'label' => $create["name"],
'data' => $create["data"],
'choices' => array_keys($create["choices"]),
'choice_label' => function ($choice, $key, $value) use ($create) {
//キーと値が逆なので変更
return $create["choices"][$choice];
},
'expanded' => $Config["a_type"] === "radio" || $Config["a_type"] === "checkbox" ? true : false,
'multiple' => $Config["a_type"] === "checkbox" || $Config["a_type"] === "relation_product_multiple" ? true : false,
'eccube_form_options' => [
'plg_product_field_required' => !empty($Config["a_not_blank"]) ? true : false,
'plg_product_field_render' => true,
'plg_product_field_image' => false,
'plg_product_field_file' => false,
'plg_product_field_hidden' => false,
'auto_render' => false, // 自動表示フラグ
],
]);
}else{
$builder->add(CommonDefine::ADD_FIELD_NAME."_".$Config["a_meta_key"],$create["type"], [
'constraints' => $validation,
'mapped' => false,//フォームのプロパティでない場合
'attr' => $create["attr"],
'required' => !empty($Config["a_not_blank"]) ? true : false,
'label' => $create["name"],
'data' => $create["data"],
'eccube_form_options' => [
'plg_product_field_required' => !empty($Config["a_not_blank"]) ? true : false,
'plg_product_field_render' => true,
'plg_product_field_image' => $Config["a_type"] === "image" ? true : false,
'plg_product_field_file' => $Config["a_type"] === "file" ? true : false,
'plg_product_field_hidden' => false,
'auto_render' => false, // 自動表示フラグ
],
]);
if($Config["a_type"] === "image" || $Config["a_type"] === "file"){
$builder->add($Config["a_type"]."_".CommonDefine::ADD_FIELD_NAME."_".$Config["a_meta_key"],HiddenType::class, [
'constraints' => !empty($Config["a_not_blank"]) && !empty($create["data"]) ? [new NotBlank()] : [],
'mapped' => false,
'data' => !empty($create["data"]) ? $this->packages->getUrl($Config["b_meta_content"], 'save_image') : "",
'error_bubbling'=>false,
'eccube_form_options' => [
'plg_product_field_required' => false,
'plg_product_field_render' => true,
'plg_product_field_image' => false,
'plg_product_field_file' => false,
'plg_product_field_hidden' => true,
'auto_render' => false, // 自動表示フラグ
],
]);
}
}
}
}
}
public function onTemplateAdminProduct(TemplateEvent $event)
{
$form_adds = [];
foreach($event->getParameters()["form"] as $f){
if(!empty($f->vars["eccube_form_options"]["plg_product_field_render"])){
$form_adds[] = $f;
}
}
$event->setParameter('form_adds', $form_adds);
$event->addSnippet('@ProductField/admin/Product/product_fields.twig');
}
public function onAdminProductEditComplete(EventArgs $event){
$form = $event->getArgument('form');
$Configs = $this->configRepository->joinMetaKey($event->getArgument('Product')->getId());
if(!empty($Configs)){
foreach($form as $key => $f){
//plg_product_field_renderがなければスキップ plg_product_field_hiddenがtrueならスキップ
if(empty($f->getConfig()->getOptions()["eccube_form_options"]["plg_product_field_render"]) || !empty($f->getConfig()->getOptions()["eccube_form_options"]["plg_product_field_hidden"])){
continue;
}
foreach($Configs as $Config){
if($key === CommonDefine::ADD_FIELD_NAME . "_" . $Config["a_meta_key"]){
$ProductFieldContent = $this->getProductFieldContent($event->getArgument('Product')->getId(),$Config["a_meta_key"]);
//画像ファイルで空でなければ
if($Config["a_type"] === "image" || $Config["a_type"] === "file"){
if(empty($form->get($Config["a_type"]."_".$f->getName())->getData())){
$ProductFieldContent->setMetaContent("");
}
if(!empty($f->getData())){
$filename = $this->productFileUploader->upload($f->getData());
$ProductFieldContent->setMetaContent($filename);
}
}elseif($Config["a_type"] === "checkbox"){
$ProductFieldContent->setMetaContent(serialize($f->getData()));
}elseif($Config["a_type"] === "relation_product_multiple"){
//getDataだと順番が初期値に置き換えられてしまう Postで取得
$relation_items = !empty($_POST[$f->getParent()->getName()][$f->getName()]) ? $_POST[$f->getParent()->getName()][$f->getName()] : [];
$ProductFieldContent->setMetaContent(serialize($relation_items));
}else{
$ProductFieldContent->setMetaContent($f->getData());
}
$this->entityManager->persist($ProductFieldContent);
$this->entityManager->flush($ProductFieldContent);
break;
}
}
}
}
}
}