12

I am needing to create a show more/less text function, but with just JavaScript and HTML.. I can't use any additional libraries such as jQuery and it can't be done with CSS. The sample code I have added displays the 'more' text, but not the 'less'.

If someone could point me in the right direction, it would be much appreciated.

I've spent the majority of the day frying my brain over this, as its clearly not the modern way to do it, however, my HTML is:

<html>
<head>
<script type="text/javascript" src="moreless.js"></script>
</head>

<body>
Lorem ipsum dolor sit amet
<p>

<p id="textarea"><!-- This is where I want to additional text--></div>
</p>

<a onclick="showtext('text')" href="javascript:void(0);">See More</a>
<p>
Here is some more text 
</body>
</html>

and my JavaScript is (moreless.js):

function showtext()
{
var text="Here is some text that I want added to the HTML file";
document.getElementById("textarea").innerHTML=text;
}
Conrad M
  • 203
  • 1
  • 3
  • 11
  • *Why* do you need to do it that way? – Pointy Dec 23 '13 at 01:02
  • The answers will differ pending more detail of your requirements. If your text is going to be static and not repeated elsewhere. You could toggle the `display` like in @akhikhl answer. This is probably requires the least amount of code? – Mal Dec 23 '13 at 01:42

12 Answers12

12

My answer is similar but different, there are a few ways to achieve toggling effect. I guess it depends on your circumstance. This may not be the best way for you in the end.

The missing piece you've been looking for is to create an if statement. This allows for you to toggle your text.

More on if statements here.

JSFiddle: http://jsfiddle.net/8u2jF/

Javascript:

var status = "less";

function toggleText()
{
    var text="Here is some text that I want added to the HTML file";

    if (status == "less") {
        document.getElementById("textArea").innerHTML=text;
        document.getElementById("toggleButton").innerText = "See Less";
        status = "more";
    } else if (status == "more") {
        document.getElementById("textArea").innerHTML = "";
        document.getElementById("toggleButton").innerText = "See More";
        status = "less"
    }
}
Mal
  • 580
  • 4
  • 13
6

With some HTML changes, you can absolutely achieve this with CSS:

Lorem ipsum dolor sit amet
<p id="textarea">
    <!-- This is where I want to additional text-->
    All that delicious text is in here!
</p>
<!-- the show/hide controls inside of the following
     list, for ease of selecting with CSS -->
<ul class="controls">
    <li class="show"><a href="#textarea">Show</a></li>
    <li class="hide"><a href="#">Hide</a></li>
</ul>

<p>Here is some more text</p>

Coupled with the CSS:

#textarea {
    display: none; /* hidden by default */
}

#textarea:target {
    display: block; /* shown when a link targeting this id is clicked */
}

#textarea + ul.controls {
    list-style-type: none; /* aesthetics only, adjust to taste, irrelevant to demo */
}

/* hiding the hide link when the #textarea is not targeted,
   hiding the show link when it is selected: */
#textarea + ul.controls .hide,
#textarea:target + ul.controls .show {
    display: none;
}

/* Showing the hide link when the #textarea is targeted,
   showing the show link when it's not: */
#textarea:target + ul.controls .hide,
#textarea + ul.controls .show {
    display: inline-block;
}

JS Fiddle demo.

Or, you could use a label and an input of type="checkbox":

Lorem ipsum dolor sit amet
<input id="textAreaToggle" type="checkbox" />
<p id="textarea">
    <!-- This is where I want to additional text-->
    All that delicious text is in here!
</p>
<label for="textAreaToggle">textarea</label>

<p>Here is some more text</p>

With the CSS:

#textarea {
    /* hide by default: */
    display: none;
}

/* when the checkbox is checked, show the neighbouring #textarea element: */
#textAreaToggle:checked + #textarea {
    display: block;
}

/* position the checkbox off-screen: */
input[type="checkbox"] {
    position: absolute;
    left: -1000px;
}

/* Aesthetics only, adjust to taste: */
label {
    display: block;
}

/* when the checkbox is unchecked (its default state) show the text
   'Show ' in the label element: */
#textAreaToggle + #textarea + label::before {
    content: 'Show ';
}

/* when the checkbox is checked 'Hide ' in the label element; the
   general-sibling combinator '~' is required for a bug in Chrome: */
#textAreaToggle:checked ~ #textarea + label::before {
    content: 'Hide ';
}

JS Fiddle demo.

David Thomas
  • 249,100
  • 51
  • 377
  • 410
  • This is interesting! I'd never heard of `:target` in CSS before. Cool. – Ryan Mar 11 '17 at 00:34
  • Great CSS-only solution, except wouldn't really work if there are `n` distinct textarea elements on a page that need to toggled between `hide` and `show` – Hassan Baig Jul 07 '19 at 16:31
1

Try to toggle height.

function toggleTextArea()
{
  var limitedHeight = '40px';
  var targetEle = document.getElementById("textarea");
  targetEle.style.height = (targetEle.style.height === '') ? limitedHeight : '';
}
shawnzhu
  • 7,233
  • 4
  • 35
  • 51
  • 1
    This almost worked for me. I had to change the last instruction to `targetEle.style.height = (targetEle.style.height == limitedHeight) ? 'initial' : limitedHeight;` – Gjaa Sep 07 '19 at 17:54
1

This is my pure HTML & Javascript solution:

var setHeight = function (element, height) {
    if (!element) {;
        return false;
    }
    else {
        var elementHeight = parseInt(window.getComputedStyle(element, null).height, 10),
        toggleButton = document.createElement('a'),
        text = document.createTextNode('...Show more'),
        parent = element.parentNode;

        toggleButton.src = '#';
        toggleButton.className = 'show-more';
        toggleButton.style.float = 'right';
        toggleButton.style.paddingRight = '15px';
        toggleButton.appendChild(text);

        parent.insertBefore(toggleButton, element.nextSibling);

        element.setAttribute('data-fullheight', elementHeight);
        element.style.height = height;
        return toggleButton;
    }
}

var toggleHeight = function (element, height) {
    if (!element) {
        return false;
    }
    else {
        var full = element.getAttribute('data-fullheight'),
        currentElementHeight = parseInt(element.style.height, 10);

        element.style.height = full == currentElementHeight ? height : full + 'px';
    }
}

var toggleText = function (element) {
    if (!element) {
        return false;
    }
    else {
        var text = element.firstChild.nodeValue;
        element.firstChild.nodeValue = text == '...Show more' ? '...Show less' : '...Show more';
    }
}


var applyToggle = function(elementHeight){
    'use strict';
    return function(){
        toggleHeight(this.previousElementSibling, elementHeight);
        toggleText(this);
    }
}


var modifyDomElements = function(className, elementHeight){
    var elements = document.getElementsByClassName(className);
    var toggleButtonsArray = [];


    for (var index = 0, arrayLength = elements.length; index < arrayLength; index++) {
        var currentElement = elements[index];
        var toggleButton = setHeight(currentElement, elementHeight);
        toggleButtonsArray.push(toggleButton);
    }

    for (var index=0, arrayLength=toggleButtonsArray.length; index<arrayLength; index++){
        toggleButtonsArray[index].onclick = applyToggle(elementHeight);
    }
}

You can then call modifyDomElements function to apply text shortening on all the elements that have shorten-text class name. For that you would need to specify the class name and the height that you would want your elements to be shortened to:

modifyDomElements('shorten-text','50px'); 

Lastly, in your your html, just set the class name on the element you would want your text to get shorten:

<div class="shorten-text">Your long text goes here...</div>
Hamid Tavakoli
  • 4,567
  • 1
  • 33
  • 34
1

I hope this helps you. Here is the functionality:

  • When text characters is less than or equal to 12. Then it displays the whole text and also does not display the more/less button
  • When text characters is more than 12. Displays only 12 characters of the text and also a More button which when pressed, shows the whole text.
  • When the More button is pressed the button changes to Less

Read more string manipulation in w3schools: String Manipulation or Mozila: String Manipulation

var startStatus = "less";

function toggleText() {
  var text = "Here is the text that I want to play around with";

  if (text.length > 12) {
    if (startStatus == "less") {
      document.getElementById("textArea").innerHTML = `${text.substring(0, 12)}...`;
      document.getElementById("more|less").innerText = "More";
      startStatus = "more";
    } else if (startStatus == "more") {
      document.getElementById("textArea").innerHTML = text;
      document.getElementById("more|less").innerText = "Less";
      startStatus = "less";
    }
  } else {
    document.getElementById("textArea").innerHTML = text;
  }
}

toggleText();
<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8" />
  <meta http-equiv="X-UA-Compatible" content="IE=edge" />
  <meta name="viewport" content="width=device-width, initial-scale=1.0" />
  <title>Document</title>
</head>

<body>
  <div>
    <p id="textArea">
      <!-- This is where i want text displayed-->
    </p>
    <span><a
          id="more|less"
          onclick="toggleText();"
          href="javascript:void(0);"
        ></a
      ></span>
  </div>
</body>

</html>
Hik Hik
  • 41
  • 5
0

This should resolve your problem:

function toggleSeeMore() {
    if(document.getElementById("textarea").style.display == 'none') {
        document.getElementById("textarea").style.display = 'block';
        document.getElementById("seeMore").innerHTML = 'See less';
    }
    else {
        document.getElementById("textarea").style.display = 'none';
        document.getElementById("seeMore").innerHTML = 'See more';        
    }
}

The complete working example is here: http://jsfiddle.net/akhikhl/zLA5K/

akhikhl
  • 2,552
  • 18
  • 23
0

Hope this Code you are looking for HTML:

            <div class="showmore">
                <div class="shorten_txt">
                    <h4> #@item.Title</h4>
                    <p>Your Text Your Text Your Text Your Text Your Text Your Text Your Text Your Text Your Text Your Text Your Text Your Text Your Text Your Text Your Text Your Text Your Text </p>
                </div>
            </div>

SCRIPT:

    var showChar = 100;
    var ellipsestext = "[...]";
    $('.showmore').each(function () {
        $(this).find('.shorten_txt p').addClass('more_p').hide();
        $(this).find('.shorten_txt p:first').removeClass('more_p').show();
        $(this).find('.shorten_txt ul').addClass('more_p').hide();
        //you can do this above with every other element
        var teaser = $(this).find('.shorten_txt p:first').html();
        var con_length = parseInt(teaser.length);
        var c = teaser.substr(0, showChar);
        var h = teaser.substr(showChar, con_length - showChar);
        var html = '<span class="teaser_txt">' + c + '<span class="moreelipses">' + ellipsestext +
        '</span></span><span class="morecontent_txt">' + h
        + '</span>';
        if (con_length > showChar) {
            $(this).find(".shorten_txt p:first").html(html);
            $(this).find(".shorten_txt p:first span.morecontent_txt").toggle();
        }
    });
    $(".showmore").click(function () {
        if ($(this).hasClass("less")) {
            $(this).removeClass("less");
        } else {
            $(this).addClass("less");
        }
        $(this).find('.shorten_txt p:first span.moreelipses').toggle();
        $(this).find('.shorten_txt p:first span.morecontent_txt').toggle();
        $(this).find('.shorten_txt .more_p').toggle();
        return false;
    });
DropAndTrap
  • 1,538
  • 16
  • 24
0
 <script type="text/javascript">
     function showml(divId,inhtmText) 
     {  
        var x = document.getElementById(divId).style.display; 

        if(x=="block")
        {
          document.getElementById(divId).style.display = "none";
          document.getElementById(inhtmText).innerHTML="Show More...";
        }
       if(x=="none")
       {
          document.getElementById(divId).style.display = "block";
          document.getElementById(inhtmText).innerHTML="Show Less";
        }
     }
</script>

 <p id="show_more1" onclick="showml('content1','show_more1')" onmouseover="this.style.cursor='pointer'">Show More...</p>

 <div id="content1" style="display: none; padding: 16px 20px 4px; margin-bottom: 15px; background-color: rgb(239, 239, 239);">
 </div>

if more div use like this change only 1 to 2

<p id="show_more2" onclick="showml('content2','show_more2')" onmouseover="this.style.cursor='pointer'">Show More...</p>

 <div id="content2" style="display: none; padding: 16px 20px 4px; margin-bottom: 15px; background-color: rgb(239, 239, 239);">
 </div>

demo jsfiddle

0

I'm not an expert, but I did a lot of looking to implement this for myself. I found something different, but modified it to accomplish this. It's really quite simple:

The function takes two arguments, a div containing only the words "show more" [or whatever] and a div containing the originally hidden text and the words "show less." The function displays the one div and hides the other.

NOTE: If more than one show/hide on page, assign different ids to divs Colors can be changed

<p>Here is text that is originally displayed</p>

<div id="div1">
<p style="color:red;" onclick="showFunction('div2','div1')">show more</p></div>
<div id="div2" style="display:none">

<p>Put expanded text here</p>

<p style="color:red;" onclick="showFunction('div1','div2')">show less</p></div>

<p>more text</p>

Here is the Script:

<script>
function showFunction(diva, divb) {
    var x = document.getElementById(diva);
    var y = document.getElementById(divb);
          x.style.display = 'block';
          y.style.display = 'none';
}
</script>
0

You can also use details HTML tag which does the work for you.

<details>
  <summary>Epcot Center</summary>
  <p>Epcot is a theme park at Walt Disney World Resort featuring exciting attractions, international pavilions, award-winning fireworks and seasonal special events.</p>
</details>

Source W3CSchool

Xfox
  • 174
  • 2
  • 10
0

Here is another way to do it.

<!DOCTYPE html>
<html>
   <head>
      <style>
         .url-container {
         white-space: nowrap;
         overflow: hidden;
         text-overflow: ellipsis;
         }
         .show-more {
         display: none;
         }
         .show-less {
         display: none;
         }
      </style>
      <script>
         function toggleUrl() {
             var urlContainer = document.getElementById("url-container");
             var isTruncated = urlContainer.classList.toggle("truncated");
             var showMoreButton = document.getElementById("show-more");
             var showLessButton = document.getElementById("show-less");
             
             showMoreButton.style.display = isTruncated ? "inline" : "none";
             showLessButton.style.display = isTruncated ? "none" : "inline";
             
             if (isTruncated) {
                 urlContainer.innerText = urlContainer.getAttribute("data-truncated-url");
             } else {
                 urlContainer.innerText = urlContainer.getAttribute("data-full-url");
             }
         }
         
         document.addEventListener("DOMContentLoaded", function() {
             var urlContainer = document.getElementById("url-container");
             var urlText = urlContainer.innerText;
             
             if (urlText.length > 10) {
                 var truncatedUrl = urlText.substring(0, 10) + "...";
                 urlContainer.setAttribute("data-full-url", urlText);
                 urlContainer.setAttribute("data-truncated-url", truncatedUrl);
                 urlContainer.innerText = truncatedUrl;
                 urlContainer.classList.add("truncated");
                 document.getElementById("show-more").style.display = "inline";
             }
         });
      </script>
   </head>
   <body>
      <div id="url-container" class="url-container">
         <p>https://www.example.com/very/long/url/that/you/want/to/show/hide</p>
      </div>
      <button id="show-more" class="show-more" onclick="toggleUrl()">Show more</button>
      <button id="show-less" class="show-less" onclick="toggleUrl()">Show less</button>
   </body>
</html>
Vijay
  • 558
  • 6
  • 22
0

Try this approach, more styled:

document.querySelector(".expand").addEventListener("click", () => {
    document.querySelector(".container").classList.add("opened");
  document.querySelector(".show-more-container").remove(); // if you want to clean
});
.container {
  width: 300px;
}

.text-content {
  max-height: 100px;
  overflow: hidden;
}

.show-more-container {
  background: linear-gradient(0deg, rgba(255,255,255,1) 30%, rgba(255,255,255,0) 100%);
  margin-top: -40px;
  height: 40px;
  padding: 5px;
  text-align: center;
  z-index: 2;
  position: relative;
}

.container.opened .show-more-container {
  display: none;
}

.container.opened .text-content {
    max-height: initial;
    /** max-height: 99999rem; some old browsers? */
}
<div class="container">
  <div class="text-content">
    Lorem Ipsum es simplemente el texto de relleno de las imprentas y archivos de texto. Lorem Ipsum ha sido el texto de relleno estándar de las industrias desde el año 1500, cuando un impresor (N. del T. persona que se dedica a la imprenta) desconocido usó una galería de textos y los mezcló de tal manera que logró hacer un libro de textos especimen. No sólo sobrevivió 500 años, sino que tambien ingresó como texto de relleno en documentos electrónicos, quedando esencialmente igual al original. Fue popularizado en los 60s con la creación de las hojas "Letraset", las cuales contenian pasajes de Lorem Ipsum, y más recientemente con software de autoedición, como por ejemplo Aldus PageMaker, el cual incluye versiones de Lorem Ipsum.
  </div>
  <div class="show-more-container">
    <button class="expand">
      Show more
    </button>
  </div>
</div>