Benito Serna Tips and tools for Ruby on Rails developers

A "read-more" behavior truncating with rails truncate helper and Stimulus.js

April 19, 2021

A code sample of a “read-more” behavior using the rails truncate method and Stimulus.js.

The example

Visit example page

The html and css

Your are going to need…

.hide { display: none; }
<div data-controller="read-more"
     data-read-more-full-content-value="This is the full content without truncation"
     data-read-more-hide-class="hide">
  <p data-read-more-target="content">
    This is the truncated....
  </p>
  <button class="hide"
    data-read-more-target="moreButton"
    data-action="read-more#showMore">
    Show more
  </button>
  <button class="hide"
    data-read-more-target="lessButton"
    data-action="read-more#showLess">
    Show less
  </button>
</div>

To truncate the content, you can use the truncate helper.

truncate("Once upon a time in a world far far away")

The javascript

Here you are going to toggle the truncated content and the full content as needed.

class ReadMoreController extends Stimulus.Controller {
  static get targets() {
    return ["content", "moreButton", "lessButton"]
  }

  static get classes() {
    return ["hide"]
  }

  static get values() {
    return { fullContent: String }
  }

  connect() {
    this.truncatedContent = this.contentTarget.textContent.trim();
    this.render()
  }

  render() {
    if (this.truncateContent != this.fullContentValue) {
      this.showLess()
    } else {
      this.hide(this.moreButtonTarget);
      this.hide(this.lessButtonTarget);
    }
  }

  showMore() {
    this.contentTarget.textContent = this.fullContentValue;
    this.hide(this.moreButtonTarget);
    this.show(this.lessButtonTarget);
  }

  showLess() {
    this.contentTarget.textContent = this.truncateContent;
    this.hide(this.lessButtonTarget);
    this.show(this.moreButtonTarget);
  }

  show(target) {
    target.classList.remove(this.hideClass)
  }

  hide(target) {
    target.classList.add(this.hideClass)
  }
}

Other ways of doing it…

If instead of number characters or words you need to truncate your content by number of lines, you can try these examples.

Subscribe to get future posts via email

Here I try to share knowledge and fixes to common problems and struggles for ruby on rails developers, like How to fetch the latest-N-of-each record or How to test that an specific mail was sent or a Capybara cheatsheet. You can see more examples on Most recent posts or all posts.