Read more toggle JS

User
Good people and a great service – enjoyed working with Jordan and the team at DEFT DIGITAL to create a series of new websites to promote our Global Innovation Challenge. I was delighted, both with the creative and the technical implementation. Wouldn't hesitate to recommend to others.

display just below part and then add read more and uplon clicking read more show remaining content and then show show lesst using js of multiple grid
Good people and a great service – enjoyed working with Jordan and the team at DEFT DIGITAL to create a series of new websites to promote our Global Innovation…

Assistant
Here's a simple solution using **HTML**, **CSS**, and **JavaScript** to create a "Read More / Show Less" toggle for multiple testimonials in a grid layout.

### ✅ HTML

<div class="testimonial-grid">
  <div class="testimonial">
    <p class="short-text">
      Good people and a great service - enjoyed working with Jordan and the team at DEFT DIGITAL to create a series of new websites to promote our Global Innovation...
    </p>
    <p class="full-text hidden">
      Good people and a great service - enjoyed working with Jordan and the team at DEFT DIGITAL to create a series of new websites to promote our Global Innovation Challenge. I was delighted, both with the creative and the technical implementation. Wouldn't hesitate to recommend to others.
    </p>
    <button class="toggle-btn">Read more</button>
  </div>
  <!-- Repeat .testimonial for more items -->
</div>

### ✅ CSS

.testimonial-grid {
  display: grid;
  gap: 1.5rem;
  grid-template-columns: repeat(auto-fill, minmax(300px, 1fr));
}

.testimonial {
  border: 1px solid #ccc;
  padding: 1rem;
  border-radius: 8px;
  position: relative;
}

.hidden {
  display: none;
}

.toggle-btn {
  background: none;
  border: none;
  color: #0073aa;
  cursor: pointer;
  padding: 0;
  margin-top: 0.5rem;
}

### ✅ JavaScript

<script>
  document.querySelectorAll('.toggle-btn').forEach(button => {
    button.addEventListener('click', function () {
      const testimonial = this.closest('.testimonial');
      const shortText = testimonial.querySelector('.short-text');
      const fullText = testimonial.querySelector('.full-text');
      
      if (fullText.classList.contains('hidden')) {
        fullText.classList.remove('hidden');
        shortText.classList.add('hidden');
        this.textContent = 'Show less';
      } else {
        fullText.classList.add('hidden');
        shortText.classList.remove('hidden');
        this.textContent = 'Read more';
      }
    });
  });
</script>

You can repeat the `.testimonial` blocks inside `.testimonial-grid` to support multiple testimonials. Each one will behave independently with its own toggle functionality.

Would you like this adapted into a shortcode or widget for WordPress or Elementor?

User
document.addEventListener('DOMContentLoaded', function() {
function toggleReadMore(button, fullText, truncatedText) {
const container = button.closest('.readmore-less-div');
const card = button.closest('.read-more-card');
const description = card.querySelector('.review-text');

if (description) {
description.classList.toggle('expanded');
if (description.classList.contains('expanded')) {
button.textContent = 'Read Less';
description.innerHTML = fullText;
} else {
button.textContent = 'Read More';
description.innerHTML = truncatedText;
}
}
}

const containers = document.querySelectorAll('.readmore-less-div');

containers.forEach(container => {
const cards = container.querySelectorAll('.read-more-card');

cards.forEach(card => {
const description = card.querySelector('.review-text');
if (description) {
const fullText = description.innerHTML.trim();
const truncatedText = fullText.length > 158 ? fullText.substring(0, 158) + '…' : fullText;
description.innerHTML = truncatedText;

const readMoreBtn = card.querySelector('.readmorebtn a');
if (readMoreBtn) {
readMoreBtn.addEventListener('click', function(e) {
e.preventDefault();
toggleReadMore(readMoreBtn, fullText, truncatedText);
});
}
}
});
});
});
dynamically add read more buton also

Assistant
To **dynamically add the "Read More" button** only when the content exceeds a certain length (e.g., 158 characters), you can modify your script like this:

### ✅ Updated JavaScript

document.addEventListener('DOMContentLoaded', function () {
    function toggleReadMore(button, fullText, truncatedText) {
        const card = button.closest('.read-more-card');
        const description = card.querySelector('.review-text');

        if (description) {
            description.classList.toggle('expanded');
            if (description.classList.contains('expanded')) {
                button.textContent = 'Read Less';
                description.innerHTML = fullText;
            } else {
                button.textContent = 'Read More';
                description.innerHTML = truncatedText;
            }
        }
    }

    const containers = document.querySelectorAll('.readmore-less-div');

    containers.forEach(container => {
        const cards = container.querySelectorAll('.read-more-card');

        cards.forEach(card => {
            const description = card.querySelector('.review-text');
            if (description) {
                const fullText = description.innerHTML.trim();
                const truncatedText = fullText.length > 158 ? fullText.substring(0, 158) + '...' : fullText;
                const needsReadMore = fullText.length > 158;

                // Set initial truncated content
                description.innerHTML = truncatedText;

                // Only add button if needed
                if (needsReadMore) {
                    let readMoreContainer = card.querySelector('.readmorebtn');

                    if (!readMoreContainer) {
                        readMoreContainer = document.createElement('div');
                        readMoreContainer.className = 'readmorebtn';
                        card.appendChild(readMoreContainer);
                    }

                    const readMoreBtn = document.createElement('a');
                    readMoreBtn.href = '#';
                    readMoreBtn.textContent = 'Read More';
                    readMoreContainer.appendChild(readMoreBtn);

                    readMoreBtn.addEventListener('click', function (e) {
                        e.preventDefault();
                        toggleReadMore(readMoreBtn, fullText, truncatedText);
                    });
                }
            }
        });
    });
});

### ✅ Optional CSS
Make sure you add some styling for `.readmorebtn` and `.review-text.expanded` if needed:

.readmorebtn a {
  display: inline-block;
  margin-top: 10px;
  color: #0073aa;
  text-decoration: underline;
  cursor: pointer;
}

This script now:
– Truncates long content to 158 characters.
– Dynamically appends a “Read More” button **only if needed**.
– Toggles between full and truncated content when clicked.

Let me know if you also want animation on expand/collapse!

User
also whe click read more show read less
Assistant
Great! You're almost there — the **updated script I shared already switches the button text** between “Read More” and “Read Less” when clicked. But just to make it **100% clear**, here’s the **fully working and complete setup** with everything you asked for:

### ✅ HTML Structure
(Use this basic format for each review card.)

<div class="readmore-less-div">
  <div class="read-more-card">
    <div class="review-text">
      Good people and a great service - enjoyed working with Jordan and the team at DEFT DIGITAL to create a series of new websites to promote our Global Innovation Challenge. I was delighted, both with the creative and the technical implementation. Wouldn't hesitate to recommend to others.
    </div>
    <!-- Button will be added dynamically -->
  </div>
</div>

### ✅ CSS (for optional styling)

.review-text {
  transition: all 0.3s ease;
}

.readmorebtn a {
  display: inline-block;
  margin-top: 10px;
  color: #0073aa;
  text-decoration: underline;
  cursor: pointer;
}

### ✅ JavaScript
This version **dynamically adds the button**, toggles the text to **"Read Less" when expanded**, and **"Read More" when collapsed**.

document.addEventListener('DOMContentLoaded', function () {
    function toggleReadMore(button, fullText, truncatedText) {
        const card = button.closest('.read-more-card');
        const description = card.querySelector('.review-text');

        if (description) {
            const isExpanded = description.classList.toggle('expanded');
            description.innerHTML = isExpanded ? fullText : truncatedText;
            button.textContent = isExpanded ? 'Read Less' : 'Read More';
        }
    }

    const containers = document.querySelectorAll('.readmore-less-div');

    containers.forEach(container => {
        const cards = container.querySelectorAll('.read-more-card');

        cards.forEach(card => {
            const description = card.querySelector('.review-text');
            if (description) {
                const fullText = description.innerHTML.trim();
                const truncatedText = fullText.length > 158 ? fullText.substring(0, 158) + '...' : fullText;
                const needsReadMore = fullText.length > 158;

                // Set initial truncated content
                description.innerHTML = truncatedText;

                if (needsReadMore) {
                    let readMoreContainer = card.querySelector('.readmorebtn');

                    if (!readMoreContainer) {
                        readMoreContainer = document.createElement('div');
                        readMoreContainer.className = 'readmorebtn';
                        card.appendChild(readMoreContainer);
                    }

                    const readMoreBtn = document.createElement('a');
                    readMoreBtn.href = '#';
                    readMoreBtn.textContent = 'Read More';
                    readMoreContainer.appendChild(readMoreBtn);

                    readMoreBtn.addEventListener('click', function (e) {
                        e.preventDefault();
                        toggleReadMore(readMoreBtn, fullText, truncatedText);
                    });
                }
            }
        });
    });
});

Let me know if you want to add a **fade animation** or **slide toggle effect** too. I can help with that next.

User
put read/hide button at left side
Assistant
To place the **"Read More / Read Less" button on the left side** of the container (instead of default right or centered), you just need to adjust the CSS for `.readmorebtn`.

### ✅ Updated CSS for Left-Aligned Button

.readmorebtn {
  text-align: left; /* Align the button container to the left */
  margin-top: 10px;
}

.readmorebtn a {
  display: inline-block;
  color: #0073aa;
  text-decoration: underline;
  cursor: pointer;
}

### ✅ Result

The button will now:
– Be added dynamically.
– Appear **only if the text is long enough**.
– Be aligned to the **left** side of each `.read-more-card`.

No need to change the JS if you're already using the version from above — it works seamlessly with this styling.

Let me know if you'd like to position it *under the text block* with padding, or floated inline with the text!

Leave a Comment

Your email address will not be published. Required fields are marked *