Commit 8e421aa5 by lmf

增加轮播图插件

增加cms首页模板文件
parent 454395ff
<?php
namespace Rokanthemes\CustomMenu\Block;
class Topmenu extends \Magento\Framework\View\Element\Template
{
protected $_categoryHelper;
protected $_categoryFlatConfig;
protected $_topMenu;
protected $_categoryFactory;
protected $_helper;
protected $_filterProvider;
protected $_blockFactory;
protected $_custommenuConfig;
protected $_storeManager;
public function __construct(
\Magento\Framework\View\Element\Template\Context $context,
\Magento\Catalog\Helper\Category $categoryHelper,
\Rokanthemes\CustomMenu\Helper\Data $helper,
\Magento\Catalog\Model\Indexer\Category\Flat\State $categoryFlatState,
\Magento\Catalog\Model\CategoryFactory $categoryFactory,
\Magento\Theme\Block\Html\Topmenu $topMenu,
\Magento\Cms\Model\Template\FilterProvider $filterProvider,
\Magento\Cms\Model\BlockFactory $blockFactory
) {
$this->_categoryHelper = $categoryHelper;
$this->_categoryFlatConfig = $categoryFlatState;
$this->_categoryFactory = $categoryFactory;
$this->_topMenu = $topMenu;
$this->_helper = $helper;
$this->_filterProvider = $filterProvider;
$this->_blockFactory = $blockFactory;
$this->_storeManager = $context->getStoreManager();
parent::__construct($context);
}
public function getCategoryHelper()
{
return $this->_categoryHelper;
}
public function getCategoryModel($id)
{
$_category = $this->_categoryFactory->create();
$_category->load($id);
return $_category;
}
public function getHtml($outermostClass = '', $childrenWrapClass = '', $limit = 0)
{
return $this->_topMenu->getHtml($outermostClass, $childrenWrapClass, $limit);
}
public function getStoreCategories($sorted = false, $asCollection = false, $toLoad = true)
{
return $this->_categoryHelper->getStoreCategories($sorted , $asCollection, $toLoad);
}
public function getChildCategories($category)
{
if ($this->_categoryFlatConfig->isFlatEnabled() && $category->getUseFlatResource()) {
$subcategories = (array)$category->getChildrenNodes();
} else {
$subcategories = $category->getChildren();
}
return $subcategories;
}
public function getActiveChildCategories($category)
{
$children = [];
if ($this->_categoryFlatConfig->isFlatEnabled() && $category->getUseFlatResource()) {
$subcategories = (array)$category->getChildrenNodes();
} else {
$subcategories = $category->getChildren();
}
foreach($subcategories as $category) {
if (!$category->getIsActive()) {
continue;
}
$children[] = $category;
}
return $children;
}
public function getBlockContent($content = '') {
if(!$this->_filterProvider)
return $content;
return $this->_filterProvider->getBlockFilter()->filter(trim($content));
}
public function getCustomBlockHtml($type='after') {
$html = '';
$block_ids = $this->_custommenuConfig['custom_links']['staticblock_'.$type];
if (!$block_ids) return '';
$block_ids = preg_replace('/\s/', '', $block_ids);
$ids = explode(',', $block_ids);
$store_id = $this->_storeManager->getStore()->getId();
foreach($ids as $block_id) {
$block = $this->_blockFactory->create();
$block->setStoreId($store_id)->load($block_id);
if(!$block) continue;
$block_content = $block->getContent();
if(!$block_content) continue;
$content = $this->_filterProvider->getBlockFilter()->setStoreId($store_id)->filter($block_content);
if(substr($content, 0, 4) == '<ul>')
$content = substr($content, 4);
if(substr($content, strlen($content) - 5) == '</ul>')
$content = substr($content, 0, -5);
$html .= $content;
}
return $html;
}
public function getSubmenuItemsHtml($children, $level = 1, $max_level = 0, $column_width=12, $menu_type = 'fullwidth', $columns = null)
{
$html = '';
if(!$max_level || ($max_level && $max_level == 0) || ($max_level && $max_level > 0 && $max_level-1 >= $level)) {
$column_class = "";
if($level == 1 && $columns && ($menu_type == 'fullwidth' || $menu_type == 'staticwidth')) {
$column_class = "col-sm-".$column_width." ";
$column_class .= "mega-columns columns".$columns;
}
$html = '<ul class="subchildmenu '.$column_class.'">';
foreach($children as $child) {
$cat_model = $this->getCategoryModel($child->getId());
$rt_menu_hide_item = $cat_model->getData('rt_menu_hide_item');
if (!$rt_menu_hide_item) {
$sub_children = $this->getActiveChildCategories($child);
$custom_style = '';
if($cat_model->getData('rt_menu_bg_img') != ''){
$custom_style = "background-image: url('" .$cat_model->getImageUrl('rt_menu_bg_img'). "');";
$custom_style = ' style="'.$custom_style.'"';
}
$rt_menu_cat_label = $cat_model->getData('rt_menu_cat_label');
$rt_menu_icon_img = $cat_model->getData('rt_menu_icon_img');
$rt_menu_font_icon = $cat_model->getData('rt_menu_font_icon');
$item_class = 'level'.$level.' ';
if(count($sub_children) > 0)
$item_class .= 'parent ';
$html .= '<li class="ui-menu-item '.$item_class.'"'.$custom_style.'>';
if(count($sub_children) > 0) {
$html .= '<div class="open-children-toggle"></div>';
}
if($level == 1 && $rt_menu_icon_img) {
$html .= '<div class="menu-thumb-img"><a class="menu-thumb-link" href="'.$this->_categoryHelper->getCategoryUrl($child).'"><img src="' .$cat_model->getImageUrl('rt_menu_icon_img'). '" alt="'.$child->getName().'"/></a></div>';
}
$html .= '<a href="'.$this->_categoryHelper->getCategoryUrl($child).'">';
if ($level > 1 && $rt_menu_icon_img)
$html .= '<img class="menu-thumb-icon" src="' .$cat_model->getImageUrl('rt_menu_icon_img'). '" alt="'.$child->getName().'"/>';
elseif($rt_menu_font_icon)
$html .= '<em class="menu-thumb-icon '.$rt_menu_font_icon.'"></em>';
$html .= '<span>'.$child->getName();
if($rt_menu_cat_label)
$html .= '<span class="cat-label cat-label-'.$rt_menu_cat_label.'">'.$this->_custommenuConfig['cat_labels'][$rt_menu_cat_label].'</span>';
$html .= '</span></a>';
if(count($sub_children) > 0) {
$html .= $this->getSubmenuItemsHtml($sub_children, $level+1, $max_level, $column_width, $menu_type);
}
$html .= '</li>';
}
}
$html .= '</ul>';
}
return $html;
}
public function getCustomMenuHtml()
{
$html = '';
$categories = $this->getStoreCategories(true,false,true);
$this->_custommenuConfig = $this->_helper->getConfig('custommenu');
$max_level = $this->_custommenuConfig['general']['max_level'];
$html .= $this->getCustomBlockHtml('before');
foreach($categories as $category) {
if (!$category->getIsActive()) {
continue;
}
$cat_model = $this->getCategoryModel($category->getId());
$rt_menu_hide_item = $cat_model->getData('rt_menu_hide_item');
if(!$rt_menu_hide_item) {
$children = $this->getActiveChildCategories($category);
$rt_menu_cat_label = $cat_model->getData('rt_menu_cat_label');
$rt_menu_icon_img = $cat_model->getData('rt_menu_icon_img');
$rt_menu_font_icon = $cat_model->getData('rt_menu_font_icon');
$rt_menu_cat_columns = $cat_model->getData('rt_menu_cat_columns');
$rt_menu_float_type = $cat_model->getData('rt_menu_float_type');
if(!$rt_menu_cat_columns){
$rt_menu_cat_columns = 4;
}
$menu_type = $cat_model->getData('rt_menu_type');
if(!$menu_type)
$menu_type = $this->_custommenuConfig['general']['menu_type'];
$custom_style = '';
$css_fixed = array();
if($cat_model->getData('rt_menu_bg_img') != ''){
$css_fixed[] = "background-image: url('" .$cat_model->getImageUrl('rt_menu_bg_img'). "')";
}
if($menu_type=="staticwidth")
$css_fixed[] = 'width: 500px';
$rt_menu_static_width = $cat_model->getData('rt_menu_static_width');
if($menu_type=="staticwidth" && $rt_menu_static_width)
$css_fixed[] = 'width: '.$rt_menu_static_width;
if(!empty($css_fixed)){
$custom_style = 'style="'.implode("; ", $css_fixed).'"';
}
$item_class = 'level0';
$item_class .= ' '.$menu_type;
$menu_top_content = $cat_model->getData('rt_menu_block_top_content');
$menu_left_content = $cat_model->getData('rt_menu_block_left_content');
$menu_left_width = $cat_model->getData('rt_menu_block_left_width');
if(!$menu_left_content || !$menu_left_width)
$menu_left_width = 0;
$menu_right_content = $cat_model->getData('rt_menu_block_right_content');
$menu_right_width = $cat_model->getData('rt_menu_block_right_width');
if(!$menu_right_content || !$menu_right_width)
$menu_right_width = 0;
$menu_bottom_content = $cat_model->getData('rt_menu_block_bottom_content');
if($rt_menu_float_type)
$rt_menu_float_type = 'fl-'.$rt_menu_float_type.' ';
if(count($children) > 0){
$item_class .= ' menu-item-has-children';
}
if(count($children) > 0 || (($menu_type=="fullwidth" || $menu_type=="staticwidth") && ($menu_top_content || $menu_left_content || $menu_right_content || $menu_bottom_content)))
$item_class .= ' parent';
$html .= '<li class="ui-menu-item '.$item_class.$rt_menu_float_type.'">';
if(count($children) > 0) {
$html .= '<div class="open-children-toggle"></div>';
}
$html .= '<a href="'.$this->_categoryHelper->getCategoryUrl($category).'" class="level-top">';
if ($rt_menu_icon_img)
$html .= '<img class="menu-thumb-icon" src="' . $cat_model->getImageUrl('rt_menu_icon_img') . '" alt="'.$category->getName().'"/>';
elseif($rt_menu_font_icon)
$html .= '<em class="menu-thumb-icon '.$rt_menu_font_icon.'"></em>';
$html .= $category->getName();
if($rt_menu_cat_label)
$html .= '<span class="cat-label cat-label-'.$rt_menu_cat_label.'">'.$this->_custommenuConfig['cat_labels'][$rt_menu_cat_label].'</span>';
$html .= '</a>';
if(count($children) > 0 || (($menu_type=="fullwidth" || $menu_type=="staticwidth") && ($menu_top_content || $menu_left_content || $menu_right_content || $menu_bottom_content))) {
$html .= '<div class="level0 submenu"'.$custom_style.'>';
if(($menu_type=="fullwidth" || $menu_type=="staticwidth") && $menu_top_content) {
$html .= '<div class="menu-top-block">'.$this->getBlockContent($menu_top_content).'</div>';
}
if(count($children) > 0 || (($menu_type=="fullwidth" || $menu_type=="staticwidth") && ($menu_left_content || $menu_right_content))) {
$html .= '<div class="row">';
if(($menu_type=="fullwidth" || $menu_type=="staticwidth") && $menu_left_content && $menu_left_width > 0) {
$html .= '<div class="menu-left-block col-sm-'.$menu_left_width.'">'.$this->getBlockContent($menu_left_content).'</div>';
}
$html .= $this->getSubmenuItemsHtml($children, 1, $max_level, 12-$menu_left_width-$menu_right_width, $menu_type, $rt_menu_cat_columns);
if(($menu_type=="fullwidth" || $menu_type=="staticwidth") && $menu_right_content && $menu_right_width > 0) {
$html .= '<div class="menu-right-block col-sm-'.$menu_right_width.'">'.$this->getBlockContent($menu_right_content).'</div>';
}
$html .= '</div>';
}
if(($menu_type=="fullwidth" || $menu_type=="staticwidth") && $menu_bottom_content) {
$html .= '<div class="menu-bottom-block">'.$this->getBlockContent($menu_bottom_content).'</div>';
}
$html .= '</div>';
}
$html .= '</li>';
}
}
$html .= $this->getCustomBlockHtml('after');
return $html;
}
}
<?php
namespace Rokanthemes\CustomMenu\Controller\Adminhtml\Category\Bgimage;
use Magento\Framework\App\Action\HttpPostActionInterface;
use Magento\Framework\Controller\ResultFactory;
class Upload extends \Magento\Backend\App\Action implements HttpPostActionInterface
{
protected $imageUploader;
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Catalog\Model\ImageUploader $imageUploader
) {
parent::__construct($context);
$this->imageUploader = $imageUploader;
}
public function execute()
{
$imageId = $this->_request->getParam('param_name', 'rt_menu_bg_img');
try {
$result = $this->imageUploader->saveFileToTmpDir($imageId);
} catch (\Exception $e) {
$result = ['error' => $e->getMessage(), 'errorcode' => $e->getCode()];
}
return $this->resultFactory->create(ResultFactory::TYPE_JSON)->setData($result);
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\CustomMenu\Controller\Adminhtml\Category\Iconimage;
use Magento\Framework\App\Action\HttpPostActionInterface;
use Magento\Framework\Controller\ResultFactory;
class Upload extends \Magento\Backend\App\Action implements HttpPostActionInterface
{
protected $imageUploader;
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Catalog\Model\ImageUploader $imageUploader
) {
parent::__construct($context);
$this->imageUploader = $imageUploader;
}
public function execute()
{
$imageId = $this->_request->getParam('param_name', 'rt_menu_icon_img');
try {
$result = $this->imageUploader->saveFileToTmpDir($imageId);
} catch (\Exception $e) {
$result = ['error' => $e->getMessage(), 'errorcode' => $e->getCode()];
}
return $this->resultFactory->create(ResultFactory::TYPE_JSON)->setData($result);
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\CustomMenu\Controller\Adminhtml\Category;
use Magento\Catalog\Controller\Adminhtml\Category\Save as SaveController;
class SavePlugin
{
/**
* Add additional images
*
* @param SaveController $subject
* @param array $data
* @return array
*/
public function beforeImagePreprocessing(SaveController $subject, $data)
{
foreach ($this->getAdditionalImages() as $imageType) {
if (empty($data[$imageType])) {
unset($data[$imageType]);
$data[$imageType]['delete'] = true;
}
}
return [$data];
}
/**
* Get additional Images
*
* @return array
*/
protected function getAdditionalImages() {
return [
'rt_menu_icon_img',
'rt_menu_bg_img',
'cat_image_thumbnail',
'vc_menu_icon_img'
];
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\CustomMenu\Helper;
use Magento\Framework\App\Helper\AbstractHelper;
class Category extends AbstractHelper
{
/**
* @return array
*/
public function getAdditionalImageTypes()
{
return array('thumbnail');
}
/**
* Retrieve image URL
* @param $image
* @return string
*/
public function getImageUrl($image)
{
$url = false;
//$image = $this->getImage();
if ($image) {
if (is_string($image)) {
$url = $this->_urlBuilder->getBaseUrl(
['_type' => \Magento\Framework\UrlInterface::URL_TYPE_MEDIA]
) . 'catalog/category/' . $image;
} else {
throw new \Magento\Framework\Exception\LocalizedException(
__('Something went wrong while getting the image url.')
);
}
}
return $url;
}
}
\ No newline at end of file
<?php
/**
* Copyright © 2016 TuanHatay. All rights reserved.
*/
namespace Rokanthemes\CustomMenu\Helper;
class Data extends \Magento\Framework\App\Helper\AbstractHelper
{
protected $_objectManager;
public function __construct(
\Magento\Framework\App\Helper\Context $context,
\Magento\Framework\ObjectManagerInterface $objectManager,
\Magento\Store\Model\StoreManagerInterface $storeManager
) {
$this->_storeManager = $storeManager;
$this->_objectManager= $objectManager;
parent::__construct($context);
}
public function getBaseUrl()
{
return $this->_storeManager->getStore()->getBaseUrl(\Magento\Framework\UrlInterface::URL_TYPE_MEDIA);
}
public function getConfig($config_path)
{
return $this->scopeConfig->getValue(
$config_path,
\Magento\Store\Model\ScopeInterface::SCOPE_STORE
);
}
public function getModel($model) {
return $this->_objectManager->create($model);
}
public function getCurrentStore() {
return $this->_storeManager->getStore();
}
public function getIconimageUrl($category)
{
$url = false;
$image = $category->getRtMenuIconImg();
if ($image) {
if (is_string($image)) {
$url = $this->_storeManager->getStore()->getBaseUrl(
\Magento\Framework\UrlInterface::URL_TYPE_MEDIA
) . 'catalog/category/' . $image;
} else {
$url = false;
}
}
return $url;
}
}
<?php
namespace Rokanthemes\CustomMenu\Model\Attribute;
class Categorylabel extends \Magento\Eav\Model\Entity\Attribute\Source\AbstractSource
{
protected $_helper;
public function __construct(
\Rokanthemes\CustomMenu\Helper\Data $helper
) {
$this->_helper = $helper;
}
public function getAllOptions()
{
$label1 = $this->_helper->getConfig('custommenu/cat_labels/label1');
$label2 = $this->_helper->getConfig('custommenu/cat_labels/label2');
$label3 = $this->_helper->getConfig('custommenu/cat_labels/label3');
if (!$this->_options) {
$this->_options = [
['value' => '', 'label' => __('No Label')],
['value' => 'label1', 'label' => $label1],
['value' => 'label2', 'label' => $label2],
['value' => 'label3', 'label' => $label3]
];
}
return $this->_options;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\CustomMenu\Model\Attribute;
class Floattype extends \Magento\Eav\Model\Entity\Attribute\Source\AbstractSource
{
public function getAllOptions()
{
if (!$this->_options) {
$this->_options = [
['value' => '', 'label' => __('Default')],
['value' => 'left', 'label' => __('Left')],
['value' => 'right', 'label' => __('Right')]
];
}
return $this->_options;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\CustomMenu\Model\Attribute;
class Menutype extends \Magento\Eav\Model\Entity\Attribute\Source\AbstractSource
{
public function getAllOptions()
{
if (!$this->_options) {
$this->_options = [
['value' => '', 'label' => __('Default')],
['value' => 'fullwidth', 'label' => __('Full Width')],
['value' => 'staticwidth', 'label' => __('Static Width')],
['value' => 'classic', 'label' => __('Classic')]
];
}
return $this->_options;
}
}
<?php
namespace Rokanthemes\CustomMenu\Model\Attribute;
class Subcatcolumns extends \Magento\Eav\Model\Entity\Attribute\Source\AbstractSource
{
public function getAllOptions()
{
if (!$this->_options) {
$this->_options = [
['value' => '', 'label' => __('Default')],
['value' => '1', 'label' => __('1 Column')],
['value' => '2', 'label' => __('2 Columns')],
['value' => '3', 'label' => __('3 Columns')],
['value' => '4', 'label' => __('4 Columns')],
['value' => '5', 'label' => __('5 Columns')],
['value' => '6', 'label' => __('6 Columns')],
['value' => '7', 'label' => __('7 Columns')],
['value' => '8', 'label' => __('8 Columns')],
['value' => '9', 'label' => __('9 Columns')],
['value' => '10', 'label' => __('10 Columns')],
['value' => '11', 'label' => __('11 Columns')],
['value' => '12', 'label' => __('12 Columns')]
];
}
return $this->_options;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\CustomMenu\Model\Attribute;
class Width extends \Magento\Eav\Model\Entity\Attribute\Source\AbstractSource
{
public function getAllOptions()
{
if (!$this->_options) {
$this->_options = [
['value' => '0', 'label' => __('Do not show')],
['value' => '1', 'label' => __('1/12')],
['value' => '2', 'label' => __('2/12')],
['value' => '3', 'label' => __('3/12')],
['value' => '4', 'label' => __('4/12')],
['value' => '5', 'label' => __('5/12')],
['value' => '6', 'label' => __('6/12')],
['value' => '7', 'label' => __('7/12')],
['value' => '8', 'label' => __('8/12')],
['value' => '9', 'label' => __('9/12')],
['value' => '10', 'label' => __('10/12')],
['value' => '11', 'label' => __('11/12')],
['value' => '12', 'label' => __('12/12')]
];
}
return $this->_options;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\CustomMenu\Model\Category\Attribute\Backend;
class Iconimage extends \Magento\Eav\Model\Entity\Attribute\Backend\AbstractBackend
{
protected $_uploaderFactory;
protected $_filesystem;
protected $_fileUploaderFactory;
protected $_logger;
private $imageUploader;
public function __construct(
\Psr\Log\LoggerInterface $logger,
\Magento\Framework\Filesystem $filesystem,
\Magento\MediaStorage\Model\File\UploaderFactory $fileUploaderFactory
) {
$this->_filesystem = $filesystem;
$this->_fileUploaderFactory = $fileUploaderFactory;
$this->_logger = $logger;
}
private function getImageUploader()
{
if ($this->imageUploader === null) {
$this->imageUploader = \Magento\Framework\App\ObjectManager::getInstance()->get(
'Magento\Catalog\CategoryImageUpload'
);
}
return $this->imageUploader;
}
public function beforeSave($object)
{
$attrCode = $this->getAttribute()->getAttributeCode();
if (!$object->hasData($attrCode)) {
$object->setData($attrCode, NULL);
} else {
$values = $object->getData($attrCode);
if (is_array($values)) {
if (!empty($values['delete'])) {
$object->setData($attrCode, NULL);
} else {
if (isset($values[0]['name']) && isset($values[0]['tmp_name'])) {
$object->setData($attrCode, $values[0]['name']);
} else {
// don't update
}
}
}
else{
$object->setData($attrCode, NULL);
}
}
return $this;
}
public function afterSave($object)
{
$image = $object->getData($this->getAttribute()->getName(), null);
if ($image !== null) {
try {
$this->getImageUploader()->moveFileFromTmp($image);
} catch (\Exception $e) {
$this->_logger->critical($e);
}
}
return $this;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\CustomMenu\Model\Category;
use Magento\Framework\Registry;
use Magento\Framework\App\RequestInterface;
use Magento\Framework\Exception\LocalizedException;
use Magento\Framework\Exception\NoSuchEntityException;
use Magento\Catalog\Api\Data\CategoryInterface;
use Magento\Catalog\Model\CategoryFactory;
use Magento\Catalog\Model\Category\DataProvider as CategoryDataProvider;
use Magento\Store\Model\Store;
use Rokanthemes\CustomMenu\Helper\Category as CategoryHelper;
class DataProvider
{
protected $registry;
protected $request;
private $categoryFactory;
private $categoryHelper;
private $requestFieldName = 'id';
private $requestScopeFieldName = 'store';
public function __construct(
Registry $registry,
RequestInterface $request,
CategoryFactory $categoryFactory,
CategoryHelper $categoryHelper
) {
$this->registry = $registry;
$this->request = $request;
$this->categoryFactory = $categoryFactory;
$this->categoryHelper = $categoryHelper;
}
public function afterGetData(CategoryDataProvider $subject, $result)
{
$category = $this->getCurrentCategory();
if ($category && $category->getId()) {
$categoryData = $result[$category->getId()];
foreach ($this->getAdditionalImageTypes() as $imageType) {
if (isset($categoryData[$imageType])) {
if(is_string($categoryData[$imageType])){
$data_cat = $categoryData[$imageType];
unset($categoryData[$imageType]);
}
}
}
//print_r($categoryData);die;
$result[$category->getId()] = $categoryData;
}
return $result;
}
private function getCurrentCategory()
{
$category = $this->registry->registry('category');
if ($category) {
return $category;
}
$requestId = $this->request->getParam($this->requestFieldName);
$requestScope = $this->request->getParam($this->requestScopeFieldName, Store::DEFAULT_STORE_ID);
if ($requestId) {
$category = $this->categoryFactory->create();
$category->setStoreId($requestScope);
$category->load($requestId);
if (!$category->getId()) {
throw NoSuchEntityException::singleField('id', $requestId);
}
}
return $category;
}
private function getAdditionalImageTypes()
{
return [
'rt_menu_icon_img',
'rt_menu_bg_img',
'cat_image_thumbnail',
'vc_menu_icon_img'
];
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\CustomMenu\Model\Config;
class Menutype implements \Magento\Framework\Option\ArrayInterface
{
public function toOptionArray()
{
return [
['value' => 'fullwidth', 'label' => __('Full Width')],
['value' => 'staticwidth', 'label' => __('Static Width')],
['value' => 'classic', 'label' => __('Classic')]
];
}
public function toArray()
{
return [
'fullwidth' => __('Full Width'),
'staticwidth' => __('Static Width'),
'classic' => __('Classic')
];
}
}
<?php
namespace Rokanthemes\CustomMenu\Model\Wysiwyg;
use Magento\Framework\Filesystem;
use Magento\Framework\App\Filesystem\DirectoryList;
use Magento\Ui\Component\Wysiwyg\ConfigInterface;
class Config extends \Magento\Cms\Model\Wysiwyg\Config
{
public function getConfig($data = [])
{
$config = new \Magento\Framework\DataObject();
$config->setData(
[
'enabled' => $this->isEnabled(),
'hidden' => $this->isHidden(),
'use_container' => false,
'add_variables' => true,
'add_widgets' => true,
'no_display' => false,
'encode_directives' => true,
'baseStaticUrl' => $this->_assetRepo->getStaticViewFileContext()->getBaseUrl(),
'baseStaticDefaultUrl' => str_replace('index.php/', '', $this->_backendUrl->getBaseUrl())
. $this->filesystem->getUri(DirectoryList::STATIC_VIEW) . '/',
'directives_url' => $this->_backendUrl->getUrl('cms/wysiwyg/directive'),
'popup_css' => $this->_assetRepo->getUrl(
'mage/adminhtml/wysiwyg/tiny_mce/themes/advanced/skins/default/dialog.css'
),
'content_css' => $this->_assetRepo->getUrl(
'mage/adminhtml/wysiwyg/tiny_mce/themes/advanced/skins/default/content.css'
),
'width' => '100%',
'add_directives' => true,
'height' => '500px',
'plugins' => [],
]
);
$config->setData('directives_url_quoted', preg_quote($config->getData('directives_url')));
if ($this->_authorization->isAllowed('Magento_Cms::media_gallery')) {
$config->addData(
[
'add_images' => true,
'files_browser_window_url' => $this->_backendUrl->getUrl('cms/wysiwyg_images/index'),
'files_browser_window_width' => $this->_windowSize['width'],
'files_browser_window_height' => $this->_windowSize['height'],
]
);
}
if (is_array($data)) {
$config->addData($data);
}
if ($config->getData('add_variables')) {
$settings = $this->_variableConfig->getWysiwygPluginSettings($config);
$config->addData($settings);
}
if ($config->getData('add_widgets')) {
$settings = $this->_widgetConfig->getPluginSettings($config);
$config->addData($settings);
}
return $config;
}
}
<?php
/**
* Copyright © 2016 TuanHatay. All rights reserved.
*/
namespace Rokanthemes\CustomMenu\Setup;
use Magento\Framework\Module\Setup\Migration;
use Magento\Framework\Setup\InstallDataInterface;
use Magento\Framework\Setup\ModuleContextInterface;
use Magento\Framework\Setup\ModuleDataSetupInterface;
use Magento\Catalog\Setup\CategorySetupFactory;
/**
* @codeCoverageIgnore
*/
class InstallData implements InstallDataInterface
{
/**
* Category setup factory
*
* @var CategorySetupFactory
*/
private $categorySetupFactory;
/**
* Init
*
* @param CategorySetupFactory $categorySetupFactory
*/
public function __construct(CategorySetupFactory $categorySetupFactory)
{
$this->categorySetupFactory = $categorySetupFactory;
}
/**
* {@inheritdoc}
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
*/
public function install(ModuleDataSetupInterface $setup, ModuleContextInterface $context)
{
$installer = $setup;
$installer->startSetup();
$categorySetup = $this->categorySetupFactory->create(['setup' => $setup]);
$entityTypeId = $categorySetup->getEntityTypeId(\Magento\Catalog\Model\Category::ENTITY);
$attributeSetId = $categorySetup->getDefaultAttributeSetId($entityTypeId);
$menu_attributes = [
'rt_menu_hide_item' => [
'type' => 'int',
'label' => 'Hide This Menu Item',
'input' => 'select',
'source' => 'Magento\Eav\Model\Entity\Attribute\Source\Boolean',
'required' => false,
'sort_order' => 10,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_type' => [
'type' => 'varchar',
'label' => 'Menu Type',
'input' => 'select',
'source' => 'Rokanthemes\CustomMenu\Model\Attribute\Menutype',
'required' => false,
'sort_order' => 20,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_static_width' => [
'type' => 'varchar',
'label' => 'Static Width',
'input' => 'text',
'required' => false,
'sort_order' => 30,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_cat_columns' => [
'type' => 'varchar',
'label' => 'Sub Category Columns',
'input' => 'select',
'source' => 'Rokanthemes\CustomMenu\Model\Attribute\Subcatcolumns',
'required' => false,
'sort_order' => 40,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_float_type' => [
'type' => 'varchar',
'label' => 'Float',
'input' => 'select',
'source' => 'Rokanthemes\CustomMenu\Model\Attribute\Floattype',
'required' => false,
'sort_order' => 50,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_cat_label' => [
'type' => 'varchar',
'label' => 'Category Label',
'input' => 'select',
'source' => 'Rokanthemes\CustomMenu\Model\Attribute\Categorylabel',
'required' => false,
'sort_order' => 60,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_icon_img' => [
'type' => 'varchar',
'label' => 'Icon Image',
'input' => 'image',
'backend' => 'Magento\Catalog\Model\Category\Attribute\Backend\Image',
'required' => false,
'sort_order' => 70,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_font_icon' => [
'type' => 'varchar',
'label' => 'Font Icon Class',
'input' => 'text',
'required' => false,
'sort_order' => 80,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_block_top_content' => [
'type' => 'text',
'label' => 'Top Block',
'input' => 'textarea',
'required' => false,
'sort_order' => 90,
'wysiwyg_enabled' => true,
'is_html_allowed_on_front' => true,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_block_left_width' => [
'type' => 'varchar',
'label' => 'Left Block Width',
'input' => 'select',
'source' => 'Rokanthemes\CustomMenu\Model\Attribute\Width',
'required' => false,
'sort_order' => 100,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_block_left_content' => [
'type' => 'text',
'label' => 'Left Block',
'input' => 'textarea',
'required' => false,
'sort_order' => 110,
'wysiwyg_enabled' => true,
'is_html_allowed_on_front' => true,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_block_right_width' => [
'type' => 'varchar',
'label' => 'Right Block Width',
'input' => 'select',
'source' => 'Rokanthemes\CustomMenu\Model\Attribute\Width',
'required' => false,
'sort_order' => 120,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_block_right_content' => [
'type' => 'text',
'label' => 'Right Block',
'input' => 'textarea',
'required' => false,
'sort_order' => 130,
'wysiwyg_enabled' => true,
'is_html_allowed_on_front' => true,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
],
'rt_menu_block_bottom_content' => [
'type' => 'text',
'label' => 'Bottom Block',
'input' => 'textarea',
'required' => false,
'sort_order' => 140,
'wysiwyg_enabled' => true,
'is_html_allowed_on_front' => true,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
]
];
foreach($menu_attributes as $item => $data) {
$categorySetup->addAttribute(\Magento\Catalog\Model\Category::ENTITY, $item, $data);
}
$idg = $categorySetup->getAttributeGroupId($entityTypeId, $attributeSetId, 'Custom Menu');
foreach($menu_attributes as $item => $data) {
$categorySetup->addAttributeToGroup(
$entityTypeId,
$attributeSetId,
$idg,
$item,
$data['sort_order']
);
}
$installer->endSetup();
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\CustomMenu\Setup;
use Magento\Framework\Module\Setup\Migration;
use Magento\Framework\Setup\UpgradeDataInterface;
use Magento\Framework\Setup\ModuleContextInterface;
use Magento\Framework\Setup\ModuleDataSetupInterface;
use Magento\Catalog\Setup\CategorySetupFactory;
/**
* Data migration:
* - Config Migration from version 2.0.1 JSON file store to 2.0.2+ Magento config way
*
*/
class UpgradeData implements UpgradeDataInterface
{
private $categorySetupFactory;
public function __construct(CategorySetupFactory $categorySetupFactory)
{
$this->categorySetupFactory = $categorySetupFactory;
}
/**
* Run data upgrade.
*
* @param ModuleDataSetupInterface $setup
* @param ModuleContextInterface $context
*/
public function upgrade(ModuleDataSetupInterface $setup, ModuleContextInterface $context)
{
$setup->startSetup();
if (version_compare($context->getVersion(), '2.3.4') < 0) {
$categorySetup = $this->categorySetupFactory->create(['setup' => $setup]);
$entityTypeId = $categorySetup->getEntityTypeId(\Magento\Catalog\Model\Category::ENTITY);
$attributeSetId = $categorySetup->getDefaultAttributeSetId($entityTypeId);
$menu_attributes = [
'rt_menu_bg_img' => [
'type' => 'varchar',
'label' => 'Background Image',
'input' => 'image',
'backend' => 'Magento\Catalog\Model\Category\Attribute\Backend\Image',
'required' => false,
'sort_order' => 70,
'global' => \Magento\Eav\Model\Entity\Attribute\ScopedAttributeInterface::SCOPE_STORE,
'group' => 'Custom Menu'
]
];
foreach($menu_attributes as $item => $data) {
$categorySetup->addAttribute(\Magento\Catalog\Model\Category::ENTITY, $item, $data);
}
$idg = $categorySetup->getAttributeGroupId($entityTypeId, $attributeSetId, 'Custom Menu');
foreach($menu_attributes as $item => $data) {
$categorySetup->addAttributeToGroup(
$entityTypeId,
$attributeSetId,
$idg,
$item,
$data['sort_order']
);
}
}
$setup->endSetup();
}
}
<?xml version="1.0"?>
<!--
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:Acl/etc/acl.xsd">
<acl>
<resources>
<resource id="Magento_Backend::admin">
<resource id="Rokanthemes_RokanBase::rokanbase" title="Rokanthemes" translate="title" sortOrder="30">
<resource id="Rokanthemes_RokanBase::rokanbase_setting" title="Configuration" translate="title" sortOrder="10">
<resource id="Rokanthemes_CustomMenu::custommenu" title="Custom Menu" translate="title" sortOrder="100" />
</resource>
</resource>
</resource>
</resources>
</acl>
</config>
\ No newline at end of file
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../Magento/Backend/etc/menu.xsd">
<menu>
<add id="Rokanthemes_CustomMenu::custommenu" title="Custom Menu" module="Rokanthemes_CustomMenu" sortOrder="0" parent="Rokanthemes_RokanBase::rokanbase_setting" resource="Rokanthemes_CustomMenu::custommenu" action="adminhtml/system_config/edit/section/custommenu" />
</menu>
</config>
\ No newline at end of file
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:App/etc/routes.xsd">
<router id="admin">
<route id="categorylist" frontName="categorylist">
<module name="Rokanthemes_CustomMenu" before="Magento_Backend" />
</route>
</router>
</config>
\ No newline at end of file
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../Magento/Backend/etc/system_file.xsd">
<system>
<section id="custommenu" translate="label" type="text" sortOrder="40" showInDefault="1" showInWebsite="1" showInStore="1">
<class>separator-top</class>
<label>Custom Menu</label>
<tab>rokanthemes</tab>
<resource>Rokanthemes_CustomMenu::custommenu</resource>
<group id="general" translate="label" type="text" sortOrder="20" showInDefault="1" showInWebsite="1" showInStore="1">
<label>General Settings</label>
<field id="enable" translate="label" type="select" sortOrder="10" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Enable</label>
<source_model>Magento\Config\Model\Config\Source\Yesno</source_model>
</field>
<field id="menu_type" translate="label" type="select" sortOrder="20" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Default Menu Type</label>
<source_model>Rokanthemes\CustomMenu\Model\Config\Menutype</source_model>
</field>
<field id="static_width" translate="label comment" type="text" sortOrder="22" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Static Width</label>
<comment>eg: 500px</comment>
<depends>
<field id="menu_type">staticwidth</field>
</depends>
</field>
<field id="max_level" translate="label comment" type="text" sortOrder="30" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Visible Menu Depth</label>
<comment>eg: 1, 2, 3, 4 (0 - disable limits). For example, if you set this value to 2, only second level categories will be displayed.</comment>
</field>
</group>
<group id="custom_links" translate="label" type="text" sortOrder="50" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Custom Links &amp; Blocks</label>
<field id="staticblock_before" translate="label comment" type="text" sortOrder="10" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Static Block(before)</label>
<comment><![CDATA[Input the Static Block ID, the block content will be shown before the default category menu items and after home link.<br/>eg: menu_custom_links_before]]></comment>
</field>
<field id="staticblock_after" translate="label comment" type="text" sortOrder="20" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Static Block(after)</label>
<comment><![CDATA[Input the Static Block ID, the block content will be shown after the default category menu items<br/>eg: menu_custom_links]]></comment>
</field>
</group>
<group id="cat_labels" translate="label" type="text" sortOrder="80" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Category Labels</label>
<field id="label1" translate="label comment" type="text" sortOrder="10" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Label 1</label>
<comment><![CDATA[Define the text of the category label 1. Labels can be assigned to every category in <b>Products > Inventory > Categories</b>]]></comment>
</field>
<field id="label2" translate="label comment" type="text" sortOrder="20" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Label 2</label>
<comment><![CDATA[Define the text of the category label 2. Labels can be assigned to every category in <b>Products > Inventory > Categories</b>]]></comment>
</field>
<field id="label3" translate="label comment" type="text" sortOrder="30" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Label 3</label>
<comment><![CDATA[Define the text of the category label 3. Labels can be assigned to every category in <b>Products > Inventory > Categories</b>]]></comment>
</field>
</group>
</section>
</system>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../Store/etc/config.xsd">
<default>
<custommenu>
<general>
<enable>1</enable>
<menu_type>fullwidth</menu_type>
<static_width>500px</static_width>
<max_level></max_level>
</general>
<custom_links>
<staticblock_before>rokanthemes_custom_menu_before</staticblock_before>
<staticblock_after>rokanthemes_custom_menu</staticblock_after>
</custom_links>
<cat_labels>
<label1>New</label1>
<label2>Hot!</label2>
<label3>Sale</label3>
</cat_labels>
</custommenu>
</default>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
<type name="Rokanthemes\CustomMenu\Controller\Adminhtml\Category\Iconimage\Upload">
<arguments>
<argument name="imageUploader" xsi:type="object">Magento\Catalog\CategoryImageUpload</argument>
</arguments>
</type>
<type name="Rokanthemes\CustomMenu\Controller\Adminhtml\Category\Bgimage\Upload">
<arguments>
<argument name="imageUploader" xsi:type="object">Magento\Catalog\CategoryImageUpload</argument>
</arguments>
</type>
<type name="Magento\Catalog\Model\Category\DataProvider">
<plugin name="custom_menu_category_data_provider" type="Rokanthemes\CustomMenu\Model\Category\DataProvider" />
</type>
<type name="Magento\Catalog\Controller\Adminhtml\Category\Save">
<plugin name="custom_menu_image_preprocessing" type="Rokanthemes\CustomMenu\Controller\Adminhtml\Category\SavePlugin" />
</type>
</config>
\ No newline at end of file
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../lib/internal/Magento/Framework/Module/etc/module.xsd">
<module name="Rokanthemes_CustomMenu" schema_version="2.3.4" setup_version="2.3.4" active="true">
<sequence>
<module name="Magento_Catalog"/>
</sequence>
</module>
</config>
\ No newline at end of file
<?php
/**
* Copyright © 2016 TuanHatay. All rights reserved.
*/
\Magento\Framework\Component\ComponentRegistrar::register(
\Magento\Framework\Component\ComponentRegistrar::MODULE,
'Rokanthemes_CustomMenu',
__DIR__
);
<?xml version="1.0" encoding="UTF-8"?>
<!--
/**
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<form xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Ui:etc/ui_configuration.xsd">
<fieldset name="custom-menu">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="label" xsi:type="string" translate="true">Custom Menu</item>
<item name="collapsible" xsi:type="boolean">true</item>
<item name="sortOrder" xsi:type="number">70</item>
</item>
</argument>
<field name="rt_menu_hide_item">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="sortOrder" xsi:type="number">10</item>
<item name="dataType" xsi:type="string">boolean</item>
<item name="formElement" xsi:type="string">checkbox</item>
<item name="source" xsi:type="string">category</item>
<item name="prefer" xsi:type="string">toggle</item>
<item name="label" xsi:type="string" translate="true">Hide This Menu Item</item>
<item name="valueMap" xsi:type="array">
<item name="true" xsi:type="string">1</item>
<item name="false" xsi:type="string">0</item>
</item>
<item name="validation" xsi:type="array">
<item name="required-entry" xsi:type="boolean">false</item>
</item>
<item name="default" xsi:type="string">0</item>
</item>
</argument>
</field>
<field name="rt_menu_type">
<argument name="data" xsi:type="array">
<item name="options" xsi:type="object">Rokanthemes\CustomMenu\Model\Attribute\Menutype</item>
<item name="config" xsi:type="array">
<item name="sortOrder" xsi:type="number">20</item>
<item name="dataType" xsi:type="string">string</item>
<item name="formElement" xsi:type="string">select</item>
<item name="label" xsi:type="string" translate="true">Menu Type</item>
</item>
</argument>
</field>
<field name="rt_menu_static_width">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="sortOrder" xsi:type="number">25</item>
<item name="dataType" xsi:type="string">string</item>
<item name="formElement" xsi:type="string">input</item>
<item name="label" xsi:type="string" translate="true">Static Width</item>
</item>
</argument>
</field>
<field name="rt_menu_cat_columns">
<argument name="data" xsi:type="array">
<item name="options" xsi:type="object">Rokanthemes\CustomMenu\Model\Attribute\Subcatcolumns</item>
<item name="config" xsi:type="array">
<item name="sortOrder" xsi:type="number">30</item>
<item name="dataType" xsi:type="string">string</item>
<item name="formElement" xsi:type="string">select</item>
<item name="label" xsi:type="string" translate="true">Sub Category Columns</item>
</item>
</argument>
</field>
<field name="rt_menu_float_type">
<argument name="data" xsi:type="array">
<item name="options" xsi:type="object">Rokanthemes\CustomMenu\Model\Attribute\Floattype</item>
<item name="config" xsi:type="array">
<item name="sortOrder" xsi:type="number">40</item>
<item name="dataType" xsi:type="string">string</item>
<item name="formElement" xsi:type="string">select</item>
<item name="label" xsi:type="string" translate="true">Float</item>
</item>
</argument>
</field>
<field name="rt_menu_cat_label">
<argument name="data" xsi:type="array">
<item name="options" xsi:type="object">Rokanthemes\CustomMenu\Model\Attribute\Categorylabel</item>
<item name="config" xsi:type="array">
<item name="sortOrder" xsi:type="number">50</item>
<item name="dataType" xsi:type="string">string</item>
<item name="formElement" xsi:type="string">select</item>
<item name="label" xsi:type="string" translate="true">Category Label</item>
</item>
</argument>
</field>
<field name="rt_menu_icon_img" sortOrder="50" formElement="imageUploader">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="source" xsi:type="string">category</item>
</item>
</argument>
<settings>
<elementTmpl>ui/form/element/uploader/image</elementTmpl>
<dataType>string</dataType>
<label translate="true">Icon Image</label>
<visible>true</visible>
<required>false</required>
</settings>
<formElements>
<imageUploader>
<settings>
<required>false</required>
<uploaderConfig>
<param xsi:type="url" name="url" path="categorylist/category_iconimage/upload"/>
</uploaderConfig>
<previewTmpl>Magento_Catalog/image-preview</previewTmpl>
<openDialogTitle>Media Gallery</openDialogTitle>
<initialMediaGalleryOpenSubpath>catalog/category</initialMediaGalleryOpenSubpath>
<allowedExtensions>jpg jpeg gif png</allowedExtensions>
<maxFileSize>4194304</maxFileSize>
</settings>
</imageUploader>
</formElements>
</field>
<field name="rt_menu_font_icon">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="sortOrder" xsi:type="number">70</item>
<item name="dataType" xsi:type="string">string</item>
<item name="formElement" xsi:type="string">input</item>
<item name="label" xsi:type="string" translate="true">Font Icon Class</item>
</item>
</argument>
</field>
<field name="rt_menu_bg_img" sortOrder="50" formElement="imageUploader">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="source" xsi:type="string">category</item>
</item>
</argument>
<settings>
<elementTmpl>ui/form/element/uploader/image</elementTmpl>
<dataType>string</dataType>
<label translate="true">Background Image</label>
<visible>true</visible>
<required>false</required>
</settings>
<formElements>
<imageUploader>
<settings>
<required>false</required>
<uploaderConfig>
<param xsi:type="url" name="url" path="categorylist/category_bgimage/upload"/>
</uploaderConfig>
<previewTmpl>Magento_Catalog/image-preview</previewTmpl>
<openDialogTitle>Media Gallery</openDialogTitle>
<initialMediaGalleryOpenSubpath>catalog/category</initialMediaGalleryOpenSubpath>
<allowedExtensions>jpg jpeg gif png</allowedExtensions>
<maxFileSize>4194304</maxFileSize>
</settings>
</imageUploader>
</formElements>
</field>
<field name="rt_menu_block_top_content" template="ui/form/field" sortOrder="80" formElement="wysiwyg">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="wysiwygConfigData" xsi:type="array">
<item name="height" xsi:type="string">100px</item>
<item name="add_variables" xsi:type="boolean">false</item>
<item name="add_widgets" xsi:type="boolean">false</item>
<item name="add_images" xsi:type="boolean">true</item>
<item name="add_directives" xsi:type="boolean">true</item>
</item>
<item name="source" xsi:type="string">category</item>
</item>
</argument>
<settings>
<label translate="true">Top Block</label>
<dataScope>rt_menu_block_top_content</dataScope>
</settings>
<formElements>
<wysiwyg class="Magento\Catalog\Ui\Component\Category\Form\Element\Wysiwyg">
<settings>
<rows>8</rows>
<wysiwyg>true</wysiwyg>
</settings>
</wysiwyg>
</formElements>
</field>
<field name="rt_menu_block_left_width">
<argument name="data" xsi:type="array">
<item name="options" xsi:type="object">Rokanthemes\CustomMenu\Model\Attribute\Width</item>
<item name="config" xsi:type="array">
<item name="sortOrder" xsi:type="number">90</item>
<item name="dataType" xsi:type="string">string</item>
<item name="formElement" xsi:type="string">select</item>
<item name="label" xsi:type="string" translate="true">Left Block Width</item>
</item>
</argument>
</field>
<field name="rt_menu_block_left_content" template="ui/form/field" sortOrder="100" formElement="wysiwyg">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="wysiwygConfigData" xsi:type="array">
<item name="height" xsi:type="string">100px</item>
<item name="add_variables" xsi:type="boolean">false</item>
<item name="add_widgets" xsi:type="boolean">false</item>
<item name="add_images" xsi:type="boolean">true</item>
<item name="add_directives" xsi:type="boolean">true</item>
</item>
<item name="source" xsi:type="string">category</item>
</item>
</argument>
<settings>
<label translate="true">Left Block</label>
<dataScope>rt_menu_block_left_content</dataScope>
</settings>
<formElements>
<wysiwyg class="Magento\Catalog\Ui\Component\Category\Form\Element\Wysiwyg">
<settings>
<rows>8</rows>
<wysiwyg>true</wysiwyg>
</settings>
</wysiwyg>
</formElements>
</field>
<field name="rt_menu_block_right_width">
<argument name="data" xsi:type="array">
<item name="options" xsi:type="object">Rokanthemes\CustomMenu\Model\Attribute\Width</item>
<item name="config" xsi:type="array">
<item name="sortOrder" xsi:type="number">110</item>
<item name="dataType" xsi:type="string">string</item>
<item name="formElement" xsi:type="string">select</item>
<item name="label" xsi:type="string" translate="true">Right Block Width</item>
</item>
</argument>
</field>
<field name="rt_menu_block_right_content" template="ui/form/field" sortOrder="120" formElement="wysiwyg">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="wysiwygConfigData" xsi:type="array">
<item name="height" xsi:type="string">100px</item>
<item name="add_variables" xsi:type="boolean">false</item>
<item name="add_widgets" xsi:type="boolean">false</item>
<item name="add_images" xsi:type="boolean">true</item>
<item name="add_directives" xsi:type="boolean">true</item>
</item>
<item name="source" xsi:type="string">category</item>
</item>
</argument>
<settings>
<label translate="true">Right Block</label>
<dataScope>rt_menu_block_right_content</dataScope>
</settings>
<formElements>
<wysiwyg class="Magento\Catalog\Ui\Component\Category\Form\Element\Wysiwyg">
<settings>
<rows>8</rows>
<wysiwyg>true</wysiwyg>
</settings>
</wysiwyg>
</formElements>
</field>
<field name="rt_menu_block_bottom_content" template="ui/form/field" sortOrder="130" formElement="wysiwyg">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="wysiwygConfigData" xsi:type="array">
<item name="height" xsi:type="string">100px</item>
<item name="add_variables" xsi:type="boolean">false</item>
<item name="add_widgets" xsi:type="boolean">false</item>
<item name="add_images" xsi:type="boolean">true</item>
<item name="add_directives" xsi:type="boolean">true</item>
</item>
<item name="source" xsi:type="string">category</item>
</item>
</argument>
<settings>
<label translate="true">Bottom Block</label>
<dataScope>rt_menu_block_bottom_content</dataScope>
</settings>
<formElements>
<wysiwyg class="Magento\Catalog\Ui\Component\Category\Form\Element\Wysiwyg">
<settings>
<rows>8</rows>
<wysiwyg>true</wysiwyg>
</settings>
</wysiwyg>
</formElements>
</field>
</fieldset>
</form>
\ No newline at end of file
<?xml version="1.0" encoding="UTF-8"?>
<form xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Ui:etc/ui_configuration.xsd">
<modal name="advanced_inventory_modal">
<fieldset name="stock_data">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="label" xsi:type="string" translate="true">Stock Configuration</item>
<item name="dataScope" xsi:type="string"/>
<item name="sortOrder" xsi:type="number">2</item>
<item name="collapsible" xsi:type="boolean">false</item>
</item>
</argument>
<field name="sold_stock">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="sortOrder" xsi:type="number">25</item>
<item name="dataType" xsi:type="string">string</item>
<item name="formElement" xsi:type="string">input</item>
<item name="label" xsi:type="string" translate="true">Static Width</item>
</item>
</argument>
</field>
</fieldset>
</modal>
</form>
\ No newline at end of file
<?xml version="1.0"?>
<!--
/**
* Copyright © 2016 TuanHatay. All rights reserved.
*/
-->
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
<body>
<referenceBlock name="catalog.topnav" remove="true"/>
<referenceContainer name="page.top">
<block class="Rokanthemes\CustomMenu\Block\Topmenu" name="custom.topnav" template="Rokanthemes_CustomMenu::topmenu.phtml" group="navigation-sections" ttl="3600" before="-"/>
</referenceContainer>
</body>
</page>
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
var config = {
"shim": {
"rokanthemes/custommenu": ["jquery"]
},
'paths': {
'rokanthemes/custommenu': 'Rokanthemes_CustomMenu/js/custommenu'
}
};
<?php
/**
* Copyright © 2016 TuanHatay. All rights reserved.
*/
?>
<?php
/**
* Top menu for store
*
* @see \Rokanthemes\CustomMenu\Block\Topmenu
*/
?>
<?php
$_helper = $this->helper('Rokanthemes\CustomMenu\Helper\Data');
$_config = $_helper->getConfig('custommenu');
$columnsLimit = 0;
if($_config['general']['enable']) {
?>
<?php $_menu = $block->getCustomMenuHtml(); ?>
<nav class="navigation custommenu side-custommenu" role="navigation">
<ul>
<?php echo $_menu; ?>
</ul>
</nav>
<script type="text/javascript">
require([
'jquery',
'rokanthemes/custommenu'
], function ($) {
$(".custommenu").CustomMenu();
});
</script>
<?php
}
?>
\ No newline at end of file
<?php
/**
* Copyright © 2016 TuanHatay. All rights reserved.
*/
?>
<?php
/**
* Top menu for store
*
* @see \Rokanthemes\CustomMenu\Block\Topmenu
*/
?>
<?php
$_helper = $this->helper('Rokanthemes\CustomMenu\Helper\Data');
$_config = $_helper->getConfig('custommenu');
$columnsLimit = 0;
if($_config['general']['enable']) {
?>
<?php $_menu = $block->getCustomMenuHtml(); ?>
<div class="navigation custommenu main-nav" role="navigation">
<ul>
<?php echo $_menu; ?>
</ul>
</div>
<script type="text/javascript">
require([
'jquery',
'rokanthemes/custommenu'
], function ($) {
$(".custommenu").CustomMenu();
});
</script>
<?php
} else {
?>
<?php $_menu = $block->getHtml('level-top', 'submenu', $columnsLimit); ?>
<div class="navigation custommenu main-nav" role="navigation">
<ul data-mage-init='{"menu":{"responsive":true, "expanded":true, "position":{"my":"left top","at":"left bottom"}}}'>
<?php /* @escapeNotVerified */ echo $_menu; ?>
</ul>
</div>
<?php
}
?>
\ No newline at end of file
// /**
// * Copyright © 2016 TuanHatay. All rights reserved.
// */
& when (@media-common = true) {
}
.media-width(@extremum, @break) when (@extremum = 'min') and (@break = @screen__m) {
.custommenu.navigation {
> ul {
position: relative;
&:after {
disaply: table;
content: '';
clear: both;
}
}
.open-children-toggle {
display: none;
}
span.cat-label {
position: absolute;
text-transform: uppercase;
font: inherit;
font-size: 9px;
padding: 2px;
border-radius: 2px;
line-height: 1;
color: #fff;
&:before {
content: "";
position: absolute;
width: 3px;
height: 3px;
border: 3px solid transparent;
}
&.cat-label-label1 {
background-color: #0cc485;
}
&.cat-label-label2 {
background-color: #eb2771;
}
&.cat-label-label3 {
background-color: #0ae3eb;
}
}
a:hover > span > span.cat-label {
text-decoration: none;
}
li {
> a > span {
position: relative;
}
&.level0 {
> .level-top {
transition-delay: 0s !important;
}
> a > span.cat-label {
top: -18px;
right: 14px;
&:before {
left: 3px;
bottom: -6px;
}
&.cat-label-label1 {
&:before {
border-top-color: #0cc485;
}
}
&.cat-label-label2 {
&:before {
border-top-color: #eb2771;
}
}
&.cat-label-label3 {
&:before {
border-top-color: #0ae3eb;
}
}
}
}
.subchildmenu {
li > a > span > span.cat-label {
top: 3px;
right: -35px;
&:before {
left: -6px;
bottom: 3px;
}
&.cat-label-label1 {
&:before {
border-right-color: #0cc485;
}
}
&.cat-label-label2 {
&:before {
border-right-color: #eb2771;
}
}
&.cat-label-label3 {
&:before {
border-right-color: #0ae3eb;
}
}
}
}
}
.subchildmenu.mega-columns {
> li {
float: left;
padding: 0 5px;
}
&.columns1 {
> li {
float: none;
}
}
&.columns2 {
> li {
width: 50%;
&:nth-child(2n+1) {
clear: both;
}
}
}
&.columns3 {
> li {
width: 33.33%;
&:nth-child(3n+1) {
clear: both;
}
}
}
&.columns4 {
> li {
width: 25%;
&:nth-child(4n+1) {
clear: both;
}
}
}
&.columns5 {
> li {
width: 20%;
&:nth-child(5n+1) {
clear: both;
}
}
}
&.columns6 {
> li {
width: 16.66%;
&:nth-child(6n+1) {
clear: both;
}
}
}
}
li.level0 {
transition-delay: 0s;
transition: .2s opacity;
&.fl-left {
float: left;
}
&.fl-right {
float: right;
&.staticwidth {
.submenu {
left: auto;
right: 0;
border-radius: 6px 0 6px 6px;
}
}
}
.submenu {
display: block;
visibility: hidden;
opacity: 0;
transition: .2s opacity;
color: #777;
> ul {
margin-top: 0;
&:before, &:after {
display: none;
}
}
}
&.parent > .submenu.popup-left {
left: auto;
right: 0;
border-radius: 6px 0 6px 6px;
}
.row {
margin-left: -5px;
margin-right: -5px;
}
.col-sm-1, .col-sm-2, .col-sm-3, .col-sm-4, .col-sm-5, .col-sm-6, .col-sm-7, .col-sm-8, .col-sm-9, .col-sm-10, .col-sm-11, .col-sm-12 {
padding-left: 5px;
padding-right: 5px;
}
&.fullwidth {
position: static;
> .submenu {
width: 100%;
border-radius: 0 0 6px 6px;
}
}
&.fullwidth, &.staticwidth {
> .submenu {
padding: 5px 8px 15px;
left: 0;
}
&:hover {
> .submenu {
visibility: visible;
opacity: 1;
}
}
.submenu {
li.parent {
> a {
&:after {
display: none;
}
}
}
li.level1 {
> a {
font-size: 14px;
font-weight: 600;
text-transform: uppercase;
margin-top: 10px;
}
.subchildmenu {
.subchildmenu {
padding-left: 10px;
}
}
> .menu-thumb-img {
margin: 10px 0 -5px;
}
}
.subchildmenu {
.subchildmenu {
padding: 5px 0;
}
}
a {
padding: 5px;
line-height: 1;
font-size: 13px;
&:hover {
background: none;
> span {
text-decoration: underline;
}
}
}
.menu-top-block, .menu-left-block, .menu-right-block, .menu-bottom-block {
a {
display: inline;
&:hover {
text-decoration: underline;
}
}
a.btn-default {
background-color: #08c;
color: #fff;
&:hover, &:focus {
background-color: #08c;
color: #fff;
text-decoration: none;
opacity: 0.8;
}
}
}
}
}
&.classic {
.submenu > .row {
margin: 0;
}
.subchildmenu {
min-width: 230px;
.subchildmenu {
visibility: hidden;
opacity: 0;
transition: .2s opacity;
padding: 6px 8px;
box-shadow: 0 0 3px rgba(0,0,0,0.25);
border-radius: 0 6px 6px 6px;
position: absolute;
left: 0;
top: -6px;
background: #fff;
z-index: 1;
}
> li:hover {
> .subchildmenu {
visibility: visible;
opacity: 1;
}
}
}
li.parent {
& > .subchildmenu.popup-left {
left: auto;
right: 100%;
border-radius: 6px 0 6px 6px;
}
}
.subchildmenu.popup-left .subchildmenu {
left: auto;
right: 100%;
border-radius: 6px 0 6px 6px;
}
&:hover {
> .submenu {
visibility: visible;
opacity: 1;
}
}
li:hover > .submenu {
visibility: visible;
opacity: 1;
}
}
&.classic {
.submenu, .subchildmenu .subchildmenu {
left: 0;
}
}
&.staticwidth {
.submenu {
left: 0;
}
}
}
&.side-custommenu {
li {
margin: 0;
position: relative;
&.level0 {
display: block;
position: relative;
border-radius: 0;
margin: 0;
&.parent > a:after {
content: '\f801';
display: inline-block;
font-family: 'porto-icons';
vertical-align: top;
margin-left: 6px;
line-height: 41px;
float: right;
}
&.classic .submenu li.parent > a:after {
content: '\f801';
display: inline-block;
font-family: 'porto-icons';
vertical-align: top;
margin-left: 6px;
margin-right: 5px;
line-height: 15px;
float: right;
}
&.fullwidth > .submenu, &.staticwidth > .submenu {
left: 100% !important;
top: 0;
padding-bottom: 15px;
}
&.classic > .submenu {
left: 100% !important;
top: 0;
}
&.fullwidth > .submenu {
width: 871px;
}
& > a {
display: block;
padding: 0 5px;
margin: 0 10px;
border-top: 1px solid #ddd;
line-height: 41px;
font-weight: 400;
font-size: 14px;
> span.cat-label {
position: relative;
margin-left: 10px;
padding: 0 2px;
top: 0;
right: 0;
&:before {
left: -6px;
top: 3px;
bottom: auto;
border-top-color: transparent;
}
&.cat-label-label1 {
&:before {
border-right-color: #0cc485;
}
}
&.cat-label-label2 {
&:before {
border-right-color: #eb2771;
}
}
&.cat-label-label3 {
&:before {
border-right-color: #0ae3eb;
}
}
}
}
&:first-child > a {
border-top: 0;
}
&:hover {
background-color: #08c;
& > a {
color: #fff;
border-top-color: #08c;
}
}
& > .submenu {
border-left-width: 5px;
padding: 5px 8px;
box-shadow: 0 0 3px rgba(0,0,0,0.25);
border-radius: 0 6px 6px 6px;
}
}
}
}
}
.home-side-menu {
background-color: #fbfbfb;
border: 1px solid #ddd;
border-radius: 5px;
margin-bottom: 20px;
}
h2.side-menu-title {
margin: 0;
background-color: #f5f5f5;
color: #a39f9c;
font-size: 13px;
font-weight: 700;
line-height: 1;
padding: 14px 15px;
border-radius: 5px 5px 0 0;
border-bottom: 1px solid #ddd;
}
}
.media-width(@extremum, @break) when (@extremum = 'max') and (@break = @screen__m) {
.custommenu.navigation {
&.side-custommenu {
display: none;
}
.submenu.level0 {
height: 0;
visibility: hidden;
&.opened {
visibility: visible;
height: auto;
}
}
li.level0 {
&.staticwidth {
> .submenu {
width: auto !important;
}
}
&.fullwidth, &.staticwidth {
.menu-top-block, .menu-right-block, .menu-left-block, .menu-bottom-block {
display: none;
}
}
.menu-thumb-img {
display: none;
}
}
li.ui-menu-item {
position: relative;
> a {
position: relative;
}
> .open-children-toggle {
display: block;
position: absolute;
width: 42px;
height: 42px;
right: 0;
top: 0;
z-index: 1;
cursor: pointer;
}
}
span.cat-label {
top: 50%;
right: 36px;
margin-top: -7px;
position: absolute;
text-transform: uppercase;
font: inherit;
font-size: 9px;
padding: 2px;
border-radius: 2px;
line-height: 1;
color: #fff;
&:before {
content: "";
position: absolute;
width: 3px;
height: 3px;
border: 3px solid transparent;
left: -6px;
bottom: 3px;
}
&.cat-label-label1 {
background-color: #0cc485;
&:before {
border-right-color: #0cc485;
}
}
&.cat-label-label2 {
background-color: #eb2771;
&:before {
border-right-color: #eb2771;
}
}
&.cat-label-label3 {
background-color: #0ae3eb;
&:before {
border-right-color: #0ae3eb;
}
}
}
}
}
\ No newline at end of file
;(function($, window, document, undefined) {
$.fn.CustomMenu = function() {
$(".navigation.custommenu li.classic .submenu, .navigation.custommenu li.staticwidth .submenu, .navigation.custommenu li.classic .subchildmenu .subchildmenu").each(function(){
$(this).css("left","-9999px");
$(this).css("right","auto");
});
$(this).find("li.classic .subchildmenu > li.parent").mouseover(function(){
var popup = $(this).children("ul.subchildmenu");
var w_width = $(window).innerWidth();
if(popup) {
var pos = $(this).offset();
var c_width = $(popup).outerWidth();
if(w_width <= pos.left + $(this).outerWidth() + c_width) {
$(popup).css("left","auto");
$(popup).css("right","100%");
$(popup).css("border-radius","6px 0 6px 6px");
} else {
$(popup).css("left","100%");
$(popup).css("right","auto");
$(popup).css("border-radius","0 6px 6px 6px");
}
}
});
$(this).find("li.staticwidth.parent,li.classic.parent").mouseover(function(){
var popup = $(this).children(".submenu");
var w_width = $(window).innerWidth();
if(popup) {
var pos = $(this).offset();
var c_width = $(popup).outerWidth();
if(w_width <= pos.left + $(this).outerWidth() + c_width) {
$(popup).css("left","auto");
$(popup).css("right","0");
$(popup).css("border-radius","6px 0 6px 6px");
} else {
$(popup).css("left","0");
$(popup).css("right","auto");
$(popup).css("border-radius","0 6px 6px 6px");
}
}
});
$(window).resize(function(){
$(".navigation.custommenu li.classic .submenu, .navigation.custommenu li.staticwidth .submenu, .navigation.custommenu li.classic .subchildmenu .subchildmenu").each(function(){
$(this).css("left","-9999px");
$(this).css("right","auto");
});
});
$(".nav-toggle").click(function(e){
if(!$("html").hasClass("nav-open")) {
$("html").addClass("nav-before-open");
setTimeout(function(){
$("html").addClass("nav-open");
}, 300);
}
else {
$("html").removeClass("nav-open");
setTimeout(function(){
$("html").removeClass("nav-before-open");
}, 300);
}
});
$(".navigation.custommenu li.ui-menu-item > .open-children-toggle").click(function(){
if(!$(this).parent().children(".submenu").hasClass("opened")) {
$(this).parent().children(".submenu").addClass("opened");
$(this).parent().children("a").addClass("ui-state-active");
}
else {
$(this).parent().children(".submenu").removeClass("opened");
$(this).parent().children("a").removeClass("ui-state-active");
}
});
$(".navigation.custommenu .submenu .subchildmenu li.ui-menu-item > .open-children-toggle").click(function() {
if (!$(this).parent().children(".subchildmenu").hasClass("opened")) {
$(this).parent().children(".subchildmenu").addClass("opened");
$(this).parent().children("a").addClass("ui-state-active");
$(this).parent().children(".subchildmenu.opened").show();
} else {
$(this).parent().children(".subchildmenu").removeClass("opened");
$(this).parent().children("a").removeClass("ui-state-active");
$(this).parent().children(".subchildmenu").hide();
}
});
};
})(window.Zepto || window.jQuery, window, document);
\ No newline at end of file
<?php
namespace Rokanthemes\Instagram\Block\Adminhtml\Button;
class Fetchposts extends \Magento\Config\Block\System\Config\Form\Field
{
protected $_indata;
public function __construct(
\Magento\Backend\Block\Template\Context $context,
\Rokanthemes\Instagram\Helper\Data $indata,
array $data = []
) {
$this->_indata = $indata;
parent::__construct($context, $data);
}
protected function _getElementHtml(\Magento\Framework\Data\Form\Element\AbstractElement $element)
{
$buttonBlock = $this->getForm()->getLayout()->createBlock('Magento\Backend\Block\Widget\Button');
$params = [
'store' => $buttonBlock->getRequest()->getParam('store')
];
$url = $this->getUrl("instagram/fetchposts/submitapi", $params);
$data = [
'id' => 'fetchposts' ,
'label' => __('Submit'),
'onclick' => "setLocation('" . $url . "')"
];
$userid = $this->_indata->getConfig('instagramsection/instagramgroup/userid');
$accesstoken = $this->_indata->getConfig('instagramsection/instagramgroup/accesstoken');
$username = $this->_indata->getConfig('instagramsection/instagramgroup/username');
if($userid == '' || $accesstoken == '' || $username == ''){
$data['disabled'] = 'disabled';
}
$html = $buttonBlock->setData($data)->toHtml();
return $html;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\Instagram\Block;
use Magento\Framework\View\Element\Template;
class Instagram extends Template {
protected function _prepareLayout() {
parent::_prepareLayout();
$this->pageConfig->getTitle()->set(__('Instagram'));
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\Instagram\Block\Widget;
use Magento\Framework\View\Element\Template;
use Magento\Widget\Block\BlockInterface;
class Instagram extends Template implements BlockInterface
{
protected $_instagrampostFactory;
protected $_storeManager;
public function __construct(
\Magento\Framework\View\Element\Template\Context $context,
\Magento\Store\Model\StoreManagerInterface $storeManager,
\Rokanthemes\Instagram\Model\InstagrampostFactory $instagrampostFactory,
array $data = []
) {
$this->_storeManager = $storeManager;
$this->_instagrampostFactory = $instagrampostFactory;
parent::__construct($context, $data);
$this->setTemplate('widget/instagram.phtml');
}
public function getStoreId()
{
return $this->_storeManager->getStore()->getId();
}
public function getInstagramPostByStoreView()
{
$store_id = $this->getStoreId();
$post_in = $this->_instagrampostFactory->create();
$collection = $post_in->getCollection()->addFieldToFilter('store',['eq' => $store_id]);
if($collection->count() <= 0){
$collection_default = $post_in->getCollection()->addFieldToFilter('store',['eq' => 0]);
return $collection_default;
}
return $collection;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\Instagram\Controller\Adminhtml\Fetchposts;
use Magento\Framework\App\Filesystem\DirectoryList;
class Submitapi extends \Magento\Backend\App\Action
{
protected $_instagrampostFactory;
protected $_resourceConnection;
protected $_indata;
protected $_filesystem;
public function __construct(
\Rokanthemes\Instagram\Model\InstagrampostFactory $instagrampostFactory,
\Magento\Framework\App\ResourceConnection $resourceConnection,
\Rokanthemes\Instagram\Helper\Data $indata,
\Magento\Framework\Filesystem $filesystem,
\Magento\Backend\App\Action\Context $context
) {
$this->_instagrampostFactory = $instagrampostFactory;
$this->_indata = $indata;
$this->_resourceConnection = $resourceConnection;
$this->_filesystem = $filesystem;
parent::__construct($context);
}
public function execute()
{
$store = $this->getRequest()->getParam('store') ? $this->getRequest()->getParam('store') : 0;
$connection = $this->_resourceConnection->getConnection();
$rokanthemes_instagram = $this->_resourceConnection->getTableName('rokanthemes_instagram');
$userid = $this->_indata->getConfig('instagramsection/instagramgroup/userid', $store);
$accesstoken = $this->_indata->getConfig('instagramsection/instagramgroup/accesstoken', $store);
$username = $this->_indata->getConfig('instagramsection/instagramgroup/username', $store);
$limit = ($this->_indata->getConfig('instagramsection/instagramgroup/limit', $store)) ? $this->_indata->getConfig('instagramsection/instagramgroup/limit', $store) : 10;
if($userid == '' || $accesstoken == '' || $username == ''){
$this->messageManager->addError(__('Error! Please enter User ID, Access Token, User Name Instagram.'));
$this->_redirect('adminhtml/system_config/edit/section/instagramsection');
return;
}
$header = [];
$header[] = 'Content-length: 0';
$header[] = 'Content-type: application/json; charset=utf-8';
$verify_url = 'https://graph.instagram.com/'.$userid.'/media';
$ch_verify = curl_init( $verify_url . '?fields=media_url,thumbnail_url,caption,media_type,username,permalink&limit='.$limit.'&access_token='.$accesstoken);
curl_setopt( $ch_verify, CURLOPT_HTTPHEADER, $header );
curl_setopt( $ch_verify, CURLOPT_SSL_VERIFYPEER, false );
curl_setopt( $ch_verify, CURLOPT_RETURNTRANSFER, 1 );
curl_setopt( $ch_verify, CURLOPT_CONNECTTIMEOUT, 5 );
curl_setopt( $ch_verify, CURLOPT_USERAGENT, 'Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.13) Gecko/20080311 Firefox/2.0.0.13');
$cinit_verify_data = curl_exec( $ch_verify );
curl_close( $ch_verify );
$result = json_decode($cinit_verify_data, true);
$mediapath = $this->_filesystem->getDirectoryRead(DirectoryList::MEDIA)->getAbsolutePath().'instagram';
if(!is_dir($mediapath)){
mkdir($mediapath);
}
if(isset($result['error']['message'])){
$this->messageManager->addError($result['error']['message']);
$this->_redirect('adminhtml/system_config/edit/section/instagramsection');
return;
}
if(isset($result['data']) && is_array($result['data']) && !empty($result['data'])){
$connection->delete(
$rokanthemes_instagram,
['store = ?' => $store]
);
foreach ($result['data'] as $key_d => $val_d) {
if(isset($val_d['media_type']) && $val_d['media_type'] == 'IMAGE'){
$instagrampost = $this->_instagrampostFactory->create();
if(isset($val_d['media_url'])){
$instagrampost->setMediaUrl($val_d['media_url']);
$img = $val_d['id'].'_'.rand().'.jpg';
$local_media_url = $mediapath.'/'.$img;
file_put_contents($local_media_url, file_get_contents($val_d['media_url']));
$instagrampost->setLocalMediaUrl('instagram/'.$img);
}
if(isset($val_d['username'])){
$instagrampost->setUsername($val_d['username']);
}
if(isset($val_d['permalink'])){
$instagrampost->setPermalink($val_d['permalink']);
}
if(isset($val_d['id'])){
$instagrampost->setIdInstagram($val_d['id']);
}
if(isset($val_d['caption'])){
$instagrampost->setCaption($val_d['caption']);
}
$instagrampost->setStore($store);
$instagrampost->save();
}
}
$this->messageManager->addSuccess(__('Fetch Posts Via API Successfully.'));
$this->_redirect('adminhtml/system_config/edit/section/instagramsection');
return;
}
else{
$this->messageManager->addError(__('Error! Please Try Again.'));
$this->_redirect('adminhtml/system_config/edit/section/instagramsection');
return;
}
$this->messageManager->addSuccess(__('You saved the configuration.'));
$this->_redirect('adminhtml/system_config/edit/section/instagramsection');
}
}
?>
\ No newline at end of file
<?php
namespace Rokanthemes\Instagram\Controller\Index;
use Magento\Framework\App\RequestInterface;
class Index extends \Magento\Framework\App\Action\Action
{
public function execute() {
$this->_view->loadLayout();
$this->_view->getLayout()->initMessages();
$this->_view->renderLayout();
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\Instagram\Helper;
use Magento\Framework\UrlInterface;
class Data extends \Magento\Framework\App\Helper\AbstractHelper
{
public function getConfig($key, $storeId = null)
{
$result = $this->scopeConfig->getValue($key, \Magento\Store\Model\ScopeInterface::SCOPE_STORE, $storeId);
return $result;
}
public function getMediaPath() {
return $this->_urlBuilder->getBaseUrl(['_type' => UrlInterface::URL_TYPE_MEDIA]);
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\Instagram\Model;
class Instagrampost extends \Magento\Framework\Model\AbstractModel implements \Magento\Framework\DataObject\IdentityInterface
{
const CACHE_TAG = 'rokanthemes_instagram_post';
protected $_cacheTag = 'rokanthemes_instagram_post';
protected $_eventPrefix = 'rokanthemes_instagram_post';
protected function _construct()
{
$this->_init('Rokanthemes\Instagram\Model\ResourceModel\Instagrampost');
}
public function getIdentities()
{
return [self::CACHE_TAG . '_' . $this->getId()];
}
public function getDefaultValues()
{
$values = [];
return $values;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\Instagram\Model\ResourceModel;
class Instagrampost extends \Magento\Framework\Model\ResourceModel\Db\AbstractDb
{
public function __construct(
\Magento\Framework\Model\ResourceModel\Db\Context $context
)
{
parent::__construct($context);
}
protected function _construct()
{
$this->_init('rokanthemes_instagram', 'id');
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\Instagram\Model\ResourceModel\Instagrampost;
class Collection extends \Magento\Framework\Model\ResourceModel\Db\Collection\AbstractCollection
{
protected $_idFieldName = 'id';
protected $_eventPrefix = 'rokanthemes_instagram_post_collection';
protected $_eventObject = 'instagram_post_collection';
/**
* Define resource model
*
* @return void
*/
protected function _construct()
{
$this->_init('Rokanthemes\Instagram\Model\Instagrampost', 'Rokanthemes\Instagram\Model\ResourceModel\Instagrampost');
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\Instagram\Model\Source;
class Resolution implements \Magento\Framework\Option\ArrayInterface
{
protected $_options;
public function toOptionArray() {
$this->_options = [
['label' => '150px x 150px', 'value' => 'thumbnail'],
['label' => '306px x 306px', 'value' => 'low_resolution'],
['label' => '612px x 612px', 'value' => 'standard_resolution'],
];
return $this->_options;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\Instagram\Setup;
use Magento\Framework\Setup\InstallDataInterface;
use Magento\Framework\Setup\ModuleContextInterface;
use Magento\Framework\Setup\ModuleDataSetupInterface;
use Magento\Eav\Setup\EavSetupFactory;
use Magento\Eav\Setup\EavSetup;
/**
* @codeCoverageIgnore
*/
class InstallData implements InstallDataInterface{
/**
* {@inheritdoc}
*/
/**
* EAV setup factory
*
* @var EavSetupFactory
*/
private $eavSetupFactory;
/**
* Init
*
* @param EavSetupFactory $eavSetupFactory
*/
public function __construct(EavSetupFactory $eavSetupFactory)
{
$this->eavSetupFactory = $eavSetupFactory;
}
public function install(ModuleDataSetupInterface $setup, ModuleContextInterface $context)
{
/** @var EavSetup $eavSetup */
$eavSetup = $this->eavSetupFactory->create(['setup' => $setup]);
$installer = $setup;
$installer->startSetup();
$installer->getConnection()->dropTable($installer->getTable('rokanthemes_instagram'));
$table = $installer->getConnection()
->newTable($installer->getTable('rokanthemes_instagram'))
->addColumn(
'id',
\Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
10,
['identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true],
'ID'
)
->addColumn(
'media_url',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
null,
['nullable' => false],
'media_url'
)
->addColumn(
'local_media_url',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
null,
['nullable' => false],
'local_media_url'
)
->addColumn(
'id_instagram',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => false, 'default' => ''],
'id_instagram'
)
->addColumn(
'username',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => false, 'default' => ''],
'username'
)
->addColumn(
'permalink',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => false, 'default' => ''],
'permalink'
)
->addColumn(
'caption',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
null,
['nullable' => true],
'Caption'
)
->addColumn(
'store',
\Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
10,
['nullable' => true],
'Store'
)
->setComment('Instagram');
$installer->getConnection()->createTable($table);
$installer->endSetup();
}
}
<?php
namespace Rokanthemes\Instagram\Setup;
use Magento\Framework\Setup\UpgradeSchemaInterface;
use Magento\Framework\Setup\ModuleContextInterface;
use Magento\Framework\Setup\SchemaSetupInterface;
class UpgradeSchema implements UpgradeSchemaInterface
{
public function upgrade(SchemaSetupInterface $setup, ModuleContextInterface $context)
{
$installer = $setup;
$setup->startSetup();
if (version_compare($context->getVersion(), '2.4.2', '<')) {
$installer->getConnection()->dropTable($installer->getTable('rokanthemes_instagram'));
$table = $installer->getConnection()
->newTable($installer->getTable('rokanthemes_instagram'))
->addColumn(
'id',
\Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
10,
['identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true],
'ID'
)
->addColumn(
'media_url',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
null,
['nullable' => false],
'media_url'
)
->addColumn(
'local_media_url',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
null,
['nullable' => false],
'local_media_url'
)
->addColumn(
'id_instagram',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => false, 'default' => ''],
'id_instagram'
)
->addColumn(
'username',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => false, 'default' => ''],
'username'
)
->addColumn(
'permalink',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => false, 'default' => ''],
'permalink'
)
->addColumn(
'caption',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
null,
['nullable' => true],
'Caption'
)
->addColumn(
'store',
\Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
10,
['nullable' => true],
'Store'
)
->setComment('Instagram');
$installer->getConnection()->createTable($table);
}
$setup->endSetup();
}
}
{
"name": "rokanthemes/module-instagram",
"description": "N/A",
"require": {
"php": "~7.1.3||~7.2.0",
"rokanthemes/module-rokanbase": "2.3.*"
},
"type": "magento2-module",
"license": [
"OSL-3.0",
"AFL-3.0"
],
"autoload": {
"files": [
"registration.php"
],
"psr-4": {
"Rokanthemes\\Themeoption\\": ""
}
},
"version": "2.4.2"
}
\ No newline at end of file
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../lib/internal/Magento/Framework/Acl/etc/acl.xsd">
<acl>
<resources>
<resource id="Magento_Backend::admin">
<resource id="Magento_Backend::stores">
<resource id="Magento_Backend::stores_settings">
<resource id="Magento_Config::config">
<resource id="Rokanthemes_Instagram::instagram_config" title="Instagram"/>
</resource>
</resource>
</resource>
</resource>
</resources>
</acl>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../Magento/Backend/etc/menu.xsd">
<menu>
<add id="Rokanthemes_Instagram::instagram_config" title="Instagram" module="Rokanthemes_Instagram" sortOrder="100" parent="Rokanthemes_RokanBase::rokanbase_setting" action="adminhtml/system_config/edit/section/instagramsection" resource="Rokanthemes_Instagram::instagram_config"/>
</menu>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:App/etc/routes.xsd">
<router id="admin">
<route id="instagram" frontName="instagram">
<module name="Rokanthemes_Instagram" before="Magento_Backend" />
</route>
</router>
</config>
\ No newline at end of file
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../Config/etc/system_file.xsd">
<system>
<section id="instagramsection" translate="label" type="text" sortOrder="90" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Instagram</label>
<tab>rokanthemes</tab>
<resource>Rokanthemes_Instagram::instagram_config</resource>
<group id="instagramgroup" translate="label" type="select" sortOrder="15" showInDefault="1" showInWebsite="1" showInStore="1">
<label>General</label>
<field id="active" translate="label" type="select" sortOrder="5" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Enable </label>
<source_model>Magento\Config\Model\Config\Source\Yesno</source_model>
<comment>Select Yes to enable module on frontend.</comment>
</field>
<field id="title" translate="label comment" type="textarea" sortOrder="6" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Title:</label>
<comment>Block Title</comment>
</field>
<field id="userid" translate="label comment" type="text" sortOrder="10" showInDefault="1" showInWebsite="1" showInStore="1">
<label>User Id</label>
<comment><![CDATA[set User Id]]></comment>
<depends>
<field id="active">1</field>
</depends>
<validate>required-entry</validate>
</field>
<field id="accesstoken" translate="label comment" type="text" sortOrder="15" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Access Token</label>
<comment><![CDATA[set Instagram Access Token]]></comment>
<depends>
<field id="active">1</field>
</depends>
<validate>required-entry</validate>
</field>
<field id="username" translate="label comment" type="text" sortOrder="25" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Username</label>
<comment><![CDATA[set Instagram Username]]></comment>
<depends>
<field id="active">1</field>
</depends>
<validate>required-entry</validate>
</field>
<field id="limit" translate="label comment" type="text" sortOrder="35" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Number of Photos</label>
<comment><![CDATA[Number of photos from Instagram API]]></comment>
<depends>
<field id="active">1</field>
</depends>
<validate>required-entry</validate>
</field>
<field id="fetch_posts" translate="label comment" type="button" sortOrder="50" showInDefault="1" showInWebsite="0" showInStore="1">
<label>Fetch Posts</label>
<frontend_model>Rokanthemes\Instagram\Block\Adminhtml\Button\Fetchposts</frontend_model>
<comment><![CDATA[Fetch Posts from Instagram API. Please enter User ID, Access Token, User Name Instagram > click Save Config before Submit]]></comment>
<depends>
<field id="active">1</field>
</depends>
</field>
</group>
</section>
</system>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Store:etc/config.xsd">
<default>
<instagramsection>
<instagramgroup>
<active>0</active>
<userid></userid>
<accesstoken></accesstoken>
<selectimageresolution>0</selectimageresolution>
</instagramgroup>
</instagramsection>
</default>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../lib/internal/Magento/Framework/App/etc/routes.xsd">
<router id="standard">
<route id="instagram" frontName="instagram">
<module name="Rokanthemes_Instagram" />
</route>
</router>
</config>
\ No newline at end of file
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../lib/internal/Magento/Framework/Module/etc/module.xsd">
<module name="Rokanthemes_Instagram" setup_version="2.4.2"/>
</config>
<?xml version="1.0" encoding="UTF-8"?>
<widgets xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Widget:etc/widget.xsd">
<widget id="instagramwidget" class="Rokanthemes\Instagram\Block\Widget\Instagram">
<label translate="true">Instagram widget</label>
<description>Instagram widget</description>
<parameters>
<parameter name="title" xsi:type="text" visible="true" required="false" sort_order="10">
<label translate="true">Title</label>
</parameter>
<parameter name="description" xsi:type="text" visible="true" required="false" sort_order="20">
<label translate="true">Description</label>
</parameter>
<parameter name="image_format" xsi:type="select" required="false" visible="true" sort_order="60">
<label translate="true">Image format</label>
<options>
<option name="square" value="square" selected="true">
<label translate="true">Square</label>
</option>
<option name="circle" value="circle">
<label translate="true">Circle</label>
</option>
</options>
</parameter>
<parameter name="show_captions" xsi:type="select" required="false" visible="true" sort_order="70">
<label>Show captions</label>
<options>
<option name="no" value="no" selected="true">
<label translate="true">No</label>
</option>
<option name="yes" value="yes">
<label translate="true">Yes</label>
</option>
</options>
</parameter>
<parameter name="show_instagram_icon" xsi:type="select" required="false" visible="true" sort_order="75">
<label>Show Instagram icon</label>
<description translate="true">Instagram icon will show if you disabled Instagram caption</description>
<options>
<option name="no" value="no" selected="true">
<label translate="true">No</label>
</option>
<option name="yes" value="yes">
<label translate="true">Yes</label>
</option>
</options>
</parameter>
<parameter name="image_resolution" xsi:type="select" required="false" visible="true" sort_order="80">
<label>Image resolution</label>
<options>
<option name="original" value="original" selected="true">
<label translate="true">Original images</label>
</option>
<option name="small" value="small">
<label translate="true">Small (80x80)</label>
</option>
<option name="thumbnail" value="thumbnail">
<label translate="true">Thumbnail (150x150)</label>
</option>
<option name="medium" value="medium">
<label translate="true">Medium (320x320)</label>
</option>
<option name="large" value="large">
<label translate="true">Large (640x640)</label>
</option>
</options>
</parameter>
<parameter name="rows" xsi:type="select" required="true" visible="true" sort_order="90">
<label translate="true">Rows</label>
<options>
<option name="default" value="1" selected="true">
<label translate="true">1 Row</label>
</option>
<option name="item2" value="2">
<label translate="true">2 Rows</label>
</option>
<option name="item3" value="3">
<label translate="true">3 Rows</label>
</option>
<option name="item4" value="4">
<label translate="true">4 Rows</label>
</option>
<option name="item5" value="5">
<label translate="true">5 Rows</label>
</option>
</options>
</parameter>
<parameter name="next_back" xsi:type="select" required="true" visible="true" sort_order="100" source_model="Magento\Config\Model\Config\Source\Yesno">
<label translate="true">Show Next/Back control</label>
</parameter>
<parameter name="owl_dots" xsi:type="select" required="false" visible="true" sort_order="130" source_model="Magento\Config\Model\Config\Source\Yesno">
<label translate="true">Owl Dots</label>
</parameter>
<parameter name="owl_item_desktop" xsi:type="text" required="true" visible="true" sort_order="150">
<label translate="true">Owl Items On Big Desktop</label>
<description translate="true">Big desktop: Over 1440 pixels</description>
<value>3</value>
</parameter>
<parameter name="owl_item_default" xsi:type="text" required="true" visible="true" sort_order="160">
<label translate="true">Owl Items Desktop</label>
<description translate="true">Desktop: 1200px - 1439px</description>
<value>3</value>
</parameter>
<parameter name="owl_item_small_desktop" xsi:type="text" required="true" visible="true" sort_order="190">
<label translate="true">Owl Items On Desktop Small</label>
<description translate="true">Desktop Small: 1024px - 1199px</description>
<value>3</value>
</parameter>
<parameter name="owl_item_big_tablet" xsi:type="text" required="true" visible="true" sort_order="200">
<label translate="true">Owl Items On Big Tablet</label>
<description translate="true">Big Tablet: 992px - 1023px</description>
<value>3</value>
</parameter>
<parameter name="owl_item_tablet" xsi:type="text" required="true" visible="true" sort_order="210">
<label translate="true">Owl Items On Tablet</label>
<description translate="true">Tablet: 768px - 991px</description>
<value>3</value>
</parameter>
<parameter name="owl_item_small_tablet" xsi:type="text" required="true" visible="true" sort_order="220">
<label translate="true">Owl Items On Small Tablet</label>
<description translate="true">Tablet Small: 576px - 767px</description>
<value>3</value>
</parameter>
<parameter name="owl_item_mobile" xsi:type="text" required="true" visible="true" sort_order="230">
<label translate="true">Owl Items On Mobile</label>
<description translate="true"> Mobile: Under 575px</description>
<value>3</value>
</parameter>
<parameter name="owl_margin" xsi:type="text" required="false" visible="true" sort_order="240">
<label translate="true">Owl Margin</label>
</parameter>
</parameters>
</widget>
</widgets>
\ No newline at end of file
<?php
\Magento\Framework\Component\ComponentRegistrar::register(
\Magento\Framework\Component\ComponentRegistrar::MODULE,
'Rokanthemes_Instagram',
__DIR__
);
\ No newline at end of file
<?xml version="1.0"?>
<!--
/**
* Rokanthemes Infotech
* Rokanthemes Instagram Extension
*
* @category Rokanthemes
* @package Rokanthemes_Instagram
* @copyright Copyright © 2006-2016 Rokanthemes (https://www.rokanthemesinfotech.com)
* @license https://www.rokanthemesinfotech.com/magento-extension-license/
*/
-->
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" layout="2columns-right" xsi:noNamespaceSchemaLocation="../../../../../../../lib/internal/Magento/Framework/View/Layout/etc/page_configuration.xsd">
<head>
<css src="Rokanthemes_Instagram::css/instagram.css"/>
</head>
</page>
<?php
$helper = $this->helper('Rokanthemes\Instagram\Helper\Data');
$owl_item_default = $block->getData('owl_item_default');
$owl_item_desktop = $block->getData('owl_item_desktop');
$owl_item_small_desktop = $block->getData('owl_item_small_desktop');
$owl_item_big_tablet = $block->getData('owl_item_big_tablet');
$owl_item_tablet = $block->getData('owl_item_tablet');
$owl_item_small_tablet = $block->getData('owl_item_small_tablet');
$owl_item_mobile = $block->getData('owl_item_mobile');
$rows = $block->getData('rows');
$owl_margin = $this->getData('owl_margin');
$next_back = (1 == $this->getData('next_back')) ? 'true' : 'false';
$owl_dots = (1 == $this->getData('owl_dots')) ? 'true' : 'false';
if($helper->getConfig('instagramsection/instagramgroup/active')){
$collections = $block->getInstagramPostByStoreView();
?>
<div class="section container-rokan-instagram rokantheme-instagram">
<!--
<div class="rokan-title header-rokan-instagram">
<?php //if($block->getData('title')): ?>
<h3 class="module-title instagram-title"><?php //$block->escapeHtml($block->getData('title')) ?></h3>
<?php //endif; ?>
<?php //if($block->getData('description')): ?>
<p class="rokan-description instagram-short-des"><?php //$block->escapeHtml($block->getData('description')) ?></p>
<?php //endif; ?>
</div>
-->
<?php if($collections->count() > 0){ ?>
<div class="content-images-rokan-instagram">
<div class="owl">
<?php
$i=0;
foreach ($collections as $val_co) {
if($i %$rows == 0){
echo '<div class="item-row">';
}
$i ++;
?>
<div class="intagram-item">
<a href="<?= $val_co->getPermalink() ;?>" target="_blank" class="<?= $block->getData('image_format') ?> <?php if($block->getData('show_captions') == 'yes'){ ?>has-caption<?php } ?> <?php if($block->getData('show_instagram_icon') == 'yes'){ ?>has-intagram-icon<?php } ?>">
<figure>
<div>
<img alt="<?= $val_co->getIdInstagram() ;?>" src="<?= $val_co->getMediaUrl() ;?>">
</div>
<?php if($block->getData('show_captions') == 'yes' && $val_co->getCaption()){ ?>
<figcaption><?= $val_co->getCaption() ?></figcaption>
<?php } ?>
</figure>
</a>
</div>
<?php if($i %$rows == 0) echo "</div>"; ?>
<?php } ?>
<?php if($i %$rows != 0) echo "</div>"; ?>
</ul>
</div>
<?php }else{ ?>
<div class="instagram-connect-error">
<p><strong><?php echo __('Error: No connected account.');?></strong></p>
<p><?php echo __('Please go to the admin > Rokanthemes > Configuration > Instagram: Settings page to connect an account.');?></p>
</div>
<?php } ?>
</div>
<?php } ?>
<script type="text/javascript">
require([
'jquery',
'mage/mage',
'rokanthemes/owl'
], function ($) {
'use strict';
jQuery(".content-images-rokan-instagram .owl").owlCarousel({
lazyLoad: false,
autoPlay : false,
items : <?php echo $owl_item_default; ?>,
itemsDesktop : [1199,<?php echo $owl_item_desktop; ?>],
itemsDesktopSmall : [991,<?php echo $owl_item_small_desktop; ?>],
itemsTablet: [768,<?php echo $owl_item_tablet; ?>],
itemsMobile : [479,<?php echo $owl_item_mobile; ?>],
slideSpeed : 500,
paginationSpeed : 500,
rewindSpeed : 500,
navigation : <?php if($next_back) echo 'true'; else echo 'false'; ?>,
stopOnHover : true,
pagination :false,
scrollPerPage:false,
});
});
</script>
\ No newline at end of file
.instangram-feed {
display: inline-block;
position: relative;
}
.instagram-image-name {
bottom: 5px;
left: 0;
position: absolute;
text-align: center;
width: 100%;
z-index: 1;
background-color: rgba(0,0,0,0.7);
color: #fff;
padding: 20px 0;
opacity: 0;
height: 0;
}
.instangram-feed:hover .instagram-image-name {
opacity: 1;
height: auto;
transition-duration: 0.5s;
transition-timing-function: ease-in;
transition-delay: 0s;
}
// Instagram module
// Copyright by Youngly - BlueskyTechco
// ________________________________________
// Variables
// ________________________________________
@intagram-caption-color: @color-white;
@intagram-caption-limited-line: 3;
@intagram-caption-font-size: @font-size__base;
@intagram-caption-font-style: false;
@intagram-caption-text-transform: false;
@intagram-caption-text-postion: absolute;
// Icons
// ________________________________________
@intagram_icon_font: "Font Awesome 5 Brands";
@intagram-icon: "\f16d";
@intagram-icon_font-weight: 400;
@_icon_intagram_font_size: 36px;
@_icon_intagram_color: @color-white;
@intagram-overlay_bg: fade(#000, 30%);
@item-row-margin: 2rem;
// Intagram icon
.icon-font-intgram(){
.lib-css(content, @intagram-icon);
.lib-css(color, @_icon_intagram_color);
.lib-css(font-size, @_icon_intagram_font_size);
.lib-css(font-family, @intagram_icon_font);
.lib-css(font-weight, @intagram-icon_font-weight);
}
// Hover effect
@hover_zoom: true;
@hover_transform: scale(1.1);
.lib-hover-intagram-effect(
@_hover_zoom: @hover_zoom
) when (@_hover_zoom = true) {
.lib-css(transform, @hover_transform, 1);
}
& when (@media-common = true) {
.rokantheme-instagram{
.item-row{
.intagram-item{
&:not(:last-of-type){
.lib-css(margin-bottom, @item-row-margin);
}
}
}
.intagram-item{
a{
display: block;
overflow: hidden;
img{
.lib-css(transition, 0.4s, 1);
}
&:hover{
img{
.lib-hover-intagram-effect();
}
}
&.circle{
@border-radius: 50%;
.lib-css(border-radius, @border-radius, 1);
img{
@border-radius: 50%;
.lib-css(border-radius, @border-radius, 1);
}
}
&.has-intagram-icon{
&:not(.has-caption){
position: relative;
&:before{
.icon-font-intgram();
position: absolute;
left: 50%;
top: 50%;
@transform: translate(-50%, -50%);
.lib-css(transform, @transform, 1);
z-index: 2;
opacity: 0;
visibility: hidden;
.lib-css(transition, 0.4s, 1);
}
&:hover{
&:before{
opacity: 1;
visibility: visible;
}
}
}
}
&.has-intagram-icon,
&.has-caption{
&:after{
content: '';
position: absolute;
left: 0;
right: 0;
top: 0;
bottom: 0;
z-index: 1;
.lib-css(background-color, @intagram-overlay_bg);
opacity: 0;
visibility: hidden;
.lib-css(transition, 0.4s, 1);
}
&:hover{
&:after{
opacity: 1;
visibility: visible;
}
}
&.circle{
&:after{
@border-radius: 50%;
.lib-css(border-radius, @border-radius, 1);
}
}
}
&.has-caption{
figcaption{
.lib-css(color, @intagram-caption-color);
.lib-css(font-size, @intagram-caption-font-size);
.lib-css(font-style, @intagram-caption-font-style);
.lib-css(text-transform, @intagram-caption-text-transform);
display: -webkit-box;
-webkit-box-orient: vertical;
overflow: hidden;
text-overflow: ellipsis;
.lib-css(-webkit-line-clamp, @intagram-caption-limited-line);
.lib-css(position, @intagram-caption-text-postion);
top: 50%;
left: 50%;
width: 100%;
@transform: translate(-50%, -50%);
.lib-css(transform, @transform, 1);
padding: 0 10%;
text-align: center;
z-index: 2;
}
&:after{
opacity: 1;
visibility: visible;
}
}
}
}
// Error
.instagram-connect-error{
text-align: center;
padding: 25px 15px;
background-color: #f8d7da;
border-color: #f5c6cb;
p{
margin-bottom: 0;
strong{
display: block;
margin-bottom: 8px;
}
}
}
}
}
\ No newline at end of file
<?php
/**
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\QuickView\Controller;
use Magento\Catalog\Model\Product as CatalogProduct;
use Magento\Framework\App\RequestInterface;
use Magento\Framework\Exception\NoSuchEntityException;
use Magento\Review\Model\Review;
/**
* Review controller
*
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
*/
abstract class Product extends \Magento\Framework\App\Action\Action
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $coreRegistry = null;
/**
* Customer session model
*
* @var \Magento\Customer\Model\Session
*/
protected $customerSession;
/**
* Generic session
*
* @var \Magento\Framework\Session\Generic
*/
protected $reviewSession;
/**
* Catalog catgory model
*
* @var \Magento\Catalog\Api\CategoryRepositoryInterface
*/
protected $categoryRepository;
/**
* Logger
*
* @var \Psr\Log\LoggerInterface
*/
protected $logger;
/**
* Catalog product model
*
* @var \Magento\Catalog\Api\ProductRepositoryInterface
*/
protected $productRepository;
/**
* Review model
*
* @var \Magento\Review\Model\ReviewFactory
*/
protected $reviewFactory;
/**
* Rating model
*
* @var \Magento\Review\Model\RatingFactory
*/
protected $ratingFactory;
/**
* Catalog design model
*
* @var \Magento\Catalog\Model\Design
*/
protected $catalogDesign;
/**
* Core model store manager interface
*
* @var \Magento\Store\Model\StoreManagerInterface
*/
protected $storeManager;
/**
* Core form key validator
*
* @var \Magento\Framework\Data\Form\FormKey\Validator
*/
protected $formKeyValidator;
/**
* @param \Magento\Framework\App\Action\Context $context
* @param \Magento\Framework\Registry $coreRegistry
* @param \Magento\Customer\Model\Session $customerSession
* @param \Magento\Catalog\Api\CategoryRepositoryInterface $categoryRepository
* @param \Psr\Log\LoggerInterface $logger
* @param \Magento\Catalog\Api\ProductRepositoryInterface $productRepository
* @param \Magento\Review\Model\ReviewFactory $reviewFactory
* @param \Magento\Review\Model\RatingFactory $ratingFactory
* @param \Magento\Catalog\Model\Design $catalogDesign
* @param \Magento\Framework\Session\Generic $reviewSession
* @param \Magento\Store\Model\StoreManagerInterface $storeManager
* @param \Magento\Framework\Data\Form\FormKey\Validator $formKeyValidator
* @SuppressWarnings(PHPMD.ExcessiveParameterList)
*/
public function __construct(
\Magento\Framework\App\Action\Context $context,
\Magento\Framework\Registry $coreRegistry,
\Magento\Customer\Model\Session $customerSession,
\Magento\Catalog\Api\CategoryRepositoryInterface $categoryRepository,
\Psr\Log\LoggerInterface $logger,
\Magento\Catalog\Api\ProductRepositoryInterface $productRepository,
\Magento\Review\Model\ReviewFactory $reviewFactory,
\Magento\Review\Model\RatingFactory $ratingFactory,
\Magento\Catalog\Model\Design $catalogDesign,
\Magento\Framework\Session\Generic $reviewSession,
\Magento\Store\Model\StoreManagerInterface $storeManager,
\Magento\Framework\Data\Form\FormKey\Validator $formKeyValidator
) {
$this->storeManager = $storeManager;
$this->coreRegistry = $coreRegistry;
$this->customerSession = $customerSession;
$this->reviewSession = $reviewSession;
$this->categoryRepository = $categoryRepository;
$this->logger = $logger;
$this->productRepository = $productRepository;
$this->reviewFactory = $reviewFactory;
$this->ratingFactory = $ratingFactory;
$this->catalogDesign = $catalogDesign;
$this->formKeyValidator = $formKeyValidator;
parent::__construct($context);
}
/**
* Dispatch request
*
* @param RequestInterface $request
* @return \Magento\Framework\App\ResponseInterface
*/
public function dispatch(RequestInterface $request)
{
$allowGuest = $this->_objectManager->get('Magento\Review\Helper\Data')->getIsGuestAllowToWrite();
if (!$request->isDispatched()) {
return parent::dispatch($request);
}
if (!$allowGuest && $request->getActionName() == 'post' && $request->isPost()) {
if (!$this->customerSession->isLoggedIn()) {
$this->_actionFlag->set('', self::FLAG_NO_DISPATCH, true);
$this->customerSession->setBeforeAuthUrl($this->_url->getUrl('*/*/*', ['_current' => true]));
$this->_reviewSession->setFormData(
$request->getPostValue()
)->setRedirectUrl(
$this->_redirect->getRefererUrl()
);
$this->getResponse()->setRedirect(
$this->_objectManager->get('Magento\Customer\Model\Url')->getLoginUrl()
);
}
}
return parent::dispatch($request);
}
/**
* Initialize and check product
*
* @return \Magento\Catalog\Model\Product|bool
*/
protected function initProduct()
{
// $this->_eventManager->dispatch('review_controller_product_init_before', ['controller_action' => $this]);
$categoryId = (int)$this->getRequest()->getParam('category', false);
$productId = (int)$this->getRequest()->getParam('id');
$product = $this->loadProduct($productId);
if (!$product) {
return false;
}
if ($categoryId) {
$category = $this->categoryRepository->get($categoryId);
$this->coreRegistry->register('current_category', $category);
}
try {
//$this->_eventManager->dispatch('review_controller_product_init', ['product' => $product]);
// $this->_eventManager->dispatch(
// 'review_controller_product_init_after',
// ['product' => $product, 'controller_action' => $this]
// );
} catch (\Magento\Framework\Exception\LocalizedException $e) {
$this->logger->critical($e);
return false;
}
return $product;
}
/**
* Load product model with data by passed id.
* Return false if product was not loaded or has incorrect status.
*
* @param int $productId
* @return bool|CatalogProduct
*/
protected function loadProduct($productId)
{
if (!$productId) {
return false;
}
try {
$product = $this->productRepository->getById($productId);
if (!$product->isVisibleInCatalog() || !$product->isVisibleInSiteVisibility()) {
throw new NoSuchEntityException();
}
} catch (NoSuchEntityException $noEntityException) {
return false;
}
$this->coreRegistry->register('current_product', $product);
$this->coreRegistry->register('product', $product);
return $product;
}
}
?>
\ No newline at end of file
<?php
/**
*
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\QuickView\Controller\Product;
use Rokanthemes\QuickView\Controller\Product as ProductController;
use Magento\Framework\Controller\ResultFactory;
class Quickview extends ProductController
{
public function execute()
{
$pr = $this->initProduct();
/** @var \Magento\Framework\View\Result\Layout $resultLayout */
$resultLayout = $this->resultFactory->create(ResultFactory::TYPE_LAYOUT);
$resultLayout->addHandle('catalog_product_view_type_'. $pr->getTypeId());
return $resultLayout;
}
}
<?php
/**
* @Author: zerokool - Do Van Tuan
* @Email: tien.uet.qh2011@gmail.com
* @File Name: Data.php
* @File Path:
* @Date: 2015-04-07 19:26:42
* @Last Modified by: zero
* @Last Modified time: 2015-07-28 08:35:17
*/
namespace Rokanthemes\QuickView\Helper;
class Data extends \Magento\Framework\App\Helper\AbstractHelper {
public function __construct(
\Magento\Framework\App\Helper\Context $context
) {
parent::__construct($context);
}
public function getConfigData($path)
{
$value = $this->scopeConfig->getValue($path, \Magento\Store\Model\ScopeInterface::SCOPE_STORE);
return $value;
}
public function isEnable()
{
return $this->getConfigData('rokanthemes_quickview/general/enabled');
}
}
<?php
/**
* Copyright 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
/**
* Used in creating options for Yes|No config value selection
*
*/
namespace Rokanthemes\QuickView\Model\Gallery;
class Orientation implements \Magento\Framework\Option\ArrayInterface
{
/**
* Options getter
*
* @return array
*/
public function toOptionArray()
{
return [['value' => 'horizontal', 'label' => __('Horizontal')], ['value' => 'vertical', 'label' => __('Vertical')]];
}
/**
* Get options in "key-value" format
*
* @return array
*/
public function toArray()
{
return ['horizontal' => __('Horizontal'), 'vertical' => __('Vertical')];
}
}
{
"name": "rokanthemes/module-QuickView",
"description": "N/A",
"require": {
"php": "~5.5.0|~5.6.0|~7.0.0"
},
"type": "magento2-module",
"version": "1.0.0",
"license": [
"OSL-3.0",
"AFL-3.0"
],
"autoload": {
"files": [ "registration.php" ],
"psr-4": {
"Rokanthemes\\QuickView\\": ""
}
}
}
<?xml version="1.0"?>
<!--
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:Acl/etc/acl.xsd">
<acl>
<resources>
<resource id="Magento_Backend::admin">
<resource id="Rokanthemes_RokanBase::rokanbase" title="Rokanthemes" translate="title" sortOrder="30">
<resource id="Rokanthemes_QuickView::quickview" title="QuickView" translate="title" sortOrder="30">
<resource id="Rokanthemes_QuickView::rokanthemes_quick_view" title="Settings" translate="title" sortOrder="10" />
</resource>
</resource>
</resource>
</resources>
</acl>
</config>
<?xml version="1.0"?>
<!--
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Backend:etc/menu.xsd">
<menu>
<add id="Rokanthemes_QuickView::quickview" title="QuickView" module="Rokanthemes_QuickView" sortOrder="30" parent="Rokanthemes_RokanBase::rokanbase" resource="Rokanthemes_QuickView::quickview"/>
<add id="Rokanthemes_QuickView::rokanthemes_quick_view" title="Settings" module="Rokanthemes_QuickView" sortOrder="10" parent="Rokanthemes_QuickView::quickview" action="adminhtml/system_config/edit/section/rokanthemes_quickview" resource="Rokanthemes_QuickView::rokanthemes_quick_view"/>
</menu>
</config>
<?xml version="1.0"?>
<!--
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../Config/etc/system_file.xsd">
<system>
<section id="rokanthemes_quickview" translate="label" type="text" sortOrder="500" showInDefault="1" showInWebsite="1" showInStore="1">
<class>separator-top</class>
<label>Quick View Setting</label>
<tab>rokanthemes</tab>
<resource>Rokanthemes_QuickView::rokanthemes_quick_view</resource>
<group id="general" translate="label" type="text" sortOrder="10" showInDefault="1" showInWebsite="1" showInStore="1">
<label>General</label>
<field id="enabled" translate="label comment" type="select" sortOrder="0" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Enable</label>
<source_model>Magento\Config\Model\Config\Source\Yesno</source_model>
</field>
</group>
</section>
</system>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../Magento/Store/etc/config.xsd">
<default>
<rokanthemes_quickview>
<general>
<enabled>1</enabled>
<enabledTab>1</enabledTab>
<enabledTagTab>1</enabledTagTab>
<enabledReviewTab>1</enabledReviewTab>
</general>
<main_image>
<image_width>370</image_width>
<image_height>470</image_height>
</main_image>
<moreview>
<enable>1</enable>
<image_width>100</image_width>
<image_height>110</image_height>
<autoplay>0</autoplay>
<orientation>horizontal</orientation>
</moreview>
</rokanthemes_quickview>
</default>
</config>
<?xml version="1.0"?>
<!--
/**
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
</config>
<?xml version="1.0"?>
<!--
/**
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:App/etc/routes.xsd">
<router id="standard">
<route id="quickview" frontName="quickview">
<module name="Rokanthemes_QuickView" />
</route>
</router>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../lib/internal/Magento/Framework/Module/etc/module.xsd">
<module name="Rokanthemes_QuickView" setup_version="1.0.0" />
</config>
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
\Magento\Framework\Component\ComponentRegistrar::register(
\Magento\Framework\Component\ComponentRegistrar::MODULE,
'Rokanthemes_QuickView',
__DIR__
);
<?xml version="1.0"?>
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../lib/internal/Magento/Framework/View/Layout/etc/page_configuration.xsd">
<head>
<link src="Rokanthemes_QuickView::css/rokan_quickview.css"/>
</head>
<referenceContainer name="content">
<block class="Magento\Framework\View\Element\Template" name="quickview" template="Rokanthemes_QuickView::quickview.phtml" />
</referenceContainer>
</page>
<?xml version="1.0"?>
<layout xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/layout_generic.xsd">
<container name="root">
<block class="Magento\Framework\Pricing\Render" name="product.price.render.default">
<arguments>
<argument name="price_render_handle" xsi:type="string">catalog_product_prices</argument>
<argument name="use_link_for_as_low_as" xsi:type="boolean">true</argument>
<!-- set "override" configuration settings here -->
</arguments>
</block>
<container name="product.info.main" htmlTag="div" htmlClass="product-info-main" before="-">
<block class="Magento\Framework\View\Element\FormKey" name="formkey"/>
<container name="product.info.price" label="Product info auxiliary container" htmlTag="div" htmlClass="product-info-price" after="product.info.review">
<block class="Magento\Catalog\Block\Product\View" name="page.main.title.quickview" template="Rokanthemes_QuickView::product/view/title.phtml"/>
<container name="product.info.stock.sku" label="Product auxiliary info" htmlTag="div" htmlClass="product-info-stock-sku">
<container name="product.info.type" before="-"/>
<block class="Magento\Catalog\Block\Product\View\Description" name="product.info.sku" template="product/view/attribute.phtml" after="product.info.type">
<arguments>
<argument name="at_call" xsi:type="string">getSku</argument>
<argument name="at_code" xsi:type="string">sku</argument>
<argument name="css_class" xsi:type="string">sku</argument>
<argument name="at_label" xsi:type="string">default</argument>
<argument name="add_attribute" xsi:type="string">itemprop="sku"</argument>
</arguments>
</block>
</container>
<block class="Magento\Catalog\Block\Product\View" name="product.info.review" template="product/view/review.phtml" after="product.info.stock.sku" />
<block class="Magento\Catalog\Pricing\Render" name="product.price.final" after="product.info.sku">
<arguments>
<argument name="price_render" xsi:type="string">product.price.render.default</argument>
<argument name="price_type_code" xsi:type="string">final_price</argument>
<argument name="zone" xsi:type="string">item_view</argument>
</arguments>
</block>
</container>
<block class="Magento\Catalog\Pricing\Render" name="product.price.tier" after="product.info.price">
<arguments>
<argument name="price_render" xsi:type="string">product.price.render.default</argument>
<argument name="price_type_code" xsi:type="string">tier_price</argument>
<argument name="zone" xsi:type="string">item_view</argument>
</arguments>
</block>
<container name="alert.urls" as="alert_urls" label="Alert Urls" after="product.price.tier"/>
<block class="Magento\Catalog\Block\Product\View" name="product.info" template="Rokanthemes_QuickView::product/view/form_quickview.phtml" after="alert.urls">
<container name="product.info.form.content" as="product_info_form_content">
<block class="Magento\Catalog\Block\Product\View" name="product.info.addtocart" as="addtocart" template="Rokanthemes_QuickView::product/view/addtocart_quickview.phtml"/>
</container>
<block class="Magento\Framework\View\Element\Template" name="product.info.form.options" as="options_container">
<block class="Magento\Catalog\Block\Product\View" name="product.info.options.wrapper" as="product_options_wrapper" template="product/view/options/wrapper.phtml">
<block class="Magento\Catalog\Block\Product\View\Options" name="product.info.options" as="product_options" template="product/view/options.phtml">
<block class="Magento\Catalog\Block\Product\View\Options\Type\DefaultType" as="default" template="product/view/options/type/default.phtml"/>
<block class="Magento\Catalog\Block\Product\View\Options\Type\Text" as="text" template="product/view/options/type/text.phtml"/>
<block class="Magento\Catalog\Block\Product\View\Options\Type\File" as="file" template="product/view/options/type/file.phtml"/>
<block class="Magento\Catalog\Block\Product\View\Options\Type\Select" as="select" template="product/view/options/type/select.phtml"/>
<block class="Magento\Catalog\Block\Product\View\Options\Type\Date" as="date" template="product/view/options/type/date.phtml"/>
</block>
<block class="Magento\Framework\View\Element\Html\Calendar" name="html_calendar" as="html_calendar" template="Magento_Theme::js/calendar.phtml"/>
</block>
<block class="Magento\Catalog\Block\Product\View" name="product.info.options.wrapper.bottom" as="product_options_wrapper_bottom" template="product/view/options/wrapper/bottom.phtml">
<block class="Magento\Catalog\Block\Product\View" name="product.info.addtocart.additional" as="product.info.addtocart" template="product/view/addtocart.phtml"/>
</block>
</block>
</block>
<container name="product.info.extrahint" as="extrahint" label="Product View Extra Hint">
<container name="product.info.social" label="Product social links container" htmlTag="div" htmlClass="product-social-links" after="product.info.overview">
<block class="Magento\Catalog\Block\Product\View" name="product.info.addto" as="addto" template="product/view/addto.phtml"/>
<block class="Magento\Catalog\Block\Product\View" name="product.info.mailto" template="product/view/mailto.phtml"/>
</container>
</container>
<block class="Magento\Catalog\Block\Product\View\Description" name="product.info.overview" template="product/view/attribute.phtml" group="detailed_info" after="product.info.extrahint">
<arguments>
<argument name="at_call" xsi:type="string">getShortDescription</argument>
<argument name="at_code" xsi:type="string">short_description</argument>
<argument name="css_class" xsi:type="string">overview</argument>
<argument name="at_label" translate="true" xsi:type="string">none</argument>
<argument name="title" translate="true" xsi:type="string">Overview</argument>
<argument name="add_attribute" xsi:type="string">itemprop="description"</argument>
</arguments>
</block>
</container>
<container name="product.info.media" htmlTag="div" htmlClass="product media" after="product.info.main">
<block class="Magento\Catalog\Block\Product\View\Gallery" name="product.info.media.image" template="Rokanthemes_QuickView::product/view/gallery.phtml"/>
</container>
<block class="Magento\Catalog\Block\Product\View\Description" name="product.info.details" template="product/view/details.phtml" after="product.info.media">
<block class="Magento\Catalog\Block\Product\View\Description" name="product.info.description" template="product/view/attribute.phtml" group="detailed_info">
<arguments>
<argument name="at_call" xsi:type="string">getDescription</argument>
<argument name="at_code" xsi:type="string">description</argument>
<argument name="css_class" xsi:type="string">description</argument>
<argument name="at_label" xsi:type="string">none</argument>
<argument name="title" translate="true" xsi:type="string">Details</argument>
</arguments>
</block>
<block class="Magento\Catalog\Block\Product\View\Attributes" name="product.attributes" as="additional" template="product/view/attributes.phtml" group="detailed_info">
<arguments>
<argument translate="true" name="title" xsi:type="string">More Information</argument>
</arguments>
</block>
</block>
<block class="Magento\Cookie\Block\RequireCookie" name="require-cookie" template="Magento_Cookie::require_cookie.phtml">
<arguments>
<argument name="triggers" xsi:type="array">
<item name="compareProductLink" xsi:type="string">.action.tocompare</item>
</argument>
</arguments>
</block>
</container>
</layout>
\ No newline at end of file
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
var config = {
"map": {
'*': {
'productQuickview': 'Rokanthemes_QuickView/js/quickview'
},
},
"shim": {
"quickview/cloudzoom": ["jquery"],
"quickview/bxslider": ["jquery"]
},
'paths': {
'quickview/cloudzoom': 'Rokanthemes_QuickView/js/cloud-zoom',
"quickview/bxslider": "Rokanthemes_QuickView/js/jquery.bxslider"
}
};
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
// @codingStandardsIgnoreFile
/** @var $block \Magento\Catalog\Block\Product\View */
?>
<?php $_product = $block->getProduct();
$config_point2 = $this->helper('Rokanthemes\RokanBase\Helper\Data')->getConfigData('setting_categories/categories/point2');
$arr_config_point2 = explode(',', $config_point2);
$qty = 1;
$categories = $_product->getCategoryIds();
if(count($categories) > 0 && count($arr_config_point2) > 0){
foreach($arr_config_point2 as $val1){
if(in_array(trim($val1), $categories)){
$qty = 3;
break;
}
}
}
?>
<?php $buttonTitle = __('Add to cart'); ?>
<?php if ($_product->isSaleable()): ?>
<div class="box-tocart">
<div class="fieldset">
<?php if ($block->shouldRenderQuantity()): ?>
<div class="field qty">
<a class="qty-down-fixed-onclick qty-down" href="#"><i class="fa fa-minus"></i></a>
<div class="control">
<input type="number"
name="qty"
id="qty-quickview"
maxlength="12"
value="<?php /* @escapeNotVerified */ echo $qty * 1 ?>"
title="<?php /* @escapeNotVerified */ echo __('Quantity') ?>" class="input-text qty"
data-validate="<?php echo $block->escapeHtml(json_encode($block->getQuantityValidators())) ?>"
/>
</div>
<a class="qty-up-fixed-onclick qty-up" href="#"><i class="fa fa-plus"></i></a>
</div>
<?php endif; ?>
<div class="actions">
<button type="submit"
title="<?php /* @escapeNotVerified */ echo $buttonTitle ?>"
class="action primary tocart"
id="product-addtocart-button-quickview">
<span><?php /* @escapeNotVerified */ echo $buttonTitle ?></span>
</button>
<?php echo $block->getChildHtml('', true) ?>
</div>
</div>
</div>
<?php endif; ?>
<?php if ($block->isRedirectToCartEnabled()) : ?>
<script type="text/x-magento-init">
{
"#product_addtocart_form_quickview": {
"Magento_Catalog/product/view/validation": {
"radioCheckboxClosest": ".nested"
}
}
}
</script>
<?php else : ?>
<script>
require([
'jquery',
'mage/mage',
'Magento_Catalog/product/view/validation',
'Magento_Catalog/js/catalog-add-to-cart'
], function ($) {
'use strict';
var number_click = <?php echo $qty;?>;
$(".qty-down-fixed-onclick").click(function() {
var val_input = $(this).closest('div.field').find('#qty-quickview').val();
val_input = parseInt(val_input);
if(val_input <= number_click){
val_input = number_click;
}
else{
val_input = val_input - number_click;
}
$('div.field div.control #qty-quickview').val(val_input);
return false;
});
$(".qty-up-fixed-onclick").click(function() {
var val_input = $(this).closest('div.field').find('#qty-quickview').val();
val_input = parseInt(val_input);
val_input = val_input + number_click;
$('div.field div.control #qty-quickview').val(val_input);
return false;
});
$('#product_addtocart_form_quickview').mage('validation', {
radioCheckboxClosest: '.nested',
submitHandler: function (form) {
var widget = $(form).catalogAddToCart({
bindSubmit: false
});
widget.catalogAddToCart('submitForm', $(form));
return false;
}
});
});
</script>
<?php endif; ?>
\ No newline at end of file
<?php
/**
* Copyright © 2013-2017 Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
// @codingStandardsIgnoreFile
/**
* Product view template
*
* @var $block \Magento\Catalog\Block\Product\View
*/
?>
<?php $_helper = $this->helper('Magento\Catalog\Helper\Output'); ?>
<?php $_product = $block->getProduct();
$config_point1 = $this->helper('Rokanthemes\RokanBase\Helper\Data')->getConfigData('setting_categories/categories/point1');
$arr_config_point1 = explode(',', $config_point1);
$show = false;
$categories = $_product->getCategoryIds();
if(count($categories) > 0 && count($arr_config_point1) > 0){
foreach($arr_config_point1 as $val){
if(in_array(trim($val), $categories)){
$show = true;
break;
}
}
}
?>
<?php if($show){?>
<div class="text-description">
<?php echo $block->getLayout()->createBlock('Magento\Cms\Block\Block')->setBlockId('product_view_description_price')->toHtml();?>
</div>
<?php } ?>
<div class="product-add-form">
<form action="<?php /* @escapeNotVerified */ echo $block->getSubmitUrl($_product) ?>" method="post"
id="product_addtocart_form_quickview"<?php if ($_product->getOptions()): ?> enctype="multipart/form-data"<?php endif; ?>>
<input type="hidden" name="product" value="<?php /* @escapeNotVerified */ echo $_product->getId() ?>" />
<input type="hidden" name="selected_configurable_option" value="" />
<input type="hidden" name="related_product" id="related-products-field" value="" />
<?php echo $block->getBlockHtml('formkey')?>
<?php echo $block->getChildHtml('form_top'); ?>
<?php if (!$block->hasOptions()):?>
<?php echo $block->getChildHtml('product_info_form_content'); ?>
<?php else:?>
<?php if ($_product->isSaleable() && $block->getOptionsContainer() == 'container1'):?>
<?php echo $block->getChildChildHtml('options_container') ?>
<?php endif;?>
<?php endif; ?>
<?php if ($_product->isSaleable() && $block->hasOptions() && $block->getOptionsContainer() == 'container2'):?>
<?php echo $block->getChildChildHtml('options_container') ?>
<?php endif;?>
<?php echo $block->getChildHtml('form_bottom'); ?>
</form>
</div>
<script>
require([
'jquery',
'priceBox'
], function($){
if($('.amasty-hide-price-text').length > 0){
$('div.short-action').hide();
$('div.text-description').hide();
}
var dataPriceBoxSelector = '[data-role=priceBox]',
dataProductIdSelector = '[data-product-id=<?php echo $block->escapeHtml($_product->getId())?>]',
priceBoxes = $(dataPriceBoxSelector + dataProductIdSelector);
priceBoxes = priceBoxes.filter(function(index, elem){
return !$(elem).find('.price-from').length;
});
priceBoxes.priceBox({'priceConfig': <?php /* @escapeNotVerified */ echo $block->getJsonConfig() ?>});
});
</script>
<div class="short-action">
<div class="short-content">
<?php echo $block->getLayout()->createBlock('Magento\Cms\Block\Block')->setBlockId('product_view_future_function')->toHtml();?>
</div>
</div>
\ No newline at end of file
<?php
/**
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
// @codingStandardsIgnoreFile
/**
* Product media data template
*
* @var $block \Magento\Catalog\Block\Product\View\Gallery
*/
$images = $block->getGalleryImages();
if(count($images) > 0)
{
$mainImage = $images->getFirstItem();
foreach($images as $image)
{
if($block->isMainImage($image))
{
$mainImage = $image;
break;
}
}
?>
<div class="gallery-placeholder _block-content-loading" data-gallery-role="gallery-placeholder" id="gallery_<?php $block->getProduct()->getId(); ?>" >
<div class="product-slider-wrapper col-md-6">
<div class="main-img-quickview">
<a href="<?php echo $mainImage->getData('large_image_url'); ?>" class="cloud-zoom" rel="transparentImage: 'data:image/gif;base64,R0lGODlhAQABAID/AMDAwAAAACH5BAEAAAAALAAAAAABAAEAAAICRAEAOw==', useWrapper: false, showTitle: false, zoomWidth:'100', adjustY:0, adjustX:0">
<img src="<?php echo $mainImage->getData('medium_image_url'); ?>">
</a>
</div>
<ul class="bxslider">
<?php foreach ($images as $_image) { ?>
<li><img src="<?php echo $_image->getData('small_image_url'); ?>" data-href="<?php echo $_image->getData('large_image_url'); ?>" data-thumb-image="<?php echo $_image->getData('medium_image_url'); ?>"></li>
<?php } ?>
</ul>
</div>
</div>
<?php } ?>
<script>
jQuery(document).ready(function() {
jQuery('#gallery_<?php $block->getProduct()->getId(); ?> .cloud-zoom, #gallery_<?php $block->getProduct()->getId(); ?> .cloud-zoom-gallery').CloudZoom({
adjustX: 0,
adjustY: 0
});
// Horizontal
var horiSlider<?php $block->getProduct()->getId(); ?> = jQuery('#gallery_<?php $block->getProduct()->getId(); ?> .bxslider').bxSlider({
mode: 'horizontal',
auto: false,
autoControls: false,
slideMargin: 9.5,
// CAROUSEL
minSlides: 4,
maxSlides: 4,
moveSlides: 1,
slideWidth: 100,
// PAGER
pager: false,
nextText: "<i class='amz-icon foxy-arrow_right'></i>",
prevText: "<i class='amz-icon foxy-arrow_left'></i>",
onSlideAfter: function() {
var currentImg = horiSlider<?php $block->getProduct()->getId(); ?>.getCurrentSlideElement().children('img');
jQuery('#gallery_<?php $block->getProduct()->getId(); ?> a.cloud-zoom').attr('href', currentImg.attr('data-href'));
jQuery('#gallery_<?php $block->getProduct()->getId(); ?> a.cloud-zoom img').attr('src', currentImg.attr('data-thumb-image'));
jQuery('.cloud-zoom, .cloud-zoom-gallery').CloudZoom();
}
});
});
</script>
<?php
/**
* Copyright © 2013-2017 Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
// @codingStandardsIgnoreFile
/**
* Product view template
*
* @see \Magento\Catalog\Block\Product\View\Description
*/
?>
<?php
$_product = $block->getProduct();
?>
<h1 class="title-quickview-product"><?php echo $_product->getName();?></h1>
<?php
/**
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
// @codingStandardsIgnoreFile
/**
* Product media data template
*
* @var $block \Magento\Catalog\Block\Product\View\Gallery
*/
?>
<script type="text/x-magento-init">
{
".quickview-product [data-role=quickview-button]": {
"productQuickview": {}
}
}
</script>
<script>
require([
'jquery',
'mage/mage',
'quickview/cloudzoom',
'quickview/bxslider'
], function ($) {
});
</script>
#fancybox-buttons {
position: fixed;
left: 0;
width: 100%;
z-index: 8050;
}
#fancybox-buttons.top {
top: 10px;
}
#fancybox-buttons.bottom {
bottom: 10px;
}
#fancybox-buttons ul {
display: block;
width: 166px;
height: 30px;
margin: 0 auto;
padding: 0;
list-style: none;
border: 1px solid #111;
border-radius: 3px;
-webkit-box-shadow: inset 0 0 0 1px rgba(255,255,255,.05);
-moz-box-shadow: inset 0 0 0 1px rgba(255,255,255,.05);
box-shadow: inset 0 0 0 1px rgba(255,255,255,.05);
background: rgb(50,50,50);
background: -moz-linear-gradient(top, rgb(68,68,68) 0%, rgb(52,52,52) 50%, rgb(41,41,41) 50%, rgb(51,51,51) 100%);
background: -webkit-gradient(linear, left top, left bottom, color-stop(0%,rgb(68,68,68)), color-stop(50%,rgb(52,52,52)), color-stop(50%,rgb(41,41,41)), color-stop(100%,rgb(51,51,51)));
background: -webkit-linear-gradient(top, rgb(68,68,68) 0%,rgb(52,52,52) 50%,rgb(41,41,41) 50%,rgb(51,51,51) 100%);
background: -o-linear-gradient(top, rgb(68,68,68) 0%,rgb(52,52,52) 50%,rgb(41,41,41) 50%,rgb(51,51,51) 100%);
background: -ms-linear-gradient(top, rgb(68,68,68) 0%,rgb(52,52,52) 50%,rgb(41,41,41) 50%,rgb(51,51,51) 100%);
background: linear-gradient(top, rgb(68,68,68) 0%,rgb(52,52,52) 50%,rgb(41,41,41) 50%,rgb(51,51,51) 100%);
filter: progid:DXImageTransform.Microsoft.gradient( startColorstr='#444444', endColorstr='#222222',GradientType=0 );
}
#fancybox-buttons ul li {
float: left;
margin: 0;
padding: 0;
}
#fancybox-buttons a {
display: block;
width: 30px;
height: 30px;
text-indent: -9999px;
background-color: transparent;
background-image: url('fancybox_buttons.png');
background-repeat: no-repeat;
outline: none;
opacity: 0.8;
}
#fancybox-buttons a:hover {
opacity: 1;
}
#fancybox-buttons a.btnPrev {
background-position: 5px 0;
}
#fancybox-buttons a.btnNext {
background-position: -33px 0;
border-right: 1px solid #3e3e3e;
}
#fancybox-buttons a.btnPlay {
background-position: 0 -30px;
}
#fancybox-buttons a.btnPlayOn {
background-position: -30px -30px;
}
#fancybox-buttons a.btnToggle {
background-position: 3px -60px;
border-left: 1px solid #111;
border-right: 1px solid #3e3e3e;
width: 35px
}
#fancybox-buttons a.btnToggleOn {
background-position: -27px -60px;
}
#fancybox-buttons a.btnClose {
border-left: 1px solid #111;
width: 35px;
background-position: -56px 0px;
}
#fancybox-buttons a.btnDisabled {
opacity : 0.4;
cursor: default;
}
\ No newline at end of file
/*!
* Buttons helper for fancyBox
* version: 1.0.5 (Mon, 15 Oct 2012)
* @requires fancyBox v2.0 or later
*
* Usage:
* $(".fancybox").fancybox({
* helpers : {
* buttons: {
* position : 'top'
* }
* }
* });
*
*/
(function ($) {
//Shortcut for fancyBox object
var F = $.fancybox;
//Add helper object
F.helpers.buttons = {
defaults : {
skipSingle : false, // disables if gallery contains single image
position : 'top', // 'top' or 'bottom'
tpl : '<div id="fancybox-buttons"><ul><li><a class="btnPrev" title="Previous" href="javascript:;"></a></li><li><a class="btnPlay" title="Start slideshow" href="javascript:;"></a></li><li><a class="btnNext" title="Next" href="javascript:;"></a></li><li><a class="btnToggle" title="Toggle size" href="javascript:;"></a></li><li><a class="btnClose" title="Close" href="javascript:;"></a></li></ul></div>'
},
list : null,
buttons: null,
beforeLoad: function (opts, obj) {
//Remove self if gallery do not have at least two items
if (opts.skipSingle && obj.group.length < 2) {
obj.helpers.buttons = false;
obj.closeBtn = true;
return;
}
//Increase top margin to give space for buttons
obj.margin[ opts.position === 'bottom' ? 2 : 0 ] += 30;
},
onPlayStart: function () {
if (this.buttons) {
this.buttons.play.attr('title', 'Pause slideshow').addClass('btnPlayOn');
}
},
onPlayEnd: function () {
if (this.buttons) {
this.buttons.play.attr('title', 'Start slideshow').removeClass('btnPlayOn');
}
},
afterShow: function (opts, obj) {
var buttons = this.buttons;
if (!buttons) {
this.list = $(opts.tpl).addClass(opts.position).appendTo('body');
buttons = {
prev : this.list.find('.btnPrev').click( F.prev ),
next : this.list.find('.btnNext').click( F.next ),
play : this.list.find('.btnPlay').click( F.play ),
toggle : this.list.find('.btnToggle').click( F.toggle ),
close : this.list.find('.btnClose').click( F.close )
}
}
//Prev
if (obj.index > 0 || obj.loop) {
buttons.prev.removeClass('btnDisabled');
} else {
buttons.prev.addClass('btnDisabled');
}
//Next / Play
if (obj.loop || obj.index < obj.group.length - 1) {
buttons.next.removeClass('btnDisabled');
buttons.play.removeClass('btnDisabled');
} else {
buttons.next.addClass('btnDisabled');
buttons.play.addClass('btnDisabled');
}
this.buttons = buttons;
this.onUpdate(opts, obj);
},
onUpdate: function (opts, obj) {
var toggle;
if (!this.buttons) {
return;
}
toggle = this.buttons.toggle.removeClass('btnDisabled btnToggleOn');
//Size toggle button
if (obj.canShrink) {
toggle.addClass('btnToggleOn');
} else if (!obj.canExpand) {
toggle.addClass('btnDisabled');
}
},
beforeClose: function () {
if (this.list) {
this.list.remove();
}
this.list = null;
this.buttons = null;
}
};
}(jQuery));
/*!
* Media helper for fancyBox
* version: 1.0.6 (Fri, 14 Jun 2013)
* @requires fancyBox v2.0 or later
*
* Usage:
* $(".fancybox").fancybox({
* helpers : {
* media: true
* }
* });
*
* Set custom URL parameters:
* $(".fancybox").fancybox({
* helpers : {
* media: {
* youtube : {
* params : {
* autoplay : 0
* }
* }
* }
* }
* });
*
* Or:
* $(".fancybox").fancybox({,
* helpers : {
* media: true
* },
* youtube : {
* autoplay: 0
* }
* });
*
* Supports:
*
* Youtube
* http://www.youtube.com/watch?v=opj24KnzrWo
* http://www.youtube.com/embed/opj24KnzrWo
* http://youtu.be/opj24KnzrWo
* http://www.youtube-nocookie.com/embed/opj24KnzrWo
* Vimeo
* http://vimeo.com/40648169
* http://vimeo.com/channels/staffpicks/38843628
* http://vimeo.com/groups/surrealism/videos/36516384
* http://player.vimeo.com/video/45074303
* Metacafe
* http://www.metacafe.com/watch/7635964/dr_seuss_the_lorax_movie_trailer/
* http://www.metacafe.com/watch/7635964/
* Dailymotion
* http://www.dailymotion.com/video/xoytqh_dr-seuss-the-lorax-premiere_people
* Twitvid
* http://twitvid.com/QY7MD
* Twitpic
* http://twitpic.com/7p93st
* Instagram
* http://instagr.am/p/IejkuUGxQn/
* http://instagram.com/p/IejkuUGxQn/
* Google maps
* http://maps.google.com/maps?q=Eiffel+Tower,+Avenue+Gustave+Eiffel,+Paris,+France&t=h&z=17
* http://maps.google.com/?ll=48.857995,2.294297&spn=0.007666,0.021136&t=m&z=16
* http://maps.google.com/?ll=48.859463,2.292626&spn=0.000965,0.002642&t=m&z=19&layer=c&cbll=48.859524,2.292532&panoid=YJ0lq28OOy3VT2IqIuVY0g&cbp=12,151.58,,0,-15.56
*/
(function ($) {
"use strict";
//Shortcut for fancyBox object
var F = $.fancybox,
format = function( url, rez, params ) {
params = params || '';
if ( $.type( params ) === "object" ) {
params = $.param(params, true);
}
$.each(rez, function(key, value) {
url = url.replace( '$' + key, value || '' );
});
if (params.length) {
url += ( url.indexOf('?') > 0 ? '&' : '?' ) + params;
}
return url;
};
//Add helper object
F.helpers.media = {
defaults : {
youtube : {
matcher : /(youtube\.com|youtu\.be|youtube-nocookie\.com)\/(watch\?v=|v\/|u\/|embed\/?)?(videoseries\?list=(.*)|[\w-]{11}|\?listType=(.*)&list=(.*)).*/i,
params : {
autoplay : 1,
autohide : 1,
fs : 1,
rel : 0,
hd : 1,
wmode : 'opaque',
enablejsapi : 1
},
type : 'iframe',
url : '//www.youtube.com/embed/$3'
},
vimeo : {
matcher : /(?:vimeo(?:pro)?.com)\/(?:[^\d]+)?(\d+)(?:.*)/,
params : {
autoplay : 1,
hd : 1,
show_title : 1,
show_byline : 1,
show_portrait : 0,
fullscreen : 1
},
type : 'iframe',
url : '//player.vimeo.com/video/$1'
},
metacafe : {
matcher : /metacafe.com\/(?:watch|fplayer)\/([\w\-]{1,10})/,
params : {
autoPlay : 'yes'
},
type : 'swf',
url : function( rez, params, obj ) {
obj.swf.flashVars = 'playerVars=' + $.param( params, true );
return '//www.metacafe.com/fplayer/' + rez[1] + '/.swf';
}
},
dailymotion : {
matcher : /dailymotion.com\/video\/(.*)\/?(.*)/,
params : {
additionalInfos : 0,
autoStart : 1
},
type : 'swf',
url : '//www.dailymotion.com/swf/video/$1'
},
twitvid : {
matcher : /twitvid\.com\/([a-zA-Z0-9_\-\?\=]+)/i,
params : {
autoplay : 0
},
type : 'iframe',
url : '//www.twitvid.com/embed.php?guid=$1'
},
twitpic : {
matcher : /twitpic\.com\/(?!(?:place|photos|events)\/)([a-zA-Z0-9\?\=\-]+)/i,
type : 'image',
url : '//twitpic.com/show/full/$1/'
},
instagram : {
matcher : /(instagr\.am|instagram\.com)\/p\/([a-zA-Z0-9_\-]+)\/?/i,
type : 'image',
url : '//$1/p/$2/media/?size=l'
},
google_maps : {
matcher : /maps\.google\.([a-z]{2,3}(\.[a-z]{2})?)\/(\?ll=|maps\?)(.*)/i,
type : 'iframe',
url : function( rez ) {
return '//maps.google.' + rez[1] + '/' + rez[3] + '' + rez[4] + '&output=' + (rez[4].indexOf('layer=c') > 0 ? 'svembed' : 'embed');
}
}
},
beforeLoad : function(opts, obj) {
var url = obj.href || '',
type = false,
what,
item,
rez,
params;
for (what in opts) {
if (opts.hasOwnProperty(what)) {
item = opts[ what ];
rez = url.match( item.matcher );
if (rez) {
type = item.type;
params = $.extend(true, {}, item.params, obj[ what ] || ($.isPlainObject(opts[ what ]) ? opts[ what ].params : null));
url = $.type( item.url ) === "function" ? item.url.call( this, rez, params, obj ) : format( item.url, rez, params );
break;
}
}
}
if (type) {
obj.href = url;
obj.type = type;
obj.autoHeight = false;
}
}
};
}(jQuery));
\ No newline at end of file
#fancybox-thumbs {
position: fixed;
left: 0;
width: 100%;
overflow: hidden;
z-index: 8050;
}
#fancybox-thumbs.bottom {
bottom: 2px;
}
#fancybox-thumbs.top {
top: 2px;
}
#fancybox-thumbs ul {
position: relative;
list-style: none;
margin: 0;
padding: 0;
}
#fancybox-thumbs ul li {
float: left;
padding: 1px;
opacity: 0.5;
}
#fancybox-thumbs ul li.active {
opacity: 0.75;
padding: 0;
border: 1px solid #fff;
}
#fancybox-thumbs ul li:hover {
opacity: 1;
}
#fancybox-thumbs ul li a {
display: block;
position: relative;
overflow: hidden;
border: 1px solid #222;
background: #111;
outline: none;
}
#fancybox-thumbs ul li img {
display: block;
position: relative;
border: 0;
padding: 0;
max-width: none;
}
\ No newline at end of file
/*!
* Thumbnail helper for fancyBox
* version: 1.0.7 (Mon, 01 Oct 2012)
* @requires fancyBox v2.0 or later
*
* Usage:
* $(".fancybox").fancybox({
* helpers : {
* thumbs: {
* width : 50,
* height : 50
* }
* }
* });
*
*/
(function ($) {
//Shortcut for fancyBox object
var F = $.fancybox;
//Add helper object
F.helpers.thumbs = {
defaults : {
width : 50, // thumbnail width
height : 50, // thumbnail height
position : 'bottom', // 'top' or 'bottom'
source : function ( item ) { // function to obtain the URL of the thumbnail image
var href;
if (item.element) {
href = $(item.element).find('img').attr('src');
}
if (!href && item.type === 'image' && item.href) {
href = item.href;
}
return href;
}
},
wrap : null,
list : null,
width : 0,
init: function (opts, obj) {
var that = this,
list,
thumbWidth = opts.width,
thumbHeight = opts.height,
thumbSource = opts.source;
//Build list structure
list = '';
for (var n = 0; n < obj.group.length; n++) {
list += '<li><a style="width:' + thumbWidth + 'px;height:' + thumbHeight + 'px;" href="javascript:jQuery.fancybox.jumpto(' + n + ');"></a></li>';
}
this.wrap = $('<div id="fancybox-thumbs"></div>').addClass(opts.position).appendTo('body');
this.list = $('<ul>' + list + '</ul>').appendTo(this.wrap);
//Load each thumbnail
$.each(obj.group, function (i) {
var href = thumbSource( obj.group[ i ] );
if (!href) {
return;
}
$("<img />").load(function () {
var width = this.width,
height = this.height,
widthRatio, heightRatio, parent;
if (!that.list || !width || !height) {
return;
}
//Calculate thumbnail width/height and center it
widthRatio = width / thumbWidth;
heightRatio = height / thumbHeight;
parent = that.list.children().eq(i).find('a');
if (widthRatio >= 1 && heightRatio >= 1) {
if (widthRatio > heightRatio) {
width = Math.floor(width / heightRatio);
height = thumbHeight;
} else {
width = thumbWidth;
height = Math.floor(height / widthRatio);
}
}
$(this).css({
width : width,
height : height,
top : Math.floor(thumbHeight / 2 - height / 2),
left : Math.floor(thumbWidth / 2 - width / 2)
});
parent.width(thumbWidth).height(thumbHeight);
$(this).hide().appendTo(parent).fadeIn(300);
}).attr('src', href);
});
//Set initial width
this.width = this.list.children().eq(0).outerWidth(true);
this.list.width(this.width * (obj.group.length + 1)).css('left', Math.floor($(window).width() * 0.5 - (obj.index * this.width + this.width * 0.5)));
},
beforeLoad: function (opts, obj) {
//Remove self if gallery do not have at least two items
if (obj.group.length < 2) {
obj.helpers.thumbs = false;
return;
}
//Increase bottom margin to give space for thumbs
obj.margin[ opts.position === 'top' ? 0 : 2 ] += ((opts.height) + 15);
},
afterShow: function (opts, obj) {
//Check if exists and create or update list
if (this.list) {
this.onUpdate(opts, obj);
} else {
this.init(opts, obj);
}
//Set active element
this.list.children().removeClass('active').eq(obj.index).addClass('active');
},
//Center list
onUpdate: function (opts, obj) {
if (this.list) {
this.list.stop(true).animate({
'left': Math.floor($(window).width() * 0.5 - (obj.index * this.width + this.width * 0.5))
}, 150);
}
},
beforeClose: function () {
if (this.wrap) {
this.wrap.remove();
}
this.wrap = null;
this.list = null;
this.width = 0;
}
}
}(jQuery));
\ No newline at end of file
#quick-background {
width: 100%;
height: 100%;
position: fixed;
left: 0;
top: 0;
z-index: 1000;
background-color: #000;
opacity: 0.4;
}
#quick-window{
position: absolute;
background-color:#fff;
width:96%;
max-width: 1024px;
display:none;
-webkit-box-shadow: 0px 0px 30px 0px #000; /* Saf3-4, iOS 4.0.2 - 4.2, Android 2.3+ */
box-shadow: 0px 0px 30px 0px #000; /* Opera 10.5, IE9, FF4+, Chrome 6+, iOS 5 */
}
#quick-window .product-img-box{width:230px; float:left}
#quickview-close{
background: #fff;
cursor: pointer;
float: right;
height: 40px;
line-height: 38px;
position: absolute;
right: -20px;
top: -20px;
width: 40px;
text-indent: -99999px;
border-radius: 100%;
-webkit-border-radius: 100%;
-moz-border-radius: 100%;
-webkit-transition: all 0.2s ease-out;
-moz-transition: all 0.2s ease-out;
-o-transition: all 0.2s ease-out;
transition: all 0.2s ease-out;
}
#quickview-close:before {
content: "\f00d";
font-family: "Fontawesome";
margin-left: 15px;
float: left;
text-indent: 0;
color: #fff;
}
#quickview-close:hover:before {
opacity: 0.8;
}
#quickview-header{}
#ajax-preloader{
opacity:0.8;
filter:alpha(opacity="80");
text-align:center;
z-index:500;
background: url(../images/ajax_loader.gif) center top no-repeat;
}
#ajax-preloader .loading{border:2px solid #777; color:#000; background:#eee; text-align:center; width:120px; padding:15px; font-weight:bold;}
.product-slider-wrapper {
float:none;
position:relative;
}
#quick-window .navi-product {
cursor: pointer;
}
#quick-window .navi-product div {
width: 26px;
height: 26px;
line-height: 26px;
color: #000;
position: absolute;
top: 50%;
z-index: 1550;
font-size: 1.2em;
background: #ccc;
cursor: pointer;
-webkit-box-shadow: 2px 2px 5px 0px #000;
box-shadow: 2px 2px 5px 0px #000;
text-align: center;
}
#quick-window .navi-product div:hover{
color:#fff;
}
#quick-window .navi-product .prev-prd {left: 0px;cursor: pointer;}
#quick-window .navi-product .next-prd {right: 0px;}
#quick-window .product-shop{float:left; position:relative; text-align:left;}
#quick-window .product-shop .quicview-skupr{}
#quick-window .product-shop .quicview-skupr h5,
#quick-window .product-shop .quicview-skupr label{
display:inline-block;
}
.quick-shortdesc h5{padding-bottom:10px;}
#quick-window .product-shop .actions{margin-top:10px;}
#quick-window .product-essential{padding:0px;}
.catalog-listing .product-image{position:relative;}
.catalog-listing .product-image .ajax{position:absolute; display:none;}
.product-image .ajax{ display:none;}
.product-image .ajax:hover{ display:block;}
.padding-10{padding-bottom:10px}
a.ajax{
text-decoration:none;
}
.quick-view-content .product-price {
font-size: 30px;
width: 100%;
display: inline-block;
}
a.ajax:hover{text-decoration:none;}
a.ajax .diamond{
line-height:34px;
}
.tab-bar { list-style: none; border-bottom: 1px solid #ccc; }
.tab-bar li { display: inline; }
.tab-bar li a { color: black; float: left; font-family: 'texgyreadventorbold';font-size: 16px; display: block; padding: 15px 25px; margin-left: -1px; position: relative; left: 1px; background: white; text-decoration: none; cursor: pointer;
text-transform:uppercase;
}
.tab-bar li a:hover { background: #ccc; }
.tab-bar .active-tab-name {
background-color: #E2D3CA;
}
.tabbed-area div[id^="box"] { background: white; padding:40px 5px 15px; display: inline-block;}
.tab-group:after { visibility: hidden; display: block; font-size: 0; content: " "; clear: both; height: 0; }
.tab-bar li a { border: 1px solid #ccc; border-bottom: 0; }
.tabbed-area div[id^="box"]{border-left:none;border-right:none;}
.box-wrap { position: relative; min-height: 200px; }
#box-one, #box-two, #box-three {
position: relative;
width: 100%;
}
#box-two,
#box-three{padding: 40px;}
.main-img-quickview{position: relative;}
.flat-button {
cursor: pointer;
color: blue;
text-decoration: underline;
}
.flat-button:hover {
text-decoration: none;
}
.product-shop label {
font-weight: bold;
}
.list-area, .review-list-area {
display: block;
width: 100%;
float: left;
text-align: left;
}
.tags-tab-quickview .form-add {
display: block;
width: 100%;
float: left;
text-align: left;
margin-bottom: 20px;
}
.tags-tab-quickview .form-add label{
float: left;
margin: 0 10px 0 0;
line-height: 42px;
}
.tags-tab-quickview .form-add input{
width: 290px;
padding: 11px 10px 10px;
}
.cz-product-name {
font-size: 1.5em;
font-weight: bold;
}
.tag-item {
zdisplay: block;
zbackground-color: #E6E6E6;
padding: 2px;
border-radius: 4px;
}
.tag-item a {
text-decoration: none;
}
.count-view {
color: orange;
font-size: 13px;
font-weight: bold;
}
.review-count{}
.review-count label{font-weight:bold;}
\ No newline at end of file
//////////////////////////////////////////////////////////////////////////////////
// Cloud Zoom V1.0.2.6
// (c) 2010 by R Cecco. <http://www.professorcloud.com>
// with enhancements by Philipp Andreas <https://github.com/smurfy/cloud-zoom>
//
// MIT License
//
// Please retain this copyright header in all versions of the software
//////////////////////////////////////////////////////////////////////////////////
(function ($) {
function format(str) {
for (var i = 1; i < arguments.length; i++) {
str = str.replace('%' + (i - 1), arguments[i]);
}
return str;
}
function CloudZoom(jWin, opts) {
var sImg = $('img', jWin);
var img1;
var img2;
var zoomDiv = null;
var $mouseTrap = null;
var lens = null;
var $tint = null;
var softFocus = null;
var $ie6Fix = null;
var zoomImage;
var controlTimer = 0;
var cw, ch;
var destU = 0;
var destV = 0;
var currV = 0;
var currU = 0;
var filesLoaded = 0;
var mx,
my;
var ctx = this, zw;
// Display an image loading message. This message gets deleted when the images have loaded and the zoom init function is called.
// We add a small delay before the message is displayed to avoid the message flicking on then off again virtually immediately if the
// images load really fast, e.g. from the cache.
//var ctx = this;
setTimeout(function () {
// <img src="/images/loading.gif"/>
if ($mouseTrap === null) {
var w = jWin.width();
jWin.parent().append(format('<div style="width:%0px;position:absolute;top:75%;left:%1px;text-align:center" class="cloud-zoom-loading" >Loading...</div>', w / 3, (w / 2) - (w / 6))).find(':last').css('opacity', 0.5);
}
}, 200);
var ie6FixRemove = function () {
if ($ie6Fix !== null) {
$ie6Fix.remove();
$ie6Fix = null;
}
};
// Removes cursor, tint layer, blur layer etc.
this.removeBits = function () {
//$mouseTrap.unbind();
if (lens) {
lens.remove();
lens = null;
}
if ($tint) {
$tint.remove();
$tint = null;
}
if (softFocus) {
softFocus.remove();
softFocus = null;
}
ie6FixRemove();
$('.cloud-zoom-loading', jWin.parent()).remove();
};
this.destroy = function () {
jWin.data('zoom', null);
if ($mouseTrap) {
$mouseTrap.unbind();
$mouseTrap.remove();
$mouseTrap = null;
}
if (zoomDiv) {
zoomDiv.remove();
zoomDiv = null;
}
//ie6FixRemove();
this.removeBits();
// DON'T FORGET TO REMOVE JQUERY 'DATA' VALUES
};
// This is called when the zoom window has faded out so it can be removed.
this.fadedOut = function () {
if (zoomDiv) {
zoomDiv.remove();
zoomDiv = null;
}
this.removeBits();
//ie6FixRemove();
};
this.controlLoop = function () {
if (lens) {
var x = (mx - sImg.offset().left - (cw * 0.5)) >> 0;
var y = (my - sImg.offset().top - (ch * 0.5)) >> 0;
if (x < 0) {
x = 0;
}
else if (x > (sImg.outerWidth() - cw)) {
x = (sImg.outerWidth() - cw);
}
if (y < 0) {
y = 0;
}
else if (y > (sImg.outerHeight() - ch)) {
y = (sImg.outerHeight() - ch);
}
lens.css({
left: x,
top: y
});
lens.css('background-position', (-x) + 'px ' + (-y) + 'px');
destU = (((x) / sImg.outerWidth()) * zoomImage.width) >> 0;
destV = (((y) / sImg.outerHeight()) * zoomImage.height) >> 0;
currU += (destU - currU) / opts.smoothMove;
currV += (destV - currV) / opts.smoothMove;
zoomDiv.css('background-position', (-(currU >> 0) + 'px ') + (-(currV >> 0) + 'px'));
}
controlTimer = setTimeout(function () {
ctx.controlLoop();
}, 30);
};
this.init2 = function (img, id) {
filesLoaded++;
//console.log(img.src + ' ' + id + ' ' + img.width);
if (id === 1) {
zoomImage = img;
}
//this.images[id] = img;
if (filesLoaded === 2) {
this.init();
}
};
/* Init function start. */
this.init = function () {
// Remove loading message (if present);
$('.cloud-zoom-loading', jWin.parent()).remove();
/* Add a box (mouseTrap) over the small image to trap mouse events.
It has priority over zoom window to avoid issues with inner zoom.
We need the dummy background image as IE does not trap mouse events on
transparent parts of a div.
*/
$mouseTrap = jWin.parent().append(format("<div class='mousetrap' style='background-image:url(\""+ opts.transparentImage +"\");z-index:999;position:absolute;width:%0px;height:%1px;left:0px;top:0px;\'></div>", sImg.outerWidth(), sImg.outerHeight(), opts.adjustX, opts.adjustY)).find(':last');
//////////////////////////////////////////////////////////////////////
/* Do as little as possible in mousemove event to prevent slowdown. */
$mouseTrap.bind('mousemove', this, function (event) {
// Just update the mouse position
mx = event.pageX;
my = event.pageY;
});
//////////////////////////////////////////////////////////////////////
$mouseTrap.bind('mouseleave', this, function (event) {
jWin.trigger('cloudzoom_end_zoom');
clearTimeout(controlTimer);
//event.data.removeBits();
if(lens) { lens.fadeOut(299); }
if($tint) { $tint.fadeOut(299); }
if(softFocus) { softFocus.fadeOut(299); }
zoomDiv.fadeOut(300, function () {
ctx.fadedOut();
});
return false;
});
//////////////////////////////////////////////////////////////////////
$mouseTrap.bind('mouseenter', this, function (event) {
jWin.trigger('cloudzoom_start_zoom');
mx = event.pageX;
my = event.pageY;
zw = event.data;
if (zoomDiv) {
zoomDiv.stop(true, false);
zoomDiv.remove();
}
var xPos = opts.adjustX,
yPos = opts.adjustY;
var siw = sImg.outerWidth();
var sih = sImg.outerHeight();
var w = opts.zoomWidth;
var h = opts.zoomHeight;
if (opts.zoomWidth == 'auto') {
w = siw;
}
if (opts.zoomHeight == 'auto') {
h = sih;
}
//$('#info').text( xPos + ' ' + yPos + ' ' + siw + ' ' + sih );
var appendTo = jWin.parent(); // attach to the wrapper
switch (opts.position) {
case 'top':
yPos -= h; // + opts.adjustY;
break;
case 'right':
xPos += siw; // + opts.adjustX;
break;
case 'bottom':
yPos += sih; // + opts.adjustY;
break;
case 'left':
xPos -= w; // + opts.adjustX;
break;
case 'inside':
w = siw;
h = sih;
break;
// All other values, try and find an id in the dom to attach to.
default:
appendTo = $('#' + opts.position);
// If dom element doesn't exit, just use 'right' position as default.
if (!appendTo.length) {
appendTo = jWin;
xPos += siw; //+ opts.adjustX;
yPos += sih; // + opts.adjustY;
} else {
w = appendTo.innerWidth();
h = appendTo.innerHeight();
}
}
zoomDiv = appendTo.append(format('<div id="cloud-zoom-big" class="cloud-zoom-big" style="display:none;position:absolute;left:%0px;top:%1px;width:%2px;height:%3px;background-image:url(\'%4\');z-index:99;"></div>', xPos, yPos, w, h, zoomImage.src)).find(':last');
// Add the title from title tag.
if (sImg.attr('title') && opts.showTitle) {
zoomDiv.append(format('<div class="cloud-zoom-title">%0</div>', sImg.attr('title'))).find(':last').css('opacity', opts.titleOpacity);
}
// Fix ie6 select elements wrong z-index bug. Placing an iFrame over the select element solves the issue...
var browserCheck = /(msie) ([\w.]+)/.exec( navigator.userAgent );
if (browserCheck) {
if ((browserCheck[1] || "") == 'msie' && (browserCheck[2] || "0" ) < 7) {
$ie6Fix = $('<iframe frameborder="0" src="#"></iframe>').css({
position: "absolute",
left: xPos,
top: yPos,
zIndex: 99,
width: w,
height: h
}).insertBefore(zoomDiv);
}
}
zoomDiv.fadeIn(500);
if (lens) {
lens.remove();
lens = null;
} /* Work out size of cursor */
cw = (sImg.outerWidth() / zoomImage.width) * zoomDiv.width();
ch = (sImg.outerHeight() / zoomImage.height) * zoomDiv.height();
// Attach mouse, initially invisible to prevent first frame glitch
lens = jWin.append(format("<div class = 'cloud-zoom-lens' style='display:none;z-index:98;position:absolute;width:%0px;height:%1px;'></div>", cw, ch)).find(':last');
$mouseTrap.css('cursor', lens.css('cursor'));
var noTrans = false;
// Init tint layer if needed. (Not relevant if using inside mode)
if (opts.tint) {
lens.css('background', 'url("' + sImg.attr('src') + '")');
$tint = jWin.append(format('<div style="display:none;position:absolute; left:0px; top:0px; width:%0px; height:%1px; background-color:%2;" />', sImg.outerWidth(), sImg.outerHeight(), opts.tint)).find(':last');
$tint.css('opacity', opts.tintOpacity);
noTrans = true;
$tint.fadeIn(500);
}
if (opts.softFocus) {
lens.css('background', 'url("' + sImg.attr('src') + '")');
softFocus = jWin.append(format('<div style="position:absolute;display:none;top:2px; left:2px; width:%0px; height:%1px;" />', sImg.outerWidth() - 2, sImg.outerHeight() - 2, opts.tint)).find(':last');
softFocus.css('background', 'url("' + sImg.attr('src') + '")');
softFocus.css('opacity', 0.5);
noTrans = true;
softFocus.fadeIn(500);
}
if (!noTrans) {
lens.css('opacity', opts.lensOpacity);
}
if ( opts.position !== 'inside' ) { lens.fadeIn(500); }
// Start processing.
zw.controlLoop();
return; // Don't return false here otherwise opera will not detect change of the mouse pointer type.
});
jWin.trigger('cloudzoom_ready');
};
img1 = new Image();
$(img1).load(function () {
ctx.init2(this, 0);
});
img1.src = sImg.attr('src');
img2 = new Image();
$(img2).load(function () {
ctx.init2(this, 1);
});
img2.src = jWin.attr('href');
}
$.fn.CloudZoom = function (options) {
// IE6 background image flicker fix
try {
document.execCommand("BackgroundImageCache", false, true);
} catch (e) {}
this.each(function () {
var relOpts, opts;
// Hmm...eval...slap on wrist.
eval('var a = {' + $(this).attr('rel') + '}');
relOpts = a;
if ($(this).is('.cloud-zoom')) {
opts = $.extend({}, $.fn.CloudZoom.defaults, options);
opts = $.extend({}, opts, relOpts);
$(this).css({
'position': 'relative',
'display': 'block'
});
$('img', $(this)).css({
'display': 'block'
});
// Wrap an outer div around the link so we can attach things without them becoming part of the link.
// But not if wrap already exists.
if (!$(this).parent().hasClass('cloud-zoom-wrap') && opts.useWrapper) {
$(this).wrap('<div class="cloud-zoom-wrap"></div>');
}
$(this).data('zoom', new CloudZoom($(this), opts));
} else if ($(this).is('.cloud-zoom-gallery')) {
opts = $.extend({}, relOpts, options);
$(this).data('relOpts', opts);
$(this).bind('click', $(this), function (event) {
var data = event.data.data('relOpts');
// Destroy the previous zoom
$('#' + data.useZoom).data('zoom').destroy();
// Change the biglink to point to the new big image.
$('#' + data.useZoom).attr('href', event.data.attr('href'));
// Change the small image to point to the new small image.
$('#' + data.useZoom + ' img').attr('src', event.data.data('relOpts').smallImage);
// Init a new zoom with the new images.
$('#' + event.data.data('relOpts').useZoom).CloudZoom();
return false;
});
}
});
return this;
};
$.fn.CloudZoom.defaults = {
zoomWidth: 'auto',
zoomHeight: 'auto',
position: 'inside',
transparentImage: '.',
useWrapper: true,
tint: false,
tintOpacity: 0.5,
lensOpacity: 0.5,
softFocus: false,
smoothMove: 3,
showTitle: true,
titleOpacity: 0.5,
adjustX: 0,
adjustY: 0
};
})(jQuery);
/**
* BxSlider v4.1.2 - Fully loaded, responsive content slider
* http://bxslider.com
*
* Copyright 2014, Steven Wanderski - http://stevenwanderski.com - http://bxcreative.com
* Written while drinking Belgian ales and listening to jazz
*
* Released under the MIT license - http://opensource.org/licenses/MIT
*/
;(function($){
var plugin = {};
var defaults = {
// GENERAL
mode: 'horizontal',
slideSelector: '',
infiniteLoop: true,
hideControlOnEnd: false,
speed: 500,
easing: null,
slideMargin: 0,
startSlide: 0,
randomStart: false,
captions: false,
ticker: false,
tickerHover: false,
adaptiveHeight: false,
adaptiveHeightSpeed: 500,
video: false,
useCSS: true,
preloadImages: 'visible',
responsive: true,
slideZIndex: 50,
wrapperClass: 'bx-wrapper',
// TOUCH
touchEnabled: true,
swipeThreshold: 50,
oneToOneTouch: true,
preventDefaultSwipeX: true,
preventDefaultSwipeY: false,
// PAGER
pager: true,
pagerType: 'full',
pagerShortSeparator: ' / ',
pagerSelector: null,
buildPager: null,
pagerCustom: null,
// CONTROLS
controls: true,
nextText: 'Next',
prevText: 'Prev',
nextSelector: null,
prevSelector: null,
autoControls: false,
startText: 'Start',
stopText: 'Stop',
autoControlsCombine: false,
autoControlsSelector: null,
// AUTO
auto: false,
pause: 4000,
autoStart: true,
autoDirection: 'next',
autoHover: false,
autoDelay: 0,
autoSlideForOnePage: false,
// CAROUSEL
minSlides: 1,
maxSlides: 1,
moveSlides: 0,
slideWidth: 0,
// CALLBACKS
onSliderLoad: function() {},
onSlideBefore: function() {},
onSlideAfter: function() {},
onSlideNext: function() {},
onSlidePrev: function() {},
onSliderResize: function() {}
}
$.fn.bxSlider = function(options){
if(this.length == 0) return this;
// support mutltiple elements
if(this.length > 1){
this.each(function(){$(this).bxSlider(options)});
return this;
}
// create a namespace to be used throughout the plugin
var slider = {};
// set a reference to our slider element
var el = this;
plugin.el = this;
/**
* Makes slideshow responsive
*/
// first get the original window dimens (thanks alot IE)
var windowWidth = $(window).width();
var windowHeight = $(window).height();
/**
* ===================================================================================
* = PRIVATE FUNCTIONS
* ===================================================================================
*/
/**
* Initializes namespace settings to be used throughout plugin
*/
var init = function(){
// merge user-supplied options with the defaults
slider.settings = $.extend({}, defaults, options);
// parse slideWidth setting
slider.settings.slideWidth = parseInt(slider.settings.slideWidth);
// store the original children
slider.children = el.children(slider.settings.slideSelector);
// check if actual number of slides is less than minSlides / maxSlides
if(slider.children.length < slider.settings.minSlides) slider.settings.minSlides = slider.children.length;
if(slider.children.length < slider.settings.maxSlides) slider.settings.maxSlides = slider.children.length;
// if random start, set the startSlide setting to random number
if(slider.settings.randomStart) slider.settings.startSlide = Math.floor(Math.random() * slider.children.length);
// store active slide information
slider.active = { index: slider.settings.startSlide }
// store if the slider is in carousel mode (displaying / moving multiple slides)
slider.carousel = slider.settings.minSlides > 1 || slider.settings.maxSlides > 1;
// if carousel, force preloadImages = 'all'
if(slider.carousel) slider.settings.preloadImages = 'all';
// calculate the min / max width thresholds based on min / max number of slides
// used to setup and update carousel slides dimensions
slider.minThreshold = (slider.settings.minSlides * slider.settings.slideWidth) + ((slider.settings.minSlides - 1) * slider.settings.slideMargin);
slider.maxThreshold = (slider.settings.maxSlides * slider.settings.slideWidth) + ((slider.settings.maxSlides - 1) * slider.settings.slideMargin);
// store the current state of the slider (if currently animating, working is true)
slider.working = false;
// initialize the controls object
slider.controls = {};
// initialize an auto interval
slider.interval = null;
// determine which property to use for transitions
slider.animProp = slider.settings.mode == 'vertical' ? 'top' : 'left';
// determine if hardware acceleration can be used
slider.usingCSS = slider.settings.useCSS && slider.settings.mode != 'fade' && (function(){
// create our test div element
var div = document.createElement('div');
// css transition properties
var props = ['WebkitPerspective', 'MozPerspective', 'OPerspective', 'msPerspective'];
// test for each property
for(var i in props){
if(div.style[props[i]] !== undefined){
slider.cssPrefix = props[i].replace('Perspective', '').toLowerCase();
slider.animProp = '-' + slider.cssPrefix + '-transform';
return true;
}
}
return false;
}());
// if vertical mode always make maxSlides and minSlides equal
if(slider.settings.mode == 'vertical') slider.settings.maxSlides = slider.settings.minSlides;
// save original style data
el.data("origStyle", el.attr("style"));
el.children(slider.settings.slideSelector).each(function() {
$(this).data("origStyle", $(this).attr("style"));
});
// perform all DOM / CSS modifications
setup();
}
/**
* Performs all DOM and CSS modifications
*/
var setup = function(){
// wrap el in a wrapper
el.wrap('<div class="' + slider.settings.wrapperClass + '"><div class="bx-viewport"></div></div>');
// store a namspace reference to .bx-viewport
slider.viewport = el.parent();
// store a namspace reference to .bx-wrapper
slider.wrapper = slider.viewport.parent();
// add a loading div to display while images are loading
slider.loader = $('<div class="bx-loading" />');
slider.viewport.prepend(slider.loader);
// set el to a massive width, to hold any needed slides
// also strip any margin and padding from el
el.css({
width: slider.settings.mode == 'horizontal' ? (slider.children.length * 100 + 215) + '%' : 'auto',
position: 'relative'
});
// if using CSS, add the easing property
if(slider.usingCSS && slider.settings.easing){
el.css('-' + slider.cssPrefix + '-transition-timing-function', slider.settings.easing);
// if not using CSS and no easing value was supplied, use the default JS animation easing (swing)
}else if(!slider.settings.easing){
slider.settings.easing = 'swing';
}
var slidesShowing = getNumberSlidesShowing();
// make modifications to the viewport (.bx-viewport)
slider.viewport.css({
width: '100%',
overflow: 'hidden',
position: 'relative'
});
slider.wrapper.css({
maxWidth: getViewportMaxWidth()
});
// make modification to the wrapper (.bx-wrapper)
if(!slider.settings.pager) {
slider.viewport.parent().css({
margin: '0 auto 0px'
});
}
// apply css to all slider children
slider.children.css({
'float': slider.settings.mode == 'horizontal' ? 'left' : 'none',
listStyle: 'none',
position: 'relative'
});
// apply the calculated width after the float is applied to prevent scrollbar interference
slider.children.css('width', getSlideWidth());
// if slideMargin is supplied, add the css
if(slider.settings.mode == 'horizontal' && slider.settings.slideMargin > 0) slider.children.css('marginRight', slider.settings.slideMargin);
if(slider.settings.mode == 'vertical' && slider.settings.slideMargin > 0) slider.children.css('marginBottom', slider.settings.slideMargin);
// if "fade" mode, add positioning and z-index CSS
if(slider.settings.mode == 'fade'){
slider.children.css({
position: 'absolute',
zIndex: 0,
display: 'none'
});
// prepare the z-index on the showing element
slider.children.eq(slider.settings.startSlide).css({zIndex: slider.settings.slideZIndex, display: 'block'});
}
// create an element to contain all slider controls (pager, start / stop, etc)
slider.controls.el = $('<div class="bx-controls" />');
// if captions are requested, add them
if(slider.settings.captions) appendCaptions();
// check if startSlide is last slide
slider.active.last = slider.settings.startSlide == getPagerQty() - 1;
// if video is true, set up the fitVids plugin
if(slider.settings.video) el.fitVids();
// set the default preload selector (visible)
var preloadSelector = slider.children.eq(slider.settings.startSlide);
if (slider.settings.preloadImages == "all") preloadSelector = slider.children;
// only check for control addition if not in "ticker" mode
if(!slider.settings.ticker){
// if pager is requested, add it
if(slider.settings.pager) appendPager();
// if controls are requested, add them
if(slider.settings.controls) appendControls();
// if auto is true, and auto controls are requested, add them
if(slider.settings.auto && slider.settings.autoControls) appendControlsAuto();
// if any control option is requested, add the controls wrapper
if(slider.settings.controls || slider.settings.autoControls || slider.settings.pager) slider.viewport.after(slider.controls.el);
// if ticker mode, do not allow a pager
}else{
slider.settings.pager = false;
}
// preload all images, then perform final DOM / CSS modifications that depend on images being loaded
loadElements(preloadSelector, start);
if (slider.settings.mode == 'horizontal') {
slider.wrapper.css('margin', '');
}else if (slider.settings.mode == 'vertical') {
slider.wrapper.css('float', 'left');
slider.wrapper.css('margin', '0px 10px 60px');
}
// make modification to controls in vertical mode
if (slider.settings.mode == 'vertical') {
$('.bx-wrapper .bx-viewport').css('left', 0);
$('.bx-wrapper .bx-controls-direction a').css('top', '');
$('.bx-wrapper .bx-controls-direction a').css('margin-top', '0');
$('.bx-wrapper .bx-controls-direction a').css('left', '15px');
$('.bx-wrapper .bx-prev').css('top', '15px');
$('.bx-wrapper .bx-prev').css('background-position', '0 -95px');
$('.bx-wrapper .bx-prev:hover').css('background-position', '0 -63px');
$('.bx-wrapper .bx-next').css('top', '233px');//viewportHeight - height + 2*slideMargin
$('.bx-wrapper .bx-next').css('background-position', '-43px -95px');
$('.bx-wrapper .bx-next:hover').css('background-position', '-43px -63px');
}
}
var loadElements = function(selector, callback){
var total = selector.find('img, iframe').length;
if (total == 0){
callback();
return;
}
var count = 0;
selector.find('img, iframe').each(function(){
$(this).bind('click', clickElementBind);
$(this).one('load', function() {
if(++count == total) {
callback();
}
}).each(function() {
if(this.complete) $(this).load();
});
});
}
/**
* Start the slider
*/
var start = function(){
// if infinite loop, prepare additional slides
if(slider.settings.infiniteLoop && slider.settings.mode != 'fade' && !slider.settings.ticker){
var slice = slider.settings.mode == 'vertical' ? slider.settings.minSlides : slider.settings.maxSlides;
var sliceAppend = slider.children.slice(0, slice).clone().addClass('bx-clone');
var slicePrepend = slider.children.slice(-slice).clone().addClass('bx-clone');
el.append(sliceAppend).prepend(slicePrepend);
}
// remove the loading DOM element
slider.loader.remove();
// set the left / top position of "el"
setSlidePosition();
// if "vertical" mode, always use adaptiveHeight to prevent odd behavior
if (slider.settings.mode == 'vertical') slider.settings.adaptiveHeight = true;
// set the viewport height
slider.viewport.height(getViewportHeight());
// make sure everything is positioned just right (same as a window resize)
el.redrawSlider();
// onSliderLoad callback
slider.settings.onSliderLoad(slider.active.index);
// slider has been fully initialized
slider.initialized = true;
// bind the resize call to the window
if (slider.settings.responsive) $(window).bind('resize', resizeWindow);
// if auto is true and has more than 1 page, start the show
if (slider.settings.auto && slider.settings.autoStart && (getPagerQty() > 1 || slider.settings.autoSlideForOnePage)) initAuto();
// if ticker is true, start the ticker
if (slider.settings.ticker) initTicker();
// if pager is requested, make the appropriate pager link active
if (slider.settings.pager) updatePagerActive(slider.settings.startSlide);
// check for any updates to the controls (like hideControlOnEnd updates)
if (slider.settings.controls) updateDirectionControls();
// if touchEnabled is true, setup the touch events
if (slider.settings.touchEnabled && !slider.settings.ticker) initTouch();
}
/**
* Returns the calculated height of the viewport, used to determine either adaptiveHeight or the maxHeight value
*/
var getViewportHeight = function(){
var height = 0;
// first determine which children (slides) should be used in our height calculation
var children = $();
// if mode is not "vertical" and adaptiveHeight is false, include all children
if(slider.settings.mode != 'vertical' && !slider.settings.adaptiveHeight){
children = slider.children;
}else{
// if not carousel, return the single active child
if(!slider.carousel){
children = slider.children.eq(slider.active.index);
// if carousel, return a slice of children
}else{
// get the individual slide index
var currentIndex = slider.settings.moveSlides == 1 ? slider.active.index : slider.active.index * getMoveBy();
// add the current slide to the children
children = slider.children.eq(currentIndex);
// cycle through the remaining "showing" slides
for (i = 1; i <= slider.settings.maxSlides - 1; i++){
// if looped back to the start
if(currentIndex + i >= slider.children.length){
children = children.add(slider.children.eq(i - 1));
}else{
children = children.add(slider.children.eq(currentIndex + i));
}
}
}
}
// if "vertical" mode, calculate the sum of the heights of the children
if(slider.settings.mode == 'vertical'){
children.each(function(index) {
height += $(this).outerHeight();
});
// add user-supplied margins
if(slider.settings.slideMargin > 0){
height += slider.settings.slideMargin * (slider.settings.minSlides - 1);
}
// if not "vertical" mode, calculate the max height of the children
}else{
height = Math.max.apply(Math, children.map(function(){
return $(this).outerHeight(false);
}).get());
}
if(slider.viewport.css('box-sizing') == 'border-box'){
height += parseFloat(slider.viewport.css('padding-top')) + parseFloat(slider.viewport.css('padding-bottom')) +
parseFloat(slider.viewport.css('border-top-width')) + parseFloat(slider.viewport.css('border-bottom-width'));
}else if(slider.viewport.css('box-sizing') == 'padding-box'){
height += parseFloat(slider.viewport.css('padding-top')) + parseFloat(slider.viewport.css('padding-bottom'));
}
return height;
}
/**
* Returns the calculated width to be used for the outer wrapper / viewport
*/
var getViewportMaxWidth = function(){
var width = '100%';
if(slider.settings.slideWidth > 0){
if(slider.settings.mode == 'horizontal'){
width = (slider.settings.maxSlides * slider.settings.slideWidth) + ((slider.settings.maxSlides - 1) * slider.settings.slideMargin);
}else{
width = slider.settings.slideWidth;
}
}
return width;
}
/**
* Returns the calculated width to be applied to each slide
*/
var getSlideWidth = function(){
// start with any user-supplied slide width
var newElWidth = slider.settings.slideWidth;
// get the current viewport width
var wrapWidth = slider.viewport.width();
// if slide width was not supplied, or is larger than the viewport use the viewport width
if(slider.settings.slideWidth == 0 ||
(slider.settings.slideWidth > wrapWidth && !slider.carousel) ||
slider.settings.mode == 'vertical'){
newElWidth = wrapWidth;
// if carousel, use the thresholds to determine the width
}else if(slider.settings.maxSlides > 1 && slider.settings.mode == 'horizontal'){
if(wrapWidth > slider.maxThreshold){
// newElWidth = (wrapWidth - (slider.settings.slideMargin * (slider.settings.maxSlides - 1))) / slider.settings.maxSlides;
}else if(wrapWidth < slider.minThreshold){
newElWidth = (wrapWidth - (slider.settings.slideMargin * (slider.settings.minSlides - 1))) / slider.settings.minSlides;
}
}
return newElWidth;
}
/**
* Returns the number of slides currently visible in the viewport (includes partially visible slides)
*/
var getNumberSlidesShowing = function(){
var slidesShowing = 1;
if(slider.settings.mode == 'horizontal' && slider.settings.slideWidth > 0){
// if viewport is smaller than minThreshold, return minSlides
if(slider.viewport.width() < slider.minThreshold){
slidesShowing = slider.settings.minSlides;
// if viewport is larger than minThreshold, return maxSlides
}else if(slider.viewport.width() > slider.maxThreshold){
slidesShowing = slider.settings.maxSlides;
// if viewport is between min / max thresholds, divide viewport width by first child width
}else{
var childWidth = slider.children.first().width() + slider.settings.slideMargin;
slidesShowing = Math.floor((slider.viewport.width() +
slider.settings.slideMargin) / childWidth);
}
// if "vertical" mode, slides showing will always be minSlides
}else if(slider.settings.mode == 'vertical'){
slidesShowing = slider.settings.minSlides;
}
return slidesShowing;
}
/**
* Returns the number of pages (one full viewport of slides is one "page")
*/
var getPagerQty = function(){
var pagerQty = 0;
// if moveSlides is specified by the user
if(slider.settings.moveSlides > 0){
if(slider.settings.infiniteLoop){
pagerQty = Math.ceil(slider.children.length / getMoveBy());
}else{
// use a while loop to determine pages
var breakPoint = 0;
var counter = 0
// when breakpoint goes above children length, counter is the number of pages
while (breakPoint < slider.children.length){
++pagerQty;
breakPoint = counter + getNumberSlidesShowing();
counter += slider.settings.moveSlides <= getNumberSlidesShowing() ? slider.settings.moveSlides : getNumberSlidesShowing();
}
}
// if moveSlides is 0 (auto) divide children length by sides showing, then round up
}else{
pagerQty = Math.ceil(slider.children.length / getNumberSlidesShowing());
}
return pagerQty;
}
/**
* Returns the number of indivual slides by which to shift the slider
*/
var getMoveBy = function(){
// if moveSlides was set by the user and moveSlides is less than number of slides showing
if(slider.settings.moveSlides > 0 && slider.settings.moveSlides <= getNumberSlidesShowing()){
return slider.settings.moveSlides;
}
// if moveSlides is 0 (auto)
return getNumberSlidesShowing();
}
/**
* Sets the slider's (el) left or top position
*/
var setSlidePosition = function(){
// if last slide, not infinite loop, and number of children is larger than specified maxSlides
if(slider.children.length > slider.settings.maxSlides && slider.active.last && !slider.settings.infiniteLoop){
if (slider.settings.mode == 'horizontal'){
// get the last child's position
var lastChild = slider.children.last();
var position = lastChild.position();
// set the left position
setPositionProperty(-(position.left - (slider.viewport.width() - lastChild.outerWidth())), 'reset', 0);
}else if(slider.settings.mode == 'vertical'){
// get the last showing index's position
var lastShowingIndex = slider.children.length - slider.settings.minSlides;
var position = slider.children.eq(lastShowingIndex).position();
// set the top position
setPositionProperty(-position.top, 'reset', 0);
}
// if not last slide
}else{
// get the position of the first showing slide
var position = slider.children.eq(slider.active.index * getMoveBy()).position();
// check for last slide
if (slider.active.index == getPagerQty() - 1) slider.active.last = true;
// set the repective position
if (position != undefined){
if (slider.settings.mode == 'horizontal') setPositionProperty(-position.left, 'reset', 0);
else if (slider.settings.mode == 'vertical') setPositionProperty(-position.top, 'reset', 0);
}
}
}
/**
* Sets the el's animating property position (which in turn will sometimes animate el).
* If using CSS, sets the transform property. If not using CSS, sets the top / left property.
*
* @param value (int)
* - the animating property's value
*
* @param type (string) 'slider', 'reset', 'ticker'
* - the type of instance for which the function is being
*
* @param duration (int)
* - the amount of time (in ms) the transition should occupy
*
* @param params (array) optional
* - an optional parameter containing any variables that need to be passed in
*/
var setPositionProperty = function(value, type, duration, params){
// use CSS transform
if(slider.usingCSS){
// determine the translate3d value
var propValue = slider.settings.mode == 'vertical' ? 'translate3d(0, ' + value + 'px, 0)' : 'translate3d(' + value + 'px, 0, 0)';
// add the CSS transition-duration
el.css('-' + slider.cssPrefix + '-transition-duration', duration / 1000 + 's');
if(type == 'slide'){
// set the property value
el.css(slider.animProp, propValue);
// bind a callback method - executes when CSS transition completes
el.bind('transitionend webkitTransitionEnd oTransitionEnd MSTransitionEnd', function(){
// unbind the callback
el.unbind('transitionend webkitTransitionEnd oTransitionEnd MSTransitionEnd');
updateAfterSlideTransition();
});
}else if(type == 'reset'){
el.css(slider.animProp, propValue);
}else if(type == 'ticker'){
// make the transition use 'linear'
el.css('-' + slider.cssPrefix + '-transition-timing-function', 'linear');
el.css(slider.animProp, propValue);
// bind a callback method - executes when CSS transition completes
el.bind('transitionend webkitTransitionEnd oTransitionEnd MSTransitionEnd', function(){
// unbind the callback
el.unbind('transitionend webkitTransitionEnd oTransitionEnd MSTransitionEnd');
// reset the position
setPositionProperty(params['resetValue'], 'reset', 0);
// start the loop again
tickerLoop();
});
}
// use JS animate
}else{
var animateObj = {};
animateObj[slider.animProp] = value;
if(type == 'slide'){
el.animate(animateObj, duration, slider.settings.easing, function(){
updateAfterSlideTransition();
});
}else if(type == 'reset'){
el.css(slider.animProp, value)
}else if(type == 'ticker'){
el.animate(animateObj, speed, 'linear', function(){
setPositionProperty(params['resetValue'], 'reset', 0);
// run the recursive loop after animation
tickerLoop();
});
}
}
}
/**
* Populates the pager with proper amount of pages
*/
var populatePager = function(){
var pagerHtml = '';
var pagerQty = getPagerQty();
// loop through each pager item
for(var i=0; i < pagerQty; i++){
var linkContent = '';
// if a buildPager function is supplied, use it to get pager link value, else use index + 1
if(slider.settings.buildPager && $.isFunction(slider.settings.buildPager)){
linkContent = slider.settings.buildPager(i);
slider.pagerEl.addClass('bx-custom-pager');
}else{
linkContent = i + 1;
slider.pagerEl.addClass('bx-default-pager');
}
// var linkContent = slider.settings.buildPager && $.isFunction(slider.settings.buildPager) ? slider.settings.buildPager(i) : i + 1;
// add the markup to the string
pagerHtml += '<div class="bx-pager-item"><a href="" data-slide-index="' + i + '" class="bx-pager-link">' + linkContent + '</a></div>';
};
// populate the pager element with pager links
slider.pagerEl.html(pagerHtml);
}
/**
* Appends the pager to the controls element
*/
var appendPager = function(){
if(!slider.settings.pagerCustom){
// create the pager DOM element
slider.pagerEl = $('<div class="bx-pager" />');
// if a pager selector was supplied, populate it with the pager
if(slider.settings.pagerSelector){
$(slider.settings.pagerSelector).html(slider.pagerEl);
// if no pager selector was supplied, add it after the wrapper
}else{
slider.controls.el.addClass('bx-has-pager').append(slider.pagerEl);
}
// populate the pager
populatePager();
}else{
slider.pagerEl = $(slider.settings.pagerCustom);
}
// assign the pager click binding
slider.pagerEl.on('click', 'a', clickPagerBind);
}
/**
* Appends prev / next controls to the controls element
*/
var appendControls = function(){
slider.controls.next = $('<a class="bx-next" href="">' + slider.settings.nextText + '</a>');
slider.controls.prev = $('<a class="bx-prev" href="">' + slider.settings.prevText + '</a>');
// bind click actions to the controls
slider.controls.next.bind('click', clickNextBind);
slider.controls.prev.bind('click', clickPrevBind);
// if nextSlector was supplied, populate it
if(slider.settings.nextSelector){
$(slider.settings.nextSelector).append(slider.controls.next);
}
// if prevSlector was supplied, populate it
if(slider.settings.prevSelector){
$(slider.settings.prevSelector).append(slider.controls.prev);
}
// if no custom selectors were supplied
if(!slider.settings.nextSelector && !slider.settings.prevSelector){
// add the controls to the DOM
slider.controls.directionEl = $('<div class="bx-controls-direction" />');
// add the control elements to the directionEl
slider.controls.directionEl.append(slider.controls.prev).append(slider.controls.next);
// slider.viewport.append(slider.controls.directionEl);
slider.controls.el.addClass('bx-has-controls-direction').append(slider.controls.directionEl);
}
}
/**
* Appends start / stop auto controls to the controls element
*/
var appendControlsAuto = function(){
slider.controls.start = $('<div class="bx-controls-auto-item"><a class="bx-start" href="">' + slider.settings.startText + '</a></div>');
slider.controls.stop = $('<div class="bx-controls-auto-item"><a class="bx-stop" href="">' + slider.settings.stopText + '</a></div>');
// add the controls to the DOM
slider.controls.autoEl = $('<div class="bx-controls-auto" />');
// bind click actions to the controls
slider.controls.autoEl.on('click', '.bx-start', clickStartBind);
slider.controls.autoEl.on('click', '.bx-stop', clickStopBind);
// if autoControlsCombine, insert only the "start" control
if(slider.settings.autoControlsCombine){
slider.controls.autoEl.append(slider.controls.start);
// if autoControlsCombine is false, insert both controls
}else{
slider.controls.autoEl.append(slider.controls.start).append(slider.controls.stop);
}
// if auto controls selector was supplied, populate it with the controls
if(slider.settings.autoControlsSelector){
$(slider.settings.autoControlsSelector).html(slider.controls.autoEl);
// if auto controls selector was not supplied, add it after the wrapper
}else{
slider.controls.el.addClass('bx-has-controls-auto').append(slider.controls.autoEl);
}
// update the auto controls
updateAutoControls(slider.settings.autoStart ? 'stop' : 'start');
}
/**
* Appends image captions to the DOM
*/
var appendCaptions = function(){
// cycle through each child
slider.children.each(function(index){
// get the image title attribute
var title = $(this).find('img:first').attr('title');
// append the caption
if (title != undefined && ('' + title).length) {
$(this).append('<div class="bx-caption"><span>' + title + '</span></div>');
}
});
}
/**
* Click next binding
*
* @param e (event)
* - DOM event object
*/
var clickNextBind = function(e){
// if auto show is running, stop it
if (slider.settings.auto) el.stopAuto();
el.goToNextSlide();
e.preventDefault();
}
/**
* Click prev binding
*
* @param e (event)
* - DOM event object
*/
var clickPrevBind = function(e){
// if auto show is running, stop it
if (slider.settings.auto) el.stopAuto();
el.goToPrevSlide();
e.preventDefault();
}
/**
* Click start binding
*
* @param e (event)
* - DOM event object
*/
var clickStartBind = function(e){
el.startAuto();
e.preventDefault();
}
/**
* Click stop binding
*
* @param e (event)
* - DOM event object
*/
var clickStopBind = function(e){
el.stopAuto();
e.preventDefault();
}
/**
* Click element binding
*
* @param e (event)
* - DOM event object
*/
var clickElementBind = function(e){
// if auto show is running, stop it
if (slider.settings.auto) el.stopAuto();
var img = $(e.currentTarget);
console.log(img.attr('src'));
for(i = 0; i < slider.children.length; i++) {
if(slider.children.eq(i).children('img').attr('src') == img.attr('src')) {
if(i != slider.active.index) el.goToSlide(i);
}
}
}
/**
* Click pager binding
*
* @param e (event)
* - DOM event object
*/
var clickPagerBind = function(e){
// if auto show is running, stop it
if (slider.settings.auto) el.stopAuto();
var pagerLink = $(e.currentTarget);
if(pagerLink.attr('data-slide-index') !== undefined){
var pagerIndex = parseInt(pagerLink.attr('data-slide-index'));
// if clicked pager link is not active, continue with the goToSlide call
if(pagerIndex != slider.active.index) el.goToSlide(pagerIndex);
e.preventDefault();
}
}
/**
* Updates the pager links with an active class
*
* @param slideIndex (int)
* - index of slide to make active
*/
var updatePagerActive = function(slideIndex){
// if "short" pager type
var len = slider.children.length; // nb of children
if(slider.settings.pagerType == 'short'){
if(slider.settings.maxSlides > 1) {
len = Math.ceil(slider.children.length/slider.settings.maxSlides);
}
slider.pagerEl.html( (slideIndex + 1) + slider.settings.pagerShortSeparator + len);
return;
}
// remove all pager active classes
slider.pagerEl.find('a').removeClass('active');
// apply the active class for all pagers
slider.pagerEl.each(function(i, el) { $(el).find('a').eq(slideIndex).addClass('active'); });
}
/**
* Performs needed actions after a slide transition
*/
var updateAfterSlideTransition = function(){
// if infinte loop is true
if(slider.settings.infiniteLoop){
var position = '';
// first slide
if(slider.active.index == 0){
// set the new position
position = slider.children.eq(0).position();
// carousel, last slide
}else if(slider.active.index == getPagerQty() - 1 && slider.carousel){
position = slider.children.eq((getPagerQty() - 1) * getMoveBy()).position();
// last slide
}else if(slider.active.index == slider.children.length - 1){
position = slider.children.eq(slider.children.length - 1).position();
}
if(position){
if (slider.settings.mode == 'horizontal') { setPositionProperty(-position.left, 'reset', 0); }
else if (slider.settings.mode == 'vertical') { setPositionProperty(-position.top, 'reset', 0); }
}
}
// declare that the transition is complete
slider.working = false;
// onSlideAfter callback
slider.settings.onSlideAfter(slider.children.eq(slider.active.index), slider.oldIndex, slider.active.index);
}
/**
* Updates the auto controls state (either active, or combined switch)
*
* @param state (string) "start", "stop"
* - the new state of the auto show
*/
var updateAutoControls = function(state){
// if autoControlsCombine is true, replace the current control with the new state
if(slider.settings.autoControlsCombine){
slider.controls.autoEl.html(slider.controls[state]);
// if autoControlsCombine is false, apply the "active" class to the appropriate control
}else{
slider.controls.autoEl.find('a').removeClass('active');
slider.controls.autoEl.find('a:not(.bx-' + state + ')').addClass('active');
}
}
/**
* Updates the direction controls (checks if either should be hidden)
*/
var updateDirectionControls = function(){
if(getPagerQty() == 1){
slider.controls.prev.addClass('disabled');
slider.controls.next.addClass('disabled');
}else if(!slider.settings.infiniteLoop && slider.settings.hideControlOnEnd){
// if first slide
if (slider.active.index == 0){
slider.controls.prev.addClass('disabled');
slider.controls.next.removeClass('disabled');
// if last slide
}else if(slider.active.index == getPagerQty() - 1){
slider.controls.next.addClass('disabled');
slider.controls.prev.removeClass('disabled');
// if any slide in the middle
}else{
slider.controls.prev.removeClass('disabled');
slider.controls.next.removeClass('disabled');
}
}
}
/**
* Initialzes the auto process
*/
var initAuto = function(){
// if autoDelay was supplied, launch the auto show using a setTimeout() call
if(slider.settings.autoDelay > 0){
var timeout = setTimeout(el.startAuto, slider.settings.autoDelay);
// if autoDelay was not supplied, start the auto show normally
}else{
el.startAuto();
}
// if autoHover is requested
if(slider.settings.autoHover){
// on el hover
el.hover(function(){
// if the auto show is currently playing (has an active interval)
if(slider.interval){
// stop the auto show and pass true agument which will prevent control update
el.stopAuto(true);
// create a new autoPaused value which will be used by the relative "mouseout" event
slider.autoPaused = true;
}
}, function(){
// if the autoPaused value was created be the prior "mouseover" event
if(slider.autoPaused){
// start the auto show and pass true agument which will prevent control update
el.startAuto(true);
// reset the autoPaused value
slider.autoPaused = null;
}
});
}
}
/**
* Initialzes the ticker process
*/
var initTicker = function(){
var startPosition = 0;
// if autoDirection is "next", append a clone of the entire slider
if(slider.settings.autoDirection == 'next'){
el.append(slider.children.clone().addClass('bx-clone'));
// if autoDirection is "prev", prepend a clone of the entire slider, and set the left position
}else{
el.prepend(slider.children.clone().addClass('bx-clone'));
var position = slider.children.first().position();
startPosition = slider.settings.mode == 'horizontal' ? -position.left : -position.top;
}
setPositionProperty(startPosition, 'reset', 0);
// do not allow controls in ticker mode
slider.settings.pager = false;
slider.settings.controls = false;
slider.settings.autoControls = false;
// if autoHover is requested
if(slider.settings.tickerHover && !slider.usingCSS){
// on el hover
slider.viewport.hover(function(){
el.stop();
}, function(){
// calculate the total width of children (used to calculate the speed ratio)
var totalDimens = 0;
slider.children.each(function(index){
totalDimens += slider.settings.mode == 'horizontal' ? $(this).outerWidth(true) : $(this).outerHeight(true);
});
// calculate the speed ratio (used to determine the new speed to finish the paused animation)
var ratio = slider.settings.speed / totalDimens;
// determine which property to use
var property = slider.settings.mode == 'horizontal' ? 'left' : 'top';
// calculate the new speed
var newSpeed = ratio * (totalDimens - (Math.abs(parseInt(el.css(property)))));
tickerLoop(newSpeed);
});
}
// start the ticker loop
tickerLoop();
}
/**
* Runs a continuous loop, news ticker-style
*/
var tickerLoop = function(resumeSpeed){
speed = resumeSpeed ? resumeSpeed : slider.settings.speed;
var position = {left: 0, top: 0};
var reset = {left: 0, top: 0};
// if "next" animate left position to last child, then reset left to 0
if(slider.settings.autoDirection == 'next'){
position = el.find('.bx-clone').first().position();
// if "prev" animate left position to 0, then reset left to first non-clone child
}else{
reset = slider.children.first().position();
}
var animateProperty = slider.settings.mode == 'horizontal' ? -position.left : -position.top;
var resetValue = slider.settings.mode == 'horizontal' ? -reset.left : -reset.top;
var params = {resetValue: resetValue};
setPositionProperty(animateProperty, 'ticker', speed, params);
}
/**
* Initializes touch events
*/
var initTouch = function(){
// initialize object to contain all touch values
slider.touch = {
start: {x: 0, y: 0},
end: {x: 0, y: 0}
}
slider.viewport.bind('touchstart', onTouchStart);
}
/**
* Event handler for "touchstart"
*
* @param e (event)
* - DOM event object
*/
var onTouchStart = function(e){
if(slider.working){
e.preventDefault();
}else{
// record the original position when touch starts
slider.touch.originalPos = el.position();
var orig = e.originalEvent;
// record the starting touch x, y coordinates
slider.touch.start.x = orig.changedTouches[0].pageX;
slider.touch.start.y = orig.changedTouches[0].pageY;
// bind a "touchmove" event to the viewport
slider.viewport.bind('touchmove', onTouchMove);
// bind a "touchend" event to the viewport
slider.viewport.bind('touchend', onTouchEnd);
}
}
/**
* Event handler for "touchmove"
*
* @param e (event)
* - DOM event object
*/
var onTouchMove = function(e){
var orig = e.originalEvent;
// if scrolling on y axis, do not prevent default
var xMovement = Math.abs(orig.changedTouches[0].pageX - slider.touch.start.x);
var yMovement = Math.abs(orig.changedTouches[0].pageY - slider.touch.start.y);
// x axis swipe
if((xMovement * 3) > yMovement && slider.settings.preventDefaultSwipeX){
e.preventDefault();
// y axis swipe
}else if((yMovement * 3) > xMovement && slider.settings.preventDefaultSwipeY){
e.preventDefault();
}
if(slider.settings.mode != 'fade' && slider.settings.oneToOneTouch){
var value = 0;
// if horizontal, drag along x axis
if(slider.settings.mode == 'horizontal'){
var change = orig.changedTouches[0].pageX - slider.touch.start.x;
value = slider.touch.originalPos.left + change;
// if vertical, drag along y axis
}else{
var change = orig.changedTouches[0].pageY - slider.touch.start.y;
value = slider.touch.originalPos.top + change;
}
setPositionProperty(value, 'reset', 0);
}
}
/**
* Event handler for "touchend"
*
* @param e (event)
* - DOM event object
*/
var onTouchEnd = function(e){
slider.viewport.unbind('touchmove', onTouchMove);
var orig = e.originalEvent;
var value = 0;
// record end x, y positions
slider.touch.end.x = orig.changedTouches[0].pageX;
slider.touch.end.y = orig.changedTouches[0].pageY;
// if fade mode, check if absolute x distance clears the threshold
if(slider.settings.mode == 'fade'){
var distance = Math.abs(slider.touch.start.x - slider.touch.end.x);
if(distance >= slider.settings.swipeThreshold){
slider.touch.start.x > slider.touch.end.x ? el.goToNextSlide() : el.goToPrevSlide();
el.stopAuto();
}
// not fade mode
}else{
var distance = 0;
// calculate distance and el's animate property
if(slider.settings.mode == 'horizontal'){
distance = slider.touch.end.x - slider.touch.start.x;
value = slider.touch.originalPos.left;
}else{
distance = slider.touch.end.y - slider.touch.start.y;
value = slider.touch.originalPos.top;
}
// if not infinite loop and first / last slide, do not attempt a slide transition
if(!slider.settings.infiniteLoop && ((slider.active.index == 0 && distance > 0) || (slider.active.last && distance < 0))){
setPositionProperty(value, 'reset', 200);
}else{
// check if distance clears threshold
if(Math.abs(distance) >= slider.settings.swipeThreshold){
distance < 0 ? el.goToNextSlide() : el.goToPrevSlide();
el.stopAuto();
}else{
// el.animate(property, 200);
setPositionProperty(value, 'reset', 200);
}
}
}
slider.viewport.unbind('touchend', onTouchEnd);
}
/**
* Window resize event callback
*/
var resizeWindow = function(e){
// don't do anything if slider isn't initialized.
if(!slider.initialized) return;
// get the new window dimens (again, thank you IE)
var windowWidthNew = $(window).width();
var windowHeightNew = $(window).height();
// make sure that it is a true window resize
// *we must check this because our dinosaur friend IE fires a window resize event when certain DOM elements
// are resized. Can you just die already?*
if(windowWidth != windowWidthNew || windowHeight != windowHeightNew){
// set the new window dimens
windowWidth = windowWidthNew;
windowHeight = windowHeightNew;
// update all dynamic elements
el.redrawSlider();
// Call user resize handler
slider.settings.onSliderResize.call(el, slider.active.index);
}
}
/**
* ===================================================================================
* = PUBLIC FUNCTIONS
* ===================================================================================
*/
/**
* Performs slide transition to the specified slide
*
* @param slideIndex (int)
* - the destination slide's index (zero-based)
*
* @param direction (string)
* - INTERNAL USE ONLY - the direction of travel ("prev" / "next")
*/
el.goToSlide = function(slideIndex, direction){
// if plugin is currently in motion, ignore request
if(slider.working || slider.active.index == slideIndex) return;
// declare that plugin is in motion
slider.working = true;
// store the old index
slider.oldIndex = slider.active.index;
// if slideIndex is less than zero, set active index to last child (this happens during infinite loop)
if(slideIndex < 0){
slider.active.index = getPagerQty() - 1;
// if slideIndex is greater than children length, set active index to 0 (this happens during infinite loop)
}else if(slideIndex >= getPagerQty()){
slider.active.index = 0;
// set active index to requested slide
}else{
slider.active.index = slideIndex;
}
// onSlideBefore, onSlideNext, onSlidePrev callbacks
slider.settings.onSlideBefore(slider.children.eq(slider.active.index), slider.oldIndex, slider.active.index);
if(direction == 'next'){
slider.settings.onSlideNext(slider.children.eq(slider.active.index), slider.oldIndex, slider.active.index);
}else if(direction == 'prev'){
slider.settings.onSlidePrev(slider.children.eq(slider.active.index), slider.oldIndex, slider.active.index);
}
// check if last slide
slider.active.last = slider.active.index >= getPagerQty() - 1;
// update the pager with active class
if(slider.settings.pager) updatePagerActive(slider.active.index);
// // check for direction control update
if(slider.settings.controls) updateDirectionControls();
// if slider is set to mode: "fade"
if(slider.settings.mode == 'fade'){
// if adaptiveHeight is true and next height is different from current height, animate to the new height
if(slider.settings.adaptiveHeight && slider.viewport.height() != getViewportHeight()){
slider.viewport.animate({height: getViewportHeight()}, slider.settings.adaptiveHeightSpeed);
}
// fade out the visible child and reset its z-index value
slider.children.filter(':visible').fadeOut(slider.settings.speed).css({zIndex: 0});
// fade in the newly requested slide
slider.children.eq(slider.active.index).css('zIndex', slider.settings.slideZIndex+1).fadeIn(slider.settings.speed, function(){
$(this).css('zIndex', slider.settings.slideZIndex);
updateAfterSlideTransition();
});
// slider mode is not "fade"
}else{
// if adaptiveHeight is true and next height is different from current height, animate to the new height
if(slider.settings.adaptiveHeight && slider.viewport.height() != getViewportHeight()){
slider.viewport.animate({height: getViewportHeight()}, slider.settings.adaptiveHeightSpeed);
}
var moveBy = 0;
var position = {left: 0, top: 0};
// if carousel and not infinite loop
if(!slider.settings.infiniteLoop && slider.carousel && slider.active.last){
if(slider.settings.mode == 'horizontal'){
// get the last child position
var lastChild = slider.children.eq(slider.children.length - 1);
position = lastChild.position();
// calculate the position of the last slide
moveBy = slider.viewport.width() - lastChild.outerWidth();
}else{
// get last showing index position
var lastShowingIndex = slider.children.length - slider.settings.minSlides;
position = slider.children.eq(lastShowingIndex).position();
}
// horizontal carousel, going previous while on first slide (infiniteLoop mode)
}else if(slider.carousel && slider.active.last && direction == 'prev'){
// get the last child position
var eq = slider.settings.moveSlides == 1 ? slider.settings.maxSlides - getMoveBy() : ((getPagerQty() - 1) * getMoveBy()) - (slider.children.length - slider.settings.maxSlides);
var lastChild = el.children('.bx-clone').eq(eq);
position = lastChild.position();
// if infinite loop and "Next" is clicked on the last slide
}else if(direction == 'next' && slider.active.index == 0){
// get the last clone position
position = el.find('> .bx-clone').eq(slider.settings.maxSlides).position();
slider.active.last = false;
// normal non-zero requests
}else if(slideIndex >= 0){
var requestEl = slideIndex * getMoveBy();
position = slider.children.eq(requestEl).position();
}
/* If the position doesn't exist
* (e.g. if you destroy the slider on a next click),
* it doesn't throw an error.
*/
if ("undefined" !== typeof(position)) {
var value = slider.settings.mode == 'horizontal' ? -(position.left - moveBy) : -position.top;
// plugin values to be animated
setPositionProperty(value, 'slide', slider.settings.speed);
}
}
el.find('.bx-clone img').each(function(ind) {
$(this).bind('click', clickElementBind);
});
}
/**
* Transitions to the next slide in the show
*/
el.goToNextSlide = function(){
// if infiniteLoop is false and last page is showing, disregard call
if (!slider.settings.infiniteLoop && slider.active.last) return;
var pagerIndex = parseInt(slider.active.index) + 1;
el.goToSlide(pagerIndex, 'next');
}
/**
* Transitions to the prev slide in the show
*/
el.goToPrevSlide = function(){
// if infiniteLoop is false and last page is showing, disregard call
if (!slider.settings.infiniteLoop && slider.active.index == 0) return;
var pagerIndex = parseInt(slider.active.index) - 1;
el.goToSlide(pagerIndex, 'prev');
}
/**
* Starts the auto show
*
* @param preventControlUpdate (boolean)
* - if true, auto controls state will not be updated
*/
el.startAuto = function(preventControlUpdate){
// if an interval already exists, disregard call
if(slider.interval) return;
// create an interval
slider.interval = setInterval(function(){
slider.settings.autoDirection == 'next' ? el.goToNextSlide() : el.goToPrevSlide();
}, slider.settings.pause);
// if auto controls are displayed and preventControlUpdate is not true
if (slider.settings.autoControls && preventControlUpdate != true) updateAutoControls('stop');
}
/**
* Stops the auto show
*
* @param preventControlUpdate (boolean)
* - if true, auto controls state will not be updated
*/
el.stopAuto = function(preventControlUpdate){
// if no interval exists, disregard call
if(!slider.interval) return;
// clear the interval
clearInterval(slider.interval);
slider.interval = null;
// if auto controls are displayed and preventControlUpdate is not true
if (slider.settings.autoControls && preventControlUpdate != true) updateAutoControls('start');
}
/**
* Returns current slide index (zero-based)
*/
el.getCurrentSlide = function(){
return slider.active.index;
}
/**
* Returns current slide element
*/
el.getCurrentSlideElement = function(){
return slider.children.eq(slider.active.index);
}
/**
* Returns number of slides in show
*/
el.getSlideCount = function(){
return slider.children.length;
}
/**
* Update all dynamic slider elements
*/
el.redrawSlider = function(){
// resize all children in ratio to new screen size
slider.children.add(el.find('.bx-clone')).width(getSlideWidth());
// adjust the height
slider.viewport.css('height', getViewportHeight());
// update the slide position
if(!slider.settings.ticker) setSlidePosition();
// if active.last was true before the screen resize, we want
// to keep it last no matter what screen size we end on
if (slider.active.last) slider.active.index = getPagerQty() - 1;
// if the active index (page) no longer exists due to the resize, simply set the index as last
if (slider.active.index >= getPagerQty()) slider.active.last = true;
// if a pager is being displayed and a custom pager is not being used, update it
if(slider.settings.pager && !slider.settings.pagerCustom){
populatePager();
updatePagerActive(slider.active.index);
}
}
/**
* Destroy the current instance of the slider (revert everything back to original state)
*/
el.destroySlider = function(){
// don't do anything if slider has already been destroyed
if(!slider.initialized) return;
slider.initialized = false;
$('.bx-clone', this).remove();
slider.children.each(function() {
$(this).data("origStyle") != undefined ? $(this).attr("style", $(this).data("origStyle")) : $(this).removeAttr('style');
});
$(this).data("origStyle") != undefined ? this.attr("style", $(this).data("origStyle")) : $(this).removeAttr('style');
$(this).unwrap().unwrap();
if(slider.controls.el) slider.controls.el.remove();
if(slider.controls.next) slider.controls.next.remove();
if(slider.controls.prev) slider.controls.prev.remove();
if(slider.pagerEl && slider.settings.controls) slider.pagerEl.remove();
$('.bx-caption', this).remove();
if(slider.controls.autoEl) slider.controls.autoEl.remove();
clearInterval(slider.interval);
if(slider.settings.responsive) $(window).unbind('resize', resizeWindow);
}
/**
* Reload the slider (revert all DOM changes, and re-initialize)
*/
el.reloadSlider = function(settings){
if (settings != undefined) options = settings;
el.destroySlider();
init();
}
init();
// returns the current jQuery object
return this;
}
})(jQuery);
/**
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
define([
'jquery',
'mage/template',
'mage/translate',
'jquery/ui',
'quickview/cloudzoom',
'rokanthemes/owl'
], function($, mageTemplate) {
"use strict";
$.widget('mage.productQuickview', {
loaderStarted: 0,
options: {
icon: '',
texts: {
loaderText: $.mage.__('Please wait...'),
imgAlt: $.mage.__('Loading...')
},
template:'<div class="loading-mask" data-role="loader">' +
'<div class="loader">' +
'<img alt="<%- data.texts.imgAlt %>" src="<%- data.icon %>">' +
'<p><%- data.texts.loaderText %></p>' +
'</div>' + '</div>'
},
_create: function() {
this._bindClick();
},
_bindClick: function() {
var self = this;
self.createWindow();
this.element.on('click', function(e) {
e.preventDefault();
self.element.removeClass('active');
$(this).addClass('active');
self.show();
self.ajaxLoad($(this));
});
},
_render: function () {
var html;
if (!this.spinnerTemplate) {
this.spinnerTemplate = mageTemplate(this.options.template);
html = $(this.spinnerTemplate({
data: this.options
}));
html.prependTo($('body'));
this.spinner = html;
}
},
show: function (e, ctx) {
//$('body').append('<div id="add-to-cart-loading-ajax-common"><span></span></div>');
$('.quickview-product a').addClass('loading');
return false;
},
hide: function () {
//$('body #add-to-cart-loading-ajax-common').remove();
$('.quickview-product a').removeClass('loading');
return false;
},
ajaxLoad: function(link) {
var self = this;
if($('#quickview-content-' + link.attr('data-id')).length > 0)
{
return self.showWindow($('#quickview-content-' + link.attr('data-id')));
}
var urlLink = link.attr('data-href');
if(!urlLink)
urlLink = link.attr('href');
$.ajax({
url: urlLink,
data: {},
success: function(res) {
var itemShow = $('#quickview-content');
if(link.attr('data-id'))
{
if($('#quickview-content-' + link.attr('data-id')).length < 1)
{
var wrapper = document.createElement('div');
$(wrapper).attr('id', 'quickview-content-' + link.attr('data-id'));
$(wrapper).addClass('wrapper_quickview_item');
$(wrapper).html(res);
$('#quickview-content').append(wrapper);
}
itemShow = $('#quickview-content-' + link.attr('data-id'));
$('#quickview-content-' + link.attr('data-id') + ' .owl .small_image').on('click', function(event){
$('#quickview-content-' + link.attr('data-id') + ' .owl .small_image').removeClass('active');
$(this).addClass('active');
var currentImg = $(this).children('img');
jQuery('#gallery_' + link.attr('data-id') + ' a.cloud-zoom').attr('href', currentImg.attr('data-href'));
jQuery('#gallery_' + link.attr('data-id') + ' a.cloud-zoom img').attr('src', currentImg.attr('data-thumb-image'));
$('.cloud-zoom, .cloud-zoom-gallery').CloudZoom();
});
$('#quickview-content-' + link.attr('data-id') + ' .owl').owlCarousel({
autoPlay : false,
items : 4,
itemsDesktop : [1199,4],
itemsDesktopSmall : [980,3],
itemsTablet: [768,3],
itemsMobile : [479,1],
slideSpeed : 500,
paginationSpeed : 500,
rewindSpeed : 500,
navigation : true,
stopOnHover : true,
pagination :false,
scrollPerPage:true,
});
}else
{
$('#quickview-content').html(res);
}
$('.cloud-zoom, .cloud-zoom-gallery').CloudZoom();
$('#quickview-content').trigger('contentUpdated');
self.showWindow(itemShow);
}
});
},
showWindow: function(itemShow)
{
this.hide();
var scrollY = $(window).scrollTop();
var width = $('body').width();
$('#quick-window .wrapper_quickview_item').hide();
$('#quick-window').css({
top: scrollY + 100 + 'px',
left: width/2 - $('#quick-window').width()/2 + 'px',
display: 'block'
});
if(itemShow)
itemShow.show();
$('#quick-background').removeClass('hidden');
},
hideWindow: function()
{
$('#quick-window').hide();
$('#quick-window .wrapper_quickview_item').hide();
$('#quick-background').addClass('hidden');
$('#quickview-content').html('');
},
createWindow: function()
{
if($('#quick-background').length > 0)
return;
var qBackground = document.createElement('div');
$(qBackground).attr('id', 'quick-background');
$(qBackground).addClass('hidden');
$('body').append(qBackground);
var qWindow = document.createElement('div');
$(qWindow).attr('id', 'quick-window');
$(qWindow).html('<div id="quickview-header"><a href="javascript:void(0)" id="quickview-close">close</a></div><div class="quick-view-content" id="quickview-content"></div>');
$('body').append(qWindow);
$('#quickview-close').on('click', this.hideWindow.bind(this));
}
});
return $.mage.productQuickview;
});
\ No newline at end of file
<?php
/**
* Copyright 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
/**
* Field renderer for PayPal merchant country selector
*/
namespace Rokanthemes\RokanBase\Block\Adminhtml\Button\Export;
use Magento\Paypal\Model\Config\StructurePlugin;
class Block extends \Magento\Config\Block\System\Config\Form\Field
{
/**
* Config path for merchant country selector
*/
const FIELD_CONFIG_PATH = 'paypal/general/merchant_country';
/**
* Request parameter name for default country
*/
const REQUEST_PARAM_DEFAULT_COUNTRY = 'paypal_default_country';
/**
* Country of default scope
*
* @var string
*/
protected $_defaultCountry;
/**
* @var \Magento\Backend\Model\Url
*/
protected $_url;
/**
* @var \Magento\Framework\View\Helper\Js
*/
protected $_jsHelper;
/**
* @var \Magento\Directory\Helper\Data
*/
protected $directoryHelper;
/**
* @param \Magento\Backend\Block\Template\Context $context
* @param \Magento\Backend\Model\Url $url
* @param \Magento\Framework\View\Helper\Js $jsHelper
* @param \Magento\Directory\Helper\Data $directoryHelper
* @param array $data
*/
public function __construct(
\Magento\Backend\Block\Template\Context $context,
\Magento\Backend\Model\Url $url,
\Magento\Framework\View\Helper\Js $jsHelper,
\Magento\Directory\Helper\Data $directoryHelper,
array $data = []
) {
parent::__construct($context, $data);
$this->_url = $url;
$this->_jsHelper = $jsHelper;
$this->directoryHelper = $directoryHelper;
}
/**
* Get country selector html
*
* @param \Magento\Framework\Data\Form\Element\AbstractElement $element
* @return string
*/
protected function _getElementHtml(\Magento\Framework\Data\Form\Element\AbstractElement $element)
{
/** @var \Magento\Backend\Block\Widget\Button $buttonBlock */
$buttonBlock = $this->getForm()->getLayout()->createBlock('Magento\Backend\Block\Widget\Button');
$params = [
'website' => $buttonBlock->getRequest()->getParam('website')
];
$url = $this->getUrl("*/rokanbase/exportblock", $params);
$data = [
'id' => 'export_block' ,
'label' => __('Export Blocks'),
'onclick' => "setLocation('" . $url . "')",
];
$html = $buttonBlock->setData($data)->toHtml();
return $html;
}
}
<?php
/**
* Copyright 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
/**
* Field renderer for PayPal merchant country selector
*/
namespace Rokanthemes\RokanBase\Block\Adminhtml\Button\Export;
use Magento\Paypal\Model\Config\StructurePlugin;
class Page extends \Magento\Config\Block\System\Config\Form\Field
{
/**
* Config path for merchant country selector
*/
const FIELD_CONFIG_PATH = 'paypal/general/merchant_country';
/**
* Request parameter name for default country
*/
const REQUEST_PARAM_DEFAULT_COUNTRY = 'paypal_default_country';
/**
* Country of default scope
*
* @var string
*/
protected $_defaultCountry;
/**
* @var \Magento\Backend\Model\Url
*/
protected $_url;
/**
* @var \Magento\Framework\View\Helper\Js
*/
protected $_jsHelper;
/**
* @var \Magento\Directory\Helper\Data
*/
protected $directoryHelper;
/**
* @param \Magento\Backend\Block\Template\Context $context
* @param \Magento\Backend\Model\Url $url
* @param \Magento\Framework\View\Helper\Js $jsHelper
* @param \Magento\Directory\Helper\Data $directoryHelper
* @param array $data
*/
public function __construct(
\Magento\Backend\Block\Template\Context $context,
\Magento\Backend\Model\Url $url,
\Magento\Framework\View\Helper\Js $jsHelper,
\Magento\Directory\Helper\Data $directoryHelper,
array $data = []
) {
parent::__construct($context, $data);
$this->_url = $url;
$this->_jsHelper = $jsHelper;
$this->directoryHelper = $directoryHelper;
}
/**
* Get country selector html
*
* @param \Magento\Framework\Data\Form\Element\AbstractElement $element
* @return string
*/
protected function _getElementHtml(\Magento\Framework\Data\Form\Element\AbstractElement $element)
{
/** @var \Magento\Backend\Block\Widget\Button $buttonBlock */
$buttonBlock = $this->getForm()->getLayout()->createBlock('Magento\Backend\Block\Widget\Button');
$params = [
'website' => $buttonBlock->getRequest()->getParam('website')
];
$url = $this->getUrl("*/rokanbase/exportpage", $params);
$data = [
'id' => 'export_page' ,
'label' => __('Export Pages'),
'onclick' => "setLocation('" . $url . "')",
];
$html = $buttonBlock->setData($data)->toHtml();
return $html;
}
}
<?php
/**
* Copyright 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
/**
* Field renderer for PayPal merchant country selector
*/
namespace Rokanthemes\RokanBase\Block\Adminhtml\Button\Import;
use Magento\Paypal\Model\Config\StructurePlugin;
class Block extends \Magento\Config\Block\System\Config\Form\Field
{
/**
* Config path for merchant country selector
*/
const FIELD_CONFIG_PATH = 'paypal/general/merchant_country';
/**
* Request parameter name for default country
*/
const REQUEST_PARAM_DEFAULT_COUNTRY = 'paypal_default_country';
/**
* Country of default scope
*
* @var string
*/
protected $_defaultCountry;
/**
* @var \Magento\Backend\Model\Url
*/
protected $_url;
/**
* @var \Magento\Framework\View\Helper\Js
*/
protected $_jsHelper;
/**
* @var \Magento\Directory\Helper\Data
*/
protected $directoryHelper;
/**
* @param \Magento\Backend\Block\Template\Context $context
* @param \Magento\Backend\Model\Url $url
* @param \Magento\Framework\View\Helper\Js $jsHelper
* @param \Magento\Directory\Helper\Data $directoryHelper
* @param array $data
*/
public function __construct(
\Magento\Backend\Block\Template\Context $context,
\Magento\Backend\Model\Url $url,
\Magento\Framework\View\Helper\Js $jsHelper,
\Magento\Directory\Helper\Data $directoryHelper,
array $data = []
) {
parent::__construct($context, $data);
$this->_url = $url;
$this->_jsHelper = $jsHelper;
$this->directoryHelper = $directoryHelper;
}
/**
* Get country selector html
*
* @param \Magento\Framework\Data\Form\Element\AbstractElement $element
* @return string
*/
protected function _getElementHtml(\Magento\Framework\Data\Form\Element\AbstractElement $element)
{
/** @var \Magento\Backend\Block\Widget\Button $buttonBlock */
$buttonBlock = $this->getForm()->getLayout()->createBlock('Magento\Backend\Block\Widget\Button');
$params = [
'website' => $buttonBlock->getRequest()->getParam('website')
];
$url = $this->getUrl("*/rokanbase/importblock", $params);
$data = [
'id' => 'import_block' ,
'label' => __('Import Block'),
'onclick' => "setLocation('" . $url . "')",
];
$html = $buttonBlock->setData($data)->toHtml();
return $html;
}
}
<?php
/**
* Copyright 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
/**
* Field renderer for PayPal merchant country selector
*/
namespace Rokanthemes\RokanBase\Block\Adminhtml\Button\Import;
use Magento\Paypal\Model\Config\StructurePlugin;
class Page extends \Magento\Config\Block\System\Config\Form\Field
{
/**
* Config path for merchant country selector
*/
const FIELD_CONFIG_PATH = 'paypal/general/merchant_country';
/**
* Request parameter name for default country
*/
const REQUEST_PARAM_DEFAULT_COUNTRY = 'paypal_default_country';
/**
* Country of default scope
*
* @var string
*/
protected $_defaultCountry;
/**
* @var \Magento\Backend\Model\Url
*/
protected $_url;
/**
* @var \Magento\Framework\View\Helper\Js
*/
protected $_jsHelper;
/**
* @var \Magento\Directory\Helper\Data
*/
protected $directoryHelper;
/**
* @param \Magento\Backend\Block\Template\Context $context
* @param \Magento\Backend\Model\Url $url
* @param \Magento\Framework\View\Helper\Js $jsHelper
* @param \Magento\Directory\Helper\Data $directoryHelper
* @param array $data
*/
public function __construct(
\Magento\Backend\Block\Template\Context $context,
\Magento\Backend\Model\Url $url,
\Magento\Framework\View\Helper\Js $jsHelper,
\Magento\Directory\Helper\Data $directoryHelper,
array $data = []
) {
parent::__construct($context, $data);
$this->_url = $url;
$this->_jsHelper = $jsHelper;
$this->directoryHelper = $directoryHelper;
}
/**
* Get country selector html
*
* @param \Magento\Framework\Data\Form\Element\AbstractElement $element
* @return string
*/
protected function _getElementHtml(\Magento\Framework\Data\Form\Element\AbstractElement $element)
{
/** @var \Magento\Backend\Block\Widget\Button $buttonBlock */
$buttonBlock = $this->getForm()->getLayout()->createBlock('Magento\Backend\Block\Widget\Button');
$params = [
'website' => $buttonBlock->getRequest()->getParam('website')
];
$url = $this->getUrl("*/rokanbase/importpage", $params);
$data = [
'id' => 'import_page' ,
'label' => __('Import Page'),
'onclick' => "setLocation('" . $url . "')",
];
$html = $buttonBlock->setData($data)->toHtml();
return $html;
}
}
<?php
/**
*
* Copyright 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\RokanBase\Controller\Adminhtml\Rokanbase;
use Magento\Framework\App\Filesystem\DirectoryList;
class Exportblock extends \Magento\Backend\App\Action
{
/**
* @var \Magento\Backend\App\Response\Http\FileFactory
*/
protected $fileFactory;
protected $_parser;
/**
* @var \Magento\PageCache\Model\Config
*/
protected $config;
/**
* @param \Magento\Backend\App\Action\Context $context
* @param \Magento\Framework\App\Response\Http\FileFactory $fileFactory
* @param \Magento\PageCache\Model\Config $config
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\App\Response\Http\FileFactory $fileFactory,
\Magento\PageCache\Model\Config $config
) {
parent::__construct($context);
$this->config = $config;
$this->_importPath = BP . '/' . DirectoryList::VAR_DIR . '/';
$this->fileFactory = $fileFactory;
$this->_parser = new \Magento\Framework\Xml\Parser();
}
/**
* Export Varnish Configuration as .vcl
*
* @return \Magento\Framework\App\ResponseInterface
*/
public function execute()
{
$fileName = 'cms_blocks.xml';
$varnishVersion = $this->getRequest()->getParam('varnish');
$collection = $this->_objectManager->get('Magento\Cms\Model\Block')->getCollection();
$dom = $this->_parser->getDom();
$dom->formatOutput = true;
$root = $dom->createElement('root');
$blocks = $dom->createElement('blocks');
$skipKeys = array('block_id', 'creation_time', 'update_time', '_first_store_id', 'store_code');
foreach($collection as $block)
{
$item = $dom->createElement('item');
foreach($block->getData() as $key=>$value)
{
if(in_array($key, $skipKeys))
continue;
$element = $dom->createElement($key);
if(is_array($value) && $key == 'store_id')
{
foreach($value as $key2=>$value2)
{
$element2 = $dom->createElement('id');
$content = $dom->createCDATASection($value2);
$element2->appendChild($content);
$element->appendChild($element2);
}
$item->appendChild($element);
continue;
}
if(is_array($value))
$value = implode(',', $value);
$element = $dom->createElement($key);
$content = $dom->createCDATASection($value);
$element->appendChild($content);
$item->appendChild($element);
}
$blocks->appendChild($item);
}
$root->appendChild($blocks);
$dom->appendChild($root);
$content = $dom->saveXML();
$dom->save($this->_importPath . $fileName);
$this->messageManager->addSuccess(__('Blocks exported to folder var.'));
$this->_redirect('adminhtml/system_config/edit/section/import_export');
}
}
?>
\ No newline at end of file
<?php
/**
*
* Copyright 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\RokanBase\Controller\Adminhtml\Rokanbase;
use Magento\Framework\App\Filesystem\DirectoryList;
class Exportpage extends \Magento\Backend\App\Action
{
/**
* @var \Magento\Backend\App\Response\Http\FileFactory
*/
protected $fileFactory;
protected $_parser;
/**
* @var \Magento\PageCache\Model\Config
*/
protected $config;
/**
* @param \Magento\Backend\App\Action\Context $context
* @param \Magento\Framework\App\Response\Http\FileFactory $fileFactory
* @param \Magento\PageCache\Model\Config $config
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\App\Response\Http\FileFactory $fileFactory,
\Magento\PageCache\Model\Config $config
) {
parent::__construct($context);
$this->config = $config;
$this->fileFactory = $fileFactory;
$this->_importPath = BP . '/' . DirectoryList::VAR_DIR . '/';
$this->_parser = new \Magento\Framework\Xml\Parser();
}
/**
* Export Varnish Configuration as .vcl
*
* @return \Magento\Framework\App\ResponseInterface
*/
public function execute()
{
$fileName = 'cms_pages.xml';
$varnishVersion = $this->getRequest()->getParam('varnish');
$collection = $this->_objectManager->get('Magento\Cms\Model\Page')->getCollection();
$dom = $this->_parser->getDom();
$dom->formatOutput = true;
$root = $dom->createElement('root');
$blocks = $dom->createElement('pages');
$skipKeys = array('page_id', 'creation_time', 'update_time', '_first_store_id', 'store_code');
foreach($collection as $block)
{
$item = $dom->createElement('item');
foreach($block->getData() as $key=>$value)
{
if(in_array($key, $skipKeys))
continue;
$element = $dom->createElement($key);
if(is_array($value) && $key == 'store_id')
{
foreach($value as $key2=>$value2)
{
$element2 = $dom->createElement('id');
$content = $dom->createCDATASection($value2);
$element2->appendChild($content);
$element->appendChild($element2);
}
$item->appendChild($element);
continue;
}
if(is_array($value))
$value = implode(',', $value);
$content = $dom->createCDATASection($value);
$element->appendChild($content);
$item->appendChild($element);
}
$blocks->appendChild($item);
}
$root->appendChild($blocks);
$dom->appendChild($root);
$content = $dom->saveXML();
$dom->save($this->_importPath . $fileName);
$this->messageManager->addSuccess(__('Pages exported to folder var.'));
$this->_redirect('adminhtml/system_config/edit/section/import_export');
}
}
?>
\ No newline at end of file
<?php
/**
*
* Copyright 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\RokanBase\Controller\Adminhtml\Rokanbase;
use Magento\Framework\App\Filesystem\DirectoryList;
class Importblock extends \Magento\Backend\App\Action
{
/**
* @var \Magento\Backend\App\Response\Http\FileFactory
*/
protected $fileFactory;
/**
* @var \Magento\PageCache\Model\Config
*/
protected $config;
protected $_helperModule;
/**
* @param \Magento\Backend\App\Action\Context $context
* @param \Magento\Framework\App\Response\Http\FileFactory $fileFactory
* @param \Magento\PageCache\Model\Config $config
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\App\Response\Http\FileFactory $fileFactory,
\Magento\PageCache\Model\Config $config,
\Rokanthemes\RokanBase\Helper\Data $helperModule
) {
parent::__construct($context);
$this->_helperModule = $helperModule;
$this->config = $config;
$this->fileFactory = $fileFactory;
$this->_importPath = BP . '/' . DirectoryList::VAR_DIR . '/';
$this->_parser = new \Magento\Framework\Xml\Parser();
}
/**
* Export Varnish Configuration as .vcl
*
* @return \Magento\Framework\App\ResponseInterface
*/
public function execute()
{
try {
$xmlPath = $this->_importPath . 'cms_blocks.xml';
$overwrite = false;
if($this->_helperModule->getConfigData("import_export/import/overwrite_blocks")) {
$overwrite = true;
}
if (!is_readable($xmlPath))
{
throw new \Exception(
__("Can't get the data file for import cms blocks/pages: ".$xmlPath)
);
}
$data = $this->_parser->load($xmlPath)->xmlToArray();
$cms_collection = null;
$conflictingOldItems = array();
$i = 0;
foreach($data['root']['blocks']['item'] as $_item) {
$exist = false;
$collection = $this->_objectManager->create('Magento\Cms\Model\Block')->getCollection();
$collection->addFieldToFilter('identifier', $_item['identifier']);
if($collection->getSize())
$exist = true;
$block = $this->_objectManager->create('Magento\Cms\Model\Block');
if($overwrite) {
if($exist) {
$conflictingOldItems[] = $_item['identifier'];
$block->load($_item['identifier']);
}
} else {
if($exist) {
continue;
}
}
$conflictingOldItems[] = $_item['identifier'];
$_item['store_id'] = array(0);
$block->addData($_item)->save();
$i++;
}
$this->messageManager->addSuccess(__('Imported %1 Item(s). ( %2 )', $i, implode("\n", $conflictingOldItems)));
} catch (\Exception $exception) {
$this->messageManager->addError($exception->getMessage());
}
$this->_redirect('*/system_config/edit/section/import_export', array('website' => $this->getRequest()->getParam('website')));
}
}
?>
\ No newline at end of file
<?php
/**
*
* Copyright 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\RokanBase\Controller\Adminhtml\Rokanbase;
use Magento\Framework\App\Filesystem\DirectoryList;
use Rokanthemes\RokanBase\Helper\Data;
class Importpage extends \Magento\Backend\App\Action
{
/**
* @var \Magento\Backend\App\Response\Http\FileFactory
*/
protected $fileFactory;
/**
* @var \Magento\PageCache\Model\Config
*/
protected $_helperModule;
/**
* @param \Magento\Backend\App\Action\Context $context
* @param \Magento\Framework\App\Response\Http\FileFactory $fileFactory
* @param \Magento\PageCache\Model\Config $config
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\App\Response\Http\FileFactory $fileFactory,
\Magento\PageCache\Model\Config $config,
\Rokanthemes\RokanBase\Helper\Data $helperModule
) {
parent::__construct($context);
$this->_helperModule = $helperModule;
$this->config = $config;
$this->fileFactory = $fileFactory;
$this->_importPath = BP . '/' . DirectoryList::VAR_DIR . '/';
$this->_parser = new \Magento\Framework\Xml\Parser();
}
/**
* Export Varnish Configuration as .vcl
*
* @return \Magento\Framework\App\ResponseInterface
*/
public function execute()
{
try {
$xmlPath = $this->_importPath . 'cms_pages.xml';
$overwrite = false;
if($this->_helperModule->getConfigData("import_export/import/overwrite_pages")) {
$overwrite = true;
}
if (!is_readable($xmlPath))
{
throw new \Exception(
__("Can't get the data file for import cms blocks/pages: ".$xmlPath)
);
}
$data = $this->_parser->load($xmlPath)->xmlToArray();
$cms_collection = null;
$conflictingOldItems = array();
$i = 0;
foreach($data['root']['pages']['item'] as $_item) {
$exist = false;
$collection = $this->_objectManager->create('Magento\Cms\Model\Page')->getCollection();
$collection->addFieldToFilter('identifier', $_item['identifier']);
if($collection->getSize())
$exist = true;
$page = $this->_objectManager->create('Magento\Cms\Model\Page');
if($overwrite) {
if($exist) {
$conflictingOldItems[] = $_item['identifier'];
$page->load($_item['identifier']);
}
} else {
if($exist) {
continue;
}
}
$_item['store_id'] = array(0);
$page->addData($_item)->save();
$i++;
}
$this->messageManager->addSuccess(__('Imported %1 Item(s). ( %2 )', $i, implode("\n", $conflictingOldItems)));
} catch (\Exception $exception) {
$this->messageManager->addError($exception->getMessage());
}
$this->_redirect('*/system_config/edit/section/import_export', array('website' => $this->getRequest()->getParam('website')));
}
}
?>
\ No newline at end of file
<?php
/**
*
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\RokanBase\Controller\Catalog\Product\Compare;
use Magento\Framework\Exception\NoSuchEntityException;
class Add extends \Magento\Catalog\Controller\Product\Compare
{
/**
* Add item to compare list
*
* @return \Magento\Framework\Controller\ResultInterface
*/
public function execute()
{
$resultRedirect = $this->resultRedirectFactory->create();
if (!$this->_formKeyValidator->validate($this->getRequest())) {
$resultRedirect->setPath('catalog/product_compare/index');
return $resultRedirect;
}
$productId = (int)$this->getRequest()->getParam('product');
if ($productId && ($this->_customerVisitor->getId() || $this->_customerSession->isLoggedIn())) {
$storeId = $this->_storeManager->getStore()->getId();
try {
$product = $this->productRepository->getById($productId, false, $storeId);
} catch (NoSuchEntityException $e) {
$product = null;
}
if ($product) {
$this->_catalogProductCompareList->addProduct($product);
$productName = $this->_objectManager->get(
\Magento\Framework\Escaper::class
)->escapeHtml($product->getName());
$this->messageManager->addSuccess(__('You added product %1 to the comparison list.', $productName));
$this->_eventManager->dispatch('catalog_product_compare_add_product', ['product' => $product]);
}
$this->_objectManager->get(\Magento\Catalog\Helper\Product\Compare::class)->calculate();
}
$resultRedirect->setPath('catalog/product_compare/index');
return $resultRedirect;
}
}
<?php
/**
*
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\RokanBase\Controller\Checkout\Cart;
use Magento\Catalog\Api\ProductRepositoryInterface;
use Magento\Checkout\Model\Cart as CustomerCart;
use Magento\Framework\Exception\NoSuchEntityException;
/**
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
*/
class Add extends \Magento\Checkout\Controller\Cart\Add
{
/**
* Add product to shopping cart action
*
* @return \Magento\Framework\Controller\Result\Redirect
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
*/
protected $_messege = '';
protected $_result = [];
public function execute()
{
if (!$this->_formKeyValidator->validate($this->getRequest())) {
return $this->resultRedirectFactory->create()->setPath('*/*/');
}
$params = $this->getRequest()->getParams();
try {
if (isset($params['qty'])) {
$filter = new \Zend_Filter_LocalizedToNormalized(
['locale' => $this->_objectManager->get('Magento\Framework\Locale\ResolverInterface')->getLocale()]
);
$params['qty'] = $filter->filter($params['qty']);
}
$product = $this->_initProduct();
$related = $this->getRequest()->getParam('related_product');
/**
* Check product availability
*/
if (!$product) {
return $this->goBack();
}
$this->cart->addProduct($product, $params);
if (!empty($related)) {
$this->cart->addProductsByIds(explode(',', $related));
}
$this->cart->save();
/**
* @todo remove wishlist observer \Magento\Wishlist\Observer\AddToCart
*/
$this->_eventManager->dispatch(
'checkout_cart_add_product_complete',
['product' => $product, 'request' => $this->getRequest(), 'response' => $this->getResponse()]
);
if (!$this->_checkoutSession->getNoCartRedirect(true)) {
if (!$this->cart->getQuote()->getHasError()) {
$message = __(
'You added %1 to your shopping cart.',
$product->getName()
);
$this->_messege = $message;
$this->messageManager->addSuccessMessage($message);
}
$this->_result['html'] = $this->_getHtmlResponeAjaxCart($product);
return $this->goBack(null, $product);
}
} catch (\Magento\Framework\Exception\LocalizedException $e) {
if ($this->_checkoutSession->getUseNotice(true)) {
$this->messageManager->addNotice(
$this->_objectManager->get('Magento\Framework\Escaper')->escapeHtml($e->getMessage())
);
} else {
$messages = array_unique(explode("\n", $e->getMessage()));
foreach ($messages as $message) {
$this->messageManager->addError(
$this->_objectManager->get('Magento\Framework\Escaper')->escapeHtml($message)
);
}
$messages = $this->messageManager->getMessages(true);
}
$url = $this->_checkoutSession->getRedirectUrl(true);
if (!$url) {
$cartUrl = $this->_objectManager->get('Magento\Checkout\Helper\Cart')->getCartUrl();
$url = $this->_redirect->getRedirectUrl($cartUrl);
}
return $this->goBack($url);
} catch (\Exception $e) {
$this->messageManager->addException($e, __('We can\'t add this item to your shopping cart right now.'));
$this->_objectManager->get('Psr\Log\LoggerInterface')->critical($e);
return $this->goBack();
}
}
/**
* Resolve response
*
* @param string $backUrl
* @param \Magento\Catalog\Model\Product $product
* @return $this|\Magento\Framework\Controller\Result\Redirect
*/
protected function goBack($backUrl = null, $product = null)
{
if (!$this->getRequest()->isAjax()) {
return parent::_goBack($backUrl);
}
$result = $this->_result;
if ($backUrl || $backUrl = $this->getBackUrl()) {
$result['backUrl'] = $backUrl;
} else {
if ($product && !$product->getIsSalable()) {
$result['product'] = [
'statusText' => __('Out of stock')
];
}
}
$this->getResponse()->representJson(
$this->_objectManager->get('Magento\Framework\Json\Helper\Data')->jsonEncode($result)
);
}
protected function _getHtmlResponeAjaxCart($product)
{
$message = __('You added <a href="'. $product->getProductUrl() .'">%1</a> to your shopping cart.',
$product->getName()
);
$html = '<div class="popup_avaiable">'.$message.'<br>
<div class="action_button">
<ul>
<li>
<button title="'. __('Continue Shopping') . '" class="button btn-continue" onclick="jQuery.fancybox.close();">'. __('Continue Shopping') . '</button>
</li>
<li>
<a title="Checkout" class="button btn-viewcart" href="'. $this->_url->getUrl('checkout/cart') .'"><span>'. __('View cart &amp; checkout'). '</span></a>
</li>
</ul>
</div>
</div>';
return $html;
}
}
<?php
/**
* @Author: Harry - Hai Le
* @Email: hailt1911@gmail.com
* @File Name: Data.php
* @File Path:
* @Date: 2015-04-07 19:26:42
* @Last Modified by: zero
* @Last Modified time: 2015-07-28 08:35:17
*/
namespace Rokanthemes\RokanBase\Helper;
class Data extends \Magento\Framework\App\Helper\AbstractHelper {
public function __construct(
\Magento\Framework\App\Helper\Context $context
) {
parent::__construct($context);
}
public function getConfigData($path)
{
$value = $this->scopeConfig->getValue($path, \Magento\Store\Model\ScopeInterface::SCOPE_STORE);
return $value;
}
public function getInstockLabel($product)
{
if($label = $product->getDeliveryLabel())
return $label;
if($label = $this->getConfigData('cataloginventory/options/delivery_label'))
return $label;
return __('In Stock');
}
}
<?php
namespace Rokanthemes\RokanBase\Model\Rewrite\Store;
class StoreManager extends \Magento\Store\Model\StoreManager
{
public function getStore($storeId = null)
{
if (!isset($storeId) || '' === $storeId || $storeId === true) {
if (null === $this->currentStoreId || '' === $this->currentStoreId) {
\Magento\Framework\Profiler::start('store.resolve');
$this->currentStoreId = $this->storeResolver->getCurrentStoreId();
\Magento\Framework\Profiler::stop('store.resolve');
}
$storeId = $this->currentStoreId;
}
if ($storeId instanceof \Magento\Store\Api\Data\StoreInterface) {
return $storeId;
}
$store = is_numeric($storeId)
? $this->storeRepository->getById($storeId)
: $this->storeRepository->get($storeId);
return $store;
}
}
<?php
namespace Rokanthemes\RokanBase\Setup;
use Magento\Framework\Setup\InstallDataInterface;
use Magento\Framework\Setup\ModuleContextInterface;
use Magento\Framework\Setup\ModuleDataSetupInterface;
use Magento\Eav\Setup\EavSetupFactory;
use Magento\Eav\Setup\EavSetup;
/**
* @codeCoverageIgnore
*/
class InstallData implements InstallDataInterface{
/**
* {@inheritdoc}
*/
/**
* EAV setup factory
*
* @var EavSetupFactory
*/
private $eavSetupFactory;
/**
* Init
*
* @param EavSetupFactory $eavSetupFactory
*/
public function __construct(EavSetupFactory $eavSetupFactory)
{
$this->eavSetupFactory = $eavSetupFactory;
}
public function install(ModuleDataSetupInterface $setup, ModuleContextInterface $context)
{
/** @var EavSetup $eavSetup */
$eavSetup = $this->eavSetupFactory->create(['setup' => $setup]);
$installer = $setup;
$installer->startSetup();
$installer->endSetup();
}
}
{
"name": "rokanthemes/module-RokanBase",
"description": "N/A",
"require": {
"php": "~5.5.0|~5.6.0|~7.0.0"
},
"type": "magento2-module",
"version": "1.0.0",
"license": [
"OSL-3.0",
"AFL-3.0"
],
"autoload": {
"files": [ "registration.php" ],
"psr-4": {
"Rokanthemes\\RokanBase\\": ""
}
}
}
<?xml version="1.0"?>
<!--
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:Acl/etc/acl.xsd">
<acl>
<resources>
<resource id="Magento_Backend::admin">
<resource id="Rokanthemes_RokanBase::rokanbase" title="Rokanthemes" translate="title" sortOrder="30">
<resource id="Rokanthemes_RokanBase::rokanbase_setting" title="Configuration" translate="title" sortOrder="10">
<resource id="Rokanthemes_RokanBase::rokanbase_import_export" title="Import and Export" translate="title" sortOrder="10" />
</resource>
</resource>
</resource>
</resources>
</acl>
</config>
<?xml version="1.0"?>
<!--
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Backend:etc/menu.xsd">
<menu>
<add id="Rokanthemes_RokanBase::rokanbase" title="Rokanthemes" module="Rokanthemes_RokanBase" sortOrder="50" resource="Rokanthemes_RokanBase::rokanbase"/>
<add id="Rokanthemes_RokanBase::rokanbase_setting" parent="Rokanthemes_RokanBase::rokanbase" title="Configuration" module="Rokanthemes_RokanBase" sortOrder="100" resource="Rokanthemes_RokanBase::rokanbase_setting"/>
<add id="Rokanthemes_RokanBase::rokanbase_import_export" parent="Rokanthemes_RokanBase::rokanbase_setting" title="Import and Export" module="Rokanthemes_RokanBase" sortOrder="100" resource="Rokanthemes_RokanBase::rokanbase_import_export" action="adminhtml/system_config/edit/section/import_export" />
</menu>
</config>
<?xml version="1.0"?>
<!--
/**
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:App/etc/routes.xsd">
<router id="admin">
<route id="adminhtml">
<module name="Rokanthemes_RokanBase" before="Magento_Backend" />
</route>
</router>
</config>
<?xml version="1.0"?>
<!--
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../Config/etc/system_file.xsd">
<system>
<tab id="rokanthemes" translate="label" sortOrder="400">
<label>Rokanthemes</label>
</tab>
<section id="import_export" translate="label" type="text" sortOrder="500" showInDefault="1" showInWebsite="1" showInStore="1">
<class>separator-top</class>
<label>Import - Export</label>
<tab>rokanthemes</tab>
<resource>Rokanthemes_RokanBase::rokanbase_import_export</resource>
<group id="import" translate="label" type="text" sortOrder="10" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Import</label>
<field id="overwrite_blocks" translate="label comment" type="select" sortOrder="0" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Overwrite Blocks</label>
<source_model>Magento\Config\Model\Config\Source\Yesno</source_model>
<comment>Set to 'Yes', if you want to overwrite blocks.</comment>
</field>
<field id="static_block" translate="label comment" type="button" sortOrder="0" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Static Blocks</label>
<frontend_model>Rokanthemes\RokanBase\Block\Adminhtml\Button\Import\Block</frontend_model>
</field>
<field id="overwrite_pages" translate="label comment" type="select" sortOrder="0" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Overwrite Pages</label>
<source_model>Magento\Config\Model\Config\Source\Yesno</source_model>
<comment>Set to 'Yes', if you want to overwrite blocks.</comment>
</field>
<field id="import_pages" translate="label comment" type="button" sortOrder="0" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Custom Pages</label>
<frontend_model>Rokanthemes\RokanBase\Block\Adminhtml\Button\Import\Page</frontend_model>
</field>
</group>
<group id="export" translate="label" type="text" sortOrder="20" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Export</label>
<field id="static_block" translate="label comment" type="button" sortOrder="0" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Static Blocks</label>
<frontend_model>Rokanthemes\RokanBase\Block\Adminhtml\Button\Export\Block</frontend_model>
</field>
<field id="export_pages" translate="label comment" type="button" sortOrder="0" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Custom Pages</label>
<frontend_model>Rokanthemes\RokanBase\Block\Adminhtml\Button\Export\Page</frontend_model>
</field>
</group>
</section>
<section id="general">
<group id="country">
<field id="flag" translate="label" type="image" sortOrder="100" showInDefault="1" showInWebsite="1" showInStore="1">
<label>Flag Image</label>
<comment>Allowed file types:PNG, GIF, JPG, JPEG, SVG.</comment>
<backend_model>Magento\Config\Model\Config\Backend\Image\Logo</backend_model>
<base_url type="media" scope_info="1">logo</base_url>
</field>
</group>
</section>
</system>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../Magento/Store/etc/config.xsd">
<default>
<cataloginventory>
<options>
<delivery_label>Ship In 3 - 5 days</delivery_label>
</options>
</cataloginventory>
<csp>
<mode>
<storefront>
<report_only>0</report_only>
</storefront>
<admin>
<report_only>0</report_only>
</admin>
</mode>
</csp>
</default>
</config>
<?xml version="1.0"?>
<csp_whitelist xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Csp/etc/csp_whitelist.xsd">
<policies>
<policy id="script-src">
<values>
<value id="cloudflare" type="host">*.cloudflare.com</value>
<value id="twitter.com" type="host">*.twitter.com</value>
<value id="google-analytics" type="host">*.google-analytics.com</value>
<value id="twimg" type="host">*.twimg.com</value>
<value id="gstatic" type="host">*.gstatic.com</value>
<value id="trustedshops" type="host">*.trustedshops.com</value>
<value id="usercentrics" type="host">*.usercentrics.eu</value>
<value id="fontawesome" type="host">*.fontawesome.com</value>
<value id="google.com" type="host">*.google.com</value>
<value id="youtube.com" type="host">*.youtube.com</value>
<value id="maps.googleapis.com" type="host">maps.googleapis.com</value>
<value id="scontent.cdninstagram.com" type="host">scontent.cdninstagram.com</value>
</values>
</policy>
<policy id="style-src">
<values>
<value id="cloudflare" type="host">*.cloudflare.com</value>
<value id="googleapis" type="host">*.googleapis.com</value>
<value id="twitter.com" type="host">*.twitter.com</value>
<value id="twimg" type="host">*.twimg.com</value>
<value id="gstatic" type="host">*.gstatic.com</value>
<value id="typekit" type="host">*.typekit.net</value>
<value id="trustedshops" type="host">*.trustedshops.com</value>
<value id="usercentrics" type="host">*.usercentrics.eu</value>
<value id="fontawesome" type="host">*.fontawesome.com</value>
<value id="google.com" type="host">*.google.com</value>
<value id="youtube.com" type="host">*.youtube.com</value>
<value id="maps.googleapis.com" type="host">maps.googleapis.com</value>
<value id="scontent.cdninstagram.com" type="host">scontent.cdninstagram.com</value>
</values>
</policy>
<policy id="img-src">
<values>
<value id="cloudflare" type="host">*.cloudflare.com</value>
<value id="klarna-base" type="host">*.klarna.com</value>
<value id="googleadservices" type="host">*.googleadservices.com</value>
<value id="google-analytics" type="host">*.google-analytics.com</value>
<value id="paypal" type="host">*.paypal.com</value>
<value id="twitter.com" type="host">*.twitter.com</value>
<value id="twimg" type="host">*.twimg.com</value>
<value id="vimeocdn" type="host">*.vimeocdn.com</value>
<value id="youtube-img" type="host">*.ytimg.com</value>
<value id="data" type="host">'self' data:</value>
<value id="lightemporium" type="host">*.lightemporium.com</value>
<value id="usercentrics" type="host">*.usercentrics.eu</value>
<value id="google.com" type="host">*.google.com</value>
<value id="youtube.com" type="host">*.youtube.com</value>
<value id="maps.googleapis.com" type="host">maps.googleapis.com</value>
<value id="scontent.cdninstagram.com" type="host">scontent.cdninstagram.com</value>
</values>
</policy>
<policy id="connect-src">
<values>
<value id="cloudflare" type="host">*.cloudflare.com</value>
<value id="twitter.com" type="host">*.twitter.com</value>
<value id="paypal" type="host">*.paypal.com</value>
<value id="twimg" type="host">*.twimg.com</value>
<value id="google.com" type="host">*.google.com</value>
<value id="youtube.com" type="host">*.youtube.com</value>
<value id="maps.googleapis.com" type="host">maps.googleapis.com</value>
<value id="scontent.cdninstagram.com" type="host">scontent.cdninstagram.com</value>
</values>
</policy>
<policy id="font-src">
<values>
<value id="cloudflare" type="host">*.cloudflare.com</value>
<value id="twitter.com" type="host">*.twitter.com</value>
<value id="gstatic" type="host">*.gstatic.com</value>
<value id="typekit" type="host">*.typekit.net</value>
<value id="twimg" type="host">*.twimg.com</value>
<value id="trustedshops" type="host">*.trustedshops.com</value>
<value id="googleapis" type="host">*.googleapis.com</value>
<value id="google.com" type="host">*.google.com</value>
<value id="youtube.com" type="host">*.youtube.com</value>
<value id="maps.googleapis.com" type="host">maps.googleapis.com</value>
<value id="scontent.cdninstagram.com" type="host">scontent.cdninstagram.com</value>
</values>
</policy>
<policy id="frame-src">
<values>
<value id="twitter.com" type="host">*.twitter.com</value>
<value id="google.com" type="host">*.google.com</value>
<value id="youtube.com" type="host">*.youtube.com</value>
<value id="maps.googleapis.com" type="host">maps.googleapis.com</value>
<value id="scontent.cdninstagram.com" type="host">scontent.cdninstagram.com</value>
</values>
</policy>
<policy id="form-action">
<values>
<value id="twitter.com" type="host">*.twitter.com</value>
<value id="google.com" type="host">*.google.com</value>
<value id="youtube.com" type="host">*.youtube.com</value>
<value id="maps.googleapis.com" type="host">maps.googleapis.com</value>
<value id="scontent.cdninstagram.com" type="host">scontent.cdninstagram.com</value>
</values>
</policy>
</policies>
</csp_whitelist>
\ No newline at end of file
<?xml version="1.0"?>
<!--
/**
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
<preference for="Magento\Checkout\Controller\Cart\Add" type="Rokanthemes\RokanBase\Controller\Checkout\Cart\Add" />
<!-- <preference for="Magento\Catalog\Controller\Product\Compare\Add" type="Rokanthemes\RokanBase\Controller\Catalog\Product\Compare\Add" /> -->
<!--<preference for="Magento\Store\Model\StoreManager" type="Rokanthemes\RokanBase\Model\Rewrite\Store\StoreManager" />-->
</config>
<?xml version="1.0"?>
<!--
/**
* Copyright © 2016 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:App/etc/routes.xsd">
<router id="standard">
<route id="rokanbase" frontName="rokanbase">
<module name="Rokanthemes_RokanBase" />
</route>
</router>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../lib/internal/Magento/Framework/Module/etc/module.xsd">
<module name="Rokanthemes_RokanBase" setup_version="1.0.0" />
</config>
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
\Magento\Framework\Component\ComponentRegistrar::register(
\Magento\Framework\Component\ComponentRegistrar::MODULE,
'Rokanthemes_RokanBase',
__DIR__
);
<?xml version="1.0"?>
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../lib/internal/Magento/Framework/View/Layout/etc/page_configuration.xsd">
<head>
<link src="Rokanthemes_RokanBase::css/chosen.css"/>
<link src="Rokanthemes_RokanBase::css/jquery.fancybox.css"/>
</head>
</page>
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
var config = {
"shim": {
"rokanthemes/owl": ["jquery"],
"rokanthemes/elevatezoom": ["jquery"],
"rokanthemes/choose": ["jquery"],
"rokanthemes/fancybox": ["jquery"],
"rokanthemes/lazyloadimg": ["jquery"]
},
'paths': {
'rokanthemes/fancybox': 'Rokanthemes_RokanBase/js/jquery_fancybox',
"rokanthemes/owl": "Rokanthemes_RokanBase/js/owl_carousel",
"rokanthemes/elevatezoom": "Rokanthemes_RokanBase/js/jquery.elevatezoom",
"rokanthemes/choose": "Rokanthemes_RokanBase/js/jquery_choose",
"rokanthemes/equalheight": "Rokanthemes_RokanBase/js/equalheight",
'rokanthemes/lazyloadimg': 'Rokanthemes_RokanBase/js/jquery.lazyload.min'
},
"deps": ['rokanthemes/theme']
};
/*!
Chosen, a Select Box Enhancer for jQuery and Prototype
by Patrick Filler for Harvest, http://getharvest.com
Version 1.4.2
Full source at https://github.com/harvesthq/chosen
Copyright (c) 2011-2015 Harvest http://getharvest.com
MIT License, https://github.com/harvesthq/chosen/blob/master/LICENSE.md
This file is generated by `grunt build`, do not edit it by hand.
*/
/* @group Base */
.chosen-container {
position: relative;
display: inline-block;
vertical-align: middle;
zoom: 1;
*display: inline;
-webkit-user-select: none;
-moz-user-select: none;
user-select: none;
}
.chosen-container * {
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
}
.chosen-container .chosen-drop {
position: absolute;
top: 100%;
left: -9999px;
z-index: 1010;
width: 100%;
border: 1px solid #e8e8e8;
border-top: 0;
background: #fff;
}
.chosen-container.chosen-with-drop .chosen-drop {
left: 0;
}
.chosen-container a {
cursor: pointer;
}
.chosen-container .search-choice .group-name, .chosen-container .chosen-single .group-name {
margin-right: 4px;
overflow: hidden;
white-space: nowrap;
text-overflow: ellipsis;
font-weight: normal;
color: #999999;
}
.chosen-container .search-choice .group-name:after, .chosen-container .chosen-single .group-name:after {
content: ":";
padding-left: 2px;
vertical-align: top;
}
/* @end */
/* @group Single Chosen */
.chosen-container-single .chosen-single {
position: relative;
display: block;
border: 1px solid #e8e8e8;
background-color: #fff;
text-decoration: none;
white-space: nowrap;
padding: 6px 15px;
color: inherit;
}
.chosen-container-single .chosen-default {
color: #999;
}
.chosen-container-single .chosen-single span {
display: block;
overflow: hidden;
margin-right: 26px;
text-overflow: ellipsis;
white-space: nowrap;
}
.chosen-container-single .chosen-single-with-deselect span {
margin-right: 38px;
}
.chosen-container-single .chosen-single abbr {
position: absolute;
top: 6px;
right: 26px;
display: block;
width: 12px;
height: 12px;
background: url('chosen-sprite.png') -42px 1px no-repeat;
font-size: 1px;
}
.chosen-container-single .chosen-single abbr:hover {
background-position: -42px -10px;
}
.chosen-container-single.chosen-disabled .chosen-single abbr:hover {
background-position: -42px -10px;
}
.chosen-container-single .chosen-single div {
position: absolute;
top: 50%;
right: 10px;
display: block;
width: 20px;
height: 20px;
text-align: center;
line-height: 20px;
-webkit-transform: translateY(-50%);
-ms-transform: translateY(-50%);
-o-transform: translateY(-50%);
transform: translateY(-50%);
}
.chosen-container-single .chosen-single div b {
display: block;
width: 100%;
height: 100%;
}
.chosen-container-single .chosen-single div b:before{
font-family: 'FontAwesome';
content: "\f0d7";
}
.chosen-container-single .chosen-search {
position: relative;
z-index: 1010;
margin: 0;
padding: 3px 4px;
white-space: nowrap;
}
.chosen-container-single .chosen-search input[type="text"] {
margin: 1px 0;
padding: 6px 15px;
width: 100%;
height: auto;
outline: 0;
border: 1px solid #e8e8e8;
line-height: normal;
border-radius: 0;
}
.chosen-container-single .chosen-drop {
margin-top: -1px;
background-clip: padding-box;
}
.chosen-container-single.chosen-container-single-nosearch .chosen-search {
position: absolute;
left: -9999px;
}
/* @end */
/* @group Results */
.chosen-container .chosen-results {
position: relative;
overflow-x: hidden;
overflow-y: auto;
margin: 0 4px 4px 0;
padding: 0 0 0 4px;
max-height: 240px;
-webkit-overflow-scrolling: touch;
}
.chosen-container .chosen-results li {
display: none;
margin: 0;
padding: 5px 6px;
list-style: none;
word-wrap: break-word;
-webkit-touch-callout: none;
}
.chosen-container .chosen-results li.active-result {
display: list-item;
cursor: pointer;
}
.chosen-container .chosen-results li.disabled-result {
display: list-item;
color: #ccc;
cursor: default;
}
.chosen-container .chosen-results li.highlighted {
background-color: #b11e22;
color: #fff;
}
.chosen-container .chosen-results li.no-results {
color: #777;
display: list-item;
background: #fafafa;
}
.chosen-container .chosen-results li.group-result {
display: list-item;
font-weight: bold;
cursor: default;
}
.chosen-container .chosen-results li.group-option {
padding-left: 15px;
}
.chosen-container .chosen-results li em {
font-style: normal;
text-decoration: underline;
}
/* @end */
/* @group Multi Chosen */
.chosen-container-multi .chosen-choices {
position: relative;
overflow: hidden;
margin: 0;
padding: 0 5px;
width: 100%;
height: auto !important;
height: 1%;
border: 1px solid #aaa;
background-color: #fff;
background-image: -webkit-gradient(linear, 50% 0%, 50% 100%, color-stop(1%, #eeeeee), color-stop(15%, #ffffff));
background-image: -webkit-linear-gradient(#eeeeee 1%, #ffffff 15%);
background-image: -moz-linear-gradient(#eeeeee 1%, #ffffff 15%);
background-image: -o-linear-gradient(#eeeeee 1%, #ffffff 15%);
background-image: linear-gradient(#eeeeee 1%, #ffffff 15%);
cursor: text;
}
.chosen-container-multi .chosen-choices li {
float: left;
list-style: none;
}
.chosen-container-multi .chosen-choices li.search-field {
margin: 0;
padding: 0;
white-space: nowrap;
}
.chosen-container-multi .chosen-choices li.search-field input[type="text"] {
margin: 1px 0;
padding: 0;
height: 25px;
outline: 0;
border: 0 !important;
background: transparent !important;
box-shadow: none;
color: #999;
font-size: 100%;
font-family: sans-serif;
line-height: normal;
border-radius: 0;
}
.chosen-container-multi .chosen-choices li.search-choice {
position: relative;
margin: 3px 5px 3px 0;
padding: 3px 20px 3px 5px;
border: 1px solid #aaa;
max-width: 100%;
border-radius: 3px;
background-color: #eeeeee;
background-image: -webkit-gradient(linear, 50% 0%, 50% 100%, color-stop(20%, #f4f4f4), color-stop(50%, #f0f0f0), color-stop(52%, #e8e8e8), color-stop(100%, #eeeeee));
background-image: -webkit-linear-gradient(#f4f4f4 20%, #f0f0f0 50%, #e8e8e8 52%, #eeeeee 100%);
background-image: -moz-linear-gradient(#f4f4f4 20%, #f0f0f0 50%, #e8e8e8 52%, #eeeeee 100%);
background-image: -o-linear-gradient(#f4f4f4 20%, #f0f0f0 50%, #e8e8e8 52%, #eeeeee 100%);
background-image: linear-gradient(#f4f4f4 20%, #f0f0f0 50%, #e8e8e8 52%, #eeeeee 100%);
background-size: 100% 19px;
background-repeat: repeat-x;
background-clip: padding-box;
box-shadow: 0 0 2px white inset, 0 1px 0 rgba(0, 0, 0, 0.05);
color: #333;
line-height: 13px;
cursor: default;
}
.chosen-container-multi .chosen-choices li.search-choice span {
word-wrap: break-word;
}
.chosen-container-multi .chosen-choices li.search-choice .search-choice-close {
position: absolute;
top: 4px;
right: 3px;
display: block;
width: 12px;
height: 12px;
background: url('chosen-sprite.png') -42px 1px no-repeat;
font-size: 1px;
}
.chosen-container-multi .chosen-choices li.search-choice .search-choice-close:hover {
background-position: -42px -10px;
}
.chosen-container-multi .chosen-choices li.search-choice-disabled {
padding-right: 5px;
border: 1px solid #ccc;
background-color: #e4e4e4;
background-image: -webkit-gradient(linear, 50% 0%, 50% 100%, color-stop(20%, #f4f4f4), color-stop(50%, #f0f0f0), color-stop(52%, #e8e8e8), color-stop(100%, #eeeeee));
background-image: -webkit-linear-gradient(top, #f4f4f4 20%, #f0f0f0 50%, #e8e8e8 52%, #eeeeee 100%);
background-image: -moz-linear-gradient(top, #f4f4f4 20%, #f0f0f0 50%, #e8e8e8 52%, #eeeeee 100%);
background-image: -o-linear-gradient(top, #f4f4f4 20%, #f0f0f0 50%, #e8e8e8 52%, #eeeeee 100%);
background-image: linear-gradient(top, #f4f4f4 20%, #f0f0f0 50%, #e8e8e8 52%, #eeeeee 100%);
color: #666;
}
.chosen-container-multi .chosen-choices li.search-choice-focus {
background: #d4d4d4;
}
.chosen-container-multi .chosen-choices li.search-choice-focus .search-choice-close {
background-position: -42px -10px;
}
.chosen-container-multi .chosen-results {
margin: 0;
padding: 0;
}
.chosen-container-multi .chosen-drop .result-selected {
display: list-item;
color: #ccc;
cursor: default;
}
/* @end */
/* @group Active */
.chosen-container-active.chosen-with-drop .chosen-single div {
border-left: none;
background: transparent;
}
.chosen-container-active .chosen-choices li.search-field input[type="text"] {
color: #222 !important;
}
/* @end */
/* @group Disabled Support */
.chosen-disabled {
opacity: 0.5 !important;
cursor: default;
}
.chosen-disabled .chosen-single {
cursor: default;
}
.chosen-disabled .chosen-choices .search-choice .search-choice-close {
cursor: default;
}
/* @end */
/* @group Right to Left */
.chosen-rtl {
text-align: right;
}
.chosen-rtl .chosen-single {
overflow: visible;
padding: 0 8px 0 0;
}
.chosen-rtl .chosen-single span {
margin-right: 0;
margin-left: 26px;
direction: rtl;
}
.chosen-rtl .chosen-single-with-deselect span {
margin-left: 38px;
}
.chosen-rtl .chosen-single div {
right: auto;
left: 3px;
}
.chosen-rtl .chosen-single abbr {
right: auto;
left: 26px;
}
.chosen-rtl .chosen-choices li {
float: right;
}
.chosen-rtl .chosen-choices li.search-field input[type="text"] {
direction: rtl;
}
.chosen-rtl .chosen-choices li.search-choice {
margin: 3px 5px 3px 0;
padding: 3px 5px 3px 19px;
}
.chosen-rtl .chosen-choices li.search-choice .search-choice-close {
right: auto;
left: 4px;
}
.chosen-rtl.chosen-container-single-nosearch .chosen-search,
.chosen-rtl .chosen-drop {
left: 9999px;
}
.chosen-rtl.chosen-container-single .chosen-results {
margin: 0 0 4px 4px;
padding: 0 4px 0 0;
}
.chosen-rtl .chosen-results li.group-option {
padding-right: 15px;
padding-left: 0;
}
.chosen-rtl.chosen-container-active.chosen-with-drop .chosen-single div {
border-right: none;
}
.chosen-rtl .chosen-search input[type="text"] {
padding: 4px 5px 4px 20px;
background: white url('chosen-sprite.png') no-repeat -30px -20px;
background: url('chosen-sprite.png') no-repeat -30px -20px;
direction: rtl;
}
.chosen-rtl.chosen-container-single .chosen-single div b {
background-position: 6px 2px;
}
.chosen-rtl.chosen-container-single.chosen-with-drop .chosen-single div b {
background-position: -12px 2px;
}
/* @end */
#fancybox-buttons {
position: fixed;
left: 0;
width: 100%;
z-index: 8050;
}
#fancybox-buttons.top {
top: 10px;
}
#fancybox-buttons.bottom {
bottom: 10px;
}
#fancybox-buttons ul {
display: block;
width: 166px;
height: 30px;
margin: 0 auto;
padding: 0;
list-style: none;
border: 1px solid #111;
border-radius: 3px;
-webkit-box-shadow: inset 0 0 0 1px rgba(255,255,255,.05);
-moz-box-shadow: inset 0 0 0 1px rgba(255,255,255,.05);
box-shadow: inset 0 0 0 1px rgba(255,255,255,.05);
background: rgb(50,50,50);
background: -moz-linear-gradient(top, rgb(68,68,68) 0%, rgb(52,52,52) 50%, rgb(41,41,41) 50%, rgb(51,51,51) 100%);
background: -webkit-gradient(linear, left top, left bottom, color-stop(0%,rgb(68,68,68)), color-stop(50%,rgb(52,52,52)), color-stop(50%,rgb(41,41,41)), color-stop(100%,rgb(51,51,51)));
background: -webkit-linear-gradient(top, rgb(68,68,68) 0%,rgb(52,52,52) 50%,rgb(41,41,41) 50%,rgb(51,51,51) 100%);
background: -o-linear-gradient(top, rgb(68,68,68) 0%,rgb(52,52,52) 50%,rgb(41,41,41) 50%,rgb(51,51,51) 100%);
background: -ms-linear-gradient(top, rgb(68,68,68) 0%,rgb(52,52,52) 50%,rgb(41,41,41) 50%,rgb(51,51,51) 100%);
background: linear-gradient(top, rgb(68,68,68) 0%,rgb(52,52,52) 50%,rgb(41,41,41) 50%,rgb(51,51,51) 100%);
filter: progid:DXImageTransform.Microsoft.gradient( startColorstr='#444444', endColorstr='#222222',GradientType=0 );
}
#fancybox-buttons ul li {
float: left;
margin: 0;
padding: 0;
}
#fancybox-buttons a {
display: block;
width: 30px;
height: 30px;
text-indent: -9999px;
background-color: transparent;
background-image: url('fancybox_buttons.png');
background-repeat: no-repeat;
outline: none;
opacity: 0.8;
}
#fancybox-buttons a:hover {
opacity: 1;
}
#fancybox-buttons a.btnPrev {
background-position: 5px 0;
}
#fancybox-buttons a.btnNext {
background-position: -33px 0;
border-right: 1px solid #3e3e3e;
}
#fancybox-buttons a.btnPlay {
background-position: 0 -30px;
}
#fancybox-buttons a.btnPlayOn {
background-position: -30px -30px;
}
#fancybox-buttons a.btnToggle {
background-position: 3px -60px;
border-left: 1px solid #111;
border-right: 1px solid #3e3e3e;
width: 35px
}
#fancybox-buttons a.btnToggleOn {
background-position: -27px -60px;
}
#fancybox-buttons a.btnClose {
border-left: 1px solid #111;
width: 35px;
background-position: -56px 0px;
}
#fancybox-buttons a.btnDisabled {
opacity : 0.4;
cursor: default;
}
\ No newline at end of file
/*!
* Buttons helper for fancyBox
* version: 1.0.5 (Mon, 15 Oct 2012)
* @requires fancyBox v2.0 or later
*
* Usage:
* $(".fancybox").fancybox({
* helpers : {
* buttons: {
* position : 'top'
* }
* }
* });
*
*/
(function ($) {
//Shortcut for fancyBox object
var F = $.fancybox;
//Add helper object
F.helpers.buttons = {
defaults : {
skipSingle : false, // disables if gallery contains single image
position : 'top', // 'top' or 'bottom'
tpl : '<div id="fancybox-buttons"><ul><li><a class="btnPrev" title="Previous" href="javascript:;"></a></li><li><a class="btnPlay" title="Start slideshow" href="javascript:;"></a></li><li><a class="btnNext" title="Next" href="javascript:;"></a></li><li><a class="btnToggle" title="Toggle size" href="javascript:;"></a></li><li><a class="btnClose" title="Close" href="javascript:;"></a></li></ul></div>'
},
list : null,
buttons: null,
beforeLoad: function (opts, obj) {
//Remove self if gallery do not have at least two items
if (opts.skipSingle && obj.group.length < 2) {
obj.helpers.buttons = false;
obj.closeBtn = true;
return;
}
//Increase top margin to give space for buttons
obj.margin[ opts.position === 'bottom' ? 2 : 0 ] += 30;
},
onPlayStart: function () {
if (this.buttons) {
this.buttons.play.attr('title', 'Pause slideshow').addClass('btnPlayOn');
}
},
onPlayEnd: function () {
if (this.buttons) {
this.buttons.play.attr('title', 'Start slideshow').removeClass('btnPlayOn');
}
},
afterShow: function (opts, obj) {
var buttons = this.buttons;
if (!buttons) {
this.list = $(opts.tpl).addClass(opts.position).appendTo('body');
buttons = {
prev : this.list.find('.btnPrev').click( F.prev ),
next : this.list.find('.btnNext').click( F.next ),
play : this.list.find('.btnPlay').click( F.play ),
toggle : this.list.find('.btnToggle').click( F.toggle ),
close : this.list.find('.btnClose').click( F.close )
}
}
//Prev
if (obj.index > 0 || obj.loop) {
buttons.prev.removeClass('btnDisabled');
} else {
buttons.prev.addClass('btnDisabled');
}
//Next / Play
if (obj.loop || obj.index < obj.group.length - 1) {
buttons.next.removeClass('btnDisabled');
buttons.play.removeClass('btnDisabled');
} else {
buttons.next.addClass('btnDisabled');
buttons.play.addClass('btnDisabled');
}
this.buttons = buttons;
this.onUpdate(opts, obj);
},
onUpdate: function (opts, obj) {
var toggle;
if (!this.buttons) {
return;
}
toggle = this.buttons.toggle.removeClass('btnDisabled btnToggleOn');
//Size toggle button
if (obj.canShrink) {
toggle.addClass('btnToggleOn');
} else if (!obj.canExpand) {
toggle.addClass('btnDisabled');
}
},
beforeClose: function () {
if (this.list) {
this.list.remove();
}
this.list = null;
this.buttons = null;
}
};
}(jQuery));
/*!
* Media helper for fancyBox
* version: 1.0.6 (Fri, 14 Jun 2013)
* @requires fancyBox v2.0 or later
*
* Usage:
* $(".fancybox").fancybox({
* helpers : {
* media: true
* }
* });
*
* Set custom URL parameters:
* $(".fancybox").fancybox({
* helpers : {
* media: {
* youtube : {
* params : {
* autoplay : 0
* }
* }
* }
* }
* });
*
* Or:
* $(".fancybox").fancybox({,
* helpers : {
* media: true
* },
* youtube : {
* autoplay: 0
* }
* });
*
* Supports:
*
* Youtube
* http://www.youtube.com/watch?v=opj24KnzrWo
* http://www.youtube.com/embed/opj24KnzrWo
* http://youtu.be/opj24KnzrWo
* http://www.youtube-nocookie.com/embed/opj24KnzrWo
* Vimeo
* http://vimeo.com/40648169
* http://vimeo.com/channels/staffpicks/38843628
* http://vimeo.com/groups/surrealism/videos/36516384
* http://player.vimeo.com/video/45074303
* Metacafe
* http://www.metacafe.com/watch/7635964/dr_seuss_the_lorax_movie_trailer/
* http://www.metacafe.com/watch/7635964/
* Dailymotion
* http://www.dailymotion.com/video/xoytqh_dr-seuss-the-lorax-premiere_people
* Twitvid
* http://twitvid.com/QY7MD
* Twitpic
* http://twitpic.com/7p93st
* Instagram
* http://instagr.am/p/IejkuUGxQn/
* http://instagram.com/p/IejkuUGxQn/
* Google maps
* http://maps.google.com/maps?q=Eiffel+Tower,+Avenue+Gustave+Eiffel,+Paris,+France&t=h&z=17
* http://maps.google.com/?ll=48.857995,2.294297&spn=0.007666,0.021136&t=m&z=16
* http://maps.google.com/?ll=48.859463,2.292626&spn=0.000965,0.002642&t=m&z=19&layer=c&cbll=48.859524,2.292532&panoid=YJ0lq28OOy3VT2IqIuVY0g&cbp=12,151.58,,0,-15.56
*/
(function ($) {
"use strict";
//Shortcut for fancyBox object
var F = $.fancybox,
format = function( url, rez, params ) {
params = params || '';
if ( $.type( params ) === "object" ) {
params = $.param(params, true);
}
$.each(rez, function(key, value) {
url = url.replace( '$' + key, value || '' );
});
if (params.length) {
url += ( url.indexOf('?') > 0 ? '&' : '?' ) + params;
}
return url;
};
//Add helper object
F.helpers.media = {
defaults : {
youtube : {
matcher : /(youtube\.com|youtu\.be|youtube-nocookie\.com)\/(watch\?v=|v\/|u\/|embed\/?)?(videoseries\?list=(.*)|[\w-]{11}|\?listType=(.*)&list=(.*)).*/i,
params : {
autoplay : 1,
autohide : 1,
fs : 1,
rel : 0,
hd : 1,
wmode : 'opaque',
enablejsapi : 1
},
type : 'iframe',
url : '//www.youtube.com/embed/$3'
},
vimeo : {
matcher : /(?:vimeo(?:pro)?.com)\/(?:[^\d]+)?(\d+)(?:.*)/,
params : {
autoplay : 1,
hd : 1,
show_title : 1,
show_byline : 1,
show_portrait : 0,
fullscreen : 1
},
type : 'iframe',
url : '//player.vimeo.com/video/$1'
},
metacafe : {
matcher : /metacafe.com\/(?:watch|fplayer)\/([\w\-]{1,10})/,
params : {
autoPlay : 'yes'
},
type : 'swf',
url : function( rez, params, obj ) {
obj.swf.flashVars = 'playerVars=' + $.param( params, true );
return '//www.metacafe.com/fplayer/' + rez[1] + '/.swf';
}
},
dailymotion : {
matcher : /dailymotion.com\/video\/(.*)\/?(.*)/,
params : {
additionalInfos : 0,
autoStart : 1
},
type : 'swf',
url : '//www.dailymotion.com/swf/video/$1'
},
twitvid : {
matcher : /twitvid\.com\/([a-zA-Z0-9_\-\?\=]+)/i,
params : {
autoplay : 0
},
type : 'iframe',
url : '//www.twitvid.com/embed.php?guid=$1'
},
twitpic : {
matcher : /twitpic\.com\/(?!(?:place|photos|events)\/)([a-zA-Z0-9\?\=\-]+)/i,
type : 'image',
url : '//twitpic.com/show/full/$1/'
},
instagram : {
matcher : /(instagr\.am|instagram\.com)\/p\/([a-zA-Z0-9_\-]+)\/?/i,
type : 'image',
url : '//$1/p/$2/media/?size=l'
},
google_maps : {
matcher : /maps\.google\.([a-z]{2,3}(\.[a-z]{2})?)\/(\?ll=|maps\?)(.*)/i,
type : 'iframe',
url : function( rez ) {
return '//maps.google.' + rez[1] + '/' + rez[3] + '' + rez[4] + '&output=' + (rez[4].indexOf('layer=c') > 0 ? 'svembed' : 'embed');
}
}
},
beforeLoad : function(opts, obj) {
var url = obj.href || '',
type = false,
what,
item,
rez,
params;
for (what in opts) {
if (opts.hasOwnProperty(what)) {
item = opts[ what ];
rez = url.match( item.matcher );
if (rez) {
type = item.type;
params = $.extend(true, {}, item.params, obj[ what ] || ($.isPlainObject(opts[ what ]) ? opts[ what ].params : null));
url = $.type( item.url ) === "function" ? item.url.call( this, rez, params, obj ) : format( item.url, rez, params );
break;
}
}
}
if (type) {
obj.href = url;
obj.type = type;
obj.autoHeight = false;
}
}
};
}(jQuery));
\ No newline at end of file
#fancybox-thumbs {
position: fixed;
left: 0;
width: 100%;
overflow: hidden;
z-index: 8050;
}
#fancybox-thumbs.bottom {
bottom: 2px;
}
#fancybox-thumbs.top {
top: 2px;
}
#fancybox-thumbs ul {
position: relative;
list-style: none;
margin: 0;
padding: 0;
}
#fancybox-thumbs ul li {
float: left;
padding: 1px;
opacity: 0.5;
}
#fancybox-thumbs ul li.active {
opacity: 0.75;
padding: 0;
border: 1px solid #fff;
}
#fancybox-thumbs ul li:hover {
opacity: 1;
}
#fancybox-thumbs ul li a {
display: block;
position: relative;
overflow: hidden;
border: 1px solid #222;
background: #111;
outline: none;
}
#fancybox-thumbs ul li img {
display: block;
position: relative;
border: 0;
padding: 0;
max-width: none;
}
\ No newline at end of file
/*!
* Thumbnail helper for fancyBox
* version: 1.0.7 (Mon, 01 Oct 2012)
* @requires fancyBox v2.0 or later
*
* Usage:
* $(".fancybox").fancybox({
* helpers : {
* thumbs: {
* width : 50,
* height : 50
* }
* }
* });
*
*/
(function ($) {
//Shortcut for fancyBox object
var F = $.fancybox;
//Add helper object
F.helpers.thumbs = {
defaults : {
width : 50, // thumbnail width
height : 50, // thumbnail height
position : 'bottom', // 'top' or 'bottom'
source : function ( item ) { // function to obtain the URL of the thumbnail image
var href;
if (item.element) {
href = $(item.element).find('img').attr('src');
}
if (!href && item.type === 'image' && item.href) {
href = item.href;
}
return href;
}
},
wrap : null,
list : null,
width : 0,
init: function (opts, obj) {
var that = this,
list,
thumbWidth = opts.width,
thumbHeight = opts.height,
thumbSource = opts.source;
//Build list structure
list = '';
for (var n = 0; n < obj.group.length; n++) {
list += '<li><a style="width:' + thumbWidth + 'px;height:' + thumbHeight + 'px;" href="javascript:jQuery.fancybox.jumpto(' + n + ');"></a></li>';
}
this.wrap = $('<div id="fancybox-thumbs"></div>').addClass(opts.position).appendTo('body');
this.list = $('<ul>' + list + '</ul>').appendTo(this.wrap);
//Load each thumbnail
$.each(obj.group, function (i) {
var href = thumbSource( obj.group[ i ] );
if (!href) {
return;
}
$("<img />").load(function () {
var width = this.width,
height = this.height,
widthRatio, heightRatio, parent;
if (!that.list || !width || !height) {
return;
}
//Calculate thumbnail width/height and center it
widthRatio = width / thumbWidth;
heightRatio = height / thumbHeight;
parent = that.list.children().eq(i).find('a');
if (widthRatio >= 1 && heightRatio >= 1) {
if (widthRatio > heightRatio) {
width = Math.floor(width / heightRatio);
height = thumbHeight;
} else {
width = thumbWidth;
height = Math.floor(height / widthRatio);
}
}
$(this).css({
width : width,
height : height,
top : Math.floor(thumbHeight / 2 - height / 2),
left : Math.floor(thumbWidth / 2 - width / 2)
});
parent.width(thumbWidth).height(thumbHeight);
$(this).hide().appendTo(parent).fadeIn(300);
}).attr('src', href);
});
//Set initial width
this.width = this.list.children().eq(0).outerWidth(true);
this.list.width(this.width * (obj.group.length + 1)).css('left', Math.floor($(window).width() * 0.5 - (obj.index * this.width + this.width * 0.5)));
},
beforeLoad: function (opts, obj) {
//Remove self if gallery do not have at least two items
if (obj.group.length < 2) {
obj.helpers.thumbs = false;
return;
}
//Increase bottom margin to give space for thumbs
obj.margin[ opts.position === 'top' ? 0 : 2 ] += ((opts.height) + 15);
},
afterShow: function (opts, obj) {
//Check if exists and create or update list
if (this.list) {
this.onUpdate(opts, obj);
} else {
this.init(opts, obj);
}
//Set active element
this.list.children().removeClass('active').eq(obj.index).addClass('active');
},
//Center list
onUpdate: function (opts, obj) {
if (this.list) {
this.list.stop(true).animate({
'left': Math.floor($(window).width() * 0.5 - (obj.index * this.width + this.width * 0.5))
}, 150);
}
},
beforeClose: function () {
if (this.wrap) {
this.wrap.remove();
}
this.wrap = null;
this.list = null;
this.width = 0;
}
}
}(jQuery));
\ No newline at end of file
/*! fancyBox v2.1.5 fancyapps.com | fancyapps.com/fancybox/#license */
.fancybox-wrap,
.fancybox-skin,
.fancybox-outer,
.fancybox-inner,
.fancybox-image,
.fancybox-wrap iframe,
.fancybox-wrap object,
.fancybox-nav,
.fancybox-nav span,
.fancybox-tmp
{
padding: 0;
margin: 0;
border: 0;
outline: none;
vertical-align: top;
}
.fancybox-wrap {
position: absolute;
top: 0;
left: 0;
z-index: 8020;
}
.fancybox-skin {
position: relative;
background: #f9f9f9;
color: #444;
text-shadow: none;
-webkit-border-radius: 4px;
-moz-border-radius: 4px;
border-radius: 4px;
}
.fancybox-opened {
z-index: 8030;
}
.fancybox-opened .fancybox-skin {
-webkit-box-shadow: 0 10px 25px rgba(0, 0, 0, 0.5);
-moz-box-shadow: 0 10px 25px rgba(0, 0, 0, 0.5);
box-shadow: 0 10px 25px rgba(0, 0, 0, 0.5);
}
.fancybox-outer, .fancybox-inner {
position: relative;
}
.fancybox-inner {
overflow: hidden;
}
.fancybox-type-iframe .fancybox-inner {
-webkit-overflow-scrolling: touch;
}
.fancybox-error {
color: #444;
font: 14px/20px "Helvetica Neue",Helvetica,Arial,sans-serif;
margin: 0;
padding: 15px;
white-space: nowrap;
}
.fancybox-image, .fancybox-iframe {
display: block;
width: 100%;
height: 100%;
}
.fancybox-image {
max-width: 100%;
max-height: 100%;
}
#fancybox-loading, .fancybox-close, .fancybox-prev span, .fancybox-next span {
background-image: url('fancybox_sprite.png');
}
#fancybox-loading {
position: fixed;
top: 50%;
left: 50%;
margin-top: -22px;
margin-left: -22px;
background-position: 0 -108px;
opacity: 0.8;
cursor: pointer;
z-index: 8060;
}
#fancybox-loading div {
width: 44px;
height: 44px;
background: url('fancybox_loading.gif') center center no-repeat;
}
.fancybox-close {
position: absolute;
top: -18px;
right: -18px;
width: 36px;
height: 36px;
cursor: pointer;
z-index: 8040;
}
.fancybox-nav {
position: absolute;
top: 0;
width: 40%;
height: 100%;
cursor: pointer;
text-decoration: none;
background: transparent url('blank.gif'); /* helps IE */
-webkit-tap-highlight-color: rgba(0,0,0,0);
z-index: 8040;
}
.fancybox-prev {
left: 0;
}
.fancybox-next {
right: 0;
}
.fancybox-nav span {
position: absolute;
top: 50%;
width: 36px;
height: 34px;
margin-top: -18px;
cursor: pointer;
z-index: 8040;
visibility: hidden;
}
.fancybox-prev span {
left: 10px;
background-position: 0 -36px;
}
.fancybox-next span {
right: 10px;
background-position: 0 -72px;
}
.fancybox-nav:hover span {
visibility: visible;
}
.fancybox-tmp {
position: absolute;
top: -99999px;
left: -99999px;
visibility: hidden;
max-width: 99999px;
max-height: 99999px;
overflow: visible !important;
}
/* Overlay helper */
.fancybox-lock {
overflow: hidden !important;
width: auto;
}
.fancybox-lock body {
overflow: hidden !important;
}
.fancybox-lock-test {
overflow-y: hidden !important;
}
.fancybox-overlay {
position: absolute;
top: 0;
left: 0;
overflow: hidden;
display: none;
z-index: 8010;
background: url('fancybox_overlay.png');
}
.fancybox-overlay-fixed {
position: fixed;
bottom: 0;
right: 0;
}
.fancybox-lock .fancybox-overlay {
overflow: auto;
overflow-y: scroll;
}
/* Title helper */
.fancybox-title {
visibility: hidden;
font: normal 13px/20px "Helvetica Neue",Helvetica,Arial,sans-serif;
position: relative;
text-shadow: none;
z-index: 8050;
}
.fancybox-opened .fancybox-title {
visibility: visible;
}
.fancybox-title-float-wrap {
position: absolute;
bottom: 0;
right: 50%;
margin-bottom: -35px;
z-index: 8050;
text-align: center;
}
.fancybox-title-float-wrap .child {
display: inline-block;
margin-right: -100%;
padding: 2px 20px;
background: transparent; /* Fallback for web browsers that doesn't support RGBa */
background: rgba(0, 0, 0, 0.8);
-webkit-border-radius: 15px;
-moz-border-radius: 15px;
border-radius: 15px;
text-shadow: 0 1px 2px #222;
color: #FFF;
font-weight: bold;
line-height: 24px;
white-space: nowrap;
}
.fancybox-title-outside-wrap {
position: relative;
margin-top: 10px;
color: #fff;
}
.fancybox-title-inside-wrap {
padding-top: 10px;
}
.fancybox-title-over-wrap {
position: absolute;
bottom: 0;
left: 0;
color: #fff;
padding: 10px;
background: #000;
background: rgba(0, 0, 0, .8);
}
/*Retina graphics!*/
@media only screen and (-webkit-min-device-pixel-ratio: 1.5),
only screen and (min--moz-device-pixel-ratio: 1.5),
only screen and (min-device-pixel-ratio: 1.5){
#fancybox-loading, .fancybox-close, .fancybox-prev span, .fancybox-next span {
background-image: url('fancybox_sprite@2x.png');
background-size: 44px 152px; /*The size of the normal image, half the size of the hi-res image*/
}
#fancybox-loading div {
background-image: url('fancybox_loading@2x.gif');
background-size: 24px 24px; /*The size of the normal image, half the size of the hi-res image*/
}
}
\ No newline at end of file
/*
* Core Owl Carousel CSS File
* v1.3.3
*/
/* clearfix */
.owl-carousel .owl-wrapper:after {
content: ".";
display: block;
clear: both;
visibility: hidden;
line-height: 0;
height: 0;
}
/* display none until init */
.owl-carousel{
display: none;
position: relative;
width: 100%;
-ms-touch-action: pan-y;
}
.owl-carousel .owl-wrapper{
display: none;
position: relative;
-webkit-transform: translate3d(0px, 0px, 0px);
}
.owl-carousel .owl-wrapper-outer{
overflow: hidden;
position: relative;
width: 100%;
}
.owl-carousel .owl-wrapper-outer.autoHeight{
-webkit-transition: height 500ms ease-in-out;
-moz-transition: height 500ms ease-in-out;
-ms-transition: height 500ms ease-in-out;
-o-transition: height 500ms ease-in-out;
transition: height 500ms ease-in-out;
}
.owl-carousel .owl-item{
float: left;
}
.owl-controls .owl-page,
.owl-controls .owl-buttons div{
cursor: pointer;
}
.owl-controls {
-webkit-user-select: none;
-khtml-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
-webkit-tap-highlight-color: rgba(0, 0, 0, 0);
}
/* mouse grab icon */
.grabbing {
cursor:url(images/grabbing.png) 8 8, move;
}
/* fix */
.owl-carousel .owl-wrapper,
.owl-carousel .owl-item{
-webkit-backface-visibility: hidden;
-moz-backface-visibility: hidden;
-ms-backface-visibility: hidden;
-webkit-transform: translate3d(0,0,0);
-moz-transform: translate3d(0,0,0);
-ms-transform: translate3d(0,0,0);
}
/****************************************/
/*
* Owl Carousel Owl Demo Theme
* v1.3.3
*/
.owl-theme .owl-pagination{position: absolute; left: 0; right: 0; margin: 0 auto; bottom: 10px; text-align: center;}
.owl-theme .owl-buttons{
text-align: center;
position: absolute;
top: -78px;
right: 15px;
opacity: 1;
width: 65px;
}
.owl-theme .owl-controls .owl-buttons > div{
float: left;
width: 30px;
height: 30px;
font-size: 0;
text-align: center;
color: #333333;
background: #eeeeee;
}
.owl-theme .owl-controls .owl-buttons .owl-next{float: right;}
.owl-theme .owl-controls .owl-buttons > div:before{
content: "\f104";
font-family: FontAwesome;
font-size: 20px;
display: block;
line-height: 28px;
}
.owl-theme .owl-controls .owl-buttons .owl-next:before{
content: "\f105";
}
.owl-theme .owl-controls .owl-buttons > div:hover{color: #fff ;background:#333; }
/* Clickable class fix problem with hover on touch devices */
/* Use it for non-touch hover action */
/* Styling Pagination*/
.owl-theme .owl-controls .owl-page{
display: inline-block;
zoom: 1;
*display: inline;/*IE7 life-saver */
}
.owl-theme .owl-controls .owl-page span{
display: block;
width: 10px;
height: 10px;
margin: 5px 4px;
background: transparent;
}
/* If PaginationNumbers is true */
.owl-theme .owl-controls .owl-page span.owl-numbers{
height: auto;
width: auto;
color: #FFF;
padding: 2px 10px;
font-size: 12px;
-webkit-border-radius: 30px;
-moz-border-radius: 30px;
border-radius: 30px;
}
/* preloading images */
.owl-item.loading{
min-height: 150px;
background: url(images/AjaxLoader.gif) no-repeat center center
}
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
define([
'jquery',
'mage/translate',
'jquery/ui',
'Magento_Catalog/js/catalog-add-to-cart'
], function($, $t) {
"use strict";
$.widget('mage.catalogAddToCart', {
options: {
processStart: null,
processStop: null,
bindSubmit: true,
minicartSelector: '[data-block="minicart"]',
messagesSelector: '[data-placeholder="messages"]',
productStatusSelector: '.stock.available',
addToCartButtonSelector: '.action.tocart',
addToCartButtonDisabledClass: 'disabled',
addToCartButtonTextWhileAdding: $t('Adding...'),
addToCartButtonTextAdded: $t('Added'),
addToCartButtonTextDefault: $t('Add to Cart')
},
_create: function() {
if (this.options.bindSubmit) {
this._bindSubmit();
}
},
_bindSubmit: function() {
var self = this;
this.element.on('submit', function(e) {
e.preventDefault();
self.submitForm($(this));
});
},
isLoaderEnabled: function() {
return this.options.processStart && this.options.processStop;
},
submitForm: function(form) {
var self = this;
if (form.has('input[type="file"]').length && form.find('input[type="file"]').val() !== '') {
self.element.off('submit');
form.submit();
} else {
self.ajaxSubmit(form);
}
},
ajaxSubmit: function(form) {
var self = this;
self.disableAddToCartButton(form);
var url = form.attr('action');
$.ajax({
url: url,
data: form.serialize(),
type: 'post',
dataType: 'json',
beforeSend: function() {
if (self.isLoaderEnabled()) {
$('body').trigger(self.options.processStart);
}
$('body').append('<div id="add-to-cart-loading-ajax-common"><span></span></div>');
},
success: function(res) {
if (self.isLoaderEnabled()) {
$('body').trigger(self.options.processStop);
}
if (res.backUrl) {
window.location = res.backUrl;
return;
}
$(self.options.minicartSelector).trigger('contentUpdated');
if (res.messages) {
$(self.options.messagesSelector).html(res.messages);
}
if (res.minicart) {
$(self.options.minicartSelector).replaceWith(res.minicart);
$(self.options.minicartSelector).trigger('contentUpdated');
}
if (res.product && res.product.statusText) {
$(self.options.productStatusSelector)
.removeClass('available')
.addClass('unavailable')
.find('span')
.html(res.product.statusText);
}
var width_window = $(window).width();
if(width_window > 480){
window.ajaxCartTransport = true;
}
else{
$('body #add-to-cart-loading-ajax-common').remove();
if(res.html){
require(['jquery', 'rokanthemes/fancybox'], function($){
$.fancybox({
content: res.html,
helpers: {
overlay: {
locked: false
}
}
});
});
}
}
self.enableAddToCartButton(form);
}
});
},
disableAddToCartButton: function(form) {
var addToCartButton = $(form).find(this.options.addToCartButtonSelector);
addToCartButton.addClass(this.options.addToCartButtonDisabledClass);
addToCartButton.attr('title', this.options.addToCartButtonTextWhileAdding);
addToCartButton.find('span').text(this.options.addToCartButtonTextWhileAdding);
},
enableAddToCartButton: function(form) {
var self = this,
addToCartButton = $(form).find(this.options.addToCartButtonSelector);
addToCartButton.find('span').text(this.options.addToCartButtonTextAdded);
addToCartButton.attr('title', this.options.addToCartButtonTextAdded);
setTimeout(function() {
addToCartButton.removeClass(self.options.addToCartButtonDisabledClass);
addToCartButton.find('span').text(self.options.addToCartButtonTextDefault);
addToCartButton.attr('title', self.options.addToCartButtonTextDefault);
}, 1000);
}
});
return $.mage.catalogAddToCart;
});
\ No newline at end of file
/*
* jQuery elevateZoom 3.0.8
* Demo's and documentation:
* www.elevateweb.co.uk/image-zoom
*
* Copyright (c) 2012 Andrew Eades
* www.elevateweb.co.uk
*
* Dual licensed under the GPL and MIT licenses.
* http://en.wikipedia.org/wiki/MIT_License
* http://en.wikipedia.org/wiki/GNU_General_Public_License
*
/*
* jQuery elevateZoom 3.0.3
* Demo's and documentation:
* www.elevateweb.co.uk/image-zoom
*
* Copyright (c) 2012 Andrew Eades
* www.elevateweb.co.uk
*
* Dual licensed under the GPL and MIT licenses.
* http://en.wikipedia.org/wiki/MIT_License
* http://en.wikipedia.org/wiki/GNU_General_Public_License
*/
if ( typeof Object.create !== 'function' ) {
Object.create = function( obj ) {
function F() {};
F.prototype = obj;
return new F();
};
}
(function( $, window, document, undefined ) {
var ElevateZoom = {
init: function( options, elem ) {
var self = this;
self.elem = elem;
self.$elem = $( elem );
self.imageSrc = self.$elem.data("zoom-image") ? self.$elem.data("zoom-image") : self.$elem.attr("src");
self.options = $.extend( {}, $.fn.elevateZoom.options, options );
//TINT OVERRIDE SETTINGS
if(self.options.tint) {
self.options.lensColour = "none", //colour of the lens background
self.options.lensOpacity = "1" //opacity of the lens
}
//INNER OVERRIDE SETTINGS
if(self.options.zoomType == "inner") {self.options.showLens = false;}
//Remove alt on hover
self.$elem.parent().removeAttr('title').removeAttr('alt');
self.zoomImage = self.imageSrc;
self.refresh( 1 );
//Create the image swap from the gallery
$('#'+self.options.gallery + ' a').click( function(e) {
//Set a class on the currently active gallery image
if(self.options.galleryActiveClass){
$('#'+self.options.gallery + ' a').removeClass(self.options.galleryActiveClass);
$(this).addClass(self.options.galleryActiveClass);
}
//stop any link on the a tag from working
e.preventDefault();
//call the swap image function
if($(this).data("zoom-image")){self.zoomImagePre = $(this).data("zoom-image")}
else{self.zoomImagePre = $(this).data("image");}
self.swaptheimage($(this).data("image"), self.zoomImagePre);
return false;
});
},
refresh: function( length ) {
var self = this;
setTimeout(function() {
self.fetch(self.imageSrc);
}, length || self.options.refresh );
},
fetch: function(imgsrc) {
//get the image
var self = this;
var newImg = new Image();
newImg.onload = function() {
//set the large image dimensions - used to calculte ratio's
self.largeWidth = newImg.width;
self.largeHeight = newImg.height;
//once image is loaded start the calls
self.startZoom();
self.currentImage = self.imageSrc;
//let caller know image has been loaded
self.options.onZoomedImageLoaded(self.$elem);
}
newImg.src = imgsrc; // this must be done AFTER setting onload
return;
},
startZoom: function( ) {
var self = this;
//get dimensions of the non zoomed image
self.nzWidth = self.$elem.width();
self.nzHeight = self.$elem.height();
//activated elements
self.isWindowActive = false;
self.isLensActive = false;
self.isTintActive = false;
self.overWindow = false;
//CrossFade Wrappe
if(self.options.imageCrossfade){
self.zoomWrap = self.$elem.wrap('<div style="height:'+self.nzHeight+'px;width:'+self.nzWidth+'px;" class="zoomWrapper" />');
self.$elem.css('position', 'absolute');
}
self.zoomLock = 1;
self.scrollingLock = false;
self.changeBgSize = false;
self.currentZoomLevel = self.options.zoomLevel;
//get offset of the non zoomed image
self.nzOffset = self.$elem.offset();
//calculate the width ratio of the large/small image
self.widthRatio = (self.largeWidth/self.currentZoomLevel) / self.nzWidth;
self.heightRatio = (self.largeHeight/self.currentZoomLevel) / self.nzHeight;
//if window zoom
if(self.options.zoomType == "window") {
self.zoomWindowStyle = "overflow: hidden;"
+ "background-position: 0px 0px;text-align:center;"
+ "background-color: " + String(self.options.zoomWindowBgColour)
+ ";width: " + String(self.options.zoomWindowWidth) + "px;"
+ "height: " + String(self.options.zoomWindowHeight)
+ "px;float: left;"
+ "background-size: "+ self.largeWidth/self.currentZoomLevel+ "px " +self.largeHeight/self.currentZoomLevel + "px;"
+ "display: none;z-index:100;"
+ "border: " + String(self.options.borderSize)
+ "px solid " + self.options.borderColour
+ ";background-repeat: no-repeat;"
+ "position: absolute;";
}
//if inner zoom
if(self.options.zoomType == "inner") {
//has a border been put on the image? Lets cater for this
var borderWidth = self.$elem.css("border-left-width");
self.zoomWindowStyle = "overflow: hidden;"
+ "margin-left: " + String(borderWidth) + ";"
+ "margin-top: " + String(borderWidth) + ";"
+ "background-position: 0px 0px;"
+ "width: " + String(self.nzWidth) + "px;"
+ "height: " + String(self.nzHeight) + "px;"
+ "px;float: left;"
+ "display: none;"
+ "cursor:"+(self.options.cursor)+";"
+ "px solid " + self.options.borderColour
+ ";background-repeat: no-repeat;"
+ "position: absolute;";
}
//lens style for window zoom
if(self.options.zoomType == "window") {
// adjust images less than the window height
if(self.nzHeight < self.options.zoomWindowWidth/self.widthRatio){
lensHeight = self.nzHeight;
}
else{
lensHeight = String((self.options.zoomWindowHeight/self.heightRatio))
}
if(self.largeWidth < self.options.zoomWindowWidth){
lensWidth = self.nzWidth;
}
else{
lensWidth = (self.options.zoomWindowWidth/self.widthRatio);
}
self.lensStyle = "background-position: 0px 0px;width: " + String((self.options.zoomWindowWidth)/self.widthRatio) + "px;height: " + String((self.options.zoomWindowHeight)/self.heightRatio)
+ "px;float: right;display: none;"
+ "overflow: hidden;"
+ "z-index: 999;"
+ "-webkit-transform: translateZ(0);"
+ "opacity:"+(self.options.lensOpacity)+";filter: alpha(opacity = "+(self.options.lensOpacity*100)+"); zoom:1;"
+ "width:"+lensWidth+"px;"
+ "height:"+lensHeight+"px;"
+ "background-color:"+(self.options.lensColour)+";"
+ "cursor:"+(self.options.cursor)+";"
+ "border: "+(self.options.lensBorderSize)+"px" +
" solid "+(self.options.lensBorderColour)+";background-repeat: no-repeat;position: absolute;";
}
//tint style
self.tintStyle = "display: block;"
+ "position: absolute;"
+ "background-color: "+self.options.tintColour+";"
+ "filter:alpha(opacity=0);"
+ "opacity: 0;"
+ "width: " + self.nzWidth + "px;"
+ "height: " + self.nzHeight + "px;"
;
//lens style for lens zoom with optional round for modern browsers
self.lensRound = '';
if(self.options.zoomType == "lens") {
self.lensStyle = "background-position: 0px 0px;"
+ "float: left;display: none;"
+ "border: " + String(self.options.borderSize) + "px solid " + self.options.borderColour+";"
+ "width:"+ String(self.options.lensSize) +"px;"
+ "height:"+ String(self.options.lensSize)+"px;"
+ "background-repeat: no-repeat;position: absolute;";
}
//does not round in all browsers
if(self.options.lensShape == "round") {
self.lensRound = "border-top-left-radius: " + String(self.options.lensSize / 2 + self.options.borderSize) + "px;"
+ "border-top-right-radius: " + String(self.options.lensSize / 2 + self.options.borderSize) + "px;"
+ "border-bottom-left-radius: " + String(self.options.lensSize / 2 + self.options.borderSize) + "px;"
+ "border-bottom-right-radius: " + String(self.options.lensSize / 2 + self.options.borderSize) + "px;";
}
//create the div's + ""
//self.zoomContainer = $('<div/>').addClass('zoomContainer').css({"position":"relative", "height":self.nzHeight, "width":self.nzWidth});
self.zoomContainer = $('<div class="zoomContainer" style="-webkit-transform: translateZ(0);position:absolute;left:'+self.nzOffset.left+'px;top:'+self.nzOffset.top+'px;height:'+self.nzHeight+'px;width:'+self.nzWidth+'px;"></div>');
$('body').append(self.zoomContainer);
//this will add overflow hidden and contrain the lens on lens mode
if(self.options.containLensZoom && self.options.zoomType == "lens"){
self.zoomContainer.css("overflow", "hidden");
}
if(self.options.zoomType != "inner") {
self.zoomLens = $("<div class='zoomLens' style='" + self.lensStyle + self.lensRound +"'>&nbsp;</div>")
.appendTo(self.zoomContainer)
.click(function () {
self.$elem.trigger('click');
});
if(self.options.tint) {
self.tintContainer = $('<div/>').addClass('tintContainer');
self.zoomTint = $("<div class='zoomTint' style='"+self.tintStyle+"'></div>");
self.zoomLens.wrap(self.tintContainer);
self.zoomTintcss = self.zoomLens.after(self.zoomTint);
//if tint enabled - set an image to show over the tint
self.zoomTintImage = $('<img style="position: absolute; left: 0px; top: 0px; max-width: none; width: '+self.nzWidth+'px; height: '+self.nzHeight+'px;" src="'+self.imageSrc+'">')
.appendTo(self.zoomLens)
.click(function () {
self.$elem.trigger('click');
});
}
}
//create zoom window
if(isNaN(self.options.zoomWindowPosition)){
self.zoomWindow = $("<div style='z-index:999;left:"+(self.windowOffsetLeft)+"px;top:"+(self.windowOffsetTop)+"px;" + self.zoomWindowStyle + "' class='zoomWindow'>&nbsp;</div>")
.appendTo('body')
.click(function () {
self.$elem.trigger('click');
});
}else{
self.zoomWindow = $("<div style='z-index:999;left:"+(self.windowOffsetLeft)+"px;top:"+(self.windowOffsetTop)+"px;" + self.zoomWindowStyle + "' class='zoomWindow'>&nbsp;</div>")
.appendTo(self.zoomContainer)
.click(function () {
self.$elem.trigger('click');
});
}
self.zoomWindowContainer = $('<div/>').addClass('zoomWindowContainer').css("width",self.options.zoomWindowWidth);
self.zoomWindow.wrap(self.zoomWindowContainer);
// self.captionStyle = "text-align: left;background-color: black;color: white;font-weight: bold;padding: 10px;font-family: sans-serif;font-size: 11px";
// self.zoomCaption = $('<div class="elevatezoom-caption" style="'+self.captionStyle+'display: block; width: 280px;">INSERT ALT TAG</div>').appendTo(self.zoomWindow.parent());
if(self.options.zoomType == "lens") {
self.zoomLens.css({ backgroundImage: "url('" + self.imageSrc + "')" });
}
if(self.options.zoomType == "window") {
self.zoomWindow.css({ backgroundImage: "url('" + self.imageSrc + "')" });
}
if(self.options.zoomType == "inner") {
self.zoomWindow.css({ backgroundImage: "url('" + self.imageSrc + "')" });
}
/*-------------------END THE ZOOM WINDOW AND LENS----------------------------------*/
//touch events
self.$elem.bind('touchmove', function(e){
e.preventDefault();
var touch = e.originalEvent.touches[0] || e.originalEvent.changedTouches[0];
self.setPosition(touch);
});
self.zoomContainer.bind('touchmove', function(e){
if(self.options.zoomType == "inner") {
self.showHideWindow("show");
}
e.preventDefault();
var touch = e.originalEvent.touches[0] || e.originalEvent.changedTouches[0];
self.setPosition(touch);
});
self.zoomContainer.bind('touchend', function(e){
self.showHideWindow("hide");
if(self.options.showLens) {self.showHideLens("hide");}
if(self.options.tint && self.options.zoomType != "inner") {self.showHideTint("hide");}
});
self.$elem.bind('touchend', function(e){
self.showHideWindow("hide");
if(self.options.showLens) {self.showHideLens("hide");}
if(self.options.tint && self.options.zoomType != "inner") {self.showHideTint("hide");}
});
if(self.options.showLens) {
self.zoomLens.bind('touchmove', function(e){
e.preventDefault();
var touch = e.originalEvent.touches[0] || e.originalEvent.changedTouches[0];
self.setPosition(touch);
});
self.zoomLens.bind('touchend', function(e){
self.showHideWindow("hide");
if(self.options.showLens) {self.showHideLens("hide");}
if(self.options.tint && self.options.zoomType != "inner") {self.showHideTint("hide");}
});
}
//Needed to work in IE
self.$elem.bind('mousemove', function(e){
if(self.overWindow == false){self.setElements("show");}
//make sure on orientation change the setposition is not fired
if(self.lastX !== e.clientX || self.lastY !== e.clientY){
self.setPosition(e);
self.currentLoc = e;
}
self.lastX = e.clientX;
self.lastY = e.clientY;
});
self.zoomContainer.bind('mousemove', function(e){
if(self.overWindow == false){self.setElements("show");}
//make sure on orientation change the setposition is not fired
if(self.lastX !== e.clientX || self.lastY !== e.clientY){
self.setPosition(e);
self.currentLoc = e;
}
self.lastX = e.clientX;
self.lastY = e.clientY;
});
if(self.options.zoomType != "inner") {
self.zoomLens.bind('mousemove', function(e){
//make sure on orientation change the setposition is not fired
if(self.lastX !== e.clientX || self.lastY !== e.clientY){
self.setPosition(e);
self.currentLoc = e;
}
self.lastX = e.clientX;
self.lastY = e.clientY;
});
}
if(self.options.tint && self.options.zoomType != "inner") {
self.zoomTint.bind('mousemove', function(e){
//make sure on orientation change the setposition is not fired
if(self.lastX !== e.clientX || self.lastY !== e.clientY){
self.setPosition(e);
self.currentLoc = e;
}
self.lastX = e.clientX;
self.lastY = e.clientY;
});
}
if(self.options.zoomType == "inner") {
self.zoomWindow.bind('mousemove', function(e) {
//self.overWindow = true;
//make sure on orientation change the setposition is not fired
if(self.lastX !== e.clientX || self.lastY !== e.clientY){
self.setPosition(e);
self.currentLoc = e;
}
self.lastX = e.clientX;
self.lastY = e.clientY;
});
}
// lensFadeOut: 500, zoomTintFadeIn
self.zoomContainer.add(self.$elem).mouseenter(function(){
if(self.overWindow == false){self.setElements("show");}
}).mouseleave(function(){
if(!self.scrollLock){
self.setElements("hide");
self.options.onDestroy(self.$elem);
}
});
//end ove image
if(self.options.zoomType != "inner") {
self.zoomWindow.mouseenter(function(){
self.overWindow = true;
self.setElements("hide");
}).mouseleave(function(){
self.overWindow = false;
});
}
//end ove image
// var delta = parseInt(e.originalEvent.wheelDelta || -e.originalEvent.detail);
// $(this).empty();
// return false;
//fix for initial zoom setting
if (self.options.zoomLevel != 1){
// self.changeZoomLevel(self.currentZoomLevel);
}
//set the min zoomlevel
if(self.options.minZoomLevel){
self.minZoomLevel = self.options.minZoomLevel;
}
else{
self.minZoomLevel = self.options.scrollZoomIncrement * 2;
}
if(self.options.scrollZoom){
self.zoomContainer.add(self.$elem).bind('mousewheel DOMMouseScroll MozMousePixelScroll', function(e){
// in IE there is issue with firing of mouseleave - So check whether still scrolling
// and on mouseleave check if scrolllock
self.scrollLock = true;
clearTimeout($.data(this, 'timer'));
$.data(this, 'timer', setTimeout(function() {
self.scrollLock = false;
//do something
}, 250));
var theEvent = e.originalEvent.wheelDelta || e.originalEvent.detail*-1
//this.scrollTop += ( delta < 0 ? 1 : -1 ) * 30;
// e.preventDefault();
e.stopImmediatePropagation();
e.stopPropagation();
e.preventDefault();
if(theEvent /120 > 0) {
//scrolling up
if(self.currentZoomLevel >= self.minZoomLevel){
self.changeZoomLevel(self.currentZoomLevel-self.options.scrollZoomIncrement);
}
}
else{
//scrolling down
if(self.options.maxZoomLevel){
if(self.currentZoomLevel <= self.options.maxZoomLevel){
self.changeZoomLevel(parseFloat(self.currentZoomLevel)+self.options.scrollZoomIncrement);
}
}
else{
//andy
self.changeZoomLevel(parseFloat(self.currentZoomLevel)+self.options.scrollZoomIncrement);
}
}
return false;
});
}
},
setElements: function(type) {
var self = this;
if(!self.options.zoomEnabled){return false;}
if(type=="show"){
if(self.isWindowSet){
if(self.options.zoomType == "inner") {self.showHideWindow("show");}
if(self.options.zoomType == "window") {self.showHideWindow("show");}
if(self.options.showLens) {self.showHideLens("show");}
if(self.options.tint && self.options.zoomType != "inner") {self.showHideTint("show");
}
}
}
if(type=="hide"){
if(self.options.zoomType == "window") {self.showHideWindow("hide");}
if(!self.options.tint) {self.showHideWindow("hide");}
if(self.options.showLens) {self.showHideLens("hide");}
if(self.options.tint) { self.showHideTint("hide");}
}
},
setPosition: function(e) {
var self = this;
if(!self.options.zoomEnabled){return false;}
//recaclc offset each time in case the image moves
//this can be caused by other on page elements
self.nzHeight = self.$elem.height();
self.nzWidth = self.$elem.width();
self.nzOffset = self.$elem.offset();
if(self.options.tint && self.options.zoomType != "inner") {
self.zoomTint.css({ top: 0});
self.zoomTint.css({ left: 0});
}
//set responsive
//will checking if the image needs changing before running this code work faster?
if(self.options.responsive && !self.options.scrollZoom){
if(self.options.showLens){
if(self.nzHeight < self.options.zoomWindowWidth/self.widthRatio){
lensHeight = self.nzHeight;
}
else{
lensHeight = String((self.options.zoomWindowHeight/self.heightRatio))
}
if(self.largeWidth < self.options.zoomWindowWidth){
lensWidth = self.nzWidth;
}
else{
lensWidth = (self.options.zoomWindowWidth/self.widthRatio);
}
self.widthRatio = self.largeWidth / self.nzWidth;
self.heightRatio = self.largeHeight / self.nzHeight;
if(self.options.zoomType != "lens") {
//possibly dont need to keep recalcalculating
//if the lens is heigher than the image, then set lens size to image size
if(self.nzHeight < self.options.zoomWindowWidth/self.widthRatio){
lensHeight = self.nzHeight;
}
else{
lensHeight = String((self.options.zoomWindowHeight/self.heightRatio))
}
if(self.nzWidth < self.options.zoomWindowHeight/self.heightRatio){
lensWidth = self.nzWidth;
}
else{
lensWidth = String((self.options.zoomWindowWidth/self.widthRatio));
}
self.zoomLens.css('width', lensWidth);
self.zoomLens.css('height', lensHeight);
if(self.options.tint){
self.zoomTintImage.css('width', self.nzWidth);
self.zoomTintImage.css('height', self.nzHeight);
}
}
if(self.options.zoomType == "lens") {
self.zoomLens.css({ width: String(self.options.lensSize) + 'px', height: String(self.options.lensSize) + 'px' })
}
//end responsive image change
}
}
//container fix
self.zoomContainer.css({ top: self.nzOffset.top});
self.zoomContainer.css({ left: self.nzOffset.left});
self.mouseLeft = parseInt(e.pageX - self.nzOffset.left);
self.mouseTop = parseInt(e.pageY - self.nzOffset.top);
//calculate the Location of the Lens
//calculate the bound regions - but only if zoom window
if(self.options.zoomType == "window") {
self.Etoppos = (self.mouseTop < (self.zoomLens.height()/2));
self.Eboppos = (self.mouseTop > self.nzHeight - (self.zoomLens.height()/2)-(self.options.lensBorderSize*2));
self.Eloppos = (self.mouseLeft < 0+((self.zoomLens.width()/2)));
self.Eroppos = (self.mouseLeft > (self.nzWidth - (self.zoomLens.width()/2)-(self.options.lensBorderSize*2)));
}
//calculate the bound regions - but only for inner zoom
if(self.options.zoomType == "inner"){
self.Etoppos = (self.mouseTop < ((self.nzHeight/2)/self.heightRatio) );
self.Eboppos = (self.mouseTop > (self.nzHeight - ((self.nzHeight/2)/self.heightRatio)));
self.Eloppos = (self.mouseLeft < 0+(((self.nzWidth/2)/self.widthRatio)));
self.Eroppos = (self.mouseLeft > (self.nzWidth - (self.nzWidth/2)/self.widthRatio-(self.options.lensBorderSize*2)));
}
// if the mouse position of the slider is one of the outerbounds, then hide window and lens
if (self.mouseLeft < 0 || self.mouseTop < 0 || self.mouseLeft > self.nzWidth || self.mouseTop > self.nzHeight ) {
self.setElements("hide");
return;
}
//else continue with operations
else {
//lens options
if(self.options.showLens) {
// self.showHideLens("show");
//set background position of lens
self.lensLeftPos = String(Math.floor(self.mouseLeft - self.zoomLens.width() / 2));
self.lensTopPos = String(Math.floor(self.mouseTop - self.zoomLens.height() / 2));
}
//adjust the background position if the mouse is in one of the outer regions
//Top region
if(self.Etoppos){
self.lensTopPos = 0;
}
//Left Region
if(self.Eloppos){
self.windowLeftPos = 0;
self.lensLeftPos = 0;
self.tintpos=0;
}
//Set bottom and right region for window mode
if(self.options.zoomType == "window") {
if(self.Eboppos){
self.lensTopPos = Math.max( (self.nzHeight)-self.zoomLens.height()-(self.options.lensBorderSize*2), 0 );
}
if(self.Eroppos){
self.lensLeftPos = (self.nzWidth-(self.zoomLens.width())-(self.options.lensBorderSize*2));
}
}
//Set bottom and right region for inner mode
if(self.options.zoomType == "inner") {
if(self.Eboppos){
self.lensTopPos = Math.max( ((self.nzHeight)-(self.options.lensBorderSize*2)), 0 );
}
if(self.Eroppos){
self.lensLeftPos = (self.nzWidth-(self.nzWidth)-(self.options.lensBorderSize*2));
}
}
//if lens zoom
if(self.options.zoomType == "lens") {
self.windowLeftPos = String(((e.pageX - self.nzOffset.left) * self.widthRatio - self.zoomLens.width() / 2) * (-1));
self.windowTopPos = String(((e.pageY - self.nzOffset.top) * self.heightRatio - self.zoomLens.height() / 2) * (-1));
self.zoomLens.css({ backgroundPosition: self.windowLeftPos + 'px ' + self.windowTopPos + 'px' });
if(self.changeBgSize){
if(self.nzHeight>self.nzWidth){
if(self.options.zoomType == "lens"){
self.zoomLens.css({ "background-size": self.largeWidth/self.newvalueheight + 'px ' + self.largeHeight/self.newvalueheight + 'px' });
}
self.zoomWindow.css({ "background-size": self.largeWidth/self.newvalueheight + 'px ' + self.largeHeight/self.newvalueheight + 'px' });
}
else{
if(self.options.zoomType == "lens"){
self.zoomLens.css({ "background-size": self.largeWidth/self.newvaluewidth + 'px ' + self.largeHeight/self.newvaluewidth + 'px' });
}
self.zoomWindow.css({ "background-size": self.largeWidth/self.newvaluewidth + 'px ' + self.largeHeight/self.newvaluewidth + 'px' });
}
self.changeBgSize = false;
}
self.setWindowPostition(e);
}
//if tint zoom
if(self.options.tint && self.options.zoomType != "inner") {
self.setTintPosition(e);
}
//set the css background position
if(self.options.zoomType == "window") {
self.setWindowPostition(e);
}
if(self.options.zoomType == "inner") {
self.setWindowPostition(e);
}
if(self.options.showLens) {
if(self.fullwidth && self.options.zoomType != "lens"){
self.lensLeftPos = 0;
}
self.zoomLens.css({ left: self.lensLeftPos + 'px', top: self.lensTopPos + 'px' })
}
} //end else
},
showHideWindow: function(change) {
var self = this;
if(change == "show"){
if(!self.isWindowActive){
if(self.options.zoomWindowFadeIn){
self.zoomWindow.stop(true, true, false).fadeIn(self.options.zoomWindowFadeIn);
}
else{self.zoomWindow.show();}
self.isWindowActive = true;
}
}
if(change == "hide"){
if(self.isWindowActive){
if(self.options.zoomWindowFadeOut){
self.zoomWindow.stop(true, true).fadeOut(self.options.zoomWindowFadeOut, function () {
if (self.loop) {
//stop moving the zoom window when zoom window is faded out
clearInterval(self.loop);
self.loop = false;
}
});
}
else{self.zoomWindow.hide();}
self.isWindowActive = false;
}
}
},
showHideLens: function(change) {
var self = this;
if(change == "show"){
if(!self.isLensActive){
if(self.options.lensFadeIn){
self.zoomLens.stop(true, true, false).fadeIn(self.options.lensFadeIn);
}
else{self.zoomLens.show();}
self.isLensActive = true;
}
}
if(change == "hide"){
if(self.isLensActive){
if(self.options.lensFadeOut){
self.zoomLens.stop(true, true).fadeOut(self.options.lensFadeOut);
}
else{self.zoomLens.hide();}
self.isLensActive = false;
}
}
},
showHideTint: function(change) {
var self = this;
if(change == "show"){
if(!self.isTintActive){
if(self.options.zoomTintFadeIn){
self.zoomTint.css({opacity:self.options.tintOpacity}).animate().stop(true, true).fadeIn("slow");
}
else{
self.zoomTint.css({opacity:self.options.tintOpacity}).animate();
self.zoomTint.show();
}
self.isTintActive = true;
}
}
if(change == "hide"){
if(self.isTintActive){
if(self.options.zoomTintFadeOut){
self.zoomTint.stop(true, true).fadeOut(self.options.zoomTintFadeOut);
}
else{self.zoomTint.hide();}
self.isTintActive = false;
}
}
},
setLensPostition: function( e ) {
},
setWindowPostition: function( e ) {
//return obj.slice( 0, count );
var self = this;
if(!isNaN(self.options.zoomWindowPosition)){
switch (self.options.zoomWindowPosition) {
case 1: //done
self.windowOffsetTop = (self.options.zoomWindowOffety);//DONE - 1
self.windowOffsetLeft =(+self.nzWidth); //DONE 1, 2, 3, 4, 16
break;
case 2:
if(self.options.zoomWindowHeight > self.nzHeight){ //positive margin
self.windowOffsetTop = ((self.options.zoomWindowHeight/2)-(self.nzHeight/2))*(-1);
self.windowOffsetLeft =(self.nzWidth); //DONE 1, 2, 3, 4, 16
}
else{ //negative margin
}
break;
case 3: //done
self.windowOffsetTop = (self.nzHeight - self.zoomWindow.height() - (self.options.borderSize*2)); //DONE 3,9
self.windowOffsetLeft =(self.nzWidth); //DONE 1, 2, 3, 4, 16
break;
case 4: //done
self.windowOffsetTop = (self.nzHeight); //DONE - 4,5,6,7,8
self.windowOffsetLeft =(self.nzWidth); //DONE 1, 2, 3, 4, 16
break;
case 5: //done
self.windowOffsetTop = (self.nzHeight); //DONE - 4,5,6,7,8
self.windowOffsetLeft =(self.nzWidth-self.zoomWindow.width()-(self.options.borderSize*2)); //DONE - 5,15
break;
case 6:
if(self.options.zoomWindowHeight > self.nzHeight){ //positive margin
self.windowOffsetTop = (self.nzHeight); //DONE - 4,5,6,7,8
self.windowOffsetLeft =((self.options.zoomWindowWidth/2)-(self.nzWidth/2)+(self.options.borderSize*2))*(-1);
}
else{ //negative margin
}
break;
case 7: //done
self.windowOffsetTop = (self.nzHeight); //DONE - 4,5,6,7,8
self.windowOffsetLeft = 0; //DONE 7, 13
break;
case 8: //done
self.windowOffsetTop = (self.nzHeight); //DONE - 4,5,6,7,8
self.windowOffsetLeft =(self.zoomWindow.width()+(self.options.borderSize*2) )* (-1); //DONE 8,9,10,11,12
break;
case 9: //done
self.windowOffsetTop = (self.nzHeight - self.zoomWindow.height() - (self.options.borderSize*2)); //DONE 3,9
self.windowOffsetLeft =(self.zoomWindow.width()+(self.options.borderSize*2) )* (-1); //DONE 8,9,10,11,12
break;
case 10:
if(self.options.zoomWindowHeight > self.nzHeight){ //positive margin
self.windowOffsetTop = ((self.options.zoomWindowHeight/2)-(self.nzHeight/2))*(-1);
self.windowOffsetLeft =(self.zoomWindow.width()+(self.options.borderSize*2) )* (-1); //DONE 8,9,10,11,12
}
else{ //negative margin
}
break;
case 11:
self.windowOffsetTop = (self.options.zoomWindowOffety);
self.windowOffsetLeft =(self.zoomWindow.width()+(self.options.borderSize*2) )* (-1); //DONE 8,9,10,11,12
break;
case 12: //done
self.windowOffsetTop = (self.zoomWindow.height()+(self.options.borderSize*2))*(-1); //DONE 12,13,14,15,16
self.windowOffsetLeft =(self.zoomWindow.width()+(self.options.borderSize*2) )* (-1); //DONE 8,9,10,11,12
break;
case 13: //done
self.windowOffsetTop = (self.zoomWindow.height()+(self.options.borderSize*2))*(-1); //DONE 12,13,14,15,16
self.windowOffsetLeft =(0); //DONE 7, 13
break;
case 14:
if(self.options.zoomWindowHeight > self.nzHeight){ //positive margin
self.windowOffsetTop = (self.zoomWindow.height()+(self.options.borderSize*2))*(-1); //DONE 12,13,14,15,16
self.windowOffsetLeft =((self.options.zoomWindowWidth/2)-(self.nzWidth/2)+(self.options.borderSize*2))*(-1);
}
else{ //negative margin
}
break;
case 15://done
self.windowOffsetTop = (self.zoomWindow.height()+(self.options.borderSize*2))*(-1); //DONE 12,13,14,15,16
self.windowOffsetLeft =(self.nzWidth-self.zoomWindow.width()-(self.options.borderSize*2)); //DONE - 5,15
break;
case 16: //done
self.windowOffsetTop = (self.zoomWindow.height()+(self.options.borderSize*2))*(-1); //DONE 12,13,14,15,16
self.windowOffsetLeft =(self.nzWidth); //DONE 1, 2, 3, 4, 16
break;
default: //done
self.windowOffsetTop = (self.options.zoomWindowOffety);//DONE - 1
self.windowOffsetLeft =(self.nzWidth); //DONE 1, 2, 3, 4, 16
}
} //end isNAN
else{
//WE CAN POSITION IN A CLASS - ASSUME THAT ANY STRING PASSED IS
self.externalContainer = $('#'+self.options.zoomWindowPosition);
self.externalContainerWidth = self.externalContainer.width();
self.externalContainerHeight = self.externalContainer.height();
self.externalContainerOffset = self.externalContainer.offset();
self.windowOffsetTop = self.externalContainerOffset.top;//DONE - 1
self.windowOffsetLeft =self.externalContainerOffset.left; //DONE 1, 2, 3, 4, 16
}
self.isWindowSet = true;
self.windowOffsetTop = self.windowOffsetTop + self.options.zoomWindowOffety;
self.windowOffsetLeft = self.windowOffsetLeft + self.options.zoomWindowOffetx;
self.zoomWindow.css({ top: self.windowOffsetTop});
self.zoomWindow.css({ left: self.windowOffsetLeft});
if(self.options.zoomType == "inner") {
self.zoomWindow.css({ top: 0});
self.zoomWindow.css({ left: 0});
}
self.windowLeftPos = String(((e.pageX - self.nzOffset.left) * self.widthRatio - self.zoomWindow.width() / 2) * (-1));
self.windowTopPos = String(((e.pageY - self.nzOffset.top) * self.heightRatio - self.zoomWindow.height() / 2) * (-1));
if(self.Etoppos){self.windowTopPos = 0;}
if(self.Eloppos){self.windowLeftPos = 0;}
if(self.Eboppos){self.windowTopPos = (self.largeHeight/self.currentZoomLevel-self.zoomWindow.height())*(-1); }
if(self.Eroppos){self.windowLeftPos = ((self.largeWidth/self.currentZoomLevel-self.zoomWindow.width())*(-1));}
//stops micro movements
if(self.fullheight){
self.windowTopPos = 0;
}
if(self.fullwidth){
self.windowLeftPos = 0;
}
//set the css background position
if(self.options.zoomType == "window" || self.options.zoomType == "inner") {
if(self.zoomLock == 1){
//overrides for images not zoomable
if(self.widthRatio <= 1){
self.windowLeftPos = 0;
}
if(self.heightRatio <= 1){
self.windowTopPos = 0;
}
}
// adjust images less than the window height
if (self.options.zoomType == "window") {
if (self.largeHeight < self.options.zoomWindowHeight) {
self.windowTopPos = 0;
}
if (self.largeWidth < self.options.zoomWindowWidth) {
self.windowLeftPos = 0;
}
}
//set the zoomwindow background position
if (self.options.easing){
// if(self.changeZoom){
// clearInterval(self.loop);
// self.changeZoom = false;
// self.loop = false;
// }
//set the pos to 0 if not set
if(!self.xp){self.xp = 0;}
if(!self.yp){self.yp = 0;}
//if loop not already started, then run it
if (!self.loop){
self.loop = setInterval(function(){
//using zeno's paradox
self.xp += (self.windowLeftPos - self.xp) / self.options.easingAmount;
self.yp += (self.windowTopPos - self.yp) / self.options.easingAmount;
if(self.scrollingLock){
clearInterval(self.loop);
self.xp = self.windowLeftPos;
self.yp = self.windowTopPos
self.xp = ((e.pageX - self.nzOffset.left) * self.widthRatio - self.zoomWindow.width() / 2) * (-1);
self.yp = (((e.pageY - self.nzOffset.top) * self.heightRatio - self.zoomWindow.height() / 2) * (-1));
if(self.changeBgSize){
if(self.nzHeight>self.nzWidth){
if(self.options.zoomType == "lens"){
self.zoomLens.css({ "background-size": self.largeWidth/self.newvalueheight + 'px ' + self.largeHeight/self.newvalueheight + 'px' });
}
self.zoomWindow.css({ "background-size": self.largeWidth/self.newvalueheight + 'px ' + self.largeHeight/self.newvalueheight + 'px' });
}
else{
if(self.options.zoomType != "lens"){
self.zoomLens.css({ "background-size": self.largeWidth/self.newvaluewidth + 'px ' + self.largeHeight/self.newvalueheight + 'px' });
}
self.zoomWindow.css({ "background-size": self.largeWidth/self.newvaluewidth + 'px ' + self.largeHeight/self.newvaluewidth + 'px' });
}
/*
if(!self.bgxp){self.bgxp = self.largeWidth/self.newvalue;}
if(!self.bgyp){self.bgyp = self.largeHeight/self.newvalue ;}
if (!self.bgloop){
self.bgloop = setInterval(function(){
self.bgxp += (self.largeWidth/self.newvalue - self.bgxp) / self.options.easingAmount;
self.bgyp += (self.largeHeight/self.newvalue - self.bgyp) / self.options.easingAmount;
self.zoomWindow.css({ "background-size": self.bgxp + 'px ' + self.bgyp + 'px' });
}, 16);
}
*/
self.changeBgSize = false;
}
self.zoomWindow.css({ backgroundPosition: self.windowLeftPos + 'px ' + self.windowTopPos + 'px' });
self.scrollingLock = false;
self.loop = false;
}
else if (Math.round(Math.abs(self.xp - self.windowLeftPos) + Math.abs(self.yp - self.windowTopPos)) < 1) {
//stops micro movements
clearInterval(self.loop);
self.zoomWindow.css({ backgroundPosition: self.windowLeftPos + 'px ' + self.windowTopPos + 'px' });
self.loop = false;
}
else{
if(self.changeBgSize){
if(self.nzHeight>self.nzWidth){
if(self.options.zoomType == "lens"){
self.zoomLens.css({ "background-size": self.largeWidth/self.newvalueheight + 'px ' + self.largeHeight/self.newvalueheight + 'px' });
}
self.zoomWindow.css({ "background-size": self.largeWidth/self.newvalueheight + 'px ' + self.largeHeight/self.newvalueheight + 'px' });
}
else{
if(self.options.zoomType != "lens"){
self.zoomLens.css({ "background-size": self.largeWidth/self.newvaluewidth + 'px ' + self.largeHeight/self.newvaluewidth + 'px' });
}
self.zoomWindow.css({ "background-size": self.largeWidth/self.newvaluewidth + 'px ' + self.largeHeight/self.newvaluewidth + 'px' });
}
self.changeBgSize = false;
}
self.zoomWindow.css({ backgroundPosition: self.xp + 'px ' + self.yp + 'px' });
}
}, 16);
}
}
else{
if(self.changeBgSize){
if(self.nzHeight>self.nzWidth){
if(self.options.zoomType == "lens"){
self.zoomLens.css({ "background-size": self.largeWidth/self.newvalueheight + 'px ' + self.largeHeight/self.newvalueheight + 'px' });
}
self.zoomWindow.css({ "background-size": self.largeWidth/self.newvalueheight + 'px ' + self.largeHeight/self.newvalueheight + 'px' });
}
else{
if(self.options.zoomType == "lens"){
self.zoomLens.css({ "background-size": self.largeWidth/self.newvaluewidth + 'px ' + self.largeHeight/self.newvaluewidth + 'px' });
}
if((self.largeHeight/self.newvaluewidth) < self.options.zoomWindowHeight){
self.zoomWindow.css({ "background-size": self.largeWidth/self.newvaluewidth + 'px ' + self.largeHeight/self.newvaluewidth + 'px' });
}
else{
self.zoomWindow.css({ "background-size": self.largeWidth/self.newvalueheight + 'px ' + self.largeHeight/self.newvalueheight + 'px' });
}
}
self.changeBgSize = false;
}
self.zoomWindow.css({ backgroundPosition: self.windowLeftPos + 'px ' + self.windowTopPos + 'px' });
}
}
},
setTintPosition: function(e){
var self = this;
self.nzOffset = self.$elem.offset();
self.tintpos = String(((e.pageX - self.nzOffset.left)-(self.zoomLens.width() / 2)) * (-1));
self.tintposy = String(((e.pageY - self.nzOffset.top) - self.zoomLens.height() / 2) * (-1));
if(self.Etoppos){
self.tintposy = 0;
}
if(self.Eloppos){
self.tintpos=0;
}
if(self.Eboppos){
self.tintposy = (self.nzHeight-self.zoomLens.height()-(self.options.lensBorderSize*2))*(-1);
}
if(self.Eroppos){
self.tintpos = ((self.nzWidth-self.zoomLens.width()-(self.options.lensBorderSize*2))*(-1));
}
if(self.options.tint) {
//stops micro movements
if(self.fullheight){
self.tintposy = 0;
}
if(self.fullwidth){
self.tintpos = 0;
}
self.zoomTintImage.css({'left': self.tintpos+'px'});
self.zoomTintImage.css({'top': self.tintposy+'px'});
}
},
swaptheimage: function(smallimage, largeimage){
var self = this;
var newImg = new Image();
if(self.options.loadingIcon){
self.spinner = $('<div style="background: url(\''+self.options.loadingIcon+'\') no-repeat center;height:'+self.nzHeight+'px;width:'+self.nzWidth+'px;z-index: 2000;position: absolute; background-position: center center;"></div>');
self.$elem.after(self.spinner);
}
self.options.onImageSwap(self.$elem);
newImg.onload = function() {
self.largeWidth = newImg.width;
self.largeHeight = newImg.height;
self.zoomImage = largeimage;
self.zoomWindow.css({ "background-size": self.largeWidth + 'px ' + self.largeHeight + 'px' });
self.swapAction(smallimage, largeimage);
return;
}
newImg.src = largeimage; // this must be done AFTER setting onload
},
swapAction: function(smallimage, largeimage){
var self = this;
var newImg2 = new Image();
newImg2.onload = function() {
//re-calculate values
self.nzHeight = newImg2.height;
self.nzWidth = newImg2.width;
self.options.onImageSwapComplete(self.$elem);
self.doneCallback();
return;
}
newImg2.src = smallimage;
//reset the zoomlevel to that initially set in options
self.currentZoomLevel = self.options.zoomLevel;
self.options.maxZoomLevel = false;
//swaps the main image
//self.$elem.attr("src",smallimage);
//swaps the zoom image
if(self.options.zoomType == "lens") {
self.zoomLens.css({ backgroundImage: "url('" + largeimage + "')" });
}
if(self.options.zoomType == "window") {
self.zoomWindow.css({ backgroundImage: "url('" + largeimage + "')" });
}
if(self.options.zoomType == "inner") {
self.zoomWindow.css({ backgroundImage: "url('" + largeimage + "')" });
}
self.currentImage = largeimage;
if(self.options.imageCrossfade){
var oldImg = self.$elem;
var newImg = oldImg.clone();
self.$elem.attr("src",smallimage)
self.$elem.after(newImg);
newImg.stop(true).fadeOut(self.options.imageCrossfade, function() {
$(this).remove();
});
// if(self.options.zoomType == "inner"){
//remove any attributes on the cloned image so we can resize later
self.$elem.width("auto").removeAttr("width");
self.$elem.height("auto").removeAttr("height");
// }
oldImg.fadeIn(self.options.imageCrossfade);
if(self.options.tint && self.options.zoomType != "inner") {
var oldImgTint = self.zoomTintImage;
var newImgTint = oldImgTint.clone();
self.zoomTintImage.attr("src",largeimage)
self.zoomTintImage.after(newImgTint);
newImgTint.stop(true).fadeOut(self.options.imageCrossfade, function() {
$(this).remove();
});
oldImgTint.fadeIn(self.options.imageCrossfade);
//self.zoomTintImage.attr("width",elem.data("image"));
//resize the tint window
self.zoomTint.css({ height: self.$elem.height()});
self.zoomTint.css({ width: self.$elem.width()});
}
self.zoomContainer.css("height", self.$elem.height());
self.zoomContainer.css("width", self.$elem.width());
if(self.options.zoomType == "inner"){
if(!self.options.constrainType){
self.zoomWrap.parent().css("height", self.$elem.height());
self.zoomWrap.parent().css("width", self.$elem.width());
self.zoomWindow.css("height", self.$elem.height());
self.zoomWindow.css("width", self.$elem.width());
}
}
if(self.options.imageCrossfade){
self.zoomWrap.css("height", self.$elem.height());
self.zoomWrap.css("width", self.$elem.width());
}
}
else{
self.$elem.attr("src",smallimage);
if(self.options.tint) {
self.zoomTintImage.attr("src",largeimage);
//self.zoomTintImage.attr("width",elem.data("image"));
self.zoomTintImage.attr("height",self.$elem.height());
//self.zoomTintImage.attr('src') = elem.data("image");
self.zoomTintImage.css({ height: self.$elem.height()});
self.zoomTint.css({ height: self.$elem.height()});
}
self.zoomContainer.css("height", self.$elem.height());
self.zoomContainer.css("width", self.$elem.width());
if(self.options.imageCrossfade){
self.zoomWrap.css("height", self.$elem.height());
self.zoomWrap.css("width", self.$elem.width());
}
}
if(self.options.constrainType){
//This will contrain the image proportions
if(self.options.constrainType == "height"){
self.zoomContainer.css("height", self.options.constrainSize);
self.zoomContainer.css("width", "auto");
if(self.options.imageCrossfade){
self.zoomWrap.css("height", self.options.constrainSize);
self.zoomWrap.css("width", "auto");
self.constwidth = self.zoomWrap.width();
}
else{
self.$elem.css("height", self.options.constrainSize);
self.$elem.css("width", "auto");
self.constwidth = self.$elem.width();
}
if(self.options.zoomType == "inner"){
self.zoomWrap.parent().css("height", self.options.constrainSize);
self.zoomWrap.parent().css("width", self.constwidth);
self.zoomWindow.css("height", self.options.constrainSize);
self.zoomWindow.css("width", self.constwidth);
}
if(self.options.tint){
self.tintContainer.css("height", self.options.constrainSize);
self.tintContainer.css("width", self.constwidth);
self.zoomTint.css("height", self.options.constrainSize);
self.zoomTint.css("width", self.constwidth);
self.zoomTintImage.css("height", self.options.constrainSize);
self.zoomTintImage.css("width", self.constwidth);
}
}
if(self.options.constrainType == "width"){
self.zoomContainer.css("height", "auto");
self.zoomContainer.css("width", self.options.constrainSize);
if(self.options.imageCrossfade){
self.zoomWrap.css("height", "auto");
self.zoomWrap.css("width", self.options.constrainSize);
self.constheight = self.zoomWrap.height();
}
else{
self.$elem.css("height", "auto");
self.$elem.css("width", self.options.constrainSize);
self.constheight = self.$elem.height();
}
if(self.options.zoomType == "inner"){
self.zoomWrap.parent().css("height", self.constheight);
self.zoomWrap.parent().css("width", self.options.constrainSize);
self.zoomWindow.css("height", self.constheight);
self.zoomWindow.css("width", self.options.constrainSize);
}
if(self.options.tint){
self.tintContainer.css("height", self.constheight);
self.tintContainer.css("width", self.options.constrainSize);
self.zoomTint.css("height", self.constheight);
self.zoomTint.css("width", self.options.constrainSize);
self.zoomTintImage.css("height", self.constheight);
self.zoomTintImage.css("width", self.options.constrainSize);
}
}
}
},
doneCallback: function(){
var self = this;
if(self.options.loadingIcon){
self.spinner.hide();
}
self.nzOffset = self.$elem.offset();
self.nzWidth = self.$elem.width();
self.nzHeight = self.$elem.height();
// reset the zoomlevel back to default
self.currentZoomLevel = self.options.zoomLevel;
//ratio of the large to small image
self.widthRatio = self.largeWidth / self.nzWidth;
self.heightRatio = self.largeHeight / self.nzHeight;
//NEED TO ADD THE LENS SIZE FOR ROUND
// adjust images less than the window height
if(self.options.zoomType == "window") {
if(self.nzHeight < self.options.zoomWindowWidth/self.widthRatio){
lensHeight = self.nzHeight;
}
else{
lensHeight = String((self.options.zoomWindowHeight/self.heightRatio))
}
if(self.options.zoomWindowWidth < self.options.zoomWindowWidth){
lensWidth = self.nzWidth;
}
else{
lensWidth = (self.options.zoomWindowWidth/self.widthRatio);
}
if(self.zoomLens){
self.zoomLens.css('width', lensWidth);
self.zoomLens.css('height', lensHeight);
}
}
},
getCurrentImage: function(){
var self = this;
return self.zoomImage;
},
getGalleryList: function(){
var self = this;
//loop through the gallery options and set them in list for fancybox
self.gallerylist = [];
if (self.options.gallery){
$('#'+self.options.gallery + ' a').each(function() {
var img_src = '';
if($(this).data("zoom-image")){
img_src = $(this).data("zoom-image");
}
else if($(this).data("image")){
img_src = $(this).data("image");
}
//put the current image at the start
if(img_src == self.zoomImage){
self.gallerylist.unshift({
href: ''+img_src+'',
title: $(this).find('img').attr("title")
});
}
else{
self.gallerylist.push({
href: ''+img_src+'',
title: $(this).find('img').attr("title")
});
}
});
}
//if no gallery - return current image
else{
self.gallerylist.push({
href: ''+self.zoomImage+'',
title: $(this).find('img').attr("title")
});
}
return self.gallerylist;
},
changeZoomLevel: function(value){
var self = this;
//flag a zoom, so can adjust the easing during setPosition
self.scrollingLock = true;
//round to two decimal places
self.newvalue = parseFloat(value).toFixed(2);
newvalue = parseFloat(value).toFixed(2);
//maxwidth & Maxheight of the image
maxheightnewvalue = self.largeHeight/((self.options.zoomWindowHeight / self.nzHeight) * self.nzHeight);
maxwidthtnewvalue = self.largeWidth/((self.options.zoomWindowWidth / self.nzWidth) * self.nzWidth);
//calculate new heightratio
if(self.options.zoomType != "inner")
{
if(maxheightnewvalue <= newvalue){
self.heightRatio = (self.largeHeight/maxheightnewvalue) / self.nzHeight;
self.newvalueheight = maxheightnewvalue;
self.fullheight = true;
}
else{
self.heightRatio = (self.largeHeight/newvalue) / self.nzHeight;
self.newvalueheight = newvalue;
self.fullheight = false;
}
// calculate new width ratio
if(maxwidthtnewvalue <= newvalue){
self.widthRatio = (self.largeWidth/maxwidthtnewvalue) / self.nzWidth;
self.newvaluewidth = maxwidthtnewvalue;
self.fullwidth = true;
}
else{
self.widthRatio = (self.largeWidth/newvalue) / self.nzWidth;
self.newvaluewidth = newvalue;
self.fullwidth = false;
}
if(self.options.zoomType == "lens"){
if(maxheightnewvalue <= newvalue){
self.fullwidth = true;
self.newvaluewidth = maxheightnewvalue;
} else{
self.widthRatio = (self.largeWidth/newvalue) / self.nzWidth;
self.newvaluewidth = newvalue;
self.fullwidth = false;
}}
}
if(self.options.zoomType == "inner")
{
maxheightnewvalue = parseFloat(self.largeHeight/self.nzHeight).toFixed(2);
maxwidthtnewvalue = parseFloat(self.largeWidth/self.nzWidth).toFixed(2);
if(newvalue > maxheightnewvalue){
newvalue = maxheightnewvalue;
}
if(newvalue > maxwidthtnewvalue){
newvalue = maxwidthtnewvalue;
}
if(maxheightnewvalue <= newvalue){
self.heightRatio = (self.largeHeight/newvalue) / self.nzHeight;
if(newvalue > maxheightnewvalue){
self.newvalueheight = maxheightnewvalue;
}else{
self.newvalueheight = newvalue;
}
self.fullheight = true;
}
else{
self.heightRatio = (self.largeHeight/newvalue) / self.nzHeight;
if(newvalue > maxheightnewvalue){
self.newvalueheight = maxheightnewvalue;
}else{
self.newvalueheight = newvalue;
}
self.fullheight = false;
}
if(maxwidthtnewvalue <= newvalue){
self.widthRatio = (self.largeWidth/newvalue) / self.nzWidth;
if(newvalue > maxwidthtnewvalue){
self.newvaluewidth = maxwidthtnewvalue;
}else{
self.newvaluewidth = newvalue;
}
self.fullwidth = true;
}
else{
self.widthRatio = (self.largeWidth/newvalue) / self.nzWidth;
self.newvaluewidth = newvalue;
self.fullwidth = false;
}
} //end inner
scrcontinue = false;
if(self.options.zoomType == "inner"){
if(self.nzWidth >= self.nzHeight){
if( self.newvaluewidth <= maxwidthtnewvalue){
scrcontinue = true;
}
else{
scrcontinue = false;
self.fullheight = true;
self.fullwidth = true;
}
}
if(self.nzHeight > self.nzWidth){
if( self.newvaluewidth <= maxwidthtnewvalue){
scrcontinue = true;
}
else{
scrcontinue = false;
self.fullheight = true;
self.fullwidth = true;
}
}
}
if(self.options.zoomType != "inner"){
scrcontinue = true;
}
if(scrcontinue){
self.zoomLock = 0;
self.changeZoom = true;
//if lens height is less than image height
if(((self.options.zoomWindowHeight)/self.heightRatio) <= self.nzHeight){
self.currentZoomLevel = self.newvalueheight;
if(self.options.zoomType != "lens" && self.options.zoomType != "inner") {
self.changeBgSize = true;
self.zoomLens.css({height: String((self.options.zoomWindowHeight)/self.heightRatio) + 'px' })
}
if(self.options.zoomType == "lens" || self.options.zoomType == "inner") {
self.changeBgSize = true;
}
}
if((self.options.zoomWindowWidth/self.widthRatio) <= self.nzWidth){
if(self.options.zoomType != "inner"){
if(self.newvaluewidth > self.newvalueheight) {
self.currentZoomLevel = self.newvaluewidth;
}
}
if(self.options.zoomType != "lens" && self.options.zoomType != "inner") {
self.changeBgSize = true;
self.zoomLens.css({width: String((self.options.zoomWindowWidth)/self.widthRatio) + 'px' })
}
if(self.options.zoomType == "lens" || self.options.zoomType == "inner") {
self.changeBgSize = true;
}
}
if(self.options.zoomType == "inner"){
self.changeBgSize = true;
if(self.nzWidth > self.nzHeight){
self.currentZoomLevel = self.newvaluewidth;
}
if(self.nzHeight > self.nzWidth){
self.currentZoomLevel = self.newvaluewidth;
}
}
} //under
//sets the boundry change, called in setWindowPos
self.setPosition(self.currentLoc);
//
},
closeAll: function(){
if(self.zoomWindow){self.zoomWindow.hide();}
if(self.zoomLens){self.zoomLens.hide();}
if(self.zoomTint){self.zoomTint.hide();}
},
changeState: function(value){
var self = this;
if(value == 'enable'){self.options.zoomEnabled = true;}
if(value == 'disable'){self.options.zoomEnabled = false;}
}
};
$.fn.elevateZoom = function( options ) {
return this.each(function() {
var elevate = Object.create( ElevateZoom );
elevate.init( options, this );
$.data( this, 'elevateZoom', elevate );
});
};
$.fn.elevateZoom.options = {
zoomActivation: "hover", // Can also be click (PLACEHOLDER FOR NEXT VERSION)
zoomEnabled: true, //false disables zoomwindow from showing
preloading: 1, //by default, load all the images, if 0, then only load images after activated (PLACEHOLDER FOR NEXT VERSION)
zoomLevel: 1, //default zoom level of image
scrollZoom: false, //allow zoom on mousewheel, true to activate
scrollZoomIncrement: 0.1, //steps of the scrollzoom
minZoomLevel: false,
maxZoomLevel: false,
easing: false,
easingAmount: 12,
lensSize: 200,
zoomWindowWidth: 400,
zoomWindowHeight: 400,
zoomWindowOffetx: 0,
zoomWindowOffety: 0,
zoomWindowPosition: 1,
zoomWindowBgColour: "#fff",
lensFadeIn: false,
lensFadeOut: false,
debug: false,
zoomWindowFadeIn: false,
zoomWindowFadeOut: false,
zoomWindowAlwaysShow: false,
zoomTintFadeIn: false,
zoomTintFadeOut: false,
borderSize: 4,
showLens: true,
borderColour: "#888",
lensBorderSize: 1,
lensBorderColour: "#000",
lensShape: "square", //can be "round"
zoomType: "window", //window is default, also "lens" available -
containLensZoom: false,
lensColour: "white", //colour of the lens background
lensOpacity: 0.4, //opacity of the lens
lenszoom: false,
tint: false, //enable the tinting
tintColour: "#333", //default tint color, can be anything, red, #ccc, rgb(0,0,0)
tintOpacity: 0.4, //opacity of the tint
gallery: false,
galleryActiveClass: "zoomGalleryActive",
imageCrossfade: false,
constrainType: false, //width or height
constrainSize: false, //in pixels the dimensions you want to constrain on
loadingIcon: false, //http://www.example.com/spinner.gif
cursor:"default", // user should set to what they want the cursor as, if they have set a click function
responsive:true,
onComplete: $.noop,
onDestroy: function() {},
onZoomedImageLoaded: function() {},
onImageSwap: $.noop,
onImageSwapComplete: $.noop
};
})( jQuery, window, document );
\ No newline at end of file
/*! jQuery v1.10.1 | (c) 2005, 2013 jQuery Foundation, Inc. | jquery.org/license
//@ sourceMappingURL=jquery-1.10.1.min.map
*/
(function(e,t){var n,r,i=typeof t,o=e.location,a=e.document,s=a.documentElement,l=e.jQuery,u=e.$,c={},p=[],f="1.10.1",d=p.concat,h=p.push,g=p.slice,m=p.indexOf,y=c.toString,v=c.hasOwnProperty,b=f.trim,x=function(e,t){return new x.fn.init(e,t,r)},w=/[+-]?(?:\d*\.|)\d+(?:[eE][+-]?\d+|)/.source,T=/\S+/g,C=/^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g,N=/^(?:\s*(<[\w\W]+>)[^>]*|#([\w-]*))$/,k=/^<(\w+)\s*\/?>(?:<\/\1>|)$/,E=/^[\],:{}\s]*$/,S=/(?:^|:|,)(?:\s*\[)+/g,A=/\\(?:["\\\/bfnrt]|u[\da-fA-F]{4})/g,j=/"[^"\\\r\n]*"|true|false|null|-?(?:\d+\.|)\d+(?:[eE][+-]?\d+|)/g,D=/^-ms-/,L=/-([\da-z])/gi,H=function(e,t){return t.toUpperCase()},q=function(e){(a.addEventListener||"load"===e.type||"complete"===a.readyState)&&(_(),x.ready())},_=function(){a.addEventListener?(a.removeEventListener("DOMContentLoaded",q,!1),e.removeEventListener("load",q,!1)):(a.detachEvent("onreadystatechange",q),e.detachEvent("onload",q))};x.fn=x.prototype={jquery:f,constructor:x,init:function(e,n,r){var i,o;if(!e)return this;if("string"==typeof e){if(i="<"===e.charAt(0)&&">"===e.charAt(e.length-1)&&e.length>=3?[null,e,null]:N.exec(e),!i||!i[1]&&n)return!n||n.jquery?(n||r).find(e):this.constructor(n).find(e);if(i[1]){if(n=n instanceof x?n[0]:n,x.merge(this,x.parseHTML(i[1],n&&n.nodeType?n.ownerDocument||n:a,!0)),k.test(i[1])&&x.isPlainObject(n))for(i in n)x.isFunction(this[i])?this[i](n[i]):this.attr(i,n[i]);return this}if(o=a.getElementById(i[2]),o&&o.parentNode){if(o.id!==i[2])return r.find(e);this.length=1,this[0]=o}return this.context=a,this.selector=e,this}return e.nodeType?(this.context=this[0]=e,this.length=1,this):x.isFunction(e)?r.ready(e):(e.selector!==t&&(this.selector=e.selector,this.context=e.context),x.makeArray(e,this))},selector:"",length:0,toArray:function(){return g.call(this)},get:function(e){return null==e?this.toArray():0>e?this[this.length+e]:this[e]},pushStack:function(e){var t=x.merge(this.constructor(),e);return t.prevObject=this,t.context=this.context,t},each:function(e,t){return x.each(this,e,t)},ready:function(e){return x.ready.promise().done(e),this},slice:function(){return this.pushStack(g.apply(this,arguments))},first:function(){return this.eq(0)},last:function(){return this.eq(-1)},eq:function(e){var t=this.length,n=+e+(0>e?t:0);return this.pushStack(n>=0&&t>n?[this[n]]:[])},map:function(e){return this.pushStack(x.map(this,function(t,n){return e.call(t,n,t)}))},end:function(){return this.prevObject||this.constructor(null)},push:h,sort:[].sort,splice:[].splice},x.fn.init.prototype=x.fn,x.extend=x.fn.extend=function(){var e,n,r,i,o,a,s=arguments[0]||{},l=1,u=arguments.length,c=!1;for("boolean"==typeof s&&(c=s,s=arguments[1]||{},l=2),"object"==typeof s||x.isFunction(s)||(s={}),u===l&&(s=this,--l);u>l;l++)if(null!=(o=arguments[l]))for(i in o)e=s[i],r=o[i],s!==r&&(c&&r&&(x.isPlainObject(r)||(n=x.isArray(r)))?(n?(n=!1,a=e&&x.isArray(e)?e:[]):a=e&&x.isPlainObject(e)?e:{},s[i]=x.extend(c,a,r)):r!==t&&(s[i]=r));return s},x.extend({expando:"jQuery"+(f+Math.random()).replace(/\D/g,""),noConflict:function(t){return e.$===x&&(e.$=u),t&&e.jQuery===x&&(e.jQuery=l),x},isReady:!1,readyWait:1,holdReady:function(e){e?x.readyWait++:x.ready(!0)},ready:function(e){if(e===!0?!--x.readyWait:!x.isReady){if(!a.body)return setTimeout(x.ready);x.isReady=!0,e!==!0&&--x.readyWait>0||(n.resolveWith(a,[x]),x.fn.trigger&&x(a).trigger("ready").off("ready"))}},isFunction:function(e){return"function"===x.type(e)},isArray:Array.isArray||function(e){return"array"===x.type(e)},isWindow:function(e){return null!=e&&e==e.window},isNumeric:function(e){return!isNaN(parseFloat(e))&&isFinite(e)},type:function(e){return null==e?e+"":"object"==typeof e||"function"==typeof e?c[y.call(e)]||"object":typeof e},isPlainObject:function(e){var n;if(!e||"object"!==x.type(e)||e.nodeType||x.isWindow(e))return!1;try{if(e.constructor&&!v.call(e,"constructor")&&!v.call(e.constructor.prototype,"isPrototypeOf"))return!1}catch(r){return!1}if(x.support.ownLast)for(n in e)return v.call(e,n);for(n in e);return n===t||v.call(e,n)},isEmptyObject:function(e){var t;for(t in e)return!1;return!0},error:function(e){throw Error(e)},parseHTML:function(e,t,n){if(!e||"string"!=typeof e)return null;"boolean"==typeof t&&(n=t,t=!1),t=t||a;var r=k.exec(e),i=!n&&[];return r?[t.createElement(r[1])]:(r=x.buildFragment([e],t,i),i&&x(i).remove(),x.merge([],r.childNodes))},parseJSON:function(n){return e.JSON&&e.JSON.parse?e.JSON.parse(n):null===n?n:"string"==typeof n&&(n=x.trim(n),n&&E.test(n.replace(A,"@").replace(j,"]").replace(S,"")))?Function("return "+n)():(x.error("Invalid JSON: "+n),t)},parseXML:function(n){var r,i;if(!n||"string"!=typeof n)return null;try{e.DOMParser?(i=new DOMParser,r=i.parseFromString(n,"text/xml")):(r=new ActiveXObject("Microsoft.XMLDOM"),r.async="false",r.loadXML(n))}catch(o){r=t}return r&&r.documentElement&&!r.getElementsByTagName("parsererror").length||x.error("Invalid XML: "+n),r},noop:function(){},globalEval:function(t){t&&x.trim(t)&&(e.execScript||function(t){e.eval.call(e,t)})(t)},camelCase:function(e){return e.replace(D,"ms-").replace(L,H)},nodeName:function(e,t){return e.nodeName&&e.nodeName.toLowerCase()===t.toLowerCase()},each:function(e,t,n){var r,i=0,o=e.length,a=M(e);if(n){if(a){for(;o>i;i++)if(r=t.apply(e[i],n),r===!1)break}else for(i in e)if(r=t.apply(e[i],n),r===!1)break}else if(a){for(;o>i;i++)if(r=t.call(e[i],i,e[i]),r===!1)break}else for(i in e)if(r=t.call(e[i],i,e[i]),r===!1)break;return e},trim:b&&!b.call("\ufeff\u00a0")?function(e){return null==e?"":b.call(e)}:function(e){return null==e?"":(e+"").replace(C,"")},makeArray:function(e,t){var n=t||[];return null!=e&&(M(Object(e))?x.merge(n,"string"==typeof e?[e]:e):h.call(n,e)),n},inArray:function(e,t,n){var r;if(t){if(m)return m.call(t,e,n);for(r=t.length,n=n?0>n?Math.max(0,r+n):n:0;r>n;n++)if(n in t&&t[n]===e)return n}return-1},merge:function(e,n){var r=n.length,i=e.length,o=0;if("number"==typeof r)for(;r>o;o++)e[i++]=n[o];else while(n[o]!==t)e[i++]=n[o++];return e.length=i,e},grep:function(e,t,n){var r,i=[],o=0,a=e.length;for(n=!!n;a>o;o++)r=!!t(e[o],o),n!==r&&i.push(e[o]);return i},map:function(e,t,n){var r,i=0,o=e.length,a=M(e),s=[];if(a)for(;o>i;i++)r=t(e[i],i,n),null!=r&&(s[s.length]=r);else for(i in e)r=t(e[i],i,n),null!=r&&(s[s.length]=r);return d.apply([],s)},guid:1,proxy:function(e,n){var r,i,o;return"string"==typeof n&&(o=e[n],n=e,e=o),x.isFunction(e)?(r=g.call(arguments,2),i=function(){return e.apply(n||this,r.concat(g.call(arguments)))},i.guid=e.guid=e.guid||x.guid++,i):t},access:function(e,n,r,i,o,a,s){var l=0,u=e.length,c=null==r;if("object"===x.type(r)){o=!0;for(l in r)x.access(e,n,l,r[l],!0,a,s)}else if(i!==t&&(o=!0,x.isFunction(i)||(s=!0),c&&(s?(n.call(e,i),n=null):(c=n,n=function(e,t,n){return c.call(x(e),n)})),n))for(;u>l;l++)n(e[l],r,s?i:i.call(e[l],l,n(e[l],r)));return o?e:c?n.call(e):u?n(e[0],r):a},now:function(){return(new Date).getTime()},swap:function(e,t,n,r){var i,o,a={};for(o in t)a[o]=e.style[o],e.style[o]=t[o];i=n.apply(e,r||[]);for(o in t)e.style[o]=a[o];return i}}),x.ready.promise=function(t){if(!n)if(n=x.Deferred(),"complete"===a.readyState)setTimeout(x.ready);else if(a.addEventListener)a.addEventListener("DOMContentLoaded",q,!1),e.addEventListener("load",q,!1);else{a.attachEvent("onreadystatechange",q),e.attachEvent("onload",q);var r=!1;try{r=null==e.frameElement&&a.documentElement}catch(i){}r&&r.doScroll&&function o(){if(!x.isReady){try{r.doScroll("left")}catch(e){return setTimeout(o,50)}_(),x.ready()}}()}return n.promise(t)},x.each("Boolean Number String Function Array Date RegExp Object Error".split(" "),function(e,t){c["[object "+t+"]"]=t.toLowerCase()});function M(e){var t=e.length,n=x.type(e);return x.isWindow(e)?!1:1===e.nodeType&&t?!0:"array"===n||"function"!==n&&(0===t||"number"==typeof t&&t>0&&t-1 in e)}r=x(a),function(e,t){var n,r,i,o,a,s,l,u,c,p,f,d,h,g,m,y,v,b="sizzle"+-new Date,w=e.document,T=0,C=0,N=lt(),k=lt(),E=lt(),S=!1,A=function(){return 0},j=typeof t,D=1<<31,L={}.hasOwnProperty,H=[],q=H.pop,_=H.push,M=H.push,O=H.slice,F=H.indexOf||function(e){var t=0,n=this.length;for(;n>t;t++)if(this[t]===e)return t;return-1},B="checked|selected|async|autofocus|autoplay|controls|defer|disabled|hidden|ismap|loop|multiple|open|readonly|required|scoped",P="[\\x20\\t\\r\\n\\f]",R="(?:\\\\.|[\\w-]|[^\\x00-\\xa0])+",W=R.replace("w","w#"),$="\\["+P+"*("+R+")"+P+"*(?:([*^$|!~]?=)"+P+"*(?:(['\"])((?:\\\\.|[^\\\\])*?)\\3|("+W+")|)|)"+P+"*\\]",I=":("+R+")(?:\\(((['\"])((?:\\\\.|[^\\\\])*?)\\3|((?:\\\\.|[^\\\\()[\\]]|"+$.replace(3,8)+")*)|.*)\\)|)",z=RegExp("^"+P+"+|((?:^|[^\\\\])(?:\\\\.)*)"+P+"+$","g"),X=RegExp("^"+P+"*,"+P+"*"),U=RegExp("^"+P+"*([>+~]|"+P+")"+P+"*"),V=RegExp(P+"*[+~]"),Y=RegExp("="+P+"*([^\\]'\"]*)"+P+"*\\]","g"),J=RegExp(I),G=RegExp("^"+W+"$"),Q={ID:RegExp("^#("+R+")"),CLASS:RegExp("^\\.("+R+")"),TAG:RegExp("^("+R.replace("w","w*")+")"),ATTR:RegExp("^"+$),PSEUDO:RegExp("^"+I),CHILD:RegExp("^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\("+P+"*(even|odd|(([+-]|)(\\d*)n|)"+P+"*(?:([+-]|)"+P+"*(\\d+)|))"+P+"*\\)|)","i"),bool:RegExp("^(?:"+B+")$","i"),needsContext:RegExp("^"+P+"*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\("+P+"*((?:-\\d)?\\d*)"+P+"*\\)|)(?=[^-]|$)","i")},K=/^[^{]+\{\s*\[native \w/,Z=/^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/,et=/^(?:input|select|textarea|button)$/i,tt=/^h\d$/i,nt=/'|\\/g,rt=RegExp("\\\\([\\da-f]{1,6}"+P+"?|("+P+")|.)","ig"),it=function(e,t,n){var r="0x"+t-65536;return r!==r||n?t:0>r?String.fromCharCode(r+65536):String.fromCharCode(55296|r>>10,56320|1023&r)};try{M.apply(H=O.call(w.childNodes),w.childNodes),H[w.childNodes.length].nodeType}catch(ot){M={apply:H.length?function(e,t){_.apply(e,O.call(t))}:function(e,t){var n=e.length,r=0;while(e[n++]=t[r++]);e.length=n-1}}}function at(e,t,n,i){var o,a,s,l,u,c,d,m,y,x;if((t?t.ownerDocument||t:w)!==f&&p(t),t=t||f,n=n||[],!e||"string"!=typeof e)return n;if(1!==(l=t.nodeType)&&9!==l)return[];if(h&&!i){if(o=Z.exec(e))if(s=o[1]){if(9===l){if(a=t.getElementById(s),!a||!a.parentNode)return n;if(a.id===s)return n.push(a),n}else if(t.ownerDocument&&(a=t.ownerDocument.getElementById(s))&&v(t,a)&&a.id===s)return n.push(a),n}else{if(o[2])return M.apply(n,t.getElementsByTagName(e)),n;if((s=o[3])&&r.getElementsByClassName&&t.getElementsByClassName)return M.apply(n,t.getElementsByClassName(s)),n}if(r.qsa&&(!g||!g.test(e))){if(m=d=b,y=t,x=9===l&&e,1===l&&"object"!==t.nodeName.toLowerCase()){c=bt(e),(d=t.getAttribute("id"))?m=d.replace(nt,"\\$&"):t.setAttribute("id",m),m="[id='"+m+"'] ",u=c.length;while(u--)c[u]=m+xt(c[u]);y=V.test(e)&&t.parentNode||t,x=c.join(",")}if(x)try{return M.apply(n,y.querySelectorAll(x)),n}catch(T){}finally{d||t.removeAttribute("id")}}}return At(e.replace(z,"$1"),t,n,i)}function st(e){return K.test(e+"")}function lt(){var e=[];function t(n,r){return e.push(n+=" ")>o.cacheLength&&delete t[e.shift()],t[n]=r}return t}function ut(e){return e[b]=!0,e}function ct(e){var t=f.createElement("div");try{return!!e(t)}catch(n){return!1}finally{t.parentNode&&t.parentNode.removeChild(t),t=null}}function pt(e,t,n){e=e.split("|");var r,i=e.length,a=n?null:t;while(i--)(r=o.attrHandle[e[i]])&&r!==t||(o.attrHandle[e[i]]=a)}function ft(e,t){var n=e.getAttributeNode(t);return n&&n.specified?n.value:e[t]===!0?t.toLowerCase():null}function dt(e,t){return e.getAttribute(t,"type"===t.toLowerCase()?1:2)}function ht(e){return"input"===e.nodeName.toLowerCase()?e.defaultValue:t}function gt(e,t){var n=t&&e,r=n&&1===e.nodeType&&1===t.nodeType&&(~t.sourceIndex||D)-(~e.sourceIndex||D);if(r)return r;if(n)while(n=n.nextSibling)if(n===t)return-1;return e?1:-1}function mt(e){return function(t){var n=t.nodeName.toLowerCase();return"input"===n&&t.type===e}}function yt(e){return function(t){var n=t.nodeName.toLowerCase();return("input"===n||"button"===n)&&t.type===e}}function vt(e){return ut(function(t){return t=+t,ut(function(n,r){var i,o=e([],n.length,t),a=o.length;while(a--)n[i=o[a]]&&(n[i]=!(r[i]=n[i]))})})}s=at.isXML=function(e){var t=e&&(e.ownerDocument||e).documentElement;return t?"HTML"!==t.nodeName:!1},r=at.support={},p=at.setDocument=function(e){var n=e?e.ownerDocument||e:w,i=n.parentWindow;return n!==f&&9===n.nodeType&&n.documentElement?(f=n,d=n.documentElement,h=!s(n),i&&i.frameElement&&i.attachEvent("onbeforeunload",function(){p()}),r.attributes=ct(function(e){return e.innerHTML="<a href='#'></a>",pt("type|href|height|width",dt,"#"===e.firstChild.getAttribute("href")),pt(B,ft,null==e.getAttribute("disabled")),e.className="i",!e.getAttribute("className")}),r.input=ct(function(e){return e.innerHTML="<input>",e.firstChild.setAttribute("value",""),""===e.firstChild.getAttribute("value")}),pt("value",ht,r.attributes&&r.input),r.getElementsByTagName=ct(function(e){return e.appendChild(n.createComment("")),!e.getElementsByTagName("*").length}),r.getElementsByClassName=ct(function(e){return e.innerHTML="<div class='a'></div><div class='a i'></div>",e.firstChild.className="i",2===e.getElementsByClassName("i").length}),r.getById=ct(function(e){return d.appendChild(e).id=b,!n.getElementsByName||!n.getElementsByName(b).length}),r.getById?(o.find.ID=function(e,t){if(typeof t.getElementById!==j&&h){var n=t.getElementById(e);return n&&n.parentNode?[n]:[]}},o.filter.ID=function(e){var t=e.replace(rt,it);return function(e){return e.getAttribute("id")===t}}):(delete o.find.ID,o.filter.ID=function(e){var t=e.replace(rt,it);return function(e){var n=typeof e.getAttributeNode!==j&&e.getAttributeNode("id");return n&&n.value===t}}),o.find.TAG=r.getElementsByTagName?function(e,n){return typeof n.getElementsByTagName!==j?n.getElementsByTagName(e):t}:function(e,t){var n,r=[],i=0,o=t.getElementsByTagName(e);if("*"===e){while(n=o[i++])1===n.nodeType&&r.push(n);return r}return o},o.find.CLASS=r.getElementsByClassName&&function(e,n){return typeof n.getElementsByClassName!==j&&h?n.getElementsByClassName(e):t},m=[],g=[],(r.qsa=st(n.querySelectorAll))&&(ct(function(e){e.innerHTML="<select><option selected=''></option></select>",e.querySelectorAll("[selected]").length||g.push("\\["+P+"*(?:value|"+B+")"),e.querySelectorAll(":checked").length||g.push(":checked")}),ct(function(e){var t=n.createElement("input");t.setAttribute("type","hidden"),e.appendChild(t).setAttribute("t",""),e.querySelectorAll("[t^='']").length&&g.push("[*^$]="+P+"*(?:''|\"\")"),e.querySelectorAll(":enabled").length||g.push(":enabled",":disabled"),e.querySelectorAll("*,:x"),g.push(",.*:")})),(r.matchesSelector=st(y=d.webkitMatchesSelector||d.mozMatchesSelector||d.oMatchesSelector||d.msMatchesSelector))&&ct(function(e){r.disconnectedMatch=y.call(e,"div"),y.call(e,"[s!='']:x"),m.push("!=",I)}),g=g.length&&RegExp(g.join("|")),m=m.length&&RegExp(m.join("|")),v=st(d.contains)||d.compareDocumentPosition?function(e,t){var n=9===e.nodeType?e.documentElement:e,r=t&&t.parentNode;return e===r||!(!r||1!==r.nodeType||!(n.contains?n.contains(r):e.compareDocumentPosition&&16&e.compareDocumentPosition(r)))}:function(e,t){if(t)while(t=t.parentNode)if(t===e)return!0;return!1},r.sortDetached=ct(function(e){return 1&e.compareDocumentPosition(n.createElement("div"))}),A=d.compareDocumentPosition?function(e,t){if(e===t)return S=!0,0;var i=t.compareDocumentPosition&&e.compareDocumentPosition&&e.compareDocumentPosition(t);return i?1&i||!r.sortDetached&&t.compareDocumentPosition(e)===i?e===n||v(w,e)?-1:t===n||v(w,t)?1:c?F.call(c,e)-F.call(c,t):0:4&i?-1:1:e.compareDocumentPosition?-1:1}:function(e,t){var r,i=0,o=e.parentNode,a=t.parentNode,s=[e],l=[t];if(e===t)return S=!0,0;if(!o||!a)return e===n?-1:t===n?1:o?-1:a?1:c?F.call(c,e)-F.call(c,t):0;if(o===a)return gt(e,t);r=e;while(r=r.parentNode)s.unshift(r);r=t;while(r=r.parentNode)l.unshift(r);while(s[i]===l[i])i++;return i?gt(s[i],l[i]):s[i]===w?-1:l[i]===w?1:0},n):f},at.matches=function(e,t){return at(e,null,null,t)},at.matchesSelector=function(e,t){if((e.ownerDocument||e)!==f&&p(e),t=t.replace(Y,"='$1']"),!(!r.matchesSelector||!h||m&&m.test(t)||g&&g.test(t)))try{var n=y.call(e,t);if(n||r.disconnectedMatch||e.document&&11!==e.document.nodeType)return n}catch(i){}return at(t,f,null,[e]).length>0},at.contains=function(e,t){return(e.ownerDocument||e)!==f&&p(e),v(e,t)},at.attr=function(e,n){(e.ownerDocument||e)!==f&&p(e);var i=o.attrHandle[n.toLowerCase()],a=i&&L.call(o.attrHandle,n.toLowerCase())?i(e,n,!h):t;return a===t?r.attributes||!h?e.getAttribute(n):(a=e.getAttributeNode(n))&&a.specified?a.value:null:a},at.error=function(e){throw Error("Syntax error, unrecognized expression: "+e)},at.uniqueSort=function(e){var t,n=[],i=0,o=0;if(S=!r.detectDuplicates,c=!r.sortStable&&e.slice(0),e.sort(A),S){while(t=e[o++])t===e[o]&&(i=n.push(o));while(i--)e.splice(n[i],1)}return e},a=at.getText=function(e){var t,n="",r=0,i=e.nodeType;if(i){if(1===i||9===i||11===i){if("string"==typeof e.textContent)return e.textContent;for(e=e.firstChild;e;e=e.nextSibling)n+=a(e)}else if(3===i||4===i)return e.nodeValue}else for(;t=e[r];r++)n+=a(t);return n},o=at.selectors={cacheLength:50,createPseudo:ut,match:Q,attrHandle:{},find:{},relative:{">":{dir:"parentNode",first:!0}," ":{dir:"parentNode"},"+":{dir:"previousSibling",first:!0},"~":{dir:"previousSibling"}},preFilter:{ATTR:function(e){return e[1]=e[1].replace(rt,it),e[3]=(e[4]||e[5]||"").replace(rt,it),"~="===e[2]&&(e[3]=" "+e[3]+" "),e.slice(0,4)},CHILD:function(e){return e[1]=e[1].toLowerCase(),"nth"===e[1].slice(0,3)?(e[3]||at.error(e[0]),e[4]=+(e[4]?e[5]+(e[6]||1):2*("even"===e[3]||"odd"===e[3])),e[5]=+(e[7]+e[8]||"odd"===e[3])):e[3]&&at.error(e[0]),e},PSEUDO:function(e){var n,r=!e[5]&&e[2];return Q.CHILD.test(e[0])?null:(e[3]&&e[4]!==t?e[2]=e[4]:r&&J.test(r)&&(n=bt(r,!0))&&(n=r.indexOf(")",r.length-n)-r.length)&&(e[0]=e[0].slice(0,n),e[2]=r.slice(0,n)),e.slice(0,3))}},filter:{TAG:function(e){var t=e.replace(rt,it).toLowerCase();return"*"===e?function(){return!0}:function(e){return e.nodeName&&e.nodeName.toLowerCase()===t}},CLASS:function(e){var t=N[e+" "];return t||(t=RegExp("(^|"+P+")"+e+"("+P+"|$)"))&&N(e,function(e){return t.test("string"==typeof e.className&&e.className||typeof e.getAttribute!==j&&e.getAttribute("class")||"")})},ATTR:function(e,t,n){return function(r){var i=at.attr(r,e);return null==i?"!="===t:t?(i+="","="===t?i===n:"!="===t?i!==n:"^="===t?n&&0===i.indexOf(n):"*="===t?n&&i.indexOf(n)>-1:"$="===t?n&&i.slice(-n.length)===n:"~="===t?(" "+i+" ").indexOf(n)>-1:"|="===t?i===n||i.slice(0,n.length+1)===n+"-":!1):!0}},CHILD:function(e,t,n,r,i){var o="nth"!==e.slice(0,3),a="last"!==e.slice(-4),s="of-type"===t;return 1===r&&0===i?function(e){return!!e.parentNode}:function(t,n,l){var u,c,p,f,d,h,g=o!==a?"nextSibling":"previousSibling",m=t.parentNode,y=s&&t.nodeName.toLowerCase(),v=!l&&!s;if(m){if(o){while(g){p=t;while(p=p[g])if(s?p.nodeName.toLowerCase()===y:1===p.nodeType)return!1;h=g="only"===e&&!h&&"nextSibling"}return!0}if(h=[a?m.firstChild:m.lastChild],a&&v){c=m[b]||(m[b]={}),u=c[e]||[],d=u[0]===T&&u[1],f=u[0]===T&&u[2],p=d&&m.childNodes[d];while(p=++d&&p&&p[g]||(f=d=0)||h.pop())if(1===p.nodeType&&++f&&p===t){c[e]=[T,d,f];break}}else if(v&&(u=(t[b]||(t[b]={}))[e])&&u[0]===T)f=u[1];else while(p=++d&&p&&p[g]||(f=d=0)||h.pop())if((s?p.nodeName.toLowerCase()===y:1===p.nodeType)&&++f&&(v&&((p[b]||(p[b]={}))[e]=[T,f]),p===t))break;return f-=i,f===r||0===f%r&&f/r>=0}}},PSEUDO:function(e,t){var n,r=o.pseudos[e]||o.setFilters[e.toLowerCase()]||at.error("unsupported pseudo: "+e);return r[b]?r(t):r.length>1?(n=[e,e,"",t],o.setFilters.hasOwnProperty(e.toLowerCase())?ut(function(e,n){var i,o=r(e,t),a=o.length;while(a--)i=F.call(e,o[a]),e[i]=!(n[i]=o[a])}):function(e){return r(e,0,n)}):r}},pseudos:{not:ut(function(e){var t=[],n=[],r=l(e.replace(z,"$1"));return r[b]?ut(function(e,t,n,i){var o,a=r(e,null,i,[]),s=e.length;while(s--)(o=a[s])&&(e[s]=!(t[s]=o))}):function(e,i,o){return t[0]=e,r(t,null,o,n),!n.pop()}}),has:ut(function(e){return function(t){return at(e,t).length>0}}),contains:ut(function(e){return function(t){return(t.textContent||t.innerText||a(t)).indexOf(e)>-1}}),lang:ut(function(e){return G.test(e||"")||at.error("unsupported lang: "+e),e=e.replace(rt,it).toLowerCase(),function(t){var n;do if(n=h?t.lang:t.getAttribute("xml:lang")||t.getAttribute("lang"))return n=n.toLowerCase(),n===e||0===n.indexOf(e+"-");while((t=t.parentNode)&&1===t.nodeType);return!1}}),target:function(t){var n=e.location&&e.location.hash;return n&&n.slice(1)===t.id},root:function(e){return e===d},focus:function(e){return e===f.activeElement&&(!f.hasFocus||f.hasFocus())&&!!(e.type||e.href||~e.tabIndex)},enabled:function(e){return e.disabled===!1},disabled:function(e){return e.disabled===!0},checked:function(e){var t=e.nodeName.toLowerCase();return"input"===t&&!!e.checked||"option"===t&&!!e.selected},selected:function(e){return e.parentNode&&e.parentNode.selectedIndex,e.selected===!0},empty:function(e){for(e=e.firstChild;e;e=e.nextSibling)if(e.nodeName>"@"||3===e.nodeType||4===e.nodeType)return!1;return!0},parent:function(e){return!o.pseudos.empty(e)},header:function(e){return tt.test(e.nodeName)},input:function(e){return et.test(e.nodeName)},button:function(e){var t=e.nodeName.toLowerCase();return"input"===t&&"button"===e.type||"button"===t},text:function(e){var t;return"input"===e.nodeName.toLowerCase()&&"text"===e.type&&(null==(t=e.getAttribute("type"))||t.toLowerCase()===e.type)},first:vt(function(){return[0]}),last:vt(function(e,t){return[t-1]}),eq:vt(function(e,t,n){return[0>n?n+t:n]}),even:vt(function(e,t){var n=0;for(;t>n;n+=2)e.push(n);return e}),odd:vt(function(e,t){var n=1;for(;t>n;n+=2)e.push(n);return e}),lt:vt(function(e,t,n){var r=0>n?n+t:n;for(;--r>=0;)e.push(r);return e}),gt:vt(function(e,t,n){var r=0>n?n+t:n;for(;t>++r;)e.push(r);return e})}};for(n in{radio:!0,checkbox:!0,file:!0,password:!0,image:!0})o.pseudos[n]=mt(n);for(n in{submit:!0,reset:!0})o.pseudos[n]=yt(n);function bt(e,t){var n,r,i,a,s,l,u,c=k[e+" "];if(c)return t?0:c.slice(0);s=e,l=[],u=o.preFilter;while(s){(!n||(r=X.exec(s)))&&(r&&(s=s.slice(r[0].length)||s),l.push(i=[])),n=!1,(r=U.exec(s))&&(n=r.shift(),i.push({value:n,type:r[0].replace(z," ")}),s=s.slice(n.length));for(a in o.filter)!(r=Q[a].exec(s))||u[a]&&!(r=u[a](r))||(n=r.shift(),i.push({value:n,type:a,matches:r}),s=s.slice(n.length));if(!n)break}return t?s.length:s?at.error(e):k(e,l).slice(0)}function xt(e){var t=0,n=e.length,r="";for(;n>t;t++)r+=e[t].value;return r}function wt(e,t,n){var r=t.dir,o=n&&"parentNode"===r,a=C++;return t.first?function(t,n,i){while(t=t[r])if(1===t.nodeType||o)return e(t,n,i)}:function(t,n,s){var l,u,c,p=T+" "+a;if(s){while(t=t[r])if((1===t.nodeType||o)&&e(t,n,s))return!0}else while(t=t[r])if(1===t.nodeType||o)if(c=t[b]||(t[b]={}),(u=c[r])&&u[0]===p){if((l=u[1])===!0||l===i)return l===!0}else if(u=c[r]=[p],u[1]=e(t,n,s)||i,u[1]===!0)return!0}}function Tt(e){return e.length>1?function(t,n,r){var i=e.length;while(i--)if(!e[i](t,n,r))return!1;return!0}:e[0]}function Ct(e,t,n,r,i){var o,a=[],s=0,l=e.length,u=null!=t;for(;l>s;s++)(o=e[s])&&(!n||n(o,r,i))&&(a.push(o),u&&t.push(s));return a}function Nt(e,t,n,r,i,o){return r&&!r[b]&&(r=Nt(r)),i&&!i[b]&&(i=Nt(i,o)),ut(function(o,a,s,l){var u,c,p,f=[],d=[],h=a.length,g=o||St(t||"*",s.nodeType?[s]:s,[]),m=!e||!o&&t?g:Ct(g,f,e,s,l),y=n?i||(o?e:h||r)?[]:a:m;if(n&&n(m,y,s,l),r){u=Ct(y,d),r(u,[],s,l),c=u.length;while(c--)(p=u[c])&&(y[d[c]]=!(m[d[c]]=p))}if(o){if(i||e){if(i){u=[],c=y.length;while(c--)(p=y[c])&&u.push(m[c]=p);i(null,y=[],u,l)}c=y.length;while(c--)(p=y[c])&&(u=i?F.call(o,p):f[c])>-1&&(o[u]=!(a[u]=p))}}else y=Ct(y===a?y.splice(h,y.length):y),i?i(null,a,y,l):M.apply(a,y)})}function kt(e){var t,n,r,i=e.length,a=o.relative[e[0].type],s=a||o.relative[" "],l=a?1:0,c=wt(function(e){return e===t},s,!0),p=wt(function(e){return F.call(t,e)>-1},s,!0),f=[function(e,n,r){return!a&&(r||n!==u)||((t=n).nodeType?c(e,n,r):p(e,n,r))}];for(;i>l;l++)if(n=o.relative[e[l].type])f=[wt(Tt(f),n)];else{if(n=o.filter[e[l].type].apply(null,e[l].matches),n[b]){for(r=++l;i>r;r++)if(o.relative[e[r].type])break;return Nt(l>1&&Tt(f),l>1&&xt(e.slice(0,l-1).concat({value:" "===e[l-2].type?"*":""})).replace(z,"$1"),n,r>l&&kt(e.slice(l,r)),i>r&&kt(e=e.slice(r)),i>r&&xt(e))}f.push(n)}return Tt(f)}function Et(e,t){var n=0,r=t.length>0,a=e.length>0,s=function(s,l,c,p,d){var h,g,m,y=[],v=0,b="0",x=s&&[],w=null!=d,C=u,N=s||a&&o.find.TAG("*",d&&l.parentNode||l),k=T+=null==C?1:Math.random()||.1;for(w&&(u=l!==f&&l,i=n);null!=(h=N[b]);b++){if(a&&h){g=0;while(m=e[g++])if(m(h,l,c)){p.push(h);break}w&&(T=k,i=++n)}r&&((h=!m&&h)&&v--,s&&x.push(h))}if(v+=b,r&&b!==v){g=0;while(m=t[g++])m(x,y,l,c);if(s){if(v>0)while(b--)x[b]||y[b]||(y[b]=q.call(p));y=Ct(y)}M.apply(p,y),w&&!s&&y.length>0&&v+t.length>1&&at.uniqueSort(p)}return w&&(T=k,u=C),x};return r?ut(s):s}l=at.compile=function(e,t){var n,r=[],i=[],o=E[e+" "];if(!o){t||(t=bt(e)),n=t.length;while(n--)o=kt(t[n]),o[b]?r.push(o):i.push(o);o=E(e,Et(i,r))}return o};function St(e,t,n){var r=0,i=t.length;for(;i>r;r++)at(e,t[r],n);return n}function At(e,t,n,i){var a,s,u,c,p,f=bt(e);if(!i&&1===f.length){if(s=f[0]=f[0].slice(0),s.length>2&&"ID"===(u=s[0]).type&&r.getById&&9===t.nodeType&&h&&o.relative[s[1].type]){if(t=(o.find.ID(u.matches[0].replace(rt,it),t)||[])[0],!t)return n;e=e.slice(s.shift().value.length)}a=Q.needsContext.test(e)?0:s.length;while(a--){if(u=s[a],o.relative[c=u.type])break;if((p=o.find[c])&&(i=p(u.matches[0].replace(rt,it),V.test(s[0].type)&&t.parentNode||t))){if(s.splice(a,1),e=i.length&&xt(s),!e)return M.apply(n,i),n;break}}}return l(e,f)(i,t,!h,n,V.test(e)),n}o.pseudos.nth=o.pseudos.eq;function jt(){}jt.prototype=o.filters=o.pseudos,o.setFilters=new jt,r.sortStable=b.split("").sort(A).join("")===b,p(),[0,0].sort(A),r.detectDuplicates=S,x.find=at,x.expr=at.selectors,x.expr[":"]=x.expr.pseudos,x.unique=at.uniqueSort,x.text=at.getText,x.isXMLDoc=at.isXML,x.contains=at.contains}(e);var O={};function F(e){var t=O[e]={};return x.each(e.match(T)||[],function(e,n){t[n]=!0}),t}x.Callbacks=function(e){e="string"==typeof e?O[e]||F(e):x.extend({},e);var n,r,i,o,a,s,l=[],u=!e.once&&[],c=function(t){for(r=e.memory&&t,i=!0,a=s||0,s=0,o=l.length,n=!0;l&&o>a;a++)if(l[a].apply(t[0],t[1])===!1&&e.stopOnFalse){r=!1;break}n=!1,l&&(u?u.length&&c(u.shift()):r?l=[]:p.disable())},p={add:function(){if(l){var t=l.length;(function i(t){x.each(t,function(t,n){var r=x.type(n);"function"===r?e.unique&&p.has(n)||l.push(n):n&&n.length&&"string"!==r&&i(n)})})(arguments),n?o=l.length:r&&(s=t,c(r))}return this},remove:function(){return l&&x.each(arguments,function(e,t){var r;while((r=x.inArray(t,l,r))>-1)l.splice(r,1),n&&(o>=r&&o--,a>=r&&a--)}),this},has:function(e){return e?x.inArray(e,l)>-1:!(!l||!l.length)},empty:function(){return l=[],o=0,this},disable:function(){return l=u=r=t,this},disabled:function(){return!l},lock:function(){return u=t,r||p.disable(),this},locked:function(){return!u},fireWith:function(e,t){return t=t||[],t=[e,t.slice?t.slice():t],!l||i&&!u||(n?u.push(t):c(t)),this},fire:function(){return p.fireWith(this,arguments),this},fired:function(){return!!i}};return p},x.extend({Deferred:function(e){var t=[["resolve","done",x.Callbacks("once memory"),"resolved"],["reject","fail",x.Callbacks("once memory"),"rejected"],["notify","progress",x.Callbacks("memory")]],n="pending",r={state:function(){return n},always:function(){return i.done(arguments).fail(arguments),this},then:function(){var e=arguments;return x.Deferred(function(n){x.each(t,function(t,o){var a=o[0],s=x.isFunction(e[t])&&e[t];i[o[1]](function(){var e=s&&s.apply(this,arguments);e&&x.isFunction(e.promise)?e.promise().done(n.resolve).fail(n.reject).progress(n.notify):n[a+"With"](this===r?n.promise():this,s?[e]:arguments)})}),e=null}).promise()},promise:function(e){return null!=e?x.extend(e,r):r}},i={};return r.pipe=r.then,x.each(t,function(e,o){var a=o[2],s=o[3];r[o[1]]=a.add,s&&a.add(function(){n=s},t[1^e][2].disable,t[2][2].lock),i[o[0]]=function(){return i[o[0]+"With"](this===i?r:this,arguments),this},i[o[0]+"With"]=a.fireWith}),r.promise(i),e&&e.call(i,i),i},when:function(e){var t=0,n=g.call(arguments),r=n.length,i=1!==r||e&&x.isFunction(e.promise)?r:0,o=1===i?e:x.Deferred(),a=function(e,t,n){return function(r){t[e]=this,n[e]=arguments.length>1?g.call(arguments):r,n===s?o.notifyWith(t,n):--i||o.resolveWith(t,n)}},s,l,u;if(r>1)for(s=Array(r),l=Array(r),u=Array(r);r>t;t++)n[t]&&x.isFunction(n[t].promise)?n[t].promise().done(a(t,u,n)).fail(o.reject).progress(a(t,l,s)):--i;return i||o.resolveWith(u,n),o.promise()}}),x.support=function(t){var n,r,o,s,l,u,c,p,f,d=a.createElement("div");if(d.setAttribute("className","t"),d.innerHTML=" <link/><table></table><a href='/a'>a</a><input type='checkbox'/>",n=d.getElementsByTagName("*")||[],r=d.getElementsByTagName("a")[0],!r||!r.style||!n.length)return t;s=a.createElement("select"),u=s.appendChild(a.createElement("option")),o=d.getElementsByTagName("input")[0],r.style.cssText="top:1px;float:left;opacity:.5",t.getSetAttribute="t"!==d.className,t.leadingWhitespace=3===d.firstChild.nodeType,t.tbody=!d.getElementsByTagName("tbody").length,t.htmlSerialize=!!d.getElementsByTagName("link").length,t.style=/top/.test(r.getAttribute("style")),t.hrefNormalized="/a"===r.getAttribute("href"),t.opacity=/^0.5/.test(r.style.opacity),t.cssFloat=!!r.style.cssFloat,t.checkOn=!!o.value,t.optSelected=u.selected,t.enctype=!!a.createElement("form").enctype,t.html5Clone="<:nav></:nav>"!==a.createElement("nav").cloneNode(!0).outerHTML,t.inlineBlockNeedsLayout=!1,t.shrinkWrapBlocks=!1,t.pixelPosition=!1,t.deleteExpando=!0,t.noCloneEvent=!0,t.reliableMarginRight=!0,t.boxSizingReliable=!0,o.checked=!0,t.noCloneChecked=o.cloneNode(!0).checked,s.disabled=!0,t.optDisabled=!u.disabled;try{delete d.test}catch(h){t.deleteExpando=!1}o=a.createElement("input"),o.setAttribute("value",""),t.input=""===o.getAttribute("value"),o.value="t",o.setAttribute("type","radio"),t.radioValue="t"===o.value,o.setAttribute("checked","t"),o.setAttribute("name","t"),l=a.createDocumentFragment(),l.appendChild(o),t.appendChecked=o.checked,t.checkClone=l.cloneNode(!0).cloneNode(!0).lastChild.checked,d.attachEvent&&(d.attachEvent("onclick",function(){t.noCloneEvent=!1}),d.cloneNode(!0).click());for(f in{submit:!0,change:!0,focusin:!0})d.setAttribute(c="on"+f,"t"),t[f+"Bubbles"]=c in e||d.attributes[c].expando===!1;d.style.backgroundClip="content-box",d.cloneNode(!0).style.backgroundClip="",t.clearCloneStyle="content-box"===d.style.backgroundClip;for(f in x(t))break;return t.ownLast="0"!==f,x(function(){var n,r,o,s="padding:0;margin:0;border:0;display:block;box-sizing:content-box;-moz-box-sizing:content-box;-webkit-box-sizing:content-box;",l=a.getElementsByTagName("body")[0];l&&(n=a.createElement("div"),n.style.cssText="border:0;width:0;height:0;position:absolute;top:0;left:-9999px;margin-top:1px",l.appendChild(n).appendChild(d),d.innerHTML="<table><tr><td></td><td>t</td></tr></table>",o=d.getElementsByTagName("td"),o[0].style.cssText="padding:0;margin:0;border:0;display:none",p=0===o[0].offsetHeight,o[0].style.display="",o[1].style.display="none",t.reliableHiddenOffsets=p&&0===o[0].offsetHeight,d.innerHTML="",d.style.cssText="box-sizing:border-box;-moz-box-sizing:border-box;-webkit-box-sizing:border-box;padding:1px;border:1px;display:block;width:4px;margin-top:1%;position:absolute;top:1%;",x.swap(l,null!=l.style.zoom?{zoom:1}:{},function(){t.boxSizing=4===d.offsetWidth}),e.getComputedStyle&&(t.pixelPosition="1%"!==(e.getComputedStyle(d,null)||{}).top,t.boxSizingReliable="4px"===(e.getComputedStyle(d,null)||{width:"4px"}).width,r=d.appendChild(a.createElement("div")),r.style.cssText=d.style.cssText=s,r.style.marginRight=r.style.width="0",d.style.width="1px",t.reliableMarginRight=!parseFloat((e.getComputedStyle(r,null)||{}).marginRight)),typeof d.style.zoom!==i&&(d.innerHTML="",d.style.cssText=s+"width:1px;padding:1px;display:inline;zoom:1",t.inlineBlockNeedsLayout=3===d.offsetWidth,d.style.display="block",d.innerHTML="<div></div>",d.firstChild.style.width="5px",t.shrinkWrapBlocks=3!==d.offsetWidth,t.inlineBlockNeedsLayout&&(l.style.zoom=1)),l.removeChild(n),n=d=o=r=null)
}),n=s=l=u=r=o=null,t}({});var B=/(?:\{[\s\S]*\}|\[[\s\S]*\])$/,P=/([A-Z])/g;function R(e,n,r,i){if(x.acceptData(e)){var o,a,s=x.expando,l=e.nodeType,u=l?x.cache:e,c=l?e[s]:e[s]&&s;if(c&&u[c]&&(i||u[c].data)||r!==t||"string"!=typeof n)return c||(c=l?e[s]=p.pop()||x.guid++:s),u[c]||(u[c]=l?{}:{toJSON:x.noop}),("object"==typeof n||"function"==typeof n)&&(i?u[c]=x.extend(u[c],n):u[c].data=x.extend(u[c].data,n)),a=u[c],i||(a.data||(a.data={}),a=a.data),r!==t&&(a[x.camelCase(n)]=r),"string"==typeof n?(o=a[n],null==o&&(o=a[x.camelCase(n)])):o=a,o}}function W(e,t,n){if(x.acceptData(e)){var r,i,o=e.nodeType,a=o?x.cache:e,s=o?e[x.expando]:x.expando;if(a[s]){if(t&&(r=n?a[s]:a[s].data)){x.isArray(t)?t=t.concat(x.map(t,x.camelCase)):t in r?t=[t]:(t=x.camelCase(t),t=t in r?[t]:t.split(" ")),i=t.length;while(i--)delete r[t[i]];if(n?!I(r):!x.isEmptyObject(r))return}(n||(delete a[s].data,I(a[s])))&&(o?x.cleanData([e],!0):x.support.deleteExpando||a!=a.window?delete a[s]:a[s]=null)}}}x.extend({cache:{},noData:{applet:!0,embed:!0,object:"clsid:D27CDB6E-AE6D-11cf-96B8-444553540000"},hasData:function(e){return e=e.nodeType?x.cache[e[x.expando]]:e[x.expando],!!e&&!I(e)},data:function(e,t,n){return R(e,t,n)},removeData:function(e,t){return W(e,t)},_data:function(e,t,n){return R(e,t,n,!0)},_removeData:function(e,t){return W(e,t,!0)},acceptData:function(e){if(e.nodeType&&1!==e.nodeType&&9!==e.nodeType)return!1;var t=e.nodeName&&x.noData[e.nodeName.toLowerCase()];return!t||t!==!0&&e.getAttribute("classid")===t}}),x.fn.extend({data:function(e,n){var r,i,o=null,a=0,s=this[0];if(e===t){if(this.length&&(o=x.data(s),1===s.nodeType&&!x._data(s,"parsedAttrs"))){for(r=s.attributes;r.length>a;a++)i=r[a].name,0===i.indexOf("data-")&&(i=x.camelCase(i.slice(5)),$(s,i,o[i]));x._data(s,"parsedAttrs",!0)}return o}return"object"==typeof e?this.each(function(){x.data(this,e)}):arguments.length>1?this.each(function(){x.data(this,e,n)}):s?$(s,e,x.data(s,e)):null},removeData:function(e){return this.each(function(){x.removeData(this,e)})}});function $(e,n,r){if(r===t&&1===e.nodeType){var i="data-"+n.replace(P,"-$1").toLowerCase();if(r=e.getAttribute(i),"string"==typeof r){try{r="true"===r?!0:"false"===r?!1:"null"===r?null:+r+""===r?+r:B.test(r)?x.parseJSON(r):r}catch(o){}x.data(e,n,r)}else r=t}return r}function I(e){var t;for(t in e)if(("data"!==t||!x.isEmptyObject(e[t]))&&"toJSON"!==t)return!1;return!0}x.extend({queue:function(e,n,r){var i;return e?(n=(n||"fx")+"queue",i=x._data(e,n),r&&(!i||x.isArray(r)?i=x._data(e,n,x.makeArray(r)):i.push(r)),i||[]):t},dequeue:function(e,t){t=t||"fx";var n=x.queue(e,t),r=n.length,i=n.shift(),o=x._queueHooks(e,t),a=function(){x.dequeue(e,t)};"inprogress"===i&&(i=n.shift(),r--),i&&("fx"===t&&n.unshift("inprogress"),delete o.stop,i.call(e,a,o)),!r&&o&&o.empty.fire()},_queueHooks:function(e,t){var n=t+"queueHooks";return x._data(e,n)||x._data(e,n,{empty:x.Callbacks("once memory").add(function(){x._removeData(e,t+"queue"),x._removeData(e,n)})})}}),x.fn.extend({queue:function(e,n){var r=2;return"string"!=typeof e&&(n=e,e="fx",r--),r>arguments.length?x.queue(this[0],e):n===t?this:this.each(function(){var t=x.queue(this,e,n);x._queueHooks(this,e),"fx"===e&&"inprogress"!==t[0]&&x.dequeue(this,e)})},dequeue:function(e){return this.each(function(){x.dequeue(this,e)})},delay:function(e,t){return e=x.fx?x.fx.speeds[e]||e:e,t=t||"fx",this.queue(t,function(t,n){var r=setTimeout(t,e);n.stop=function(){clearTimeout(r)}})},clearQueue:function(e){return this.queue(e||"fx",[])},promise:function(e,n){var r,i=1,o=x.Deferred(),a=this,s=this.length,l=function(){--i||o.resolveWith(a,[a])};"string"!=typeof e&&(n=e,e=t),e=e||"fx";while(s--)r=x._data(a[s],e+"queueHooks"),r&&r.empty&&(i++,r.empty.add(l));return l(),o.promise(n)}});var z,X,U=/[\t\r\n\f]/g,V=/\r/g,Y=/^(?:input|select|textarea|button|object)$/i,J=/^(?:a|area)$/i,G=/^(?:checked|selected)$/i,Q=x.support.getSetAttribute,K=x.support.input;x.fn.extend({attr:function(e,t){return x.access(this,x.attr,e,t,arguments.length>1)},removeAttr:function(e){return this.each(function(){x.removeAttr(this,e)})},prop:function(e,t){return x.access(this,x.prop,e,t,arguments.length>1)},removeProp:function(e){return e=x.propFix[e]||e,this.each(function(){try{this[e]=t,delete this[e]}catch(n){}})},addClass:function(e){var t,n,r,i,o,a=0,s=this.length,l="string"==typeof e&&e;if(x.isFunction(e))return this.each(function(t){x(this).addClass(e.call(this,t,this.className))});if(l)for(t=(e||"").match(T)||[];s>a;a++)if(n=this[a],r=1===n.nodeType&&(n.className?(" "+n.className+" ").replace(U," "):" ")){o=0;while(i=t[o++])0>r.indexOf(" "+i+" ")&&(r+=i+" ");n.className=x.trim(r)}return this},removeClass:function(e){var t,n,r,i,o,a=0,s=this.length,l=0===arguments.length||"string"==typeof e&&e;if(x.isFunction(e))return this.each(function(t){x(this).removeClass(e.call(this,t,this.className))});if(l)for(t=(e||"").match(T)||[];s>a;a++)if(n=this[a],r=1===n.nodeType&&(n.className?(" "+n.className+" ").replace(U," "):"")){o=0;while(i=t[o++])while(r.indexOf(" "+i+" ")>=0)r=r.replace(" "+i+" "," ");n.className=e?x.trim(r):""}return this},toggleClass:function(e,t){var n=typeof e,r="boolean"==typeof t;return x.isFunction(e)?this.each(function(n){x(this).toggleClass(e.call(this,n,this.className,t),t)}):this.each(function(){if("string"===n){var o,a=0,s=x(this),l=t,u=e.match(T)||[];while(o=u[a++])l=r?l:!s.hasClass(o),s[l?"addClass":"removeClass"](o)}else(n===i||"boolean"===n)&&(this.className&&x._data(this,"__className__",this.className),this.className=this.className||e===!1?"":x._data(this,"__className__")||"")})},hasClass:function(e){var t=" "+e+" ",n=0,r=this.length;for(;r>n;n++)if(1===this[n].nodeType&&(" "+this[n].className+" ").replace(U," ").indexOf(t)>=0)return!0;return!1},val:function(e){var n,r,i,o=this[0];{if(arguments.length)return i=x.isFunction(e),this.each(function(n){var o;1===this.nodeType&&(o=i?e.call(this,n,x(this).val()):e,null==o?o="":"number"==typeof o?o+="":x.isArray(o)&&(o=x.map(o,function(e){return null==e?"":e+""})),r=x.valHooks[this.type]||x.valHooks[this.nodeName.toLowerCase()],r&&"set"in r&&r.set(this,o,"value")!==t||(this.value=o))});if(o)return r=x.valHooks[o.type]||x.valHooks[o.nodeName.toLowerCase()],r&&"get"in r&&(n=r.get(o,"value"))!==t?n:(n=o.value,"string"==typeof n?n.replace(V,""):null==n?"":n)}}}),x.extend({valHooks:{option:{get:function(e){var t=x.find.attr(e,"value");return null!=t?t:e.text}},select:{get:function(e){var t,n,r=e.options,i=e.selectedIndex,o="select-one"===e.type||0>i,a=o?null:[],s=o?i+1:r.length,l=0>i?s:o?i:0;for(;s>l;l++)if(n=r[l],!(!n.selected&&l!==i||(x.support.optDisabled?n.disabled:null!==n.getAttribute("disabled"))||n.parentNode.disabled&&x.nodeName(n.parentNode,"optgroup"))){if(t=x(n).val(),o)return t;a.push(t)}return a},set:function(e,t){var n,r,i=e.options,o=x.makeArray(t),a=i.length;while(a--)r=i[a],(r.selected=x.inArray(x(r).val(),o)>=0)&&(n=!0);return n||(e.selectedIndex=-1),o}}},attr:function(e,n,r){var o,a,s=e.nodeType;if(e&&3!==s&&8!==s&&2!==s)return typeof e.getAttribute===i?x.prop(e,n,r):(1===s&&x.isXMLDoc(e)||(n=n.toLowerCase(),o=x.attrHooks[n]||(x.expr.match.bool.test(n)?X:z)),r===t?o&&"get"in o&&null!==(a=o.get(e,n))?a:(a=x.find.attr(e,n),null==a?t:a):null!==r?o&&"set"in o&&(a=o.set(e,r,n))!==t?a:(e.setAttribute(n,r+""),r):(x.removeAttr(e,n),t))},removeAttr:function(e,t){var n,r,i=0,o=t&&t.match(T);if(o&&1===e.nodeType)while(n=o[i++])r=x.propFix[n]||n,x.expr.match.bool.test(n)?K&&Q||!G.test(n)?e[r]=!1:e[x.camelCase("default-"+n)]=e[r]=!1:x.attr(e,n,""),e.removeAttribute(Q?n:r)},attrHooks:{type:{set:function(e,t){if(!x.support.radioValue&&"radio"===t&&x.nodeName(e,"input")){var n=e.value;return e.setAttribute("type",t),n&&(e.value=n),t}}}},propFix:{"for":"htmlFor","class":"className"},prop:function(e,n,r){var i,o,a,s=e.nodeType;if(e&&3!==s&&8!==s&&2!==s)return a=1!==s||!x.isXMLDoc(e),a&&(n=x.propFix[n]||n,o=x.propHooks[n]),r!==t?o&&"set"in o&&(i=o.set(e,r,n))!==t?i:e[n]=r:o&&"get"in o&&null!==(i=o.get(e,n))?i:e[n]},propHooks:{tabIndex:{get:function(e){var t=x.find.attr(e,"tabindex");return t?parseInt(t,10):Y.test(e.nodeName)||J.test(e.nodeName)&&e.href?0:-1}}}}),X={set:function(e,t,n){return t===!1?x.removeAttr(e,n):K&&Q||!G.test(n)?e.setAttribute(!Q&&x.propFix[n]||n,n):e[x.camelCase("default-"+n)]=e[n]=!0,n}},x.each(x.expr.match.bool.source.match(/\w+/g),function(e,n){var r=x.expr.attrHandle[n]||x.find.attr;x.expr.attrHandle[n]=K&&Q||!G.test(n)?function(e,n,i){var o=x.expr.attrHandle[n],a=i?t:(x.expr.attrHandle[n]=t)!=r(e,n,i)?n.toLowerCase():null;return x.expr.attrHandle[n]=o,a}:function(e,n,r){return r?t:e[x.camelCase("default-"+n)]?n.toLowerCase():null}}),K&&Q||(x.attrHooks.value={set:function(e,n,r){return x.nodeName(e,"input")?(e.defaultValue=n,t):z&&z.set(e,n,r)}}),Q||(z={set:function(e,n,r){var i=e.getAttributeNode(r);return i||e.setAttributeNode(i=e.ownerDocument.createAttribute(r)),i.value=n+="","value"===r||n===e.getAttribute(r)?n:t}},x.expr.attrHandle.id=x.expr.attrHandle.name=x.expr.attrHandle.coords=function(e,n,r){var i;return r?t:(i=e.getAttributeNode(n))&&""!==i.value?i.value:null},x.valHooks.button={get:function(e,n){var r=e.getAttributeNode(n);return r&&r.specified?r.value:t},set:z.set},x.attrHooks.contenteditable={set:function(e,t,n){z.set(e,""===t?!1:t,n)}},x.each(["width","height"],function(e,n){x.attrHooks[n]={set:function(e,r){return""===r?(e.setAttribute(n,"auto"),r):t}}})),x.support.hrefNormalized||x.each(["href","src"],function(e,t){x.propHooks[t]={get:function(e){return e.getAttribute(t,4)}}}),x.support.style||(x.attrHooks.style={get:function(e){return e.style.cssText||t},set:function(e,t){return e.style.cssText=t+""}}),x.support.optSelected||(x.propHooks.selected={get:function(e){var t=e.parentNode;return t&&(t.selectedIndex,t.parentNode&&t.parentNode.selectedIndex),null}}),x.each(["tabIndex","readOnly","maxLength","cellSpacing","cellPadding","rowSpan","colSpan","useMap","frameBorder","contentEditable"],function(){x.propFix[this.toLowerCase()]=this}),x.support.enctype||(x.propFix.enctype="encoding"),x.each(["radio","checkbox"],function(){x.valHooks[this]={set:function(e,n){return x.isArray(n)?e.checked=x.inArray(x(e).val(),n)>=0:t}},x.support.checkOn||(x.valHooks[this].get=function(e){return null===e.getAttribute("value")?"on":e.value})});var Z=/^(?:input|select|textarea)$/i,et=/^key/,tt=/^(?:mouse|contextmenu)|click/,nt=/^(?:focusinfocus|focusoutblur)$/,rt=/^([^.]*)(?:\.(.+)|)$/;function it(){return!0}function ot(){return!1}function at(){try{return a.activeElement}catch(e){}}x.event={global:{},add:function(e,n,r,o,a){var s,l,u,c,p,f,d,h,g,m,y,v=x._data(e);if(v){r.handler&&(c=r,r=c.handler,a=c.selector),r.guid||(r.guid=x.guid++),(l=v.events)||(l=v.events={}),(f=v.handle)||(f=v.handle=function(e){return typeof x===i||e&&x.event.triggered===e.type?t:x.event.dispatch.apply(f.elem,arguments)},f.elem=e),n=(n||"").match(T)||[""],u=n.length;while(u--)s=rt.exec(n[u])||[],g=y=s[1],m=(s[2]||"").split(".").sort(),g&&(p=x.event.special[g]||{},g=(a?p.delegateType:p.bindType)||g,p=x.event.special[g]||{},d=x.extend({type:g,origType:y,data:o,handler:r,guid:r.guid,selector:a,needsContext:a&&x.expr.match.needsContext.test(a),namespace:m.join(".")},c),(h=l[g])||(h=l[g]=[],h.delegateCount=0,p.setup&&p.setup.call(e,o,m,f)!==!1||(e.addEventListener?e.addEventListener(g,f,!1):e.attachEvent&&e.attachEvent("on"+g,f))),p.add&&(p.add.call(e,d),d.handler.guid||(d.handler.guid=r.guid)),a?h.splice(h.delegateCount++,0,d):h.push(d),x.event.global[g]=!0);e=null}},remove:function(e,t,n,r,i){var o,a,s,l,u,c,p,f,d,h,g,m=x.hasData(e)&&x._data(e);if(m&&(c=m.events)){t=(t||"").match(T)||[""],u=t.length;while(u--)if(s=rt.exec(t[u])||[],d=g=s[1],h=(s[2]||"").split(".").sort(),d){p=x.event.special[d]||{},d=(r?p.delegateType:p.bindType)||d,f=c[d]||[],s=s[2]&&RegExp("(^|\\.)"+h.join("\\.(?:.*\\.|)")+"(\\.|$)"),l=o=f.length;while(o--)a=f[o],!i&&g!==a.origType||n&&n.guid!==a.guid||s&&!s.test(a.namespace)||r&&r!==a.selector&&("**"!==r||!a.selector)||(f.splice(o,1),a.selector&&f.delegateCount--,p.remove&&p.remove.call(e,a));l&&!f.length&&(p.teardown&&p.teardown.call(e,h,m.handle)!==!1||x.removeEvent(e,d,m.handle),delete c[d])}else for(d in c)x.event.remove(e,d+t[u],n,r,!0);x.isEmptyObject(c)&&(delete m.handle,x._removeData(e,"events"))}},trigger:function(n,r,i,o){var s,l,u,c,p,f,d,h=[i||a],g=v.call(n,"type")?n.type:n,m=v.call(n,"namespace")?n.namespace.split("."):[];if(u=f=i=i||a,3!==i.nodeType&&8!==i.nodeType&&!nt.test(g+x.event.triggered)&&(g.indexOf(".")>=0&&(m=g.split("."),g=m.shift(),m.sort()),l=0>g.indexOf(":")&&"on"+g,n=n[x.expando]?n:new x.Event(g,"object"==typeof n&&n),n.isTrigger=o?2:3,n.namespace=m.join("."),n.namespace_re=n.namespace?RegExp("(^|\\.)"+m.join("\\.(?:.*\\.|)")+"(\\.|$)"):null,n.result=t,n.target||(n.target=i),r=null==r?[n]:x.makeArray(r,[n]),p=x.event.special[g]||{},o||!p.trigger||p.trigger.apply(i,r)!==!1)){if(!o&&!p.noBubble&&!x.isWindow(i)){for(c=p.delegateType||g,nt.test(c+g)||(u=u.parentNode);u;u=u.parentNode)h.push(u),f=u;f===(i.ownerDocument||a)&&h.push(f.defaultView||f.parentWindow||e)}d=0;while((u=h[d++])&&!n.isPropagationStopped())n.type=d>1?c:p.bindType||g,s=(x._data(u,"events")||{})[n.type]&&x._data(u,"handle"),s&&s.apply(u,r),s=l&&u[l],s&&x.acceptData(u)&&s.apply&&s.apply(u,r)===!1&&n.preventDefault();if(n.type=g,!o&&!n.isDefaultPrevented()&&(!p._default||p._default.apply(h.pop(),r)===!1)&&x.acceptData(i)&&l&&i[g]&&!x.isWindow(i)){f=i[l],f&&(i[l]=null),x.event.triggered=g;try{i[g]()}catch(y){}x.event.triggered=t,f&&(i[l]=f)}return n.result}},dispatch:function(e){e=x.event.fix(e);var n,r,i,o,a,s=[],l=g.call(arguments),u=(x._data(this,"events")||{})[e.type]||[],c=x.event.special[e.type]||{};if(l[0]=e,e.delegateTarget=this,!c.preDispatch||c.preDispatch.call(this,e)!==!1){s=x.event.handlers.call(this,e,u),n=0;while((o=s[n++])&&!e.isPropagationStopped()){e.currentTarget=o.elem,a=0;while((i=o.handlers[a++])&&!e.isImmediatePropagationStopped())(!e.namespace_re||e.namespace_re.test(i.namespace))&&(e.handleObj=i,e.data=i.data,r=((x.event.special[i.origType]||{}).handle||i.handler).apply(o.elem,l),r!==t&&(e.result=r)===!1&&(e.preventDefault(),e.stopPropagation()))}return c.postDispatch&&c.postDispatch.call(this,e),e.result}},handlers:function(e,n){var r,i,o,a,s=[],l=n.delegateCount,u=e.target;if(l&&u.nodeType&&(!e.button||"click"!==e.type))for(;u!=this;u=u.parentNode||this)if(1===u.nodeType&&(u.disabled!==!0||"click"!==e.type)){for(o=[],a=0;l>a;a++)i=n[a],r=i.selector+" ",o[r]===t&&(o[r]=i.needsContext?x(r,this).index(u)>=0:x.find(r,this,null,[u]).length),o[r]&&o.push(i);o.length&&s.push({elem:u,handlers:o})}return n.length>l&&s.push({elem:this,handlers:n.slice(l)}),s},fix:function(e){if(e[x.expando])return e;var t,n,r,i=e.type,o=e,s=this.fixHooks[i];s||(this.fixHooks[i]=s=tt.test(i)?this.mouseHooks:et.test(i)?this.keyHooks:{}),r=s.props?this.props.concat(s.props):this.props,e=new x.Event(o),t=r.length;while(t--)n=r[t],e[n]=o[n];return e.target||(e.target=o.srcElement||a),3===e.target.nodeType&&(e.target=e.target.parentNode),e.metaKey=!!e.metaKey,s.filter?s.filter(e,o):e},props:"altKey bubbles cancelable ctrlKey currentTarget eventPhase metaKey relatedTarget shiftKey target timeStamp view which".split(" "),fixHooks:{},keyHooks:{props:"char charCode key keyCode".split(" "),filter:function(e,t){return null==e.which&&(e.which=null!=t.charCode?t.charCode:t.keyCode),e}},mouseHooks:{props:"button buttons clientX clientY fromElement offsetX offsetY pageX pageY screenX screenY toElement".split(" "),filter:function(e,n){var r,i,o,s=n.button,l=n.fromElement;return null==e.pageX&&null!=n.clientX&&(i=e.target.ownerDocument||a,o=i.documentElement,r=i.body,e.pageX=n.clientX+(o&&o.scrollLeft||r&&r.scrollLeft||0)-(o&&o.clientLeft||r&&r.clientLeft||0),e.pageY=n.clientY+(o&&o.scrollTop||r&&r.scrollTop||0)-(o&&o.clientTop||r&&r.clientTop||0)),!e.relatedTarget&&l&&(e.relatedTarget=l===e.target?n.toElement:l),e.which||s===t||(e.which=1&s?1:2&s?3:4&s?2:0),e}},special:{load:{noBubble:!0},focus:{trigger:function(){if(this!==at()&&this.focus)try{return this.focus(),!1}catch(e){}},delegateType:"focusin"},blur:{trigger:function(){return this===at()&&this.blur?(this.blur(),!1):t},delegateType:"focusout"},click:{trigger:function(){return x.nodeName(this,"input")&&"checkbox"===this.type&&this.click?(this.click(),!1):t},_default:function(e){return x.nodeName(e.target,"a")}},beforeunload:{postDispatch:function(e){e.result!==t&&(e.originalEvent.returnValue=e.result)}}},simulate:function(e,t,n,r){var i=x.extend(new x.Event,n,{type:e,isSimulated:!0,originalEvent:{}});r?x.event.trigger(i,null,t):x.event.dispatch.call(t,i),i.isDefaultPrevented()&&n.preventDefault()}},x.removeEvent=a.removeEventListener?function(e,t,n){e.removeEventListener&&e.removeEventListener(t,n,!1)}:function(e,t,n){var r="on"+t;e.detachEvent&&(typeof e[r]===i&&(e[r]=null),e.detachEvent(r,n))},x.Event=function(e,n){return this instanceof x.Event?(e&&e.type?(this.originalEvent=e,this.type=e.type,this.isDefaultPrevented=e.defaultPrevented||e.returnValue===!1||e.getPreventDefault&&e.getPreventDefault()?it:ot):this.type=e,n&&x.extend(this,n),this.timeStamp=e&&e.timeStamp||x.now(),this[x.expando]=!0,t):new x.Event(e,n)},x.Event.prototype={isDefaultPrevented:ot,isPropagationStopped:ot,isImmediatePropagationStopped:ot,preventDefault:function(){var e=this.originalEvent;this.isDefaultPrevented=it,e&&(e.preventDefault?e.preventDefault():e.returnValue=!1)},stopPropagation:function(){var e=this.originalEvent;this.isPropagationStopped=it,e&&(e.stopPropagation&&e.stopPropagation(),e.cancelBubble=!0)},stopImmediatePropagation:function(){this.isImmediatePropagationStopped=it,this.stopPropagation()}},x.each({mouseenter:"mouseover",mouseleave:"mouseout"},function(e,t){x.event.special[e]={delegateType:t,bindType:t,handle:function(e){var n,r=this,i=e.relatedTarget,o=e.handleObj;return(!i||i!==r&&!x.contains(r,i))&&(e.type=o.origType,n=o.handler.apply(this,arguments),e.type=t),n}}}),x.support.submitBubbles||(x.event.special.submit={setup:function(){return x.nodeName(this,"form")?!1:(x.event.add(this,"click._submit keypress._submit",function(e){var n=e.target,r=x.nodeName(n,"input")||x.nodeName(n,"button")?n.form:t;r&&!x._data(r,"submitBubbles")&&(x.event.add(r,"submit._submit",function(e){e._submit_bubble=!0}),x._data(r,"submitBubbles",!0))}),t)},postDispatch:function(e){e._submit_bubble&&(delete e._submit_bubble,this.parentNode&&!e.isTrigger&&x.event.simulate("submit",this.parentNode,e,!0))},teardown:function(){return x.nodeName(this,"form")?!1:(x.event.remove(this,"._submit"),t)}}),x.support.changeBubbles||(x.event.special.change={setup:function(){return Z.test(this.nodeName)?(("checkbox"===this.type||"radio"===this.type)&&(x.event.add(this,"propertychange._change",function(e){"checked"===e.originalEvent.propertyName&&(this._just_changed=!0)}),x.event.add(this,"click._change",function(e){this._just_changed&&!e.isTrigger&&(this._just_changed=!1),x.event.simulate("change",this,e,!0)})),!1):(x.event.add(this,"beforeactivate._change",function(e){var t=e.target;Z.test(t.nodeName)&&!x._data(t,"changeBubbles")&&(x.event.add(t,"change._change",function(e){!this.parentNode||e.isSimulated||e.isTrigger||x.event.simulate("change",this.parentNode,e,!0)}),x._data(t,"changeBubbles",!0))}),t)},handle:function(e){var n=e.target;return this!==n||e.isSimulated||e.isTrigger||"radio"!==n.type&&"checkbox"!==n.type?e.handleObj.handler.apply(this,arguments):t},teardown:function(){return x.event.remove(this,"._change"),!Z.test(this.nodeName)}}),x.support.focusinBubbles||x.each({focus:"focusin",blur:"focusout"},function(e,t){var n=0,r=function(e){x.event.simulate(t,e.target,x.event.fix(e),!0)};x.event.special[t]={setup:function(){0===n++&&a.addEventListener(e,r,!0)},teardown:function(){0===--n&&a.removeEventListener(e,r,!0)}}}),x.fn.extend({on:function(e,n,r,i,o){var a,s;if("object"==typeof e){"string"!=typeof n&&(r=r||n,n=t);for(a in e)this.on(a,n,r,e[a],o);return this}if(null==r&&null==i?(i=n,r=n=t):null==i&&("string"==typeof n?(i=r,r=t):(i=r,r=n,n=t)),i===!1)i=ot;else if(!i)return this;return 1===o&&(s=i,i=function(e){return x().off(e),s.apply(this,arguments)},i.guid=s.guid||(s.guid=x.guid++)),this.each(function(){x.event.add(this,e,i,r,n)})},one:function(e,t,n,r){return this.on(e,t,n,r,1)},off:function(e,n,r){var i,o;if(e&&e.preventDefault&&e.handleObj)return i=e.handleObj,x(e.delegateTarget).off(i.namespace?i.origType+"."+i.namespace:i.origType,i.selector,i.handler),this;if("object"==typeof e){for(o in e)this.off(o,n,e[o]);return this}return(n===!1||"function"==typeof n)&&(r=n,n=t),r===!1&&(r=ot),this.each(function(){x.event.remove(this,e,r,n)})},trigger:function(e,t){return this.each(function(){x.event.trigger(e,t,this)})},triggerHandler:function(e,n){var r=this[0];return r?x.event.trigger(e,n,r,!0):t}});var st=/^.[^:#\[\.,]*$/,lt=/^(?:parents|prev(?:Until|All))/,ut=x.expr.match.needsContext,ct={children:!0,contents:!0,next:!0,prev:!0};x.fn.extend({find:function(e){var t,n=[],r=this,i=r.length;if("string"!=typeof e)return this.pushStack(x(e).filter(function(){for(t=0;i>t;t++)if(x.contains(r[t],this))return!0}));for(t=0;i>t;t++)x.find(e,r[t],n);return n=this.pushStack(i>1?x.unique(n):n),n.selector=this.selector?this.selector+" "+e:e,n},has:function(e){var t,n=x(e,this),r=n.length;return this.filter(function(){for(t=0;r>t;t++)if(x.contains(this,n[t]))return!0})},not:function(e){return this.pushStack(ft(this,e||[],!0))},filter:function(e){return this.pushStack(ft(this,e||[],!1))},is:function(e){return!!ft(this,"string"==typeof e&&ut.test(e)?x(e):e||[],!1).length},closest:function(e,t){var n,r=0,i=this.length,o=[],a=ut.test(e)||"string"!=typeof e?x(e,t||this.context):0;for(;i>r;r++)for(n=this[r];n&&n!==t;n=n.parentNode)if(11>n.nodeType&&(a?a.index(n)>-1:1===n.nodeType&&x.find.matchesSelector(n,e))){n=o.push(n);break}return this.pushStack(o.length>1?x.unique(o):o)},index:function(e){return e?"string"==typeof e?x.inArray(this[0],x(e)):x.inArray(e.jquery?e[0]:e,this):this[0]&&this[0].parentNode?this.first().prevAll().length:-1},add:function(e,t){var n="string"==typeof e?x(e,t):x.makeArray(e&&e.nodeType?[e]:e),r=x.merge(this.get(),n);return this.pushStack(x.unique(r))},addBack:function(e){return this.add(null==e?this.prevObject:this.prevObject.filter(e))}});function pt(e,t){do e=e[t];while(e&&1!==e.nodeType);return e}x.each({parent:function(e){var t=e.parentNode;return t&&11!==t.nodeType?t:null},parents:function(e){return x.dir(e,"parentNode")},parentsUntil:function(e,t,n){return x.dir(e,"parentNode",n)},next:function(e){return pt(e,"nextSibling")},prev:function(e){return pt(e,"previousSibling")},nextAll:function(e){return x.dir(e,"nextSibling")},prevAll:function(e){return x.dir(e,"previousSibling")},nextUntil:function(e,t,n){return x.dir(e,"nextSibling",n)},prevUntil:function(e,t,n){return x.dir(e,"previousSibling",n)},siblings:function(e){return x.sibling((e.parentNode||{}).firstChild,e)},children:function(e){return x.sibling(e.firstChild)},contents:function(e){return x.nodeName(e,"iframe")?e.contentDocument||e.contentWindow.document:x.merge([],e.childNodes)}},function(e,t){x.fn[e]=function(n,r){var i=x.map(this,t,n);return"Until"!==e.slice(-5)&&(r=n),r&&"string"==typeof r&&(i=x.filter(r,i)),this.length>1&&(ct[e]||(i=x.unique(i)),lt.test(e)&&(i=i.reverse())),this.pushStack(i)}}),x.extend({filter:function(e,t,n){var r=t[0];return n&&(e=":not("+e+")"),1===t.length&&1===r.nodeType?x.find.matchesSelector(r,e)?[r]:[]:x.find.matches(e,x.grep(t,function(e){return 1===e.nodeType}))},dir:function(e,n,r){var i=[],o=e[n];while(o&&9!==o.nodeType&&(r===t||1!==o.nodeType||!x(o).is(r)))1===o.nodeType&&i.push(o),o=o[n];return i},sibling:function(e,t){var n=[];for(;e;e=e.nextSibling)1===e.nodeType&&e!==t&&n.push(e);return n}});function ft(e,t,n){if(x.isFunction(t))return x.grep(e,function(e,r){return!!t.call(e,r,e)!==n});if(t.nodeType)return x.grep(e,function(e){return e===t!==n});if("string"==typeof t){if(st.test(t))return x.filter(t,e,n);t=x.filter(t,e)}return x.grep(e,function(e){return x.inArray(e,t)>=0!==n})}function dt(e){var t=ht.split("|"),n=e.createDocumentFragment();if(n.createElement)while(t.length)n.createElement(t.pop());return n}var ht="abbr|article|aside|audio|bdi|canvas|data|datalist|details|figcaption|figure|footer|header|hgroup|mark|meter|nav|output|progress|section|summary|time|video",gt=/ jQuery\d+="(?:null|\d+)"/g,mt=RegExp("<(?:"+ht+")[\\s/>]","i"),yt=/^\s+/,vt=/<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\w:]+)[^>]*)\/>/gi,bt=/<([\w:]+)/,xt=/<tbody/i,wt=/<|&#?\w+;/,Tt=/<(?:script|style|link)/i,Ct=/^(?:checkbox|radio)$/i,Nt=/checked\s*(?:[^=]|=\s*.checked.)/i,kt=/^$|\/(?:java|ecma)script/i,Et=/^true\/(.*)/,St=/^\s*<!(?:\[CDATA\[|--)|(?:\]\]|--)>\s*$/g,At={option:[1,"<select multiple='multiple'>","</select>"],legend:[1,"<fieldset>","</fieldset>"],area:[1,"<map>","</map>"],param:[1,"<object>","</object>"],thead:[1,"<table>","</table>"],tr:[2,"<table><tbody>","</tbody></table>"],col:[2,"<table><tbody></tbody><colgroup>","</colgroup></table>"],td:[3,"<table><tbody><tr>","</tr></tbody></table>"],_default:x.support.htmlSerialize?[0,"",""]:[1,"X<div>","</div>"]},jt=dt(a),Dt=jt.appendChild(a.createElement("div"));At.optgroup=At.option,At.tbody=At.tfoot=At.colgroup=At.caption=At.thead,At.th=At.td,x.fn.extend({text:function(e){return x.access(this,function(e){return e===t?x.text(this):this.empty().append((this[0]&&this[0].ownerDocument||a).createTextNode(e))},null,e,arguments.length)},append:function(){return this.domManip(arguments,function(e){if(1===this.nodeType||11===this.nodeType||9===this.nodeType){var t=Lt(this,e);t.appendChild(e)}})},prepend:function(){return this.domManip(arguments,function(e){if(1===this.nodeType||11===this.nodeType||9===this.nodeType){var t=Lt(this,e);t.insertBefore(e,t.firstChild)}})},before:function(){return this.domManip(arguments,function(e){this.parentNode&&this.parentNode.insertBefore(e,this)})},after:function(){return this.domManip(arguments,function(e){this.parentNode&&this.parentNode.insertBefore(e,this.nextSibling)})},remove:function(e,t){var n,r=e?x.filter(e,this):this,i=0;for(;null!=(n=r[i]);i++)t||1!==n.nodeType||x.cleanData(Ft(n)),n.parentNode&&(t&&x.contains(n.ownerDocument,n)&&_t(Ft(n,"script")),n.parentNode.removeChild(n));return this},empty:function(){var e,t=0;for(;null!=(e=this[t]);t++){1===e.nodeType&&x.cleanData(Ft(e,!1));while(e.firstChild)e.removeChild(e.firstChild);e.options&&x.nodeName(e,"select")&&(e.options.length=0)}return this},clone:function(e,t){return e=null==e?!1:e,t=null==t?e:t,this.map(function(){return x.clone(this,e,t)})},html:function(e){return x.access(this,function(e){var n=this[0]||{},r=0,i=this.length;if(e===t)return 1===n.nodeType?n.innerHTML.replace(gt,""):t;if(!("string"!=typeof e||Tt.test(e)||!x.support.htmlSerialize&&mt.test(e)||!x.support.leadingWhitespace&&yt.test(e)||At[(bt.exec(e)||["",""])[1].toLowerCase()])){e=e.replace(vt,"<$1></$2>");try{for(;i>r;r++)n=this[r]||{},1===n.nodeType&&(x.cleanData(Ft(n,!1)),n.innerHTML=e);n=0}catch(o){}}n&&this.empty().append(e)},null,e,arguments.length)},replaceWith:function(){var e=x.map(this,function(e){return[e.nextSibling,e.parentNode]}),t=0;return this.domManip(arguments,function(n){var r=e[t++],i=e[t++];i&&(r&&r.parentNode!==i&&(r=this.nextSibling),x(this).remove(),i.insertBefore(n,r))},!0),t?this:this.remove()},detach:function(e){return this.remove(e,!0)},domManip:function(e,t,n){e=d.apply([],e);var r,i,o,a,s,l,u=0,c=this.length,p=this,f=c-1,h=e[0],g=x.isFunction(h);if(g||!(1>=c||"string"!=typeof h||x.support.checkClone)&&Nt.test(h))return this.each(function(r){var i=p.eq(r);g&&(e[0]=h.call(this,r,i.html())),i.domManip(e,t,n)});if(c&&(l=x.buildFragment(e,this[0].ownerDocument,!1,!n&&this),r=l.firstChild,1===l.childNodes.length&&(l=r),r)){for(a=x.map(Ft(l,"script"),Ht),o=a.length;c>u;u++)i=l,u!==f&&(i=x.clone(i,!0,!0),o&&x.merge(a,Ft(i,"script"))),t.call(this[u],i,u);if(o)for(s=a[a.length-1].ownerDocument,x.map(a,qt),u=0;o>u;u++)i=a[u],kt.test(i.type||"")&&!x._data(i,"globalEval")&&x.contains(s,i)&&(i.src?x._evalUrl(i.src):x.globalEval((i.text||i.textContent||i.innerHTML||"").replace(St,"")));l=r=null}return this}});function Lt(e,t){return x.nodeName(e,"table")&&x.nodeName(1===t.nodeType?t:t.firstChild,"tr")?e.getElementsByTagName("tbody")[0]||e.appendChild(e.ownerDocument.createElement("tbody")):e}function Ht(e){return e.type=(null!==x.find.attr(e,"type"))+"/"+e.type,e}function qt(e){var t=Et.exec(e.type);return t?e.type=t[1]:e.removeAttribute("type"),e}function _t(e,t){var n,r=0;for(;null!=(n=e[r]);r++)x._data(n,"globalEval",!t||x._data(t[r],"globalEval"))}function Mt(e,t){if(1===t.nodeType&&x.hasData(e)){var n,r,i,o=x._data(e),a=x._data(t,o),s=o.events;if(s){delete a.handle,a.events={};for(n in s)for(r=0,i=s[n].length;i>r;r++)x.event.add(t,n,s[n][r])}a.data&&(a.data=x.extend({},a.data))}}function Ot(e,t){var n,r,i;if(1===t.nodeType){if(n=t.nodeName.toLowerCase(),!x.support.noCloneEvent&&t[x.expando]){i=x._data(t);for(r in i.events)x.removeEvent(t,r,i.handle);t.removeAttribute(x.expando)}"script"===n&&t.text!==e.text?(Ht(t).text=e.text,qt(t)):"object"===n?(t.parentNode&&(t.outerHTML=e.outerHTML),x.support.html5Clone&&e.innerHTML&&!x.trim(t.innerHTML)&&(t.innerHTML=e.innerHTML)):"input"===n&&Ct.test(e.type)?(t.defaultChecked=t.checked=e.checked,t.value!==e.value&&(t.value=e.value)):"option"===n?t.defaultSelected=t.selected=e.defaultSelected:("input"===n||"textarea"===n)&&(t.defaultValue=e.defaultValue)}}x.each({appendTo:"append",prependTo:"prepend",insertBefore:"before",insertAfter:"after",replaceAll:"replaceWith"},function(e,t){x.fn[e]=function(e){var n,r=0,i=[],o=x(e),a=o.length-1;for(;a>=r;r++)n=r===a?this:this.clone(!0),x(o[r])[t](n),h.apply(i,n.get());return this.pushStack(i)}});function Ft(e,n){var r,o,a=0,s=typeof e.getElementsByTagName!==i?e.getElementsByTagName(n||"*"):typeof e.querySelectorAll!==i?e.querySelectorAll(n||"*"):t;if(!s)for(s=[],r=e.childNodes||e;null!=(o=r[a]);a++)!n||x.nodeName(o,n)?s.push(o):x.merge(s,Ft(o,n));return n===t||n&&x.nodeName(e,n)?x.merge([e],s):s}function Bt(e){Ct.test(e.type)&&(e.defaultChecked=e.checked)}x.extend({clone:function(e,t,n){var r,i,o,a,s,l=x.contains(e.ownerDocument,e);if(x.support.html5Clone||x.isXMLDoc(e)||!mt.test("<"+e.nodeName+">")?o=e.cloneNode(!0):(Dt.innerHTML=e.outerHTML,Dt.removeChild(o=Dt.firstChild)),!(x.support.noCloneEvent&&x.support.noCloneChecked||1!==e.nodeType&&11!==e.nodeType||x.isXMLDoc(e)))for(r=Ft(o),s=Ft(e),a=0;null!=(i=s[a]);++a)r[a]&&Ot(i,r[a]);if(t)if(n)for(s=s||Ft(e),r=r||Ft(o),a=0;null!=(i=s[a]);a++)Mt(i,r[a]);else Mt(e,o);return r=Ft(o,"script"),r.length>0&&_t(r,!l&&Ft(e,"script")),r=s=i=null,o},buildFragment:function(e,t,n,r){var i,o,a,s,l,u,c,p=e.length,f=dt(t),d=[],h=0;for(;p>h;h++)if(o=e[h],o||0===o)if("object"===x.type(o))x.merge(d,o.nodeType?[o]:o);else if(wt.test(o)){s=s||f.appendChild(t.createElement("div")),l=(bt.exec(o)||["",""])[1].toLowerCase(),c=At[l]||At._default,s.innerHTML=c[1]+o.replace(vt,"<$1></$2>")+c[2],i=c[0];while(i--)s=s.lastChild;if(!x.support.leadingWhitespace&&yt.test(o)&&d.push(t.createTextNode(yt.exec(o)[0])),!x.support.tbody){o="table"!==l||xt.test(o)?"<table>"!==c[1]||xt.test(o)?0:s:s.firstChild,i=o&&o.childNodes.length;while(i--)x.nodeName(u=o.childNodes[i],"tbody")&&!u.childNodes.length&&o.removeChild(u)}x.merge(d,s.childNodes),s.textContent="";while(s.firstChild)s.removeChild(s.firstChild);s=f.lastChild}else d.push(t.createTextNode(o));s&&f.removeChild(s),x.support.appendChecked||x.grep(Ft(d,"input"),Bt),h=0;while(o=d[h++])if((!r||-1===x.inArray(o,r))&&(a=x.contains(o.ownerDocument,o),s=Ft(f.appendChild(o),"script"),a&&_t(s),n)){i=0;while(o=s[i++])kt.test(o.type||"")&&n.push(o)}return s=null,f},cleanData:function(e,t){var n,r,o,a,s=0,l=x.expando,u=x.cache,c=x.support.deleteExpando,f=x.event.special;for(;null!=(n=e[s]);s++)if((t||x.acceptData(n))&&(o=n[l],a=o&&u[o])){if(a.events)for(r in a.events)f[r]?x.event.remove(n,r):x.removeEvent(n,r,a.handle);
u[o]&&(delete u[o],c?delete n[l]:typeof n.removeAttribute!==i?n.removeAttribute(l):n[l]=null,p.push(o))}},_evalUrl:function(e){return x.ajax({url:e,type:"GET",dataType:"script",async:!1,global:!1,"throws":!0})}}),x.fn.extend({wrapAll:function(e){if(x.isFunction(e))return this.each(function(t){x(this).wrapAll(e.call(this,t))});if(this[0]){var t=x(e,this[0].ownerDocument).eq(0).clone(!0);this[0].parentNode&&t.insertBefore(this[0]),t.map(function(){var e=this;while(e.firstChild&&1===e.firstChild.nodeType)e=e.firstChild;return e}).append(this)}return this},wrapInner:function(e){return x.isFunction(e)?this.each(function(t){x(this).wrapInner(e.call(this,t))}):this.each(function(){var t=x(this),n=t.contents();n.length?n.wrapAll(e):t.append(e)})},wrap:function(e){var t=x.isFunction(e);return this.each(function(n){x(this).wrapAll(t?e.call(this,n):e)})},unwrap:function(){return this.parent().each(function(){x.nodeName(this,"body")||x(this).replaceWith(this.childNodes)}).end()}});var Pt,Rt,Wt,$t=/alpha\([^)]*\)/i,It=/opacity\s*=\s*([^)]*)/,zt=/^(top|right|bottom|left)$/,Xt=/^(none|table(?!-c[ea]).+)/,Ut=/^margin/,Vt=RegExp("^("+w+")(.*)$","i"),Yt=RegExp("^("+w+")(?!px)[a-z%]+$","i"),Jt=RegExp("^([+-])=("+w+")","i"),Gt={BODY:"block"},Qt={position:"absolute",visibility:"hidden",display:"block"},Kt={letterSpacing:0,fontWeight:400},Zt=["Top","Right","Bottom","Left"],en=["Webkit","O","Moz","ms"];function tn(e,t){if(t in e)return t;var n=t.charAt(0).toUpperCase()+t.slice(1),r=t,i=en.length;while(i--)if(t=en[i]+n,t in e)return t;return r}function nn(e,t){return e=t||e,"none"===x.css(e,"display")||!x.contains(e.ownerDocument,e)}function rn(e,t){var n,r,i,o=[],a=0,s=e.length;for(;s>a;a++)r=e[a],r.style&&(o[a]=x._data(r,"olddisplay"),n=r.style.display,t?(o[a]||"none"!==n||(r.style.display=""),""===r.style.display&&nn(r)&&(o[a]=x._data(r,"olddisplay",ln(r.nodeName)))):o[a]||(i=nn(r),(n&&"none"!==n||!i)&&x._data(r,"olddisplay",i?n:x.css(r,"display"))));for(a=0;s>a;a++)r=e[a],r.style&&(t&&"none"!==r.style.display&&""!==r.style.display||(r.style.display=t?o[a]||"":"none"));return e}x.fn.extend({css:function(e,n){return x.access(this,function(e,n,r){var i,o,a={},s=0;if(x.isArray(n)){for(o=Rt(e),i=n.length;i>s;s++)a[n[s]]=x.css(e,n[s],!1,o);return a}return r!==t?x.style(e,n,r):x.css(e,n)},e,n,arguments.length>1)},show:function(){return rn(this,!0)},hide:function(){return rn(this)},toggle:function(e){var t="boolean"==typeof e;return this.each(function(){(t?e:nn(this))?x(this).show():x(this).hide()})}}),x.extend({cssHooks:{opacity:{get:function(e,t){if(t){var n=Wt(e,"opacity");return""===n?"1":n}}}},cssNumber:{columnCount:!0,fillOpacity:!0,fontWeight:!0,lineHeight:!0,opacity:!0,orphans:!0,widows:!0,zIndex:!0,zoom:!0},cssProps:{"float":x.support.cssFloat?"cssFloat":"styleFloat"},style:function(e,n,r,i){if(e&&3!==e.nodeType&&8!==e.nodeType&&e.style){var o,a,s,l=x.camelCase(n),u=e.style;if(n=x.cssProps[l]||(x.cssProps[l]=tn(u,l)),s=x.cssHooks[n]||x.cssHooks[l],r===t)return s&&"get"in s&&(o=s.get(e,!1,i))!==t?o:u[n];if(a=typeof r,"string"===a&&(o=Jt.exec(r))&&(r=(o[1]+1)*o[2]+parseFloat(x.css(e,n)),a="number"),!(null==r||"number"===a&&isNaN(r)||("number"!==a||x.cssNumber[l]||(r+="px"),x.support.clearCloneStyle||""!==r||0!==n.indexOf("background")||(u[n]="inherit"),s&&"set"in s&&(r=s.set(e,r,i))===t)))try{u[n]=r}catch(c){}}},css:function(e,n,r,i){var o,a,s,l=x.camelCase(n);return n=x.cssProps[l]||(x.cssProps[l]=tn(e.style,l)),s=x.cssHooks[n]||x.cssHooks[l],s&&"get"in s&&(a=s.get(e,!0,r)),a===t&&(a=Wt(e,n,i)),"normal"===a&&n in Kt&&(a=Kt[n]),""===r||r?(o=parseFloat(a),r===!0||x.isNumeric(o)?o||0:a):a}}),e.getComputedStyle?(Rt=function(t){return e.getComputedStyle(t,null)},Wt=function(e,n,r){var i,o,a,s=r||Rt(e),l=s?s.getPropertyValue(n)||s[n]:t,u=e.style;return s&&(""!==l||x.contains(e.ownerDocument,e)||(l=x.style(e,n)),Yt.test(l)&&Ut.test(n)&&(i=u.width,o=u.minWidth,a=u.maxWidth,u.minWidth=u.maxWidth=u.width=l,l=s.width,u.width=i,u.minWidth=o,u.maxWidth=a)),l}):a.documentElement.currentStyle&&(Rt=function(e){return e.currentStyle},Wt=function(e,n,r){var i,o,a,s=r||Rt(e),l=s?s[n]:t,u=e.style;return null==l&&u&&u[n]&&(l=u[n]),Yt.test(l)&&!zt.test(n)&&(i=u.left,o=e.runtimeStyle,a=o&&o.left,a&&(o.left=e.currentStyle.left),u.left="fontSize"===n?"1em":l,l=u.pixelLeft+"px",u.left=i,a&&(o.left=a)),""===l?"auto":l});function on(e,t,n){var r=Vt.exec(t);return r?Math.max(0,r[1]-(n||0))+(r[2]||"px"):t}function an(e,t,n,r,i){var o=n===(r?"border":"content")?4:"width"===t?1:0,a=0;for(;4>o;o+=2)"margin"===n&&(a+=x.css(e,n+Zt[o],!0,i)),r?("content"===n&&(a-=x.css(e,"padding"+Zt[o],!0,i)),"margin"!==n&&(a-=x.css(e,"border"+Zt[o]+"Width",!0,i))):(a+=x.css(e,"padding"+Zt[o],!0,i),"padding"!==n&&(a+=x.css(e,"border"+Zt[o]+"Width",!0,i)));return a}function sn(e,t,n){var r=!0,i="width"===t?e.offsetWidth:e.offsetHeight,o=Rt(e),a=x.support.boxSizing&&"border-box"===x.css(e,"boxSizing",!1,o);if(0>=i||null==i){if(i=Wt(e,t,o),(0>i||null==i)&&(i=e.style[t]),Yt.test(i))return i;r=a&&(x.support.boxSizingReliable||i===e.style[t]),i=parseFloat(i)||0}return i+an(e,t,n||(a?"border":"content"),r,o)+"px"}function ln(e){var t=a,n=Gt[e];return n||(n=un(e,t),"none"!==n&&n||(Pt=(Pt||x("<iframe frameborder='0' width='0' height='0'/>").css("cssText","display:block !important")).appendTo(t.documentElement),t=(Pt[0].contentWindow||Pt[0].contentDocument).document,t.write("<!doctype html><html><body>"),t.close(),n=un(e,t),Pt.detach()),Gt[e]=n),n}function un(e,t){var n=x(t.createElement(e)).appendTo(t.body),r=x.css(n[0],"display");return n.remove(),r}x.each(["height","width"],function(e,n){x.cssHooks[n]={get:function(e,r,i){return r?0===e.offsetWidth&&Xt.test(x.css(e,"display"))?x.swap(e,Qt,function(){return sn(e,n,i)}):sn(e,n,i):t},set:function(e,t,r){var i=r&&Rt(e);return on(e,t,r?an(e,n,r,x.support.boxSizing&&"border-box"===x.css(e,"boxSizing",!1,i),i):0)}}}),x.support.opacity||(x.cssHooks.opacity={get:function(e,t){return It.test((t&&e.currentStyle?e.currentStyle.filter:e.style.filter)||"")?.01*parseFloat(RegExp.$1)+"":t?"1":""},set:function(e,t){var n=e.style,r=e.currentStyle,i=x.isNumeric(t)?"alpha(opacity="+100*t+")":"",o=r&&r.filter||n.filter||"";n.zoom=1,(t>=1||""===t)&&""===x.trim(o.replace($t,""))&&n.removeAttribute&&(n.removeAttribute("filter"),""===t||r&&!r.filter)||(n.filter=$t.test(o)?o.replace($t,i):o+" "+i)}}),x(function(){x.support.reliableMarginRight||(x.cssHooks.marginRight={get:function(e,n){return n?x.swap(e,{display:"inline-block"},Wt,[e,"marginRight"]):t}}),!x.support.pixelPosition&&x.fn.position&&x.each(["top","left"],function(e,n){x.cssHooks[n]={get:function(e,r){return r?(r=Wt(e,n),Yt.test(r)?x(e).position()[n]+"px":r):t}}})}),x.expr&&x.expr.filters&&(x.expr.filters.hidden=function(e){return 0>=e.offsetWidth&&0>=e.offsetHeight||!x.support.reliableHiddenOffsets&&"none"===(e.style&&e.style.display||x.css(e,"display"))},x.expr.filters.visible=function(e){return!x.expr.filters.hidden(e)}),x.each({margin:"",padding:"",border:"Width"},function(e,t){x.cssHooks[e+t]={expand:function(n){var r=0,i={},o="string"==typeof n?n.split(" "):[n];for(;4>r;r++)i[e+Zt[r]+t]=o[r]||o[r-2]||o[0];return i}},Ut.test(e)||(x.cssHooks[e+t].set=on)});var cn=/%20/g,pn=/\[\]$/,fn=/\r?\n/g,dn=/^(?:submit|button|image|reset|file)$/i,hn=/^(?:input|select|textarea|keygen)/i;x.fn.extend({serialize:function(){return x.param(this.serializeArray())},serializeArray:function(){return this.map(function(){var e=x.prop(this,"elements");return e?x.makeArray(e):this}).filter(function(){var e=this.type;return this.name&&!x(this).is(":disabled")&&hn.test(this.nodeName)&&!dn.test(e)&&(this.checked||!Ct.test(e))}).map(function(e,t){var n=x(this).val();return null==n?null:x.isArray(n)?x.map(n,function(e){return{name:t.name,value:e.replace(fn,"\r\n")}}):{name:t.name,value:n.replace(fn,"\r\n")}}).get()}}),x.param=function(e,n){var r,i=[],o=function(e,t){t=x.isFunction(t)?t():null==t?"":t,i[i.length]=encodeURIComponent(e)+"="+encodeURIComponent(t)};if(n===t&&(n=x.ajaxSettings&&x.ajaxSettings.traditional),x.isArray(e)||e.jquery&&!x.isPlainObject(e))x.each(e,function(){o(this.name,this.value)});else for(r in e)gn(r,e[r],n,o);return i.join("&").replace(cn,"+")};function gn(e,t,n,r){var i;if(x.isArray(t))x.each(t,function(t,i){n||pn.test(e)?r(e,i):gn(e+"["+("object"==typeof i?t:"")+"]",i,n,r)});else if(n||"object"!==x.type(t))r(e,t);else for(i in t)gn(e+"["+i+"]",t[i],n,r)}x.each("blur focus focusin focusout load resize scroll unload click dblclick mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave change select submit keydown keypress keyup error contextmenu".split(" "),function(e,t){x.fn[t]=function(e,n){return arguments.length>0?this.on(t,null,e,n):this.trigger(t)}}),x.fn.extend({hover:function(e,t){return this.mouseenter(e).mouseleave(t||e)},bind:function(e,t,n){return this.on(e,null,t,n)},unbind:function(e,t){return this.off(e,null,t)},delegate:function(e,t,n,r){return this.on(t,e,n,r)},undelegate:function(e,t,n){return 1===arguments.length?this.off(e,"**"):this.off(t,e||"**",n)}});var mn,yn,vn=x.now(),bn=/\?/,xn=/#.*$/,wn=/([?&])_=[^&]*/,Tn=/^(.*?):[ \t]*([^\r\n]*)\r?$/gm,Cn=/^(?:about|app|app-storage|.+-extension|file|res|widget):$/,Nn=/^(?:GET|HEAD)$/,kn=/^\/\//,En=/^([\w.+-]+:)(?:\/\/([^\/?#:]*)(?::(\d+)|)|)/,Sn=x.fn.load,An={},jn={},Dn="*/".concat("*");try{yn=o.href}catch(Ln){yn=a.createElement("a"),yn.href="",yn=yn.href}mn=En.exec(yn.toLowerCase())||[];function Hn(e){return function(t,n){"string"!=typeof t&&(n=t,t="*");var r,i=0,o=t.toLowerCase().match(T)||[];if(x.isFunction(n))while(r=o[i++])"+"===r[0]?(r=r.slice(1)||"*",(e[r]=e[r]||[]).unshift(n)):(e[r]=e[r]||[]).push(n)}}function qn(e,n,r,i){var o={},a=e===jn;function s(l){var u;return o[l]=!0,x.each(e[l]||[],function(e,l){var c=l(n,r,i);return"string"!=typeof c||a||o[c]?a?!(u=c):t:(n.dataTypes.unshift(c),s(c),!1)}),u}return s(n.dataTypes[0])||!o["*"]&&s("*")}function _n(e,n){var r,i,o=x.ajaxSettings.flatOptions||{};for(i in n)n[i]!==t&&((o[i]?e:r||(r={}))[i]=n[i]);return r&&x.extend(!0,e,r),e}x.fn.load=function(e,n,r){if("string"!=typeof e&&Sn)return Sn.apply(this,arguments);var i,o,a,s=this,l=e.indexOf(" ");return l>=0&&(i=e.slice(l,e.length),e=e.slice(0,l)),x.isFunction(n)?(r=n,n=t):n&&"object"==typeof n&&(a="POST"),s.length>0&&x.ajax({url:e,type:a,dataType:"html",data:n}).done(function(e){o=arguments,s.html(i?x("<div>").append(x.parseHTML(e)).find(i):e)}).complete(r&&function(e,t){s.each(r,o||[e.responseText,t,e])}),this},x.each(["ajaxStart","ajaxStop","ajaxComplete","ajaxError","ajaxSuccess","ajaxSend"],function(e,t){x.fn[t]=function(e){return this.on(t,e)}}),x.extend({active:0,lastModified:{},etag:{},ajaxSettings:{url:yn,type:"GET",isLocal:Cn.test(mn[1]),global:!0,processData:!0,async:!0,contentType:"application/x-www-form-urlencoded; charset=UTF-8",accepts:{"*":Dn,text:"text/plain",html:"text/html",xml:"application/xml, text/xml",json:"application/json, text/javascript"},contents:{xml:/xml/,html:/html/,json:/json/},responseFields:{xml:"responseXML",text:"responseText",json:"responseJSON"},converters:{"* text":String,"text html":!0,"text json":x.parseJSON,"text xml":x.parseXML},flatOptions:{url:!0,context:!0}},ajaxSetup:function(e,t){return t?_n(_n(e,x.ajaxSettings),t):_n(x.ajaxSettings,e)},ajaxPrefilter:Hn(An),ajaxTransport:Hn(jn),ajax:function(e,n){"object"==typeof e&&(n=e,e=t),n=n||{};var r,i,o,a,s,l,u,c,p=x.ajaxSetup({},n),f=p.context||p,d=p.context&&(f.nodeType||f.jquery)?x(f):x.event,h=x.Deferred(),g=x.Callbacks("once memory"),m=p.statusCode||{},y={},v={},b=0,w="canceled",C={readyState:0,getResponseHeader:function(e){var t;if(2===b){if(!c){c={};while(t=Tn.exec(a))c[t[1].toLowerCase()]=t[2]}t=c[e.toLowerCase()]}return null==t?null:t},getAllResponseHeaders:function(){return 2===b?a:null},setRequestHeader:function(e,t){var n=e.toLowerCase();return b||(e=v[n]=v[n]||e,y[e]=t),this},overrideMimeType:function(e){return b||(p.mimeType=e),this},statusCode:function(e){var t;if(e)if(2>b)for(t in e)m[t]=[m[t],e[t]];else C.always(e[C.status]);return this},abort:function(e){var t=e||w;return u&&u.abort(t),k(0,t),this}};if(h.promise(C).complete=g.add,C.success=C.done,C.error=C.fail,p.url=((e||p.url||yn)+"").replace(xn,"").replace(kn,mn[1]+"//"),p.type=n.method||n.type||p.method||p.type,p.dataTypes=x.trim(p.dataType||"*").toLowerCase().match(T)||[""],null==p.crossDomain&&(r=En.exec(p.url.toLowerCase()),p.crossDomain=!(!r||r[1]===mn[1]&&r[2]===mn[2]&&(r[3]||("http:"===r[1]?"80":"443"))===(mn[3]||("http:"===mn[1]?"80":"443")))),p.data&&p.processData&&"string"!=typeof p.data&&(p.data=x.param(p.data,p.traditional)),qn(An,p,n,C),2===b)return C;l=p.global,l&&0===x.active++&&x.event.trigger("ajaxStart"),p.type=p.type.toUpperCase(),p.hasContent=!Nn.test(p.type),o=p.url,p.hasContent||(p.data&&(o=p.url+=(bn.test(o)?"&":"?")+p.data,delete p.data),p.cache===!1&&(p.url=wn.test(o)?o.replace(wn,"$1_="+vn++):o+(bn.test(o)?"&":"?")+"_="+vn++)),p.ifModified&&(x.lastModified[o]&&C.setRequestHeader("If-Modified-Since",x.lastModified[o]),x.etag[o]&&C.setRequestHeader("If-None-Match",x.etag[o])),(p.data&&p.hasContent&&p.contentType!==!1||n.contentType)&&C.setRequestHeader("Content-Type",p.contentType),C.setRequestHeader("Accept",p.dataTypes[0]&&p.accepts[p.dataTypes[0]]?p.accepts[p.dataTypes[0]]+("*"!==p.dataTypes[0]?", "+Dn+"; q=0.01":""):p.accepts["*"]);for(i in p.headers)C.setRequestHeader(i,p.headers[i]);if(p.beforeSend&&(p.beforeSend.call(f,C,p)===!1||2===b))return C.abort();w="abort";for(i in{success:1,error:1,complete:1})C[i](p[i]);if(u=qn(jn,p,n,C)){C.readyState=1,l&&d.trigger("ajaxSend",[C,p]),p.async&&p.timeout>0&&(s=setTimeout(function(){C.abort("timeout")},p.timeout));try{b=1,u.send(y,k)}catch(N){if(!(2>b))throw N;k(-1,N)}}else k(-1,"No Transport");function k(e,n,r,i){var c,y,v,w,T,N=n;2!==b&&(b=2,s&&clearTimeout(s),u=t,a=i||"",C.readyState=e>0?4:0,c=e>=200&&300>e||304===e,r&&(w=Mn(p,C,r)),w=On(p,w,C,c),c?(p.ifModified&&(T=C.getResponseHeader("Last-Modified"),T&&(x.lastModified[o]=T),T=C.getResponseHeader("etag"),T&&(x.etag[o]=T)),204===e||"HEAD"===p.type?N="nocontent":304===e?N="notmodified":(N=w.state,y=w.data,v=w.error,c=!v)):(v=N,(e||!N)&&(N="error",0>e&&(e=0))),C.status=e,C.statusText=(n||N)+"",c?h.resolveWith(f,[y,N,C]):h.rejectWith(f,[C,N,v]),C.statusCode(m),m=t,l&&d.trigger(c?"ajaxSuccess":"ajaxError",[C,p,c?y:v]),g.fireWith(f,[C,N]),l&&(d.trigger("ajaxComplete",[C,p]),--x.active||x.event.trigger("ajaxStop")))}return C},getJSON:function(e,t,n){return x.get(e,t,n,"json")},getScript:function(e,n){return x.get(e,t,n,"script")}}),x.each(["get","post"],function(e,n){x[n]=function(e,r,i,o){return x.isFunction(r)&&(o=o||i,i=r,r=t),x.ajax({url:e,type:n,dataType:o,data:r,success:i})}});function Mn(e,n,r){var i,o,a,s,l=e.contents,u=e.dataTypes;while("*"===u[0])u.shift(),o===t&&(o=e.mimeType||n.getResponseHeader("Content-Type"));if(o)for(s in l)if(l[s]&&l[s].test(o)){u.unshift(s);break}if(u[0]in r)a=u[0];else{for(s in r){if(!u[0]||e.converters[s+" "+u[0]]){a=s;break}i||(i=s)}a=a||i}return a?(a!==u[0]&&u.unshift(a),r[a]):t}function On(e,t,n,r){var i,o,a,s,l,u={},c=e.dataTypes.slice();if(c[1])for(a in e.converters)u[a.toLowerCase()]=e.converters[a];o=c.shift();while(o)if(e.responseFields[o]&&(n[e.responseFields[o]]=t),!l&&r&&e.dataFilter&&(t=e.dataFilter(t,e.dataType)),l=o,o=c.shift())if("*"===o)o=l;else if("*"!==l&&l!==o){if(a=u[l+" "+o]||u["* "+o],!a)for(i in u)if(s=i.split(" "),s[1]===o&&(a=u[l+" "+s[0]]||u["* "+s[0]])){a===!0?a=u[i]:u[i]!==!0&&(o=s[0],c.unshift(s[1]));break}if(a!==!0)if(a&&e["throws"])t=a(t);else try{t=a(t)}catch(p){return{state:"parsererror",error:a?p:"No conversion from "+l+" to "+o}}}return{state:"success",data:t}}x.ajaxSetup({accepts:{script:"text/javascript, application/javascript, application/ecmascript, application/x-ecmascript"},contents:{script:/(?:java|ecma)script/},converters:{"text script":function(e){return x.globalEval(e),e}}}),x.ajaxPrefilter("script",function(e){e.cache===t&&(e.cache=!1),e.crossDomain&&(e.type="GET",e.global=!1)}),x.ajaxTransport("script",function(e){if(e.crossDomain){var n,r=a.head||x("head")[0]||a.documentElement;return{send:function(t,i){n=a.createElement("script"),n.async=!0,e.scriptCharset&&(n.charset=e.scriptCharset),n.src=e.url,n.onload=n.onreadystatechange=function(e,t){(t||!n.readyState||/loaded|complete/.test(n.readyState))&&(n.onload=n.onreadystatechange=null,n.parentNode&&n.parentNode.removeChild(n),n=null,t||i(200,"success"))},r.insertBefore(n,r.firstChild)},abort:function(){n&&n.onload(t,!0)}}}});var Fn=[],Bn=/(=)\?(?=&|$)|\?\?/;x.ajaxSetup({jsonp:"callback",jsonpCallback:function(){var e=Fn.pop()||x.expando+"_"+vn++;return this[e]=!0,e}}),x.ajaxPrefilter("json jsonp",function(n,r,i){var o,a,s,l=n.jsonp!==!1&&(Bn.test(n.url)?"url":"string"==typeof n.data&&!(n.contentType||"").indexOf("application/x-www-form-urlencoded")&&Bn.test(n.data)&&"data");return l||"jsonp"===n.dataTypes[0]?(o=n.jsonpCallback=x.isFunction(n.jsonpCallback)?n.jsonpCallback():n.jsonpCallback,l?n[l]=n[l].replace(Bn,"$1"+o):n.jsonp!==!1&&(n.url+=(bn.test(n.url)?"&":"?")+n.jsonp+"="+o),n.converters["script json"]=function(){return s||x.error(o+" was not called"),s[0]},n.dataTypes[0]="json",a=e[o],e[o]=function(){s=arguments},i.always(function(){e[o]=a,n[o]&&(n.jsonpCallback=r.jsonpCallback,Fn.push(o)),s&&x.isFunction(a)&&a(s[0]),s=a=t}),"script"):t});var Pn,Rn,Wn=0,$n=e.ActiveXObject&&function(){var e;for(e in Pn)Pn[e](t,!0)};function In(){try{return new e.XMLHttpRequest}catch(t){}}function zn(){try{return new e.ActiveXObject("Microsoft.XMLHTTP")}catch(t){}}x.ajaxSettings.xhr=e.ActiveXObject?function(){return!this.isLocal&&In()||zn()}:In,Rn=x.ajaxSettings.xhr(),x.support.cors=!!Rn&&"withCredentials"in Rn,Rn=x.support.ajax=!!Rn,Rn&&x.ajaxTransport(function(n){if(!n.crossDomain||x.support.cors){var r;return{send:function(i,o){var a,s,l=n.xhr();if(n.username?l.open(n.type,n.url,n.async,n.username,n.password):l.open(n.type,n.url,n.async),n.xhrFields)for(s in n.xhrFields)l[s]=n.xhrFields[s];n.mimeType&&l.overrideMimeType&&l.overrideMimeType(n.mimeType),n.crossDomain||i["X-Requested-With"]||(i["X-Requested-With"]="XMLHttpRequest");try{for(s in i)l.setRequestHeader(s,i[s])}catch(u){}l.send(n.hasContent&&n.data||null),r=function(e,i){var s,u,c,p;try{if(r&&(i||4===l.readyState))if(r=t,a&&(l.onreadystatechange=x.noop,$n&&delete Pn[a]),i)4!==l.readyState&&l.abort();else{p={},s=l.status,u=l.getAllResponseHeaders(),"string"==typeof l.responseText&&(p.text=l.responseText);try{c=l.statusText}catch(f){c=""}s||!n.isLocal||n.crossDomain?1223===s&&(s=204):s=p.text?200:404}}catch(d){i||o(-1,d)}p&&o(s,c,p,u)},n.async?4===l.readyState?setTimeout(r):(a=++Wn,$n&&(Pn||(Pn={},x(e).unload($n)),Pn[a]=r),l.onreadystatechange=r):r()},abort:function(){r&&r(t,!0)}}}});var Xn,Un,Vn=/^(?:toggle|show|hide)$/,Yn=RegExp("^(?:([+-])=|)("+w+")([a-z%]*)$","i"),Jn=/queueHooks$/,Gn=[nr],Qn={"*":[function(e,t){var n=this.createTween(e,t),r=n.cur(),i=Yn.exec(t),o=i&&i[3]||(x.cssNumber[e]?"":"px"),a=(x.cssNumber[e]||"px"!==o&&+r)&&Yn.exec(x.css(n.elem,e)),s=1,l=20;if(a&&a[3]!==o){o=o||a[3],i=i||[],a=+r||1;do s=s||".5",a/=s,x.style(n.elem,e,a+o);while(s!==(s=n.cur()/r)&&1!==s&&--l)}return i&&(a=n.start=+a||+r||0,n.unit=o,n.end=i[1]?a+(i[1]+1)*i[2]:+i[2]),n}]};function Kn(){return setTimeout(function(){Xn=t}),Xn=x.now()}function Zn(e,t,n){var r,i=(Qn[t]||[]).concat(Qn["*"]),o=0,a=i.length;for(;a>o;o++)if(r=i[o].call(n,t,e))return r}function er(e,t,n){var r,i,o=0,a=Gn.length,s=x.Deferred().always(function(){delete l.elem}),l=function(){if(i)return!1;var t=Xn||Kn(),n=Math.max(0,u.startTime+u.duration-t),r=n/u.duration||0,o=1-r,a=0,l=u.tweens.length;for(;l>a;a++)u.tweens[a].run(o);return s.notifyWith(e,[u,o,n]),1>o&&l?n:(s.resolveWith(e,[u]),!1)},u=s.promise({elem:e,props:x.extend({},t),opts:x.extend(!0,{specialEasing:{}},n),originalProperties:t,originalOptions:n,startTime:Xn||Kn(),duration:n.duration,tweens:[],createTween:function(t,n){var r=x.Tween(e,u.opts,t,n,u.opts.specialEasing[t]||u.opts.easing);return u.tweens.push(r),r},stop:function(t){var n=0,r=t?u.tweens.length:0;if(i)return this;for(i=!0;r>n;n++)u.tweens[n].run(1);return t?s.resolveWith(e,[u,t]):s.rejectWith(e,[u,t]),this}}),c=u.props;for(tr(c,u.opts.specialEasing);a>o;o++)if(r=Gn[o].call(u,e,c,u.opts))return r;return x.map(c,Zn,u),x.isFunction(u.opts.start)&&u.opts.start.call(e,u),x.fx.timer(x.extend(l,{elem:e,anim:u,queue:u.opts.queue})),u.progress(u.opts.progress).done(u.opts.done,u.opts.complete).fail(u.opts.fail).always(u.opts.always)}function tr(e,t){var n,r,i,o,a;for(n in e)if(r=x.camelCase(n),i=t[r],o=e[n],x.isArray(o)&&(i=o[1],o=e[n]=o[0]),n!==r&&(e[r]=o,delete e[n]),a=x.cssHooks[r],a&&"expand"in a){o=a.expand(o),delete e[r];for(n in o)n in e||(e[n]=o[n],t[n]=i)}else t[r]=i}x.Animation=x.extend(er,{tweener:function(e,t){x.isFunction(e)?(t=e,e=["*"]):e=e.split(" ");var n,r=0,i=e.length;for(;i>r;r++)n=e[r],Qn[n]=Qn[n]||[],Qn[n].unshift(t)},prefilter:function(e,t){t?Gn.unshift(e):Gn.push(e)}});function nr(e,t,n){var r,i,o,a,s,l,u=this,c={},p=e.style,f=e.nodeType&&nn(e),d=x._data(e,"fxshow");n.queue||(s=x._queueHooks(e,"fx"),null==s.unqueued&&(s.unqueued=0,l=s.empty.fire,s.empty.fire=function(){s.unqueued||l()}),s.unqueued++,u.always(function(){u.always(function(){s.unqueued--,x.queue(e,"fx").length||s.empty.fire()})})),1===e.nodeType&&("height"in t||"width"in t)&&(n.overflow=[p.overflow,p.overflowX,p.overflowY],"inline"===x.css(e,"display")&&"none"===x.css(e,"float")&&(x.support.inlineBlockNeedsLayout&&"inline"!==ln(e.nodeName)?p.zoom=1:p.display="inline-block")),n.overflow&&(p.overflow="hidden",x.support.shrinkWrapBlocks||u.always(function(){p.overflow=n.overflow[0],p.overflowX=n.overflow[1],p.overflowY=n.overflow[2]}));for(r in t)if(i=t[r],Vn.exec(i)){if(delete t[r],o=o||"toggle"===i,i===(f?"hide":"show"))continue;c[r]=d&&d[r]||x.style(e,r)}if(!x.isEmptyObject(c)){d?"hidden"in d&&(f=d.hidden):d=x._data(e,"fxshow",{}),o&&(d.hidden=!f),f?x(e).show():u.done(function(){x(e).hide()}),u.done(function(){var t;x._removeData(e,"fxshow");for(t in c)x.style(e,t,c[t])});for(r in c)a=Zn(f?d[r]:0,r,u),r in d||(d[r]=a.start,f&&(a.end=a.start,a.start="width"===r||"height"===r?1:0))}}function rr(e,t,n,r,i){return new rr.prototype.init(e,t,n,r,i)}x.Tween=rr,rr.prototype={constructor:rr,init:function(e,t,n,r,i,o){this.elem=e,this.prop=n,this.easing=i||"swing",this.options=t,this.start=this.now=this.cur(),this.end=r,this.unit=o||(x.cssNumber[n]?"":"px")},cur:function(){var e=rr.propHooks[this.prop];return e&&e.get?e.get(this):rr.propHooks._default.get(this)},run:function(e){var t,n=rr.propHooks[this.prop];return this.pos=t=this.options.duration?x.easing[this.easing](e,this.options.duration*e,0,1,this.options.duration):e,this.now=(this.end-this.start)*t+this.start,this.options.step&&this.options.step.call(this.elem,this.now,this),n&&n.set?n.set(this):rr.propHooks._default.set(this),this}},rr.prototype.init.prototype=rr.prototype,rr.propHooks={_default:{get:function(e){var t;return null==e.elem[e.prop]||e.elem.style&&null!=e.elem.style[e.prop]?(t=x.css(e.elem,e.prop,""),t&&"auto"!==t?t:0):e.elem[e.prop]},set:function(e){x.fx.step[e.prop]?x.fx.step[e.prop](e):e.elem.style&&(null!=e.elem.style[x.cssProps[e.prop]]||x.cssHooks[e.prop])?x.style(e.elem,e.prop,e.now+e.unit):e.elem[e.prop]=e.now}}},rr.propHooks.scrollTop=rr.propHooks.scrollLeft={set:function(e){e.elem.nodeType&&e.elem.parentNode&&(e.elem[e.prop]=e.now)}},x.each(["toggle","show","hide"],function(e,t){var n=x.fn[t];x.fn[t]=function(e,r,i){return null==e||"boolean"==typeof e?n.apply(this,arguments):this.animate(ir(t,!0),e,r,i)}}),x.fn.extend({fadeTo:function(e,t,n,r){return this.filter(nn).css("opacity",0).show().end().animate({opacity:t},e,n,r)},animate:function(e,t,n,r){var i=x.isEmptyObject(e),o=x.speed(t,n,r),a=function(){var t=er(this,x.extend({},e),o);(i||x._data(this,"finish"))&&t.stop(!0)};return a.finish=a,i||o.queue===!1?this.each(a):this.queue(o.queue,a)},stop:function(e,n,r){var i=function(e){var t=e.stop;delete e.stop,t(r)};return"string"!=typeof e&&(r=n,n=e,e=t),n&&e!==!1&&this.queue(e||"fx",[]),this.each(function(){var t=!0,n=null!=e&&e+"queueHooks",o=x.timers,a=x._data(this);if(n)a[n]&&a[n].stop&&i(a[n]);else for(n in a)a[n]&&a[n].stop&&Jn.test(n)&&i(a[n]);for(n=o.length;n--;)o[n].elem!==this||null!=e&&o[n].queue!==e||(o[n].anim.stop(r),t=!1,o.splice(n,1));(t||!r)&&x.dequeue(this,e)})},finish:function(e){return e!==!1&&(e=e||"fx"),this.each(function(){var t,n=x._data(this),r=n[e+"queue"],i=n[e+"queueHooks"],o=x.timers,a=r?r.length:0;for(n.finish=!0,x.queue(this,e,[]),i&&i.stop&&i.stop.call(this,!0),t=o.length;t--;)o[t].elem===this&&o[t].queue===e&&(o[t].anim.stop(!0),o.splice(t,1));for(t=0;a>t;t++)r[t]&&r[t].finish&&r[t].finish.call(this);delete n.finish})}});function ir(e,t){var n,r={height:e},i=0;for(t=t?1:0;4>i;i+=2-t)n=Zt[i],r["margin"+n]=r["padding"+n]=e;return t&&(r.opacity=r.width=e),r}x.each({slideDown:ir("show"),slideUp:ir("hide"),slideToggle:ir("toggle"),fadeIn:{opacity:"show"},fadeOut:{opacity:"hide"},fadeToggle:{opacity:"toggle"}},function(e,t){x.fn[e]=function(e,n,r){return this.animate(t,e,n,r)}}),x.speed=function(e,t,n){var r=e&&"object"==typeof e?x.extend({},e):{complete:n||!n&&t||x.isFunction(e)&&e,duration:e,easing:n&&t||t&&!x.isFunction(t)&&t};return r.duration=x.fx.off?0:"number"==typeof r.duration?r.duration:r.duration in x.fx.speeds?x.fx.speeds[r.duration]:x.fx.speeds._default,(null==r.queue||r.queue===!0)&&(r.queue="fx"),r.old=r.complete,r.complete=function(){x.isFunction(r.old)&&r.old.call(this),r.queue&&x.dequeue(this,r.queue)},r},x.easing={linear:function(e){return e},swing:function(e){return.5-Math.cos(e*Math.PI)/2}},x.timers=[],x.fx=rr.prototype.init,x.fx.tick=function(){var e,n=x.timers,r=0;for(Xn=x.now();n.length>r;r++)e=n[r],e()||n[r]!==e||n.splice(r--,1);n.length||x.fx.stop(),Xn=t},x.fx.timer=function(e){e()&&x.timers.push(e)&&x.fx.start()},x.fx.interval=13,x.fx.start=function(){Un||(Un=setInterval(x.fx.tick,x.fx.interval))},x.fx.stop=function(){clearInterval(Un),Un=null},x.fx.speeds={slow:600,fast:200,_default:400},x.fx.step={},x.expr&&x.expr.filters&&(x.expr.filters.animated=function(e){return x.grep(x.timers,function(t){return e===t.elem}).length}),x.fn.offset=function(e){if(arguments.length)return e===t?this:this.each(function(t){x.offset.setOffset(this,e,t)});var n,r,o={top:0,left:0},a=this[0],s=a&&a.ownerDocument;if(s)return n=s.documentElement,x.contains(n,a)?(typeof a.getBoundingClientRect!==i&&(o=a.getBoundingClientRect()),r=or(s),{top:o.top+(r.pageYOffset||n.scrollTop)-(n.clientTop||0),left:o.left+(r.pageXOffset||n.scrollLeft)-(n.clientLeft||0)}):o},x.offset={setOffset:function(e,t,n){var r=x.css(e,"position");"static"===r&&(e.style.position="relative");var i=x(e),o=i.offset(),a=x.css(e,"top"),s=x.css(e,"left"),l=("absolute"===r||"fixed"===r)&&x.inArray("auto",[a,s])>-1,u={},c={},p,f;l?(c=i.position(),p=c.top,f=c.left):(p=parseFloat(a)||0,f=parseFloat(s)||0),x.isFunction(t)&&(t=t.call(e,n,o)),null!=t.top&&(u.top=t.top-o.top+p),null!=t.left&&(u.left=t.left-o.left+f),"using"in t?t.using.call(e,u):i.css(u)}},x.fn.extend({position:function(){if(this[0]){var e,t,n={top:0,left:0},r=this[0];return"fixed"===x.css(r,"position")?t=r.getBoundingClientRect():(e=this.offsetParent(),t=this.offset(),x.nodeName(e[0],"html")||(n=e.offset()),n.top+=x.css(e[0],"borderTopWidth",!0),n.left+=x.css(e[0],"borderLeftWidth",!0)),{top:t.top-n.top-x.css(r,"marginTop",!0),left:t.left-n.left-x.css(r,"marginLeft",!0)}}},offsetParent:function(){return this.map(function(){var e=this.offsetParent||s;while(e&&!x.nodeName(e,"html")&&"static"===x.css(e,"position"))e=e.offsetParent;return e||s})}}),x.each({scrollLeft:"pageXOffset",scrollTop:"pageYOffset"},function(e,n){var r=/Y/.test(n);x.fn[e]=function(i){return x.access(this,function(e,i,o){var a=or(e);return o===t?a?n in a?a[n]:a.document.documentElement[i]:e[i]:(a?a.scrollTo(r?x(a).scrollLeft():o,r?o:x(a).scrollTop()):e[i]=o,t)},e,i,arguments.length,null)}});function or(e){return x.isWindow(e)?e:9===e.nodeType?e.defaultView||e.parentWindow:!1}x.each({Height:"height",Width:"width"},function(e,n){x.each({padding:"inner"+e,content:n,"":"outer"+e},function(r,i){x.fn[i]=function(i,o){var a=arguments.length&&(r||"boolean"!=typeof i),s=r||(i===!0||o===!0?"margin":"border");return x.access(this,function(n,r,i){var o;return x.isWindow(n)?n.document.documentElement["client"+e]:9===n.nodeType?(o=n.documentElement,Math.max(n.body["scroll"+e],o["scroll"+e],n.body["offset"+e],o["offset"+e],o["client"+e])):i===t?x.css(n,r,s):x.style(n,r,i,s)},n,a?i:t,a,null)}})}),x.fn.size=function(){return this.length},x.fn.andSelf=x.fn.addBack,"object"==typeof module&&module&&"object"==typeof module.exports?module.exports=x:(e.jQuery=e.$=x,"function"==typeof define&&define.amd&&define("jquery",[],function(){return x}))})(window);
/*! Lazy Load 1.9.7 - MIT license - Copyright 2010-2015 Mika Tuupola */
!function(a,b,c,d){var e=a(b);a.fn.lazyload=function(f){function g(){var b=0;i.each(function(){var c=a(this);if(!j.skip_invisible||c.is(":visible"))if(a.abovethetop(this,j)||a.leftofbegin(this,j));else if(a.belowthefold(this,j)||a.rightoffold(this,j)){if(++b>j.failure_limit)return!1}else c.trigger("appear"),b=0})}var h,i=this,j={threshold:0,failure_limit:0,event:"scroll",effect:"show",container:b,data_attribute:"original",skip_invisible:!1,appear:null,load:null,placeholder:"data:image/gif;base64,R0lGODlh9AH0AfewAERERHt7e3h4eHZ2dv7+/n19ff39/X9/f3x8fPz8/Pn5+X5+fm5ubvv7+6GhofPz8////4GBgfT09L6+vvf396mpqdHR0e7u7sPDw/X19aCgoPb29ubm5vj4+Hl5efDw8KSkpOvr693d3e3t7eTk5Pr6+o6OjtTU1JCQkOrq6s3Nzefn59jY2MHBwcfHx56envHx8bq6unNzc9bW1tzc3IaGhpiYmJaWlrW1teHh4ZKSkoWFheDg4Hd3d7e3t7Ozs2tra4yMjLi4uNPT08TExOPj48XFxd7e3qOjo7GxsZSUlGFhYezs7IeHh42NjaampkVFRYiIiNra2vLy8oSEhIODg7y8vNvb24CAgIKCgr29vYqKisvLy9/f34uLi66urrS0tMjIyOnp6e/v76ysrNnZ2aurq8rKypycnJOTk+jo6Jubm52dnbu7u8nJyeLi4s7OzkZGRsLCwszMzI+Pj6KiopmZmeXl5ba2ttDQ0HR0dNfX13p6erm5udLS0qenp7KysqioqMDAwMbGxp+fn9XV1ZeXl5qamqWlpYmJic/Pz29vb62trZGRka+vr7CwsL+/v5WVlUhISKqqqktLS3JycnV1dUlJSUdHR2xsbE5OTnFxcWRkZEpKSk1NTVZWVnBwcG1tbUxMTFFRUVNTU2hoaFJSUlBQUFVVVVRUVF9fX2BgYFlZWU9PT2VlZVtbW////wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACH/C05FVFNDQVBFMi4wAwEAAAAh/wtYTVAgRGF0YVhNUDw/eHBhY2tldCBiZWdpbj0i77u/IiBpZD0iVzVNME1wQ2VoaUh6cmVTek5UY3prYzlkIj8+IDx4OnhtcG1ldGEgeG1sbnM6eD0iYWRvYmU6bnM6bWV0YS8iIHg6eG1wdGs9IkFkb2JlIFhNUCBDb3JlIDUuMy1jMDExIDY2LjE0NTY2MSwgMjAxMi8wMi8wNi0xNDo1NjoyNyAgICAgICAgIj4gPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gPHJkZjpEZXNjcmlwdGlvbiByZGY6YWJvdXQ9IiIgeG1sbnM6eG1wPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvIiB4bWxuczp4bXBNTT0iaHR0cDovL25zLmFkb2JlLmNvbS94YXAvMS4wL21tLyIgeG1sbnM6c3RSZWY9Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC9zVHlwZS9SZXNvdXJjZVJlZiMiIHhtcDpDcmVhdG9yVG9vbD0iQWRvYmUgUGhvdG9zaG9wIENTNiAoV2luZG93cykiIHhtcE1NOkluc3RhbmNlSUQ9InhtcC5paWQ6N0QzQTcxRTE5QTJCMTFFNzhFQTNFODBFOEM2MzhBMUYiIHhtcE1NOkRvY3VtZW50SUQ9InhtcC5kaWQ6N0QzQTcxRTI5QTJCMTFFNzhFQTNFODBFOEM2MzhBMUYiPiA8eG1wTU06RGVyaXZlZEZyb20gc3RSZWY6aW5zdGFuY2VJRD0ieG1wLmlpZDo3RDNBNzFERjlBMkIxMUU3OEVBM0U4MEU4QzYzOEExRiIgc3RSZWY6ZG9jdW1lbnRJRD0ieG1wLmRpZDo3RDNBNzFFMDlBMkIxMUU3OEVBM0U4MEU4QzYzOEExRiIvPiA8L3JkZjpEZXNjcmlwdGlvbj4gPC9yZGY6UkRGPiA8L3g6eG1wbWV0YT4gPD94cGFja2V0IGVuZD0iciI/PgH//v38+/r5+Pf29fTz8vHw7+7t7Ovq6ejn5uXk4+Lh4N/e3dzb2tnY19bV1NPS0dDPzs3My8rJyMfGxcTDwsHAv769vLu6ubi3trW0s7KxsK+urayrqqmop6alpKOioaCfnp2cm5qZmJeWlZSTkpGQj46NjIuKiYiHhoWEg4KBgH9+fXx7enl4d3Z1dHNycXBvbm1sa2ppaGdmZWRjYmFgX15dXFtaWVhXVlVUU1JRUE9OTUxLSklIR0ZFRENCQUA/Pj08Ozo5ODc2NTQzMjEwLy4tLCsqKSgnJiUkIyIhIB8eHRwbGhkYFxYVFBMSERAPDg0MCwoJCAcGBQQDAgEAACH5BAUEALAALAAAAAD0AfQBAAj/AGEJHEiwoMGDCBMqXMiwocOHECNKnEixosWLGDNq3Mixo8ePIEOKHEmypMmTKFOqXMmypcuXMGPKnEmzps2bOHPq3Mmzp8+fQIMKHUq0qNGjSJMqXcq0qdOnUKNKnUq1qtWrWLNq3cq1q9evYMOKHUu2rNmzaNOqXcu2rdu3cOPKnUu3rt27ePPq3cu3r9+/gAMLHky4sOHDiBMrXsy4sePHkCNLnky5suXLmDNr3sy5s+fPoEOLHk26tOnTqFOrXs26tevXsGPLnk27tu3buHPr3s27t+/fwIMLH068uPHjyJMrX868ufPn0KNLn069uvXr2LNr3869u/fv4MOL/x9Pvrz58+jTq1/Pvr379/Djy59Pv779+/jz69/Pv7///wAGKOCABBZo4IEIJqjgggw26OCDEEYo4YQUVmjhhRhmqOGGHHbo4YcghijiiCSWaOKJKKao4oostujiizDGKOOMNNZo44045qjjjjz26OOPQAYp5JBEFmnkkUgmqeSSTDbp5JNQRinllFRWaeWVWGap5ZZcdunll2CGKeaYZJZp5plopqnmmmy26eabcMYp55x01mnnnXjmqeeefPbp55+ABirooIQWauihiCaq6KKMNuroo5BGKumklFZq6aWYZqrpppx26umnoIYq6qiklmrqqaimquqqrLbq6quwxv8q66y01mrrrbjmquuuvPbq66/ABivssMQWa+yxyCar7LLMNuvss9BGK+201FZr7bXYZqvtttx26+234IYr7rjk7koABxg4gIITL8QgggLlDvQBCAEAYO+99gaAAg+lEmBATwbQi+/A9wbgBAyfZiBHEwE0HEAEeIyAUwgLEGxxwSpwSgEa9VocgBch1MRDxxdfHEAMXmZwxRluzPCBTSeQXHIAPsw0gswle2zEll3cIPPHFsyEAc4zOxATAQfkrDQAAaSAZcBE53sDBTCxEPXMj8BUwdJLU3GlATcsHcUGLilwdc4BFOHSA2dznW/QVW7NtRIQtOSA2wR73RIZeCv/fUCVRbQ9sBssdSD4zDm0dLjbAUg8pR1970DASmf0TfALLIWwuNtyTGm45SushILlAwfAkgqk55zGlEWQTrhKm5tcwkqPpD7zlCeQjjLstt/7wEoa9O4x7qQLsVLsF/+u0gvCE2y6lDm4frzwAcCr0hfNlz4lBcgDELpKJlDPkgvZ4+sElWHjncXkKpHfuw0srVD+vVZQOTLeLrCUQfcFi8ASAfwzmRqqBAK3pYF9K4Fc6hbgkuCV73lUakAauiYBl+yPdAHwX0tuVr6dWakBGjhbGjIAEy4gLwBPgAkasreAumGJBSb42Q5U4EKY4GBzAYAfTMxGPQ1qCQYnwIAc/yzgOJoMbWkB+MNMuhBApv1AUx9AwdUexi+aqIB/KOzUCJKAgI41zAFvwInV+hYAHISKAB2gQAJ4kgEpIvEAVRQXD7YwRQRwIV4CyYAFQBCBhiEADUYoIh4HSchCGvKQiEykIhfJyEY68pGQjKQkJ0nJSlrykpjMpCY3yclOevKToAylKEdJylKa8pSoTKUqV8nKVrrylbCMpSxnScta2vKWuMylLnfJy1768pfADKYwh0nMYhrzmMhMpjKXycxmOvOZ0IymNKdJzWpa85rYzKY2t8nNbnrzm+AMpzjHSc5ymvOc6EynOtfJzna6853wjKc850nPetrznvjMpz73yW7PfvrznwANqEAHStCCGvSgCE2oQhfK0IY69KEQjahEJ0rRilr0ohjNqEY3ytGOevSjIA2pSEdK0pKa9KQoTalKV8rSlrr0pTCNqUxnStOa2vSmOM2pTnfK05769KdADapQh0rUohr1qEhNqp0CAgAh+QQFBACwACypAOsApAAeAAAI/wBhCRxIsKDBgwgTKlzIsKHDhxARGiiixUaNCJF+lFEQsaPHjyBDimR4YQ0DAChTomSwQ0THBg+YMIHBcaTNhQYS3NyJMIFJlUBTMojwoWGCLj90nKJESZMJMzM68LwpwUoABlgZ6PkSYupOMZuCihUaZiGPF5LGxlFyQqdXjxR0nBTL4ICYtyFpzB07lsGPnkQC8E0p6dEGvBDz7OXL4BHijiEWDw7KAJLBBEIwTU4JBUmGxwy1SGZsCLRDA5U2D2agpiARzapRQvni1rTBE6NXV7C90EHswT0IFkHwOyUmOLwLdsg9mQGP5AenMC/OYI7ABL6LpwwiAbpAG9pTBv/3ThBJ+LGVBBbpdB4AFOvQKUxvfoT8wPnUu8Zoj/KFAeiD8AeAEvbBIgZ+xVmRgCECjvIAdDUIyECBYQgYVBQbpCLgJRxAh+BqNXlXgYVAMQCDJgLGUV9yHw42hX0MkijUiSm6xKKFL5IXiYxCbUCKgJLc4aGEUpH3BI8rLdhgjrxlIWGBLSAJQASwCCHgGrXZFiV/JhR4h5Q4wMJDWudBURZ0ErRIWRkFGqBmcx02wEZ7UcBAngntbVKgQDGSOKFAR1ASXhxnepdmeAywuWdkMlomEARaxKHdEyF6N8ibDLCx50A6kLgJBASV8AgUv63BpH1ftMhAl5sKpMCbaxqMpEAb7E0WRwWnFijaZgy80CpBV8AqlBkIEcCCIbAFBYUXZ5Twq0AX7MCcVjQ8S1AYwma6UAczVPCJKJJcQgkpDszxoLUDhVDBInNhZUMX6BaEG3VfOAQBBUzcUUQKEvwXr0EGdEBBlv8OJIG0vFZiY8EM20bDAdMuMkjDFCcnwRxr6IHVIjpAwoRCAQEAIfkEBQQAsAAspwDqAKYAIAAACP8AYQkcSJAgAQIFEypcyLChw4cQI0qcSJHiBRWMDunQYeiJHA4JKoocSbKkSYEG7rR4ESTRGh80FFA0wIINAgA4c+KEosONzJNAgwqtOEbDAJ06BwTpElHMCyhIo+IMwmKoUAMhrWqFlcDBUalJE31waAELWLAehBjYWjGDoCoD4g5A8IMJ25MpPJyVOoALQxd89oKFYibrXYcUbHyNOqBGisMijywWnFSIQj+BKYMFA7nhkMlgB3DuHJEJaM04B2AoGKIKarA9LJBO2OJ06BezHRrI/BrpADEDCTjoDTbRg9wCZ9g+O4AR8oVPiEs9MFBEHOlSYyBXsHzvgDfPCz7/6P56gCKBGrBLrUEh9wv11MMPDKQ+Kh9YMArUj3pidgfy3vEgn0AAlsfEEPtF9cVsbux3yIApFPiaIGAkiJQSCHUWxH4DDMiFhTqZkB6IOGnyE2QSMncicoyQmJoNLgJAyQakpXjWFPKxEeMAMLo4Y40J4hjeGjuOSKInK95lI19JzmbGjoDESMdanW3B4YBGxJiICjFWMBsR+ykx4Aox9nGBJC6eR1oGSyZFw4AGtMmcGhAcQmIVEuQWiXoeDCiQjiB2CMsJUFkICHJsSjfAm36aBuJqXPW4XxUXPOfGkgMg4edAktbnAQQDFaFffVAYIR8gKQ4g5qYCccchowMZnKGXek9QGV5tlGXKKkEiyJnaIwr1cZ10LzSJ3BhBLDfXEbsWxIWcuioEQQs3vQZFBcaGx8QXPXwV1ws5NKuQcr0NcGhDNOiAWhUu2CquAR1QYJi4CmWQbK58MPWQAi4EUahUVeAwFr0EU3REDcr24AZFDXTRBxtBaKLJKIY8Ukh7BWdMUQaKOIBAXD3YgMEIJiVQggINgKrxyp0FBAAh+QQJBACwACymAOoApwAgAAAI/wBhCRxIEFYJHhMc3NDBBkchCQUjSpxIsaLFixgzatzI8WKRQwcAiBwp8oAXOAQ6qlzJsqVLAhyMIFLSqI6VIyU4jmgUEsDEkVUKuRxKtGjLD38OTDygJEfGFj0xAjjgwIDRogSsXt060EAgpRYPNJpi8atPjSLp5OTa0YiXA3AP1BAygi1RJlk2HoBDsULIjiK9JLCLsQMhsBEP0GFCeGUOxBoPWJGI4e9KAIcaV5wBeWkMzRtHdI7souAFy5cPlAZd0MjopYhYXyRQpeWBEASVnG0JAMta2WVeUzzwQ3ZFMkOjDOSAmrcQ47CEVzxAArpE6ZH9CHSw22VvCLJjq/9Ubp2go6K1DTT3Xp019ulFyg98H3kEh+5DATwHPaelA/mwMEGfRka4gZ93jbCmhG0A8mXUDWQcyBsW7tn2G3TFGXUAIRKyNFWFLT0gHwhXbdhhaiCyJGJ5dZRYwYkqAZAXaAMOB2ASJRoBI2B0sKYDg/K5cVUjOezIEQA4giYkS2gAqMZVE5SwHm9HyFZjYlXKR8CVYYkByw1GZtSbVqCxsdKMAJJIFFgiTBkjcsZxKdABWQIoGlGrwZJImBZNBZFxKnB5QAUAEkTIUGjCQoKbaB2wH3RC1HhAk4UOJKVtdQqUBKNSBQGgaxcdMEmlBfEg53w4SHSISDFWsUGhHyh7IZxcTpFakCKnDjoRATdwKpFIVXxg6wg/YAEWXIjEZ6tEwen16ER+8TkVHRQsOxABCnRg7UWyhlpFrRaxUMVIFJU02bbobpQDHbNiocJGBLhRQ08kjYRFEtWmq+9GfgQy7wFYEOLCBSyNMAghUWSRRQ03xHBHSvtGTFhAACH5BAkEALAALAAAAAD0AfQBAAj/AGEJHEiwoMGDCBMqXMiwocOHECNKnEixosWLGDNq3Mixo8ePIEOKHEmypMmTKFOqXMmypcuXMGPKnEmzps2bOHPq3Mmzp8+fQIMKHUq0qNGjSJMqXcq0qdOnUKNKnUq1qtWrWLNq3cq1q9evYMOKHUu2rNmzaNOqXcu2rdu3cOPKnUu3rt27ePPq3cu3r9+/gAMLHky4sOHDiBMrXsy4sePHkCNLnky5suXLmDNr3sy5s+fPoEOLHk26tOnTqFOrXs26tevXsGPLnk27tu3buHPr3s27t+/fwIMLH068uPHjyJMrX868ufPn0KNLn069uvXr2LNr3869u/fv4MOL/x9Pvrz58+jTq1/Pvr379/Djy59Pv779+/jz69/Pv7///wAGKOCABBZo4IEIJqjgggw26OCDEEYo4YQUVmjhhRhmqOGGHHbo4YcghijiiCSWaOKJKKao4oostujiizDGKOOMNNZo44045qjjjjz26OOPQAYp5JBEFmnkkUgmqeSSTDbp5JNQRinllFRWaeWVWGap5ZZcdunll2CGKeaYZJZp5plopqnmmmy26eabcMYp55x01mnnnXjmqeeefPbp55+ABirooIQWauihiCaq6KKMNuroo5BGKumklFZq6aWYZqrpppx26umnoIYq6qiklmrqqaimquqqrLbq6quwxv8q66y01mrrrbjmquuuvPbq66/ABivssMQWa+yxyCar7LLMNuvss9BGK+201FZr7bXYZqvtttx26+234IYr7rgmQtBAAwSQixABVzwRQQAAABDAAjYo0kFfBHCAgQMoOPFCDCIo8GUDeCAQ78EIy/sCDHl9AAK8CccbAAo8cGmBwRFnHMAPNxFgQE8GPJxxwgE4wTCWFUA8csQllxBTBnI0EcDMAUSAxwg4hbDAyhqrcCUaKvMcMRUCt0QB0CMH4EUINfEQtNAHBxBDlSlDvfIWELB0wtMa+zDTCFxbLa8RU24t9soVrIRB2Bo7EBMBB5ytcQpRGrCz3BpzkBILbCf//QhMFeCdMRVRWiH4yCagpEDfKwdQhEsPMC52ABY8CQHGh5OMs0kOZE54S2RkHvEBT74hesYcl9SB5I3n0BLrk2/O5COnR5yFSWec/gJLIcAuthxORlE7yQ2UhMLpAbCkwvAIp+Ek5swDcPJIviftskq0Ry9vkwRULzbdJHmf8QMraaD99kx2fz4AapQkfsTkq/TC+ck3+b7QH7iPfNEpfUG/kzug3/VGYgLkscQF53OCkwKnPdKVBIGiswFLVnA+KzjpCudLW0kycD95iYAl6mNeANrXJANAD3l6M4kdMrcAl5hPhFDyH/OagBIOCi4AH2wJ2JhHticp4ISHC8AV/1LCBe8F4AkwQcPwFpA1KBmhgwezw0pw4LsASBAmi0NeDqO0QtFFoHhqY10A/jCTLnRwY1QigBMyh4D8teQDKGBbzSpGExW874hWIsANxBeB6blkBElAAMRm5oA34IRvcgsADrIUgyqiAYwzIUAHKJAAnmQgjlALwAHomCUYvIBxAdgCJ+3Cgy3IEQFc+NIG5OCEoAWACklgGl8yYAEQvCsACECDEWQXJgJQAAYfyMDH1EXMYhrzmMhMpjKXycxmOvOZ0IymNKdJzWpa85rYzKY2t8nNbnrzm+AMpzjHSc5ymvOc6EynOtfJzna6853wjKc850nPetrznvjMpz73ycfPfvrznwANqEAHStCCGvSgCE2oQhfK0IY69KEQjahEJ0rRilr0ohjNqEY3ytGOevSjIA2pSEdK0pKa9KQoTalKV8rSlrr0pTCNqUxnStOa2vSmOM2pTnfK05769KdADapQh0rUohr1qEhNqlKXytSmOvWpUI2qVKdK1apa9apYzapWt8rVrnr1q2ANq1jHStaymvWsaE2rWtfK1ra69a1wjatc50rXutr1rnjNq173yte++vWvgA2sYAdL2MIa9rCITaxiPRUQACH5BAkEALAALAAAAAD0AfQBAAj/AGEJHEiwoMGDCBMqXMiwocOHECNKnEixosWLGDNq3Mixo8ePIEOKHEmypMmTKFOqXMmypcuXMGPKnEmzps2bOHPq3Mmzp8+fQIMKHUq0qNGjSJMqXcq0qdOnUKNKnUq1qtWrWLNq3cq1q9evYMOKHUu2rNmzaNOqXcu2rdu3cOPKnUu3rt27ePPq3cu3r9+/gAMLHky4sOHDiBMrXsy4sePHkCNLnky5suXLmDNr3sy5s+fPoEOLHk26tOnTqFOrXs26tevXsGPLnk27tu3buHPr3s27t+/fwIMLH068uPHjyJMrX868ufPn0KNLn069uvXr2LNr3869u/fv4MOL/x9Pvrz58+jTq1/Pvr379/Djy59Pv779+/jz69/Pv7///wAGKOCABBZo4IEIJqjgggw26OCDEEYo4YQUVmjhhRhmqOGGHHbo4YcghijiiCSWaOKJKKao4oostujiizDGKOOMNNZo44045qjjjjz26OOPQAYp5JBEFmnkkUgmqeSSTDbp5JNQRinllFRWaeWVWGap5ZZcdunll2CGKeaYZJZp5plopqnmmmy26eabcMYp55x01mnnnXjmqeeefPbp55+ABirooIQWauihiCaq6KKMNuroo5BGKumklFZq6aWYZqrpppx26umnoIYq6qiklmrqqaimquqqrLbq6quwxv8q66y01mrrrbjmquuuvPbq66/ABivssMQWa+yxyCar7LLMNuvss9BGK+201FZr7bXYZqvtttx26+234IYr7rjk1igBCVLskQMMBPxlwB1yaGCCF2wIQYMCYa6AhAcCAOCvvwIowcJeH9TR778IC2ACD12m4MXBCCd8wBA3lfDAFB3wZAASEEecsBcwaIlHxx4nbEgCMhUxyQEHC4CABnsYcFMICJRsMwACzIElGiTf/G8VG7zEgQk9/0wxTV0U7TPOfVh5iNJLZ9FAS21A/a8AdcgcExNW+ywAEVQK0bXPOrBExtj/6oDySwbUvLTXKUg5Ato3CzCISlrQ/S8bMAX/8vbbWUhpwt9Le7C2SWroffUZLj2guM0C5AEl14QvDfZJOlQe8QFTszSJ5j4jACUZoN9cxUmJl/5vGC09XjcTT7qtesQCBF0SILP7awJLIbh+cwtOKuC7zTSYVEPuOJew0hzIe9yIkyE0HzEGJRkw/L8hrOSI9Ak7WQT3/+JRUgfS57DSC+AD7OQb6QMARkkUSM+wSmy0L4CTKbQPPEkJXO9v3CohXfru1yQK+C9iZTBJFZAnAHypZBDt80LswCeAB5iEEciT4EpW0L42PAkJ4DvASYpwPeqtxHoUVMOTOHBAf3nwJEGYnQcceD4KRikK0msgSnLgOgHIwSWUk97l/55EAv8JoGkpAcPjlACTQ0gPARCQUiCuVwOWaEBvXqBhS4THwOJNaXCqQ4AEWnK2twngBlp0yRGGJ4AkVMkAMQQdAmDnkjLsIHR3o8kcegiCK0HgioQTQBQyEBMC7IFnCdPBGZRnkz0oTgDvyxILWFY4LdjEAA8Qgxo+cDicZIBoZkTA/LZUiCD0TABZkEPn8NKFKChNAB5gHJgasII8YKAFc8gBBf6SgTwggWWwPAQRRlCuYhrzmMhMpjKXycxmOvOZ0IymNKdJzWpa85rYzKY2t8nNbnrzm+AMpzjHSc5ymvOc6EynOtfJzna6853wjKc850nPetrznvjMpz73ycrPfvrznwANqEAHStCCGvSgCE2oQhfK0IY69KEQjahEJ0rRilr0ohjNqEY3ytGOevSjIA2pSEdK0pKa9KQoTalKV8rSlrr0pTCNqUxnStOa2vSmOM2pTnfK05769KdADapQh0rUohr1qEhNqlKXytSmOvWpUI2qVKdK1apa9apYzapWt8rVrnr1q2ANq1jHStaymvWsaE2rWtfK1ra69a1wjatc50rXutr1rnjNq173yte++vWvgA2sYAdL2MIa9rCITaxiF8tYrgQEACH5BAkEALAALAAAAAD0AfQBAAj/AGEJHEiwoMGDCBMqXMiwocOHECNKnEixosWLGDNq3Mixo8ePIEOKHEmypMmTKFOqXMmypcuXMGPKnEmzps2bOHPq3Mmzp8+fQIMKHUq0qNGjSJMqXcq0qdOnUKNKnUq1qtWrWLNq3cq1q9evYMOKHUu2rNmzaNOqXcu2rdu3cOPKnUu3rt27ePPq3cu3r9+/gAMLHky4sOHDiBMrXsy4sePHkCNLnky5suXLmDNr3sy5s+fPoEOLHk26tOnTqFOrXs26tevXsGPLnk27tu3buHPr3s27t+/fwIMLH068uPHjyJMrX868ufPn0KNLn069uvXr2LNr3869u/fv4MOL/x9Pvrz58+jTq1/Pvr379/Djy59Pv779+/jz69/Pv7///wAGKOCABBZo4IEIJqjgggw26OCDEEYo4YQUVmjhhRhmqOGGHHbo4YcghijiiCSWaOKJKKao4oostujiizDGKOOMNNZo44045qjjjjz26OOPQAYp5JBEFmnkkUgmqeSSTDbp5JNQRinllFRWaeWVWGap5ZZcdunll2CGKeaYZJZp5plopqnmmmy26eabcMYp55x01mnnnXjmqeeefPbp55+ABirooIQWauihiCaq6KKMNuroo5BGKumklFZq6aWYZqrpppx26umnoIYq6qiklmrqqaimquqqrLbq6quwxv8q66y01mrrrbjmquuuvPbq66/ABivssMQWa+yxyCar7LLMNuvss9BGK+201FZr7bXYZqvtttx26+234IYr7rhnEmCAAQSQixABI1gABiGrqILGF2Fw0ABPBrxhxQ1VHKBDEiwoMGYIRjhARxBrWPGGATQlcIUDnkABwMQUA0DJDSpsgNMFNgBRccVAZEGDlw3gsYjHHwOQyQswxCQGCJKknDIUOpQBQcN2oCwzxUAcMMaWLmSyM8gVvDREFUPLTIkg97rMQNIpA+FCljfoDDUQHmi8kgqWQC1zHGCUABMNVns9MRCAXFlD2V5XojVKhXRtdspxtJFuSymwPTcQE1T/WfXcH1tyt0kpIA14yp0U0pIBixwe9QpTcqH33GicZEAFjsscRMsrEZJ5ypZIacDTn58thklHXFJ6xVAIshIMkx8OBBdRWrE6xYmUBMEft1ecyNsnOdA7xYtEWcnwQAAP0genDD9xHHuoFLvjQKTw5AfTA077SHtI7DwAYKQkRvaHt/GkIt/fQFIb309sA8MnudA+ADU86cj3HpDEe/ufdIDS/t8DwpNe8L3iiQQCBGyfKSSAkkjMT4BOWkMBR0KABH5vgSjRwQOfRIbvhW4kIJgfKpQHwg06iQvfiwRJ+jC/GyQAJYKY3wGeNALymW1qI7GA95zniJSQYH7he1Lj/3oHhAeQZASe+B4UhpASA9jQbEC4A5SSMLwZksQAnnNeFaagEgc6D4JPKoHQVgeELphkDzEbXh9Wkjfn9S1KWniizExwkhJYcHVVGAFL6DA8BtxMSlEoXSXEdpIiFOB2ktjeShQgR5kBoQxUMgACMseAEKiEC2nMHBS+8MKWXKGRRLNSAqogx0roUSUEEEQmAQeFP5BQJS4AJQCAsIYsOYJ8QNBB01ZiABd44HCSSMIrVzKERgKBDFt6ABomB4QakCAmR7jBDocGhRqooJMykUAWcLmIkXXJYWSogQAscQBCKGKYLNkAF3Sguq9FwQo/uwkNEMDMTBgBVArggSAc8P+KT3yCFWvAAwsYuBMJcMEOlQACEDJBhwlYklQEaEAHKFCCwanrohjNqEY3ytGOevSjIA2pSEdK0pKa9KQoTalKV8rSlrr0pTCNqUxnStOa2vSmOM2pTnfK05769KdADapQh0rUohr1qEhNqlKXytSmOvWpUI2qVKdK1apa9apYzapWt8rVrnr1q2ANq1jHStaymvWsaE2rWtfK1ra69a1wjatc50rXutr1rnjNq173yte++vWvgA2sYAdL2MIa9rCITaxiF8vYxjr2sZCNrGQnS9nKWvaymM2sZjfL2c569rOgDa1oR0va0pr2tKhNrWpXy9rWuva1sI2tbGdL29o62va2uM2tbnfL29769rfADa5wh0vc4hr3uMhNrnKXy9zmOve50I2udKdL3epa97rYza52t8vd7m4pIAAh+QQJBACwACwAAAAA9AH0AQAI/wBhCRxIsKDBgwgTKlzIsKHDhxAjSpxIsaLFixgzatzIsaPHjyBDihxJsqTJkyhTqlzJsqXLlzBjypxJs6bNmzhz6tzJs6fPn0CDCh1KtKjRo0iTKl3KtKnTp1CjSp1KtarVq1izat3KtavXr2DDih1LtqzZs2jTql3Ltq3bt3Djyp1Lt67du3jz6t3Lt6/fv4ADCx5MuLDhw4gTK17MuLHjx5AjS55MubLly5gza97MubPnz6BDix5NurTp06hTq17NurXr17Bjy55Nu7bt27hz697Nu7fv38CDCx9OvLjx48iTK1/OvLnz59CjS59Ovbr169iza9/Ovbv37+DDi/8fT768+fPo06tfz769+/fw48ufT7++/fv48+vfz7+///8ABijggAQWaOCBCCao4IIMNujggxBGKOGEFFZo4YUYZqjhhhx26OGHIIYo4ogklmjiiSimqOKKLLbo4oswxijjjDTWaOONOOao44489ujjj0AGKeSQRBZp5JFIJqnkkkw26eSTUEYp5ZRUVmnllVhmqeWWXHbp5ZdghinmmGSWaeaZaKap5ppstunmm3DGKeecdNZp55145qnnnnz26eefgAYq6KCEFmrooYgmquiijDbq6KOQRirppJRWaumlmGaq6aacdurpp6CGKuqopJZq6qmopqrqqqy26uqrsMb/KuustNZq66245qrrrrz26uuvwAYr7LDEFmvsscgmq+yyzDbr7LPQRivttNRWa+212Gar7bbcduvtt+CGG2QDIcyAQQx9QAIHCR2IW5ABXZjRRBwA1GsvFBG8YEG74pZxA732BixwE0Q08O0DT/Qg8MILo/DGTQaQAAkaW9RgBw5XKGAmAQbQVMQWDIcsMB9h0DTGCzKELMMWR4D5QRs16CHDzFh8wcFLNGAh8s726qFFTAkQkjLPMtTwAZcrbDH0wjIsUAhLd+jM89Q9YPBSCgpPba8MZ2g5ydIiy4CCwShlALLWU/NxRUtHgI22DHhcSQAKbu/MxwMoVYA22lts/7BSCHW/LYeVKOxtLx8alyRC1obzjINKBjDeeL0yiEHlF4FPvUVJBKwx+dQLHI0SCJ8LXMCUgJcuQ8kjkQBw6SK3gdIUmRsuAxxSFg57DwSMlATsPAeRwElPAB9wD1FKUDvaM4hkQBDGixyH5SYtb3sIUBIRvQ4ifSBJ9CKzTlIK1hsOCZS6A6+HSEeAL3ISJp3hfr1BQCm56ol/NMf8DL9gkhn8kwGUyqc1vIEEA/xbmA1M4rn5CfBJBJzaFEIihwQK7AYmsUMA7Rc9GfDrI/KzoL38VxK9ORBK0DPe+kJSBhHaywwm0d78agAlSETPCSJhwussaLWScIB/QoDSB/8iKDLchaQBTXBhHEhgEgMQkWgriFISd9cxkZjQgk3IH0ka2EEpkeCJAZPBz0ZCAyiIEH4nSV30BiclB5SuCiVJQPrmxwc1pOQG0esBBKZEACpMrgcGJIkFzMi/P6hEAWAUmAzWRqUGVMFwPUjBSQyABv5h4QIrEUEiKfeFKxlgDeWTQRUCaZIQRMB9UOgaS86QSBk4QEtlWEDtesBGlZyAD+BLwh5bMoMnygCNWyoCCPgwNBnowQZ76F1LzoBL4FVgeC+RgNKmJoMetAxMBuhAB6AZEwssoHR6+AE3YXKEKmTOmOLDFAfSMLkIGLEmEoADIYhpzBvIgQmeKgEG/Kj/NT6YQXTg2kAYbvA9hsVhC3jAnrsEQgAYnKANFXDAC0AAhjmIgWwLzahGN8rRjnr0oyANqUhHStKSmvSkKE2pSlfK0pa69KUwjalMZ0rTmtr0pjjNqU53ytOe+vSnQA2qUIdK1KIa9ahITapSl8rUpjr1qVCNqlSnStWqWvWqWM2qVrfK1a569atgDatYx0rWspr1rGhNq1rXyta2uvWtcI2rXOdK17ra9a54zate98rXvvr1r4ANrGAHS9jCGvawiE2sYhfL2MY69rGQjaxkJ0vZylr2spjNrGY3y9nOevazoA2taEdL2tKa9rSoTa1qV8va1rr2tbCNrWxnS9vaPNr2trjNrW53y9ve+va3wA2ucIdL3OIa97jITa5yl8vc5jr3udCNrnSnS93qWve62M2udrfL3e56lzwBAQAh+QQJBACwACwAAAAA9AH0AQAI/wBhCRxIsKDBgwgTKlzIsKHDhxAjSpxIsaLFixgzatzIsaPHjyBDihxJsqTJkyhTqlzJsqXLlzBjypxJs6bNmzhz6tzJs6fPn0CDCh1KtKjRo0iTKl3KtKnTp1CjSp1KtarVq1izat3KtavXr2DDih1LtqzZs2jTql3Ltq3bt3Djyp1Lt67du3jz6t3Lt6/fv4ADCx5MuLDhw4gTK17MuLHjx5AjS55MubLly5gza97MubPnz6BDix5NurTp06hTq17NurXr17Bjy55Nu7bt27hz697Nu7fv38CDCx9OvLjx48iTK1/OvLnz59CjS59Ovbr169iza9/Ovbv37+DDi/8fT768+fPo06tfz769+/fw48ufT7++/fv48+vfz7+///8ABijggAQWaOCBCCao4IIMNujggxBGKOGEFFZo4YUYZqjhhhx26OGHIIYo4ogklmjiiSimqOKKLLbo4oswxijjjDTWaOONOOao44489ujjj0AGKeSQRBZp5JFIJqnkkkw26eSTUEYp5ZRUVmnllVhmqeWWXHbp5ZdghinmmGSWaeaZaKap5ppstunmm3DGKeecdNZp55145qnnnnz26eefgAYq6KCEFmrooYgmquiijDbq6KOQRirppJRWaumlmGaq6aacdurpp6CGKuqopJZq6qmopqrqqqy26uqrsMb/KuustNZq66245qrrrrz26uuvwAYr7LDEFmvsscgmq+yyzDbr7LPQRivttNRWa+212Gar7bbcduvtt+C+qIAYM6jgxhBvPBAuQiEwUsAAAMQr7wA92CAFAevCQkMN8Mrr778eCIKvtxLQ0e+/CPtbgBTdntBDwhD/O0AFNhlwRwsvBJHIGj7QoMCmExwc8cgD6DAwTGNoILK/AwTRhZgNMPFGDmJ0AFPII+fsrw4wJeDAygkPkMgHXSbgQhUiD1CAEBuwNAPQOkM8gAYupeBB1PNysaULV0c8wCMnm7RB11jrPIAKLB0Bdc4DCIElAUqs/W8VGaCkRNlle/BxSkzI/802BlYSsAXefKhbUg5+4/3vEykZwIfiEotRpSGQH2BASYlAjvUAFKD0hOb/HkClColDjARJY5QOOgBWnPSA6mwrIiUBZCs+wBgj4bB61AicFMju/vIhpSK7ny4SFsCzXXdJsJvNRJSZr95D2B010DzoLJSUwvU5CwKlAdwj/DxIFySvcwwlcWG+vCZAOUXyhYTEw/ojv1ASI/QDMACUYiTvQkgzyB/ElFASNuRvf0/qH/D+B5IAChBhPCPJGg4IpQ8kbwghOcIDEcaGkpiBgk9KQPj+lYKQhGCD//pBSYyQv0REqQa7G8DlQKKAEeLNAiVZQf76ECU37K6DIkEACv/jNQCikQR86xuAGqKUgIdpbgCSE0kFhggAD5zEgOZDYJQwMEIgimQFNowaI07SN/MBbkomgBwfGlCSA6BwABdAiQ2S5wEIUKkByCtbD0JgEguEcWQEREkNY0gDKzUgEapDwPhMAkMB3k4lIrDh17LkA79NjY0oEcMfETYAQLCEC+EbgPGyRAEw8CFpPUBCHFdihU36KwgueRreOvmlB+RgCBaggRFdggRXAuAAJXhJBoJQugHw4WWWUhnwsNC0mByBX1LrgRs0BQhJBiGYNMmAIhyAgAHQywYYGEGnRCBE2/ngWwQQghPNZoMprCsBKoBm0BCAA8PlSyANKIIbvoD/hBeYYQI0WN49B0rQghr0oAhNqEIXytCGOvShEI2oRCdK0Ypa9KIYzahGN8rRjnr0oyANqUhHStKSmvSkKE2pSlfK0pa69KUwjalMZ0rTmtr0pjjNqU53ytOe+vSnQA2qUIdK1KIa9ahITapSl8rUpjr1qVCNqlSnStWqWvWqWM2qVrfK1a569atgDatYx0rWspr1rGhNq1rXyta2uvWtcI2rXOdK17ra9a54zate98rXvvr1r4ANrGAHS9jCGvawiE2sYhfL2MY69rGQjaxkJ0vZylr2spjNrGY3y9nOevazoA2taEdL2tKa9rSoTa1qV8va1rr2tbCNrWxnS9vaHNr2trjNrW53y9ve+va3wA2ucIdL3OIa97ibCggAIfkECQQAsAAsAAAAAPQB9AEACP8AYQkcSLCgwYMIEypcyLChw4cQI0qcSLGixYsYM2rcyLGjx48gQ4ocSbKkyZMoU6pcybKly5cwY8qcSbOmzZs4c+rcybOnz59AgwodSrSo0aNIkypdyrSp06dQo0qdSrWq1atYs2rdyrWr169gw4odS7as2bNo06pdy7at27dw48qdS7eu3bt48+rdy7ev37+AAwseTLiw4cOIEytezLix48eQI0ueTLmy5cuYM2vezLmz58+gQ4seTbq06dOoU6tezbq169ewY8ueTbu27du4c+vezbu379/AgwsfTry48ePIkytfzry58+fQo0ufTr269evYs2vfzr279+/gw4v/H0++vPnz6NOrX8++vfv38OPLn0+/vv37+PPr38+/v///AAYo4IAEFmjggQgmqOCCDDbo4IMQRijhhBRWaOGFGGao4YYcdujhhyCGKOKIJJZo4okopqjiiiy26OKLMMYo44w01mjjjTjmqOOOPPbo449ABinkkEQWaeSRSCap5JJMNunkk1BGKeWUVFZp5ZVYZqnlllx26eWXYIYp5phklmnmmWimqeaabLbp5ptwxinnnHTWaeedeOap55589unnn4AGKuighBZq6KGIJqrooow26uijkEYq6aSUVmrppZhmqummnHbq6aeghirqqKSWauqpqKaq6qqsturqq7DG/yrrrLTWauutuOaq66689urrr8AGK+ywxBZr7LHIJqvsssw26+yz0EYr7bTUVmvttdhmq+223Hbr7bfghhukBIXgcAgdTkRixhkhQCAuQSXIQUUBANRrr70LmHGBuATgscC9AANcgA0PfHsHFQEnLLAcNxHAARFI6ECHBm2IUAKnRNCr8Mb1FsCGuzJ9gIjGARegQw6Z9kEyxxzrQABMBjyxssIF0AHDlwrQ0EYgT+BRiAQvGTEzyxvb8FIIWBB9bwFwcJmCDUMXsAUNLHEwtNIJF4BHSzxczXIBbWQJwSRedxyJAilBgDDWShcgxkojlP31IFcmgALWVHyAUhtss/8dhEoERNB3ySlYSUffEXRgUgL/Dk50ASKkZIbjAddQJSNyJ4yCSWdQrjQdKD2Qedt+THnB6CVbUFITnj+ewUmMtA5wBFNq4DkVJHWAuuelm7T74yNEmcDvAhcukgiyE12HSSEQzzIGUb4huyAjCZI8y5aXBMf19yoRZRiyszESItxvXIBJgJTfcZR4yP63SIeon/XLJNUh//lQtt/6+yHZIH/J9BuJ7dSHvycRQXaHGAkS/icwkzjiflHigey0MBK+MdBeuCsJ+NQHOiiVwHn2KsAKRrKHC9orgSVRg/woGCX/UY52I5EACNkWBpMQYIZZe1uUxADCApyhJGtjYAH/9GYS+3GvgFEi3+C2YBILMrAJKIkb9+g2JQIkom9YKFhJKIBDlikiJWy4HhZANiUFsE5pWNChSQLBQCqQ0SQflB3krmQANsitAEEAGkpKkDQClmElXcBhAcCgJR44IWpUyANLhtDFgC2PJXDoYSC69ABFmMEGNkDEIILnEjM00l5NMIBLykA8rVlKA5+kguJekgEdjK4AEUDZpQLRxUSsMiY8CILXCrCAOWwqDD1EQgBnkgE/PGFevGTDIPbVqQdADWsFoALVwpUCO3IMj4V410Aa0AVA0AELBSgAFhKBBAvoUZvoTKc618nOdrrznfCMpzznSc962vOe+MynPvfJ989++vOfAA2oQAdK0IIa9KAITahCF8rQhjr0oRCNqEQnStGKWvSiGM2oRjfK0Y569KMgDalIR0rSkpr0pChNqUpXytKWuvSlMI2pTGdK05ra9KY4zalOd8rTnvr0p0ANqlCHStSiGvWoSE2qUpfK1KY69alQjapUp0rVqlr1qljNqla3ytWuevWrYA2rWMdK1rKa9axoTata18rWtrr1rXCNq1znSte62vWueM2rXvfK17769a+ADaxgB0vYwhr2sIhNrGIXy9jGOvaxkI2sZCdL2cpa9rKYzaxmN8vZznr2s6ANrWhHS9rSmva0qE2talfL2taSJyAAIfkECQQAsAAsAAAAAPQB9AEACP8AYQkcSLCgwYMIEypcyLChw4cQI0qcSLGixYsYM2rcyLGjx48gQ4ocSbKkyZMoU6pcybKly5cwY8qcSbOmzZs4c+rcybOnz59AgwodSrSo0aNIkypdyrSp06dQo0qdSrWq1atYs2rdyrWr169gw4odS7as2bNo06pdy7at27dw48qdS7eu3bt48+rdy7ev37+AAwseTLiw4cOIEytezLix48eQI0ueTLmy5cuYM2vezLmz58+gQ4seTbq06dOoU6tezbq169ewY8ueTbu27du4c+vezbu379/AgwsfTry48ePIkytfzry58+fQo0ufTr269evYs2vfzr279+/gw4v/H0++vPnz6NOrX8++vfv38OPLn0+/vv37+PPr38+/v///AAYo4IAEFmjggQgmqOCCDDbo4IMQRijhhBRWaOGFGGao4YYcdujhhyCGKOKIJJZo4okopqjiiiy26OKLMMYo44w01mjjjTjmqOOOPPbo449ABinkkEQWaeSRSCap5JJMNunkk1BGKeWUVFZp5ZVYZqnlllx26eWXYIYp5phklmnmmWimqeaabLbp5ptwxinnnHTWaeedeOap55589unnn4AGKuighBZq6KGIJqrooow26uijkEYq6aSUVmrppZhmqummnHbq6aeghirqqKSWauqpqKaq6qqsturqq7DG/yrrrLTWauutuOaq66689urrr8AGK+ywxBZr7LHIJqvsssw26+yz0EYr7bTUVmvttdhmq+223Hbr7bfghkukAQ2UYIC4Cklwxg0ICAAAAAJ44EUbKaA7UA5BuPvuvvwKcMAZEIT7QCP68mswvwdIgZMEeUyiQw1VmIAEESF0OocHB2dssACI1ESDEgVvvEMY52IKRsgaayyACSW/9AHIKfNbBQ2X4oFyzBqbELBLhWCMc79gdEnAHi8cIIAACNwARwMu5XHzzxm/4FIYT+MsAAhbhoGAymAQsJIEPkNt9Rws7VH1zwI4gmUCBONcBQwqKSG22AiUoNIUYc/d7xBWJv+wg9gefIASB2frzW8SKhlieMYH2E2lDnof0DJJci+OswcJoJRD4XP3QeUcnB8ciEkUhG453yfZYXnGmE+5teECZFDSEKv/fMNJpdd+8B5SdmH6wVqURIjuMXtw0gzEGzyJlIGsXkNJWSSv8gYmgSH9vlFIWcPqAng90u+W11sSGte/232Ur1vueEgGgL94ESaZUP67TEOZt+Hrg9T+/AbnED//+WvS3yx3vu/xj19qMInqylfAJyFidVUoyQEOuC8JmMQR84tglGiwOh+URHEUbOBI/DA/rEWJAOmbmwAeUJIzUBAAJjiJBNyHMz9MaRA0rINJHkBDsYUBJY24ngD/AvikIOgNAfUrSRQOKIAOoMRs0mNElRQwQah5QHwmKUMPcabDlMiPeB6Q3RSjwLkDVCwl22OgBVOSgi3uSwBEyFIb7vdGRCQRJWpw48EE4MGV4LB2UtNSA+agg3bFywuQoF5L+qBHfgXBJTaznBImtyUDUNIlhGgkAA6ggJdAwn0C0MAlIYUGPR5AjC95Qxp/5oEfYsoRPVwZEVtigDBk4WwCAAMFNkWDKopNAG3ACQmEoARDeiAIjGBB5jpFAAy0y2p/UOROCDDKT+UABM98owdukIdZoqsBMAhBCj7QSXuZ85zoTKc618nOdrrznfCMpzznSc962vOe+MynPvfJ9c9++vOfAA2oQAdK0IIa9KAITahCF8rQhjr0oRCNqEQnStGKWvSiGM2oRjfK0Y569KMgDalIR0rSkpr0pChNqUpXytKWuvSlMI2pTGdK05ra9KY4zalOd8rTnvr0p0ANqlCHStSiGvWoSE2qUpfK1KY69alQjapUp0rVqlr1qljNqla3ytWuevWrYA2rWMdK1rKa9axoTata18rWtrr1rXCNq1znSte62vWueM2rXvfK17769a+ADaxgB0vYwhr2sIhNrGIXy9jGOvaxkI2sZCdL2cpa9rKYzaxmN8vZznr2s6ANrWhHS9rSmva0qE2taleLnoAAACH5BAkEALAALAAAAAD0AfQBAAj/AGEJHEiwoMGDCBMqXMiwocOHECNKnEixosWLGDNq3Mixo8ePIEOKHEmypMmTKFOqXMmypcuXMGPKnEmzps2bOHPq3Mmzp8+fQIMKHUq0qNGjSJMqXcq0qdOnUKNKnUq1qtWrWLNq3cq1q9evYMOKHUu2rNmzaNOqXcu2rdu3cOPKnUu3rt27ePPq3cu3r9+/gAMLHky4sOHDiBMrXsy4sePHkCNLnky5suXLmDNr3sy5s+fPoEOLHk26tOnTqFOrXs26tevXsGPLnk27tu3buHPr3s27t+/fwIMLH068uPHjyJMrX868ufPn0KNLn069uvXr2LNr3869u/fv4MOL/x9Pvrz58+jTq1/Pvr379/Djy59Pv779+/jz69/Pv7///wAGKOCABBZo4IEIJqjgggw26OCDEEYo4YQUVmjhhRhmqOGGHHbo4YcghijiiCSWaOKJKKao4oostujiizDGKOOMNNZo44045qjjjjz26OOPQAYp5JBEFmnkkUgmqeSSTDbp5JNQRinllFRWaeWVWGap5ZZcdunll2CGKeaYZJZp5plopqnmmmy26eabcMYp55x01mnnnXjmqeeefPbp55+ABirooIQWauihiCaq6KKMNuroo5BGKumklFZq6aWYZqrpppx26umnoIYq6qiklmrqqaimquqqrLbq6quwxv8q66y01mrrrbjmquuuvPbq66/ABivssMQWa+yxyCar7LLMNuvss9BGK+201FZr7bXYZqvtttx26+234IaLqAJizDDIBFZg4EcRGUAwqgEX0JAHHDOIocBOCXThSBOUQAHAvwBAcQkqDgyxgacNhBHAEgADvEQoSUxhEwFS2HBJwxgDHEcTLnSgqQGTMJwxxkt48cFMU0zSycgsAxCHDjlgyoIrLY+8xBcxFeFFzTUP4Ia7lJIhMs8kY2GASzQsQHTNnQhCwKRoDL00xnocvVIRSk/d8iUucDnFHSSM8TRMjEitdcMBrDTFzme3LAMNWIrRyBJDL0EF3C1JYXbb/y7/4UBKEDDiL98sRyFBlQbMzfISCxysEgGlEG7zHSjRQInkLEPRB5UdLEI0J2qolATmIw9wkgEvkM5yABdISQAoU3PyAEoGcKI6yTGXVMTlt2MMhSBSRnK26Sfl0TvGJpjkw/EZm1AClCPsXfMSfpy0A/MOjy1SAyZg3zAlK0CJBt96nCT97eGPNIIn3gMMxRxQ2t72Eh6TJMH5qrtBkgiYtA8wGE+iAP5qlruRkMB/AJgESeAwOP/9zUkjkFz1SEIDBK6BJC5A4L9sADQmRZBweSiJFBBoA5IYQYMAsIH2lrSBAbasgCJ5AwKfQJI5oFADUHKhzShQkikgEAMkkUIc/zSYBCgJr22gMAkBdEi4N5AkBaLQYBiglAImOgx+JglA+5aQAJIooAkI7EQRokSHsyXxJCf0HhZMwggE7qB+T0pAJqa2hDGgpARWpOMMTEIDSfgPgFLKwBx5xgkYmiR1zMvESUrQiPZpIn1SakAUzreEAcBgJQqQ3+2WsMeTDMGP2CNDB6eUgx1IbQk9GIJLBpHHmnkhJQ0gBPYWwIQsGSAEIqCBGhoQEx20cmShsBpKxJC1210CDpKiwi8bVorDrWQGMrhdHMAgTEiZYJkACEUGXDIH2GEuDox4HqV80Mol0KGaLBkCHyR3CR+Is1JTMCXRlrAIKcyEBJEY4tmwkP+HFVpqBA7ghPSWEAW80aQDRqCCPnk2AEe0zlMwmEEMyFABMMBBDP6siQTOYINWLNR9lPBCG8QgLoLAawaCIAMSHFCBPsBhBfcqqUxnStOa2vSmOM2pTnfK05769KdADapQh0rUohr1qEhNqlKXytSmOvWpUI2qVKdK1apa9apYzapWt8rVrnr1q2ANq1jHStaymvWsaE2rWtfK1ra69a1wjatc50rXutr1rnjNq173yte++vWvgA2sYAdL2MIa9rCITaxiF8vYxjr2sZCNrGQnS9nKWvaymM2sZjfL2c569rOgDa1oR0va0pr2tKhNrWpXy9rWuva1sI2tbGdL29pe2va2uM2tbnfL29769rfADa5wh0vc4hr3uMhNrnKXy9zmOve50I2udKdL3epa97rYza52t8vd7nr3u+ANr3jHS97ymve86E2vetfL3va6973wja9850vf+tr3vmUKCAAh+QQJBACwACwAAAAA9AH0AQAI/wBhCRxIsKDBgwgTKlzIsKHDhxAjSpxIsaLFixgzatzIsaPHjyBDihxJsqTJkyhTqlzJsqXLlzBjypxJs6bNmzhz6tzJs6fPn0CDCh1KtKjRo0iTKl3KtKnTp1CjSp1KtarVq1izat3KtavXr2DDih1LtqzZs2jTql3Ltq3bt3Djyp1Lt67du3jz6t3Lt6/fv4ADCx5MuLDhw4gTK17MuLHjx5AjS55MubLly5gza97MubPnz6BDix5NurTp06hTq17NurXr17Bjy55Nu7bt27hz697Nu7fv38CDCx9OvLjx48iTK1/OvLnz59CjS59Ovbr169iza9/Ovbv37+DDi/8fT768+fPo06tfz769+/fw48ufT7++/fv48+vfz7+///8ABijggAQWaOCBCCao4IIMNujggxBGKOGEFFZo4YUYZqjhhhx26OGHIIYo4ogklmjiiSimqOKKLLbo4oswxijjjDTWaOONOOao44489ujjj0AGKeSQRBZp5JFIJqnkkkw26eSTUEYp5ZRUVmnllVhmqeWWXHbp5ZdghinmmGSWaeaZaKap5ppstunmm3DGKeecdNZp55145qnnnnz26eefgAYq6KCEFmrooYgmquiijDbq6KOQRirppJRWaumlmGaq6aacdurpp6CGKuqopJZq6qmopqrqqqy26uqrsMb/KuustNZq66245qrrrrz26uuvwAYr7LDEFmvsscgmq+yyzDbr7LPQRivttNRWa+212Gar7bbcduttkwlkwAQHJKQAQwnfKnTBIC/s0EkcUMQryQFKCMFDAukKZEAZNugBwL8AB/xvHFG0sMG3POgAhcAMM3zAIPhq28AP/jZsccBQRBLCpgnwoMUaJkRhyA8sUEDTFJFcrLLAB8yAKQk6MGAxAwfkEdMIXqysM8B6zFHpGDXIvDIDerDg0hQ576y0HidM2oLQSjOwBgErNWCI0lgDIMAdkSIBddZZNKASDllnHUQHj3pddsAHGIASCZasjbUQV6pBhBkVQPIG1S9h//C13DqcRMDVcivdQwpUElHJ34v8wPdKU/wtNwNhmETDwoUrbYaUHUQgOcCWMMFS0pkDvEjEI71QutICPAClAnGvvMjGKanxeeF0jzRFD6srXfmTOyyNuklr9B7wJiTBYfzONjx5xu0NP4ESAYss/y8DXIuEhPUrI2BykxVHLbZJK3D/Lw4iERCF+RfHsUKTF0BvcSEnhcG+FyJ1IAr7F/vRpPJlq8BJzMA+PYgEBpLgn8Uw0KQYrK0RJyme+RYhEibEQYENi0EDHxhB9lEwJBbEIMM0yKQ5rE2AJnkC+yohkg9gQoQCa0GTmCC/hjXNJERgXw1EsgFKwDBgcHBS+P92xgB0maQI7PuCSAxQgx/+CwpFcNIgahgwJKAkAVQsWxdS50QAUEICT4qA0ioxvpOYgHuLeBxIcuhEHahxSRQYosUWwQGVHCGLSkOhSELwwh+2IUobQAD09FDHlRxgeQz4nkggoIMf6oF2UWpD9QS2iAoMLyUcwKPKGIC+ksABcxhcQ5Ug8IYYOOAFOLjCJVfyBU1aLAsnacD6MLiJIziqEa4UmB7QdpITXFCBVnyUCXL5Lz24DiUQcIACD3CBrrmSATXgZUoe0ETzbcJ/krqCHrK4iD+25A0B4B4UvEmpMwjgdgzYxCMUAJMyCGB5UHAcpj4QhjUcQA+V6IEJhFD/SJnwQIyrq4QVIICtCxgClGs7wA2zlQAiHLJslXjCB7z1ACE8VGeWcEAU89WBEyBhB33EGAIM0YJm5qsgDbgADeYwCAycoRBiUORJZ0rTmtr0pjjNqU53ytOe+vSnQA2qUIdK1KIa9ahITapSl8rUpjr1qVCNqlSnStWqWvWqWM2qVrfK1a569atgDatYx0rWspr1rGhNq1rXyta2uvWtcI2rXOdK17ra9a54zate98rXvvr1r4ANrGAHS9jCGvawiE2sYhfL2MY69rGQjaxkJ0vZylr2spjNrGY3y9nOevazoA2taEdL2tKa9rSoTa1qV8va1rr2tbCNrWxnS9vaXdr2trjNrW53y9ve+va3wA2ucIdL3OIa97jITa5yl8vc5jr3udCNrnSnS93qWve62M2udrfL3e5697vgDa94x0ve8pr3vOhNr3rXy972uve98I2vfOdL3/ra11MBAQAh+QQJBACwACwAAAAA9AH0AQAI/wBhCRxIsKDBgwgTKlzIsKHDhxAjSpxIsaLFixgzatzIsaPHjyBDihxJsqTJkyhTqlzJsqXLlzBjypxJs6bNmzhz6tzJs6fPn0CDCh1KtKjRo0iTKl3KtKnTp1CjSp1KtarVq1izat3KtavXr2DDih1LtqzZs2jTql3Ltq3bt3Djyp1Lt67du3jz6t3Lt6/fv4ADCx5MuLDhw4gTK17MuLHjx5AjS55MubLly5gza97MubPnz6BDix5NurTp06hTq17NurXr17Bjy55Nu7bt27hz697Nu7fv38CDCx9OvLjx48iTK1/OvLnz59CjS59Ovbr169iza9/Ovbv37+DDi/8fT768+fPo06tfz769+/fw48ufT7++/fv48+vfz7+///8ABijggAQWaOCBCCao4IIMNujggxBGKOGEFFZo4YUYZqjhhhx26OGHIIYo4ogklmjiiSimqOKKLLbo4oswxijjjDTWaOONOOao44489ujjj0AGKeSQRBZp5JFIJqnkkkw26eSTUEYp5ZRUVmnllVhmqeWWXHbp5ZdghinmmGSWaeaZaKap5ppstunmm3DGKeecdNZp55145qnnnnz26eefgAYq6KCEFmrooYgmquiijDbq6KOQRirppJRWaumlmGaq6aacdurpp6CGKuqopJZq6qmopqrqqqy26uqrsMb/KuustNZq66245qrrrrz26uuvwAYr7LDEFmvsscgmq+yyzDbr7LPQRivttNRWa+212Gar7bbcdosjAQpk8EAHCXjLUAeFaFDAAAC0C8AAHpiAwQjmFiQCHey6q6++AxTQQrne8lBFvvsWrG8PVkCwbQKHEGzww+4ecEe2YiAA8cX7DmCFpwYAXBMNPWAssrsDPIEpBDyYgcUALA+AwAt+lBATDQ6PjPEADlRqgBUhQ4zzAy6l0LPNNg8AyKQs8FG0ECwlUADRUL8rRaSM1HyzCR6f9ELUUfcgs6MaWD1yFQ2gRILYXF+cc6NfoD1yIijVkHbUA3xAJQxW1OBBD1Uk/5ECTFK4PfIAZpj0huBzG/yClAm8YPUAdGTQEgEWJ97uAH+TZIjlUA9Q9pMZPA2xBxyw1ALn7tJBUgOIo66vCk86LbIHQKvkgevv2i0SDbjbrMOTSNgchEoctE60DyOZ0fvIPSjMZAbGv1tESmAsX8VIci8vcu1LEgE1EiklsvwABog0tPYQv9GkDlDzkdL5rnPvkQHR935Ckwd07rxJ9dtML0gKQJ/IuIA//aGkfyP730cCKMCLuaFJdGhfSm63PPl1JAEIRJ0fmnQ6omkgJdnD3QCy5pEMck4ETXpA9AaQg5R8YXkFGEn+Gvgw3TFJAzaDW0p4sLwvjGRrNCwY+f+c1IDKXawHNjwJAeCXOMyNxA9BLFgNoDQF0T2sB+pbSfVcN8WRQC+K+ppAlErQMCEGYQotKQEFLcfCkogPjO+yoJMuAIYq7O0AZlgBTLhgQn2xwSR+6GPUhscoxyXuAOUziRFpOIAsMsoEc+ODHEWiAkEK71EQsAECsSC58AVxABeI1ARW+IJEpuQDTBRhHyaVgbBdbABbmFhLFGFJiP2uUh1wgQl6QLABVEEIY4iJEGopRVNeSgESeAAFCFATMBDTXTX4HLWIQMwBKIGZ1xKDFdOmsW0RAAcZHIAJkqitDiQhlQYbgA5KVy9YEIAGSOCD2CDnAgq08yAKYMIRZnD/AhrcIQP7u6dAB0rQghr0oAhNqEIXytCGOvShEI2oRCdK0Ypa9KIYzahGN8rRjnr0oyANqUhHStKSmvSkKE2pSlfK0pa69KUwjalMZ0rTmtr0pjjNqU53ytOe+vSnQA2qUIdK1KIa9ahITapSl8rUpjr1qVCNqlSnStWqWvWqWM2qVrfK1a569atgDatYx0rWspr1rGhNq1rXyta2uvWtcI2rXOdK17ra9a54zate98rXvvr1r4ANrGAHS9jCGvawiE2sYhfL2MY69rGQjaxkJ0vZylr2spjNrGY3y9nOevazoA2taEdL2tKa9rSoTa1qV8va1rr2tbCNrWxnS9vaGNr2trjNrW53y9ve+va3wA2ucIdL3LcGBAAh+QQJBACwACwAAAAA9AH0AQAI/wBhCRxIsKDBgwgTKlzIsKHDhxAjSpxIsaLFixgzatzIsaPHjyBDihxJsqTJkyhTqlzJsqXLlzBjypxJs6bNmzhz6tzJs6fPn0CDCh1KtKjRo0iTKl3KtKnTp1CjSp1KtarVq1izat3KtavXr2DDih1LtqzZs2jTql3Ltq3bt3Djyp1Lt67du3jz6t3Lt6/fv4ADCx5MuLDhw4gTK17MuLHjx5AjS55MubLly5gza97MubPnz6BDix5NurTp06hTq17NurXr17Bjy55Nu7bt27hz697Nu7fv38CDCx9OvLjx48iTK1/OvLnz59CjS59Ovbr169iza9/Ovbv37+DDi/8fT768+fPo06tfz769+/fw48ufT7++/fv48+vfz7+///8ABijggAQWaOCBCCao4IIMNujggxBGKOGEFFZo4YUYZqjhhhx26OGHIIYo4ogklmjiiSimqOKKLLbo4oswxijjjDTWaOONOOao44489ujjj0AGKeSQRBZp5JFIJqnkkkw26eSTUEYp5ZRUVmnllVhmqeWWXHbp5ZdghinmmGSWaeaZaKap5ppstunmm3DGKeecdNZp55145qnnnnz26eefgAYq6KCEFmrooYgmquiijDbq6KOQRirppJRWaumlmGaq6aacdurpp6CGKuqopJZq6qmopqrqqqy26uqrsMb/KuustNZq66245qrrrrz26uuvwAYr7LDEFmvsscgmq+yyzDbr7LPQRivttNRWa+212Gar7bbcduttkxmQcMIZYeRBwwcGfIuQASwc4oEAAMQrLwACRNFCBuoKpAAgHszrr78CKLHCt1rA++/B8wpgyAbbPlCDwQhHHK8HeWR7RL8SZxyvAJNwSoEaXRzBgQQ1DQGxxhkL8AKmTJCBwMkCeHDIETEdcTLKKf9R6QUm3AxwFlK4JAHGOOMsgByTFmz0C+muFEXRUNPLRKQa+JxxFCWohIHVUUccBaR1cJ3xDk2b1ADRXaMsQMVVpgBJIEhoQYJMkIitsSEoCZF21AdQ/3nCywkLgMFLMNitsQBwmAQBAntDLUAXUlaNsAAmENCSEo3Li4DlJB2ROdSHRBl2xiaw9IHhOM9REhKfFy0A502ygLoAWqwERuvx1lAS47ijLMaTBxhd9knB4y6AAiMpgHrvAJzh5AXLxxs0Sg1Ej3IOI4XAPModNzkH1N2f9MH2zovk+fYZK+EkHlA3kpIa29cu0gzoZxyEk7cX7T5KK8Q/0hD1k5gXnHQGqAUiJRfYXhhGQoMARkx9TYJe0cqQkhJYT2M0E0n/HHgwJDyJd4cbnkmK1zoBMEwkG7jg54jwpBnMrg8rmUTvslAStHEwXm+AEiEMN8CVhECFCEMaSf8MccOENSBKL+CaAIIgQpQEoXUeOCJJ8lBEefUwSnl4F8Dk1xIxADFhkDDbF7vmhyqtoA11IAQeeAA7lzhijAC4YknqUEUENBFRmEvbATqAkinAEWdteBQBGqHCA8BAJYG4oR0j9YfoUY6PKkkACNEngD1MqgtZMBwCBuGSHPwxYoiw1BWU4DMB1OAMd0yJ0rYXBAhgygAh2AO5/LCCrM3kjcyrQQKs1YdP0ssEu7zWDGwYNQEcUFsZuMEXDzA9bnXBC9ZDQAva2K0QTEKLk1PCHqiZrymwoA1IsIMSCOEIOIghlflKpzrXyc52uvOd8IynPOdJz3ra8574zKc+98n2z376858ADahAB0rQghr0oAhNqEIXytCGOvShEI2oRCdK0Ypa9KIYzahGN8rRjnr0oyANqUhHStKSmvSkKE2pSlfK0pa69KUwjalMZ0rTmtr0pjjNqU53ytOe+vSnQA2qUIdK1KIa9ahITapSl8rUpjr1qVCNqlSnStWqWvWqWM2qVrfK1a569atgDatYx0rWspr1rGhNq1rXyta2uvWtcI2rXOdK17ra9a54zate98rXvvr1r4ANrGAHS9jCGvawiE2sYhfL2MY69rGQjaxkJ0vZylr2spjNrGY3y9nOevazoA2taEdL2tKa9rSoTa1qV8tasgYEACH5BAkEALAALAAAAAD0AfQBAAj/AGEJHEiwoMGDCBMqXMiwocOHECNKnEixosWLGDNq3Mixo8ePIEOKHEmypMmTKFOqXMmypcuXMGPKnEmzps2bOHPq3Mmzp8+fQIMKHUq0qNGjSJMqXcq0qdOnUKNKnUq1qtWrWLNq3cq1q9evYMOKHUu2rNmzaNOqXcu2rdu3cOPKnUu3rt27ePPq3cu3r9+/gAMLHky4sOHDiBMrXsy4sePHkCNLnky5suXLmDNr3sy5s+fPoEOLHk26tOnTqFOrXs26tevXsGPLnk27tu3buHPr3s27t+/fwIMLH068uPHjyJMrX868ufPn0KNLn069uvXr2LNr3869u/fv4MOL/x9Pvrz58+jTq1/Pvr379/Djy59Pv779+/jz69/Pv7///wAGKOCABBZo4IEIJqjgggw26OCDEEYo4YQUVmjhhRhmqOGGHHbo4YcghijiiCSWaOKJKKao4oostujiizDGKOOMNNZo44045qjjjjz26OOPQAYp5JBEFmnkkUgmqeSSTDbp5JNQRinllFRWaeWVWGap5ZZcdunll2CGKeaYZJZp5plopqnmmmy26eabcMYp55x01mnnnXjmqeeefPbp55+ABirooIQWauihiCaq6KKMNuroo5BGKumklFZq6aWYZqrpppx26umnoIYq6qiklmrqqaimquqqrLbq6quwxv8q66y01mrrrbjmquuuvPbq66/ABivssMQWa+yxyCar7LLMNuvss9BGK+201FZr7bXYZqvtttx26+23YEIQAhdkKOHFFiho0AIPJYBr0AogIADAvPTWG4ATQxDgbg5bBFDvvwAv0IK3JaDhL8AI20tFEdsWcUDCEP8bgBDZDnFwxBgDEAAIm8JgwQ8gaPDFGSlAMNMJF2eMcQAaXGqAERGkTC8Cj2wAEwcyqxxxAF9UesICGQcQg0sNPKzz0QHMMOkfOSccgAntrqTB0VQDgEADka7RdMRUKKASCVtXnXAFV6bQQgUgTEDCTBWEHfEWKpkgNtUB2DzlzykHEAARMLH/4PbOPZ8Uwt9z/5vElA5sHQAK+rJEgNGFBzDGSWQUTjUCUoLwNwotcWE5vS+cBPTnKgewApRlEB7ABCztQLrGUY8EA+GvAzD0kxHoHIABKm1Ae8YslHRC7Spz7uQYvwNwhUpSEE9GSUIQnzHmTqpA9fMpTUC8EyVNLf3OjTPpA9VpqJQE8VSUdMP3GGPdJA7kq/QF8VmUpAT7EbvPpOdHk52SFcTzQklegD+nhW9JF0ieFFQyA+I9oSSPKCDCqOek0QWNdymZQvIiNoSSKEKCAIPbk2agutupJHekCwAFShICEP4rcE9KHMa4xxI5vO4GJiHABi3XBSlpQHEmOGBK/xIgL8uZ7iRocOG8ApCAKVkAATJbHUxUsMN6OQAlPKhi1VpWpRVYAQQO8AEPhNiSJM4tCxg8CRVcGIAQPIoAThDbAh6gEouBEIeQIsANkkcFOq5EbgUMwBQm1QLVPSGNKvmAFldmhUpR4AtFBFgA1uDGl3BhkRBTAqYIQAIrrMEJW7jBD64QO5jgAJMhRKS0HoFKem2hlNQq5OcCcANVVosDWYgc67gFgRhEsnR2kAC4GiCHLPwNAX+4gLsI8oEzoIEKetPbAdIQAw6QcZkEIcA1scnNbnrzm+AMpzjHSc5ymvOc6EynOtfJzna6853wjKc850nPetrznvjMpz73yeTPfvrznwANqEAHStCCGvSgCE2oQhfK0IY69KEQjahEJ0rRilr0ohjNqEY3ytGOevSjIA2pSEdK0pKa9KQoTalKV8rSlrr0pTCNqUxnStOa2vSmOM2pTnfK05769KdADapQh0rUohr1qEhNqlKXytSmOvWpUI2qVKdK1apa9apYzapWt8rVrnr1q2ANq1jHStaymvWsaE2rWtfK1ra69a1wjatc50rXutr1rnjNq173yte++vWvgA2sYAdL2MIa9rCITaxiF8vYxjr2sZCNrGQnS9nKWvaymM2sZjfL2c569rPZCQgAIfkECQQAsAAsAAAAAPQB9AEACP8AYQkcSLCgwYMIEypcyLChw4cQI0qcSLGixYsYM2rcyLGjx48gQ4ocSbKkyZMoU6pcybKly5cwY8qcSbOmzZs4c+rcybOnz59AgwodSrSo0aNIkypdyrSp06dQo0qdSrWq1atYs2rdyrWr169gw4odS7as2bNo06pdy7at27dw48qdS7eu3bt48+rdy7ev37+AAwseTLiw4cOIEytezLix48eQI0ueTLmy5cuYM2vezLmz58+gQ4seTbq06dOoU6tezbq169ewY8ueTbu27du4c+vezbu379/AgwsfTry48ePIkytfzry58+fQo0ufTr269evYs2vfzr279+/gw4v/H0++vPnz6NOrX8++vfv38OPLn0+/vv37+PPr38+/v///AAYo4IAEFmjggQgmqOCCDDbo4IMQRijhhBRWaOGFGGao4YYcdujhhyCGKOKIJJZo4okopqjiiiy26OKLMMYo44w01mjjjTjmqOOOPPbo449ABinkkEQWaeSRSCap5JJMNunkk1BGKeWUVFZp5ZVYZqnlllx26eWXYIYp5phklmnmmWimqeaabLbp5ptwxinnnHTWaeedeOap55589unnn4AGKuighBZq6KGIJqrooow26uijkEYq6aSUVmrppZhmqummnHbq6aeghirqqKSWauqpqKaq6qqsturqq7DG/yrrrLTWauutuOaq66689urrr8AGK+ywxBZr7LHIJqvsssw26+yz0EYr7bTUVmvttdhmq+223Hbr7bdkGqCAAg2Ay9AKVpiAQAAAABBAADtUcEW55gpUQgwHsNvuvvy6q8EI5k6AQL8E9xvAGht0e8EO+hbscLsBqLDtCQ0/bHEAT2TrRsUWX7yGphK4oMQC7yLgRAwhzDQDxx1f7MClF9zAMsRRiADTBwO3rDPELVTqw8wGv2CAS03sbLS7TExqB9AF70ABSy0wfTTBTmCZQgsVgDABCTStIXXT9KKUQM5T6xyAFFWeQDK/7xIRUwxfO3yDSnKUfXQUVDoAdAAoEP/gEgxxOxyAHylFYLfRAVwgJQhfo+DSC4e3GwFKIwQeOQB4RFlG3AFMwBIFlgt+xElEXL7zDlEabvbQKiliOgAvm3TD6y0HkMCTY4R+xUqQm77ASQfQ3vIHT6pwNBkrUfF6AGGLBEHolxfxpA9Hp7HSArQnTJIBwre8u5M4VL8S2ZdrPxL33VuMtpNcHF3BSqpfznxJz6f/8BtPXhD6+inZ8frvJiGf/fgFsCdhb3UrccPrPmYSFAyQYAEoAZRWVrsYsEQC0CsYC04Sgwf2a3JR0lvHqtYSJVxuAX4zCQc8yK/3SUkDezNBClkSggzuKwAuQAkEBGi/AHBtShZYl8H/PAeTL9gQACRESRJYCIADXAldIHCAD3gwQ5g4cGoHeFpKNnDEnbkhUgYwwdEOQLyVVMCDEaiioyDwBM6hQIsrScAB0xeA703qDVvY2wEk9hIRdPFhGbuUGh7BMIgdAASjk4kQ/kg1CGyKAA0ogRplQgZG7qsJzaPWDxgZABNkslp+4OHOAuDCbW1gaUcLQBYS6a0VyKx2WVBEvQSyAReg4F0G28EPUjDLg2wgBBwoghoewLpeGvOYyEymMpfJzGY685nQjKY0p0nNalrzmtjMpja3yc1uevOb4AynOMdJznKa85zoTKc618nOdrrznfCMpzznSc962vOe+MynPvfJxs9++vOfAA2oQAdK0IIa9KAITahCF8rQhjr0oRCNqEQnStGKWvSiGM2oRjfK0Y569KMgDalIR0rSkpr0pChNqUpXytKWuvSlMI2pTGdK05ra9KY4zalOd8rTnvr0p0ANqlCHStSiGvWoSE2qUpfK1KY69alQjapUp0rVqlr1qljNqla3ytWuevWrYA2rWMdK1rKa9axoTata18rWtrr1rXCNq1znSte62vWueM2rXvfK17769a+ADaxgB0vYwhr2sIhN7DoDAgAh+QQJBACwACwAAAAA9AH0AQAI/wBhCRxIsKDBgwgTKlzIsKHDhxAjSpxIsaLFixgzatzIsaPHjyBDihxJsqTJkyhTqlzJsqXLlzBjypxJs6bNmzhz6tzJs6fPn0CDCh1KtKjRo0iTKl3KtKnTp1CjSp1KtarVq1izat3KtavXr2DDih1LtqzZs2jTql3Ltq3bt3Djyp1Lt67du3jz6t3Lt6/fv4ADCx5MuLDhw4gTK17MuLHjx5AjS55MubLly5gza97MubPnz6BDix5NurTp06hTq17NurXr17Bjy55Nu7bt27hz697Nu7fv38CDCx9OvLjx48iTK1/OvLnz59CjS59Ovbr169iza9/Ovbv37+DDi/8fT768+fPo06tfz769+/fw48ufT7++/fv48+vfz7+///8ABijggAQWaOCBCCao4IIMNujggxBGKOGEFFZo4YUYZqjhhhx26OGHIIYo4ogklmjiiSimqOKKLLbo4oswxijjjDTWaOONOOao44489ujjj0AGKeSQRBZp5JFIJqnkkkw26eSTUEYp5ZRUVmnllVhmqeWWXHbp5ZdghinmmGSWaeaZaKap5ppstunmm3DGKeecdNZp55145qnnnnz26eefgAYq6KCEFmrooYgmquiijDbq6KOQRirppJRWaumlmGaq6aacdurpp6CGKuqopJZq6qmopqrqqqy26uqrsMb/KuustNZq66245qrrrrz26uuvwAYr7LDEFmvsscgmq+yyzDbr7LPQRivttNRWa+212Gar7bbcduvtt+Da2cAINAxhgRQcbBAuQmOAgcUAAMQr7wAeaJDDugK9sQW88vbb7wAIuABuB5Hw6+/B8x7AQ7c09IDww/4OAMi2LhgM8cUD2NCpAR+scMcFJdhU8cUkzxtJpgQosu+/WEyggEwiWFwyxk9caoEHGPsAkwI4z+zzAENUyobMCA9QQwcuHeLz0gB40ACWYkzwhANWFFGTCURDjAAFLK2QNdMPM2LlEB5YPMAAcsj0wtcQVwHBSnSAvfQAL0+59sMDBEHASyew/32xGSo94Lfc/hIxpQaDB/ESH4QDMMADKU3QuM9VSMnC4I5b0VIhmEMMOEo1TD7zAEhDicDPBrAU9+Q9oGRA56KLAOUFsAMgxUoQ1F70BydNIbrPLUDJBdOBrJTB7wDQcNIdyJdc85NgMG3CShcgr8JJIjRPMhtQAiL9SiNYfxIN2l98CJRuMP18Ssf/frtJRZQPMRKz187CSgTojvAFJ40h/8Oag1LPSjaABLAkCKLrwdtM0gD9ye1+UOIcAYXQEkWIjn4oOcD/Iga5KN3tYolwiQEcRrgB8A8l3tugvPhApaHhbQupcwkXHAgAB6iECTT0GRiqpIgeyGwAAYSJEv/kVgADqqQKKnRcB6vEgT5o4AVg6MLeZGKA0C3NA7xbyeVUuIZJJYAOnTsADFyyhQ0+rlITICHenhDDltBOfkC8VAmsUACz9cAMU5AJEXKIMB1sigJ3kMIM3rDEmZiBj/2qghGt9QREAqAKdcNWDHI4AB0sMlskOID+BjABcAligCQbgAYysC4CnCAIXxvAASagLnwNxABqUIQPzPCEH7iAB1xzpS53ycte+vKXwAymMIdJzGIa85jITKYyl8nMZjrzmdCMpjSnSc1qWvOa2MymNrfJzW5685vgDKc4x0nOcprznOhMpzrXyc52uvOd8IynPOdJz3ra8574zKc+98m3z376858ADahAB0rQghr0oAhNqEIXytCGOvShEI2oRCdK0Ypa9KIYzahGN8rRjnr0oyANqUhHStKSmvSkKE2pSlfK0pa69KUwjalMZ0rTmtr0pjjNqU53ytOe+vSnQA2qUIdK1KIa9ahITapSl8rUpjr1qVCNqlSnStWqWvWqWM2qVrfK1a569atgDatYx0rWspr1rGhNq1rXyta2uvWtcI2rXOdK17ra9a54zate98rXvvq1SgEBACH5BAkEALAALAAAAAD0AfQBAAj/AGEJHEiwoMGDCBMqXMiwocOHECNKnEixosWLGDNq3Mixo8ePIEOKHEmypMmTKFOqXMmypcuXMGPKnEmzps2bOHPq3Mmzp8+fQIMKHUq0qNGjSJMqXcq0qdOnUKNKnUq1qtWrWLNq3cq1q9evYMOKHUu2rNmzaNOqXcu2rdu3cOPKnUu3rt27ePPq3cu3r9+/gAMLHky4sOHDiBMrXsy4sePHkCNLnky5suXLmDNr3sy5s+fPoEOLHk26tOnTqFOrXs26tevXsGPLnk27tu3buHPr3s27t+/fwIMLH068uPHjyJMrX868ufPn0KNLn069uvXr2LNr3869u/fv4MOL/x9Pvrz58+jTq1/Pvr379/Djy59Pv779+/jz69/Pv7///wAGKOCABBZo4IEIJqjgggw26OCDEEYo4YQUVmjhhRhmqOGGHHbo4YcghijiiCSWaOKJKKao4oostujiizDGKOOMNNZo44045qjjjjz26OOPQAYp5JBEFmnkkUgmqeSSTDbp5JNQRinllFRWaeWVWGap5ZZcdunll2CGKeaYZJZp5plopqnmmmy26eabcMYp55x01mnnnXjmqeeefPbp55+ABirooIQWauihiCaq6KKMNuroo5BGKumklFZq6aWYZqrpppx26umnoIYq6qiklmrqqaimquqqrLbq6quwxv8q66y01mrrrbjmquuuvPbq66/ABivssMQWa+yxyCar7LLMNuvss9BGK+201FZr7bXYZqvtttx26+234IaLKAVSaFGHDTqwAYgFH4hbUAJnNFEAAPTWS28BCwAyhbgQaLGAvQADXIAGG3ybAhUBJyxwGN1yMa/CEN9bx7aCPBxxxAXYwGkCOWDwiCNaSEFBTXBYfDHGbGQ6hgYm34vCGzKF0PLJEBegxaWAzGxvAWskAFMTNAcNQAEjZJmCHGY8IcgdNRGgg84BUyGBSxhALXTAdFxZCBYmF1CAETMpcTUVJbBEwL9X01wAzFQiAXUBOhAAEw5WKxwJS3mkLfTdUyL/UjcAOrwEw98JF8DCSkHoHXQBHUgpBeEFCOISIooD0IRKJRBeOQB7SImw2gawZIDmhY+R0hub01xBlGOQDgANLK2QOsMohZH6yVtECcfVjLC0++ZIpMTI7RcvEGUfVyvBkhapB45SHcRjHCUeybPURvMpaRB9zRBAOcfVZrDEReoTo2TG9gobD2XrQkvB0h2pE5GSHOgnfHmUWCwe+koJuC5wCCkRQf0CVj4o7QFybXCJ9hRHBZVQwH9pU8SU3HaxrLnkAhAcmgVW8rkBDm1qU6rD21Agt5ecL20WVAkRPEivIFjJDwtoWeRkAgEnXA0LBVuJAjJ4sgIUAksr0AIi/5DQhxyUUCYNSBzNInABlzzCgw2kFAH8hjEdjMwlCcgf+grQhUtx4GkBK0AiOheTx6EvEJraQCEAoQE2MAIO7aIJGHgYsCAcsVpPoGO9alC2bDlCj07oo7YUgbarFaAC3esWBdhAugI0gW3gugAiClk4FMDOXQIxQBH6YAMqYGEBEaCDGfZwRUya8pSoTKUqV8nKVrrylbCMpSxnScta2vKWuMylLnfJy1768pfADKYwh0nMYhrzmMhMpjKXycxmOvOZ0IymNKdJzWpa85rYzKY2t8nNbnrzm+AMpzjHSc5ymvOc6EynOtfJzna6853wjKc850nPetrznvjMpz73yZ3PfvrznwANqEAHStCCGvSgCE2oQhfK0IY69KEQjahEJ0rRilr0ohjNqEY3ytGOevSjIA2pSEdK0pKa9KQoTalKV8rSlrr0pTCNqUxnStOa2vSmOM2pTnfK05769KdADapQh0rUohr1qEhNqlKXytSmOvWpUI2qVKdK1apa9apYzapWt8rVrnr1q2ANq1jHStaymvWsaE2rWtfamYAAACH5BAkEALAALAAAAAD0AfQBAAj/AGEJHEiwoMGDCBMqXMiwocOHECNKnEixosWLGDNq3Mixo8ePIEOKHEmypMmTKFOqXMmypcuXMGPKnEmzps2bOHPq3Mmzp8+fQIMKHUq0qNGjSJMqXcq0qdOnUKNKnUq1qtWrWLNq3cq1q9evYMOKHUu2rNmzaNOqXcu2rdu3cOPKnUu3rt27ePPq3cu3r9+/gAMLHky4sOHDiBMrXsy4sePHkCNLnky5suXLmDNr3sy5s+fPoEOLHk26tOnTqFOrXs26tevXsGPLnk27tu3buHPr3s27t+/fwIMLH068uPHjyJMrX868ufPn0KNLn069uvXr2LNr3869u/fv4MOL/x9Pvrz58+jTq1/Pvr379/Djy59Pv779+/jz69/Pv7///wAGKOCABBZo4IEIJqjgggw26OCDEEYo4YQUVmjhhRhmqOGGHHbo4YcghijiiCSWaOKJKKao4oostujiizDGKOOMNNZo44045qjjjjz26OOPQAYp5JBEFmnkkUgmqeSSTDbp5JNQRinllFRWaeWVWGap5ZZcdunll2CGKeaYZJZp5plopqnmmmy26eabcMYp55x01mnnnXjmqeeefPbp55+ABirooIQWauihiCaq6KKMNuroo5BGKumklFZq6aWYZqrpppx26umnoIYq6qiklmrqqaimquqqrLbq6quwxv8q66y01mrrrbjmquuuvPbq66/ABivssMQWa+yxyCar7LLMNuvss9BGK+201FZr7bXYZqvtttx26+234Ia7KAQGJECAuApRYMELEQQAAAABLJAGBhegO9AKN7j77r78BrCDBeJuYIe+/Ba8bwBU5PDtCQgY7HDBAXzR7QQEP2xxADacy2kDIRwhwgoU3ESxxSTze8OmQzRRcbwYJDATCxWXfPETmBZxQMz9qhATBQvI7DO8J2iZQgsVgDABCTaNXHIAIMCExs8/L+CylScssHIARMzUAs4PB+CASyFwDbXDMVjpgNgBoKCxSxyI3bURLa0x9s8IrB0lCG6/iwJMEcz/Da8CK5WQt9/7SjFlGYPDO4FLMBOexEplEO7zC1P27XMABrTkhOQBrFSB5DIjIOUYie97BUsGlO5wAPWmFAXoSwMOpQpjk8ESDLDPoFLDsJPc+pM+jJ0GSxzA7oJKqhOuRpQ4CE887HCjBEHyfq8QJRdjV8DSB7AHnRL1c48Q5QXJG75SAuAfLH5KO/R+cchR9nx55iy9TnjnKjng/sOiSzlD4gEoW0uGkD4AaE8lFtifw042pbOVzAkwkd/YArCBlWyggDJTRJU0gDYT2I0lXaBeAFuCAgX2qwRWsgACYhaAxckEB6rDmEt4gEGL2Q5LK7ACCBzgAx58ECY/AKAd/2BiAhMCAAEVrBQLeNc1F75kBDWEWAswRQAMWK1fAfhBB2YihyjuSwmcykAOLGABEcDgJn/w4g4aoC28gW4HW9yWD9IXgBtMjVsk2EHyEJC1cKmgXSVDQBLiiC4OfCELK0OABmZAP3sRxAAZ+MAFHsBGR1rykpjMpCY3yclOevKToAylKEdJylKa8pSoTKUqV8nKVrrylbCMpSxnScta2vKWuMylLnfJy1768pfADKYwh0nMYhrzmMhMpjKXycxmOvOZ0IymNKdJzWpa85rYzKY2t8nNbnrzm+AMpzjHSc5ymvOc6EynOtfJzna6853wjKc850nPetrznvjMpz73yYXPfvrznwANqEAHStCCGvSgCE2oQhfK0IY69KEQjahEJ0rRilr0ohjNqEY3ytGOevSjIA2pSEdK0pKa9KQoTalKV8rSlrr0pTCNqUxnStOa2vSmOM2pTnfK05769KdADapQh0rUohr1qEhNqlKXytSmOvWpUI2qVKdK1apa9apYzapWaxoQACH5BAkEALAALAAAAAD0AfQBAAj/AGEJHEiwoMGDCBMqXMiwocOHECNKnEixosWLGDNq3Mixo8ePIEOKHEmypMmTKFOqXMmypcuXMGPKnEmzps2bOHPq3Mmzp8+fQIMKHUq0qNGjSJMqXcq0qdOnUKNKnUq1qtWrWLNq3cq1q9evYMOKHUu2rNmzaNOqXcu2rdu3cOPKnUu3rt27ePPq3cu3r9+/gAMLHky4sOHDiBMrXsy4sePHkCNLnky5suXLmDNr3sy5s+fPoEOLHk26tOnTqFOrXs26tevXsGPLnk27tu3buHPr3s27t+/fwIMLH068uPHjyJMrX868ufPn0KNLn069uvXr2LNr3869u/fv4MOL/x9Pvrz58+jTq1/Pvr379/Djy59Pv779+/jz69/Pv7///wAGKOCABBZo4IEIJqjgggw26OCDEEYo4YQUVmjhhRhmqOGGHHbo4YcghijiiCSWaOKJKKao4oostujiizDGKOOMNNZo44045qjjjjz26OOPQAYp5JBEFmnkkUgmqeSSTDbp5JNQRinllFRWaeWVWGap5ZZcdunll2CGKeaYZJZp5plopqnmmmy26eabcMYp55x01mnnnXjmqeeefPbp55+ABirooIQWauihiCaq6KKMNuroo5BGKumklFZq6aWYZqrpppx26umnoIYq6qiklmrqqaimquqqrLbq6quwxv8q66y01mrrrbjmquuuvPbq66/ABivssMQWa+yxyCar7LLMNuvss9BGK+201FZr7bXYZqvtttx26+234IYr7qYQSHAHDVe88YEB4xpkwB5KeADAvPQKEAUGFLQLgRby0uuvvwLUsUG4JBzw78H/eoDBt5AIgPDD9R4CgacNhHAEDSvkexMYDkPsMQAmELCpHzt0PK8ACMiRAE0tmPwxxDdkWgQCLv8rwBwycVDzywgLIMSWKUASCBJakGCTFjsfHHBMWfDMswAXYHkCzQALsLBMDTstACEvEZG00webcKUGXwsQMkw6gw2AAES0BAECar8sQAhV1vE1vWK/ZHDcAij/wBINcfOMCJUs3F2vFi7tYTjEjrD0QuAve0Dl3nKzy5IXkK/NUr+ZPwy1lBcs7q8ULBkguudRp6TA6YHvIeUcak/C0gedAzCDSkzU7jHiUeKhdiMscVD7ICrdoTvEgEgJxu8sGd952ymRcPzDjUd5htqBzF77CSqFMD3CbYDOOgBlsJTA+DYzodIG6IM9xJRwP235SjVkLsDm3/9Lt5QziC5AHy7xQ/vmlb2VKCF/9RLZlAixOC/AJH5qE8DAVjIEBM7rEFZ6QdmCML+WHAF9/2uJATg3PQHk4Ep58EDNBMC7mHBMazFzyfLyVwMtraANdSAEHnigwJkAwn+GgEkC/yCoOxNeag8kVFoLX9K/6SEhUwaQA9XqJYAkdIAmkxjgv6LQw0xlIAd5yAMNYIATNmhxXgfw27YQocUoqJFbZ0jixwSAiIl9iwIMlFsU7tAuCQjhADsTgAfqsIJ2FWQDOZgDJLQQhit8wJCQjKQkJ0nJSlrykpjMpCY3yclOevKToAylKEdJylKa8pSoTKUqV8nKVrrylbCMpSxnScta2vKWuMylLnfJy1768pfADKYwh0nMYhrzmMhMpjKXycxmOvOZ0IymNKdJzWpa85rYzKY2t8nNbnrzm+AMpzjHSc5ymvOc6EynOtfJzna6853wjKc850nPetrznvjMpz73yX7PfvrznwANqEAHStCCGvSgCE2oQhfK0IY69KEQjahEJ0rRilr0ohjNqEY3ytGOevSjIA2pSEdK0pKa9KQoTalKV8rSlrr0pTCNqUxnStOa2vSmOM2pTnfK05769KdADapQh0rUohr1qEhNqlKXytSmOvWpUI2qVKdK1ao6KyAAIfkECQQAsAAsAAAAAPQB9AEACP8AYQkcSLCgwYMIEypcyLChw4cQI0qcSLGixYsYM2rcyLGjx48gQ4ocSbKkyZMoU6pcybKly5cwY8qcSbOmzZs4c+rcybOnz59AgwodSrSo0aNIkypdyrSp06dQo0qdSrWq1atYs2rdyrWr169gw4odS7as2bNo06pdy7at27dw48qdS7eu3bt48+rdy7ev37+AAwseTLiw4cOIEytezLix48eQI0ueTLmy5cuYM2vezLmz58+gQ4seTbq06dOoU6tezbq169ewY8ueTbu27du4c+vezbu379/AgwsfTry48ePIkytfzry58+fQo0ufTr269evYs2vfzr279+/gw4v/H0++vPnz6NOrX8++vfv38OPLn0+/vv37+PPr38+/v///AAYo4IAEFmjggQgmqOCCDDbo4IMQRijhhBRWaOGFGGao4YYcdujhhyCGKOKIJJZo4okopqjiiiy26OKLMMYo44w01mjjjTjmqOOOPPbo449ABinkkEQWaeSRSCap5JJMNunkk1BGKeWUVFZp5ZVYZqnlllx26eWXYIYp5phklmnmmWimqeaabLbp5ptwxinnnHTWaeedeOap55589unnn4AGKuighBZq6KGIJqrooow26uijkEYq6aSUVmrppZhmqummnHbq6aeghirqqKSWauqpqKaq6qqsturqq7DG/yrrrLTWauutuOaq66689urrr8AGK+ywxBZr7LHIJqvsssw26+yz0EYr7bTUVmvttdhmq+223Hbr7bfghivuuKsSIMYZjtTBRgUY8FACuQSFgEgBANRrb70F6CAFuRLYQO+9AONbwxvhwvFvwAgDUIAZoDYQQhciqNFBTjgcnDDC+RrA6QmJWFwAFkQkUBMeFl+csA4QZFpEBCXfWwAcM1nQsskII8FlCnKY8YQgd9gkyMwAF4BITBQsQPPRCheSZSFYeFyAETPJAXTABdj8EhtIIx0BAVciAXS+XL/EwdQYD+LSGGRnba/ZVc5Lsw4wUaG2vQUo0JIZcx9NRZVSpP+tsCAuleE3woC0ZHTeJhcwApVyI12AxizRgTi+LF0w+NxETIm22jSwZMDlVI+xUiGT08zGlHDMzQhLMJRe7x4rteH6xTVM2cfcSrDEwexhrMTI7AljMSUeuOs+O9sp/Q58wMJLOcfcDK/0wexKq3T78gDvLeXmWe+7UgKgB724SnlgD7ANVGKR9eMtbVF6ASylYP69WlC5h98FtOHSCeHbG71KBOgfzQqghip5jWZ0gIn68laADbREA/MDQPOqVIevoSBsLulC+PLnkhUI8GJ9wJIfFlCyAgBOJiRb3yFgggLzLeBdWVqBFhCBhD7kAIMyqdjRCrCGmFhueU/DVBn/DpcwE87kZ8CLhKYIQISmuawAYJgYTSrouiY0oFMZeIMf/CACGOREAx9sAgW8lUK1FcAGIvtWEZowOCycgVx7CMLXqCCINMIrA0MwAwqaUIMgICEM44OXIAdJyEIa8pCITKQiF8nIRjrykZCMpCQnSclKWvKSmMykJjfJyU568pOgDKUoR0nKUprylKhMpSpXycpWuvKVsIylLGdJy1ra8pa4zKUud8nLXvryl8AMpjCHScxiGvOYyEymMpfJzGY685nQjKY0p0nNalrzmtjMpja3yc1uevOb4AynOMdJznKa85zoTKc618nOdrrznfCMpzznSc962vOe+MynPvfJbc9++vOfAA2oQAdK0IIa9KAITahCF8rQhjr0oRCNqEQnStGKWvSiGM2oRjfK0Y569KMgDalIR0rSkpr0pChNqUpXytKWuvSlMI2pTGdK05ra9KY4zalOd8rTnvr0p0ANqlCHStSiGvWoSJ1QQAAAIfkECQQAsAAsAAAAAPQB9AEACP8AYQkcSLCgwYMIEypcyLChw4cQI0qcSLGixYsYM2rcyLGjx48gQ4ocSbKkyZMoU6pcybKly5cwY8qcSbOmzZs4c+rcybOnz59AgwodSrSo0aNIkypdyrSp06dQo0qdSrWq1atYs2rdyrWr169gw4odS7as2bNo06pdy7at27dw48qdS7eu3bt48+rdy7ev37+AAwseTLiw4cOIEytezLix48eQI0ueTLmy5cuYM2vezLmz58+gQ4seTbq06dOoU6tezbq169ewY8ueTbu27du4c+vezbu379/AgwsfTry48ePIkytfzry58+fQo0ufTr269evYs2vfzr279+/gw4v/H0++vPnz6NOrX8++vfv38OPLn0+/vv37+PPr38+/v///AAYo4IAEFmjggQgmqOCCDDbo4IMQRijhhBRWaOGFGGao4YYcdujhhyCGKOKIJJZo4okopqjiiiy26OKLMMYo44w01mjjjTjmqOOOPPbo449ABinkkEQWaeSRSCap5JJMNunkk1BGKeWUVFZp5ZVYZqnlllx26eWXYIYp5phklmnmmWimqeaabLbp5ptwxinnnHTWaeedeOap55589unnn4AGKuighBZq6KGIJqrooow26uijkEYq6aSUVmrppZhmqummnHbq6aeghirqqKSWauqpqKaq6qqsturqq7DG/yrrrLTWauutuOaq66689urrr8AGK+ywxBZr7LHIJqvsssw26+yz0EYr7bTUVmvttdhmq+223Hbr7bfghivuuK9CQAC5CnGAhxcIBODuDn9IYQC6sBBgxAEBAKDvvvsGQAYF43YRAb8EE4yAHKE2EMIRIqwAcE4+5FvwxPoGcMO5nA7RhMQVL4BBAjZVwDHFFHsxb6ZF4EtyACrQJMTIJFOcRpcptFABCBOQYNMEME8cAAgyvdFzzAUH4IOWJywwsrtEzNTC0D47EFMWRFcNQAAfYOkA1AGggLFLHEBNcQBGvMSF2Fbva8eVIKANAAowDZx2vwq4RPXcMQcgQZVluP999QQuseD3xEm0FMLgabdQpdxVB3DySk7gzW8ALU0gOdFeUDkG4gBcwZIBnBMcwAUs3XB53l9DqQLeZLAEw+n7zsAS47AX/HCUPuA980oc1A6ACywh4PvEU0yJg+4s9V572SsJPzzBMEzJBd4VsPSB7yewtMDzBG8w5QWcS8FSAqFPPgJLKHDfb+pQbm+14y1FATvlLAmhvr5NVDmD3wHE4NIQ5dNX9ZIXQJIJwUpbI5oTYOI+vAXAey1p4PCwdiUNcM0E7FtJF0LXv5dYjntww5IF2iU6wMkEB4gLgA1gYgAJzm8FW1qBFUDgAB/wIIMv+QH/1haTExSQX0/IFAv/nDc2E8rkDz8EQBNwOCkCYEBpkwvADzpgExsUMAK321QGcmABC4ggejlJIN6iQMVvuYGIRAtABZiorQ6QAW0WSwG9GpAHO0DxaghwQgseQC+DNIACFChBHwdJyEIa8pCITKQiF8nIRjrykZCMpCQnSclKWvKSmMykJjfJyU568pOgDKUoR0nKUprylKhMpSpXycpWuvKVsIylLGdJy1ra8pa4zKUud8nLXvryl8AMpjCHScxiGvOYyEymMpfJzGY685nQjKY0p0nNalrzmtjMpja3yc1uevOb4AynOMdJznKa85zoTKc618nOdrrznfCMpzznSc962vOe+MynPvfJbc9++vOfAA2oQAdK0IIa9KAITahCF8rQhjr0oRCNqEQnStGKWvSiGM2oRjfK0Y569KMgDalIR0rSkpr0pChNqUpXytKWuvSlMI2pTGdK05ra9KY4zalOd8rTnvr0p0ANqlCHStSiGvWoSI1mQAAAIfkECQQAsAAsAAAAAPQB9AEACP8AYQkcSLCgwYMIEypcyLChw4cQI0qcSLGixYsYM2rcyLGjx48gQ4ocSbKkyZMoU6pcybKly5cwY8qcSbOmzZs4c+rcybOnz59AgwodSrSo0aNIkypdyrSp06dQo0qdSrWq1atYs2rdyrWr169gw4odS7as2bNo06pdy7at27dw48qdS7eu3bt48+rdy7ev37+AAwseTLiw4cOIEytezLix48eQI0ueTLmy5cuYM2vezLmz58+gQ4seTbq06dOoU6tezbq169ewY8ueTbu27du4c+vezbu379/AgwsfTry48ePIkytfzry58+fQo0ufTr269evYs2vfzr279+/gw4v/H0++vPnz6NOrX8++vfv38OPLn0+/vv37+PPr38+/v///AAYo4IAEFmjggQgmqOCCDDbo4IMQRijhhBRWaOGFGGao4YYcdujhhyCGKOKIJJZo4okopqjiiiy26OKLMMYo44w01mjjjTjmqOOOPPbo449ABinkkEQWaeSRSCap5JJMNunkk1BGKeWUVFZp5ZVYZqnlllx26eWXYIYp5phklmnmmWimqeaabLbp5ptwxinnnHTWaeedeOap55589unnn4AGKuighBZq6KGIJqrooow26uijkEYq6aSUVmrppZhmqummnHbq6aeghirqqKSWauqpqKaq6qqsturqq7DG/yrrrLTWauutuOaq66689urrr8AGK+ywxBZr7LHIJqvsssw26+yz0EYr7bTUVmvttdhmq+223Hbr7bfghivuuOT2WsIIdxQRAgXlGvQBIAcIAMC8AAjgQR0ktPuAIfLS6++8AuyQg6gNhHAEDSuwqxMR/f7rcL0gQOCpHzs0XC8CciRw0x8WP+xwEA1sWgQCHfsrwBw1BVKyx/9GQUCXKUASCBJa5FuTFiv/K0AdM4WRM8v+vrDlCSSbLAAGM0Hys86ExJTB0kADXEiWGuQsgAkvv8QB1DoTARMaUYcNwAFY1gG1CTAdILbOCrgkAddhCzCElSxwLYAWLu0Bt8OOuP+kxdphe2Gl2mILYEBLXgCus0s7KA60ACFPecHeAEjBkgGU63zB5ZlHvQKVcyg+CUsfOP7vDCw9YDrQeVCJh+KNsMTB6vQOwhITtHvs9ZRgwM7SHbkDsLtKIQTvMNJTnqF4IKQHfwJLMBj/LxxUTg54GSwl0Dm9AjCR/fYs2zwlAmsb3lINtAvgUhbSA9w2lTPY3YdLfoDPfEuAtA/ADlcSArXgLyGf4wSwAZdYT3pnwNILrBaEw73kCJkTwPxeogPpIcCBV8qDBzp2t5mAYW8CuEFMDpi+MHBpBW2oAyHwwIOszQQQdjPETHwAvnnFLlN78MDj8EYTO4DvACXYlAH/5FA07gkgCR24Cb8cl4UMfCoDOchDHmgAg504AoRKCGK47lADqCEAZeXKwSF0qDMv5MGF7SLAB2iQBziwIASRa5cc50jHOtrxjnjMox73yMc++vGPgAykIAdJyEIa8pCITKQiF8nIRjrykZCMpCQnSclKWvKSmMykJjfJyU568pOgDKUoR0nKUprylKhMpSpXycpWuvKVsIylLGdJy1ra8pa4zKUud8nLXvryl8AMpjCHScxiGvOYyEymMpfJzGY685nQjKY0p0nNalrzmtjMpja3yc1uevOb4AynOMdJznKa85zoTKc618nOdrrznfCMpzznSc962vOe+MynPvfJV89++vOfAA2oQAdK0IIa9KAITahCF8rQhjr0oRCNqEQnStGKWvSiGM2oRjfK0Y569KMgDalIR0rSkpr0pChNqUpXytKWuvSlMI2pTGdK05ra9KY4XWZAAAAh+QQFBACwACwAAAAA9AH0AQAI/wBhCRxIsKDBgwgTKlzIsKHDhxAjSpxIsaLFixgzatzIsaPHjyBDihxJsqTJkyhTqlzJsqXLlzBjypxJs6bNmzhz6tzJs6fPn0CDCh1KtKjRo0iTKl3KtKnTp1CjSp1KtarVq1izat3KtavXr2DDih1LtqzZs2jTql3Ltq3bt3Djyp1Lt67du3jz6t3Lt6/fv4ADCx5MuLDhw4gTK17MuLHjx5AjS55MubLly5gza97MubPnz6BDix5NurTp06hTq17NurXr17Bjy55Nu7bt27hz697Nu7fv38CDCx9OvLjx48iTK1/OvLnz59CjS59Ovbr169iza9/Ovbv37+DDi/8fT768+fPo06tfz769+/fw48ufT7++/fv48+vfz7+///8ABijggAQWaOCBCCao4IIMNujggxBGKOGEFFZo4YUYZqjhhhx26OGHIIYo4ogklmjiiSimqOKKLLbo4oswxijjjDTWaOONOOao44489ujjj0AGKeSQRBZp5JFIJqnkkkw26eSTUEYp5ZRUVmnllVhmqeWWXHbp5ZdghinmmGSWaeaZaKap5ppstunmm3DGKeecdNZp55145qnnnnz26eefgAYq6KCEFmrooYgmquiijDbq6KOQRirppJRWaumlmGaq6aacdurpp6CGKuqopJZq6qmopqrqqqy26uqrsMb/KuustNZq66245qrrrrz26uuvwAYr7LDEFmvsscgmq+yyzDbr7LPQRivttNRWa+212Gar7bbcduvtt+CGK+645P6aQAMElIsQCV8gEEAAALyrAQsGqAuLCu4CoO+++wbwQ72hNhDCESKsQMFODzQBL78M93vFp0MozG8AC2CQwE0iLNzwxvEKwWkRB2jccAAq1JQxxyjH64OXKbRQAQgTkGDTBCJzHAAIM0lQc8oMB3DClicsIPK7RMzUws42OyDTFjzzHIACWTqAdLwopPsSB1PbbARMFmTdtL4aYAmC1wCgAFMEX/cMtUtop41yAAdXWQbZ8U7gEgt0b5yES2rk/910C1a23XQAAK/khNs9uyQE4ilnUeUYfgPw8EoGRN7zBS3twPjbVkupAuJksATD5vzO0JLlPEtApQ+Ip8ESB6Tv6wJLEKCe8ghU4tD667Hru/VKBNiOMhNUcoF4BSx90DsAP7MkPMeqT3lB5FKwlMDzAeDOkuDLx3sxlQukTXhLUcQegEtJdL/vAVbOQHcAMbg0hPDIt0TC8wzHb6XUPDsBU/iMC8AGXoIA9QVgCljSwNQCYILOtaQLloMfTFyAP33dQEsWyNfE7CYTHPgtADaQCfc2F4AHcGkFVgCBA3zAAwfG5Afvs8NMUoA9DGiKBQV8GwdnogLbBeAJnCIABv+ENjF/deAmbojgH0CVgRxYwAIigMFOSJDDwc1OXATwYMoCgIYMqMsAFkDBu/q1AwwM0F4EUYAEHtABCKDxjXCMoxznSMc62vGOeMyjHvfIxz768Y+ADKQgB0nIQhrykIhMpCIXychGOvKRkIykJCdJyUpa8pKYzKQmN8nJTnryk6AMpShHScpSmvKUqEylKlfJyla68pWwjKUsZ0nLWtrylrjMpS53ycte+vKXwAymMIdJzGIa85jITKYyl8nMZjrzmdCMpjSnSc1qWvOa2MymNrfJzW5685vgDKc4x0nOcprznOhMpzrXyc52uvOd8IynPOdJz3ra8574zKc+98lSz376858ADahAB0rQghr0oAhNqEIXytCGOvShEI2oRCdK0Ypa9KIYzahGN8rRjnr0oyANqUhHStKSmvSkKE2pSlfK0pa69KUwjalMZ0rTms4mIAAh+QQFBACwACwAAAAAAQABAAAIBABhBQQAIfkEBQQAsAAsAAAAAAEAAQAACAQAYQUEACH5BAUEALAALAAAAAABAAEAAAgEAGEFBAAh+QQFBACwACwAAAAAAQABAAAIBABhBQQAIfkEBQQAsAAsAAAAAAEAAQAACAQAYQUEACH5BAUEALAALAAAAAABAAEAAAgEAGEFBAAh+QQFBACwACwAAAAAAQABAAAIBABhBQQAIfkEBQQAsAAsAAAAAAEAAQAACAQAYQUEACH5BAUEALAALAAAAAABAAEAAAgEAGEFBAA7"};return f&&(d!==f.failurelimit&&(f.failure_limit=f.failurelimit,delete f.failurelimit),d!==f.effectspeed&&(f.effect_speed=f.effectspeed,delete f.effectspeed),a.extend(j,f)),h=j.container===d||j.container===b?e:a(j.container),0===j.event.indexOf("scroll")&&h.bind(j.event,function(){return g()}),this.each(function(){var b=this,c=a(b);b.loaded=!1,(c.attr("src")===d||c.attr("src")===!1)&&c.is("img")&&c.attr("src",j.placeholder),c.one("appear",function(){if(!this.loaded){if(j.appear){var d=i.length;j.appear.call(b,d,j)}a("<img />").bind("load",function(){var d=c.attr("data-"+j.data_attribute);c.hide(),c.is("img")?c.attr("src",d):c.css("background-image","url('"+d+"')"),c[j.effect](j.effect_speed),b.loaded=!0;var e=a.grep(i,function(a){return!a.loaded});if(i=a(e),j.load){var f=i.length;j.load.call(b,f,j)}}).attr("src",c.attr("data-"+j.data_attribute))}}),0!==j.event.indexOf("scroll")&&c.bind(j.event,function(){b.loaded||c.trigger("appear")})}),e.bind("resize",function(){g()}),/(?:iphone|ipod|ipad).*os 5/gi.test(navigator.appVersion)&&e.bind("pageshow",function(b){b.originalEvent&&b.originalEvent.persisted&&i.each(function(){a(this).trigger("appear")})}),a(c).ready(function(){g()}),this},a.belowthefold=function(c,f){var g;return g=f.container===d||f.container===b?(b.innerHeight?b.innerHeight:e.height())+e.scrollTop():a(f.container).offset().top+a(f.container).height(),g<=a(c).offset().top-f.threshold},a.rightoffold=function(c,f){var g;return g=f.container===d||f.container===b?e.width()+e.scrollLeft():a(f.container).offset().left+a(f.container).width(),g<=a(c).offset().left-f.threshold},a.abovethetop=function(c,f){var g;return g=f.container===d||f.container===b?e.scrollTop():a(f.container).offset().top,g>=a(c).offset().top+f.threshold+a(c).height()},a.leftofbegin=function(c,f){var g;return g=f.container===d||f.container===b?e.scrollLeft():a(f.container).offset().left,g>=a(c).offset().left+f.threshold+a(c).width()},a.inviewport=function(b,c){return!(a.rightoffold(b,c)||a.leftofbegin(b,c)||a.belowthefold(b,c)||a.abovethetop(b,c))},a.extend(a.expr[":"],{"below-the-fold":function(b){return a.belowthefold(b,{threshold:0})},"above-the-top":function(b){return!a.belowthefold(b,{threshold:0})},"right-of-screen":function(b){return a.rightoffold(b,{threshold:0})},"left-of-screen":function(b){return!a.rightoffold(b,{threshold:0})},"in-viewport":function(b){return a.inviewport(b,{threshold:0})},"above-the-fold":function(b){return!a.belowthefold(b,{threshold:0})},"right-of-fold":function(b){return a.rightoffold(b,{threshold:0})},"left-of-fold":function(b){return!a.rightoffold(b,{threshold:0})}})}(jQuery,window,document);
\ No newline at end of file
/* Chosen v1.4.2 | (c) 2011-2015 by Harvest | MIT License, https://github.com/harvesthq/chosen/blob/master/LICENSE.md */
(function(){var a,AbstractChosen,Chosen,SelectParser,b,c={}.hasOwnProperty,d=function(a,b){function d(){this.constructor=a}for(var e in b)c.call(b,e)&&(a[e]=b[e]);return d.prototype=b.prototype,a.prototype=new d,a.__super__=b.prototype,a};SelectParser=function(){function SelectParser(){this.options_index=0,this.parsed=[]}return SelectParser.prototype.add_node=function(a){return"OPTGROUP"===a.nodeName.toUpperCase()?this.add_group(a):this.add_option(a)},SelectParser.prototype.add_group=function(a){var b,c,d,e,f,g;for(b=this.parsed.length,this.parsed.push({array_index:b,group:!0,label:this.escapeExpression(a.label),title:a.title?a.title:void 0,children:0,disabled:a.disabled,classes:a.className}),f=a.childNodes,g=[],d=0,e=f.length;e>d;d++)c=f[d],g.push(this.add_option(c,b,a.disabled));return g},SelectParser.prototype.add_option=function(a,b,c){return"OPTION"===a.nodeName.toUpperCase()?(""!==a.text?(null!=b&&(this.parsed[b].children+=1),this.parsed.push({array_index:this.parsed.length,options_index:this.options_index,value:a.value,text:a.text,html:a.innerHTML,title:a.title?a.title:void 0,selected:a.selected,disabled:c===!0?c:a.disabled,group_array_index:b,group_label:null!=b?this.parsed[b].label:null,classes:a.className,style:a.style.cssText})):this.parsed.push({array_index:this.parsed.length,options_index:this.options_index,empty:!0}),this.options_index+=1):void 0},SelectParser.prototype.escapeExpression=function(a){var b,c;return null==a||a===!1?"":/[\&\<\>\"\'\`]/.test(a)?(b={"<":"&lt;",">":"&gt;",'"':"&quot;","'":"&#x27;","`":"&#x60;"},c=/&(?!\w+;)|[\<\>\"\'\`]/g,a.replace(c,function(a){return b[a]||"&amp;"})):a},SelectParser}(),SelectParser.select_to_array=function(a){var b,c,d,e,f;for(c=new SelectParser,f=a.childNodes,d=0,e=f.length;e>d;d++)b=f[d],c.add_node(b);return c.parsed},AbstractChosen=function(){function AbstractChosen(a,b){this.form_field=a,this.options=null!=b?b:{},AbstractChosen.browser_is_supported()&&(this.is_multiple=this.form_field.multiple,this.set_default_text(),this.set_default_values(),this.setup(),this.set_up_html(),this.register_observers(),this.on_ready())}return AbstractChosen.prototype.set_default_values=function(){var a=this;return this.click_test_action=function(b){return a.test_active_click(b)},this.activate_action=function(b){return a.activate_field(b)},this.active_field=!1,this.mouse_on_container=!1,this.results_showing=!1,this.result_highlighted=null,this.allow_single_deselect=null!=this.options.allow_single_deselect&&null!=this.form_field.options[0]&&""===this.form_field.options[0].text?this.options.allow_single_deselect:!1,this.disable_search_threshold=this.options.disable_search_threshold||0,this.disable_search=this.options.disable_search||!1,this.enable_split_word_search=null!=this.options.enable_split_word_search?this.options.enable_split_word_search:!0,this.group_search=null!=this.options.group_search?this.options.group_search:!0,this.search_contains=this.options.search_contains||!1,this.single_backstroke_delete=null!=this.options.single_backstroke_delete?this.options.single_backstroke_delete:!0,this.max_selected_options=this.options.max_selected_options||1/0,this.inherit_select_classes=this.options.inherit_select_classes||!1,this.display_selected_options=null!=this.options.display_selected_options?this.options.display_selected_options:!0,this.display_disabled_options=null!=this.options.display_disabled_options?this.options.display_disabled_options:!0,this.include_group_label_in_selected=this.options.include_group_label_in_selected||!1},AbstractChosen.prototype.set_default_text=function(){return this.default_text=this.form_field.getAttribute("data-placeholder")?this.form_field.getAttribute("data-placeholder"):this.is_multiple?this.options.placeholder_text_multiple||this.options.placeholder_text||AbstractChosen.default_multiple_text:this.options.placeholder_text_single||this.options.placeholder_text||AbstractChosen.default_single_text,this.results_none_found=this.form_field.getAttribute("data-no_results_text")||this.options.no_results_text||AbstractChosen.default_no_result_text},AbstractChosen.prototype.choice_label=function(a){return this.include_group_label_in_selected&&null!=a.group_label?"<b class='group-name'>"+a.group_label+"</b>"+a.html:a.html},AbstractChosen.prototype.mouse_enter=function(){return this.mouse_on_container=!0},AbstractChosen.prototype.mouse_leave=function(){return this.mouse_on_container=!1},AbstractChosen.prototype.input_focus=function(){var a=this;if(this.is_multiple){if(!this.active_field)return setTimeout(function(){return a.container_mousedown()},50)}else if(!this.active_field)return this.activate_field()},AbstractChosen.prototype.input_blur=function(){var a=this;return this.mouse_on_container?void 0:(this.active_field=!1,setTimeout(function(){return a.blur_test()},100))},AbstractChosen.prototype.results_option_build=function(a){var b,c,d,e,f;for(b="",f=this.results_data,d=0,e=f.length;e>d;d++)c=f[d],b+=c.group?this.result_add_group(c):this.result_add_option(c),(null!=a?a.first:void 0)&&(c.selected&&this.is_multiple?this.choice_build(c):c.selected&&!this.is_multiple&&this.single_set_selected_text(this.choice_label(c)));return b},AbstractChosen.prototype.result_add_option=function(a){var b,c;return a.search_match?this.include_option_in_results(a)?(b=[],a.disabled||a.selected&&this.is_multiple||b.push("active-result"),!a.disabled||a.selected&&this.is_multiple||b.push("disabled-result"),a.selected&&b.push("result-selected"),null!=a.group_array_index&&b.push("group-option"),""!==a.classes&&b.push(a.classes),c=document.createElement("li"),c.className=b.join(" "),c.style.cssText=a.style,c.setAttribute("data-option-array-index",a.array_index),c.innerHTML=a.search_text,a.title&&(c.title=a.title),this.outerHTML(c)):"":""},AbstractChosen.prototype.result_add_group=function(a){var b,c;return a.search_match||a.group_match?a.active_options>0?(b=[],b.push("group-result"),a.classes&&b.push(a.classes),c=document.createElement("li"),c.className=b.join(" "),c.innerHTML=a.search_text,a.title&&(c.title=a.title),this.outerHTML(c)):"":""},AbstractChosen.prototype.results_update_field=function(){return this.set_default_text(),this.is_multiple||this.results_reset_cleanup(),this.result_clear_highlight(),this.results_build(),this.results_showing?this.winnow_results():void 0},AbstractChosen.prototype.reset_single_select_options=function(){var a,b,c,d,e;for(d=this.results_data,e=[],b=0,c=d.length;c>b;b++)a=d[b],a.selected?e.push(a.selected=!1):e.push(void 0);return e},AbstractChosen.prototype.results_toggle=function(){return this.results_showing?this.results_hide():this.results_show()},AbstractChosen.prototype.results_search=function(){return this.results_showing?this.winnow_results():this.results_show()},AbstractChosen.prototype.winnow_results=function(){var a,b,c,d,e,f,g,h,i,j,k,l;for(this.no_results_clear(),d=0,f=this.get_search_text(),a=f.replace(/[-[\]{}()*+?.,\\^$|#\s]/g,"\\$&"),i=new RegExp(a,"i"),c=this.get_search_regex(a),l=this.results_data,j=0,k=l.length;k>j;j++)b=l[j],b.search_match=!1,e=null,this.include_option_in_results(b)&&(b.group&&(b.group_match=!1,b.active_options=0),null!=b.group_array_index&&this.results_data[b.group_array_index]&&(e=this.results_data[b.group_array_index],0===e.active_options&&e.search_match&&(d+=1),e.active_options+=1),b.search_text=b.group?b.label:b.html,(!b.group||this.group_search)&&(b.search_match=this.search_string_match(b.search_text,c),b.search_match&&!b.group&&(d+=1),b.search_match?(f.length&&(g=b.search_text.search(i),h=b.search_text.substr(0,g+f.length)+"</em>"+b.search_text.substr(g+f.length),b.search_text=h.substr(0,g)+"<em>"+h.substr(g)),null!=e&&(e.group_match=!0)):null!=b.group_array_index&&this.results_data[b.group_array_index].search_match&&(b.search_match=!0)));return this.result_clear_highlight(),1>d&&f.length?(this.update_results_content(""),this.no_results(f)):(this.update_results_content(this.results_option_build()),this.winnow_results_set_highlight())},AbstractChosen.prototype.get_search_regex=function(a){var b;return b=this.search_contains?"":"^",new RegExp(b+a,"i")},AbstractChosen.prototype.search_string_match=function(a,b){var c,d,e,f;if(b.test(a))return!0;if(this.enable_split_word_search&&(a.indexOf(" ")>=0||0===a.indexOf("["))&&(d=a.replace(/\[|\]/g,"").split(" "),d.length))for(e=0,f=d.length;f>e;e++)if(c=d[e],b.test(c))return!0},AbstractChosen.prototype.choices_count=function(){var a,b,c,d;if(null!=this.selected_option_count)return this.selected_option_count;for(this.selected_option_count=0,d=this.form_field.options,b=0,c=d.length;c>b;b++)a=d[b],a.selected&&(this.selected_option_count+=1);return this.selected_option_count},AbstractChosen.prototype.choices_click=function(a){return a.preventDefault(),this.results_showing||this.is_disabled?void 0:this.results_show()},AbstractChosen.prototype.keyup_checker=function(a){var b,c;switch(b=null!=(c=a.which)?c:a.keyCode,this.search_field_scale(),b){case 8:if(this.is_multiple&&this.backstroke_length<1&&this.choices_count()>0)return this.keydown_backstroke();if(!this.pending_backstroke)return this.result_clear_highlight(),this.results_search();break;case 13:if(a.preventDefault(),this.results_showing)return this.result_select(a);break;case 27:return this.results_showing&&this.results_hide(),!0;case 9:case 38:case 40:case 16:case 91:case 17:break;default:return this.results_search()}},AbstractChosen.prototype.clipboard_event_checker=function(){var a=this;return setTimeout(function(){return a.results_search()},50)},AbstractChosen.prototype.container_width=function(){return null!=this.options.width?this.options.width:""+this.form_field.offsetWidth+"px"},AbstractChosen.prototype.include_option_in_results=function(a){return this.is_multiple&&!this.display_selected_options&&a.selected?!1:!this.display_disabled_options&&a.disabled?!1:a.empty?!1:!0},AbstractChosen.prototype.search_results_touchstart=function(a){return this.touch_started=!0,this.search_results_mouseover(a)},AbstractChosen.prototype.search_results_touchmove=function(a){return this.touch_started=!1,this.search_results_mouseout(a)},AbstractChosen.prototype.search_results_touchend=function(a){return this.touch_started?this.search_results_mouseup(a):void 0},AbstractChosen.prototype.outerHTML=function(a){var b;return a.outerHTML?a.outerHTML:(b=document.createElement("div"),b.appendChild(a),b.innerHTML)},AbstractChosen.browser_is_supported=function(){return"Microsoft Internet Explorer"===window.navigator.appName?document.documentMode>=8:/iP(od|hone)/i.test(window.navigator.userAgent)?!1:/Android/i.test(window.navigator.userAgent)&&/Mobile/i.test(window.navigator.userAgent)?!1:!0},AbstractChosen.default_multiple_text="Select Some Options",AbstractChosen.default_single_text="Select an Option",AbstractChosen.default_no_result_text="No results match",AbstractChosen}(),a=jQuery,a.fn.extend({chosen:function(b){return AbstractChosen.browser_is_supported()?this.each(function(){var c,d;c=a(this),d=c.data("chosen"),"destroy"===b&&d instanceof Chosen?d.destroy():d instanceof Chosen||c.data("chosen",new Chosen(this,b))}):this}}),Chosen=function(c){function Chosen(){return b=Chosen.__super__.constructor.apply(this,arguments)}return d(Chosen,c),Chosen.prototype.setup=function(){return this.form_field_jq=a(this.form_field),this.current_selectedIndex=this.form_field.selectedIndex,this.is_rtl=this.form_field_jq.hasClass("chosen-rtl")},Chosen.prototype.set_up_html=function(){var b,c;return b=["chosen-container"],b.push("chosen-container-"+(this.is_multiple?"multi":"single")),this.inherit_select_classes&&this.form_field.className&&b.push(this.form_field.className),this.is_rtl&&b.push("chosen-rtl"),c={"class":b.join(" "),style:"width: "+this.container_width()+";",title:this.form_field.title},this.form_field.id.length&&(c.id=this.form_field.id.replace(/[^\w]/g,"_")+"_chosen"),this.container=a("<div />",c),this.is_multiple?this.container.html('<ul class="chosen-choices"><li class="search-field"><input type="text" value="'+this.default_text+'" class="default" autocomplete="off" style="width:25px;" /></li></ul><div class="chosen-drop"><ul class="chosen-results"></ul></div>'):this.container.html('<a class="chosen-single chosen-default" tabindex="-1"><span>'+this.default_text+'</span><div><b></b></div></a><div class="chosen-drop"><div class="chosen-search"><input type="text" autocomplete="off" /></div><ul class="chosen-results"></ul></div>'),this.form_field_jq.hide().after(this.container),this.dropdown=this.container.find("div.chosen-drop").first(),this.search_field=this.container.find("input").first(),this.search_results=this.container.find("ul.chosen-results").first(),this.search_field_scale(),this.search_no_results=this.container.find("li.no-results").first(),this.is_multiple?(this.search_choices=this.container.find("ul.chosen-choices").first(),this.search_container=this.container.find("li.search-field").first()):(this.search_container=this.container.find("div.chosen-search").first(),this.selected_item=this.container.find(".chosen-single").first()),this.results_build(),this.set_tab_index(),this.set_label_behavior()},Chosen.prototype.on_ready=function(){return this.form_field_jq.trigger("chosen:ready",{chosen:this})},Chosen.prototype.register_observers=function(){var a=this;return this.container.bind("touchstart.chosen",function(b){return a.container_mousedown(b),b.preventDefault()}),this.container.bind("touchend.chosen",function(b){return a.container_mouseup(b),b.preventDefault()}),this.container.bind("mousedown.chosen",function(b){a.container_mousedown(b)}),this.container.bind("mouseup.chosen",function(b){a.container_mouseup(b)}),this.container.bind("mouseenter.chosen",function(b){a.mouse_enter(b)}),this.container.bind("mouseleave.chosen",function(b){a.mouse_leave(b)}),this.search_results.bind("mouseup.chosen",function(b){a.search_results_mouseup(b)}),this.search_results.bind("mouseover.chosen",function(b){a.search_results_mouseover(b)}),this.search_results.bind("mouseout.chosen",function(b){a.search_results_mouseout(b)}),this.search_results.bind("mousewheel.chosen DOMMouseScroll.chosen",function(b){a.search_results_mousewheel(b)}),this.search_results.bind("touchstart.chosen",function(b){a.search_results_touchstart(b)}),this.search_results.bind("touchmove.chosen",function(b){a.search_results_touchmove(b)}),this.search_results.bind("touchend.chosen",function(b){a.search_results_touchend(b)}),this.form_field_jq.bind("chosen:updated.chosen",function(b){a.results_update_field(b)}),this.form_field_jq.bind("chosen:activate.chosen",function(b){a.activate_field(b)}),this.form_field_jq.bind("chosen:open.chosen",function(b){a.container_mousedown(b)}),this.form_field_jq.bind("chosen:close.chosen",function(b){a.input_blur(b)}),this.search_field.bind("blur.chosen",function(b){a.input_blur(b)}),this.search_field.bind("keyup.chosen",function(b){a.keyup_checker(b)}),this.search_field.bind("keydown.chosen",function(b){a.keydown_checker(b)}),this.search_field.bind("focus.chosen",function(b){a.input_focus(b)}),this.search_field.bind("cut.chosen",function(b){a.clipboard_event_checker(b)}),this.search_field.bind("paste.chosen",function(b){a.clipboard_event_checker(b)}),this.is_multiple?this.search_choices.bind("click.chosen",function(b){a.choices_click(b)}):this.container.bind("click.chosen",function(a){a.preventDefault()})},Chosen.prototype.destroy=function(){return a(this.container[0].ownerDocument).unbind("click.chosen",this.click_test_action),this.search_field[0].tabIndex&&(this.form_field_jq[0].tabIndex=this.search_field[0].tabIndex),this.container.remove(),this.form_field_jq.removeData("chosen"),this.form_field_jq.show()},Chosen.prototype.search_field_disabled=function(){return this.is_disabled=this.form_field_jq[0].disabled,this.is_disabled?(this.container.addClass("chosen-disabled"),this.search_field[0].disabled=!0,this.is_multiple||this.selected_item.unbind("focus.chosen",this.activate_action),this.close_field()):(this.container.removeClass("chosen-disabled"),this.search_field[0].disabled=!1,this.is_multiple?void 0:this.selected_item.bind("focus.chosen",this.activate_action))},Chosen.prototype.container_mousedown=function(b){return this.is_disabled||(b&&"mousedown"===b.type&&!this.results_showing&&b.preventDefault(),null!=b&&a(b.target).hasClass("search-choice-close"))?void 0:(this.active_field?this.is_multiple||!b||a(b.target)[0]!==this.selected_item[0]&&!a(b.target).parents("a.chosen-single").length||(b.preventDefault(),this.results_toggle()):(this.is_multiple&&this.search_field.val(""),a(this.container[0].ownerDocument).bind("click.chosen",this.click_test_action),this.results_show()),this.activate_field())},Chosen.prototype.container_mouseup=function(a){return"ABBR"!==a.target.nodeName||this.is_disabled?void 0:this.results_reset(a)},Chosen.prototype.search_results_mousewheel=function(a){var b;return a.originalEvent&&(b=a.originalEvent.deltaY||-a.originalEvent.wheelDelta||a.originalEvent.detail),null!=b?(a.preventDefault(),"DOMMouseScroll"===a.type&&(b=40*b),this.search_results.scrollTop(b+this.search_results.scrollTop())):void 0},Chosen.prototype.blur_test=function(){return!this.active_field&&this.container.hasClass("chosen-container-active")?this.close_field():void 0},Chosen.prototype.close_field=function(){return a(this.container[0].ownerDocument).unbind("click.chosen",this.click_test_action),this.active_field=!1,this.results_hide(),this.container.removeClass("chosen-container-active"),this.clear_backstroke(),this.show_search_field_default(),this.search_field_scale()},Chosen.prototype.activate_field=function(){return this.container.addClass("chosen-container-active"),this.active_field=!0,this.search_field.val(this.search_field.val()),this.search_field.focus()},Chosen.prototype.test_active_click=function(b){var c;return c=a(b.target).closest(".chosen-container"),c.length&&this.container[0]===c[0]?this.active_field=!0:this.close_field()},Chosen.prototype.results_build=function(){return this.parsing=!0,this.selected_option_count=null,this.results_data=SelectParser.select_to_array(this.form_field),this.is_multiple?this.search_choices.find("li.search-choice").remove():this.is_multiple||(this.single_set_selected_text(),this.disable_search||this.form_field.options.length<=this.disable_search_threshold?(this.search_field[0].readOnly=!0,this.container.addClass("chosen-container-single-nosearch")):(this.search_field[0].readOnly=!1,this.container.removeClass("chosen-container-single-nosearch"))),this.update_results_content(this.results_option_build({first:!0})),this.search_field_disabled(),this.show_search_field_default(),this.search_field_scale(),this.parsing=!1},Chosen.prototype.result_do_highlight=function(a){var b,c,d,e,f;if(a.length){if(this.result_clear_highlight(),this.result_highlight=a,this.result_highlight.addClass("highlighted"),d=parseInt(this.search_results.css("maxHeight"),10),f=this.search_results.scrollTop(),e=d+f,c=this.result_highlight.position().top+this.search_results.scrollTop(),b=c+this.result_highlight.outerHeight(),b>=e)return this.search_results.scrollTop(b-d>0?b-d:0);if(f>c)return this.search_results.scrollTop(c)}},Chosen.prototype.result_clear_highlight=function(){return this.result_highlight&&this.result_highlight.removeClass("highlighted"),this.result_highlight=null},Chosen.prototype.results_show=function(){return this.is_multiple&&this.max_selected_options<=this.choices_count()?(this.form_field_jq.trigger("chosen:maxselected",{chosen:this}),!1):(this.container.addClass("chosen-with-drop"),this.results_showing=!0,this.search_field.focus(),this.search_field.val(this.search_field.val()),this.winnow_results(),this.form_field_jq.trigger("chosen:showing_dropdown",{chosen:this}))},Chosen.prototype.update_results_content=function(a){return this.search_results.html(a)},Chosen.prototype.results_hide=function(){return this.results_showing&&(this.result_clear_highlight(),this.container.removeClass("chosen-with-drop"),this.form_field_jq.trigger("chosen:hiding_dropdown",{chosen:this})),this.results_showing=!1},Chosen.prototype.set_tab_index=function(){var a;return this.form_field.tabIndex?(a=this.form_field.tabIndex,this.form_field.tabIndex=-1,this.search_field[0].tabIndex=a):void 0},Chosen.prototype.set_label_behavior=function(){var b=this;return this.form_field_label=this.form_field_jq.parents("label"),!this.form_field_label.length&&this.form_field.id.length&&(this.form_field_label=a("label[for='"+this.form_field.id+"']")),this.form_field_label.length>0?this.form_field_label.bind("click.chosen",function(a){return b.is_multiple?b.container_mousedown(a):b.activate_field()}):void 0},Chosen.prototype.show_search_field_default=function(){return this.is_multiple&&this.choices_count()<1&&!this.active_field?(this.search_field.val(this.default_text),this.search_field.addClass("default")):(this.search_field.val(""),this.search_field.removeClass("default"))},Chosen.prototype.search_results_mouseup=function(b){var c;return c=a(b.target).hasClass("active-result")?a(b.target):a(b.target).parents(".active-result").first(),c.length?(this.result_highlight=c,this.result_select(b),this.search_field.focus()):void 0},Chosen.prototype.search_results_mouseover=function(b){var c;return c=a(b.target).hasClass("active-result")?a(b.target):a(b.target).parents(".active-result").first(),c?this.result_do_highlight(c):void 0},Chosen.prototype.search_results_mouseout=function(b){return a(b.target).hasClass("active-result")?this.result_clear_highlight():void 0},Chosen.prototype.choice_build=function(b){var c,d,e=this;return c=a("<li />",{"class":"search-choice"}).html("<span>"+this.choice_label(b)+"</span>"),b.disabled?c.addClass("search-choice-disabled"):(d=a("<a />",{"class":"search-choice-close","data-option-array-index":b.array_index}),d.bind("click.chosen",function(a){return e.choice_destroy_link_click(a)}),c.append(d)),this.search_container.before(c)},Chosen.prototype.choice_destroy_link_click=function(b){return b.preventDefault(),b.stopPropagation(),this.is_disabled?void 0:this.choice_destroy(a(b.target))},Chosen.prototype.choice_destroy=function(a){return this.result_deselect(a[0].getAttribute("data-option-array-index"))?(this.show_search_field_default(),this.is_multiple&&this.choices_count()>0&&this.search_field.val().length<1&&this.results_hide(),a.parents("li").first().remove(),this.search_field_scale()):void 0},Chosen.prototype.results_reset=function(){return this.reset_single_select_options(),this.form_field.options[0].selected=!0,this.single_set_selected_text(),this.show_search_field_default(),this.results_reset_cleanup(),this.form_field_jq.trigger("change"),this.active_field?this.results_hide():void 0},Chosen.prototype.results_reset_cleanup=function(){return this.current_selectedIndex=this.form_field.selectedIndex,this.selected_item.find("abbr").remove()},Chosen.prototype.result_select=function(a){var b,c;return this.result_highlight?(b=this.result_highlight,this.result_clear_highlight(),this.is_multiple&&this.max_selected_options<=this.choices_count()?(this.form_field_jq.trigger("chosen:maxselected",{chosen:this}),!1):(this.is_multiple?b.removeClass("active-result"):this.reset_single_select_options(),b.addClass("result-selected"),c=this.results_data[b[0].getAttribute("data-option-array-index")],c.selected=!0,this.form_field.options[c.options_index].selected=!0,this.selected_option_count=null,this.is_multiple?this.choice_build(c):this.single_set_selected_text(this.choice_label(c)),(a.metaKey||a.ctrlKey)&&this.is_multiple||this.results_hide(),this.search_field.val(""),(this.is_multiple||this.form_field.selectedIndex!==this.current_selectedIndex)&&this.form_field_jq.trigger("change",{selected:this.form_field.options[c.options_index].value}),this.current_selectedIndex=this.form_field.selectedIndex,a.preventDefault(),this.search_field_scale())):void 0},Chosen.prototype.single_set_selected_text=function(a){return null==a&&(a=this.default_text),a===this.default_text?this.selected_item.addClass("chosen-default"):(this.single_deselect_control_build(),this.selected_item.removeClass("chosen-default")),this.selected_item.find("span").html(a)},Chosen.prototype.result_deselect=function(a){var b;return b=this.results_data[a],this.form_field.options[b.options_index].disabled?!1:(b.selected=!1,this.form_field.options[b.options_index].selected=!1,this.selected_option_count=null,this.result_clear_highlight(),this.results_showing&&this.winnow_results(),this.form_field_jq.trigger("change",{deselected:this.form_field.options[b.options_index].value}),this.search_field_scale(),!0)},Chosen.prototype.single_deselect_control_build=function(){return this.allow_single_deselect?(this.selected_item.find("abbr").length||this.selected_item.find("span").first().after('<abbr class="search-choice-close"></abbr>'),this.selected_item.addClass("chosen-single-with-deselect")):void 0},Chosen.prototype.get_search_text=function(){return a("<div/>").text(a.trim(this.search_field.val())).html()},Chosen.prototype.winnow_results_set_highlight=function(){var a,b;return b=this.is_multiple?[]:this.search_results.find(".result-selected.active-result"),a=b.length?b.first():this.search_results.find(".active-result").first(),null!=a?this.result_do_highlight(a):void 0},Chosen.prototype.no_results=function(b){var c;return c=a('<li class="no-results">'+this.results_none_found+' "<span></span>"</li>'),c.find("span").first().html(b),this.search_results.append(c),this.form_field_jq.trigger("chosen:no_results",{chosen:this})},Chosen.prototype.no_results_clear=function(){return this.search_results.find(".no-results").remove()},Chosen.prototype.keydown_arrow=function(){var a;return this.results_showing&&this.result_highlight?(a=this.result_highlight.nextAll("li.active-result").first())?this.result_do_highlight(a):void 0:this.results_show()},Chosen.prototype.keyup_arrow=function(){var a;return this.results_showing||this.is_multiple?this.result_highlight?(a=this.result_highlight.prevAll("li.active-result"),a.length?this.result_do_highlight(a.first()):(this.choices_count()>0&&this.results_hide(),this.result_clear_highlight())):void 0:this.results_show()},Chosen.prototype.keydown_backstroke=function(){var a;return this.pending_backstroke?(this.choice_destroy(this.pending_backstroke.find("a").first()),this.clear_backstroke()):(a=this.search_container.siblings("li.search-choice").last(),a.length&&!a.hasClass("search-choice-disabled")?(this.pending_backstroke=a,this.single_backstroke_delete?this.keydown_backstroke():this.pending_backstroke.addClass("search-choice-focus")):void 0)},Chosen.prototype.clear_backstroke=function(){return this.pending_backstroke&&this.pending_backstroke.removeClass("search-choice-focus"),this.pending_backstroke=null},Chosen.prototype.keydown_checker=function(a){var b,c;switch(b=null!=(c=a.which)?c:a.keyCode,this.search_field_scale(),8!==b&&this.pending_backstroke&&this.clear_backstroke(),b){case 8:this.backstroke_length=this.search_field.val().length;break;case 9:this.results_showing&&!this.is_multiple&&this.result_select(a),this.mouse_on_container=!1;break;case 13:this.results_showing&&a.preventDefault();break;case 32:this.disable_search&&a.preventDefault();break;case 38:a.preventDefault(),this.keyup_arrow();break;case 40:a.preventDefault(),this.keydown_arrow()}},Chosen.prototype.search_field_scale=function(){var b,c,d,e,f,g,h,i,j;if(this.is_multiple){for(d=0,h=0,f="position:absolute; left: -1000px; top: -1000px; display:none;",g=["font-size","font-style","font-weight","font-family","line-height","text-transform","letter-spacing"],i=0,j=g.length;j>i;i++)e=g[i],f+=e+":"+this.search_field.css(e)+";";return b=a("<div />",{style:f}),b.text(this.search_field.val()),a("body").append(b),h=b.width()+25,b.remove(),c=this.container.outerWidth(),h>c-10&&(h=c-10),this.search_field.css({width:h+"px"})}},Chosen}(AbstractChosen)}).call(this);
\ No newline at end of file
/*!
* fancyBox - jQuery Plugin
* version: 2.1.5 (Fri, 14 Jun 2013)
* @requires jQuery v1.6 or later
*
* Examples at http://fancyapps.com/fancybox/
* License: www.fancyapps.com/fancybox/#license
*
* Copyright 2012 Janis Skarnelis - janis@fancyapps.com
*
*/
(function (window, document, $, undefined) {
"use strict";
var H = $("html"),
W = $(window),
D = $(document),
F = $.fancybox = function () {
F.open.apply( this, arguments );
},
IE = navigator.userAgent.match(/msie/i),
didUpdate = null,
isTouch = document.createTouch !== undefined,
isQuery = function(obj) {
return obj && obj.hasOwnProperty && obj instanceof $;
},
isString = function(str) {
return str && $.type(str) === "string";
},
isPercentage = function(str) {
return isString(str) && str.indexOf('%') > 0;
},
isScrollable = function(el) {
return (el && !(el.style.overflow && el.style.overflow === 'hidden') && ((el.clientWidth && el.scrollWidth > el.clientWidth) || (el.clientHeight && el.scrollHeight > el.clientHeight)));
},
getScalar = function(orig, dim) {
var value = parseInt(orig, 10) || 0;
if (dim && isPercentage(orig)) {
value = F.getViewport()[ dim ] / 100 * value;
}
return Math.ceil(value);
},
getValue = function(value, dim) {
return getScalar(value, dim) + 'px';
};
$.extend(F, {
// The current version of fancyBox
version: '2.1.5',
defaults: {
padding : 15,
margin : 20,
width : 800,
height : 600,
minWidth : 100,
minHeight : 100,
maxWidth : 9999,
maxHeight : 9999,
pixelRatio: 1, // Set to 2 for retina display support
autoSize : true,
autoHeight : false,
autoWidth : false,
autoResize : true,
autoCenter : !isTouch,
fitToView : true,
aspectRatio : false,
topRatio : 0.5,
leftRatio : 0.5,
scrolling : 'auto', // 'auto', 'yes' or 'no'
wrapCSS : '',
arrows : true,
closeBtn : true,
closeClick : false,
nextClick : false,
mouseWheel : true,
autoPlay : false,
playSpeed : 3000,
preload : 3,
modal : false,
loop : true,
ajax : {
dataType : 'html',
headers : { 'X-fancyBox': true }
},
iframe : {
scrolling : 'auto',
preload : true
},
swf : {
wmode: 'transparent',
allowfullscreen : 'true',
allowscriptaccess : 'always'
},
keys : {
next : {
13 : 'left', // enter
34 : 'up', // page down
39 : 'left', // right arrow
40 : 'up' // down arrow
},
prev : {
8 : 'right', // backspace
33 : 'down', // page up
37 : 'right', // left arrow
38 : 'down' // up arrow
},
close : [27], // escape key
play : [32], // space - start/stop slideshow
toggle : [70] // letter "f" - toggle fullscreen
},
direction : {
next : 'left',
prev : 'right'
},
scrollOutside : true,
// Override some properties
index : 0,
type : null,
href : null,
content : null,
title : null,
// HTML templates
tpl: {
wrap : '<div class="fancybox-wrap" tabIndex="-1"><div class="fancybox-skin"><div class="fancybox-outer"><div class="fancybox-inner"></div></div></div></div>',
image : '<img class="fancybox-image" src="{href}" alt="" />',
iframe : '<iframe id="fancybox-frame{rnd}" name="fancybox-frame{rnd}" class="fancybox-iframe" frameborder="0" vspace="0" hspace="0" webkitAllowFullScreen mozallowfullscreen allowFullScreen' + (IE ? ' allowtransparency="true"' : '') + '></iframe>',
error : '<p class="fancybox-error">The requested content cannot be loaded.<br/>Please try again later.</p>',
closeBtn : '<a title="Close" class="fancybox-item fancybox-close" href="javascript:;"></a>',
next : '<a title="Next" class="fancybox-nav fancybox-next" href="javascript:;"><span></span></a>',
prev : '<a title="Previous" class="fancybox-nav fancybox-prev" href="javascript:;"><span></span></a>'
},
// Properties for each animation type
// Opening fancyBox
openEffect : 'fade', // 'elastic', 'fade' or 'none'
openSpeed : 250,
openEasing : 'swing',
openOpacity : true,
openMethod : 'zoomIn',
// Closing fancyBox
closeEffect : 'fade', // 'elastic', 'fade' or 'none'
closeSpeed : 250,
closeEasing : 'swing',
closeOpacity : true,
closeMethod : 'zoomOut',
// Changing next gallery item
nextEffect : 'elastic', // 'elastic', 'fade' or 'none'
nextSpeed : 250,
nextEasing : 'swing',
nextMethod : 'changeIn',
// Changing previous gallery item
prevEffect : 'elastic', // 'elastic', 'fade' or 'none'
prevSpeed : 250,
prevEasing : 'swing',
prevMethod : 'changeOut',
// Enable default helpers
helpers : {
overlay : true,
title : true
},
// Callbacks
onCancel : $.noop, // If canceling
beforeLoad : $.noop, // Before loading
afterLoad : $.noop, // After loading
beforeShow : $.noop, // Before changing in current item
afterShow : $.noop, // After opening
beforeChange : $.noop, // Before changing gallery item
beforeClose : $.noop, // Before closing
afterClose : $.noop // After closing
},
//Current state
group : {}, // Selected group
opts : {}, // Group options
previous : null, // Previous element
coming : null, // Element being loaded
current : null, // Currently loaded element
isActive : false, // Is activated
isOpen : false, // Is currently open
isOpened : false, // Have been fully opened at least once
wrap : null,
skin : null,
outer : null,
inner : null,
player : {
timer : null,
isActive : false
},
// Loaders
ajaxLoad : null,
imgPreload : null,
// Some collections
transitions : {},
helpers : {},
/*
* Static methods
*/
open: function (group, opts) {
if (!group) {
return;
}
if (!$.isPlainObject(opts)) {
opts = {};
}
// Close if already active
if (false === F.close(true)) {
return;
}
// Normalize group
if (!$.isArray(group)) {
group = isQuery(group) ? $(group).get() : [group];
}
// Recheck if the type of each element is `object` and set content type (image, ajax, etc)
$.each(group, function(i, element) {
var obj = {},
href,
title,
content,
type,
rez,
hrefParts,
selector;
if ($.type(element) === "object") {
// Check if is DOM element
if (element.nodeType) {
element = $(element);
}
if (isQuery(element)) {
obj = {
href : element.data('fancybox-href') || element.attr('href'),
title : element.data('fancybox-title') || element.attr('title'),
isDom : true,
element : element
};
if ($.metadata) {
$.extend(true, obj, element.metadata());
}
} else {
obj = element;
}
}
href = opts.href || obj.href || (isString(element) ? element : null);
title = opts.title !== undefined ? opts.title : obj.title || '';
content = opts.content || obj.content;
type = content ? 'html' : (opts.type || obj.type);
if (!type && obj.isDom) {
type = element.data('fancybox-type');
if (!type) {
rez = element.prop('class').match(/fancybox\.(\w+)/);
type = rez ? rez[1] : null;
}
}
if (isString(href)) {
// Try to guess the content type
if (!type) {
if (F.isImage(href)) {
type = 'image';
} else if (F.isSWF(href)) {
type = 'swf';
} else if (href.charAt(0) === '#') {
type = 'inline';
} else if (isString(element)) {
type = 'html';
content = element;
}
}
// Split url into two pieces with source url and content selector, e.g,
// "/mypage.html #my_id" will load "/mypage.html" and display element having id "my_id"
if (type === 'ajax') {
hrefParts = href.split(/\s+/, 2);
href = hrefParts.shift();
selector = hrefParts.shift();
}
}
if (!content) {
if (type === 'inline') {
if (href) {
content = $( isString(href) ? href.replace(/.*(?=#[^\s]+$)/, '') : href ); //strip for ie7
} else if (obj.isDom) {
content = element;
}
} else if (type === 'html') {
content = href;
} else if (!type && !href && obj.isDom) {
type = 'inline';
content = element;
}
}
$.extend(obj, {
href : href,
type : type,
content : content,
title : title,
selector : selector
});
group[ i ] = obj;
});
// Extend the defaults
F.opts = $.extend(true, {}, F.defaults, opts);
// All options are merged recursive except keys
if (opts.keys !== undefined) {
F.opts.keys = opts.keys ? $.extend({}, F.defaults.keys, opts.keys) : false;
}
F.group = group;
return F._start(F.opts.index);
},
// Cancel image loading or abort ajax request
cancel: function () {
var coming = F.coming;
if (!coming || false === F.trigger('onCancel')) {
return;
}
F.hideLoading();
if (F.ajaxLoad) {
F.ajaxLoad.abort();
}
F.ajaxLoad = null;
if (F.imgPreload) {
F.imgPreload.onload = F.imgPreload.onerror = null;
}
if (coming.wrap) {
coming.wrap.stop(true, true).trigger('onReset').remove();
}
F.coming = null;
// If the first item has been canceled, then clear everything
if (!F.current) {
F._afterZoomOut( coming );
}
},
// Start closing animation if is open; remove immediately if opening/closing
close: function (event) {
F.cancel();
if (false === F.trigger('beforeClose')) {
return;
}
F.unbindEvents();
if (!F.isActive) {
return;
}
if (!F.isOpen || event === true) {
$('.fancybox-wrap').stop(true).trigger('onReset').remove();
F._afterZoomOut();
} else {
F.isOpen = F.isOpened = false;
F.isClosing = true;
$('.fancybox-item, .fancybox-nav').remove();
F.wrap.stop(true, true).removeClass('fancybox-opened');
F.transitions[ F.current.closeMethod ]();
}
},
// Manage slideshow:
// $.fancybox.play(); - toggle slideshow
// $.fancybox.play( true ); - start
// $.fancybox.play( false ); - stop
play: function ( action ) {
var clear = function () {
clearTimeout(F.player.timer);
},
set = function () {
clear();
if (F.current && F.player.isActive) {
F.player.timer = setTimeout(F.next, F.current.playSpeed);
}
},
stop = function () {
clear();
D.unbind('.player');
F.player.isActive = false;
F.trigger('onPlayEnd');
},
start = function () {
if (F.current && (F.current.loop || F.current.index < F.group.length - 1)) {
F.player.isActive = true;
D.bind({
'onCancel.player beforeClose.player' : stop,
'onUpdate.player' : set,
'beforeLoad.player' : clear
});
set();
F.trigger('onPlayStart');
}
};
if (action === true || (!F.player.isActive && action !== false)) {
start();
} else {
stop();
}
},
// Navigate to next gallery item
next: function ( direction ) {
var current = F.current;
if (current) {
if (!isString(direction)) {
direction = current.direction.next;
}
F.jumpto(current.index + 1, direction, 'next');
}
},
// Navigate to previous gallery item
prev: function ( direction ) {
var current = F.current;
if (current) {
if (!isString(direction)) {
direction = current.direction.prev;
}
F.jumpto(current.index - 1, direction, 'prev');
}
},
// Navigate to gallery item by index
jumpto: function ( index, direction, router ) {
var current = F.current;
if (!current) {
return;
}
index = getScalar(index);
F.direction = direction || current.direction[ (index >= current.index ? 'next' : 'prev') ];
F.router = router || 'jumpto';
if (current.loop) {
if (index < 0) {
index = current.group.length + (index % current.group.length);
}
index = index % current.group.length;
}
if (current.group[ index ] !== undefined) {
F.cancel();
F._start(index);
}
},
// Center inside viewport and toggle position type to fixed or absolute if needed
reposition: function (e, onlyAbsolute) {
var current = F.current,
wrap = current ? current.wrap : null,
pos;
if (wrap) {
pos = F._getPosition(onlyAbsolute);
if (e && e.type === 'scroll') {
delete pos.position;
wrap.stop(true, true).animate(pos, 200);
} else {
wrap.css(pos);
current.pos = $.extend({}, current.dim, pos);
}
}
},
update: function (e) {
var type = (e && e.type),
anyway = !type || type === 'orientationchange';
if (anyway) {
clearTimeout(didUpdate);
didUpdate = null;
}
if (!F.isOpen || didUpdate) {
return;
}
didUpdate = setTimeout(function() {
var current = F.current;
if (!current || F.isClosing) {
return;
}
F.wrap.removeClass('fancybox-tmp');
if (anyway || type === 'load' || (type === 'resize' && current.autoResize)) {
F._setDimension();
}
if (!(type === 'scroll' && current.canShrink)) {
F.reposition(e);
}
F.trigger('onUpdate');
didUpdate = null;
}, (anyway && !isTouch ? 0 : 300));
},
// Shrink content to fit inside viewport or restore if resized
toggle: function ( action ) {
if (F.isOpen) {
F.current.fitToView = $.type(action) === "boolean" ? action : !F.current.fitToView;
// Help browser to restore document dimensions
if (isTouch) {
F.wrap.removeAttr('style').addClass('fancybox-tmp');
F.trigger('onUpdate');
}
F.update();
}
},
hideLoading: function () {
D.unbind('.loading');
$('#fancybox-loading').remove();
},
showLoading: function () {
var el, viewport;
F.hideLoading();
el = $('<div id="fancybox-loading"><div></div></div>').click(F.cancel).appendTo('body');
// If user will press the escape-button, the request will be canceled
D.bind('keydown.loading', function(e) {
if ((e.which || e.keyCode) === 27) {
e.preventDefault();
F.cancel();
}
});
if (!F.defaults.fixed) {
viewport = F.getViewport();
el.css({
position : 'absolute',
top : (viewport.h * 0.5) + viewport.y,
left : (viewport.w * 0.5) + viewport.x
});
}
},
getViewport: function () {
var locked = (F.current && F.current.locked) || false,
rez = {
x: W.scrollLeft(),
y: W.scrollTop()
};
if (locked) {
rez.w = locked[0].clientWidth;
rez.h = locked[0].clientHeight;
} else {
// See http://bugs.jquery.com/ticket/6724
rez.w = isTouch && window.innerWidth ? window.innerWidth : W.width();
rez.h = isTouch && window.innerHeight ? window.innerHeight : W.height();
}
return rez;
},
// Unbind the keyboard / clicking actions
unbindEvents: function () {
if (F.wrap && isQuery(F.wrap)) {
F.wrap.unbind('.fb');
}
D.unbind('.fb');
W.unbind('.fb');
},
bindEvents: function () {
var current = F.current,
keys;
if (!current) {
return;
}
// Changing document height on iOS devices triggers a 'resize' event,
// that can change document height... repeating infinitely
W.bind('orientationchange.fb' + (isTouch ? '' : ' resize.fb') + (current.autoCenter && !current.locked ? ' scroll.fb' : ''), F.update);
keys = current.keys;
if (keys) {
D.bind('keydown.fb', function (e) {
var code = e.which || e.keyCode,
target = e.target || e.srcElement;
// Skip esc key if loading, because showLoading will cancel preloading
if (code === 27 && F.coming) {
return false;
}
// Ignore key combinations and key events within form elements
if (!e.ctrlKey && !e.altKey && !e.shiftKey && !e.metaKey && !(target && (target.type || $(target).is('[contenteditable]')))) {
$.each(keys, function(i, val) {
if (current.group.length > 1 && val[ code ] !== undefined) {
F[ i ]( val[ code ] );
e.preventDefault();
return false;
}
if ($.inArray(code, val) > -1) {
F[ i ] ();
e.preventDefault();
return false;
}
});
}
});
}
if ($.fn.mousewheel && current.mouseWheel) {
F.wrap.bind('mousewheel.fb', function (e, delta, deltaX, deltaY) {
var target = e.target || null,
parent = $(target),
canScroll = false;
while (parent.length) {
if (canScroll || parent.is('.fancybox-skin') || parent.is('.fancybox-wrap')) {
break;
}
canScroll = isScrollable( parent[0] );
parent = $(parent).parent();
}
if (delta !== 0 && !canScroll) {
if (F.group.length > 1 && !current.canShrink) {
if (deltaY > 0 || deltaX > 0) {
F.prev( deltaY > 0 ? 'down' : 'left' );
} else if (deltaY < 0 || deltaX < 0) {
F.next( deltaY < 0 ? 'up' : 'right' );
}
e.preventDefault();
}
}
});
}
},
trigger: function (event, o) {
var ret, obj = o || F.coming || F.current;
if (!obj) {
return;
}
if ($.isFunction( obj[event] )) {
ret = obj[event].apply(obj, Array.prototype.slice.call(arguments, 1));
}
if (ret === false) {
return false;
}
if (obj.helpers) {
$.each(obj.helpers, function (helper, opts) {
if (opts && F.helpers[helper] && $.isFunction(F.helpers[helper][event])) {
F.helpers[helper][event]($.extend(true, {}, F.helpers[helper].defaults, opts), obj);
}
});
}
D.trigger(event);
},
isImage: function (str) {
return isString(str) && str.match(/(^data:image\/.*,)|(\.(jp(e|g|eg)|gif|png|bmp|webp|svg)((\?|#).*)?$)/i);
},
isSWF: function (str) {
return isString(str) && str.match(/\.(swf)((\?|#).*)?$/i);
},
_start: function (index) {
var coming = {},
obj,
href,
type,
margin,
padding;
index = getScalar( index );
obj = F.group[ index ] || null;
if (!obj) {
return false;
}
coming = $.extend(true, {}, F.opts, obj);
// Convert margin and padding properties to array - top, right, bottom, left
margin = coming.margin;
padding = coming.padding;
if ($.type(margin) === 'number') {
coming.margin = [margin, margin, margin, margin];
}
if ($.type(padding) === 'number') {
coming.padding = [padding, padding, padding, padding];
}
// 'modal' propery is just a shortcut
if (coming.modal) {
$.extend(true, coming, {
closeBtn : false,
closeClick : false,
nextClick : false,
arrows : false,
mouseWheel : false,
keys : null,
helpers: {
overlay : {
closeClick : false
}
}
});
}
// 'autoSize' property is a shortcut, too
if (coming.autoSize) {
coming.autoWidth = coming.autoHeight = true;
}
if (coming.width === 'auto') {
coming.autoWidth = true;
}
if (coming.height === 'auto') {
coming.autoHeight = true;
}
/*
* Add reference to the group, so it`s possible to access from callbacks, example:
* afterLoad : function() {
* this.title = 'Image ' + (this.index + 1) + ' of ' + this.group.length + (this.title ? ' - ' + this.title : '');
* }
*/
coming.group = F.group;
coming.index = index;
// Give a chance for callback or helpers to update coming item (type, title, etc)
F.coming = coming;
if (false === F.trigger('beforeLoad')) {
F.coming = null;
return;
}
type = coming.type;
href = coming.href;
if (!type) {
F.coming = null;
//If we can not determine content type then drop silently or display next/prev item if looping through gallery
if (F.current && F.router && F.router !== 'jumpto') {
F.current.index = index;
return F[ F.router ]( F.direction );
}
return false;
}
F.isActive = true;
if (type === 'image' || type === 'swf') {
coming.autoHeight = coming.autoWidth = false;
coming.scrolling = 'visible';
}
if (type === 'image') {
coming.aspectRatio = true;
}
if (type === 'iframe' && isTouch) {
coming.scrolling = 'scroll';
}
// Build the neccessary markup
coming.wrap = $(coming.tpl.wrap).addClass('fancybox-' + (isTouch ? 'mobile' : 'desktop') + ' fancybox-type-' + type + ' fancybox-tmp ' + coming.wrapCSS).appendTo( coming.parent || 'body' );
$.extend(coming, {
skin : $('.fancybox-skin', coming.wrap),
outer : $('.fancybox-outer', coming.wrap),
inner : $('.fancybox-inner', coming.wrap)
});
$.each(["Top", "Right", "Bottom", "Left"], function(i, v) {
coming.skin.css('padding' + v, getValue(coming.padding[ i ]));
});
F.trigger('onReady');
// Check before try to load; 'inline' and 'html' types need content, others - href
if (type === 'inline' || type === 'html') {
if (!coming.content || !coming.content.length) {
return F._error( 'content' );
}
} else if (!href) {
return F._error( 'href' );
}
if (type === 'image') {
F._loadImage();
} else if (type === 'ajax') {
F._loadAjax();
} else if (type === 'iframe') {
F._loadIframe();
} else {
F._afterLoad();
}
},
_error: function ( type ) {
$.extend(F.coming, {
type : 'html',
autoWidth : true,
autoHeight : true,
minWidth : 0,
minHeight : 0,
scrolling : 'no',
hasError : type,
content : F.coming.tpl.error
});
F._afterLoad();
},
_loadImage: function () {
// Reset preload image so it is later possible to check "complete" property
var img = F.imgPreload = new Image();
img.onload = function () {
this.onload = this.onerror = null;
F.coming.width = this.width / F.opts.pixelRatio;
F.coming.height = this.height / F.opts.pixelRatio;
F._afterLoad();
};
img.onerror = function () {
this.onload = this.onerror = null;
F._error( 'image' );
};
img.src = F.coming.href;
if (img.complete !== true) {
F.showLoading();
}
},
_loadAjax: function () {
var coming = F.coming;
F.showLoading();
F.ajaxLoad = $.ajax($.extend({}, coming.ajax, {
url: coming.href,
error: function (jqXHR, textStatus) {
if (F.coming && textStatus !== 'abort') {
F._error( 'ajax', jqXHR );
} else {
F.hideLoading();
}
},
success: function (data, textStatus) {
if (textStatus === 'success') {
coming.content = data;
F._afterLoad();
}
}
}));
},
_loadIframe: function() {
var coming = F.coming,
iframe = $(coming.tpl.iframe.replace(/\{rnd\}/g, new Date().getTime()))
.attr('scrolling', isTouch ? 'auto' : coming.iframe.scrolling)
.attr('src', coming.href);
// This helps IE
$(coming.wrap).bind('onReset', function () {
try {
$(this).find('iframe').hide().attr('src', '//about:blank').end().empty();
} catch (e) {}
});
if (coming.iframe.preload) {
F.showLoading();
iframe.one('load', function() {
$(this).data('ready', 1);
// iOS will lose scrolling if we resize
if (!isTouch) {
$(this).bind('load.fb', F.update);
}
// Without this trick:
// - iframe won't scroll on iOS devices
// - IE7 sometimes displays empty iframe
$(this).parents('.fancybox-wrap').width('100%').removeClass('fancybox-tmp').show();
F._afterLoad();
});
}
coming.content = iframe.appendTo( coming.inner );
if (!coming.iframe.preload) {
F._afterLoad();
}
},
_preloadImages: function() {
var group = F.group,
current = F.current,
len = group.length,
cnt = current.preload ? Math.min(current.preload, len - 1) : 0,
item,
i;
for (i = 1; i <= cnt; i += 1) {
item = group[ (current.index + i ) % len ];
if (item.type === 'image' && item.href) {
new Image().src = item.href;
}
}
},
_afterLoad: function () {
var coming = F.coming,
previous = F.current,
placeholder = 'fancybox-placeholder',
current,
content,
type,
scrolling,
href,
embed;
F.hideLoading();
if (!coming || F.isActive === false) {
return;
}
if (false === F.trigger('afterLoad', coming, previous)) {
coming.wrap.stop(true).trigger('onReset').remove();
F.coming = null;
return;
}
if (previous) {
F.trigger('beforeChange', previous);
previous.wrap.stop(true).removeClass('fancybox-opened')
.find('.fancybox-item, .fancybox-nav')
.remove();
}
F.unbindEvents();
current = coming;
content = coming.content;
type = coming.type;
scrolling = coming.scrolling;
$.extend(F, {
wrap : current.wrap,
skin : current.skin,
outer : current.outer,
inner : current.inner,
current : current,
previous : previous
});
href = current.href;
switch (type) {
case 'inline':
case 'ajax':
case 'html':
if (current.selector) {
content = $('<div>').html(content).find(current.selector);
} else if (isQuery(content)) {
if (!content.data(placeholder)) {
content.data(placeholder, $('<div class="' + placeholder + '"></div>').insertAfter( content ).hide() );
}
content = content.show().detach();
current.wrap.bind('onReset', function () {
if ($(this).find(content).length) {
content.hide().replaceAll( content.data(placeholder) ).data(placeholder, false);
}
});
}
break;
case 'image':
content = current.tpl.image.replace('{href}', href);
break;
case 'swf':
content = '<object id="fancybox-swf" classid="clsid:D27CDB6E-AE6D-11cf-96B8-444553540000" width="100%" height="100%"><param name="movie" value="' + href + '"></param>';
embed = '';
$.each(current.swf, function(name, val) {
content += '<param name="' + name + '" value="' + val + '"></param>';
embed += ' ' + name + '="' + val + '"';
});
content += '<embed src="' + href + '" type="application/x-shockwave-flash" width="100%" height="100%"' + embed + '></embed></object>';
break;
}
if (!(isQuery(content) && content.parent().is(current.inner))) {
current.inner.append( content );
}
// Give a chance for helpers or callbacks to update elements
F.trigger('beforeShow');
// Set scrolling before calculating dimensions
current.inner.css('overflow', scrolling === 'yes' ? 'scroll' : (scrolling === 'no' ? 'hidden' : scrolling));
// Set initial dimensions and start position
F._setDimension();
F.reposition();
F.isOpen = false;
F.coming = null;
F.bindEvents();
if (!F.isOpened) {
$('.fancybox-wrap').not( current.wrap ).stop(true).trigger('onReset').remove();
} else if (previous.prevMethod) {
F.transitions[ previous.prevMethod ]();
}
F.transitions[ F.isOpened ? current.nextMethod : current.openMethod ]();
F._preloadImages();
},
_setDimension: function () {
var viewport = F.getViewport(),
steps = 0,
canShrink = false,
canExpand = false,
wrap = F.wrap,
skin = F.skin,
inner = F.inner,
current = F.current,
width = current.width,
height = current.height,
minWidth = current.minWidth,
minHeight = current.minHeight,
maxWidth = current.maxWidth,
maxHeight = current.maxHeight,
scrolling = current.scrolling,
scrollOut = current.scrollOutside ? current.scrollbarWidth : 0,
margin = current.margin,
wMargin = getScalar(margin[1] + margin[3]),
hMargin = getScalar(margin[0] + margin[2]),
wPadding,
hPadding,
wSpace,
hSpace,
origWidth,
origHeight,
origMaxWidth,
origMaxHeight,
ratio,
width_,
height_,
maxWidth_,
maxHeight_,
iframe,
body;
// Reset dimensions so we could re-check actual size
wrap.add(skin).add(inner).width('auto').height('auto').removeClass('fancybox-tmp');
wPadding = getScalar(skin.outerWidth(true) - skin.width());
hPadding = getScalar(skin.outerHeight(true) - skin.height());
// Any space between content and viewport (margin, padding, border, title)
wSpace = wMargin + wPadding;
hSpace = hMargin + hPadding;
origWidth = isPercentage(width) ? (viewport.w - wSpace) * getScalar(width) / 100 : width;
origHeight = isPercentage(height) ? (viewport.h - hSpace) * getScalar(height) / 100 : height;
if (current.type === 'iframe') {
iframe = current.content;
if (current.autoHeight && iframe.data('ready') === 1) {
try {
if (iframe[0].contentWindow.document.location) {
inner.width( origWidth ).height(9999);
body = iframe.contents().find('body');
if (scrollOut) {
body.css('overflow-x', 'hidden');
}
origHeight = body.outerHeight(true);
}
} catch (e) {}
}
} else if (current.autoWidth || current.autoHeight) {
inner.addClass( 'fancybox-tmp' );
// Set width or height in case we need to calculate only one dimension
if (!current.autoWidth) {
inner.width( origWidth );
}
if (!current.autoHeight) {
inner.height( origHeight );
}
if (current.autoWidth) {
origWidth = inner.width();
}
if (current.autoHeight) {
origHeight = inner.height();
}
inner.removeClass( 'fancybox-tmp' );
}
width = getScalar( origWidth );
height = getScalar( origHeight );
ratio = origWidth / origHeight;
// Calculations for the content
minWidth = getScalar(isPercentage(minWidth) ? getScalar(minWidth, 'w') - wSpace : minWidth);
maxWidth = getScalar(isPercentage(maxWidth) ? getScalar(maxWidth, 'w') - wSpace : maxWidth);
minHeight = getScalar(isPercentage(minHeight) ? getScalar(minHeight, 'h') - hSpace : minHeight);
maxHeight = getScalar(isPercentage(maxHeight) ? getScalar(maxHeight, 'h') - hSpace : maxHeight);
// These will be used to determine if wrap can fit in the viewport
origMaxWidth = maxWidth;
origMaxHeight = maxHeight;
if (current.fitToView) {
maxWidth = Math.min(viewport.w - wSpace, maxWidth);
maxHeight = Math.min(viewport.h - hSpace, maxHeight);
}
maxWidth_ = viewport.w - wMargin;
maxHeight_ = viewport.h - hMargin;
if (current.aspectRatio) {
if (width > maxWidth) {
width = maxWidth;
height = getScalar(width / ratio);
}
if (height > maxHeight) {
height = maxHeight;
width = getScalar(height * ratio);
}
if (width < minWidth) {
width = minWidth;
height = getScalar(width / ratio);
}
if (height < minHeight) {
height = minHeight;
width = getScalar(height * ratio);
}
} else {
width = Math.max(minWidth, Math.min(width, maxWidth));
if (current.autoHeight && current.type !== 'iframe') {
inner.width( width );
height = inner.height();
}
height = Math.max(minHeight, Math.min(height, maxHeight));
}
// Try to fit inside viewport (including the title)
if (current.fitToView) {
inner.width( width ).height( height );
wrap.width( width + wPadding );
// Real wrap dimensions
width_ = wrap.width();
height_ = wrap.height();
if (current.aspectRatio) {
while ((width_ > maxWidth_ || height_ > maxHeight_) && width > minWidth && height > minHeight) {
if (steps++ > 19) {
break;
}
height = Math.max(minHeight, Math.min(maxHeight, height - 10));
width = getScalar(height * ratio);
if (width < minWidth) {
width = minWidth;
height = getScalar(width / ratio);
}
if (width > maxWidth) {
width = maxWidth;
height = getScalar(width / ratio);
}
inner.width( width ).height( height );
wrap.width( width + wPadding );
width_ = wrap.width();
height_ = wrap.height();
}
} else {
width = Math.max(minWidth, Math.min(width, width - (width_ - maxWidth_)));
height = Math.max(minHeight, Math.min(height, height - (height_ - maxHeight_)));
}
}
if (scrollOut && scrolling === 'auto' && height < origHeight && (width + wPadding + scrollOut) < maxWidth_) {
width += scrollOut;
}
inner.width( width ).height( height );
wrap.width( width + wPadding );
width_ = wrap.width();
height_ = wrap.height();
canShrink = (width_ > maxWidth_ || height_ > maxHeight_) && width > minWidth && height > minHeight;
canExpand = current.aspectRatio ? (width < origMaxWidth && height < origMaxHeight && width < origWidth && height < origHeight) : ((width < origMaxWidth || height < origMaxHeight) && (width < origWidth || height < origHeight));
$.extend(current, {
dim : {
width : getValue( width_ ),
height : getValue( height_ )
},
origWidth : origWidth,
origHeight : origHeight,
canShrink : canShrink,
canExpand : canExpand,
wPadding : wPadding,
hPadding : hPadding,
wrapSpace : height_ - skin.outerHeight(true),
skinSpace : skin.height() - height
});
if (!iframe && current.autoHeight && height > minHeight && height < maxHeight && !canExpand) {
inner.height('auto');
}
},
_getPosition: function (onlyAbsolute) {
var current = F.current,
viewport = F.getViewport(),
margin = current.margin,
width = F.wrap.width() + margin[1] + margin[3],
height = F.wrap.height() + margin[0] + margin[2],
rez = {
position: 'absolute',
top : margin[0],
left : margin[3]
};
if (current.autoCenter && current.fixed && !onlyAbsolute && height <= viewport.h && width <= viewport.w) {
rez.position = 'fixed';
} else if (!current.locked) {
rez.top += viewport.y;
rez.left += viewport.x;
}
rez.top = getValue(Math.max(rez.top, rez.top + ((viewport.h - height) * current.topRatio)));
rez.left = getValue(Math.max(rez.left, rez.left + ((viewport.w - width) * current.leftRatio)));
return rez;
},
_afterZoomIn: function () {
var current = F.current;
if (!current) {
return;
}
F.isOpen = F.isOpened = true;
F.wrap.css('overflow', 'visible').addClass('fancybox-opened');
F.update();
// Assign a click event
if ( current.closeClick || (current.nextClick && F.group.length > 1) ) {
F.inner.css('cursor', 'pointer').bind('click.fb', function(e) {
if (!$(e.target).is('a') && !$(e.target).parent().is('a')) {
e.preventDefault();
F[ current.closeClick ? 'close' : 'next' ]();
}
});
}
// Create a close button
if (current.closeBtn) {
$(current.tpl.closeBtn).appendTo(F.skin).bind('click.fb', function(e) {
e.preventDefault();
F.close();
});
}
// Create navigation arrows
if (current.arrows && F.group.length > 1) {
if (current.loop || current.index > 0) {
$(current.tpl.prev).appendTo(F.outer).bind('click.fb', F.prev);
}
if (current.loop || current.index < F.group.length - 1) {
$(current.tpl.next).appendTo(F.outer).bind('click.fb', F.next);
}
}
F.trigger('afterShow');
// Stop the slideshow if this is the last item
if (!current.loop && current.index === current.group.length - 1) {
F.play( false );
} else if (F.opts.autoPlay && !F.player.isActive) {
F.opts.autoPlay = false;
F.play();
}
},
_afterZoomOut: function ( obj ) {
obj = obj || F.current;
$('.fancybox-wrap').trigger('onReset').remove();
$.extend(F, {
group : {},
opts : {},
router : false,
current : null,
isActive : false,
isOpened : false,
isOpen : false,
isClosing : false,
wrap : null,
skin : null,
outer : null,
inner : null
});
F.trigger('afterClose', obj);
}
});
/*
* Default transitions
*/
F.transitions = {
getOrigPosition: function () {
var current = F.current,
element = current.element,
orig = current.orig,
pos = {},
width = 50,
height = 50,
hPadding = current.hPadding,
wPadding = current.wPadding,
viewport = F.getViewport();
if (!orig && current.isDom && element.is(':visible')) {
orig = element.find('img:first');
if (!orig.length) {
orig = element;
}
}
if (isQuery(orig)) {
pos = orig.offset();
if (orig.is('img')) {
width = orig.outerWidth();
height = orig.outerHeight();
}
} else {
pos.top = viewport.y + (viewport.h - height) * current.topRatio;
pos.left = viewport.x + (viewport.w - width) * current.leftRatio;
}
if (F.wrap.css('position') === 'fixed' || current.locked) {
pos.top -= viewport.y;
pos.left -= viewport.x;
}
pos = {
top : getValue(pos.top - hPadding * current.topRatio),
left : getValue(pos.left - wPadding * current.leftRatio),
width : getValue(width + wPadding),
height : getValue(height + hPadding)
};
return pos;
},
step: function (now, fx) {
var ratio,
padding,
value,
prop = fx.prop,
current = F.current,
wrapSpace = current.wrapSpace,
skinSpace = current.skinSpace;
if (prop === 'width' || prop === 'height') {
ratio = fx.end === fx.start ? 1 : (now - fx.start) / (fx.end - fx.start);
if (F.isClosing) {
ratio = 1 - ratio;
}
padding = prop === 'width' ? current.wPadding : current.hPadding;
value = now - padding;
F.skin[ prop ]( getScalar( prop === 'width' ? value : value - (wrapSpace * ratio) ) );
F.inner[ prop ]( getScalar( prop === 'width' ? value : value - (wrapSpace * ratio) - (skinSpace * ratio) ) );
}
},
zoomIn: function () {
var current = F.current,
startPos = current.pos,
effect = current.openEffect,
elastic = effect === 'elastic',
endPos = $.extend({opacity : 1}, startPos);
// Remove "position" property that breaks older IE
delete endPos.position;
if (elastic) {
startPos = this.getOrigPosition();
if (current.openOpacity) {
startPos.opacity = 0.1;
}
} else if (effect === 'fade') {
startPos.opacity = 0.1;
}
F.wrap.css(startPos).animate(endPos, {
duration : effect === 'none' ? 0 : current.openSpeed,
easing : current.openEasing,
step : elastic ? this.step : null,
complete : F._afterZoomIn
});
},
zoomOut: function () {
var current = F.current,
effect = current.closeEffect,
elastic = effect === 'elastic',
endPos = {opacity : 0.1};
if (elastic) {
endPos = this.getOrigPosition();
if (current.closeOpacity) {
endPos.opacity = 0.1;
}
}
F.wrap.animate(endPos, {
duration : effect === 'none' ? 0 : current.closeSpeed,
easing : current.closeEasing,
step : elastic ? this.step : null,
complete : F._afterZoomOut
});
},
changeIn: function () {
var current = F.current,
effect = current.nextEffect,
startPos = current.pos,
endPos = { opacity : 1 },
direction = F.direction,
distance = 200,
field;
startPos.opacity = 0.1;
if (effect === 'elastic') {
field = direction === 'down' || direction === 'up' ? 'top' : 'left';
if (direction === 'down' || direction === 'right') {
startPos[ field ] = getValue(getScalar(startPos[ field ]) - distance);
endPos[ field ] = '+=' + distance + 'px';
} else {
startPos[ field ] = getValue(getScalar(startPos[ field ]) + distance);
endPos[ field ] = '-=' + distance + 'px';
}
}
// Workaround for http://bugs.jquery.com/ticket/12273
if (effect === 'none') {
F._afterZoomIn();
} else {
F.wrap.css(startPos).animate(endPos, {
duration : current.nextSpeed,
easing : current.nextEasing,
complete : F._afterZoomIn
});
}
},
changeOut: function () {
var previous = F.previous,
effect = previous.prevEffect,
endPos = { opacity : 0.1 },
direction = F.direction,
distance = 200;
if (effect === 'elastic') {
endPos[ direction === 'down' || direction === 'up' ? 'top' : 'left' ] = ( direction === 'up' || direction === 'left' ? '-' : '+' ) + '=' + distance + 'px';
}
previous.wrap.animate(endPos, {
duration : effect === 'none' ? 0 : previous.prevSpeed,
easing : previous.prevEasing,
complete : function () {
$(this).trigger('onReset').remove();
}
});
}
};
/*
* Overlay helper
*/
F.helpers.overlay = {
defaults : {
closeClick : true, // if true, fancyBox will be closed when user clicks on the overlay
speedOut : 200, // duration of fadeOut animation
showEarly : true, // indicates if should be opened immediately or wait until the content is ready
css : {}, // custom CSS properties
locked : !isTouch, // if true, the content will be locked into overlay
fixed : true // if false, the overlay CSS position property will not be set to "fixed"
},
overlay : null, // current handle
fixed : false, // indicates if the overlay has position "fixed"
el : $('html'), // element that contains "the lock"
// Public methods
create : function(opts) {
opts = $.extend({}, this.defaults, opts);
if (this.overlay) {
this.close();
}
this.overlay = $('<div class="fancybox-overlay"></div>').appendTo( F.coming ? F.coming.parent : opts.parent );
this.fixed = false;
if (opts.fixed && F.defaults.fixed) {
this.overlay.addClass('fancybox-overlay-fixed');
this.fixed = true;
}
},
open : function(opts) {
var that = this;
opts = $.extend({}, this.defaults, opts);
if (this.overlay) {
this.overlay.unbind('.overlay').width('auto').height('auto');
} else {
this.create(opts);
}
if (!this.fixed) {
W.bind('resize.overlay', $.proxy( this.update, this) );
this.update();
}
if (opts.closeClick) {
this.overlay.bind('click.overlay', function(e) {
if ($(e.target).hasClass('fancybox-overlay')) {
if (F.isActive) {
F.close();
} else {
that.close();
}
return false;
}
});
}
this.overlay.css( opts.css ).show();
},
close : function() {
var scrollV, scrollH;
W.unbind('resize.overlay');
if (this.el.hasClass('fancybox-lock')) {
$('.fancybox-margin').removeClass('fancybox-margin');
scrollV = W.scrollTop();
scrollH = W.scrollLeft();
this.el.removeClass('fancybox-lock');
W.scrollTop( scrollV ).scrollLeft( scrollH );
}
$('.fancybox-overlay').remove().hide();
$.extend(this, {
overlay : null,
fixed : false
});
},
// Private, callbacks
update : function () {
var width = '100%', offsetWidth;
// Reset width/height so it will not mess
this.overlay.width(width).height('100%');
// jQuery does not return reliable result for IE
if (IE) {
offsetWidth = Math.max(document.documentElement.offsetWidth, document.body.offsetWidth);
if (D.width() > offsetWidth) {
width = D.width();
}
} else if (D.width() > W.width()) {
width = D.width();
}
this.overlay.width(width).height(D.height());
},
// This is where we can manipulate DOM, because later it would cause iframes to reload
onReady : function (opts, obj) {
var overlay = this.overlay;
$('.fancybox-overlay').stop(true, true);
if (!overlay) {
this.create(opts);
}
if (opts.locked && this.fixed && obj.fixed) {
if (!overlay) {
this.margin = D.height() > W.height() ? $('html').css('margin-right').replace("px", "") : false;
}
obj.locked = this.overlay.append( obj.wrap );
obj.fixed = false;
}
if (opts.showEarly === true) {
this.beforeShow.apply(this, arguments);
}
},
beforeShow : function(opts, obj) {
var scrollV, scrollH;
if (obj.locked) {
if (this.margin !== false) {
$('*').filter(function(){
return ($(this).css('position') === 'fixed' && !$(this).hasClass("fancybox-overlay") && !$(this).hasClass("fancybox-wrap") );
}).addClass('fancybox-margin');
this.el.addClass('fancybox-margin');
}
scrollV = W.scrollTop();
scrollH = W.scrollLeft();
this.el.addClass('fancybox-lock');
W.scrollTop( scrollV ).scrollLeft( scrollH );
}
this.open(opts);
},
onUpdate : function() {
if (!this.fixed) {
this.update();
}
},
afterClose: function (opts) {
// Remove overlay if exists and fancyBox is not opening
// (e.g., it is not being open using afterClose callback)
//if (this.overlay && !F.isActive) {
if (this.overlay && !F.coming) {
this.overlay.fadeOut(opts.speedOut, $.proxy( this.close, this ));
}
}
};
/*
* Title helper
*/
F.helpers.title = {
defaults : {
type : 'float', // 'float', 'inside', 'outside' or 'over',
position : 'bottom' // 'top' or 'bottom'
},
beforeShow: function (opts) {
var current = F.current,
text = current.title,
type = opts.type,
title,
target;
if ($.isFunction(text)) {
text = text.call(current.element, current);
}
if (!isString(text) || $.trim(text) === '') {
return;
}
title = $('<div class="fancybox-title fancybox-title-' + type + '-wrap">' + text + '</div>');
switch (type) {
case 'inside':
target = F.skin;
break;
case 'outside':
target = F.wrap;
break;
case 'over':
target = F.inner;
break;
default: // 'float'
target = F.skin;
title.appendTo('body');
if (IE) {
title.width( title.width() );
}
title.wrapInner('<span class="child"></span>');
//Increase bottom margin so this title will also fit into viewport
F.current.margin[2] += Math.abs( getScalar(title.css('margin-bottom')) );
break;
}
title[ (opts.position === 'top' ? 'prependTo' : 'appendTo') ](target);
}
};
// jQuery plugin initialization
$.fn.fancybox = function (options) {
var index,
that = $(this),
selector = this.selector || '',
run = function(e) {
var what = $(this).blur(), idx = index, relType, relVal;
if (!(e.ctrlKey || e.altKey || e.shiftKey || e.metaKey) && !what.is('.fancybox-wrap')) {
relType = options.groupAttr || 'data-fancybox-group';
relVal = what.attr(relType);
if (!relVal) {
relType = 'rel';
relVal = what.get(0)[ relType ];
}
if (relVal && relVal !== '' && relVal !== 'nofollow') {
what = selector.length ? $(selector) : that;
what = what.filter('[' + relType + '="' + relVal + '"]');
idx = what.index(this);
}
options.index = idx;
// Stop an event from bubbling if everything is fine
if (F.open(what, options) !== false) {
e.preventDefault();
}
}
};
options = options || {};
index = options.index || 0;
if (!selector || options.live === false) {
that.unbind('click.fb-start').bind('click.fb-start', run);
} else {
D.undelegate(selector, 'click.fb-start').delegate(selector + ":not('.fancybox-item, .fancybox-nav')", 'click.fb-start', run);
}
this.filter('[data-fancybox-start=1]').trigger('click');
return this;
};
// Tests that need a body at doc ready
D.ready(function() {
var w1, w2;
if ( $.scrollbarWidth === undefined ) {
// http://benalman.com/projects/jquery-misc-plugins/#scrollbarwidth
$.scrollbarWidth = function() {
var parent = $('<div style="width:50px;height:50px;overflow:auto"><div/></div>').appendTo('body'),
child = parent.children(),
width = child.innerWidth() - child.height( 99 ).innerWidth();
parent.remove();
return width;
};
}
if ( $.support.fixedPosition === undefined ) {
$.support.fixedPosition = (function() {
var elem = $('<div style="position:fixed;top:20px;"></div>').appendTo('body'),
fixed = ( elem[0].offsetTop === 20 || elem[0].offsetTop === 15 );
elem.remove();
return fixed;
}());
}
$.extend(F.defaults, {
scrollbarWidth : $.scrollbarWidth(),
fixed : $.support.fixedPosition,
parent : $('body')
});
//Get real width of page scroll-bar
w1 = $(window).width();
H.addClass('fancybox-lock-test');
w2 = $(window).width();
H.removeClass('fancybox-lock-test');
$("<style type='text/css'>.fancybox-margin{margin-right:" + (w2 - w1) + "px;}</style>").appendTo("head");
});
}(window, document, jQuery));
\ No newline at end of file
/*
* jQuery OwlCarousel v1.3.3
*
* Copyright (c) 2013 Bartosz Wojciechowski
* http://www.owlgraphic.com/owlcarousel/
*
* Licensed under MIT
*
*/
/*JS Lint helpers: */
/*global dragMove: false, dragEnd: false, $, jQuery, alert, window, document */
/*jslint nomen: true, continue:true */
if (typeof Object.create !== "function") {
Object.create = function (obj) {
function F() {}
F.prototype = obj;
return new F();
};
}
(function ($, window, document) {
var Carousel = {
init : function (options, el) {
var base = this;
base.$elem = $(el);
base.options = $.extend({}, $.fn.owlCarousel.options, base.$elem.data(), options);
base.userOptions = options;
base.loadContent();
},
loadContent : function () {
var base = this, url;
function getData(data) {
var i, content = "";
if (typeof base.options.jsonSuccess === "function") {
base.options.jsonSuccess.apply(this, [data]);
} else {
for (i in data.owl) {
if (data.owl.hasOwnProperty(i)) {
content += data.owl[i].item;
}
}
base.$elem.html(content);
}
base.logIn();
}
if (typeof base.options.beforeInit === "function") {
base.options.beforeInit.apply(this, [base.$elem]);
}
if (typeof base.options.jsonPath === "string") {
url = base.options.jsonPath;
$.getJSON(url, getData);
} else {
base.logIn();
}
},
logIn : function () {
var base = this;
base.$elem.data("owl-originalStyles", base.$elem.attr("style"));
base.$elem.data("owl-originalClasses", base.$elem.attr("class"));
base.$elem.css({opacity: 0});
base.orignalItems = base.options.items;
base.checkBrowser();
base.wrapperWidth = 0;
base.checkVisible = null;
base.setVars();
},
setVars : function () {
var base = this;
if (base.$elem.children().length === 0) {return false; }
base.baseClass();
base.eventTypes();
base.$userItems = base.$elem.children();
base.itemsAmount = base.$userItems.length;
base.wrapItems();
base.$owlItems = base.$elem.find(".owl-item");
base.$owlWrapper = base.$elem.find(".owl-wrapper");
base.playDirection = "next";
base.prevItem = 0;
base.prevArr = [0];
base.currentItem = 0;
base.customEvents();
base.onStartup();
},
onStartup : function () {
var base = this;
base.updateItems();
base.calculateAll();
base.buildControls();
base.updateControls();
base.response();
base.moveEvents();
base.stopOnHover();
base.owlStatus();
if (base.options.transitionStyle !== false) {
base.transitionTypes(base.options.transitionStyle);
}
if (base.options.autoPlay === true) {
base.options.autoPlay = 5000;
}
base.play();
base.$elem.find(".owl-wrapper").css("display", "block");
if (!base.$elem.is(":visible")) {
base.watchVisibility();
} else {
base.$elem.css("opacity", 1);
}
base.onstartup = false;
base.eachMoveUpdate();
if (typeof base.options.afterInit === "function") {
base.options.afterInit.apply(this, [base.$elem]);
}
},
eachMoveUpdate : function () {
var base = this;
if (base.options.lazyLoad === true) {
base.lazyLoad();
}
if (base.options.autoHeight === true) {
base.autoHeight();
}
base.onVisibleItems();
if (typeof base.options.afterAction === "function") {
base.options.afterAction.apply(this, [base.$elem]);
}
},
updateVars : function () {
var base = this;
if (typeof base.options.beforeUpdate === "function") {
base.options.beforeUpdate.apply(this, [base.$elem]);
}
base.watchVisibility();
base.updateItems();
base.calculateAll();
base.updatePosition();
base.updateControls();
base.eachMoveUpdate();
if (typeof base.options.afterUpdate === "function") {
base.options.afterUpdate.apply(this, [base.$elem]);
}
},
reload : function () {
var base = this;
window.setTimeout(function () {
base.updateVars();
}, 0);
},
watchVisibility : function () {
var base = this;
if (base.$elem.is(":visible") === false) {
base.$elem.css({opacity: 0});
window.clearInterval(base.autoPlayInterval);
window.clearInterval(base.checkVisible);
} else {
return false;
}
base.checkVisible = window.setInterval(function () {
if (base.$elem.is(":visible")) {
base.reload();
base.$elem.animate({opacity: 1}, 200);
window.clearInterval(base.checkVisible);
}
}, 500);
},
wrapItems : function () {
var base = this;
base.$userItems.wrapAll("<div class=\"owl-wrapper\">").wrap("<div class=\"owl-item\"></div>");
base.$elem.find(".owl-wrapper").wrap("<div class=\"owl-wrapper-outer\">");
base.wrapperOuter = base.$elem.find(".owl-wrapper-outer");
base.$elem.css("display", "block");
},
baseClass : function () {
var base = this,
hasBaseClass = base.$elem.hasClass(base.options.baseClass),
hasThemeClass = base.$elem.hasClass(base.options.theme);
if (!hasBaseClass) {
base.$elem.addClass(base.options.baseClass);
}
if (!hasThemeClass) {
base.$elem.addClass(base.options.theme);
}
},
updateItems : function () {
var base = this, width, i;
if (base.options.responsive === false) {
return false;
}
if (base.options.singleItem === true) {
base.options.items = base.orignalItems = 1;
base.options.itemsCustom = false;
base.options.itemsDesktop = false;
base.options.itemsDesktopSmall = false;
base.options.itemsTablet = false;
base.options.itemsTabletSmall = false;
base.options.itemsMobile = false;
return false;
}
width = $(base.options.responsiveBaseWidth).width();
if (width > (base.options.itemsDesktop[0] || base.orignalItems)) {
base.options.items = base.orignalItems;
}
if (base.options.itemsCustom !== false) {
//Reorder array by screen size
base.options.itemsCustom.sort(function (a, b) {return a[0] - b[0]; });
for (i = 0; i < base.options.itemsCustom.length; i += 1) {
if (base.options.itemsCustom[i][0] <= width) {
base.options.items = base.options.itemsCustom[i][1];
}
}
} else {
if (width <= base.options.itemsDesktop[0] && base.options.itemsDesktop !== false) {
base.options.items = base.options.itemsDesktop[1];
}
if (width <= base.options.itemsDesktopSmall[0] && base.options.itemsDesktopSmall !== false) {
base.options.items = base.options.itemsDesktopSmall[1];
}
if (width <= base.options.itemsTablet[0] && base.options.itemsTablet !== false) {
base.options.items = base.options.itemsTablet[1];
}
if (width <= base.options.itemsTabletSmall[0] && base.options.itemsTabletSmall !== false) {
base.options.items = base.options.itemsTabletSmall[1];
}
if (width <= base.options.itemsMobile[0] && base.options.itemsMobile !== false) {
base.options.items = base.options.itemsMobile[1];
}
}
//if number of items is less than declared
if (base.options.items > base.itemsAmount && base.options.itemsScaleUp === true) {
base.options.items = base.itemsAmount;
}
},
response : function () {
var base = this,
smallDelay,
lastWindowWidth;
if (base.options.responsive !== true) {
return false;
}
lastWindowWidth = $(window).width();
base.resizer = function () {
if ($(window).width() !== lastWindowWidth) {
if (base.options.autoPlay !== false) {
window.clearInterval(base.autoPlayInterval);
}
window.clearTimeout(smallDelay);
smallDelay = window.setTimeout(function () {
lastWindowWidth = $(window).width();
base.updateVars();
}, base.options.responsiveRefreshRate);
}
};
$(window).resize(base.resizer);
},
updatePosition : function () {
var base = this;
base.jumpTo(base.currentItem);
if (base.options.autoPlay !== false) {
base.checkAp();
}
},
appendItemsSizes : function () {
var base = this,
roundPages = 0,
lastItem = base.itemsAmount - base.options.items;
base.$owlItems.each(function (index) {
var $this = $(this);
$this
.css({"width": base.itemWidth})
.data("owl-item", Number(index));
if (index % base.options.items === 0 || index === lastItem) {
if (!(index > lastItem)) {
roundPages += 1;
}
}
$this.data("owl-roundPages", roundPages);
});
},
appendWrapperSizes : function () {
var base = this,
width = base.$owlItems.length * base.itemWidth;
base.$owlWrapper.css({
"width": width * 2,
"left": 0
});
base.appendItemsSizes();
},
calculateAll : function () {
var base = this;
base.calculateWidth();
base.appendWrapperSizes();
base.loops();
base.max();
},
calculateWidth : function () {
var base = this;
base.itemWidth = Math.round(base.$elem.width() / base.options.items);
},
max : function () {
var base = this,
maximum = ((base.itemsAmount * base.itemWidth) - base.options.items * base.itemWidth) * -1;
if (base.options.items > base.itemsAmount) {
base.maximumItem = 0;
maximum = 0;
base.maximumPixels = 0;
} else {
base.maximumItem = base.itemsAmount - base.options.items;
base.maximumPixels = maximum;
}
return maximum;
},
min : function () {
return 0;
},
loops : function () {
var base = this,
prev = 0,
elWidth = 0,
i,
item,
roundPageNum;
base.positionsInArray = [0];
base.pagesInArray = [];
for (i = 0; i < base.itemsAmount; i += 1) {
elWidth += base.itemWidth;
base.positionsInArray.push(-elWidth);
if (base.options.scrollPerPage === true) {
item = $(base.$owlItems[i]);
roundPageNum = item.data("owl-roundPages");
if (roundPageNum !== prev) {
base.pagesInArray[prev] = base.positionsInArray[i];
prev = roundPageNum;
}
}
}
},
buildControls : function () {
var base = this;
if (base.options.navigation === true || base.options.pagination === true) {
base.owlControls = $("<div class=\"owl-controls\"/>").toggleClass("clickable", !base.browser.isTouch).appendTo(base.$elem);
}
if (base.options.pagination === true) {
base.buildPagination();
}
if (base.options.navigation === true) {
base.buildButtons();
}
},
buildButtons : function () {
var base = this,
buttonsWrapper = $("<div class=\"owl-buttons\"/>");
base.owlControls.append(buttonsWrapper);
base.buttonPrev = $("<div/>", {
"class" : "owl-prev",
"html" : base.options.navigationText[0] || ""
});
base.buttonNext = $("<div/>", {
"class" : "owl-next",
"html" : base.options.navigationText[1] || ""
});
buttonsWrapper
.append(base.buttonPrev)
.append(base.buttonNext);
buttonsWrapper.on("touchstart.owlControls mousedown.owlControls", "div[class^=\"owl\"]", function (event) {
event.preventDefault();
});
buttonsWrapper.on("touchend.owlControls mouseup.owlControls", "div[class^=\"owl\"]", function (event) {
event.preventDefault();
if ($(this).hasClass("owl-next")) {
base.next();
} else {
base.prev();
}
});
},
buildPagination : function () {
var base = this;
base.paginationWrapper = $("<div class=\"owl-pagination\"/>");
base.owlControls.append(base.paginationWrapper);
base.paginationWrapper.on("touchend.owlControls mouseup.owlControls", ".owl-page", function (event) {
event.preventDefault();
if (Number($(this).data("owl-page")) !== base.currentItem) {
base.goTo(Number($(this).data("owl-page")), true);
}
});
},
updatePagination : function () {
var base = this,
counter,
lastPage,
lastItem,
i,
paginationButton,
paginationButtonInner;
if (base.options.pagination === false) {
return false;
}
base.paginationWrapper.html("");
counter = 0;
lastPage = base.itemsAmount - base.itemsAmount % base.options.items;
for (i = 0; i < base.itemsAmount; i += 1) {
if (i % base.options.items === 0) {
counter += 1;
if (lastPage === i) {
lastItem = base.itemsAmount - base.options.items;
}
paginationButton = $("<div/>", {
"class" : "owl-page"
});
paginationButtonInner = $("<span></span>", {
"text": base.options.paginationNumbers === true ? counter : "",
"class": base.options.paginationNumbers === true ? "owl-numbers" : ""
});
paginationButton.append(paginationButtonInner);
paginationButton.data("owl-page", lastPage === i ? lastItem : i);
paginationButton.data("owl-roundPages", counter);
base.paginationWrapper.append(paginationButton);
}
}
base.checkPagination();
},
checkPagination : function () {
var base = this;
if (base.options.pagination === false) {
return false;
}
base.paginationWrapper.find(".owl-page").each(function () {
if ($(this).data("owl-roundPages") === $(base.$owlItems[base.currentItem]).data("owl-roundPages")) {
base.paginationWrapper
.find(".owl-page")
.removeClass("active");
$(this).addClass("active");
}
});
},
checkNavigation : function () {
var base = this;
if (base.options.navigation === false) {
return false;
}
if (base.options.rewindNav === false) {
if (base.currentItem === 0 && base.maximumItem === 0) {
base.buttonPrev.addClass("disabled");
base.buttonNext.addClass("disabled");
} else if (base.currentItem === 0 && base.maximumItem !== 0) {
base.buttonPrev.addClass("disabled");
base.buttonNext.removeClass("disabled");
} else if (base.currentItem === base.maximumItem) {
base.buttonPrev.removeClass("disabled");
base.buttonNext.addClass("disabled");
} else if (base.currentItem !== 0 && base.currentItem !== base.maximumItem) {
base.buttonPrev.removeClass("disabled");
base.buttonNext.removeClass("disabled");
}
}
},
updateControls : function () {
var base = this;
base.updatePagination();
base.checkNavigation();
if (base.owlControls) {
if (base.options.items >= base.itemsAmount) {
base.owlControls.hide();
} else {
base.owlControls.show();
}
}
},
destroyControls : function () {
var base = this;
if (base.owlControls) {
base.owlControls.remove();
}
},
next : function (speed) {
var base = this;
if (base.isTransition) {
return false;
}
base.currentItem += base.options.scrollPerPage === true ? base.options.items : 1;
if (base.currentItem > base.maximumItem + (base.options.scrollPerPage === true ? (base.options.items - 1) : 0)) {
if (base.options.rewindNav === true) {
base.currentItem = 0;
speed = "rewind";
} else {
base.currentItem = base.maximumItem;
return false;
}
}
base.goTo(base.currentItem, speed);
},
prev : function (speed) {
var base = this;
if (base.isTransition) {
return false;
}
if (base.options.scrollPerPage === true && base.currentItem > 0 && base.currentItem < base.options.items) {
base.currentItem = 0;
} else {
base.currentItem -= base.options.scrollPerPage === true ? base.options.items : 1;
}
if (base.currentItem < 0) {
if (base.options.rewindNav === true) {
base.currentItem = base.maximumItem;
speed = "rewind";
} else {
base.currentItem = 0;
return false;
}
}
base.goTo(base.currentItem, speed);
},
goTo : function (position, speed, drag) {
var base = this,
goToPixel;
if (base.isTransition) {
return false;
}
if (typeof base.options.beforeMove === "function") {
base.options.beforeMove.apply(this, [base.$elem]);
}
if (position >= base.maximumItem) {
position = base.maximumItem;
} else if (position <= 0) {
position = 0;
}
base.currentItem = base.owl.currentItem = position;
if (base.options.transitionStyle !== false && drag !== "drag" && base.options.items === 1 && base.browser.support3d === true) {
base.swapSpeed(0);
if (base.browser.support3d === true) {
base.transition3d(base.positionsInArray[position]);
} else {
base.css2slide(base.positionsInArray[position], 1);
}
base.afterGo();
base.singleItemTransition();
return false;
}
goToPixel = base.positionsInArray[position];
if (base.browser.support3d === true) {
base.isCss3Finish = false;
if (speed === true) {
base.swapSpeed("paginationSpeed");
window.setTimeout(function () {
base.isCss3Finish = true;
}, base.options.paginationSpeed);
} else if (speed === "rewind") {
base.swapSpeed(base.options.rewindSpeed);
window.setTimeout(function () {
base.isCss3Finish = true;
}, base.options.rewindSpeed);
} else {
base.swapSpeed("slideSpeed");
window.setTimeout(function () {
base.isCss3Finish = true;
}, base.options.slideSpeed);
}
base.transition3d(goToPixel);
} else {
if (speed === true) {
base.css2slide(goToPixel, base.options.paginationSpeed);
} else if (speed === "rewind") {
base.css2slide(goToPixel, base.options.rewindSpeed);
} else {
base.css2slide(goToPixel, base.options.slideSpeed);
}
}
base.afterGo();
},
jumpTo : function (position) {
var base = this;
if (typeof base.options.beforeMove === "function") {
base.options.beforeMove.apply(this, [base.$elem]);
}
if (position >= base.maximumItem || position === -1) {
position = base.maximumItem;
} else if (position <= 0) {
position = 0;
}
base.swapSpeed(0);
if (base.browser.support3d === true) {
base.transition3d(base.positionsInArray[position]);
} else {
base.css2slide(base.positionsInArray[position], 1);
}
base.currentItem = base.owl.currentItem = position;
base.afterGo();
},
afterGo : function () {
var base = this;
base.prevArr.push(base.currentItem);
base.prevItem = base.owl.prevItem = base.prevArr[base.prevArr.length - 2];
base.prevArr.shift(0);
if (base.prevItem !== base.currentItem) {
base.checkPagination();
base.checkNavigation();
base.eachMoveUpdate();
if (base.options.autoPlay !== false) {
base.checkAp();
}
}
if (typeof base.options.afterMove === "function" && base.prevItem !== base.currentItem) {
base.options.afterMove.apply(this, [base.$elem]);
}
},
stop : function () {
var base = this;
base.apStatus = "stop";
window.clearInterval(base.autoPlayInterval);
},
checkAp : function () {
var base = this;
if (base.apStatus !== "stop") {
base.play();
}
},
play : function () {
var base = this;
base.apStatus = "play";
if (base.options.autoPlay === false) {
return false;
}
window.clearInterval(base.autoPlayInterval);
base.autoPlayInterval = window.setInterval(function () {
base.next(true);
}, base.options.autoPlay);
},
swapSpeed : function (action) {
var base = this;
if (action === "slideSpeed") {
base.$owlWrapper.css(base.addCssSpeed(base.options.slideSpeed));
} else if (action === "paginationSpeed") {
base.$owlWrapper.css(base.addCssSpeed(base.options.paginationSpeed));
} else if (typeof action !== "string") {
base.$owlWrapper.css(base.addCssSpeed(action));
}
},
addCssSpeed : function (speed) {
return {
"-webkit-transition": "all " + speed + "ms ease",
"-moz-transition": "all " + speed + "ms ease",
"-o-transition": "all " + speed + "ms ease",
"transition": "all " + speed + "ms ease"
};
},
removeTransition : function () {
return {
"-webkit-transition": "",
"-moz-transition": "",
"-o-transition": "",
"transition": ""
};
},
doTranslate : function (pixels) {
return {
"-webkit-transform": "translate3d(" + pixels + "px, 0px, 0px)",
"-moz-transform": "translate3d(" + pixels + "px, 0px, 0px)",
"-o-transform": "translate3d(" + pixels + "px, 0px, 0px)",
"-ms-transform": "translate3d(" + pixels + "px, 0px, 0px)",
"transform": "translate3d(" + pixels + "px, 0px,0px)"
};
},
transition3d : function (value) {
var base = this;
base.$owlWrapper.css(base.doTranslate(value));
},
css2move : function (value) {
var base = this;
base.$owlWrapper.css({"left" : value});
},
css2slide : function (value, speed) {
var base = this;
base.isCssFinish = false;
base.$owlWrapper.stop(true, true).animate({
"left" : value
}, {
duration : speed || base.options.slideSpeed,
complete : function () {
base.isCssFinish = true;
}
});
},
checkBrowser : function () {
var base = this,
translate3D = "translate3d(0px, 0px, 0px)",
tempElem = document.createElement("div"),
regex,
asSupport,
support3d,
isTouch;
tempElem.style.cssText = " -moz-transform:" + translate3D +
"; -ms-transform:" + translate3D +
"; -o-transform:" + translate3D +
"; -webkit-transform:" + translate3D +
"; transform:" + translate3D;
regex = /translate3d\(0px, 0px, 0px\)/g;
asSupport = tempElem.style.cssText.match(regex);
support3d = (asSupport !== null && asSupport.length === 1);
isTouch = "ontouchstart" in window || window.navigator.msMaxTouchPoints;
base.browser = {
"support3d" : support3d,
"isTouch" : isTouch
};
},
moveEvents : function () {
var base = this;
if (base.options.mouseDrag !== false || base.options.touchDrag !== false) {
base.gestures();
base.disabledEvents();
}
},
eventTypes : function () {
var base = this,
types = ["s", "e", "x"];
base.ev_types = {};
if (base.options.mouseDrag === true && base.options.touchDrag === true) {
types = [
"touchstart.owl mousedown.owl",
"touchmove.owl mousemove.owl",
"touchend.owl touchcancel.owl mouseup.owl"
];
} else if (base.options.mouseDrag === false && base.options.touchDrag === true) {
types = [
"touchstart.owl",
"touchmove.owl",
"touchend.owl touchcancel.owl"
];
} else if (base.options.mouseDrag === true && base.options.touchDrag === false) {
types = [
"mousedown.owl",
"mousemove.owl",
"mouseup.owl"
];
}
base.ev_types.start = types[0];
base.ev_types.move = types[1];
base.ev_types.end = types[2];
},
disabledEvents : function () {
var base = this;
base.$elem.on("dragstart.owl", function (event) { event.preventDefault(); });
base.$elem.on("mousedown.disableTextSelect", function (e) {
return $(e.target).is('input, textarea, select, option');
});
},
gestures : function () {
/*jslint unparam: true*/
var base = this,
locals = {
offsetX : 0,
offsetY : 0,
baseElWidth : 0,
relativePos : 0,
position: null,
minSwipe : null,
maxSwipe: null,
sliding : null,
dargging: null,
targetElement : null
};
base.isCssFinish = true;
function getTouches(event) {
if (event.touches !== undefined) {
return {
x : event.touches[0].pageX,
y : event.touches[0].pageY
};
}
if (event.touches === undefined) {
if (event.pageX !== undefined) {
return {
x : event.pageX,
y : event.pageY
};
}
if (event.pageX === undefined) {
return {
x : event.clientX,
y : event.clientY
};
}
}
}
function swapEvents(type) {
if (type === "on") {
$(document).on(base.ev_types.move, dragMove);
$(document).on(base.ev_types.end, dragEnd);
} else if (type === "off") {
$(document).off(base.ev_types.move);
$(document).off(base.ev_types.end);
}
}
function dragStart(event) {
var ev = event.originalEvent || event || window.event,
position;
if (ev.which === 3) {
return false;
}
if (base.itemsAmount <= base.options.items) {
return;
}
if (base.isCssFinish === false && !base.options.dragBeforeAnimFinish) {
return false;
}
if (base.isCss3Finish === false && !base.options.dragBeforeAnimFinish) {
return false;
}
if (base.options.autoPlay !== false) {
window.clearInterval(base.autoPlayInterval);
}
if (base.browser.isTouch !== true && !base.$owlWrapper.hasClass("grabbing")) {
base.$owlWrapper.addClass("grabbing");
}
base.newPosX = 0;
base.newRelativeX = 0;
$(this).css(base.removeTransition());
position = $(this).position();
locals.relativePos = position.left;
locals.offsetX = getTouches(ev).x - position.left;
locals.offsetY = getTouches(ev).y - position.top;
swapEvents("on");
locals.sliding = false;
locals.targetElement = ev.target || ev.srcElement;
}
function dragMove(event) {
var ev = event.originalEvent || event || window.event,
minSwipe,
maxSwipe;
base.newPosX = getTouches(ev).x - locals.offsetX;
base.newPosY = getTouches(ev).y - locals.offsetY;
base.newRelativeX = base.newPosX - locals.relativePos;
if (typeof base.options.startDragging === "function" && locals.dragging !== true && base.newRelativeX !== 0) {
locals.dragging = true;
base.options.startDragging.apply(base, [base.$elem]);
}
if ((base.newRelativeX > 8 || base.newRelativeX < -8) && (base.browser.isTouch === true)) {
if (ev.preventDefault !== undefined) {
ev.preventDefault();
} else {
ev.returnValue = false;
}
locals.sliding = true;
}
if ((base.newPosY > 10 || base.newPosY < -10) && locals.sliding === false) {
$(document).off("touchmove.owl");
}
minSwipe = function () {
return base.newRelativeX / 5;
};
maxSwipe = function () {
return base.maximumPixels + base.newRelativeX / 5;
};
base.newPosX = Math.max(Math.min(base.newPosX, minSwipe()), maxSwipe());
if (base.browser.support3d === true) {
base.transition3d(base.newPosX);
} else {
base.css2move(base.newPosX);
}
}
function dragEnd(event) {
var ev = event.originalEvent || event || window.event,
newPosition,
handlers,
owlStopEvent;
ev.target = ev.target || ev.srcElement;
locals.dragging = false;
if (base.browser.isTouch !== true) {
base.$owlWrapper.removeClass("grabbing");
}
if (base.newRelativeX < 0) {
base.dragDirection = base.owl.dragDirection = "left";
} else {
base.dragDirection = base.owl.dragDirection = "right";
}
if (base.newRelativeX !== 0) {
newPosition = base.getNewPosition();
base.goTo(newPosition, false, "drag");
if (locals.targetElement === ev.target && base.browser.isTouch !== true) {
$(ev.target).on("click.disable", function (ev) {
ev.stopImmediatePropagation();
ev.stopPropagation();
ev.preventDefault();
$(ev.target).off("click.disable");
});
handlers = $._data(ev.target, "events").click;
owlStopEvent = handlers.pop();
handlers.splice(0, 0, owlStopEvent);
}
}
swapEvents("off");
}
base.$elem.on(base.ev_types.start, ".owl-wrapper", dragStart);
},
getNewPosition : function () {
var base = this,
newPosition = base.closestItem();
if (newPosition > base.maximumItem) {
base.currentItem = base.maximumItem;
newPosition = base.maximumItem;
} else if (base.newPosX >= 0) {
newPosition = 0;
base.currentItem = 0;
}
return newPosition;
},
closestItem : function () {
var base = this,
array = base.options.scrollPerPage === true ? base.pagesInArray : base.positionsInArray,
goal = base.newPosX,
closest = null;
$.each(array, function (i, v) {
if (goal - (base.itemWidth / 20) > array[i + 1] && goal - (base.itemWidth / 20) < v && base.moveDirection() === "left") {
closest = v;
if (base.options.scrollPerPage === true) {
base.currentItem = $.inArray(closest, base.positionsInArray);
} else {
base.currentItem = i;
}
} else if (goal + (base.itemWidth / 20) < v && goal + (base.itemWidth / 20) > (array[i + 1] || array[i] - base.itemWidth) && base.moveDirection() === "right") {
if (base.options.scrollPerPage === true) {
closest = array[i + 1] || array[array.length - 1];
base.currentItem = $.inArray(closest, base.positionsInArray);
} else {
closest = array[i + 1];
base.currentItem = i + 1;
}
}
});
return base.currentItem;
},
moveDirection : function () {
var base = this,
direction;
if (base.newRelativeX < 0) {
direction = "right";
base.playDirection = "next";
} else {
direction = "left";
base.playDirection = "prev";
}
return direction;
},
customEvents : function () {
/*jslint unparam: true*/
var base = this;
base.$elem.on("owl.next", function () {
base.next();
});
base.$elem.on("owl.prev", function () {
base.prev();
});
base.$elem.on("owl.play", function (event, speed) {
base.options.autoPlay = speed;
base.play();
base.hoverStatus = "play";
});
base.$elem.on("owl.stop", function () {
base.stop();
base.hoverStatus = "stop";
});
base.$elem.on("owl.goTo", function (event, item) {
base.goTo(item);
});
base.$elem.on("owl.jumpTo", function (event, item) {
base.jumpTo(item);
});
},
stopOnHover : function () {
var base = this;
if (base.options.stopOnHover === true && base.browser.isTouch !== true && base.options.autoPlay !== false) {
base.$elem.on("mouseover", function () {
base.stop();
});
base.$elem.on("mouseout", function () {
if (base.hoverStatus !== "stop") {
base.play();
}
});
}
},
lazyLoad : function () {
var base = this,
i,
$item,
itemNumber,
$lazyImg,
follow;
if (base.options.lazyLoad === false) {
return false;
}
for (i = 0; i < base.itemsAmount; i += 1) {
$item = $(base.$owlItems[i]);
if ($item.data("owl-loaded") === "loaded") {
continue;
}
itemNumber = $item.data("owl-item");
$lazyImg = $item.find(".lazyOwl");
if (typeof $lazyImg.data("src") !== "string") {
$item.data("owl-loaded", "loaded");
continue;
}
if ($item.data("owl-loaded") === undefined) {
$lazyImg.hide();
$item.addClass("loading").data("owl-loaded", "checked");
}
if (base.options.lazyFollow === true) {
follow = itemNumber >= base.currentItem;
} else {
follow = true;
}
if (follow && itemNumber < base.currentItem + base.options.items && $lazyImg.length) {
base.lazyPreload($item, $lazyImg);
}
}
},
lazyPreload : function ($item, $lazyImg) {
var base = this,
iterations = 0,
isBackgroundImg;
if ($lazyImg.prop("tagName") === "DIV") {
$lazyImg.css("background-image", "url(" + $lazyImg.data("src") + ")");
isBackgroundImg = true;
} else {
$lazyImg[0].src = $lazyImg.data("src");
}
function showImage() {
$item.data("owl-loaded", "loaded").removeClass("loading");
$lazyImg.removeAttr("data-src");
if (base.options.lazyEffect === "fade") {
$lazyImg.fadeIn(400);
} else {
$lazyImg.show();
}
if (typeof base.options.afterLazyLoad === "function") {
base.options.afterLazyLoad.apply(this, [base.$elem]);
}
}
function checkLazyImage() {
iterations += 1;
if (base.completeImg($lazyImg.get(0)) || isBackgroundImg === true) {
showImage();
} else if (iterations <= 100) {//if image loads in less than 10 seconds
window.setTimeout(checkLazyImage, 100);
} else {
showImage();
}
}
checkLazyImage();
},
autoHeight : function () {
var base = this,
$currentimg = $(base.$owlItems[base.currentItem]).find("img"),
iterations;
function addHeight() {
var $currentItem = $(base.$owlItems[base.currentItem]).height();
base.wrapperOuter.css("height", $currentItem + "px");
if (!base.wrapperOuter.hasClass("autoHeight")) {
window.setTimeout(function () {
base.wrapperOuter.addClass("autoHeight");
}, 0);
}
}
function checkImage() {
iterations += 1;
if (base.completeImg($currentimg.get(0))) {
addHeight();
} else if (iterations <= 100) { //if image loads in less than 10 seconds
window.setTimeout(checkImage, 100);
} else {
base.wrapperOuter.css("height", ""); //Else remove height attribute
}
}
if ($currentimg.get(0) !== undefined) {
iterations = 0;
checkImage();
} else {
addHeight();
}
},
completeImg : function (img) {
var naturalWidthType;
if (!img.complete) {
return false;
}
naturalWidthType = typeof img.naturalWidth;
if (naturalWidthType !== "undefined" && img.naturalWidth === 0) {
return false;
}
return true;
},
onVisibleItems : function () {
var base = this,
i;
if (base.options.addClassActive === true) {
base.$owlItems.removeClass("active");
}
base.visibleItems = [];
for (i = base.currentItem; i < base.currentItem + base.options.items; i += 1) {
base.visibleItems.push(i);
if (base.options.addClassActive === true) {
$(base.$owlItems[i]).addClass("active");
}
}
base.owl.visibleItems = base.visibleItems;
},
transitionTypes : function (className) {
var base = this;
//Currently available: "fade", "backSlide", "goDown", "fadeUp"
base.outClass = "owl-" + className + "-out";
base.inClass = "owl-" + className + "-in";
},
singleItemTransition : function () {
var base = this,
outClass = base.outClass,
inClass = base.inClass,
$currentItem = base.$owlItems.eq(base.currentItem),
$prevItem = base.$owlItems.eq(base.prevItem),
prevPos = Math.abs(base.positionsInArray[base.currentItem]) + base.positionsInArray[base.prevItem],
origin = Math.abs(base.positionsInArray[base.currentItem]) + base.itemWidth / 2,
animEnd = 'webkitAnimationEnd oAnimationEnd MSAnimationEnd animationend';
base.isTransition = true;
base.$owlWrapper
.addClass('owl-origin')
.css({
"-webkit-transform-origin" : origin + "px",
"-moz-perspective-origin" : origin + "px",
"perspective-origin" : origin + "px"
});
function transStyles(prevPos) {
return {
"position" : "relative",
"left" : prevPos + "px"
};
}
$prevItem
.css(transStyles(prevPos, 10))
.addClass(outClass)
.on(animEnd, function () {
base.endPrev = true;
$prevItem.off(animEnd);
base.clearTransStyle($prevItem, outClass);
});
$currentItem
.addClass(inClass)
.on(animEnd, function () {
base.endCurrent = true;
$currentItem.off(animEnd);
base.clearTransStyle($currentItem, inClass);
});
},
clearTransStyle : function (item, classToRemove) {
var base = this;
item.css({
"position" : "",
"left" : ""
}).removeClass(classToRemove);
if (base.endPrev && base.endCurrent) {
base.$owlWrapper.removeClass('owl-origin');
base.endPrev = false;
base.endCurrent = false;
base.isTransition = false;
}
},
owlStatus : function () {
var base = this;
base.owl = {
"userOptions" : base.userOptions,
"baseElement" : base.$elem,
"userItems" : base.$userItems,
"owlItems" : base.$owlItems,
"currentItem" : base.currentItem,
"prevItem" : base.prevItem,
"visibleItems" : base.visibleItems,
"isTouch" : base.browser.isTouch,
"browser" : base.browser,
"dragDirection" : base.dragDirection
};
},
clearEvents : function () {
var base = this;
base.$elem.off(".owl owl mousedown.disableTextSelect");
$(document).off(".owl owl");
$(window).off("resize", base.resizer);
},
unWrap : function () {
var base = this;
if (base.$elem.children().length !== 0) {
base.$owlWrapper.unwrap();
base.$userItems.unwrap().unwrap();
if (base.owlControls) {
base.owlControls.remove();
}
}
base.clearEvents();
base.$elem
.attr("style", base.$elem.data("owl-originalStyles") || "")
.attr("class", base.$elem.data("owl-originalClasses"));
},
destroy : function () {
var base = this;
base.stop();
window.clearInterval(base.checkVisible);
base.unWrap();
base.$elem.removeData();
},
reinit : function (newOptions) {
var base = this,
options = $.extend({}, base.userOptions, newOptions);
base.unWrap();
base.init(options, base.$elem);
},
addItem : function (htmlString, targetPosition) {
var base = this,
position;
if (!htmlString) {return false; }
if (base.$elem.children().length === 0) {
base.$elem.append(htmlString);
base.setVars();
return false;
}
base.unWrap();
if (targetPosition === undefined || targetPosition === -1) {
position = -1;
} else {
position = targetPosition;
}
if (position >= base.$userItems.length || position === -1) {
base.$userItems.eq(-1).after(htmlString);
} else {
base.$userItems.eq(position).before(htmlString);
}
base.setVars();
},
removeItem : function (targetPosition) {
var base = this,
position;
if (base.$elem.children().length === 0) {
return false;
}
if (targetPosition === undefined || targetPosition === -1) {
position = -1;
} else {
position = targetPosition;
}
base.unWrap();
base.$userItems.eq(position).remove();
base.setVars();
}
};
$.fn.owlCarousel = function (options) {
return this.each(function () {
if ($(this).data("owl-init") === true) {
return false;
}
$(this).data("owl-init", true);
var carousel = Object.create(Carousel);
carousel.init(options, this);
$.data(this, "owlCarousel", carousel);
});
};
$.fn.owlCarousel.options = {
items : 5,
itemsCustom : false,
itemsDesktop : [1199, 4],
itemsDesktopSmall : [979, 3],
itemsTablet : [768, 2],
itemsTabletSmall : false,
itemsMobile : [479, 1],
singleItem : false,
itemsScaleUp : false,
slideSpeed : 200,
paginationSpeed : 800,
rewindSpeed : 1000,
autoPlay : false,
stopOnHover : false,
navigation : false,
navigationText : ["prev", "next"],
rewindNav : true,
scrollPerPage : false,
pagination : true,
paginationNumbers : false,
responsive : true,
responsiveRefreshRate : 200,
responsiveBaseWidth : window,
baseClass : "owl-carousel",
theme : "owl-theme",
lazyLoad : false,
lazyFollow : true,
lazyEffect : "fade",
autoHeight : false,
jsonPath : false,
jsonSuccess : false,
dragBeforeAnimFinish : true,
mouseDrag : true,
touchDrag : true,
addClassActive : false,
transitionStyle : false,
beforeUpdate : false,
afterUpdate : false,
beforeInit : false,
afterInit : false,
beforeMove : false,
afterMove : false,
afterAction : false,
startDragging : false,
afterLazyLoad: false
};
}(jQuery, window, document));
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\SlideBanner\Api\Data;
/**
* CMS page interface.
* @api
*/
interface SliderInterface
{
/**#@+
* Constants for keys of data array. Identical to the name of the getter in snake case
*/
const SLIDER_ID = 'slider_id';
const IDENTIFIER = 'identifier';
const SLIDER_TITLE = 'slider_title';
const SLIDER_STATUS = 'slider_status';
const SLIDER_SETTING = 'slider_setting';
const STOREIDS = 'storeids';
const SLIDER_STYLE = 'slider_styles';
const SLIDER_SCRIPT = 'slider_script';
const CREATED_AT = 'created_at';
/**#@-*/
/**
* Get ID
*
* @return int|null
*/
public function getId();
public function setId($value);
public function getIdentifier();
public function setIdentifier($value);
public function getSliderTitle();
public function setSliderTitle($value);
public function getSliderStatus();
public function setSliderStatus($value);
public function getSliderSetting();
public function setSliderSetting($value);
public function getStoreids();
public function setStoreids($value);
public function getSliderStyles();
public function setSliderStyles($value);
public function getSliderScript();
public function setSliderScript($value);
public function getCreatedAt();
public function setCreatedAt($value);
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\SlideBanner\Api;
use Magento\Framework\Api\SearchCriteriaInterface;
/**
* CMS page CRUD interface.
* @api
*/
interface SliderRepositoryInterface
{
/**
* Save page.
*
* @param \Magento\Cms\Api\Data\PageInterface $page
* @return \Magento\Cms\Api\Data\PageInterface
* @throws \Magento\Framework\Exception\LocalizedException
*/
public function save(\Magento\Cms\Api\Data\PageInterface $page);
/**
* Retrieve page.
*
* @param int $pageId
* @return \Magento\Cms\Api\Data\PageInterface
* @throws \Magento\Framework\Exception\LocalizedException
*/
public function getById($pageId);
/**
* Retrieve pages matching the specified criteria.
*
* @param \Magento\Framework\Api\SearchCriteriaInterface $searchCriteria
* @return \Magento\Cms\Api\Data\PageSearchResultsInterface
* @throws \Magento\Framework\Exception\LocalizedException
*/
public function getList(\Magento\Framework\Api\SearchCriteriaInterface $searchCriteria);
/**
* Delete page.
*
* @param \Magento\Cms\Api\Data\PageInterface $page
* @return bool true on success
* @throws \Magento\Framework\Exception\LocalizedException
*/
public function delete(\Magento\Cms\Api\Data\PageInterface $page);
/**
* Delete page by ID.
*
* @param int $pageId
* @return bool true on success
* @throws \Magento\Framework\Exception\NoSuchEntityException
* @throws \Magento\Framework\Exception\LocalizedException
*/
public function deleteById($pageId);
}
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml;
use Magento\Backend\Block\Widget\Grid\Container;
class Slide extends Container
{
/**
* Constructor
*
* @return void
*/
protected function _construct()
{
$this->_controller = 'adminhtml_slide';
$this->_blockGroup = 'Rokanthemes_SlideBanner';
$this->_headerText = __('Manage Banner');
$this->_addButtonLabel = __('Add Banner');
parent::_construct();
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slide;
use Magento\Backend\Block\Widget\Form\Container;
use Magento\Backend\Block\Widget\Context;
use Magento\Framework\Registry;
class Edit extends Container
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry = null;
/**
* @param Context $context
* @param Registry $registry
* @param array $data
*/
public function __construct(
Context $context,
Registry $registry,
array $data = []
) {
$this->_coreRegistry = $registry;
parent::__construct($context, $data);
}
/**
* Class constructor
*
* @return void
*/
protected function _construct()
{
$this->_objectId = 'slide_id';
$this->_controller = 'adminhtml_slide';
$this->_blockGroup = 'Rokanthemes_SlideBanner';
parent::_construct();
$this->buttonList->update('save', 'label', __('Save'));
$this->buttonList->add(
'saveandcontinue',
[
'label' => __('Save and Continue Edit'),
'class' => 'save',
'data_attribute' => [
'mage-init' => [
'button' => [
'event' => 'saveAndContinueEdit',
'target' => '#edit_form'
]
]
]
],
-100
);
$this->buttonList->update('delete', 'label', __('Delete'));
}
/**
* Retrieve text for header element depending on loaded news
*
* @return string
*/
public function getHeaderText()
{
$newsRegistry = $this->_coreRegistry->registry('slide_form_data');
if ($newsRegistry->getId()) {
$newsTitle = $this->escapeHtml($newsRegistry->getTitle());
return __("Edit Banner '%1'", $newsTitle);
} else {
return __('Add Banner');
}
}
/**
* Prepare layout
*
* @return \Magento\Framework\View\Element\AbstractBlock
*/
protected function _prepareLayout()
{
$this->_formScripts[] = "
function toggleEditor() {
if (tinyMCE.getInstanceById('post_content') == null) {
tinyMCE.execCommand('mceAddControl', false, 'post_content');
} else {
tinyMCE.execCommand('mceRemoveControl', false, 'post_content');
}
};
";
return parent::_prepareLayout();
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slide\Edit;
use Magento\Backend\Block\Widget\Form\Generic;
class Form extends Generic
{
/**
* @return $this
*/
protected function _prepareForm()
{
/** @var \Magento\Framework\Data\Form $form */
$form = $this->_formFactory->create(
[
'data' => [
'id' => 'edit_form',
'action' => $this->getUrl('*/*/save', ['slide_id' => $this->getRequest()->getParam('slide_id')]),
'method' => 'post',
'enctype' => 'multipart/form-data',
]
]
);
$form->setUseContainer(true);
$this->setForm($form);
return parent::_prepareForm();
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slide\Edit\Tab;
use Magento\Backend\Block\Widget\Form\Generic;
use Magento\Backend\Block\Widget\Tab\TabInterface;
use Magento\Backend\Block\Template\Context;
use Magento\Framework\Registry;
use Magento\Framework\Data\FormFactory;
use Magento\Cms\Model\Wysiwyg\Config;
class Info extends Generic implements TabInterface
{
/**
* @var \Magento\Cms\Model\Wysiwyg\Config
*/
protected $_wysiwygConfig;
protected $_newsStatus;
protected $_objectManager;
/**
* @param Context $context
* @param Registry $registry
* @param FormFactory $formFactory
* @param Config $wysiwygConfig
* @param array $data
*/
public function __construct(
Context $context,
Registry $registry,
FormFactory $formFactory,
Config $wysiwygConfig,
\Magento\Framework\ObjectManagerInterface $objectManager,
array $data = []
) {
$this->_wysiwygConfig = $wysiwygConfig;
$this->_objectManager = $objectManager;
parent::__construct($context, $registry, $formFactory, $data);
}
/**
* Prepare form fields
*
* @return \Magento\Backend\Block\Widget\Form
*/
protected function _prepareForm()
{
/** @var $model \Rokanthemes\SlideBanner\Model\Slide */
$model = $this->_coreRegistry->registry('slide_form_data');
/** @var \Magento\Framework\Data\Form $form */
$form = $this->_formFactory->create();
$form->setHtmlIdPrefix('slide_');
$form->setFieldNameSuffix('slide');
$fieldset = $form->addFieldset(
'base_fieldset',
['legend' => __('General')]
);
$fieldset->addField(
'slider_id',
'select',
[
'name' => 'slider_id',
'label' => __('Slider'),
'required' => false,
'values'=>$this->_getSliderOptions()
]
);
$fieldset->addField(
'slide_status',
'select',
[
'name' => 'slide_status',
'label' => __('Status'),
'required' => false,
'values'=> [['value'=>1, 'label'=> __('Enable')], ['value'=>2, 'label'=> __('Disable')]]
]
);
$fieldset->addField(
'slide_image',
'image',
[
'name' => 'slide_image',
'label' => __('Image'),
'required' => false
]
);
$fieldset->addField(
'slide_link',
'text',
[
'name' => 'slide_link',
'label' => __('Link Banner'),
'required' => false
]
);
$wysiwygConfig = $this->_wysiwygConfig->getConfig();
$fieldset->addField(
'slide_text',
'editor',
[
'name' => 'slide_text',
'label' => __('Banner Text'),
'required' => false,
'config' => $wysiwygConfig
]
);
$data = $model->getData();
$form->setValues($data);
$this->setForm($form);
return parent::_prepareForm();
}
protected function _getSliderOptions()
{
$result = [];
$collection = $this->_objectManager->create('Rokanthemes\SlideBanner\Model\Slider', [])->getCollection();
foreach($collection as $slider)
{
$result[] = array('value'=>$slider->getId(), 'label'=>$slider->getSliderTitle());
}
return $result;
}
/**
* Prepare label for tab
*
* @return string
*/
public function getTabLabel()
{
return __('Banner Info');
}
/**
* Prepare title for tab
*
* @return string
*/
public function getTabTitle()
{
return __('Banner Info');
}
/**
* {@inheritdoc}
*/
public function canShowTab()
{
return true;
}
/**
* {@inheritdoc}
*/
public function isHidden()
{
return false;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slide\Edit;
use Magento\Backend\Block\Widget\Tabs as WidgetTabs;
class Tabs extends WidgetTabs
{
/**
* Class constructor
*
* @return void
*/
protected function _construct()
{
parent::_construct();
$this->setId('slide_edit_tabs');
$this->setDestElementId('edit_form');
$this->setTitle(__('Banner Information'));
}
/**
* @return $this
*/
protected function _beforeToHtml()
{
$this->addTab(
'news_info',
[
'label' => __('General'),
'title' => __('General'),
'content' => $this->getLayout()->createBlock(
'Rokanthemes\SlideBanner\Block\Adminhtml\Slide\Edit\Tab\Info'
)->toHtml(),
'active' => true
]
);
return parent::_beforeToHtml();
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slide;
use Magento\Backend\Block\Widget\Grid as WidgetGrid;
class Grid extends \Magento\Backend\Block\Widget\Grid\Extended
{
/**
* @var \Magento\Framework\Module\Manager
*/
protected $moduleManager;
/**
* @var \Webkul\Grid\Model\GridFactory
*/
protected $_collection;
/**
* @var \Webkul\Grid\Model\Status
*/
protected $_status;
protected $_objectManager;
/**
* @param \Magento\Backend\Block\Template\Context $context
* @param \Magento\Backend\Helper\Data $backendHelper
* @param \Magento\Framework\Module\Manager $moduleManager
* @param array $data
*
* @SuppressWarnings(PHPMD.ExcessiveParameterList)
*/
public function __construct(
\Magento\Backend\Block\Template\Context $context,
\Magento\Backend\Helper\Data $backendHelper,
\Magento\Framework\ObjectManagerInterface $objectManager,
array $data = []
) {
$this->_objectManager = $objectManager;
parent::__construct($context, $backendHelper, $data);
}
/**
* @return void
*/
protected function _construct()
{
parent::_construct();
$this->setId('gridGrid');
$this->setDefaultSort('slide_id');
$this->setDefaultDir('DESC');
$this->setSaveParametersInSession(true);
$this->setUseAjax(true);
$this->setVarNameFilter('grid_record');
}
/**
* @return $this
*/
protected function _prepareCollection()
{
$collection = $this->_objectManager->create('Rokanthemes\SlideBanner\Model\Slide', [])->getCollection()->joinSlider();
$this->setCollection($collection);
parent::_prepareCollection();
return $this;
}
/**
* @return $this
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
*/
protected function _prepareColumns()
{
$this->addColumn(
'slide_id',
[
'header' => __('ID'),
'type' => 'number',
'index' => 'slide_id',
'header_css_class' => 'col-id',
'column_css_class' => 'col-id'
]
);
$this->addColumn(
'slider_id',
[
'header' => __('Slider'),
'type' => 'options',
'index' => 'slider_id',
'filter_index' => 'main_table.slider_id',
'options'=> $this->_getSliderOptions(),
'header_css_class' => 'col-id',
'column_css_class' => 'col-id'
]
);
$this->addColumn(
'slide_status',
[
'header' => __('Status'),
'type' => 'options',
'index' => 'slide_status',
'options'=> [1=>__('Enable'), 2=>__('Disable')],
'header_css_class' => 'col-id',
'column_css_class' => 'col-id'
]
);
$this->addColumn(
'slide_image',
[
'header' => __('Images'),
'renderer' => 'Rokanthemes\SlideBanner\Block\Adminhtml\Slide\Renderer\Image',
'filter' => false,
'order' => false,
'options'=> [1=>__('Enable'), 2=>__('Disable')],
'header_css_class' => 'col-id',
'column_css_class' => 'col-id'
]
);
$block = $this->getLayout()->getBlock('grid.bottom.links');
if ($block) {
$this->setChild('grid.bottom.links', $block);
}
return parent::_prepareColumns();
}
protected function _getSliderOptions()
{
$result = [];
$collection = $this->_objectManager->create('Rokanthemes\SlideBanner\Model\Slider', [])->getCollection();
foreach($collection as $slider)
{
$result[$slider->getId()] = $slider->getSliderTitle();
}
return $result;
}
/**
* @return $this
*/
//
/**
* @return string
*/
public function getGridUrl()
{
return $this->getUrl('*/*/grid', ['_current' => true]);
}
public function getRowUrl($row)
{
return $this->getUrl(
'*/*/edit',
['slide_id' => $row->getId()]
);
}
}
\ No newline at end of file
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slide\Renderer;
/**
* Adminhtml customers wishlist grid item action renderer for few action controls in one cell
*
* @author Magento Core Team <core@magentocommerce.com>
*/
class Image extends \Magento\Backend\Block\Widget\Grid\Column\Renderer\Text
{
protected $_storeManager;
/**
* Renders column
*
* @param \Magento\Framework\DataObject $row
* @return string
*/
public function __construct(
\Magento\Backend\Block\Context $context,
\Magento\Store\Model\StoreManagerInterface $storeManager,
array $data = []
) {
$this->_storeManager = $storeManager;
parent::__construct($context, $data);
}
public function render(\Magento\Framework\DataObject $row)
{
$html = '';
$mediaUrl = $this->_storeManager->getStore()->getBaseUrl(\Magento\Framework\UrlInterface::URL_TYPE_MEDIA);
if($image = $row->getSlideImage())
$html = '<img height="50" src="' . $mediaUrl . $image . '" />';
return $html;
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\SlideBanner\Block\Adminhtml;
/**
* Adminhtml cms pages content block
*/
use Magento\Backend\Block\Widget\Grid\Container;
class Slider extends Container
{
/**
* Constructor
*
* @return void
*/
protected function _construct()
{
$this->_controller = 'adminhtml_slider';
$this->_blockGroup = 'Rokanthemes_SlideBanner';
$this->_headerText = __('Manage Slider');
$this->_addButtonLabel = __('Add Slider');
parent::_construct();
}
}
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slider;
use Magento\Backend\Block\Widget\Form\Container;
use Magento\Backend\Block\Widget\Context;
use Magento\Framework\Registry;
class Edit extends Container
{
protected $_objectId = 'slider_id';
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry = null;
/**
* @param Context $context
* @param Registry $registry
* @param array $data
*/
public function __construct(
Context $context,
Registry $registry,
array $data = []
) {
$this->_coreRegistry = $registry;
parent::__construct($context, $data);
}
/**
* Class constructor
*
* @return void
*/
protected function _construct()
{
$this->_objectId = 'slider_id';
$this->_controller = 'adminhtml_slider';
$this->_blockGroup = 'Rokanthemes_SlideBanner';
parent::_construct();
$this->buttonList->update('save', 'label', __('Save'));
$this->buttonList->update('delete', 'label', __('Delete'));
$this->buttonList->add(
'saveandcontinue',
[
'label' => __('Save and Continue Edit'),
'class' => 'save',
'data_attribute' => [
'mage-init' => [
'button' => [
'event' => 'saveAndContinueEdit',
'target' => '#edit_form'
]
]
]
],
-100
);
}
/**
* Retrieve text for header element depending on loaded news
*
* @return string
*/
public function getHeaderText()
{
$newsRegistry = $this->_coreRegistry->registry('simplenews_news');
if ($newsRegistry->getId()) {
$newsTitle = $this->escapeHtml($newsRegistry->getTitle());
return __("Edit News '%1'", $newsTitle);
} else {
return __('Add News');
}
}
/**
* Prepare layout
*
* @return \Magento\Framework\View\Element\AbstractBlock
*/
protected function _prepareLayout()
{
$this->_formScripts[] = "
function toggleEditor() {
if (tinyMCE.getInstanceById('post_content') == null) {
tinyMCE.execCommand('mceAddControl', false, 'post_content');
} else {
tinyMCE.execCommand('mceRemoveControl', false, 'post_content');
}
};
";
return parent::_prepareLayout();
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slider\Edit;
use Magento\Backend\Block\Widget\Form\Generic;
class Form extends Generic
{
/**
* @return $this
*/
protected function _prepareForm()
{
/** @var \Magento\Framework\Data\Form $form */
$form = $this->_formFactory->create(
[
'data' => [
'id' => 'edit_form',
'action' => $this->getUrl('*/*/save', ['slider_id' => $this->getRequest()->getParam('slider_id')]),
'method' => 'post',
'enctype' => 'multipart/form-data',
]
]
);
$form->setUseContainer(true);
$this->setForm($form);
return parent::_prepareForm();
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slider\Edit\Tab;
use Magento\Backend\Block\Widget\Grid as WidgetGrid;
class Banner extends \Magento\Backend\Block\Widget\Grid\Extended
{
/**
* @var \Magento\Framework\Module\Manager
*/
protected $moduleManager;
/**
* @var \Webkul\Grid\Model\GridFactory
*/
protected $_collection;
/**
* @var \Webkul\Grid\Model\Status
*/
protected $_status;
protected $_objectManager;
/**
* @param \Magento\Backend\Block\Template\Context $context
* @param \Magento\Backend\Helper\Data $backendHelper
* @param \Magento\Framework\Module\Manager $moduleManager
* @param array $data
*
* @SuppressWarnings(PHPMD.ExcessiveParameterList)
*/
public function __construct(
\Magento\Backend\Block\Template\Context $context,
\Magento\Backend\Helper\Data $backendHelper,
\Magento\Framework\ObjectManagerInterface $objectManager,
array $data = []
) {
$this->_objectManager = $objectManager;
parent::__construct($context, $backendHelper, $data);
}
/**
* @return void
*/
protected function _construct()
{
parent::_construct();
$this->setId('slideGrid');
$this->setDefaultSort('slide_id');
$this->setDefaultDir('DESC');
$this->setSaveParametersInSession(true);
$this->setUseAjax(true);
$this->setVarNameFilter('grid_record');
}
/**
* @return $this
*/
protected function _prepareCollection()
{
$collection = $this->_objectManager->create('Rokanthemes\SlideBanner\Model\Slide', [])->getCollection();
$collection->addFieldToFilter('slider_id', $this->getRequest()->getParam('slider_id'));
$this->setCollection($collection);
parent::_prepareCollection();
return $this;
}
/**
* @return $this
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
*/
protected function _prepareColumns()
{
$this->addColumn(
'slide_id',
[
'header' => __('ID'),
'type' => 'number',
'index' => 'slide_id',
'header_css_class' => 'col-id',
'column_css_class' => 'col-id'
]
);
$this->addColumn(
'slide_status',
[
'header' => __('Status'),
'type' => 'options',
'index' => 'slide_status',
'options'=> [1=>__('Enable'), 2=>__('Disable')],
'header_css_class' => 'col-id',
'column_css_class' => 'col-id'
]
);
$this->addColumn(
'slide_image',
[
'header' => __('Images'),
'renderer' => 'Rokanthemes\SlideBanner\Block\Adminhtml\Slide\Renderer\Image',
'filter' => false,
'order' => false,
'options'=> [1=>__('Enable'), 2=>__('Disable')],
'header_css_class' => 'col-id',
'column_css_class' => 'col-id'
]
);
$block = $this->getLayout()->getBlock('grid.bottom.links');
if ($block) {
$this->setChild('grid.bottom.links', $block);
}
return parent::_prepareColumns();
}
/**
* @return $this
*/
//
/**
* @return string
*/
public function getGridUrl()
{
return $this->getUrl('*/*/slidegrid', ['_current' => true]);
}
public function getRowUrl($row)
{
return $this->getUrl(
'*/slide/edit',
['slide_id' => $row->getId(), 'slider_id'=>$this->getRequest()->getParam('slider_id')]
);
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slider\Edit\Tab;
use Magento\Backend\Block\Widget\Form\Generic;
use Magento\Backend\Block\Widget\Tab\TabInterface;
use Magento\Backend\Block\Template\Context;
use Magento\Framework\Registry;
use Magento\Framework\Data\FormFactory;
use Magento\Cms\Model\Wysiwyg\Config;
class Info extends Generic implements TabInterface
{
/**
* @var \Magento\Cms\Model\Wysiwyg\Config
*/
protected $_wysiwygConfig;
protected $_newsStatus;
protected $_objectManager;
/**
* @param Context $context
* @param Registry $registry
* @param FormFactory $formFactory
* @param Config $wysiwygConfig
* @param array $data
*/
public function __construct(
Context $context,
Registry $registry,
FormFactory $formFactory,
Config $wysiwygConfig,
\Magento\Framework\ObjectManagerInterface $objectManager,
array $data = []
) {
$this->_wysiwygConfig = $wysiwygConfig;
$this->_objectManager = $objectManager;
parent::__construct($context, $registry, $formFactory, $data);
}
/**
* Prepare form fields
*
* @return \Magento\Backend\Block\Widget\Form
*/
protected function _prepareForm()
{
/** @var $model \Rokanthemes\SlideBanner\Model\Slide */
$model = $this->_coreRegistry->registry('slider_form_data');
/** @var \Magento\Framework\Data\Form $form */
$form = $this->_formFactory->create();
$form->setHtmlIdPrefix('slider_');
$form->setFieldNameSuffix('slider');
$fieldset = $form->addFieldset(
'base_fieldset',
['legend' => __('General')]
);
$fieldset->addField(
'slider_title',
'text',
[
'name' => 'slider_title',
'label' => __('Title'),
'required' => true,
]
);
$fieldset->addField(
'slider_identifier',
'text',
[
'name' => 'slider_identifier',
'label' => __('Identifier'),
'required' => true,
]
);
$fieldset->addField(
'slider_status',
'select',
[
'name' => 'slider_status',
'label' => __('Status'),
'required' => false,
'values'=> [['value'=>1, 'label'=> __('Enable')], ['value'=>2, 'label'=> __('Disable')]]
]
);/*
$wysiwygConfig = $this->_wysiwygConfig->getConfig();
$fieldset->addField(
'slide_text',
'editor',
[
'name' => 'slide_text',
'label' => __('Slide Text'),
'required' => false,
'config' => $wysiwygConfig
]
); */
$data = $model->getData();
$form->setValues($data);
$this->setForm($form);
return parent::_prepareForm();
}
/**
* Prepare label for tab
*
* @return string
*/
public function getTabLabel()
{
return __('Slider Info');
}
/**
* Prepare title for tab
*
* @return string
*/
public function getTabTitle()
{
return __('Slider Info');
}
/**
* {@inheritdoc}
*/
public function canShowTab()
{
return true;
}
/**
* {@inheritdoc}
*/
public function isHidden()
{
return false;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slider\Edit\Tab;
use Magento\Backend\Block\Widget\Form\Generic;
use Magento\Backend\Block\Widget\Tab\TabInterface;
use Magento\Backend\Block\Template\Context;
use Magento\Framework\Registry;
use Magento\Framework\Data\FormFactory;
use Magento\Cms\Model\Wysiwyg\Config;
class Setting extends Generic implements TabInterface
{
/**
* @var \Magento\Cms\Model\Wysiwyg\Config
*/
protected $_wysiwygConfig;
protected $_newsStatus;
protected $_objectManager;
/**
* @param Context $context
* @param Registry $registry
* @param FormFactory $formFactory
* @param Config $wysiwygConfig
* @param array $data
*/
public function __construct(
Context $context,
Registry $registry,
FormFactory $formFactory,
Config $wysiwygConfig,
\Magento\Framework\ObjectManagerInterface $objectManager,
array $data = []
) {
$this->_wysiwygConfig = $wysiwygConfig;
$this->_objectManager = $objectManager;
parent::__construct($context, $registry, $formFactory, $data);
}
/**
* Prepare form fields
*
* @return \Magento\Backend\Block\Widget\Form
*/
protected function _prepareForm()
{
/** @var $model \Rokanthemes\SlideBanner\Model\Slide */
$model = $this->_coreRegistry->registry('slider_form_data');
$defaultSetting = array('items'=>1, 'itemsDesktop'=>'[1199,1]', 'itemsDesktopSmall' => '[980,3]', 'itemsTablet' => '[768,2]', 'itemsMobile' => '[479,1]', 'slideSpeed' => 500, 'paginationSpeed' => 500, 'rewindSpeed'=>500);
$setting = $model->getSliderSetting();
$data = array_merge($defaultSetting, $setting);
/** @var \Magento\Framework\Data\Form $form */
$form = $this->_formFactory->create();
$form->setHtmlIdPrefix('slider_');
$form->setFieldNameSuffix('slider');
$fieldset = $form->addFieldset(
'base_fieldset',
['legend' => __('Setting')]
);
$fieldset->addField(
'autoPlay',
'select',
[
'name' => 'slider_setting[autoPlay]',
'label' => __('Autoplay'),
'required' => false,
'values'=> [['value'=>false, 'label'=> __('False')], ['value'=>true, 'label'=> __('True')]]
]
);
$fieldset->addField(
'navigation',
'select',
[
'name' => 'slider_setting[navigation]',
'label' => __('Navigation'),
'required' => false,
'values'=> [['value'=>false, 'label'=> __('False')], ['value'=>true, 'label'=> __('True')]]
]
);
$fieldset->addField(
'stopOnHover',
'select',
[
'name' => 'slider_setting[stopOnHover]',
'label' => __('Stop On Hover'),
'required' => false,
'values'=> [['value'=>false, 'label'=> __('False')], ['value'=>true, 'label'=> __('True')]]
]
);
$fieldset->addField(
'pagination',
'select',
[
'name' => 'slider_setting[pagination]',
'label' => __('Pagination'),
'required' => false,
'values'=> [['value'=>false, 'label'=> __('False')], ['value'=>true, 'label'=> __('True')]]
]
);
$fieldset->addField(
'scrollPerPage',
'select',
[
'name' => 'slider_setting[scrollPerPage]',
'label' => __('Scroll Per Page'),
'required' => false,
'values'=> [['value'=>false, 'label'=> __('False')], ['value'=>true, 'label'=> __('True')]]
]
);
$fieldset->addField(
'items',
'text',
[
'name' => 'slider_setting[items]',
'label' => __('Items'),
'required' => true,
'class' => 'validate-number',
'default'=> 1
]
);
$fieldset->addField(
'rewindSpeed',
'text',
[
'name' => 'slider_setting[rewindSpeed]',
'label' => __('Rewind Speed'),
'required' => true,
'class' => 'validate-number',
'default'=> 1
]
);
$fieldset->addField(
'paginationSpeed',
'text',
[
'name' => 'slider_setting[paginationSpeed]',
'label' => __('Pagination Speed'),
'required' => true,
'class' => 'validate-number',
'default'=> 1
]
);
$fieldset->addField(
'slideSpeed',
'text',
[
'name' => 'slider_setting[slideSpeed]',
'label' => __('Slide Speed'),
'required' => true,
'class' => 'validate-number',
'default'=> 1
]
);
$fieldset->addField(
'itemsDesktop',
'text',
[
'name' => 'slider_setting[itemsDesktop]',
'label' => __('Items Desktop'),
'required' => true
]
);
$fieldset->addField(
'itemsDesktopSmall',
'text',
[
'name' => 'slider_setting[itemsDesktopSmall]',
'label' => __('Items Desktop Small'),
'required' => true
]
);
$fieldset->addField(
'itemsTablet',
'text',
[
'name' => 'slider_setting[itemsTablet]',
'label' => __('Items Tablet'),
'required' => true
]
);
$form->setValues($data);
$this->setForm($form);
return parent::_prepareForm();
}
/**
* Prepare label for tab
*
* @return string
*/
public function getTabLabel()
{
return __('Slider Info');
}
/**
* Prepare title for tab
*
* @return string
*/
public function getTabTitle()
{
return __('Slider Info');
}
/**
* {@inheritdoc}
*/
public function canShowTab()
{
return true;
}
/**
* {@inheritdoc}
*/
public function isHidden()
{
return false;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slider\Edit;
use Magento\Backend\Block\Widget\Tabs as WidgetTabs;
class Tabs extends WidgetTabs
{
/**
* Class constructor
*
* @return void
*/
protected function _construct()
{
parent::_construct();
$this->setId('slide_edit_tabs');
$this->setDestElementId('edit_form');
$this->setTitle(__('Slider Information'));
}
/**
* @return $this
*/
protected function _beforeToHtml()
{
$this->addTab(
'slider_info',
[
'label' => __('General'),
'title' => __('General'),
'content' => $this->getLayout()->createBlock(
'Rokanthemes\SlideBanner\Block\Adminhtml\Slider\Edit\Tab\Info'
)->toHtml(),
'active' => true
]
);
$this->addTab(
'slider_setting',
[
'label' => __('Setting Slider'),
'title' => __('Setting Slider'),
'content' => $this->getLayout()->createBlock(
'Rokanthemes\SlideBanner\Block\Adminhtml\Slider\Edit\Tab\Setting'
)->toHtml(),
'active' => false
]
);
$this->addTab(
'slide_info',
[
'label' => __('Banner List'),
'title' => __('Banner List'),
'content' => $this->getLayout()->createBlock(
'Rokanthemes\SlideBanner\Block\Adminhtml\Slider\Edit\Tab\Banner'
)->toHtml(),
'active' => false
]
);
return parent::_beforeToHtml();
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slider;
use Magento\Backend\Block\Widget\Grid as WidgetGrid;
class Grid extends \Magento\Backend\Block\Widget\Grid\Extended
{
/**
* @var \Magento\Framework\Module\Manager
*/
protected $moduleManager;
protected $_collection;
/**
* @var \Webkul\Grid\Model\Status
*/
protected $_status;
protected $_objectManager;
/**
* @param \Magento\Backend\Block\Template\Context $context
* @param \Magento\Backend\Helper\Data $backendHelper
* @param \Magento\Framework\Module\Manager $moduleManager
* @param array $data
*
* @SuppressWarnings(PHPMD.ExcessiveParameterList)
*/
public function __construct(
\Magento\Backend\Block\Template\Context $context,
\Magento\Backend\Helper\Data $backendHelper,
\Magento\Framework\ObjectManagerInterface $objectManager,
array $data = []
) {
$this->_objectManager = $objectManager;
parent::__construct($context, $backendHelper, $data);
}
/**
* @return void
*/
protected function _construct()
{
parent::_construct();
$this->setId('sliderGrid');
$this->setDefaultSort('slider_id');
$this->setDefaultDir('DESC');
$this->setSaveParametersInSession(true);
$this->setUseAjax(true);
$this->setVarNameFilter('slider_record');
}
/**
* @return $this
*/
protected function _prepareCollection()
{
$collection = $this->_objectManager->create('Rokanthemes\SlideBanner\Model\Slider', [])->getCollection();
$this->setCollection($collection);
parent::_prepareCollection();
return $this;
}
/**
* @return $this
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
*/
protected function _prepareColumns()
{
$this->addColumn(
'slider_id',
[
'header' => __('ID'),
'type' => 'number',
'index' => 'slider_id',
'header_css_class' => 'col-id',
'column_css_class' => 'col-id'
]
);
$this->addColumn(
'slider_identifier',
[
'header' => __('Identifier'),
'type' => 'text',
'index' => 'slider_identifier',
'header_css_class' => 'col-id',
'column_css_class' => 'col-id'
]
);
$this->addColumn(
'slider_title',
[
'header' => __('Title'),
'type' => 'text',
'index' => 'slider_title',
'header_css_class' => 'col-id',
'column_css_class' => 'col-id'
]
);
$this->addColumn(
'slider_status',
[
'header' => __('Status'),
'type' => 'options',
'index' => 'slider_status',
'options'=> [1=>__('Enable'), 2=>__('Disable')],
'header_css_class' => 'col-id',
'column_css_class' => 'col-id'
]
);
$block = $this->getLayout()->getBlock('grid.bottom.links');
if ($block) {
$this->setChild('grid.bottom.links', $block);
}
return parent::_prepareColumns();
}
/**
* @return $this
*/
//
/**
* @return string
*/
public function getGridUrl()
{
return $this->getUrl('*/*/grid', ['_current' => true]);
}
public function getRowUrl($row)
{
return $this->getUrl(
'*/*/edit',
['slider_id' => $row->getId()]
);
}
}
\ No newline at end of file
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\SlideBanner\Block\Adminhtml\Slide\Renderer;
/**
* Adminhtml customers wishlist grid item action renderer for few action controls in one cell
*
* @author Magento Core Team <core@magentocommerce.com>
*/
class Image extends \Magento\Backend\Block\Widget\Grid\Column\Renderer\Text
{
protected $_storeManager;
/**
* Renders column
*
* @param \Magento\Framework\DataObject $row
* @return string
*/
public function __construct(
\Magento\Backend\Block\Context $context,
\Magento\Store\Model\StoreManagerInterface $storeManager,
array $data = []
) {
$this->_storeManager = $storeManager;
parent::__construct($context, $data);
}
public function render(\Magento\Framework\DataObject $row)
{
$html = '';
$mediaUrl = $this->_storeManager->getStore()->getBaseUrl(\Magento\Framework\UrlInterface::URL_TYPE_MEDIA);
if($image = $row->getSlideImage())
$html = '<img height="50" src="' . $mediaUrl . $image . '" />';
return $html;
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Block\Adminhtml\Wysiwyg\Images;
/**
* Wysiwyg Images content block
*/
class Content extends \Magento\Backend\Block\Widget\Container
{
/**
* @var \Magento\Framework\Json\EncoderInterface
*/
protected $_jsonEncoder;
/**
* @param \Magento\Backend\Block\Widget\Context $context
* @param \Magento\Framework\Json\EncoderInterface $jsonEncoder
* @param array $data
*/
public function __construct(
\Magento\Backend\Block\Widget\Context $context,
\Magento\Framework\Json\EncoderInterface $jsonEncoder,
array $data = []
) {
$this->_jsonEncoder = $jsonEncoder;
parent::__construct($context, $data);
}
/**
* Block construction
*
* @return void
*/
protected function _construct()
{
parent::_construct();
$this->_headerText = __('Media Storage');
$this->buttonList->remove('back');
$this->buttonList->remove('edit');
$this->buttonList->add(
'new_folder',
['class' => 'save', 'label' => __('Create Folder...'), 'type' => 'button'],
0,
0,
'header'
);
$this->buttonList->add(
'delete_folder',
['class' => 'delete no-display', 'label' => __('Delete Folder'), 'type' => 'button'],
0,
0,
'header'
);
$this->buttonList->add(
'delete_files',
['class' => 'delete no-display', 'label' => __('Delete File'), 'type' => 'button'],
0,
0,
'header'
);
$this->buttonList->add(
'insert_files',
['class' => 'save no-display primary', 'label' => __('Insert File'), 'type' => 'button'],
0,
0,
'header'
);
}
/**
* Files action source URL
*
* @return string
*/
public function getContentsUrl()
{
return $this->getUrl('cms/*/contents', ['type' => $this->getRequest()->getParam('type')]);
}
/**
* Javascript setup object for filebrowser instance
*
* @return string
*/
public function getFilebrowserSetupObject()
{
$setupObject = new \Magento\Framework\DataObject();
$setupObject->setData(
[
'newFolderPrompt' => __('New Folder Name:'),
'deleteFolderConfirmationMessage' => __('Are you sure you want to delete this folder?'),
'deleteFileConfirmationMessage' => __('Are you sure you want to delete this file?'),
'targetElementId' => $this->getTargetElementId(),
'contentsUrl' => $this->getContentsUrl(),
'onInsertUrl' => $this->getOnInsertUrl(),
'newFolderUrl' => $this->getNewfolderUrl(),
'deleteFolderUrl' => $this->getDeletefolderUrl(),
'deleteFilesUrl' => $this->getDeleteFilesUrl(),
'headerText' => $this->getHeaderText(),
'showBreadcrumbs' => true,
]
);
return $this->_jsonEncoder->encode($setupObject);
}
/**
* New directory action target URL
*
* @return string
*/
public function getNewfolderUrl()
{
return $this->getUrl('cms/*/newFolder');
}
/**
* Delete directory action target URL
*
* @return string
*/
protected function getDeletefolderUrl()
{
return $this->getUrl('cms/*/deleteFolder');
}
/**
* Description goes here...
*
* @return string
*/
public function getDeleteFilesUrl()
{
return $this->getUrl('cms/*/deleteFiles');
}
/**
* New directory action target URL
*
* @return string
*/
public function getOnInsertUrl()
{
return $this->getUrl('cms/*/onInsert');
}
/**
* Target element ID getter
*
* @return string
*/
public function getTargetElementId()
{
return $this->getRequest()->getParam('target_element_id');
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Block\Adminhtml\Wysiwyg\Images\Content;
/**
* Directory contents block for Wysiwyg Images
*
* @author Magento Core Team <core@magentocommerce.com>
*/
class Files extends \Magento\Backend\Block\Template
{
/**
* Files collection object
*
* @var \Magento\Framework\Data\Collection\Filesystem
*/
protected $_filesCollection;
/**
* @var \Magento\Cms\Model\Wysiwyg\Images\Storage
*/
protected $_imageStorage;
/**
* @var \Magento\Cms\Helper\Wysiwyg\Images
*/
protected $_imageHelper;
/**
* @param \Magento\Backend\Block\Template\Context $context
* @param \Magento\Cms\Model\Wysiwyg\Images\Storage $imageStorage
* @param \Magento\Cms\Helper\Wysiwyg\Images $imageHelper
* @param array $data
*/
public function __construct(
\Magento\Backend\Block\Template\Context $context,
\Magento\Cms\Model\Wysiwyg\Images\Storage $imageStorage,
\Magento\Cms\Helper\Wysiwyg\Images $imageHelper,
array $data = []
) {
$this->_imageHelper = $imageHelper;
$this->_imageStorage = $imageStorage;
parent::__construct($context, $data);
}
/**
* Prepared Files collection for current directory
*
* @return \Magento\Framework\Data\Collection\Filesystem
*/
public function getFiles()
{
if (!$this->_filesCollection) {
$this->_filesCollection = $this->_imageStorage->getFilesCollection(
$this->_imageHelper->getCurrentPath(),
$this->_getMediaType()
);
}
return $this->_filesCollection;
}
/**
* Files collection count getter
*
* @return int
*/
public function getFilesCount()
{
return $this->getFiles()->count();
}
/**
* File idetifier getter
*
* @param \Magento\Framework\DataObject $file
* @return string
*/
public function getFileId(\Magento\Framework\DataObject $file)
{
return $file->getId();
}
/**
* File thumb URL getter
*
* @param \Magento\Framework\DataObject $file
* @return string
*/
public function getFileThumbUrl(\Magento\Framework\DataObject $file)
{
return $file->getThumbUrl();
}
/**
* File name URL getter
*
* @param \Magento\Framework\DataObject $file
* @return string
*/
public function getFileName(\Magento\Framework\DataObject $file)
{
return $file->getName();
}
/**
* Image file width getter
*
* @param \Magento\Framework\DataObject $file
* @return string
*/
public function getFileWidth(\Magento\Framework\DataObject $file)
{
return $file->getWidth();
}
/**
* Image file height getter
*
* @param \Magento\Framework\DataObject $file
* @return string
*/
public function getFileHeight(\Magento\Framework\DataObject $file)
{
return $file->getHeight();
}
/**
* File short name getter
*
* @param \Magento\Framework\DataObject $file
* @return string
*/
public function getFileShortName(\Magento\Framework\DataObject $file)
{
return $file->getShortName();
}
/**
* Get image width
*
* @return int
*/
public function getImagesWidth()
{
return $this->_imageStorage->getResizeWidth();
}
/**
* Get image height
*
* @return int
*/
public function getImagesHeight()
{
return $this->_imageStorage->getResizeHeight();
}
/**
* Return current media type based on request or data
* @return string
*/
protected function _getMediaType()
{
if ($this->hasData('media_type')) {
return $this->_getData('media_type');
}
return $this->getRequest()->getParam('type');
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Block\Adminhtml\Wysiwyg\Images\Content;
/**
* New directory block for Wysiwyg Images
*
* @author Magento Core Team <core@magentocommerce.com>
*/
class Newfolder extends \Magento\Backend\Block\Template
{
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Block\Adminhtml\Wysiwyg\Images\Content;
/**
* Uploader block for Wysiwyg Images
*
* @author Magento Core Team <core@magentocommerce.com>
*/
class Uploader extends \Magento\Backend\Block\Media\Uploader
{
/**
* @var \Magento\Cms\Model\Wysiwyg\Images\Storage
*/
protected $_imagesStorage;
/**
* @param \Magento\Backend\Block\Template\Context $context
* @param \Magento\Framework\File\Size $fileSize
* @param \Magento\Cms\Model\Wysiwyg\Images\Storage $imagesStorage
* @param array $data
*/
public function __construct(
\Magento\Backend\Block\Template\Context $context,
\Magento\Framework\File\Size $fileSize,
\Magento\Cms\Model\Wysiwyg\Images\Storage $imagesStorage,
array $data = []
) {
$this->_imagesStorage = $imagesStorage;
parent::__construct($context, $fileSize, $data);
}
/**
* @return void
*/
protected function _construct()
{
parent::_construct();
$type = $this->_getMediaType();
$allowed = $this->_imagesStorage->getAllowedExtensions($type);
$labels = [];
$files = [];
foreach ($allowed as $ext) {
$labels[] = '.' . $ext;
$files[] = '*.' . $ext;
}
$this->getConfig()->setUrl(
$this->_urlBuilder->addSessionParam()->getUrl('cms/*/upload', ['type' => $type])
)->setFileField(
'image'
)->setFilters(
['images' => ['label' => __('Images (%1)', implode(', ', $labels)), 'files' => $files]]
);
}
/**
* Return current media type based on request or data
*
* @return string
*/
protected function _getMediaType()
{
if ($this->hasData('media_type')) {
return $this->_getData('media_type');
}
return $this->getRequest()->getParam('type');
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Block\Adminhtml\Wysiwyg\Images;
/**
* Directory tree renderer for Cms Wysiwyg Images
*
* @author Magento Core Team <core@magentocommerce.com>
*/
class Tree extends \Magento\Backend\Block\Template
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry = null;
/**
* Cms wysiwyg images
*
* @var \Magento\Cms\Helper\Wysiwyg\Images
*/
protected $_cmsWysiwygImages = null;
/**
* @param \Magento\Backend\Block\Template\Context $context
* @param \Magento\Cms\Helper\Wysiwyg\Images $cmsWysiwygImages
* @param \Magento\Framework\Registry $registry
* @param array $data
*/
public function __construct(
\Magento\Backend\Block\Template\Context $context,
\Magento\Cms\Helper\Wysiwyg\Images $cmsWysiwygImages,
\Magento\Framework\Registry $registry,
array $data = []
) {
$this->_coreRegistry = $registry;
$this->_cmsWysiwygImages = $cmsWysiwygImages;
parent::__construct($context, $data);
}
/**
* Json tree builder
*
* @return string
*/
public function getTreeJson()
{
$storageRoot = $this->_cmsWysiwygImages->getStorageRoot();
$collection = $this->_coreRegistry->registry(
'storage'
)->getDirsCollection(
$this->_cmsWysiwygImages->getCurrentPath()
);
$jsonArray = [];
foreach ($collection as $item) {
$jsonArray[] = [
'text' => $this->_cmsWysiwygImages->getShortFilename($item->getBasename(), 20),
'id' => $this->_cmsWysiwygImages->convertPathToId($item->getFilename()),
'path' => substr($item->getFilename(), strlen($storageRoot)),
'cls' => 'folder',
];
}
return \Zend_Json::encode($jsonArray);
}
/**
* Json source URL
*
* @return string
*/
public function getTreeLoaderUrl()
{
return $this->getUrl('cms/*/treeJson');
}
/**
* Root node name of tree
*
* @return \Magento\Framework\Phrase
*/
public function getRootNodeName()
{
return __('Storage Root');
}
/**
* Return tree node full path based on current path
*
* @return string
*/
public function getTreeCurrentPath()
{
$treePath = ['root'];
if ($path = $this->_coreRegistry->registry('storage')->getSession()->getCurrentPath()) {
$path = str_replace($this->_cmsWysiwygImages->getStorageRoot(), '', $path);
$relative = [];
foreach (explode('/', $path) as $dirName) {
if ($dirName) {
$relative[] = $dirName;
$treePath[] = $this->_cmsWysiwygImages->idEncode(implode('/', $relative));
}
}
}
return $treePath;
}
/**
* Get tree widget options
*
* @return array
*/
public function getTreeWidgetOptions()
{
return [
"folderTree" => [
"rootName" => $this->getRootNodeName(),
"url" => $this->getTreeLoaderUrl(),
"currentPath" => array_reverse($this->getTreeCurrentPath()),
]
];
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
// @codingStandardsIgnoreFile
namespace Rokanthemes\SlideBanner\Block;
/**
* Cms block content block
*/
class Slider extends \Magento\Framework\View\Element\Template
{
protected $_filterProvider;
protected $_sliderFactory;
protected $_bannerFactory;
protected $_scopeConfig;
/**
* @var \Magento\Store\Model\StoreManagerInterface
*/
protected $_storeManager;
protected $_slider;
/**
* @param Context $context
* @param array $data
*/
public function __construct(
\Magento\Framework\View\Element\Template\Context $context,
\Rokanthemes\SlideBanner\Model\SliderFactory $sliderFactory,
\Rokanthemes\SlideBanner\Model\SlideFactory $slideFactory,
\Magento\Cms\Model\Template\FilterProvider $filterProvider,
array $data = []
) {
parent::__construct($context, $data);
$this->_sliderFactory = $sliderFactory;
$this->_bannerFactory = $slideFactory;
$this->_scopeConfig = $context->getScopeConfig();
$this->_storeManager = $context->getStoreManager();
$this->_filterProvider = $filterProvider;
}
/**
* Prepare Content HTML
*
* @return string
*/
protected function _beforeToHtml()
{
$sliderId = $this->getSliderId();
if ($sliderId && !$this->getTemplate()) {
$this->setTemplate("Rokanthemes_SlideBanner::slider.phtml");
}
return parent::_beforeToHtml();
}
/**
* Return identifiers for produced content
*
* @return array
*/
public function getImageElement($src)
{
$mediaUrl = $this->_storeManager->getStore()->getBaseUrl(\Magento\Framework\UrlInterface::URL_TYPE_MEDIA);
return '<img alt="' . $this->getSlider()->getSliderTitle() . '" src="'. $mediaUrl . $src . '" />';
}
public function getBannerCollection()
{
$slider = $this->getSlider();
$sliderId = $slider->getId();
if(!$sliderId || $slider->getSliderStatus() != '1')
return [];
$collection = $this->_bannerFactory->create()->getCollection();
$collection->addFieldToFilter('slider_id', $sliderId);
$collection->addFieldToFilter('slide_status', 1);
return $collection;
}
public function getSlider()
{
if(is_null($this->_slider)):
$sliderId = $this->getSliderId();
$this->_slider = $this->_sliderFactory->create();
$this->_slider->load($sliderId);
endif;
return $this->_slider;
}
public function getContentText($html)
{
$html = $this->_filterProvider->getPageFilter()->filter($html);
return $html;
}
}
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slide;
class Delete extends \Magento\Backend\App\Action
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry;
/**
* Result page factory
*
* @var \Magento\Framework\View\Result\PageFactory
*/
protected $_resultPageFactory;
/**
* News model factory
*
* @var \Tutorial\SimpleNews\Model\NewsFactory
*/
protected $_slideFactory;
/**
* @param Context $context
* @param Registry $coreRegistry
* @param PageFactory $resultPageFactory
* @param NewsFactory $newsFactory
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\Registry $coreRegistry,
\Magento\Framework\View\Result\PageFactory $resultPageFactory
) {
$this->_coreRegistry = $coreRegistry;
$this->_resultPageFactory = $resultPageFactory;
parent::__construct($context);
}
/**
* News access rights checking
*
* @return bool
*/
protected function _isAllowed()
{
return $this->_authorization->isAllowed('Rokanthemes_SlideBanner::slide');
}
protected function _initAction()
{
// load layout, set active menu and breadcrumbs
/** @var \Magento\Backend\Model\View\Result\Page $resultPage */
$resultPage = $this->_resultPageFactory->create();
$resultPage->setActiveMenu('Rokanthemes_SlideBanner::slide');
return $resultPage;
}
/**
* @return void
*/
public function execute()
{
/** @var \Magento\Backend\Model\View\Result\Redirect $resultRedirect */
$resultRedirect = $this->resultRedirectFactory->create();
// check if we know what should be deleted
$id = $this->getRequest()->getParam('slide_id');
if ($id) {
try {
// init model and delete
$model = $this->_objectManager->create('Rokanthemes\SlideBanner\Model\Slide');
$model->load($id);
$name = $model->getSlideTitle();
$model->delete();
// display success message
$this->messageManager->addSuccess(__('You deleted the Slide %1.', $name));
// go to grid
return $resultRedirect->setPath('*/*/');
} catch (\Exception $e) {
// display error message
$this->messageManager->addError($e->getMessage());
// go back to edit form
return $resultRedirect->setPath('*/*/edit', ['slide_id' => $id]);
}
}
// display error message
$this->messageManager->addError(__('We can\'t find a Slider to delete.'));
// go to grid
return $resultRedirect->setPath('*/*/');
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slide;
class Edit extends \Magento\Backend\App\Action
{
protected $_objectId = 'slide_id';
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry;
/**
* Result page factory
*
* @var \Magento\Framework\View\Result\PageFactory
*/
protected $_resultPageFactory;
/**
* News model factory
*
* @var \Tutorial\SimpleNews\Model\NewsFactory
*/
protected $_slideFactory;
/**
* @param Context $context
* @param Registry $coreRegistry
* @param PageFactory $resultPageFactory
* @param NewsFactory $newsFactory
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\Registry $coreRegistry,
\Magento\Framework\View\Result\PageFactory $resultPageFactory
) {
$this->_coreRegistry = $coreRegistry;
$this->_resultPageFactory = $resultPageFactory;
parent::__construct($context);
}
/**
* News access rights checking
*
* @return bool
*/
protected function _isAllowed()
{
return $this->_authorization->isAllowed('Rokanthemes_SlideBanner::slide');
}
protected function _initAction()
{
// load layout, set active menu and breadcrumbs
/** @var \Magento\Backend\Model\View\Result\Page $resultPage */
$resultPage = $this->_resultPageFactory->create();
// $resultPage->setActiveMenu('Webkul_Grid::grid')
// ->addBreadcrumb(__('Grid'), __('Grid'))
// ->addBreadcrumb(__('Manage Grid'), __('Manage Grid'));
return $resultPage;
}
/**
* @return void
*/
public function execute()
{
// 1. Get ID and create model
$id = $this->getRequest()->getParam('slide_id');
$model = $this->_objectManager->create('Rokanthemes\SlideBanner\Model\Slide');
// 2. Initial checking
if ($id) {
$model->load($id);
if (!$model->getId()) {
$this->messageManager->addError(__('This grid record no longer exists.'));
/** \Magento\Backend\Model\View\Result\Redirect $resultRedirect */
$resultRedirect = $this->resultRedirectFactory->create();
return $resultRedirect->setPath('*/*/');
}
}
// 3. Set entered data if was error when we do save
$data = $this->_objectManager->get('Magento\Backend\Model\Session')->getFormData(true);
if (!empty($data)) {
$model->setData($data);
}
// 4. Register model to use later in blocks
$this->_coreRegistry->register('slide_form_data', $model);
// 5. Build edit form
/** @var \Magento\Backend\Model\View\Result\Page $resultPage */
$resultPage = $this->_initAction();
$resultPage->addBreadcrumb(
$id ? __('Edit Post') : __('New Grid'),
$id ? __('Edit Post') : __('New Grid')
);
$resultPage->getConfig()->getTitle()->prepend(__('Grids'));
$resultPage->getConfig()->getTitle()
->prepend($model->getId() ? $model->getTitle() : __('New Grid'));
return $resultPage;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slide;
class Grid extends \Magento\Backend\App\Action
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry;
/**
* Result page factory
*
* @var \Magento\Framework\View\Result\PageFactory
*/
protected $_resultPageFactory;
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\Registry $coreRegistry,
\Magento\Framework\View\Result\PageFactory $resultPageFactory
) {
$this->_coreRegistry = $coreRegistry;
$this->_resultPageFactory = $resultPageFactory;
parent::__construct($context);
}
public function execute()
{
return $this->_resultPageFactory->create();
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slide;
use Magento\Backend\App\Action;
use Magento\Backend\App\Action\Context;
use Magento\Framework\Registry;
use Magento\Framework\View\Result\PageFactory;
class Index extends Action
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry;
/**
* Result page factory
*
* @var \Magento\Framework\View\Result\PageFactory
*/
protected $_resultPageFactory;
/**
* News model factory
*
* @var \Tutorial\SimpleNews\Model\NewsFactory
*/
protected $_slideFactory;
/**
* @param Context $context
* @param Registry $coreRegistry
* @param PageFactory $resultPageFactory
* @param NewsFactory $newsFactory
*/
public function __construct(
Context $context,
Registry $coreRegistry,
PageFactory $resultPageFactory
) {
parent::__construct($context);
$this->_coreRegistry = $coreRegistry;
$this->_resultPageFactory = $resultPageFactory;
}
/**
* News access rights checking
*
* @return bool
*/
protected function _isAllowed()
{
return $this->_authorization->isAllowed('Rokanthemes_SlideBanner::slide');
}
/**
* @return void
*/
public function execute()
{
if ($this->getRequest()->getQuery('ajax')) {
$this->_forward('grid');
return;
}
/** @var \Magento\Backend\Model\View\Result\Page $resultPage */
$resultPage = $this->_resultPageFactory->create();
//$resultPage->setActiveMenu('Tutorial_SimpleNews::main_menu');
//$resultPage->getConfig()->getTitle()->prepend(__('Simple News'));
return $resultPage;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slide;
class NewAction extends \Magento\Backend\App\Action
{
/**
* @var \Magento\Backend\Model\View\Result\Forward
*/
protected $resultForwardFactory;
/**
* @param \Magento\Backend\App\Action\Context $context
* @param \Magento\Backend\Model\View\Result\ForwardFactory $resultForwardFactory
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Backend\Model\View\Result\ForwardFactory $resultForwardFactory
) {
$this->resultForwardFactory = $resultForwardFactory;
parent::__construct($context);
}
/**
* Forward to edit
*
* @return \Magento\Backend\Model\View\Result\Forward
*/
public function execute()
{
/** @var \Magento\Backend\Model\View\Result\Forward $resultForward */
$resultForward = $this->resultForwardFactory->create();
return $resultForward->forward('edit');
}
/**
* {@inheritdoc}
*/
protected function _isAllowed()
{
return true;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slide;
use Magento\Framework\App\Filesystem\DirectoryList;
class Save extends \Magento\Backend\App\Action
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry;
/**
* Result page factory
*
* @var \Magento\Framework\View\Result\PageFactory
*/
protected $_resultPageFactory;
/**
* News model factory
*
* @var \Tutorial\SimpleNews\Model\NewsFactory
*/
protected $_slideFactory;
/**
* @param Context $context
* @param Registry $coreRegistry
* @param PageFactory $resultPageFactory
* @param NewsFactory $newsFactory
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\Registry $coreRegistry,
\Magento\Framework\View\Result\PageFactory $resultPageFactory
) {
$this->_coreRegistry = $coreRegistry;
$this->_resultPageFactory = $resultPageFactory;
parent::__construct($context);
}
/**
* News access rights checking
*
* @return bool
*/
protected function _isAllowed()
{
return $this->_authorization->isAllowed('Rokanthemes_SlideBanner::slide');
}
protected function _initAction()
{
// load layout, set active menu and breadcrumbs
/** @var \Magento\Backend\Model\View\Result\Page $resultPage */
$resultPage = $this->_resultPageFactory->create();
// $resultPage->setActiveMenu('Webkul_Grid::grid')
// ->addBreadcrumb(__('Grid'), __('Grid'))
// ->addBreadcrumb(__('Manage Grid'), __('Manage Grid'));
return $resultPage;
}
/**
* @return void
*/
public function execute()
{
if ($data = $this->getRequest()->getPostValue('slide')) {
$model = $this->_objectManager->create('Rokanthemes\SlideBanner\Model\Slide');
$storeViewId = $this->getRequest()->getParam("store");
if ($id = $this->getRequest()->getParam('slide_id')) {
$model->load($id);
//print_r($model->getData()); die;
}
/**
* Save image upload
*/
try {
$uploader = $this->_objectManager->create(
'Magento\MediaStorage\Model\File\Uploader',
['fileId' => 'slide_image']
);
$uploader->setAllowedExtensions(['jpg', 'jpeg', 'gif', 'png']);
/** @var \Magento\Framework\Image\Adapter\AdapterInterface $imageAdapter */
$imageAdapter = $this->_objectManager->get('Magento\Framework\Image\AdapterFactory')->create();
$uploader->addValidateCallback('banner_image', $imageAdapter, 'validateUploadFile');
$uploader->setAllowRenameFiles(true);
$uploader->setFilesDispersion(true);
/** @var \Magento\Framework\Filesystem\Directory\Read $mediaDirectory */
$mediaDirectory = $this->_objectManager->get('Magento\Framework\Filesystem')
->getDirectoryRead(DirectoryList::MEDIA);
$result = $uploader->save($mediaDirectory->getAbsolutePath(\Rokanthemes\SlideBanner\Model\Slide::BASE_MEDIA_PATH));
$data['slide_image'] = \Rokanthemes\SlideBanner\Model\Slide::BASE_MEDIA_PATH . $result['file'];
} catch (\Exception $e) {
if ($e->getCode() == 0) {
$this->messageManager->addError($e->getMessage());
}
if (isset($data['slide_image']) && isset($data['slide_image']['value'])) {
if (isset($data['slide_image']['delete'])) {
$data['slide_image'] = null;
$data['delete_image'] = true;
} else if (isset($data['slide_image']['value'])) {
$data['slide_image'] = $data['slide_image']['value'];
} else {
$data['slide_image'] = null;
}
}
}
$model->addData($data);
try {
$model->save();
$this->messageManager->addSuccess(__('The banner has been saved.'));
$this->_getSession()->setFormData(false);
if ($this->getRequest()->getParam('back') === 'edit') {
$this->_redirect(
'*/*/edit',
[
'slide_id' => $model->getId(),
'_current' => true,
'current_slide_id' => $this->getRequest()->getParam('current_slide_id'),
'saveandclose' => $this->getRequest()->getParam('saveandclose'),
]
);
return;
} elseif ($this->getRequest()->getParam('back') === "new") {
$this->_redirect('*/*/new', array('_current' => true));
return;
}
$this->_redirect('*/*/');
return;
} catch (\Magento\Framework\Model\Exception $e) {
$this->messageManager->addError($e->getMessage());
} catch (\RuntimeException $e) {
$this->messageManager->addError($e->getMessage());
} catch (\Exception $e) {
$this->messageManager->addError($e->getMessage());
$this->messageManager->addException($e, __('Something went wrong while saving the banner.'));
}
$this->_getSession()->setFormData($data);
$this->_redirect('*/*/edit', array('slide_id' => $this->getRequest()->getParam('slide_id')));
return;
}
$this->_redirect('*/*/');
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slider;
class Delete extends \Magento\Backend\App\Action
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry;
/**
* Result page factory
*
* @var \Magento\Framework\View\Result\PageFactory
*/
protected $_resultPageFactory;
/**
* News model factory
*
* @var \Tutorial\SimpleNews\Model\NewsFactory
*/
protected $_slideFactory;
/**
* @param Context $context
* @param Registry $coreRegistry
* @param PageFactory $resultPageFactory
* @param NewsFactory $newsFactory
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\Registry $coreRegistry,
\Magento\Framework\View\Result\PageFactory $resultPageFactory
) {
$this->_coreRegistry = $coreRegistry;
$this->_resultPageFactory = $resultPageFactory;
parent::__construct($context);
}
/**
* News access rights checking
*
* @return bool
*/
protected function _isAllowed()
{
return $this->_authorization->isAllowed('Rokanthemes_SlideBanner::slider');
}
protected function _initAction()
{
// load layout, set active menu and breadcrumbs
/** @var \Magento\Backend\Model\View\Result\Page $resultPage */
$resultPage = $this->_resultPageFactory->create();
$resultPage->setActiveMenu('Rokanthemes_SlideBanner::slider');
return $resultPage;
}
/**
* @return void
*/
public function execute()
{
/** @var \Magento\Backend\Model\View\Result\Redirect $resultRedirect */
$resultRedirect = $this->resultRedirectFactory->create();
// check if we know what should be deleted
$id = $this->getRequest()->getParam('slider_id');
if ($id) {
try {
// init model and delete
$model = $this->_objectManager->create('Rokanthemes\SlideBanner\Model\Slider');
$model->load($id);
$name = $model->getSliderTitle();
$model->delete();
// display success message
$this->messageManager->addSuccess(__('You deleted the Slider %1.', $name));
// go to grid
return $resultRedirect->setPath('*/*/');
} catch (\Exception $e) {
// display error message
$this->messageManager->addError($e->getMessage());
// go back to edit form
return $resultRedirect->setPath('*/*/edit', ['slider_id' => $id]);
}
}
// display error message
$this->messageManager->addError(__('We can\'t find a Slider to delete.'));
// go to grid
return $resultRedirect->setPath('*/*/');
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slider;
class Edit extends \Magento\Backend\App\Action
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry;
/**
* Result page factory
*
* @var \Magento\Framework\View\Result\PageFactory
*/
protected $_resultPageFactory;
/**
* News model factory
*
* @var \Tutorial\SimpleNews\Model\NewsFactory
*/
protected $_slideFactory;
/**
* @param Context $context
* @param Registry $coreRegistry
* @param PageFactory $resultPageFactory
* @param NewsFactory $newsFactory
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\Registry $coreRegistry,
\Magento\Framework\View\Result\PageFactory $resultPageFactory
) {
$this->_coreRegistry = $coreRegistry;
$this->_resultPageFactory = $resultPageFactory;
parent::__construct($context);
}
/**
* News access rights checking
*
* @return bool
*/
protected function _isAllowed()
{
return $this->_authorization->isAllowed('Rokanthemes_SlideBanner::slider');
}
protected function _initAction()
{
// load layout, set active menu and breadcrumbs
/** @var \Magento\Backend\Model\View\Result\Page $resultPage */
$resultPage = $this->_resultPageFactory->create();
$resultPage->setActiveMenu('Rokanthemes_SlideBanner::slider');
return $resultPage;
}
/**
* @return void
*/
public function execute()
{
// 1. Get ID and create model
$id = $this->getRequest()->getParam('slider_id');
$model = $this->_objectManager->create('Rokanthemes\SlideBanner\Model\Slider');
// 2. Initial checking
if ($id) {
$model->load($id);
if (!$model->getId()) {
$this->messageManager->addError(__('This grid record no longer exists.'));
/** \Magento\Backend\Model\View\Result\Redirect $resultRedirect */
$resultRedirect = $this->resultRedirectFactory->create();
return $resultRedirect->setPath('*/*/');
}
}
// 3. Set entered data if was error when we do save
$data = $this->_objectManager->get('Magento\Backend\Model\Session')->getFormData(true);
if (!empty($data)) {
$model->setData($data);
}
// 4. Register model to use later in blocks
$this->_coreRegistry->register('slider_form_data', $model);
// 5. Build edit form
/** @var \Magento\Backend\Model\View\Result\Page $resultPage */
$resultPage = $this->_initAction();
$resultPage->addBreadcrumb(
$id ? __('Edit Post') : __('New Slider'),
$id ? __('Edit Post') : __('New Slider')
);
$resultPage->getConfig()->getTitle()->prepend(__('Sliders'));
$resultPage->getConfig()->getTitle()
->prepend($model->getId() ? $model->getTitle() : __('New Slider'));
return $resultPage;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slider;
class Grid extends \Magento\Backend\App\Action
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry;
/**
* Result page factory
*
* @var \Magento\Framework\View\Result\PageFactory
*/
protected $_resultPageFactory;
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\Registry $coreRegistry,
\Magento\Framework\View\Result\PageFactory $resultPageFactory
) {
$this->_coreRegistry = $coreRegistry;
$this->_resultPageFactory = $resultPageFactory;
parent::__construct($context);
}
public function execute()
{
return $this->_resultPageFactory->create();
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slider;
use Magento\Backend\App\Action;
use Magento\Backend\App\Action\Context;
use Magento\Framework\Registry;
use Magento\Framework\View\Result\PageFactory;
class Index extends Action
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry;
/**
* Result page factory
*
* @var \Magento\Framework\View\Result\PageFactory
*/
protected $_resultPageFactory;
/**
* News model factory
*
* @var \Tutorial\SimpleNews\Model\NewsFactory
*/
protected $_slideFactory;
/**
* @param Context $context
* @param Registry $coreRegistry
* @param PageFactory $resultPageFactory
* @param NewsFactory $newsFactory
*/
public function __construct(
Context $context,
Registry $coreRegistry,
PageFactory $resultPageFactory
) {
parent::__construct($context);
$this->_coreRegistry = $coreRegistry;
$this->_resultPageFactory = $resultPageFactory;
}
/**
* News access rights checking
*
* @return bool
*/
protected function _isAllowed()
{
return $this->_authorization->isAllowed('Rokanthemes_SlideBanner::slider');
}
/**
* @return void
*/
public function execute()
{
if ($this->getRequest()->getQuery('ajax')) {
$this->_forward('grid');
return;
}
/** @var \Magento\Backend\Model\View\Result\Page $resultPage */
$resultPage = $this->_resultPageFactory->create();
$resultPage->setActiveMenu('Rokanthemes_SlideBanner::slider');
$resultPage->getConfig()->getTitle()->prepend(__('Manage Slider'));
return $resultPage;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slider;
class NewAction extends \Magento\Backend\App\Action
{
/**
* @var \Magento\Backend\Model\View\Result\Forward
*/
protected $resultForwardFactory;
/**
* @param \Magento\Backend\App\Action\Context $context
* @param \Magento\Backend\Model\View\Result\ForwardFactory $resultForwardFactory
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Backend\Model\View\Result\ForwardFactory $resultForwardFactory
) {
$this->resultForwardFactory = $resultForwardFactory;
parent::__construct($context);
}
/**
* Forward to edit
*
* @return \Magento\Backend\Model\View\Result\Forward
*/
public function execute()
{
/** @var \Magento\Backend\Model\View\Result\Forward $resultForward */
$resultForward = $this->resultForwardFactory->create();
return $resultForward->forward('edit');
}
/**
* {@inheritdoc}
*/
protected function _isAllowed()
{
return true;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slider;
use Magento\Framework\App\Filesystem\DirectoryList;
class Save extends \Magento\Backend\App\Action
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry;
/**
* Result page factory
*
* @var \Magento\Framework\View\Result\PageFactory
*/
protected $_resultPageFactory;
/**
* News model factory
*
* @var \Tutorial\SimpleNews\Model\NewsFactory
*/
protected $_slideFactory;
/**
* @param Context $context
* @param Registry $coreRegistry
* @param PageFactory $resultPageFactory
* @param NewsFactory $newsFactory
*/
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\Registry $coreRegistry,
\Magento\Framework\View\Result\PageFactory $resultPageFactory
) {
$this->_coreRegistry = $coreRegistry;
$this->_resultPageFactory = $resultPageFactory;
parent::__construct($context);
}
/**
* News access rights checking
*
* @return bool
*/
protected function _isAllowed()
{
return $this->_authorization->isAllowed('Rokanthemes_SlideBanner::slider');
}
/**
* @return void
*/
public function execute()
{
if ($data = $this->getRequest()->getPostValue('slider')) {
$model = $this->_objectManager->create('Rokanthemes\SlideBanner\Model\Slider');
$storeViewId = $this->getRequest()->getParam("store");
if ($id = $this->getRequest()->getParam('slider_id')) {
$model->load($id);
}
if(isset($data['slider_setting']) && is_array($data['slider_setting']))
$data['slider_setting'] = json_encode($data['slider_setting']);
$model->addData($data);
try {
$model->save();
$this->messageManager->addSuccess(__('The Slider has been saved.'));
$this->_getSession()->setFormData(false);
if ($this->getRequest()->getParam('back') === 'edit') {
$this->_redirect(
'*/*/edit',
[
'slider_id' => $model->getId(),
'_current' => true,
'current_slider_id' => $this->getRequest()->getParam('current_slider_id'),
'saveandclose' => $this->getRequest()->getParam('saveandclose'),
]
);
return;
} elseif ($this->getRequest()->getParam('back') === "new") {
$this->_redirect('*/*/new', array('_current' => true));
return;
}
$this->_redirect('*/*/');
return;
} catch (\Magento\Framework\Model\Exception $e) {
$this->messageManager->addError($e->getMessage());
} catch (\RuntimeException $e) {
$this->messageManager->addError($e->getMessage());
} catch (\Exception $e) {
$this->messageManager->addError($e->getMessage());
$this->messageManager->addException($e, __('Something went wrong while saving the Slider.'));
}
$this->_getSession()->setFormData($data);
$this->_redirect('*/*/edit', array('slider_id' => $this->getRequest()->getParam('slider_id')));
return;
}
$this->_redirect('*/*/');
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Controller\Adminhtml\Slider;
class Slidegrid extends \Magento\Backend\App\Action
{
/**
* Core registry
*
* @var \Magento\Framework\Registry
*/
protected $_coreRegistry;
/**
* Result page factory
*
* @var \Magento\Framework\View\Result\PageFactory
*/
protected $_resultPageFactory;
public function __construct(
\Magento\Backend\App\Action\Context $context,
\Magento\Framework\Registry $coreRegistry,
\Magento\Framework\View\Result\PageFactory $resultPageFactory
) {
$this->_coreRegistry = $coreRegistry;
$this->_resultPageFactory = $resultPageFactory;
parent::__construct($context);
}
public function execute()
{
return $this->_resultPageFactory->create();
}
}
\ No newline at end of file
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\Config\Source;
use Magento\Cms\Model\ResourceModel\Page\CollectionFactory;
/**
* Class Page
*/
class Page implements \Magento\Framework\Option\ArrayInterface
{
/**
* @var array
*/
protected $options;
/**
* @var CollectionFactory
*/
protected $collectionFactory;
/**
* @param CollectionFactory $collectionFactory
*/
public function __construct(
CollectionFactory $collectionFactory
) {
$this->collectionFactory = $collectionFactory;
}
/**
* To option array
*
* @return array
*/
public function toOptionArray()
{
if (!$this->options) {
$this->options = $this->collectionFactory->create()->toOptionIdArray();
}
return $this->options;
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\Config\Source\Wysiwyg;
/**
* Configuration source model for Wysiwyg toggling
*/
class Enabled implements \Magento\Framework\Option\ArrayInterface
{
/**
* {@inheritdoc}
*/
public function toOptionArray()
{
return [
['value' => \Magento\Cms\Model\Wysiwyg\Config::WYSIWYG_ENABLED, 'label' => __('Enabled by Default')],
['value' => \Magento\Cms\Model\Wysiwyg\Config::WYSIWYG_HIDDEN, 'label' => __('Disabled by Default')],
['value' => \Magento\Cms\Model\Wysiwyg\Config::WYSIWYG_DISABLED, 'label' => __('Disabled Completely')]
];
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\Page\Source;
/**
* Custom layout source
*/
class CustomLayout extends PageLayout
{
/**
* {@inheritdoc}
*/
public function toOptionArray()
{
return array_merge([['label' => 'Default', 'value' => '']], parent::toOptionArray());
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\Page\Source;
use Magento\Framework\Data\OptionSourceInterface;
/**
* Class IsActive
*/
class IsActive implements OptionSourceInterface
{
/**
* @var \Magento\Cms\Model\Page
*/
protected $cmsPage;
/**
* Constructor
*
* @param \Magento\Cms\Model\Page $cmsPage
*/
public function __construct(\Magento\Cms\Model\Page $cmsPage)
{
$this->cmsPage = $cmsPage;
}
/**
* Get options
*
* @return array
*/
public function toOptionArray()
{
$availableOptions = $this->cmsPage->getAvailableStatuses();
$options = [];
foreach ($availableOptions as $key => $value) {
$options[] = [
'label' => $value,
'value' => $key,
];
}
return $options;
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\Page\Source;
/**
* Is active filter source
*/
class IsActiveFilter extends IsActive
{
/**
* {@inheritdoc}
*/
public function toOptionArray()
{
return array_merge([['label' => '', 'value' => '']], parent::toOptionArray());
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\Page\Source;
use Magento\Framework\Data\OptionSourceInterface;
use Magento\Framework\View\Model\PageLayout\Config\BuilderInterface;
/**
* Class PageLayout
*/
class PageLayout implements OptionSourceInterface
{
/**
* @var \Magento\Framework\View\Model\PageLayout\Config\BuilderInterface
*/
protected $pageLayoutBuilder;
/**
* @var array
*/
protected $options;
/**
* Constructor
*
* @param BuilderInterface $pageLayoutBuilder
*/
public function __construct(BuilderInterface $pageLayoutBuilder)
{
$this->pageLayoutBuilder = $pageLayoutBuilder;
}
/**
* Get options
*
* @return array
*/
public function toOptionArray()
{
if ($this->options !== null) {
return $this->options;
}
$configOptions = $this->pageLayoutBuilder->getPageLayoutsConfig()->getOptions();
$options = [];
foreach ($configOptions as $key => $value) {
$options[] = [
'label' => $value,
'value' => $key,
];
}
$this->options = $options;
return $this->options;
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\Page\Source;
/**
* Page layout filter source
*/
class PageLayoutFilter extends PageLayout
{
/**
* {@inheritdoc}
*/
public function toOptionArray()
{
return array_merge([['label' => '', 'value' => '']], parent::toOptionArray());
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\Page\Source;
use Magento\Framework\Data\OptionSourceInterface;
use Magento\Framework\View\Design\Theme\Label\ListInterface;
/**
* Class Theme
*/
class Theme implements OptionSourceInterface
{
/**
* @var \Magento\Framework\View\Design\Theme\Label\ListInterface
*/
protected $themeList;
/**
* Constructor
*
* @param ListInterface $themeList
*/
public function __construct(ListInterface $themeList)
{
$this->themeList = $themeList;
}
/**
* Get options
*
* @return array
*/
public function toOptionArray()
{
$options[] = ['label' => 'Default', 'value' => ''];
return array_merge($options, $this->themeList->getLabels());
}
}
<?php
namespace Rokanthemes\SlideBanner\Model\Resource;
class Slide extends \Magento\Framework\Model\ResourceModel\Db\AbstractDb
{
/**
* Define main table
*/
protected function _construct()
{
$this->_init('rokanthemes_slide', 'slide_id');
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Model\Resource\Slide;
use Magento\Framework\DB\Select;
class Collection extends \Magento\Framework\Model\ResourceModel\Db\Collection\AbstractCollection
{
/**
* @var string
*/
protected $_idFieldName = 'slide_id';
/**
* Define model & resource model
*/
protected function _construct()
{
$this->_init(
'Rokanthemes\SlideBanner\Model\Slide','Rokanthemes\SlideBanner\Model\Resource\Slide'
);
}
public function joinSlider()
{
$this->getSelect()->joinLeft(['slider'=>$this->getTable('rokanthemes_slider')], "main_table.slider_id = slider.slider_id", ['slider_title']);
return $this;
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Model\Resource;
class Slider extends \Magento\Framework\Model\ResourceModel\Db\AbstractDb
{
/**
* Define main table
*/
protected function _construct()
{
$this->_init('rokanthemes_slider', 'slider_id');
}
public function load(\Magento\Framework\Model\AbstractModel $object, $value, $field = null)
{
if (!is_numeric($value) && $field === null) {
$field = 'slider_identifier';
}
return parent::load($object, $value, $field);
}
}
\ No newline at end of file
<?php
namespace Rokanthemes\SlideBanner\Model\Resource\Slider;
use Magento\Framework\DB\Select;
class Collection extends \Magento\Framework\Model\ResourceModel\Db\Collection\AbstractCollection
{
/**
* @var string
*/
protected $_idFieldName = 'slider_id';
/**
* Define model & resource model
*/
protected function _construct()
{
$this->_init(
'Rokanthemes\SlideBanner\Model\Slider','Rokanthemes\SlideBanner\Model\Resource\Slider'
);
}
}
\ No newline at end of file
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\SlideBanner\Model\ResourceModel;
/**
* Abstract collection of CMS pages and blocks
*/
abstract class AbstractCollection extends \Magento\Framework\Model\ResourceModel\Db\Collection\AbstractCollection
{
/**
* Store manager
*
* @var \Magento\Store\Model\StoreManagerInterface
*/
protected $storeManager;
/**
* @param \Magento\Framework\Data\Collection\EntityFactoryInterface $entityFactory
* @param \Psr\Log\LoggerInterface $logger
* @param \Magento\Framework\Data\Collection\Db\FetchStrategyInterface $fetchStrategy
* @param \Magento\Framework\Event\ManagerInterface $eventManager
* @param \Magento\Store\Model\StoreManagerInterface $storeManager
* @param \Magento\Framework\DB\Adapter\AdapterInterface|null $connection
* @param \Magento\Framework\Model\ResourceModel\Db\AbstractDb|null $resource
*/
public function __construct(
\Magento\Framework\Data\Collection\EntityFactoryInterface $entityFactory,
\Psr\Log\LoggerInterface $logger,
\Magento\Framework\Data\Collection\Db\FetchStrategyInterface $fetchStrategy,
\Magento\Framework\Event\ManagerInterface $eventManager,
\Magento\Store\Model\StoreManagerInterface $storeManager,
\Magento\Framework\DB\Adapter\AdapterInterface $connection = null,
\Magento\Framework\Model\ResourceModel\Db\AbstractDb $resource = null
) {
parent::__construct($entityFactory, $logger, $fetchStrategy, $eventManager, $connection, $resource);
$this->storeManager = $storeManager;
}
/**
* Add filter by store
*
* @param int|array|\Magento\Store\Model\Store $store
* @param bool $withAdmin
* @return $this
*/
abstract public function addStoreFilter($store, $withAdmin = true);
/**
* Perform adding filter by store
*
* @param int|array|\Magento\Store\Model\Store $store
* @param bool $withAdmin
* @return void
*/
protected function performAddStoreFilter($store, $withAdmin = true)
{
if ($store instanceof \Magento\Store\Model\Store) {
$store = [$store->getId()];
}
if (!is_array($store)) {
$store = [$store];
}
if ($withAdmin) {
$store[] = \Magento\Store\Model\Store::DEFAULT_STORE_ID;
}
// $this->addFilter('store', ['in' => $store], 'public');
}
/**
* Join store relation table if there is store filter
*
* @param string $tableName
* @param string $columnName
* @return void
*/
/**
* Get SQL for get record count
*
* Extra GROUP BY strip added.
*
* @return \Magento\Framework\DB\Select
*/
public function getSelectCountSql()
{
$countSelect = parent::getSelectCountSql();
$countSelect->reset(\Magento\Framework\DB\Select::GROUP);
return $countSelect;
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\ResourceModel;
/**
* CMS block model
*/
class Block extends \Magento\Framework\Model\ResourceModel\Db\AbstractDb
{
/**
* Store manager
*
* @var \Magento\Store\Model\StoreManagerInterface
*/
protected $_storeManager;
/**
* Construct
*
* @param \Magento\Framework\Model\ResourceModel\Db\Context $context
* @param \Magento\Store\Model\StoreManagerInterface $storeManager
* @param string $connectionName
*/
public function __construct(
\Magento\Framework\Model\ResourceModel\Db\Context $context,
\Magento\Store\Model\StoreManagerInterface $storeManager,
$connectionName = null
) {
parent::__construct($context, $connectionName);
$this->_storeManager = $storeManager;
}
/**
* Initialize resource model
*
* @return void
*/
protected function _construct()
{
$this->_init('cms_block', 'block_id');
}
/**
* Process block data before deleting
*
* @param \Magento\Framework\Model\AbstractModel $object
* @return \Magento\Cms\Model\ResourceModel\Page
*/
protected function _beforeDelete(\Magento\Framework\Model\AbstractModel $object)
{
$condition = ['block_id = ?' => (int)$object->getId()];
$this->getConnection()->delete($this->getTable('cms_block_store'), $condition);
return parent::_beforeDelete($object);
}
/**
* Perform operations before object save
*
* @param \Magento\Framework\Model\AbstractModel $object
* @return $this
* @throws \Magento\Framework\Exception\LocalizedException
*/
protected function _beforeSave(\Magento\Framework\Model\AbstractModel $object)
{
if (!$this->getIsUniqueBlockToStores($object)) {
throw new \Magento\Framework\Exception\LocalizedException(
__('A block identifier with the same properties already exists in the selected store.')
);
}
return $this;
}
/**
* Perform operations after object save
*
* @param \Magento\Framework\Model\AbstractModel $object
* @return $this
*/
protected function _afterSave(\Magento\Framework\Model\AbstractModel $object)
{
$oldStores = $this->lookupStoreIds($object->getId());
$newStores = (array)$object->getStores();
$table = $this->getTable('cms_block_store');
$insert = array_diff($newStores, $oldStores);
$delete = array_diff($oldStores, $newStores);
if ($delete) {
$where = ['block_id = ?' => (int)$object->getId(), 'store_id IN (?)' => $delete];
$this->getConnection()->delete($table, $where);
}
if ($insert) {
$data = [];
foreach ($insert as $storeId) {
$data[] = ['block_id' => (int)$object->getId(), 'store_id' => (int)$storeId];
}
$this->getConnection()->insertMultiple($table, $data);
}
return parent::_afterSave($object);
}
/**
* Load an object using 'identifier' field if there's no field specified and value is not numeric
*
* @param \Magento\Framework\Model\AbstractModel $object
* @param mixed $value
* @param string $field
* @return $this
*/
public function load(\Magento\Framework\Model\AbstractModel $object, $value, $field = null)
{
if (!is_numeric($value) && $field === null) {
$field = 'identifier';
}
return parent::load($object, $value, $field);
}
/**
* Perform operations after object load
*
* @param \Magento\Framework\Model\AbstractModel $object
* @return $this
*/
protected function _afterLoad(\Magento\Framework\Model\AbstractModel $object)
{
if ($object->getId()) {
$stores = $this->lookupStoreIds($object->getId());
$object->setData('store_id', $stores);
$object->setData('stores', $stores);
}
return parent::_afterLoad($object);
}
/**
* Retrieve select object for load object data
*
* @param string $field
* @param mixed $value
* @param \Magento\Cms\Model\Block $object
* @return \Magento\Framework\DB\Select
*/
protected function _getLoadSelect($field, $value, $object)
{
$select = parent::_getLoadSelect($field, $value, $object);
if ($object->getStoreId()) {
$stores = [(int)$object->getStoreId(), \Magento\Store\Model\Store::DEFAULT_STORE_ID];
$select->join(
['cbs' => $this->getTable('cms_block_store')],
$this->getMainTable() . '.block_id = cbs.block_id',
['store_id']
)->where(
'is_active = ?',
1
)->where(
'cbs.store_id in (?)',
$stores
)->order(
'store_id DESC'
)->limit(
1
);
}
return $select;
}
/**
* Check for unique of identifier of block to selected store(s).
*
* @param \Magento\Framework\Model\AbstractModel $object
* @return bool
* @SuppressWarnings(PHPMD.BooleanGetMethodName)
*/
public function getIsUniqueBlockToStores(\Magento\Framework\Model\AbstractModel $object)
{
if ($this->_storeManager->hasSingleStore()) {
$stores = [\Magento\Store\Model\Store::DEFAULT_STORE_ID];
} else {
$stores = (array)$object->getData('stores');
}
$select = $this->getConnection()->select()->from(
['cb' => $this->getMainTable()]
)->join(
['cbs' => $this->getTable('cms_block_store')],
'cb.block_id = cbs.block_id',
[]
)->where(
'cb.identifier = ?',
$object->getData('identifier')
)->where(
'cbs.store_id IN (?)',
$stores
);
if ($object->getId()) {
$select->where('cb.block_id <> ?', $object->getId());
}
if ($this->getConnection()->fetchRow($select)) {
return false;
}
return true;
}
/**
* Get store ids to which specified item is assigned
*
* @param int $id
* @return array
*/
public function lookupStoreIds($id)
{
$connection = $this->getConnection();
$select = $connection->select()->from(
$this->getTable('cms_block_store'),
'store_id'
)->where(
'block_id = :block_id'
);
$binds = [':block_id' => (int)$id];
return $connection->fetchCol($select, $binds);
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\ResourceModel\Block;
use \Magento\Cms\Model\ResourceModel\AbstractCollection;
/**
* CMS Block Collection
*/
class Collection extends AbstractCollection
{
/**
* @var string
*/
protected $_idFieldName = 'block_id';
/**
* Perform operations after collection load
*
* @return $this
*/
protected function _afterLoad()
{
$this->performAfterLoad('cms_block_store', 'block_id');
return parent::_afterLoad();
}
/**
* Define resource model
*
* @return void
*/
protected function _construct()
{
$this->_init('Magento\Cms\Model\Block', 'Magento\Cms\Model\ResourceModel\Block');
$this->_map['fields']['store'] = 'store_table.store_id';
}
/**
* Returns pairs block_id - title
*
* @return array
*/
public function toOptionArray()
{
return $this->_toOptionArray('block_id', 'title');
}
/**
* Add filter by store
*
* @param int|array|\Magento\Store\Model\Store $store
* @param bool $withAdmin
* @return $this
*/
public function addStoreFilter($store, $withAdmin = true)
{
$this->performAddStoreFilter($store, $withAdmin);
return $this;
}
/**
* Join store relation table if there is store filter
*
* @return void
*/
protected function _renderFiltersBefore()
{
$this->joinStoreRelationTable('cms_block_store', 'block_id');
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\ResourceModel\Block\Grid;
use Magento\Framework\Api\Search\SearchResultInterface;
use Magento\Framework\Search\AggregationInterface;
use Magento\Cms\Model\ResourceModel\Block\Collection as BlockCollection;
/**
* Collection for displaying grid of cms blocks
*/
class Collection extends BlockCollection implements SearchResultInterface
{
/**
* @var AggregationInterface
*/
protected $aggregations;
/**
* @param \Magento\Framework\Data\Collection\EntityFactoryInterface $entityFactory
* @param \Psr\Log\LoggerInterface $logger
* @param \Magento\Framework\Data\Collection\Db\FetchStrategyInterface $fetchStrategy
* @param \Magento\Framework\Event\ManagerInterface $eventManager
* @param \Magento\Store\Model\StoreManagerInterface $storeManager
* @param string $mainTable
* @param string $eventPrefix
* @param string $eventObject
* @param string $resourceModel
* @param string $model
* @param string|null $connection
* @param \Magento\Framework\Model\ResourceModel\Db\AbstractDb $resource
*
* @SuppressWarnings(PHPMD.ExcessiveParameterList)
*/
public function __construct(
\Magento\Framework\Data\Collection\EntityFactoryInterface $entityFactory,
\Psr\Log\LoggerInterface $logger,
\Magento\Framework\Data\Collection\Db\FetchStrategyInterface $fetchStrategy,
\Magento\Framework\Event\ManagerInterface $eventManager,
\Magento\Store\Model\StoreManagerInterface $storeManager,
$mainTable,
$eventPrefix,
$eventObject,
$resourceModel,
$model = 'Magento\Framework\View\Element\UiComponent\DataProvider\Document',
$connection = null,
\Magento\Framework\Model\ResourceModel\Db\AbstractDb $resource = null
) {
parent::__construct(
$entityFactory,
$logger,
$fetchStrategy,
$eventManager,
$storeManager,
$connection,
$resource
);
$this->_eventPrefix = $eventPrefix;
$this->_eventObject = $eventObject;
$this->_init($model, $resourceModel);
$this->setMainTable($mainTable);
}
/**
* @return AggregationInterface
*/
public function getAggregations()
{
return $this->aggregations;
}
/**
* @param AggregationInterface $aggregations
* @return $this
*/
public function setAggregations($aggregations)
{
$this->aggregations = $aggregations;
}
/**
* Retrieve all ids for collection
* Backward compatibility with EAV collection
*
* @param int $limit
* @param int $offset
* @return array
*/
public function getAllIds($limit = null, $offset = null)
{
return $this->getConnection()->fetchCol($this->_getAllIdsSelect($limit, $offset), $this->_bindParams);
}
/**
* Get search criteria.
*
* @return \Magento\Framework\Api\SearchCriteriaInterface|null
*/
public function getSearchCriteria()
{
return null;
}
/**
* Set search criteria.
*
* @param \Magento\Framework\Api\SearchCriteriaInterface $searchCriteria
* @return $this
* @SuppressWarnings(PHPMD.UnusedFormalParameter)
*/
public function setSearchCriteria(\Magento\Framework\Api\SearchCriteriaInterface $searchCriteria = null)
{
return $this;
}
/**
* Get total count.
*
* @return int
*/
public function getTotalCount()
{
return $this->getSize();
}
/**
* Set total count.
*
* @param int $totalCount
* @return $this
* @SuppressWarnings(PHPMD.UnusedFormalParameter)
*/
public function setTotalCount($totalCount)
{
return $this;
}
/**
* Set items list.
*
* @param \Magento\Framework\Api\ExtensibleDataInterface[] $items
* @return $this
* @SuppressWarnings(PHPMD.UnusedFormalParameter)
*/
public function setItems(array $items = null)
{
return $this;
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
// @codingStandardsIgnoreFile
namespace Rokanthemes\SlideBanner\Model\ResourceModel;
/**
* Cms page mysql resource
*/
class Slider extends \Magento\Framework\Model\ResourceModel\Db\AbstractDb
{
/**
* Store model
*
* @var null|\Magento\Store\Model\Store
*/
protected $_store = null;
/**
* Store manager
*
* @var \Magento\Store\Model\StoreManagerInterface
*/
protected $_storeManager;
/**
* @var \Magento\Framework\Stdlib\DateTime
*/
protected $dateTime;
/**
* Construct
*
* @param \Magento\Framework\Model\ResourceModel\Db\Context $context
* @param \Magento\Store\Model\StoreManagerInterface $storeManager
* @param \Magento\Framework\Stdlib\DateTime $dateTime
* @param string $connectionName
*/
public function __construct(
\Magento\Framework\Model\ResourceModel\Db\Context $context,
\Magento\Store\Model\StoreManagerInterface $storeManager,
\Magento\Framework\Stdlib\DateTime $dateTime,
$connectionName = null
) {
parent::__construct($context, $connectionName);
$this->_storeManager = $storeManager;
$this->dateTime = $dateTime;
}
/**
* Initialize resource model
*
* @return void
*/
protected function _construct()
{
$this->_init('rokanthemes_slider', 'slider_id');
}
/**
* Process page data before deleting
*
* @param \Magento\Framework\Model\AbstractModel $object
* @return $this
*/
protected function _beforeDelete(\Magento\Framework\Model\AbstractModel $object)
{
$condition = ['slider_id = ?' => (int)$object->getId()];
//$this->getConnection()->delete($this->getTable('cms_page_store'), $condition);
return parent::_beforeDelete($object);
}
/**
* Process page data before saving
*
* @param \Magento\Framework\Model\AbstractModel $object
* @return $this
* @throws \Magento\Framework\Exception\LocalizedException
*/
protected function _beforeSave(\Magento\Framework\Model\AbstractModel $object)
{
/*
* For two attributes which represent timestamp data in DB
* we should make converting such as:
* If they are empty we need to convert them into DB
* type NULL so in DB they will be empty and not some default value
*/
if (!$this->isValidPageIdentifier($object)) {
throw new \Magento\Framework\Exception\LocalizedException(
__('The page URL key contains capital letters or disallowed symbols.')
);
}
if ($this->isNumericPageIdentifier($object)) {
throw new \Magento\Framework\Exception\LocalizedException(
__('The page URL key cannot be made of only numbers.')
);
}
return parent::_beforeSave($object);
}
/**
* Assign page to store views
*
* @param \Magento\Framework\Model\AbstractModel $object
* @return $this
*/
protected function _afterSave(\Magento\Framework\Model\AbstractModel $object)
{
return parent::_afterSave($object);
}
/**
* Load an object using 'identifier' field if there's no field specified and value is not numeric
*
* @param \Magento\Framework\Model\AbstractModel $object
* @param mixed $value
* @param string $field
* @return $this
*/
public function load(\Magento\Framework\Model\AbstractModel $object, $value, $field = null)
{
if (!is_numeric($value) && is_null($field)) {
$field = 'identifier';
}
return parent::load($object, $value, $field);
}
/**
* Perform operations after object load
*
* @param \Magento\Framework\Model\AbstractModel $object
* @return $this
*/
protected function _afterLoad(\Magento\Framework\Model\AbstractModel $object)
{
return parent::_afterLoad($object);
}
/**
* Retrieve select object for load object data
*
* @param string $field
* @param mixed $value
* @param \Magento\Cms\Model\Page $object
* @return \Magento\Framework\DB\Select
*/
protected function _getLoadSelect($field, $value, $object)
{
$select = parent::_getLoadSelect($field, $value, $object);
return $select;
}
/**
* Retrieve load select with filter by identifier, store and activity
*
* @param string $identifier
* @param int|array $store
* @param int $isActive
* @return \Magento\Framework\DB\Select
*/
protected function _getLoadByIdentifierSelect($identifier, $store, $isActive = null)
{
$select = $this->getConnection()->select()->from(
['cp' => $this->getMainTable()]
)->where(
'cp.identifier = ?',
$identifier
);
if (!is_null($isActive)) {
$select->where('cp.is_active = ?', $isActive);
}
return $select;
}
/**
* Check whether page identifier is numeric
*
* @param \Magento\Framework\Model\AbstractModel $object
* @return bool
*/
protected function isNumericPageIdentifier(\Magento\Framework\Model\AbstractModel $object)
{
return preg_match('/^[0-9]+$/', $object->getData('identifier'));
}
/**
* Check whether page identifier is valid
*
* @param \Magento\Framework\Model\AbstractModel $object
* @return bool
*/
protected function isValidPageIdentifier(\Magento\Framework\Model\AbstractModel $object)
{
return preg_match('/^[a-z0-9][a-z0-9_\/-]+(\.[a-z0-9_-]+)?$/', $object->getData('identifier'));
}
/**
* Check if page identifier exist for specific store
* return page id if page exists
*
* @param string $identifier
* @param int $storeId
* @return int
*/
public function checkIdentifier($identifier, $storeId)
{
$stores = [\Magento\Store\Model\Store::DEFAULT_STORE_ID, $storeId];
$select = $this->_getLoadByIdentifierSelect($identifier, $stores, 1);
$select->reset(\Magento\Framework\DB\Select::COLUMNS)->columns('cp.slider_id')->limit(1);
return $this->getConnection()->fetchOne($select);
}
/**
* Retrieves cms page title from DB by passed identifier.
*
* @param string $identifier
* @return string|false
*/
public function getSliderTitleByIdentifier($identifier)
{
$stores = [\Magento\Store\Model\Store::DEFAULT_STORE_ID];
if ($this->_store) {
$stores[] = (int)$this->getStore()->getId();
}
$select = $this->_getLoadByIdentifierSelect($identifier, $stores);
$select->reset(\Magento\Framework\DB\Select::COLUMNS)->columns('cp.slider_title')->limit(1);
return $this->getConnection()->fetchOne($select);
}
/**
* Retrieves cms page title from DB by passed id.
*
* @param string $id
* @return string|false
*/
public function getSliderTitleTitleById($id)
{
$connection = $this->getConnection();
$select = $connection->select()->from($this->getMainTable(), 'slider_title')->where('slider_id = :slider_id');
$binds = ['slider_id' => (int)$id];
return $connection->fetchOne($select, $binds);
}
/**
* Retrieves cms page identifier from DB by passed id.
*
* @param string $id
* @return string|false
*/
public function getSliderIdentifierById($id)
{
$connection = $this->getConnection();
$select = $connection->select()->from($this->getMainTable(), 'identifier')->where('slider_id = :slider_id');
$binds = ['slider_id' => (int)$id];
return $connection->fetchOne($select, $binds);
}
/**
* Set store model
*
* @param \Magento\Store\Model\Store $store
* @return $this
*/
public function setStore($store)
{
$this->_store = $store;
return $this;
}
/**
* Retrieve store model
*
* @return \Magento\Store\Model\Store
*/
public function getStore()
{
return $this->_storeManager->getStore($this->_store);
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\SlideBanner\Model\ResourceModel\Slider;
use \Rokanthemes\SlideBanner\Model\ResourceModel\AbstractCollection;
/**
* CMS page collection
*/
class Collection extends AbstractCollection
{
/**
* @var string
*/
protected $_idFieldName = 'slider_id';
/**
* Load data for preview flag
*
* @var bool
*/
protected $_previewFlag;
/**
* Define resource model
*
* @return void
*/
protected function _construct()
{
$this->_init('Rokanthemes\SlideBanner\Model\Slider', 'Rokanthemes\SlideBanner\Model\ResourceModel\Slider');
$this->_map['fields']['slider_id'] = 'main_table.slider_id';
}
/**
* Returns pairs identifier - title for unique identifiers
* and pairs identifier|page_id - title for non-unique after first
*
* @return array
*/
public function toOptionIdArray()
{
$res = [];
$existingIdentifiers = [];
foreach ($this as $item) {
$identifier = $item->getData('identifier');
$data['value'] = $identifier;
$data['label'] = $item->getData('title');
if (in_array($identifier, $existingIdentifiers)) {
$data['value'] .= '|' . $item->getData('page_id');
} else {
$existingIdentifiers[] = $identifier;
}
$res[] = $data;
}
return $res;
}
/**
* Set first store flag
*
* @param bool $flag
* @return $this
*/
public function setFirstStoreFlag($flag = false)
{
$this->_previewFlag = $flag;
return $this;
}
/**
* Add filter by store
*
* @param int|array|\Magento\Store\Model\Store $store
* @param bool $withAdmin
* @return $this
*/
public function addStoreFilter($store, $withAdmin = true)
{
if (!$this->getFlag('store_filter_added')) {
$this->performAddStoreFilter($store, $withAdmin);
}
return $this;
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\SlideBanner\Model\ResourceModel\Slider\Grid;
use Magento\Framework\Api\Search\SearchResultInterface;
use Magento\Framework\Search\AggregationInterface;
use Rokanthemes\SlideBanner\Model\ResourceModel\Slider\Collection as SliderCollection;
/**
* Class Collection
* Collection for displaying grid of sales documents
*/
class Collection extends SliderCollection implements SearchResultInterface
{
/**
* @var AggregationInterface
*/
protected $aggregations;
/**
* @param \Magento\Framework\Data\Collection\EntityFactoryInterface $entityFactory
* @param \Psr\Log\LoggerInterface $logger
* @param \Magento\Framework\Data\Collection\Db\FetchStrategyInterface $fetchStrategy
* @param \Magento\Framework\Event\ManagerInterface $eventManager
* @param \Magento\Store\Model\StoreManagerInterface $storeManager
* @param mixed|null $mainTable
* @param \Magento\Framework\Model\ResourceModel\Db\AbstractDb $eventPrefix
* @param mixed $eventObject
* @param mixed $resourceModel
* @param string $model
* @param null $connection
* @param \Magento\Framework\Model\ResourceModel\Db\AbstractDb|null $resource
*
* @SuppressWarnings(PHPMD.ExcessiveParameterList)
*/
public function __construct(
\Magento\Framework\Data\Collection\EntityFactoryInterface $entityFactory,
\Psr\Log\LoggerInterface $logger,
\Magento\Framework\Data\Collection\Db\FetchStrategyInterface $fetchStrategy,
\Magento\Framework\Event\ManagerInterface $eventManager,
\Magento\Store\Model\StoreManagerInterface $storeManager,
$mainTable,
$eventPrefix,
$eventObject,
$resourceModel,
$model = 'Magento\Framework\View\Element\UiComponent\DataProvider\Document',
$connection = null,
\Magento\Framework\Model\ResourceModel\Db\AbstractDb $resource = null
) {
parent::__construct(
$entityFactory,
$logger,
$fetchStrategy,
$eventManager,
$storeManager,
$connection,
$resource
);
$this->_eventPrefix = $eventPrefix;
$this->_eventObject = $eventObject;
$this->_init($model, $resourceModel);
$this->setMainTable($mainTable);
}
/**
* @return AggregationInterface
*/
public function getAggregations()
{
return $this->aggregations;
}
/**
* @param AggregationInterface $aggregations
* @return $this
*/
public function setAggregations($aggregations)
{
$this->aggregations = $aggregations;
}
/**
* Retrieve all ids for collection
* Backward compatibility with EAV collection
*
* @param int $limit
* @param int $offset
* @return array
*/
public function getAllIds($limit = null, $offset = null)
{
return $this->getConnection()->fetchCol($this->_getAllIdsSelect($limit, $offset), $this->_bindParams);
}
/**
* Get search criteria.
*
* @return \Magento\Framework\Api\SearchCriteriaInterface|null
*/
public function getSearchCriteria()
{
return null;
}
/**
* Set search criteria.
*
* @param \Magento\Framework\Api\SearchCriteriaInterface $searchCriteria
* @return $this
* @SuppressWarnings(PHPMD.UnusedFormalParameter)
*/
public function setSearchCriteria(\Magento\Framework\Api\SearchCriteriaInterface $searchCriteria = null)
{
return $this;
}
/**
* Get total count.
*
* @return int
*/
public function getTotalCount()
{
return $this->getSize();
}
/**
* Set total count.
*
* @param int $totalCount
* @return $this
* @SuppressWarnings(PHPMD.UnusedFormalParameter)
*/
public function setTotalCount($totalCount)
{
return $this;
}
/**
* Set items list.
*
* @param \Magento\Framework\Api\ExtensibleDataInterface[] $items
* @return $this
* @SuppressWarnings(PHPMD.UnusedFormalParameter)
*/
public function setItems(array $items = null)
{
return $this;
}
}
<?php
namespace Rokanthemes\SlideBanner\Model;
class Slide extends \Magento\Framework\Model\AbstractModel
{
/**
* Define resource model
*/
const BASE_MEDIA_PATH = 'slidebanner';
protected function _construct()
{
$this->_init('Rokanthemes\SlideBanner\Model\Resource\Slide');
}
}
\ No newline at end of file
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model;
use Magento\Cms\Api\Data;
use Magento\Cms\Api\BlockRepositoryInterface;
use Magento\Framework\Api\DataObjectHelper;
use Magento\Framework\Api\SortOrder;
use Magento\Framework\Exception\CouldNotDeleteException;
use Magento\Framework\Exception\CouldNotSaveException;
use Magento\Framework\Exception\NoSuchEntityException;
use Magento\Framework\Reflection\DataObjectProcessor;
use Magento\Cms\Model\ResourceModel\Block as ResourceBlock;
use Magento\Cms\Model\ResourceModel\Block\CollectionFactory as BlockCollectionFactory;
use Magento\Store\Model\StoreManagerInterface;
/**
* Class BlockRepository
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
*/
class BlockRepository implements BlockRepositoryInterface
{
/**
* @var ResourceBlock
*/
protected $resource;
/**
* @var BlockFactory
*/
protected $blockFactory;
/**
* @var BlockCollectionFactory
*/
protected $blockCollectionFactory;
/**
* @var Data\BlockSearchResultsInterfaceFactory
*/
protected $searchResultsFactory;
/**
* @var DataObjectHelper
*/
protected $dataObjectHelper;
/**
* @var DataObjectProcessor
*/
protected $dataObjectProcessor;
/**
* @var \Magento\Cms\Api\Data\BlockInterfaceFactory
*/
protected $dataBlockFactory;
/**
* @var \Magento\Store\Model\StoreManagerInterface
*/
private $storeManager;
/**
* @param ResourceBlock $resource
* @param BlockFactory $blockFactory
* @param Data\BlockInterfaceFactory $dataBlockFactory
* @param BlockCollectionFactory $blockCollectionFactory
* @param Data\BlockSearchResultsInterfaceFactory $searchResultsFactory
* @param DataObjectHelper $dataObjectHelper
* @param DataObjectProcessor $dataObjectProcessor
* @param StoreManagerInterface $storeManager
*/
public function __construct(
ResourceBlock $resource,
BlockFactory $blockFactory,
\Magento\Cms\Api\Data\BlockInterfaceFactory $dataBlockFactory,
BlockCollectionFactory $blockCollectionFactory,
Data\BlockSearchResultsInterfaceFactory $searchResultsFactory,
DataObjectHelper $dataObjectHelper,
DataObjectProcessor $dataObjectProcessor,
StoreManagerInterface $storeManager
) {
$this->resource = $resource;
$this->blockFactory = $blockFactory;
$this->blockCollectionFactory = $blockCollectionFactory;
$this->searchResultsFactory = $searchResultsFactory;
$this->dataObjectHelper = $dataObjectHelper;
$this->dataBlockFactory = $dataBlockFactory;
$this->dataObjectProcessor = $dataObjectProcessor;
$this->storeManager = $storeManager;
}
/**
* Save Block data
*
* @param \Magento\Cms\Api\Data\BlockInterface $block
* @return Block
* @throws CouldNotSaveException
*/
public function save(Data\BlockInterface $block)
{
$storeId = $this->storeManager->getStore()->getId();
$block->setStoreId($storeId);
try {
$this->resource->save($block);
} catch (\Exception $exception) {
throw new CouldNotSaveException(__($exception->getMessage()));
}
return $block;
}
/**
* Load Block data by given Block Identity
*
* @param string $blockId
* @return Block
* @throws \Magento\Framework\Exception\NoSuchEntityException
*/
public function getById($blockId)
{
$block = $this->blockFactory->create();
$this->resource->load($block, $blockId);
if (!$block->getId()) {
throw new NoSuchEntityException(__('CMS Block with id "%1" does not exist.', $blockId));
}
return $block;
}
/**
* Load Block data collection by given search criteria
*
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
* @SuppressWarnings(PHPMD.NPathComplexity)
* @param \Magento\Framework\Api\SearchCriteriaInterface $criteria
* @return \Magento\Cms\Model\ResourceModel\Block\Collection
*/
public function getList(\Magento\Framework\Api\SearchCriteriaInterface $criteria)
{
$searchResults = $this->searchResultsFactory->create();
$searchResults->setSearchCriteria($criteria);
$collection = $this->blockCollectionFactory->create();
foreach ($criteria->getFilterGroups() as $filterGroup) {
foreach ($filterGroup->getFilters() as $filter) {
if ($filter->getField() === 'store_id') {
$collection->addStoreFilter($filter->getValue(), false);
continue;
}
$condition = $filter->getConditionType() ?: 'eq';
$collection->addFieldToFilter($filter->getField(), [$condition => $filter->getValue()]);
}
}
$searchResults->setTotalCount($collection->getSize());
$sortOrders = $criteria->getSortOrders();
if ($sortOrders) {
foreach ($sortOrders as $sortOrder) {
$collection->addOrder(
$sortOrder->getField(),
($sortOrder->getDirection() == SortOrder::SORT_ASC) ? 'ASC' : 'DESC'
);
}
}
$collection->setCurPage($criteria->getCurrentPage());
$collection->setPageSize($criteria->getPageSize());
$blocks = [];
/** @var Block $blockModel */
foreach ($collection as $blockModel) {
$blockData = $this->dataBlockFactory->create();
$this->dataObjectHelper->populateWithArray(
$blockData,
$blockModel->getData(),
'Magento\Cms\Api\Data\BlockInterface'
);
$blocks[] = $this->dataObjectProcessor->buildOutputDataArray(
$blockData,
'Magento\Cms\Api\Data\BlockInterface'
);
}
$searchResults->setItems($blocks);
return $searchResults;
}
/**
* Delete Block
*
* @param \Magento\Cms\Api\Data\BlockInterface $block
* @return bool
* @throws CouldNotDeleteException
*/
public function delete(Data\BlockInterface $block)
{
try {
$this->resource->delete($block);
} catch (\Exception $exception) {
throw new CouldNotDeleteException(__($exception->getMessage()));
}
return true;
}
/**
* Delete Block by given Block Identity
*
* @param string $blockId
* @return bool
* @throws CouldNotDeleteException
* @throws NoSuchEntityException
*/
public function deleteById($blockId)
{
return $this->delete($this->getById($blockId));
}
}
<?php
namespace Rokanthemes\SlideBanner\Model;
class Slider extends \Magento\Framework\Model\AbstractModel
{
/**
* Define resource model
*/
protected function _construct()
{
$this->_init('Rokanthemes\SlideBanner\Model\Resource\Slider');
}
public function getSliderSetting()
{
if(!$this->getData('slider_setting'))
return $defaultSetting = array('items'=>1, 'itemsDesktop'=>'[1199,1]', 'itemsDesktopSmall' => '[980,3]', 'itemsTablet' => '[768,2]', 'itemsMobile' => '[479,1]', 'slideSpeed' => 500, 'paginationSpeed' => 500, 'rewindSpeed'=>500);
$data = $this->getData('slider_setting');
$data = json_decode($data, true);
return $data;
}
public function getSetting()
{
$data = $this->getData('slider_setting');
return $data;
}
}
\ No newline at end of file
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model;
use Magento\Cms\Api\Data;
use Magento\Cms\Api\PageRepositoryInterface;
use Magento\Framework\Api\DataObjectHelper;
use Magento\Framework\Api\SortOrder;
use Magento\Framework\Exception\CouldNotDeleteException;
use Magento\Framework\Exception\CouldNotSaveException;
use Magento\Framework\Exception\NoSuchEntityException;
use Magento\Framework\Reflection\DataObjectProcessor;
use Magento\Cms\Model\ResourceModel\Page as ResourcePage;
use Magento\Cms\Model\ResourceModel\Page\CollectionFactory as PageCollectionFactory;
use Magento\Store\Model\StoreManagerInterface;
/**
* Class PageRepository
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
*/
class PageRepository implements PageRepositoryInterface
{
/**
* @var ResourcePage
*/
protected $resource;
/**
* @var PageFactory
*/
protected $pageFactory;
/**
* @var PageCollectionFactory
*/
protected $pageCollectionFactory;
/**
* @var Data\PageSearchResultsInterfaceFactory
*/
protected $searchResultsFactory;
/**
* @var DataObjectHelper
*/
protected $dataObjectHelper;
/**
* @var DataObjectProcessor
*/
protected $dataObjectProcessor;
/**
* @var \Magento\Cms\Api\Data\PageInterfaceFactory
*/
protected $dataPageFactory;
/**
* @var \Magento\Store\Model\StoreManagerInterface
*/
private $storeManager;
/**
* @param ResourcePage $resource
* @param PageFactory $pageFactory
* @param Data\PageInterfaceFactory $dataPageFactory
* @param PageCollectionFactory $pageCollectionFactory
* @param Data\PageSearchResultsInterfaceFactory $searchResultsFactory
* @param DataObjectHelper $dataObjectHelper
* @param DataObjectProcessor $dataObjectProcessor
* @param StoreManagerInterface $storeManager
*/
public function __construct(
ResourcePage $resource,
PageFactory $pageFactory,
Data\PageInterfaceFactory $dataPageFactory,
PageCollectionFactory $pageCollectionFactory,
Data\PageSearchResultsInterfaceFactory $searchResultsFactory,
DataObjectHelper $dataObjectHelper,
DataObjectProcessor $dataObjectProcessor,
StoreManagerInterface $storeManager
) {
$this->resource = $resource;
$this->pageFactory = $pageFactory;
$this->pageCollectionFactory = $pageCollectionFactory;
$this->searchResultsFactory = $searchResultsFactory;
$this->dataObjectHelper = $dataObjectHelper;
$this->dataPageFactory = $dataPageFactory;
$this->dataObjectProcessor = $dataObjectProcessor;
$this->storeManager = $storeManager;
}
/**
* Save Page data
*
* @param \Magento\Cms\Api\Data\PageInterface $page
* @return Page
* @throws CouldNotSaveException
*/
public function save(\Magento\Cms\Api\Data\PageInterface $page)
{
$storeId = $this->storeManager->getStore()->getId();
$page->setStoreId($storeId);
try {
$this->resource->save($page);
} catch (\Exception $exception) {
throw new CouldNotSaveException(__($exception->getMessage()));
}
return $page;
}
/**
* Load Page data by given Page Identity
*
* @param string $pageId
* @return Page
* @throws \Magento\Framework\Exception\NoSuchEntityException
*/
public function getById($pageId)
{
$page = $this->pageFactory->create();
$page->load($pageId);
if (!$page->getId()) {
throw new NoSuchEntityException(__('CMS Page with id "%1" does not exist.', $pageId));
}
return $page;
}
/**
* Load Page data collection by given search criteria
*
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
* @SuppressWarnings(PHPMD.NPathComplexity)
* @param \Magento\Framework\Api\SearchCriteriaInterface $criteria
* @return \Magento\Cms\Model\ResourceModel\Page\Collection
*/
public function getList(\Magento\Framework\Api\SearchCriteriaInterface $criteria)
{
$searchResults = $this->searchResultsFactory->create();
$searchResults->setSearchCriteria($criteria);
$collection = $this->pageCollectionFactory->create();
foreach ($criteria->getFilterGroups() as $filterGroup) {
foreach ($filterGroup->getFilters() as $filter) {
if ($filter->getField() === 'store_id') {
$collection->addStoreFilter($filter->getValue(), false);
continue;
}
$condition = $filter->getConditionType() ?: 'eq';
$collection->addFieldToFilter($filter->getField(), [$condition => $filter->getValue()]);
}
}
$searchResults->setTotalCount($collection->getSize());
$sortOrders = $criteria->getSortOrders();
if ($sortOrders) {
/** @var SortOrder $sortOrder */
foreach ($sortOrders as $sortOrder) {
$collection->addOrder(
$sortOrder->getField(),
($sortOrder->getDirection() == SortOrder::SORT_ASC) ? 'ASC' : 'DESC'
);
}
}
$collection->setCurPage($criteria->getCurrentPage());
$collection->setPageSize($criteria->getPageSize());
$pages = [];
/** @var Page $pageModel */
foreach ($collection as $pageModel) {
$pageData = $this->dataPageFactory->create();
$this->dataObjectHelper->populateWithArray(
$pageData,
$pageModel->getData(),
'Magento\Cms\Api\Data\PageInterface'
);
$pages[] = $this->dataObjectProcessor->buildOutputDataArray(
$pageData,
'Magento\Cms\Api\Data\PageInterface'
);
}
$searchResults->setItems($pages);
return $searchResults;
}
/**
* Delete Page
*
* @param \Magento\Cms\Api\Data\PageInterface $page
* @return bool
* @throws CouldNotDeleteException
*/
public function delete(\Magento\Cms\Api\Data\PageInterface $page)
{
try {
$this->resource->delete($page);
} catch (\Exception $exception) {
throw new CouldNotDeleteException(__($exception->getMessage()));
}
return true;
}
/**
* Delete Page by given Page Identity
*
* @param string $pageId
* @return bool
* @throws CouldNotDeleteException
* @throws NoSuchEntityException
*/
public function deleteById($pageId)
{
return $this->delete($this->getById($pageId));
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\Template;
/**
* Cms Template Filter Model
*/
class Filter extends \Magento\Email\Model\Template\Filter
{
/**
* Whether to allow SID in store directive: AUTO
*
* @var bool
*/
protected $_useSessionInUrl;
/**
* Setter whether SID is allowed in store directive
*
* @param bool $flag
* @return $this
*/
public function setUseSessionInUrl($flag)
{
$this->_useSessionInUrl = (bool)$flag;
return $this;
}
/**
* Retrieve media file URL directive
*
* @param string[] $construction
* @return string
*/
public function mediaDirective($construction)
{
$params = $this->getParameters($construction[2]);
return $this->_storeManager->getStore()->getBaseMediaDir() . '/' . $params['url'];
}
}
<?php
/**
* Cms Template Filter Provider
*
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Cms\Model\Template;
/**
* Filter provider model
*/
class FilterProvider
{
/**
* @var \Magento\Framework\ObjectManagerInterface
*/
protected $_objectManager;
/**
* @var string
*/
protected $_pageFilter;
/**
* @var string
*/
protected $_blockFilter;
/**
* @var array
*/
protected $_instanceList;
/**
* @param \Magento\Framework\ObjectManagerInterface $objectManager
* @param string $pageFilter
* @param string $blockFilter
*/
public function __construct(
\Magento\Framework\ObjectManagerInterface $objectManager,
$pageFilter = 'Magento\Cms\Model\Template\Filter',
$blockFilter = 'Magento\Cms\Model\Template\Filter'
) {
$this->_objectManager = $objectManager;
$this->_pageFilter = $pageFilter;
$this->_blockFilter = $blockFilter;
}
/**
* @param string $instanceName
* @return \Magento\Framework\Filter\Template
* @throws \Exception
*/
protected function _getFilterInstance($instanceName)
{
if (!isset($this->_instanceList[$instanceName])) {
$instance = $this->_objectManager->get($instanceName);
if (!$instance instanceof \Magento\Framework\Filter\Template) {
throw new \Exception('Template filter ' . $instanceName . ' does not implement required interface');
}
$this->_instanceList[$instanceName] = $instance;
}
return $this->_instanceList[$instanceName];
}
/**
* @return \Magento\Framework\Filter\Template
*/
public function getBlockFilter()
{
return $this->_getFilterInstance($this->_blockFilter);
}
/**
* @return \Magento\Framework\Filter\Template
*/
public function getPageFilter()
{
return $this->_getFilterInstance($this->_pageFilter);
}
}
<?php
/**
* Theme file uploader service
*
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Magento\Theme\Model;
use Magento\Framework\Filesystem;
use Magento\Framework\Filesystem\DirectoryList;
class Uploader
{
/**
* Uploaded file path
*
* @var string|null
*/
protected $_filePath;
/**
* @var \Magento\Framework\Filesystem\Directory\ReadInterface
*/
protected $_tmpDirectory;
/**
* File size
*
* @var \Magento\Framework\File\Size
*/
protected $_fileSize;
/**
* File uploader
*
* @var \Magento\MediaStorage\Model\File\Uploader
*/
protected $_uploader;
/**
* @var \Magento\MediaStorage\Model\File\Uploader
*/
protected $_uploaderFactory;
/**
* @var string|null
*/
protected $_cssUploadLimit;
/**
* @var string|null
*/
protected $_jsUploadLimit;
/**
* Constructor
*
* @param \Magento\Framework\Filesystem $filesystem
* @param \Magento\Framework\File\Size $fileSize
* @param \Magento\MediaStorage\Model\File\UploaderFactory $uploaderFactory
* @param array $uploadLimits keys are 'css' and 'js' for file type, values defines maximum file size, example: 2M
*/
public function __construct(
\Magento\Framework\Filesystem $filesystem,
\Magento\Framework\File\Size $fileSize,
\Magento\MediaStorage\Model\File\UploaderFactory $uploaderFactory,
array $uploadLimits = []
) {
$this->_tmpDirectory = $filesystem->getDirectoryRead(DirectoryList::SYS_TMP);
$this->_fileSize = $fileSize;
$this->_uploaderFactory = $uploaderFactory;
if (isset($uploadLimits['css'])) {
$this->_cssUploadLimit = $uploadLimits['css'];
}
if (isset($uploadLimits['js'])) {
$this->_jsUploadLimit = $uploadLimits['js'];
}
}
public function uploadImageFile($file)
{
}
/**
* Upload css file
*
* @param string $file - Key in the $_FILES array
* @return array
* @throws \Magento\Framework\Exception\LocalizedException
*/
public function uploadCssFile($file)
{
/** @var $fileUploader \Magento\MediaStorage\Model\File\Uploader */
$fileUploader = $this->_uploaderFactory->create(['fileId' => $file]);
$fileUploader->setAllowedExtensions(['css']);
$fileUploader->setAllowRenameFiles(true);
$fileUploader->setAllowCreateFolders(true);
$isValidFileSize = $this->_validateFileSize($fileUploader->getFileSize(), $this->getCssUploadMaxSize());
if (!$isValidFileSize) {
throw new \Magento\Framework\Exception\LocalizedException(
__('The CSS file must be less than %1M.', $this->getCssUploadMaxSizeInMb())
);
}
$file = $fileUploader->validateFile();
return ['filename' => $file['name'], 'content' => $this->getFileContent($file['tmp_name'])];
}
/**
* Upload js file
*
* @param string $file - Key in the $_FILES array
* @return array
* @throws \Magento\Framework\Exception\LocalizedException
*/
public function uploadJsFile($file)
{
/** @var $fileUploader \Magento\MediaStorage\Model\File\Uploader */
$fileUploader = $this->_uploaderFactory->create(['fileId' => $file]);
$fileUploader->setAllowedExtensions(['js']);
$fileUploader->setAllowRenameFiles(true);
$fileUploader->setAllowCreateFolders(true);
$isValidFileSize = $this->_validateFileSize($fileUploader->getFileSize(), $this->getJsUploadMaxSize());
if (!$isValidFileSize) {
throw new \Magento\Framework\Exception\LocalizedException(
__('The JS file must be less than %1M.', $this->getJsUploadMaxSizeInMb())
);
}
$file = $fileUploader->validateFile();
return ['filename' => $file['name'], 'content' => $this->getFileContent($file['tmp_name'])];
}
/**
* Get uploaded file content
*
* @param string $filePath
* @return string
*/
public function getFileContent($filePath)
{
return $this->_tmpDirectory->readFile($this->_tmpDirectory->getRelativePath($filePath));
}
/**
* Get css upload max size
*
* @return int
*/
public function getCssUploadMaxSize()
{
return $this->_getMaxUploadSize($this->_cssUploadLimit);
}
/**
* Get js upload max size
*
* @return int
*/
public function getJsUploadMaxSize()
{
return $this->_getMaxUploadSize($this->_jsUploadLimit);
}
/**
* Get max upload size
*
* @param string $configuredLimit
* @return int
*/
private function _getMaxUploadSize($configuredLimit)
{
$maxIniUploadSize = $this->_fileSize->getMaxFileSize();
if ($configuredLimit === null) {
return $maxIniUploadSize;
}
$maxUploadSize = $this->_fileSize->convertSizeToInteger($configuredLimit);
return min($maxUploadSize, $maxIniUploadSize);
}
/**
* Get css upload max size in megabytes
*
* @return float
*/
public function getCssUploadMaxSizeInMb()
{
return $this->_fileSize->getFileSizeInMb($this->getCssUploadMaxSize());
}
/**
* Get js upload max size in megabytes
*
* @return float
*/
public function getJsUploadMaxSizeInMb()
{
return $this->_fileSize->getFileSizeInMb($this->getJsUploadMaxSize());
}
/**
* Validate max file size
*
* @param int $fileSize
* @param int $maxFileSize
* @return bool
*/
protected function _validateFileSize($fileSize, $maxFileSize)
{
if ($fileSize > $maxFileSize) {
return false;
}
return true;
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\SlideBanner\Model\Wysiwyg;
/**
* Wysiwyg Config for Editor HTML Element
*/
class Config extends \Magento\Framework\DataObject
{
/**
* Wysiwyg status enabled
*/
const WYSIWYG_ENABLED = 'enabled';
/**
* Wysiwyg status configuration path
*/
const WYSIWYG_STATUS_CONFIG_PATH = 'cms/wysiwyg/enabled';
/**
*
*/
const WYSIWYG_SKIN_IMAGE_PLACEHOLDER_ID = 'Magento_Cms::images/wysiwyg_skin_image.png';
/**
* Wysiwyg status hidden
*/
const WYSIWYG_HIDDEN = 'hidden';
/**
* Wysiwyg status disabled
*/
const WYSIWYG_DISABLED = 'disabled';
/**
* Wysiwyg image directory
*/
const IMAGE_DIRECTORY = 'wysiwyg';
/**
* @var \Magento\Framework\AuthorizationInterface
*/
protected $_authorization;
/**
* @var \Magento\Framework\View\Asset\Repository
*/
protected $_assetRepo;
/**
* @var \Magento\Variable\Model\Variable\Config
*/
protected $_variableConfig;
/**
* @var \Magento\Widget\Model\Widget\Config
*/
protected $_widgetConfig;
/**
* Core event manager proxy
*
* @var \Magento\Framework\Event\ManagerInterface
*/
protected $_eventManager;
/**
* Core store config
*
* @var \Magento\Framework\App\Config\ScopeConfigInterface
*/
protected $_scopeConfig;
/**
* @var array
*/
protected $_windowSize;
/**
* @var \Magento\Backend\Model\UrlInterface
*/
protected $_backendUrl;
/**
* @var \Magento\Store\Model\StoreManagerInterface
*/
protected $_storeManager;
/**
* @param \Magento\Backend\Model\UrlInterface $backendUrl
* @param \Magento\Framework\Event\ManagerInterface $eventManager
* @param \Magento\Framework\AuthorizationInterface $authorization
* @param \Magento\Framework\View\Asset\Repository $assetRepo
* @param \Magento\Variable\Model\Variable\Config $variableConfig
* @param \Magento\Widget\Model\Widget\Config $widgetConfig
* @param \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig
* @param \Magento\Store\Model\StoreManagerInterface $storeManager
* @param array $windowSize
* @param array $data
* @SuppressWarnings(PHPMD.ExcessiveParameterList)
*/
public function __construct(
\Magento\Backend\Model\UrlInterface $backendUrl,
\Magento\Framework\Event\ManagerInterface $eventManager,
\Magento\Framework\AuthorizationInterface $authorization,
\Magento\Framework\View\Asset\Repository $assetRepo,
\Magento\Variable\Model\Variable\Config $variableConfig,
\Magento\Widget\Model\Widget\Config $widgetConfig,
\Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig,
\Magento\Store\Model\StoreManagerInterface $storeManager,
array $windowSize = [],
array $data = []
) {
$this->_backendUrl = $backendUrl;
$this->_eventManager = $eventManager;
$this->_scopeConfig = $scopeConfig;
$this->_authorization = $authorization;
$this->_assetRepo = $assetRepo;
$this->_variableConfig = $variableConfig;
$this->_widgetConfig = $widgetConfig;
$this->_windowSize = $windowSize;
$this->_storeManager = $storeManager;
parent::__construct($data);
}
/**
* Return Wysiwyg config as \Magento\Framework\DataObject
*
* Config options description:
*
* enabled: Enabled Visual Editor or not
* hidden: Show Visual Editor on page load or not
* use_container: Wrap Editor contents into div or not
* no_display: Hide Editor container or not (related to use_container)
* translator: Helper to translate phrases in lib
* files_browser_*: Files Browser (media, images) settings
* encode_directives: Encode template directives with JS or not
*
* @param array|\Magento\Framework\DataObject $data Object constructor params to override default config values
* @return \Magento\Framework\DataObject
*/
public function getConfig($data = [])
{
$config = new \Magento\Framework\DataObject();
$config->setData(
[
'enabled' => $this->isEnabled(),
'hidden' => $this->isHidden(),
'use_container' => false,
'add_variables' => true,
'add_widgets' => true,
'no_display' => false,
'encode_directives' => true,
'directives_url' => $this->_backendUrl->getUrl('cms/wysiwyg/directive'),
'popup_css' => $this->_assetRepo->getUrl(
'mage/adminhtml/wysiwyg/tiny_mce/themes/advanced/skins/default/dialog.css'
),
'content_css' => $this->_assetRepo->getUrl(
'mage/adminhtml/wysiwyg/tiny_mce/themes/advanced/skins/default/content.css'
),
'width' => '100%',
'plugins' => [],
]
);
$config->setData('directives_url_quoted', preg_quote($config->getData('directives_url')));
if ($this->_authorization->isAllowed('Magento_Cms::media_gallery')) {
$config->addData(
[
'add_images' => true,
'files_browser_window_url' => $this->_backendUrl->getUrl('cms/wysiwyg_images/index'),
'files_browser_window_width' => $this->_windowSize['width'],
'files_browser_window_height' => $this->_windowSize['height'],
]
);
}
if (is_array($data)) {
$config->addData($data);
}
if ($config->getData('add_variables')) {
$settings = $this->_variableConfig->getWysiwygPluginSettings($config);
$config->addData($settings);
}
if ($config->getData('add_widgets')) {
$settings = $this->_widgetConfig->getPluginSettings($config);
$config->addData($settings);
}
return $config;
}
/**
* Return path for skin images placeholder
*
* @return string
*/
public function getSkinImagePlaceholderPath()
{
$staticPath = $this->_storeManager->getStore()->getBaseStaticDir();
$placeholderPath = $this->_assetRepo->createAsset(self::WYSIWYG_SKIN_IMAGE_PLACEHOLDER_ID)->getPath();
return $staticPath . '/' . $placeholderPath;
}
/**
* Check whether Wysiwyg is enabled or not
*
* @return bool
*/
public function isEnabled()
{
$wysiwygState = $this->_scopeConfig->getValue(
self::WYSIWYG_STATUS_CONFIG_PATH,
\Magento\Store\Model\ScopeInterface::SCOPE_STORE,
$this->getStoreId()
);
return in_array($wysiwygState, [self::WYSIWYG_ENABLED, self::WYSIWYG_HIDDEN]);
}
/**
* Check whether Wysiwyg is loaded on demand or not
*
* @return bool
*/
public function isHidden()
{
$status = $this->_scopeConfig->getValue(
self::WYSIWYG_STATUS_CONFIG_PATH,
\Magento\Store\Model\ScopeInterface::SCOPE_STORE
);
return $status == self::WYSIWYG_HIDDEN;
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
namespace Rokanthemes\SlideBanner\Model\Wysiwyg\Images;
use Magento\Cms\Helper\Wysiwyg\Images;
use Magento\Framework\App\Filesystem\DirectoryList;
/**
* Wysiwyg Images model
*
* @SuppressWarnings(PHPMD.LongVariable)
* @SuppressWarnings(PHPMD.TooManyFields)
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
*/
class Storage extends \Magento\Framework\DataObject
{
const DIRECTORY_NAME_REGEXP = '/^[a-z0-9\-\_]+$/si';
const THUMBS_DIRECTORY_NAME = '.thumbs';
const THUMB_PLACEHOLDER_PATH_SUFFIX = 'Magento_Cms::images/placeholder_thumbnail.jpg';
/**
* Config object
*
* @var \Magento\Framework\App\Config\Element
*/
protected $_config;
/**
* Config object as array
*
* @var array
*/
protected $_configAsArray;
/**
* @var \Magento\Framework\Filesystem\Directory\Write
*/
protected $_directory;
/**
* @var \Magento\Framework\Image\AdapterFactory
*/
protected $_imageFactory;
/**
* @var \Magento\Framework\View\Asset\Repository
*/
protected $_assetRepo;
/**
* Core file storage database
*
* @var \Magento\MediaStorage\Helper\File\Storage\Database
*/
protected $_coreFileStorageDb = null;
/**
* Cms wysiwyg images
*
* @var \Magento\Cms\Helper\Wysiwyg\Images
*/
protected $_cmsWysiwygImages = null;
/**
* @var array
*/
protected $_resizeParameters;
/**
* @var array
*/
protected $_extensions;
/**
* @var array
*/
protected $_dirs;
/**
* @var \Magento\Backend\Model\UrlInterface
*/
protected $_backendUrl;
/**
* @var \Magento\Backend\Model\Session
*/
protected $_session;
/**
* Directory database factory
*
* @var \Magento\MediaStorage\Model\File\Storage\Directory\DatabaseFactory
*/
protected $_directoryDatabaseFactory;
/**
* Storage database factory
*
* @var \Magento\MediaStorage\Model\File\Storage\DatabaseFactory
*/
protected $_storageDatabaseFactory;
/**
* Storage file factory
*
* @var \Magento\MediaStorage\Model\File\Storage\FileFactory
*/
protected $_storageFileFactory;
/**
* Storage collection factory
*
* @var \Magento\Cms\Model\Wysiwyg\Images\Storage\CollectionFactory
*/
protected $_storageCollectionFactory;
/**
* Uploader factory
*
* @var \Magento\MediaStorage\Model\File\UploaderFactory
*/
protected $_uploaderFactory;
/**
* Construct
*
* @param \Magento\Backend\Model\Session $session
* @param \Magento\Backend\Model\UrlInterface $backendUrl
* @param \Magento\Cms\Helper\Wysiwyg\Images $cmsWysiwygImages
* @param \Magento\MediaStorage\Helper\File\Storage\Database $coreFileStorageDb
* @param \Magento\Framework\Filesystem $filesystem
* @param \Magento\Framework\Image\AdapterFactory $imageFactory
* @param \Magento\Framework\View\Asset\Repository $assetRepo
* @param \Magento\Cms\Model\Wysiwyg\Images\Storage\CollectionFactory $storageCollectionFactory
* @param \Magento\MediaStorage\Model\File\Storage\FileFactory $storageFileFactory
* @param \Magento\MediaStorage\Model\File\Storage\DatabaseFactory $storageDatabaseFactory
* @param \Magento\MediaStorage\Model\File\Storage\Directory\DatabaseFactory $directoryDatabaseFactory
* @param \Magento\MediaStorage\Model\File\UploaderFactory $uploaderFactory
* @param array $resizeParameters
* @param array $extensions
* @param array $dirs
* @param array $data
*
* @SuppressWarnings(PHPMD.ExcessiveParameterList)
*/
public function __construct(
\Magento\Backend\Model\Session $session,
\Magento\Backend\Model\UrlInterface $backendUrl,
\Magento\Cms\Helper\Wysiwyg\Images $cmsWysiwygImages,
\Magento\MediaStorage\Helper\File\Storage\Database $coreFileStorageDb,
\Magento\Framework\Filesystem $filesystem,
\Magento\Framework\Image\AdapterFactory $imageFactory,
\Magento\Framework\View\Asset\Repository $assetRepo,
\Magento\Cms\Model\Wysiwyg\Images\Storage\CollectionFactory $storageCollectionFactory,
\Magento\MediaStorage\Model\File\Storage\FileFactory $storageFileFactory,
\Magento\MediaStorage\Model\File\Storage\DatabaseFactory $storageDatabaseFactory,
\Magento\MediaStorage\Model\File\Storage\Directory\DatabaseFactory $directoryDatabaseFactory,
\Magento\MediaStorage\Model\File\UploaderFactory $uploaderFactory,
array $resizeParameters = [],
array $extensions = [],
array $dirs = [],
array $data = []
) {
$this->_session = $session;
$this->_backendUrl = $backendUrl;
$this->_cmsWysiwygImages = $cmsWysiwygImages;
$this->_coreFileStorageDb = $coreFileStorageDb;
$this->_directory = $filesystem->getDirectoryWrite(DirectoryList::MEDIA);
$this->_imageFactory = $imageFactory;
$this->_assetRepo = $assetRepo;
$this->_storageCollectionFactory = $storageCollectionFactory;
$this->_storageFileFactory = $storageFileFactory;
$this->_storageDatabaseFactory = $storageDatabaseFactory;
$this->_directoryDatabaseFactory = $directoryDatabaseFactory;
$this->_uploaderFactory = $uploaderFactory;
$this->_resizeParameters = $resizeParameters;
$this->_extensions = $extensions;
$this->_dirs = $dirs;
parent::__construct($data);
}
/**
* Create sub directories if DB storage is used
*
* @param string $path
* @return void
*/
protected function createSubDirectories($path)
{
if ($this->_coreFileStorageDb->checkDbUsage()) {
/** @var \Magento\MediaStorage\Model\File\Storage\Directory\Database $subDirectories */
$subDirectories = $this->_directoryDatabaseFactory->create();
$directories = $subDirectories->getSubdirectories($path);
foreach ($directories as $directory) {
$fullPath = rtrim($path, '/') . '/' . $directory['name'];
$this->_directory->create($fullPath);
}
}
}
/**
* Prepare and get conditions for exclude directories
*
* @return array
*/
protected function getConditionsForExcludeDirs()
{
$conditions = ['reg_exp' => [], 'plain' => []];
if ($this->_dirs['exclude']) {
foreach ($this->_dirs['exclude'] as $dir) {
$conditions[!empty($dir['regexp']) ? 'reg_exp' : 'plain'][$dir['name']] = true;
}
}
// "include" section takes precedence and can revoke directory exclusion
if ($this->_dirs['include']) {
foreach ($this->_dirs['include'] as $dir) {
unset($conditions['reg_exp'][$dir['name']], $conditions['plain'][$dir['name']]);
}
}
return $conditions;
}
/**
* Remove excluded directories from collection
*
* @param \Magento\Framework\Data\Collection\Filesystem $collection
* @param array $conditions
* @return \Magento\Framework\Data\Collection\Filesystem
*/
protected function removeItemFromCollection($collection, $conditions)
{
$regExp = $conditions['reg_exp'] ? '~' . implode('|', array_keys($conditions['reg_exp'])) . '~i' : null;
$storageRootLength = strlen($this->_cmsWysiwygImages->getStorageRoot());
foreach ($collection as $key => $value) {
$rootChildParts = explode('/', substr($value->getFilename(), $storageRootLength));
if (array_key_exists($rootChildParts[1], $conditions['plain'])
|| ($regExp && preg_match($regExp, $value->getFilename()))) {
$collection->removeItemByKey($key);
}
}
return $collection;
}
/**
* Return one-level child directories for specified path
*
* @param string $path Parent directory path
* @return \Magento\Framework\Data\Collection\Filesystem
*/
public function getDirsCollection($path)
{
$this->createSubDirectories($path);
$collection = $this->getCollection($path)
->setCollectDirs(true)
->setCollectFiles(false)
->setCollectRecursively(false);
$conditions = $this->getConditionsForExcludeDirs();
return $this->removeItemFromCollection($collection, $conditions);
}
/**
* Return files
*
* @param string $path Parent directory path
* @param string $type Type of storage, e.g. image, media etc.
* @return \Magento\Framework\Data\Collection\Filesystem
*/
public function getFilesCollection($path, $type = null)
{
if ($this->_coreFileStorageDb->checkDbUsage()) {
$files = $this->_storageDatabaseFactory->create()->getDirectoryFiles($path);
/** @var \Magento\MediaStorage\Model\File\Storage\File $fileStorageModel */
$fileStorageModel = $this->_storageFileFactory->create();
foreach ($files as $file) {
$fileStorageModel->saveFile($file);
}
}
$collection = $this->getCollection(
$path
)->setCollectDirs(
false
)->setCollectFiles(
true
)->setCollectRecursively(
false
)->setOrder(
'mtime',
\Magento\Framework\Data\Collection::SORT_ORDER_ASC
);
// Add files extension filter
if ($allowed = $this->getAllowedExtensions($type)) {
$collection->setFilesFilter('/\.(' . implode('|', $allowed) . ')$/i');
}
// prepare items
foreach ($collection as $item) {
$item->setId($this->_cmsWysiwygImages->idEncode($item->getBasename()));
$item->setName($item->getBasename());
$item->setShortName($this->_cmsWysiwygImages->getShortFilename($item->getBasename()));
$item->setUrl($this->_cmsWysiwygImages->getCurrentUrl() . $item->getBasename());
if ($this->isImage($item->getBasename())) {
$thumbUrl = $this->getThumbnailUrl($item->getFilename(), true);
// generate thumbnail "on the fly" if it does not exists
if (!$thumbUrl) {
$thumbUrl = $this->_backendUrl->getUrl('cms/*/thumbnail', ['file' => $item->getId()]);
}
$size = @getimagesize($item->getFilename());
if (is_array($size)) {
$item->setWidth($size[0]);
$item->setHeight($size[1]);
}
} else {
$thumbUrl = $this->_assetRepo->getUrl(self::THUMB_PLACEHOLDER_PATH_SUFFIX);
}
$item->setThumbUrl($thumbUrl);
}
return $collection;
}
/**
* Storage collection
*
* @param string $path Path to the directory
* @return \Magento\Cms\Model\Wysiwyg\Images\Storage\Collection
*/
public function getCollection($path = null)
{
/** @var \Magento\Cms\Model\Wysiwyg\Images\Storage\Collection $collection */
$collection = $this->_storageCollectionFactory->create();
if ($path !== null) {
$collection->addTargetDir($path);
}
return $collection;
}
/**
* Create new directory in storage
*
* @param string $name New directory name
* @param string $path Parent directory path
* @return array New directory info
* @throws \Magento\Framework\Exception\LocalizedException
*/
public function createDirectory($name, $path)
{
if (!preg_match(self::DIRECTORY_NAME_REGEXP, $name)) {
throw new \Magento\Framework\Exception\LocalizedException(
__('Please rename the folder using only letters, numbers, underscores and dashes.')
);
}
$relativePath = $this->_directory->getRelativePath($path);
if (!$this->_directory->isDirectory($relativePath) || !$this->_directory->isWritable($relativePath)) {
$path = $this->_cmsWysiwygImages->getStorageRoot();
}
$newPath = $path . '/' . $name;
$relativeNewPath = $this->_directory->getRelativePath($newPath);
if ($this->_directory->isDirectory($relativeNewPath)) {
throw new \Magento\Framework\Exception\LocalizedException(
__('We found a directory with the same name. Please try another folder name.')
);
}
$this->_directory->create($relativeNewPath);
try {
if ($this->_coreFileStorageDb->checkDbUsage()) {
$relativePath = $this->_coreFileStorageDb->getMediaRelativePath($newPath);
$this->_directoryDatabaseFactory->create()->createRecursive($relativePath);
}
$result = [
'name' => $name,
'short_name' => $this->_cmsWysiwygImages->getShortFilename($name),
'path' => $newPath,
'id' => $this->_cmsWysiwygImages->convertPathToId($newPath),
];
return $result;
} catch (\Magento\Framework\Exception\FileSystemException $e) {
throw new \Magento\Framework\Exception\LocalizedException(__('We cannot create a new directory.'));
}
}
/**
* Recursively delete directory from storage
*
* @param string $path Target dir
* @return void
* @throws \Magento\Framework\Exception\LocalizedException
*/
public function deleteDirectory($path)
{
if ($this->_coreFileStorageDb->checkDbUsage()) {
$this->_directoryDatabaseFactory->create()->deleteDirectory($path);
}
try {
$this->_deleteByPath($path);
$path = $this->getThumbnailRoot() . $this->_getRelativePathToRoot($path);
$this->_deleteByPath($path);
} catch (\Magento\Framework\Exception\FileSystemException $e) {
throw new \Magento\Framework\Exception\LocalizedException(__('We cannot delete directory %1.', $path));
}
}
/**
* Delete by path
*
* @param string $path
* @return void
*/
protected function _deleteByPath($path)
{
$path = $this->_sanitizePath($path);
if (!empty($path)) {
$this->_validatePath($path);
$this->_directory->delete($this->_directory->getRelativePath($path));
}
}
/**
* Delete file (and its thumbnail if exists) from storage
*
* @param string $target File path to be deleted
* @return $this
*/
public function deleteFile($target)
{
$relativePath = $this->_directory->getRelativePath($target);
if ($this->_directory->isFile($relativePath)) {
$this->_directory->delete($relativePath);
}
$this->_coreFileStorageDb->deleteFile($target);
$thumb = $this->getThumbnailPath($target, true);
$relativePathThumb = $this->_directory->getRelativePath($thumb);
if ($thumb) {
if ($this->_directory->isFile($relativePathThumb)) {
$this->_directory->delete($relativePathThumb);
}
$this->_coreFileStorageDb->deleteFile($thumb);
}
return $this;
}
/**
* Upload and resize new file
*
* @param string $targetPath Target directory
* @param string $type Type of storage, e.g. image, media etc.
* @return array File info Array
* @throws \Magento\Framework\Exception\LocalizedException
*/
public function uploadFile($targetPath, $type = null)
{
/** @var \Magento\MediaStorage\Model\File\Uploader $uploader */
$uploader = $this->_uploaderFactory->create(['fileId' => 'image']);
$allowed = $this->getAllowedExtensions($type);
if ($allowed) {
$uploader->setAllowedExtensions($allowed);
}
$uploader->setAllowRenameFiles(true);
$uploader->setFilesDispersion(false);
$result = $uploader->save($targetPath);
if (!$result) {
throw new \Magento\Framework\Exception\LocalizedException(__('We can\'t upload the file right now.'));
}
// create thumbnail
$this->resizeFile($targetPath . '/' . $uploader->getUploadedFileName(), true);
$result['cookie'] = [
'name' => $this->getSession()->getName(),
'value' => $this->getSession()->getSessionId(),
'lifetime' => $this->getSession()->getCookieLifetime(),
'path' => $this->getSession()->getCookiePath(),
'domain' => $this->getSession()->getCookieDomain(),
];
return $result;
}
/**
* Thumbnail path getter
*
* @param string $filePath original file path
* @param bool $checkFile OPTIONAL is it necessary to check file availability
* @return string|false
*/
public function getThumbnailPath($filePath, $checkFile = false)
{
$mediaRootDir = $this->_cmsWysiwygImages->getStorageRoot();
if (strpos($filePath, $mediaRootDir) === 0) {
$thumbPath = $this->getThumbnailRoot() . substr($filePath, strlen($mediaRootDir));
if (!$checkFile || $this->_directory->isExist($this->_directory->getRelativePath($thumbPath))) {
return $thumbPath;
}
}
return false;
}
/**
* Thumbnail URL getter
*
* @param string $filePath original file path
* @param bool $checkFile OPTIONAL is it necessary to check file availability
* @return string|false
*/
public function getThumbnailUrl($filePath, $checkFile = false)
{
$mediaRootDir = $this->_cmsWysiwygImages->getStorageRoot();
if (strpos($filePath, $mediaRootDir) === 0) {
$thumbSuffix = self::THUMBS_DIRECTORY_NAME . substr($filePath, strlen($mediaRootDir));
if (!$checkFile || $this->_directory->isExist(
$this->_directory->getRelativePath($mediaRootDir . '/' . $thumbSuffix)
)
) {
$thumbSuffix = substr(
$mediaRootDir,
strlen($this->_directory->getAbsolutePath())
) . '/' . $thumbSuffix;
$randomIndex = '?rand=' . time();
return str_replace('\\', '/', $this->_cmsWysiwygImages->getBaseUrl() . $thumbSuffix) . $randomIndex;
}
}
return false;
}
/**
* Create thumbnail for image and save it to thumbnails directory
*
* @param string $source Image path to be resized
* @param bool $keepRation Keep aspect ratio or not
* @return bool|string Resized filepath or false if errors were occurred
*/
public function resizeFile($source, $keepRation = true)
{
$realPath = $this->_directory->getRelativePath($source);
if (!$this->_directory->isFile($realPath) || !$this->_directory->isExist($realPath)) {
return false;
}
$targetDir = $this->getThumbsPath($source);
$pathTargetDir = $this->_directory->getRelativePath($targetDir);
if (!$this->_directory->isExist($pathTargetDir)) {
$this->_directory->create($pathTargetDir);
}
if (!$this->_directory->isExist($pathTargetDir)) {
return false;
}
$image = $this->_imageFactory->create();
$image->open($source);
$image->keepAspectRatio($keepRation);
$image->resize($this->_resizeParameters['width'], $this->_resizeParameters['height']);
$dest = $targetDir . '/' . pathinfo($source, PATHINFO_BASENAME);
$image->save($dest);
if ($this->_directory->isFile($this->_directory->getRelativePath($dest))) {
return $dest;
}
return false;
}
/**
* Resize images on the fly in controller action
*
* @param string $filename File basename
* @return bool|string Thumbnail path or false for errors
*/
public function resizeOnTheFly($filename)
{
$path = $this->getSession()->getCurrentPath();
if (!$path) {
$path = $this->_cmsWysiwygImages->getCurrentPath();
}
return $this->resizeFile($path . '/' . $filename);
}
/**
* Return thumbnails directory path for file/current directory
*
* @param bool|string $filePath Path to the file
* @return string
*/
public function getThumbsPath($filePath = false)
{
$mediaRootDir = $this->_cmsWysiwygImages->getStorageRoot();
$thumbnailDir = $this->getThumbnailRoot();
if ($filePath && strpos($filePath, $mediaRootDir) === 0) {
$thumbnailDir .= dirname(substr($filePath, strlen($mediaRootDir)));
}
return $thumbnailDir;
}
/**
* Storage session
*
* @return \Magento\Backend\Model\Session
*/
public function getSession()
{
return $this->_session;
}
/**
* Prepare allowed_extensions config settings
*
* @param string $type Type of storage, e.g. image, media etc.
* @return array Array of allowed file extensions
*/
public function getAllowedExtensions($type = null)
{
if (is_string($type) && array_key_exists("{$type}_allowed", $this->_extensions)) {
$allowed = $this->_extensions["{$type}_allowed"];
} else {
$allowed = $this->_extensions['allowed'];
}
return array_keys(array_filter($allowed));
}
/**
* Thumbnail root directory getter
*
* @return string
*/
public function getThumbnailRoot()
{
return $this->_cmsWysiwygImages->getStorageRoot() . '/' . self::THUMBS_DIRECTORY_NAME;
}
/**
* Simple way to check whether file is image or not based on extension
*
* @param string $filename
* @return bool
*/
public function isImage($filename)
{
if (!$this->hasData('_image_extensions')) {
$this->setData('_image_extensions', $this->getAllowedExtensions('image'));
}
$ext = strtolower(pathinfo($filename, PATHINFO_EXTENSION));
return in_array($ext, $this->_getData('_image_extensions'));
}
/**
* Get resize width
*
* @return int
*/
public function getResizeWidth()
{
return $this->_resizeParameters['width'];
}
/**
* Get resize height
*
* @return int
*/
public function getResizeHeight()
{
return $this->_resizeParameters['height'];
}
/**
* Get cms wysiwyg images helper
*
* @return Images|null
*/
public function getCmsWysiwygImages()
{
return $this->_cmsWysiwygImages;
}
/**
* Is path under storage root directory
*
* @param string $path
* @return void
* @throws \Magento\Framework\Exception\LocalizedException
*/
protected function _validatePath($path)
{
$root = $this->_sanitizePath($this->_cmsWysiwygImages->getStorageRoot());
if ($root == $path) {
throw new \Magento\Framework\Exception\LocalizedException(
__('We can\'t delete root directory %1 right now.', $path)
);
}
if (strpos($path, $root) !== 0) {
throw new \Magento\Framework\Exception\LocalizedException(
__('Directory %1 is not under storage root path.', $path)
);
}
}
/**
* Sanitize path
*
* @param string $path
* @return string
*/
protected function _sanitizePath($path)
{
return rtrim(preg_replace('~[/\\\]+~', '/', $this->_directory->getDriver()->getRealPath($path)), '/');
}
/**
* Get path in root storage dir
*
* @param string $path
* @return string|bool
*/
protected function _getRelativePathToRoot($path)
{
return substr(
$this->_sanitizePath($path),
strlen($this->_sanitizePath($this->_cmsWysiwygImages->getStorageRoot()))
);
}
}
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
// @codingStandardsIgnoreFile
namespace Magento\Cms\Model\Wysiwyg\Images\Storage;
use Magento\Framework\App\Filesystem\DirectoryList;
/**
* Wysiwyg Images storage collection
*/
class Collection extends \Magento\Framework\Data\Collection\Filesystem
{
/**
* @var \Magento\Framework\Filesystem
*/
protected $_filesystem;
/**
* @param \Magento\Framework\Data\Collection\EntityFactory $entityFactory
* @param \Magento\Framework\Filesystem $filesystem
*/
public function __construct(\Magento\Framework\Data\Collection\EntityFactory $entityFactory, \Magento\Framework\Filesystem $filesystem)
{
$this->_filesystem = $filesystem;
parent::__construct($entityFactory);
}
/**
* Generate row
*
* @param string $filename
* @return array
*/
protected function _generateRow($filename)
{
$filename = preg_replace('~[/\\\]+~', '/', $filename);
$path = $this->_filesystem->getDirectoryWrite(DirectoryList::MEDIA);
return [
'filename' => $filename,
'basename' => basename($filename),
'mtime' => $path->stat($path->getRelativePath($filename))['mtime']
];
}
}
<?php
namespace Rokanthemes\SlideBanner\Setup;
use Magento\Framework\Setup\InstallDataInterface;
use Magento\Framework\Setup\ModuleContextInterface;
use Magento\Framework\Setup\ModuleDataSetupInterface;
use Magento\Eav\Setup\EavSetupFactory;
use Magento\Eav\Setup\EavSetup;
/**
* @codeCoverageIgnore
*/
class InstallData implements InstallDataInterface{
/**
* {@inheritdoc}
*/
/**
* EAV setup factory
*
* @var EavSetupFactory
*/
private $eavSetupFactory;
/**
* Init
*
* @param EavSetupFactory $eavSetupFactory
*/
public function __construct(EavSetupFactory $eavSetupFactory)
{
$this->eavSetupFactory = $eavSetupFactory;
}
public function install(ModuleDataSetupInterface $setup, ModuleContextInterface $context)
{
/** @var EavSetup $eavSetup */
$eavSetup = $this->eavSetupFactory->create(['setup' => $setup]);
$installer = $setup;
$installer->startSetup();
/**
* Install eav entity types to the eav/entity_type table
*/
$installer->getConnection()->dropTable($installer->getTable('rokanthemes_slider'));
$installer->getConnection()->dropTable($installer->getTable('rokanthemes_slide'));
$table = $installer->getConnection()
->newTable($installer->getTable('rokanthemes_slider'))
->addColumn(
'slider_id',
\Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
10,
['identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true],
'Timer ID'
)
->addColumn(
'slider_identifier',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => false],
'Identifier'
)
->addColumn(
'slider_title',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => false, 'default' => ''],
'Slider title'
)->addColumn(
'slider_status',
\Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
6,
['nullable' => false, 'default'=>1],
'Status'
)->addColumn(
'slider_setting',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => true],
'Setting slider'
)->addColumn(
'storeids',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
50,
['nullable' => true],
'Stores Ids'
)->addColumn(
'slider_styles',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => true],
'Styles'
)->addColumn(
'slider_script',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => true],
'Styles'
)->addColumn(
'slider_template',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => true],
'Template'
)->addColumn(
'created_at',
\Magento\Framework\DB\Ddl\Table::TYPE_TIMESTAMP,
null,
[],
'Creation Time'
)
->addIndex(
'slider_identifier',
['slider_identifier']
)
->setComment('SlideBanner');
$installer->getConnection()
->createTable($table);
$table = $installer->getConnection()
->newTable($installer->getTable('rokanthemes_slide'))
->addColumn(
'slide_id',
\Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
10,
['identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true],
'Slide ID'
)
->addColumn(
'slider_id',
\Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
10,
['nullable' => false],
'Slider ID'
)
->addColumn(
'slide_type',
\Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
6,
['nullable' => false, 'default'=>1],
'Slide Type'
)
->addColumn(
'slide_text',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => true],
'Slide Text'
)->addColumn(
'slide_image',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => true],
'File Name'
)->addColumn(
'slide_link',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => true],
'Link Slide'
)->addColumn(
'slide_status',
\Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
6,
['nullable' => false, 'default' => '1'],
'Timer status'
)
->addColumn(
'slide_position',
\Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
10,
['nullable' => false],
'slide position'
)
->addColumn(
'created_at',
\Magento\Framework\DB\Ddl\Table::TYPE_TIMESTAMP,
null,
[],
'Creation Time'
)
->setComment('Slide item');
$installer->getConnection()
->createTable($table);
$installer->endSetup();
}
}
{
"name": "rokanthemes/module-SlideBanner",
"description": "N/A",
"require": {
"php": "~5.5.0|~5.6.0|~7.0.0",
"rokanthemes/module-RokanBase": "1.0.*"
},
"type": "magento2-module",
"version": "1.0.0",
"license": [
"OSL-3.0",
"AFL-3.0"
],
"autoload": {
"files": [ "registration.php" ],
"psr-4": {
"Rokanthemes\\SlideBanner\\": ""
}
}
}
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../lib/internal/Magento/Framework/Acl/etc/acl.xsd">
<acl>
<resources>
<resource id="Magento_Backend::admin">
<resource id="Rokanthemes_RokanBase::rokanbase" title="Rokanthemes" translate="title" sortOrder="30">
<resource id="Rokanthemes_SlideBanner::slidebanner" title="SlideShow" sortOrder="10">
<resource id="Rokanthemes_SlideBanner::slider" title="Manage Sliders" sortOrder="10" />
<resource id="Rokanthemes_SlideBanner::slide" title="Manage Slider items" sortOrder="10" />
</resource>
</resource>
</resource>
</resources>
</acl>
</config>
<?xml version="1.0"?>
<!--
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Backend:etc/menu.xsd">
<menu>
<add id="Rokanthemes_SlideBanner::slidebanner" title="SlideBanner" module="Rokanthemes_SlideBanner" sortOrder="0" parent="Rokanthemes_RokanBase::rokanbase" resource="Rokanthemes_SlideBanner::slidebanner"/>
<add id="Rokanthemes_SlideBanner::slider" title="Manage Slider" module="Rokanthemes_SlideBanner" sortOrder="0" parent="Rokanthemes_SlideBanner::slidebanner" action="slidebanner/slider" resource="Rokanthemes_SlideBanner::slider"/>
<add id="Rokanthemes_SlideBanner::slide" title="Manage Slider Items" module="Rokanthemes_SlideBanner" sortOrder="30" parent="Rokanthemes_SlideBanner::slidebanner" action="slidebanner/slide" resource="Rokanthemes_SlideBanner::slide"/>
</menu>
</config>
<?xml version="1.0"?>
<!--
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:App/etc/routes.xsd">
<router id="admin">
<route id="slidebanner" frontName="slidebanner">
<module name="Rokanthemes_SlideBanner" before="Magento_Backend" />
</route>
</router>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../lib/internal/Magento/Framework/ObjectManager/etc/config.xsd">
</config>
\ No newline at end of file
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../lib/internal/Magento/Framework/App/etc/routes.xsd">
<router id="standard">
<route id="pricecountdown" frontName="pricecountdown">
<module name="Rokanthemes_PriceCountdown" />
</route>
</router>
</config>
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../lib/internal/Magento/Framework/Module/etc/module.xsd">
<module name="Rokanthemes_SlideBanner" setup_version="1.0.0" />
</config>
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
\Magento\Framework\Component\ComponentRegistrar::register(
\Magento\Framework\Component\ComponentRegistrar::MODULE,
'Rokanthemes_SlideBanner',
__DIR__
);
<?xml version="1.0"?>
<layout xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="../../../../../Magento/Core/etc/layout_single.xsd">
<update handle="slidebanner_slide_edit"/>
</layout>
\ No newline at end of file
<?xml version="1.0"?>
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" layout="admin-2columns-left" xsi:noNamespaceSchemaLocation="../../../../../../../lib/internal/Magento/Framework/View/Layout/etc/page_configuration.xsd">
<head>
<css src="jquery/fileUploader/css/jquery.fileupload-ui.css"/>
</head>
<update handle="editor"/>
<body>
<referenceContainer name="content">
<block class="Rokanthemes\SlideBanner\Block\Adminhtml\Slide\Edit" name="grid_grid_edit"/>
</referenceContainer>
<referenceContainer name="left">
<block class="Rokanthemes\SlideBanner\Block\Adminhtml\Slide\Edit\Tabs" name="grid_grid_edit_tabs"/>
</referenceContainer>
</body>
</page>
\ No newline at end of file
<?xml version="1.0"?>
<layout xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="../../../../../../../lib/internal/Magento/
Framework/View/Layout/etc/layout_generic.xsd">
<update handle="formkey"/>
<container name="root">
<block class="Rokanthemes\SlideBanner\Block\Adminhtml\Slide" name="grid_grid_listing"/>
</container>
</layout>
\ No newline at end of file
<?xml version="1.0"?>
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../lib/internal/Magento/Framework/View/Layout/etc/page_configuration.xsd">
<body>
<referenceContainer name="content">
<block class="Rokanthemes\SlideBanner\Block\Adminhtml\Slide" name="grid_grid_listing"/>
</referenceContainer>
<referenceContainer name="admin.grid.grid.view">
<block class="Magento\Framework\View\Element\Text\ListText" name="grid.bottom.links">
<block class="Magento\Catalog\Block\Adminhtml\Rss\Grid\Link" name="grid.rss.link"/>
</block>
</referenceContainer>
</body>
</page>
\ No newline at end of file
<?xml version="1.0"?>
<layout xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="../../../../../Magento/Core/etc/layout_single.xsd">
<update handle="slidebanner_slide_edit"/>
</layout>
\ No newline at end of file
<?xml version="1.0"?>
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" layout="admin-2columns-left" xsi:noNamespaceSchemaLocation="../../../../../../../lib/internal/Magento/Framework/View/Layout/etc/page_configuration.xsd">
<head>
<css src="jquery/fileUploader/css/jquery.fileupload-ui.css"/>
</head>
<update handle="editor"/>
<body>
<referenceContainer name="content">
<block class="Rokanthemes\SlideBanner\Block\Adminhtml\Slider\Edit" name="grid_grid_edit"/>
</referenceContainer>
<referenceContainer name="left">
<block class="Rokanthemes\SlideBanner\Block\Adminhtml\Slider\Edit\Tabs" name="grid_grid_edit_tabs"/>
</referenceContainer>
</body>
</page>
\ No newline at end of file
<?xml version="1.0"?>
<layout xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="../../../../../../../lib/internal/Magento/
Framework/View/Layout/etc/layout_generic.xsd">
<update handle="formkey"/>
<container name="root">
<block class="Rokanthemes\SlideBanner\Block\Adminhtml\Slider" name="grid_grid_listing"/>
</container>
</layout>
\ No newline at end of file
<?xml version="1.0"?>
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../lib/internal/Magento/Framework/View/Layout/etc/page_configuration.xsd">
<body>
<referenceContainer name="content">
<block class="Rokanthemes\SlideBanner\Block\Adminhtml\Slider" name="grid_grid_listing"/>
</referenceContainer>
<referenceContainer name="admin.grid.grid.view">
<block class="Magento\Framework\View\Element\Text\ListText" name="grid.bottom.links">
<block class="Magento\Catalog\Block\Adminhtml\Rss\Grid\Link" name="grid.rss.link"/>
</block>
</referenceContainer>
</body>
</page>
\ No newline at end of file
<?xml version="1.0"?>
<layout xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="../../../../../../../lib/internal/Magento/
Framework/View/Layout/etc/layout_generic.xsd">
<update handle="formkey"/>
<container name="root">
<block class="Rokanthemes\SlideBanner\Block\Adminhtml\Slider\Edit\Tab\Banner" name="grid_grid_listing"/>
</container>
</layout>
\ No newline at end of file
<?xml version="1.0" encoding="UTF-8"?>
<!--
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<listing xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Ui:etc/ui_configuration.xsd">
<argument name="data" xsi:type="array">
<item name="js_config" xsi:type="array">
<item name="provider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing_data_source</item>
<item name="deps" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing_data_source</item>
</item>
<item name="spinner" xsi:type="string">cms_page_columns</item>
<item name="buttons" xsi:type="array">
<item name="add" xsi:type="array">
<item name="name" xsi:type="string">add</item>
<item name="label" xsi:type="string" translate="true">Add New Page</item>
<item name="class" xsi:type="string">primary</item>
<item name="url" xsi:type="string">*/*/new</item>
</item>
</item>
</argument>
<dataSource name="slidebanner_slider_listing_data_source">
<argument name="dataProvider" xsi:type="configurableObject">
<argument name="class" xsi:type="string">SliderGridDataProvider</argument>
<argument name="name" xsi:type="string">slidebanner_slider_listing_data_source</argument>
<argument name="primaryFieldName" xsi:type="string">page_id</argument>
<argument name="requestFieldName" xsi:type="string">id</argument>
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="update_url" xsi:type="url" path="mui/index/render"/>
</item>
</argument>
</argument>
<argument name="data" xsi:type="array">
<item name="js_config" xsi:type="array">
<item name="component" xsi:type="string">Magento_Ui/js/grid/provider</item>
</item>
</argument>
</dataSource>
<container name="listing_top">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="template" xsi:type="string">ui/grid/toolbar</item>
<item name="stickyTmpl" xsi:type="string">ui/grid/sticky/toolbar</item>
</item>
</argument>
<bookmark name="bookmarks">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="storageConfig" xsi:type="array">
<item name="namespace" xsi:type="string">slidebanner_slider_listing</item>
</item>
</item>
</argument>
</bookmark>
<component name="columns_controls">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="columnsData" xsi:type="array">
<item name="provider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.cms_page_columns</item>
</item>
<item name="component" xsi:type="string">Magento_Ui/js/grid/controls/columns</item>
<item name="displayArea" xsi:type="string">dataGridActions</item>
</item>
</argument>
</component>
<filterSearch name="fulltext">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="provider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing_data_source</item>
<item name="chipsProvider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.listing_top.listing_filters_chips</item>
<item name="storageConfig" xsi:type="array">
<item name="provider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.listing_top.bookmarks</item>
<item name="namespace" xsi:type="string">current.search</item>
</item>
</item>
</argument>
</filterSearch>
<filters name="listing_filters">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="columnsProvider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.cms_page_columns</item>
<item name="storageConfig" xsi:type="array">
<item name="provider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.listing_top.bookmarks</item>
<item name="namespace" xsi:type="string">current.filters</item>
</item>
<item name="templates" xsi:type="array">
<item name="filters" xsi:type="array">
<item name="select" xsi:type="array">
<item name="component" xsi:type="string">Magento_Ui/js/form/element/ui-select</item>
<item name="template" xsi:type="string">ui/grid/filters/elements/ui-select</item>
</item>
</item>
</item>
<item name="childDefaults" xsi:type="array">
<item name="provider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.listing_top.listing_filters</item>
<item name="imports" xsi:type="array">
<item name="visible" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.cms_page_columns.${ $.index }:visible</item>
</item>
</item>
</item>
<item name="observers" xsi:type="array">
<item name="column" xsi:type="string">column</item>
</item>
</argument>
<filterSelect name="store_id">
<argument name="optionsProvider" xsi:type="configurableObject">
<argument name="class" xsi:type="string">Magento\Cms\Ui\Component\Listing\Column\Cms\Options</argument>
</argument>
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="dataScope" xsi:type="string">store_id</item>
<item name="label" xsi:type="string" translate="true">Store View</item>
<item name="captionValue" xsi:type="string">0</item>
</item>
</argument>
</filterSelect>
</filters>
<massaction name="listing_massaction">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="selectProvider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.cms_page_columns.ids</item>
<item name="indexField" xsi:type="string">page_id</item>
</item>
</argument>
<action name="delete">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="type" xsi:type="string">delete</item>
<item name="label" xsi:type="string" translate="true">Delete</item>
<item name="url" xsi:type="url" path="cms/page/massDelete"/>
<item name="confirm" xsi:type="array">
<item name="title" xsi:type="string" translate="true">Delete items</item>
<item name="message" xsi:type="string" translate="true">Are you sure you wan't to delete selected items?</item>
</item>
</item>
</argument>
</action>
<action name="disable">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="type" xsi:type="string">disable</item>
<item name="label" xsi:type="string" translate="true">Disable</item>
<item name="url" xsi:type="url" path="cms/page/massDisable"/>
</item>
</argument>
</action>
<action name="enable">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="type" xsi:type="string">enable</item>
<item name="label" xsi:type="string" translate="true">Enable</item>
<item name="url" xsi:type="url" path="cms/page/massEnable"/>
</item>
</argument>
</action>
<action name="edit">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="type" xsi:type="string">edit</item>
<item name="label" xsi:type="string" translate="true">Edit</item>
<item name="callback" xsi:type="array">
<item name="provider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.cms_page_columns_editor</item>
<item name="target" xsi:type="string">editSelected</item>
</item>
</item>
</argument>
</action>
</massaction>
<paging name="listing_paging">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="storageConfig" xsi:type="array">
<item name="provider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.listing_top.bookmarks</item>
<item name="namespace" xsi:type="string">current.paging</item>
</item>
<item name="selectProvider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.cms_page_columns.ids</item>
</item>
</argument>
</paging>
</container>
<columns name="cms_page_columns">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="storageConfig" xsi:type="array">
<item name="provider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.listing_top.bookmarks</item>
<item name="namespace" xsi:type="string">current</item>
</item>
<item name="editorConfig" xsi:type="array">
<item name="selectProvider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.cms_page_columns.ids</item>
<item name="enabled" xsi:type="boolean">true</item>
<item name="indexField" xsi:type="string">page_id</item>
<item name="clientConfig" xsi:type="array">
<item name="saveUrl" xsi:type="url" path="cms/page/inlineEdit"/>
<item name="validateBeforeSave" xsi:type="boolean">false</item>
</item>
</item>
<item name="childDefaults" xsi:type="array">
<item name="fieldAction" xsi:type="array">
<item name="provider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.cms_page_columns_editor</item>
<item name="target" xsi:type="string">startEdit</item>
<item name="params" xsi:type="array">
<item name="0" xsi:type="string">${ $.$data.rowIndex }</item>
<item name="1" xsi:type="boolean">true</item>
</item>
</item>
<item name="storageConfig" xsi:type="array">
<item name="provider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.listing_top.bookmarks</item>
<item name="root" xsi:type="string">columns.${ $.index }</item>
<item name="namespace" xsi:type="string">current.${ $.storageConfig.root}</item>
</item>
</item>
</item>
</argument>
<selectionsColumn name="ids">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="resizeEnabled" xsi:type="boolean">false</item>
<item name="resizeDefaultWidth" xsi:type="string">55</item>
<item name="indexField" xsi:type="string">page_id</item>
</item>
</argument>
</selectionsColumn>
<column name="page_id">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">textRange</item>
<item name="sorting" xsi:type="string">asc</item>
<item name="label" xsi:type="string" translate="true">ID</item>
</item>
</argument>
</column>
<column name="title">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">text</item>
<item name="editor" xsi:type="array">
<item name="editorType" xsi:type="string">text</item>
<item name="validation" xsi:type="array">
<item name="required-entry" xsi:type="boolean">true</item>
</item>
</item>
<item name="label" xsi:type="string" translate="true">Title</item>
</item>
</argument>
</column>
<column name="identifier">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">text</item>
<item name="editor" xsi:type="array">
<item name="editorType" xsi:type="string">text</item>
<item name="validation" xsi:type="array">
<item name="validate-identifier" xsi:type="boolean">true</item>
</item>
</item>
<item name="label" xsi:type="string" translate="true">URL Key</item>
</item>
</argument>
</column>
<column name="page_layout">
<argument name="data" xsi:type="array">
<item name="options" xsi:type="object">Magento\Cms\Model\Page\Source\PageLayout</item>
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">select</item>
<item name="component" xsi:type="string">Magento_Ui/js/grid/columns/select</item>
<item name="editor" xsi:type="string">select</item>
<item name="dataType" xsi:type="string">select</item>
<item name="label" xsi:type="string" translate="true">Layout</item>
</item>
</argument>
</column>
<column name="store_id" class="Magento\Store\Ui\Component\Listing\Column\Store">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="bodyTmpl" xsi:type="string">ui/grid/cells/html</item>
<item name="sortable" xsi:type="boolean">false</item>
<item name="label" xsi:type="string" translate="true">Store View</item>
</item>
</argument>
</column>
<column name="is_active">
<argument name="data" xsi:type="array">
<item name="options" xsi:type="object">Magento\Cms\Model\Page\Source\IsActive</item>
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">select</item>
<item name="component" xsi:type="string">Magento_Ui/js/grid/columns/select</item>
<item name="editor" xsi:type="string">select</item>
<item name="dataType" xsi:type="string">select</item>
<item name="label" xsi:type="string" translate="true">Status</item>
</item>
</argument>
</column>
<column name="creation_time" class="Magento\Ui\Component\Listing\Columns\Date">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">dateRange</item>
<item name="component" xsi:type="string">Magento_Ui/js/grid/columns/date</item>
<item name="dataType" xsi:type="string">date</item>
<item name="label" xsi:type="string" translate="true">Created</item>
</item>
</argument>
</column>
<column name="update_time" class="Magento\Ui\Component\Listing\Columns\Date">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">dateRange</item>
<item name="component" xsi:type="string">Magento_Ui/js/grid/columns/date</item>
<item name="dataType" xsi:type="string">date</item>
<item name="label" xsi:type="string" translate="true">Modified</item>
</item>
</argument>
</column>
<column name="custom_theme_from" class="Magento\Ui\Component\Listing\Columns\Date">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">dateRange</item>
<item name="component" xsi:type="string">Magento_Ui/js/grid/columns/date</item>
<item name="editor" xsi:type="string">date</item>
<item name="dataType" xsi:type="string">date</item>
<item name="label" xsi:type="string" translate="true">Custom design from</item>
<item name="dateFormat" xsi:type="string">MMM d, y</item>
<item name="visible" xsi:type="boolean">false</item>
</item>
</argument>
</column>
<column name="custom_theme_to" class="Magento\Ui\Component\Listing\Columns\Date">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">dateRange</item>
<item name="component" xsi:type="string">Magento_Ui/js/grid/columns/date</item>
<item name="editor" xsi:type="string">date</item>
<item name="dataType" xsi:type="string">date</item>
<item name="label" xsi:type="string" translate="true">Custom design to</item>
<item name="dateFormat" xsi:type="string">MMM d, y</item>
<item name="visible" xsi:type="boolean">false</item>
</item>
</argument>
</column>
<column name="custom_theme">
<argument name="data" xsi:type="array">
<item name="options" xsi:type="object">Magento\Cms\Model\Page\Source\Theme</item>
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">select</item>
<item name="component" xsi:type="string">Magento_Ui/js/grid/columns/select</item>
<item name="editor" xsi:type="string">select</item>
<item name="dataType" xsi:type="string">select</item>
<item name="label" xsi:type="string" translate="true">Custom Theme</item>
<item name="visible" xsi:type="boolean">false</item>
</item>
</argument>
</column>
<column name="custom_root_template">
<argument name="data" xsi:type="array">
<item name="options" xsi:type="object">Magento\Cms\Model\Page\Source\CustomLayout</item>
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">select</item>
<item name="component" xsi:type="string">Magento_Ui/js/grid/columns/select</item>
<item name="editor" xsi:type="string">select</item>
<item name="dataType" xsi:type="string">select</item>
<item name="label" xsi:type="string" translate="true">Custom Layout</item>
<item name="visible" xsi:type="boolean">false</item>
</item>
</argument>
</column>
<column name="meta_keywords">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">text</item>
<item name="editor" xsi:type="string">text</item>
<item name="label" xsi:type="string" translate="true">Meta Keywords</item>
<item name="visible" xsi:type="boolean">false</item>
</item>
</argument>
</column>
<column name="meta_description">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="filter" xsi:type="string">text</item>
<item name="editor" xsi:type="string">text</item>
<item name="label" xsi:type="string" translate="true">Meta Description</item>
<item name="visible" xsi:type="boolean">false</item>
</item>
</argument>
</column>
<actionsColumn name="actions" class="Magento\Cms\Ui\Component\Listing\Column\PageActions">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="resizeEnabled" xsi:type="boolean">false</item>
<item name="resizeDefaultWidth" xsi:type="string">107</item>
<item name="indexField" xsi:type="string">page_id</item>
</item>
</argument>
</actionsColumn>
</columns>
<container name="sticky">
<argument name="data" xsi:type="array">
<item name="config" xsi:type="array">
<item name="component" xsi:type="string">Magento_Ui/js/grid/sticky/sticky</item>
<item name="toolbarProvider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.listing_top</item>
<item name="listingProvider" xsi:type="string">slidebanner_slider_listing.slidebanner_slider_listing.cms_page_columns</item>
</item>
</argument>
</container>
</listing>
<?php
/**
* Copyright © 2015 Magento. All rights reserved.
* See COPYING.txt for license details.
*/
// @codingStandardsIgnoreFile
if($banners = $block->getBannerCollection()):
$slider = $block->getSlider();
$sliderId = $block->getSliderId();
?>
<div class="wrapper_slider slider_<?php echo $sliderId; ?>">
<div class="row">
<div class="owl">
<?php foreach($banners as $banner){ ?>
<div class="banner_item">
<?php
$html = $block->getImageElement($banner->getSlideImage());
if($link = $banner->getSlideLink())
$html = '<a href="'. $link .'">' . $html . '</a>' ;
echo $html;
?>
<?php if($text = $banner->getSlideText()){
echo $block->getContentText($text);
}
?>
</div>
<?php } ?>
</div>
</div>
</div>
<script>
require([
'jquery',
'mage/mage',
'rokanthemes/owl'
], function ($) {
'use strict';
jQuery(".slider_<?php echo $sliderId; ?> .owl").owlCarousel(
{<?php foreach($slider->getSliderSetting() as $key=>$value)
{
if(in_array($key, array('autoPlay', 'navigation', 'stopOnHover', 'pagination', 'scrollPerPage'))){
$value == 0 ? $value = 'false': '';
$value == 1 ? $value = 'true': '';
}
echo $key . ':' . $value . ',';
} ?>}
);
});
</script>
<?php endif; ?>
<?xml version="1.0"?>
<!--
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" layout="1column" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
<body>
<referenceContainer name="content">
<block class="Magento\Framework\View\Element\Template" name="default_home_page" template="Magento_Cms::default/home.phtml"/>
</referenceContainer>
</body>
</page>
<?xml version="1.0"?>
<!--
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" layout="1column" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
<body>
<referenceContainer name="content">
<block class="Magento\Framework\View\Element\Template" name="default_no_route" template="Magento_Cms::default/no-route.phtml"/>
</referenceContainer>
</body>
</page>
<?xml version="1.0"?>
<!--
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
<body>
<referenceContainer name="content">
<block class="Magento\Framework\View\Element\Template" name="default_home_page" template="Magento_Cms::default/home.phtml"/>
</referenceContainer>
</body>
</page>
<?xml version="1.0"?>
<!--
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
-->
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
<body/>
</page>
<?php
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
?>
<div class="top-content-home">
<div class="container-custom clearfix">
<?php echo $block->getLayout()->createBlock('Magento\Cms\Block\Block')->setBlockId('homepageslider')->toHtml();?>
</div>
</div>
<?php
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
var config = {
deps: [
]
};
?>
There was no 404 CMS page configured or found.
<?php
$layout = $block->getLayout();
?><div class="actions-header-pc hidden-xs">
<?php //echo $layout->getBlock('minicart')?>
</div>
\ No newline at end of file
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
define(['jquery'], function($){
$(function () { // to ensure that code evaluates on page load
$("h4").click(function () {
var dis = $(this).siblings("ul").css("display");
if (dis == "none"){
$(this).siblings("ul").css("display","block");
$(this).children("span").html('^')
}else{
$(this).siblings("ul").css("display","none");
$(this).children("span").html('>')
}
})
});
});
......@@ -553,3 +553,44 @@ ul {
letter-spacing: -1.5px;
line-height: 1;
}
.wrapper_slider {
.banner_item {
position: relative;
img {
position: absolute;
top: 0;
left: 0;
z-index: -1;
}
&:first-child {
img {
position: static;
}
}
}
.owl-wrapper-outer{
.owl-wrapper{
.owl-item{
.banner_item{
img{
width: 100%;
height: auto;
}
}
}
}
}
.owl-theme {
.owl-controls {
.owl-buttons {
.owl-prev {
left: 20px;
}
.owl-next {
right: 20px;
}
}
}
}
}
\ No newline at end of file
<?php declare(strict_types = 1);
namespace PHPStan\PhpDocParser\Ast\PhpDoc;
use PHPStan\PhpDocParser\Ast\NodeAttributes;
use PHPStan\PhpDocParser\Ast\Type\TypeNode;
use function trim;
class AssertTagMethodValueNode implements PhpDocTagValueNode
{
use NodeAttributes;
/** @var TypeNode */
public $type;
/** @var string */
public $parameter;
/** @var string */
public $method;
/** @var bool */
public $isNegated;
/** @var string (may be empty) */
public $description;
public function __construct(TypeNode $type, string $parameter, string $method, bool $isNegated, string $description)
{
$this->type = $type;
$this->parameter = $parameter;
$this->method = $method;
$this->isNegated = $isNegated;
$this->description = $description;
}
public function __toString(): string
{
$isNegated = $this->isNegated ? '!' : '';
return trim("{$this->type} {$isNegated}{$this->parameter}->{$this->method}() {$this->description}");
}
}
<?php declare(strict_types = 1);
namespace PHPStan\PhpDocParser\Ast\PhpDoc;
use PHPStan\PhpDocParser\Ast\NodeAttributes;
use PHPStan\PhpDocParser\Ast\Type\TypeNode;
use function trim;
class AssertTagPropertyValueNode implements PhpDocTagValueNode
{
use NodeAttributes;
/** @var TypeNode */
public $type;
/** @var string */
public $parameter;
/** @var string */
public $property;
/** @var bool */
public $isNegated;
/** @var string (may be empty) */
public $description;
public function __construct(TypeNode $type, string $parameter, string $property, bool $isNegated, string $description)
{
$this->type = $type;
$this->parameter = $parameter;
$this->property = $property;
$this->isNegated = $isNegated;
$this->description = $description;
}
public function __toString(): string
{
$isNegated = $this->isNegated ? '!' : '';
return trim("{$this->type} {$isNegated}{$this->parameter}->{$this->property} {$this->description}");
}
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment