I am learning Shopify development. I wonder how can I make this code fragment less verbose, to follow DRY rule. I render product list with a featured image and check if a product has a second image. If so, then I also render second image and use it for a hover functionality. This is my code:
<ul class="homepage-products">
{% for product in collections.homepage.products %}
{% liquid
assign featuredImage = product.featured_image
assign hoverImage = product.images[1]
%}
<li class="homepage-products-li">
<h2 class="homepage-products-title">{{ product.title }}</h2>
<a class="homepage-products-a" href="{{ product.url }}">
<img
class="homepage-products-image"
srcset="
{{ featuredImage | image_url: width: 300 }} 300w,
{{ featuredImage | image_url: width: 500 }} 500w,
{{ featuredImage | image_url: width: 700 }} 700w,
{{ featuredImage | image_url: width: 900 }} 900w,
{{ featuredImage | image_url: width: 1000 }} 1000w,
{{ featuredImage | image_url: width: 1445 }} 1445w,
{{ featuredImage | image_url: width: 1680 }} 1680w,
{{ featuredImage | image_url: width: 2048 }} 2048w,
{{ featuredImage | image_url: width: 2200 }} 2200w,
{{ featuredImage | image_url: width: 2890 }} 2890w,
{{ featuredImage | image_url: width: 4096 }} 4096w,"
src="{{ featuredImage | image_url }}"
alt="{{product.title}}"
width="{{featuredImage.width}}"
height="{{featuredImage.height}}" />
{% if hoverImage != null %}
<img
class="homepage-products-hover-image"
srcset="
{{ hoverImage | image_url: width: 300 }} 300w,
{{ hoverImage | image_url: width: 500 }} 500w,
{{ hoverImage | image_url: width: 700 }} 700w,
{{ hoverImage | image_url: width: 900 }} 900w,
{{ hoverImage | image_url: width: 1000 }} 1000w,
{{ hoverImage | image_url: width: 1445 }} 1445w,
{{ hoverImage | image_url: width: 1680 }} 1680w,
{{ hoverImage | image_url: width: 2048 }} 2048w,
{{ hoverImage | image_url: width: 2200 }} 2200w,
{{ hoverImage | image_url: width: 2890 }} 2890w,
{{ hoverImage | image_url: width: 4096 }} 4096w,"
src="{{ hoverImage | image_url }}"
alt="{{product.title}}"
width="{{hoverImage.width}}"
height="{{hoverImage.height}}" />
{% else %}
<img
class="homepage-products-hover-image"
srcset="
{{ featuredImage | image_url: width: 300 }} 300w,
{{ featuredImage | image_url: width: 500 }} 500w,
{{ featuredImage | image_url: width: 700 }} 700w,
{{ featuredImage | image_url: width: 900 }} 900w,
{{ featuredImage | image_url: width: 1000 }} 1000w,
{{ featuredImage | image_url: width: 1445 }} 1445w,
{{ featuredImage | image_url: width: 1680 }} 1680w,
{{ featuredImage | image_url: width: 2048 }} 2048w,
{{ featuredImage | image_url: width: 2200 }} 2200w,
{{ featuredImage | image_url: width: 2890 }} 2890w,
{{ featuredImage | image_url: width: 4096 }} 4096w,"
src="{{ featuredImage | image_url }}"
alt="{{product.title}}"
width="{{featuredImage.width}}"
height="{{featuredImage.height}}" />
{% endif %}
</a>
</li>
{% endfor %}
</ul>
I was thinking about using a snippet or making conditional rendering more simple like "? :" kind of conditional rendering, that JS has, but I don't know how to make it work in Liquid.
This is completely untested, so you might find a typo or two, but this gives you a general idea about how to effectively make Liquid a little bit less verbose. It will always be pretty long and ugly though.
{% assign sizes = '500,700,900,1000,1445,1680,2048,2200,2890,4096' | split: ',' %}
{% capture feature_sizes %}
{% for size in sizes %}
,{{ featuredImage | image_url: width: size }} {{ size }}w
{% endfor %}
{% endcapture %}
{% capture feature_img %}
<img class="homepage-products-image" srcset="{{ feature_sizes | remove_first: ',' }}" src="{{ featuredImage | image_url }}" alt="{{ product.title }}" width="{{ featuredImage.width }}" height="{{ featuredImage.height }}" />
{% endcapture %}
{% if hoverImage %}
{% capture hover_sizes %}
{% for size in sizes %}
,{{ hoverImage | image_url: width: size }} {{ size }}w
{% endfor %}
{% endcapture %}
{% capture hover_img %}
<img class="homepage-products-hover-image" srcset="{{ hover_sizes | remove_first: ',' }}" src="{{ hoverImage | image_url }}" alt="{{ product.title }}" width="{{ hoverImage.width }}" height="{{ hoverImage.height }}" />
{% endcapture %}
{% endif %}
<li class="homepage-products-li">
<h2 class="homepage-products-title">{{ product.title }}</h2>
<a class="homepage-products-a" href="{{ product.url }}">
{{ feature_img }}
{% if hoverImage %}
{{ hover_img }}
{% else %}
{{ feature_img | replace: 'homepage-products-image', 'homepage-products-hover-image' }}
{% endif %}
...