I have a <div>
of constrained size, and I want to put multiline text in it, but if it's going to overflow, I'd like to put a "..." at the end with a link to view the entire content on another page.
Is this doable in Javascript/CSS? I tried searching a bit but I'm not sure what to look for.
Hmm -- looks like there's a CSS text-overflow: ellipsis;
but I don't think I can put a link on the ellipsis.
this answer is really close but there are cases where if it just starts to overflow then only part of the ellipsis shows up.
library requirements: I can use jQuery (somewhat reluctantly), would prefer a no-framework-dependency cross-browser solution.
Here is a basic example that iterates over elements with a class of .smart-overflow
. It adds a clickable a
element with a class of ellipsis-link
only if the content is clipped. The link has a click event listener that will reveal the hidden content that was hidden with overflow: hidden
. This example only works for a single line. See the alternative example below for an approach that works for multiple lines in supported browsers.
var elements = document.querySelectorAll('.smart-overflow');
Array.prototype.forEach.call(elements, function (el) {
var link = document.createElement('a');
link.href = '#'; link.className = 'ellipsis-link';
if (el.offsetWidth < el.scrollWidth) {
link.addEventListener('click', function (e) {
e.preventDefault();
el.classList.remove('smart-overflow');
});
el.appendChild(link);
}
});
p {
width: 200px;
position: relative;
}
.smart-overflow {
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
a.ellipsis-link {
display: none;
}
.smart-overflow a.ellipsis-link {
display: block;
position: absolute;
right: 0; bottom: 0;
width: 1.2em;
height: 100%;
cursor: pointer;
}
<p class="smart-overflow">No ellipsis.</p>
<p class="smart-overflow">This is a longer string of text which should have ellipsis. This is a longer string of text which should have ellipsis.</p>
<p class="smart-overflow">Another string of text which should have ellipsis. Another string of text which should have ellipsis.</p>
In the example above, text-overflow: ellipsis
requires white-space: nowrap
in order to work which means that it only works for a single line.
If you want support for multiple lines, you can do something like this in supported browsers. If that doesn't work, see the jQuery solution below for full browser support.
var elements = document.querySelectorAll('.smart-overflow');
Array.prototype.forEach.call(elements, function (el) {
var link = document.createElement('a');
link.href = '#'; link.className = 'ellipsis-link';
link.addEventListener('click', function (e) {
e.preventDefault();
el.classList.remove('smart-overflow');
});
el.appendChild(link);
});
p {
width: 200px;
position: relative;
}
.smart-overflow {
display: -webkit-box;
-webkit-line-clamp: 2;
-webkit-box-orient: vertical;
max-height: 2.2em;
overflow: hidden;
position: relative;
}
a.ellipsis-link {
display: none;
}
.smart-overflow a.ellipsis-link {
display: block;
position: absolute;
right: 0; bottom: 0;
width: 4.2em;
height: 1.2em;
cursor: pointer;
}
<p class="smart-overflow">No ellipsis.</p>
<p class="smart-overflow">This is a longer multi-line string of text which should have ellipsis. This is a longer string of text which should have ellipsis.</p>
<p class="smart-overflow">Another multi-line string of text which should have ellipsis. Another multi-line string of text which should have ellipsis.</p>
jQuery multi-line alternative with full browser support using this library.
$('.smart-overflow').dotdotdot({
ellipsis: '',
wrap: 'word',
callback: function(isTruncated, content) {
var self = this;
if (isTruncated) {
$(this).append($('<a/>', {
class: 'ellipsis-link',
text: '...',
href: '#',
click: function(e) {
e.preventDefault();
$(this).remove();
$(self).removeClass('smart-overflow is-truncated').trigger("destroy");
}
}));
}
}
});
p { width: 200px; }
.smart-overflow { max-height: 2.8em; }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jQuery.dotdotdot/1.7.4/jquery.dotdotdot.min.js"></script>
<p class="smart-overflow">No ellipsis.</p>
<p class="smart-overflow">This is a longer multi-line string of text which should have ellipsis. This is a longer string of text which should have ellipsis.</p>
<p class="smart-overflow">Another multi-line string of text which should have ellipsis. Another multi-line string of text which should have ellipsis.</p>
Check out these jQuery plugins:
https://github.com/jjenzz/jquery.ellipsis https://github.com/rviscomi/trunk8
Here's some code I wrote awhile back, that wraps trunk8, to make the ellipsis in to links and to make them responsive as well.
(function($, window, document, undefined) {
'use strict';
window.seeMore = function() {
function addSeeMoreLinks() {
$article.find('p').trunk8(options).each(function() {
var $this = $(this);
if (0 === $this.find('.trunk8').length) {
$this.append(' <a href="#" class="seeMore">see more</a>.');
}
});
}
function removeSeeMoreLinks() {
$article.find('p').each(function() {
$(this).find('.seeMore').remove();
});
}
function setupSeeMoreLinks() {
addSeeMoreLinks();
$(window).resize(function() {
removeSeeMoreLinks();
addSeeMoreLinks();
});
}
var
$article = $('.blogArticleList article'),
options = {
lines: 6,
fill: '… <a href="#" class="trunk8">see more</a>.',
tooltip: false
};
setupSeeMoreLinks();
};
if (window.addEventListener && $().trunk8) {
window.seeMore();
}
})(jQuery, window, document);
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With