Is there a way to style dynamic text like this using HTML?
https://i.sstatic.net/NQ9Cs.jpg I'm open to using CSS or Javascript, as long as it does not involve animation.
Is there a way to style dynamic text like this using HTML?
https://i.sstatic.net/NQ9Cs.jpg I'm open to using CSS or Javascript, as long as it does not involve animation.
Using CSS transforms to create a faux effect:
Math.easeInOutSine = function (t, b, c, d) {
return -c/2 * (Math.cos(Math.PI*t/d) - 1) + b;
};
var easing = Math.easeInOutSine,
$target = $('#target'),
position = $target.position(),
width = $target.width(),
height = 100;
$target.html($target.text().split('').map(
function(char){
return '<span>'+char+'</span>';
}
).join(''));
var $chars = $target.children();
$chars.each(function(){
var $char = $(this),
w = $char.width(),
l = $char.position().left,
offset = easing(l, 0, height, width),
skew = offset - easing(w + l, 0, height, width),
angle = Math.atan(skew/w) * 180 / Math.PI;
offset = -offset;
$char.css({
transform: 'translateY('+offset+'px) skewY('+angle+'deg)'
});
});
$target.css({
paddingTop: height
});
#target {
white-space:pre;
display:inline-block;
}
#target span {
position:relative;
display:inline-block;
transform-origin:left;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div><div id="target">This is a test of the emergency broadcast system.</div></div>
http://codepen.io/ouroborus/pen/mmbzje
I refer to it as faking because the letters are not actually curved. Instead, they are broken down into linear segments that approximate a curve based on the width of each character. This approximation becomes more evident at larger font sizes.
To obtain glyph data for any text, you can utilize the opentypejs library. Subsequently, convert this data into an SVG path. By employing the warpjs library, custom functions can be used to distort the SVG into the desired format.
If you wish to explore more examples, visit the link provided below.
An illustration showing a waving text in SVG is demonstrated below.
opentype.load(
'https://fonts.gstatic.com/s/montserrat/v13/JTURjIg1_i6t8kCHKm45_c5H3gnD-A.woff',
(err, font) => {
const glyphs = font.stringToGlyphs('DEVELOPER');
const { width, yValues, svgPath } = glyphs.reduce(
(prev, glyph) => {
const d = glyph.path.commands.map(({ type, x1, y1, x, y }) => {
switch (type) {
case 'M':
case 'L':
return `${type} ${x + prev.width} ${y}`;
case 'Q':
return `${type} ${x1 + prev.width} ${y1} ${x +
prev.width} ${y}`;
default:
return type;
}
});
return {
svgPath: `${prev.svgPath}<path d="${d.join('')}" />`,
width: prev.width + glyph.advanceWidth,
yValues:
typeof glyph.yMax !== 'number'
? prev.yValues
: [...prev.yValues, glyph.yMax, glyph.yMin],
};
},
{ svgPath: '', width: 0, yValues: [] },
);
const yMax = Math.max(...yValues);
const yMin = Math.min(...yValues);
const height = yMax - yMin;
const period = width;
const amplitude = height / 2;
const svg = document.createElementNS('http://www.w3.org/2000/svg', 'svg');
svg.setAttribute('viewBox', `0 0 ${width} ${height + amplitude * 2}`);
svg.innerHTML = `<g transform="translate(0,${yMax +
amplitude}) scale(1 -1)">${svgPath}</g>`;
const warp = new Warp(svg);
warp.transform(([x, y]) => [
x,
y + amplitude * Math.sin((x / period) * Math.PI * 2),
]);
document.getElementById('example').appendChild(svg);
},
);
<script src="https://cdn.jsdelivr.net/npm/<a href="/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="e4938596948e97a4d5cad4cadc">[email protected]</a>/dist/warp.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/opentype.js/1.1.0/opentype.min.js"></script>
<div id="example" />
After taking inspiration from @Mike Diglio's solution, we can improve upon it.
var letterContainer = document.querySelector(".letters");
var letters = letterContainer.innerText;
letters = letters.split("");
letterContainer.innerText = "";
var offset = 0;
letters.forEach(function(letter, i){
var wrap = document.createElement("span");
wrap.innerText = letter;
wrap.style.position = "relative";
wrap.style.bottom = i+"px";
wrap.style.transform = "rotate("+-i+"deg)";
letterContainer.appendChild(wrap);
})
<div class="letters">HELLO WORLD</div>
You now just have to devise a function that handles the mapping for you.
It is possible to achieve the desired outcome in a variety of ways.
span
tag and assigning unique classes to each span
. While this method may not be visually appealing in the markup, it can present challenges with responsiveness depending on the word length and placement. (You can view an example HERE).container {
margin: 50px;
font-size: 20px;
letter-spacing: -2px;
}
span {
display: inline-block;
}
.h {
position: relative;
transform: rotate(-2deg);
}
.e {
position: relative;
bottom: 2px;
transform: rotate(-5deg);
}
.l {
position: relative;
bottom: 5px;
transform: rotate(-7deg);
}
.el {
position: relative;
bottom: 7px;
transform: rotate(-9deg);
}
.o {
position: relative;
bottom: 10px;
transform: rotate(-11deg);
}
<div class="container">
<span class="h">H</span>
<span class="e">E</span>
<span class="l">L</span>
<span class="el">L</span>
<span class="o">O</span>
</div>
path
for text movement along a curve effect can be effective (Further information available HERE). Currently, I am facing an issue while trying to install yarn on my Macbook Pro (2017). The installation process seems to be downloading a folder called /react-praktis/ instead of completing successfully. Below is a screenshot for reference: https://i.stac ...
I'm attempting to transfer the textbox value from Page-1 to Page-2 using the code below, but I am encountering difficulties. Page-1.html <div > <div style="height: 400px"> <h2>Partial view-1</h2> <p> ...
I have a list of countries displayed as an unordered list inside a table column. I would like to implement keyboard search functionality for quicker navigation within the list. <ul class="country-search"> <li id="1">Country 1</li> ...
I'm struggling to make the menu align with the text logo. Every time I try, the menu ends up below the logo instead of beside it. Can anyone provide some assistance? nav{ width: 1330px; margin: 0px auto; } nav ul li{ text-transform: up ...
I need to automatically trigger a JavaScript function based on the value pulled from the dropdown options that are populated by a database. Currently, the JavaScript function only runs when I manually select an option on the front-end. Below is my code. I ...
My issue involves two HTML pages: 1) The first HTML Page (page1.html): <html lang="en"> <head> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js" type="text/javascript"></script> <script type="text/ ...
I am facing an issue while updating user data in Angular. When I send a 'PUT' request, the entire user $scope is being sent instead of only the fields visible on the form. To retrieve and update the data, I am using a Factory. Below is my edit f ...
After deploying my Angular app on Azure static web app, I encountered an error. Whenever I try to redirect to certain routes, it returns a 404 error. However, if I navigate from one route to another within the app, everything works fine. I have attempted t ...
Can you assist me with this issue? I need to modify the code below so that the border color remains blue while a user selects an item from the UL LI list. Here is an image showing the current problem: https://i.sstatic.net/DS7hO.png And here is a pictu ...
Upon loading the page, I am trying to store the height of an element. To achieve this, I have utilized the jQuery "ready" function to establish a callback: var h_top; var h_what; var h_nav; $(".people").ready(function() { h_top = $(".to ...
import React from 'react'; import { makeStyles } from '@material-ui/core/styles'; import Paper from '@material-ui/core/Paper'; import Grid from '@material-ui/core/Grid'; const useStyles = makeStyles((theme) => ({ ...
Attempting to modify and override certain classes within the complex control (dxList) of DevExtreme has been successful thus far. .dx-loadpanel-content { transform: translate(0px, 0px) !important; margin: auto !important; left: 0px !important; ...
I am attempting to showcase unlisted search results that can be clicked on to redirect the user to a specific HTML page based on data retrieved from a MySQL database. My development environment is PhoneGap. Thus far, I have successfully set up a basic PH ...
I am attempting to retrieve the secure file URL provided by Cloudinary after successfully uploading the asset to their servers. Although I can upload the file to Cloudinary, when I try to view the response using console.log(res), I unfortunately receive &a ...
After completing an AngularJS tutorial on http://www.tutorialspoint.com/angularjs/angularjs_services.htm, I found myself puzzled by the method used in the CalcService service. It seemed unclear whether Angular was using revealing prototype or a different ...
I am a newcomer to NextJS and facing a challenge where I need to transfer data from the current page to another page. However, instead of loading the defined path in router.push as pathname: "/booking/checkout/", it loads the current page. I wan ...
Currently diving into the world of Angular2 and completing both the quickstart and heroes tutorial. Each time I start these applications, I use the "npm start" command. On top of that, I've developed a Ruby on Rails backend application alongside an A ...
I recently took over maintenance of an NPM package. It has a unique setup where the main file is located in the 'dist/' directory and it's built using webpack (via 'npm run build'). While this works for us, installing this package ...
I've been working on converting a CSV file to a local 2D array and I'm curious if there's a more efficient method of changing strings to floats/int rather than relying on regex paired with parseFloat() / parseInt. Any bright ideas or sugges ...
Experiencing issues updating the directive when the drop down list is changed using AngularJS. Below is my application code: HTML Code <div ng-app="myApp" ng-controller="MyCtrl"> <select ng-model="opt" ng-options="font.title for font in font ...