1

I have embedded images in text blocks on my Divi website. I'd like that when the user clicks on the image, the largest/original size of the image opens up in a lightbox (instead of the thumbnail size as stated in the src). I have hundreds of images and therefore would be too time consuming to change the src link on each to the original size url. Could anyone help me on how I can change the src link to point to the largest/original image size and then for it to open in a lightbox upon click? I'm not sure of the JQuery to go about this. I've included below the HTML structure I'm using for each embedded image in the text blocks. I've also included the JQuery snippet I'm currently using. The snippet opens the image in a lightbox but only the thumbnail version (not the largest size possible).

Here are a few examples of the URLs of the images on my site:

  • https://mydomain/wp-content/uploads/2023/01/myimage-235x300.jpg
  • https://mydomain/wp-content/uploads/2023/01/myimage.jpg
  • https://mydomain/wp-content/uploads/2023/01/myimage-1.jpg

HTML:

<div class="dmpro_timeline_item_description">
  <img decoding="async" loading="lazy" src="https://mydomain/wp-content/uploads/2023/01/myimage-235x300.jpg" width="235" height="300"  class="wp-image-2129 alignnone size-medium">
  <br>
  <em>Image caption</em>
</div>

JQuery:

<script>
if ( jQuery('.dmpro_timeline_item_description').length > 0 ) {
        jQuery(".dmpro_timeline_item_description p img").each(function(i, e){
            var img_src = jQuery(this).attr("src");
            var img = jQuery(this).parent().html();
            
            var new_elem = jQuery('<a style="color: inherit;" href="'+img_src+'">'+img+'</a>');
           jQuery(this).parent().html(new_elem);
        }); 
    }
    
    jQuery(document).ready(function($){ 
        $(".dmpro_timeline_item_description p").magnificPopup({
            delegate: 'a',
            type: 'image',        
            closeOnContentClick: true,
            closeBtnInside: false,
            mainClass: 'mfp-no-margins mfp-with-zoom',
            gallery:{
              enabled:false,
            },
            zoom: {
                enabled: true,
                duration: 200
            }
        });
    });

</script>
Lloyd
  • 435
  • 3
  • 12
  • 29

1 Answers1

1

In the snippet below you can see that the width and the height attributes can be toggled.

function toggleLarge(context) {
    if (!context.large) {
        context.large = true;
        context.formerWidth = context.width;
        context.formerHeight = context.height;
        context.removeAttribute("width");
        context.removeAttribute("height");
    } else {
        context.large = false;
        context.width = context.formerWidth;
        context.height = context.formerHeight;
    }
}

for (let img of document.querySelectorAll("img.size-medium")) {
    img.addEventListener('click', function(event) {
        toggleLarge(this);
    });
}
<div class="dmpro_timeline_item_description">
  <img decoding="async" loading="lazy" src="https://www.yourtango.com/sites/default/files/styles/header_slider/public/image_blog/lion-meaning.png?itok=-eB2XSyC" width="235" height="300"  class="wp-image-2129 alignnone size-medium">
  <br>
  <em>Image caption</em>
</div>

If you also need to change the URLs, then you will need to proceed similarly. Since you have not given a sample of large URLs, it's impossible to tell you how to convert the URL to something you did not specify. However, if the "-235x300" part is the problematic, then you can do something like this:

function toggleSrc(context) {
    if (context.large) {
        context.src = context.src.replace(".", "-235x300.");
    } else {
        context.src = context.src.replace("-235x300", "");
    }
}

and call this function in toggleLarge just before the if, passing context. If this is inappropriate to your problem, then you need to provide further information.

EDIT

Initially, for the sake of simplicity, the event listener was defined with the onclick attribute, but I have changed it to be an addEventListener as per Roko C. Buljan's suggestion.

EDIT2

As Roko C. Buljan explained, it's also possible to use forEach instead of a for loop. For those who prefer that syntax, there is another snippet below:

function toggleLarge(context) {
    if (!context.large) {
        context.large = true;
        context.formerWidth = context.width;
        context.formerHeight = context.height;
        context.removeAttribute("width");
        context.removeAttribute("height");
    } else {
        context.large = false;
        context.width = context.formerWidth;
        context.height = context.formerHeight;
    }
}

document.querySelectorAll("img.size-medium").forEach(function(img) {
    img.addEventListener('click', function(event) {
        toggleLarge(this);
    });
});
<div class="dmpro_timeline_item_description">
  <img decoding="async" loading="lazy" src="https://www.yourtango.com/sites/default/files/styles/header_slider/public/image_blog/lion-meaning.png?itok=-eB2XSyC" width="235" height="300"  class="wp-image-2129 alignnone size-medium">
  <br>
  <em>Image caption</em>
</div>

EDIT3

In the snippet below I have implemented the two functions you need based on the comment section's content:

/*
    https://mydomain/wp-content/uploads/2023/01/myimage-235x300.jpg
    https://mydomain/wp-content/uploads/2023/01/myimage.jpg
    https://mydomain/wp-content/uploads/2023/01/myimage-1.jpg
*/

function thumbnailToLarge(input) {
    return input.substring(0, input.lastIndexOf(".")).split("-").filter((item) => (
        !/[0-9]+x.*[0-9]+/g.test(item)
    )).join("-") + input.substring(input.lastIndexOf("."));
}

console.log("Thumbnail to large: " + thumbnailToLarge("https://mydomain/wp-content/uploads/2023/01/myimage-235x300.jpg"));

function largeToThumbnail(input) {
    return input.substring(0, input.lastIndexOf(".")) + "-235x300" + input.substring(input.lastIndexOf("."))
}

console.log("Large to thumbnail " + largeToThumbnail("https://mydomain/wp-content/uploads/2023/01/myimage.jpg"));
console.log("Large to thumbnail " + largeToThumbnail("https://mydomain/wp-content/uploads/2023/01/myimage-1.jpg"));
Lajos Arpad
  • 64,414
  • 37
  • 100
  • 175
  • 1
    Avoid suggesting the use of inline `on` attribute handlers. addEventListener() is the preferred way, better for debugging, and keeping the JS where due, and that's the respective tag or file. – Roko C. Buljan Jan 30 '23 at 00:23
  • @RokoC.Buljan edited my answer, changed it to use `addEventListener` instead of `onclick`. – Lajos Arpad Jan 30 '23 at 00:29
  • 1
    Great! PS: `[document|Element].querySelectorAll("selector")` returns a NodeList which exposes natively a `.forEach()` method prototype. Much cleaner to read `document.querySelectorAll("img.size-medium").forEach((img, i) => {` than `for (let [i, img] of document.querySelectorAll("img.size-medium").entries()) {` – Roko C. Buljan Jan 30 '23 at 00:38
  • 1
    @RokoC.Buljan thanks for making another good point. I still think the loop deserves its own place, but I have also added a `forEach` snippet so the reader can choose the syntax he/she prefers. Thanks for the comments/suggestions. – Lajos Arpad Jan 30 '23 at 00:44
  • O wow, thank you for your solution @LajosArpad. Like you said, the "-235x300" causes the issue. I can’t do a replace like you noted as the dimensions are different for each image on the page (and there are hundreds of them unfortunately!). Would it be possible therefore to automatically swap out the thumbnail url for the original image url (the largest size)? – Lloyd Jan 30 '23 at 12:41
  • @Lloyd it should be possible, but you need to provide a pattern/sample data we can work with. So far I only have one example of thumbnail, not the whole problem-space and I have not seen an example of your large URLs. If you could edit your question, add some sample data/pattern to it and then notify me here, then I could edit my question with further ideas/code. – Lajos Arpad Jan 31 '23 at 10:33
  • Hi @LajosArpad, I've just edited my question with sample image URLs from my site. They either include the thumbnail size at the end, the full size image url (without the thumbnail size at the end) or the full image size with a number at the end indicating the year/sequence etc. Hope this gives more clarity? Thank you – Lloyd Feb 01 '23 at 19:05
  • @Lloyd edited my answer, provided functions to convert thumbnail to large and back. If my answer contributed to a solution, then you might consider accepting it as the correct answer. – Lajos Arpad Feb 01 '23 at 20:40
  • Thank you @LajosArpad for your help with this. Sorry, I should have been clearer before... the sample URLs I provided are just examples of the naming structures. For example, the ones that feature the thumbnail size at the end will include random dimensions (depending on the image size). I therefore have 1920x1080, 972x832, 834x22 etc etc. The ones that include a number at the end (to denote the year or sequence no) have, for example, image-1, image-2020, image-2020-21 etc etc. Hope that makes more sense? – Lloyd Feb 02 '23 at 18:39
  • @Lloyd I had some understanding of your URL format even after your previous comment and have written two functions that may turn out to be helpful. Have you managed to test them with your URLs by any chance? If so, were they doing what you expected? If not, can you provide an example input and the expected output for it that the functions failed to handle properly? Thanks! – Lajos Arpad Feb 03 '23 at 13:13
  • Thanks for your patience with this @LajosArpad. I managed to get a JQuery snippet working (on the most part) that opens the image in a new tab upon clicked (edited my original question to include the code). It doesn't display the full size version though (or in a lightbox). So sorry about this I'm not entirely sure how to integrate your code with mine!? I'm rather new to JavaScript/jQuery :( – Lloyd Feb 05 '23 at 20:25
  • @Lloyd please don't worry about patience, this is a site where professional help out each-other with questions and problems. I was not aware earlier that you are opening a new tab. Also, there are several references in your code to resources we have no access to, so, even though you have provided code chunks, they are not reproducible from the perspective of people who want to help you. Can you provide either a reproducible snippet or a link to your site so we could experiment with your problem? – Lajos Arpad Feb 06 '23 at 10:47
  • Thank you @LajosArpad. Just to clarify therefore, I don't want the images to open in a new tab. They should appear in a lightbox... not sure why that isn't working. I think the best way would be to send you a link to the page itself. The content is quite sensitive so unable to share a link here. Is there a way I can share it with you privately? – Lloyd Feb 06 '23 at 13:17
  • @Lloyd I think we need to keep this public, but you could obfuscate the content, export the page source with obfuscated/changed content so I and others will not see your actual content, but we will see your problem. If you could create a snippet/JSFiddle without your sensitive content, but with your problem being reproducible, that would great. Since you are opening this only in a lightbox, you could change the `src` of your `a` temporarily while the lightbox is opened. This sounds to be a solvable problem, but we definitely need to play around with it in order to solve it. – Lajos Arpad Feb 07 '23 at 17:18
  • So sorry for the delay in responding to you @LajosArpad! I've had other commitments over the last few weeks so couldn't look at this until now. The project has changed slightly so the website is now live and accessible via Google :) The URL to the page that shows the timeline images I need to open in a lightbox can be seen here: bit.ly/timeline_2023. Many thanks. – Lloyd Mar 01 '23 at 23:05
  • @Lloyd thanks for the reply! Let's narrow down the problem. Can you point to an example of your Welsh history site of a picture where this feature should be applied? I think the first visible image (Stonehenge) could be such an example, but I need confirmation from you. Also, can you point out what was the problem when you tried applying the change? Finally: if we could have a JSFiddle where you would have the problem in a reproducible manner, then it would be much easier to me to understand and solve your current problem. – Lajos Arpad Mar 02 '23 at 10:46
  • 1
    So sorry again for my slow reply @LajosArpad! Sorry for not being clear in my previous response, but I would like every image on the following page (bit.ly/timeline_2023) to open/maximise into a lightbox, if possible. I'll try and prepare a JSFiddle asap. I'm not using any JQuery at the moment so I will have to try and implement your code again. – Lloyd Mar 19 '23 at 22:21
  • @Lloyd no worries. I think we will arrive a solution, but your JSFiddle will certainly be needed. – Lajos Arpad Mar 20 '23 at 12:14