How to implement lazy loading in checkout cart page ?
2 Answers
@KGR In Weltpixel we dont have the feature for cart page. In that module, We have lazy load features like catalog page,search page and not cart page.
I was used proto theme.
etc/frontend/di.xml
<preference for="Magento\Catalog\Block\Product\ImageFactory" type="Vendor\Module\Block\Product\ImageFactory" />
Block/Product/ImageFactory.php
<?php namespace Expedux\Checkout\Block\Product;
use Magento\Catalog\Block\Product\Image as ImageBlock;
use Magento\Catalog\Model\View\Asset\ImageFactory as AssetImageFactory;
use Magento\Catalog\Model\Product;
use Magento\Catalog\Model\Product\Image\ParamsBuilder;
use Magento\Catalog\Model\View\Asset\PlaceholderFactory;
use Magento\Framework\ObjectManagerInterface;
use Magento\Framework\View\ConfigInterface;
use Magento\Catalog\Helper\Image as ImageHelper;
/**
* Create imageBlock from product and view.xml
*/
class ImageFactory extends \Magento\Catalog\Block\Product\ImageFactory
{
/**
* @var ConfigInterface
*/
private $presentationConfig;
/**
* @var AssetImageFactory
*/
private $viewAssetImageFactory;
/**
* @var ParamsBuilder
*/
private $imageParamsBuilder;
/**
* @var ObjectManagerInterface
*/
private $objectManager;
/**
* @var PlaceholderFactory
*/
private $viewAssetPlaceholderFactory;
/**
* @param ObjectManagerInterface $objectManager
* @param ConfigInterface $presentationConfig
* @param AssetImageFactory $viewAssetImageFactory
* @param PlaceholderFactory $viewAssetPlaceholderFactory
* @param ParamsBuilder $imageParamsBuilder
*
*/
public function __construct(
ObjectManagerInterface $objectManager,
ConfigInterface $presentationConfig,
AssetImageFactory $viewAssetImageFactory,
PlaceholderFactory $viewAssetPlaceholderFactory,
ParamsBuilder $imageParamsBuilder
) {
$this->objectManager = $objectManager;
$this->presentationConfig = $presentationConfig;
$this->viewAssetPlaceholderFactory = $viewAssetPlaceholderFactory;
$this->viewAssetImageFactory = $viewAssetImageFactory;
$this->imageParamsBuilder = $imageParamsBuilder;
}
/**
* Retrieve image custom attributes for HTML element
*
* @param array $attributes
* @return string
*/
private function getStringCustomAttributes(array $attributes): string
{
$result = [];
foreach ($attributes as $name => $value) {
$result[] = $name . '="' . $value . '"';
}
return !empty($result) ? implode(' ', $result) : '';
}
/**
* Retrieve image class for HTML element
*
* @param array $attributes
* @return string
*/
private function getClass(array $attributes): string
{
return $attributes['class'] ?? 'product-image-photo';
}
/**
* Calculate image ratio
*
* @param int $width
* @param int $height
* @return float
*/
private function getRatio(int $width, int $height): float
{
if ($width && $height) {
return $height / $width;
}
return 1.0;
}
/**
* Get image label
*
* @param Product $product
* @param string $imageType
* @return string
*/
private function getLabel(Product $product, string $imageType): string
{
$label = $product->getData($imageType . '_' . 'label');
if (empty($label)) {
$label = $product->getName();
}
return (string) $label;
}
/**
* Create image block from product
*
* @param Product $product
* @param string $imageId
* @param array|null $attributes
* @return ImageBlock
*/
public function create(Product $product, string $imageId, array $attributes = null): ImageBlock
{
$viewImageConfig = $this->presentationConfig->getViewConfig()->getMediaAttributes(
'Magento_Catalog',
ImageHelper::MEDIA_TYPE_CONFIG_NODE,
$imageId
);
$imageMiscParams = $this->imageParamsBuilder->build($viewImageConfig);
$originalFilePath = $product->getData($imageMiscParams['image_type']);
if ($originalFilePath === null || $originalFilePath === 'no_selection') {
$imageAsset = $this->viewAssetPlaceholderFactory->create(
[
'type' => $imageMiscParams['image_type']
]
);
} else {
$imageAsset = $this->viewAssetImageFactory->create(
[
'miscParams' => $imageMiscParams,
'filePath' => $originalFilePath,
]
);
}
$ratioWidth = $imageMiscParams['image_width'] ? intval($imageMiscParams['image_width']) : 0;
$ratioHeight = $imageMiscParams['image_height'] ? intval($imageMiscParams['image_height']) : 0;
$data = [
'data' => [
'template' => 'Vendor_Module::product/image_with_borders.phtml',
'image_url' => $imageAsset->getUrl(),
'width' => $imageMiscParams['image_width'],
'height' => $imageMiscParams['image_height'],
'label' => $this->getLabel($product, $imageMiscParams['image_type']),
'ratio' => $this->getRatio($ratioWidth, $ratioHeight),
'custom_attributes' => $this->getStringCustomAttributes($attributes),
'class' => $this->getClass($attributes),
'product_id' => $product->getId()
],
];
return $this->objectManager->create(ImageBlock::class, $data);
}
}
view/frontend/templates/product/image_with_borders.phtml
<?php
/**
* Copyright © Magento, Inc. All rights reserved.
* See COPYING.txt for license details.
*/
?>
<?php /** @var $block \Magento\Catalog\Block\Product\Image */ ?>
<span class="product-image-container"
style="width:<?= $block->escapeHtmlAttr($block->getWidth()) ?>px;">
<span class="product-image-wrapper"
style="padding-bottom: <?= ($block->getRatio() * 100) ?>%;">
<img class="porto-lazyload <?= $block->escapeHtmlAttr($block->getClass()) ?>"
<?= $block->escapeHtmlAttr($block->getCustomAttributes()) ?>
data-src="<?= $block->escapeUrl($block->getImageUrl()) ?>"
max-width="<?= $block->escapeHtmlAttr($block->getWidth()) ?>"
max-height="<?= $block->escapeHtmlAttr($block->getHeight()) ?>"
alt="<?= /* @noEscape */ $block->stripTags($block->getLabel(), null, true) ?>"/></span>
</span>