Wrapping a text around a circular element - css

I have 2 DIV's as shown below and I've been trying to get the text between the two circles to wrap around the inner circle as shown on the attacthed image. I have not been able to achieve the desired result.
HTML
<div id="outer-circle">
This is just a test logo name
<div id="inner-circle">
</div><!-- End Inner Circle -->
</div><!-- End Outer Circle -->
CSS
* {
margin: 0 auto;
}
#inner-circle {
width: 200px;
height: 200px;
border-radius: 100%;
background-color: green;
margin-top: 28px;
position: relative;
}
#outer-circle {
width: 300px;
height: 300px;
border-radius: 100%;
background-color: blue;
margin-top: 50px;
text-align center;
text-align: left;
}
Click here to see current but undesired result
Example of desired result

See this post by Chris Coyier in which he separates each character of text into <span>s and rotates each one in turn using CSS rotation:
.char1 {
-webkit-transform: rotate(6deg);
-moz-transform: rotate(6deg);
-ms-transform: rotate(6deg);
-o-transform: rotate(6deg);
transform: rotate(6deg);
}
.char2 {
-webkit-transform: rotate(12deg);
-moz-transform: rotate(12deg);
-ms-transform: rotate(12deg);
-o-transform: rotate(12deg);
transform: rotate(12deg);
}
...etc
Or use Dirk Weber's csswarp.js Service which pretty much does the same but uses javascript to generate the html and css for you. (csswarp.js on GitHub)
Or use SVG text on a path as in this example from useragentman.com
<svg id="myShape" xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink">
<defs>
<path id="path1"
fill="none" stroke="black" stroke-width="1"
d="M 212,65
C 276,81 292,91 305,103 361,155
363,245 311,302 300,314 286,324
271,332 248,343 227,347 202,347
190,346 174,343 163,339 143,333">
</path>
</defs>
<text id="myText">
<textPath xlink:href="#path1" >
<tspan dy="0.3em">C is for Cookie, That's Good Enough For Me!</tspan>
</textPath>
</text>
</svg>
Or...
Use an image.

Use base info from https://css-tricks.com/set-text-on-a-circle/
BUT with a simplifications and without any additional libs.
And it will work with any text you type...
var lettering = function(node,text){
var str = typeof text=='undefined'
?node.textContent
:text;
node.innerHTML='';
var openTag = '<span>';
var closeTag = '</span>';
var newHTML = openTag;
var closeTags = closeTag;
for(var i=0,iCount=str.length;i<iCount;i++){
newHTML+=str[i]+openTag;
closeTags+=closeTag;
}
node.innerHTML = newHTML+closeTags;
}
lettering(
document.getElementById('text'),
Math.round(Math.random()*1000) + ' : Hello world!!!'
);
.badge {
position: relative;
width: 400px;
border-radius: 50%;
transform: rotate(-50deg);
}
h1 span {
font: 26px Monaco, MonoSpace;
height: 200px;
position: absolute;
width: 20px;
left: 0;
top: 0;
transform-origin: bottom center;
transform: rotate(10deg);
}
<div class='badge'>
<h1 id="text">Any custom text you type...</h1>
</div>

Related

How can I give this blob svg a scroll morph effect?

I currently have a blob in the background of my website and I'd like to morph it and make it interactive as the user scrolls down the page, what can I add to do this? ATM, the blob is animated but not on scroll.
Here is the html
<div class="morph-wrap">
<svg class="morph" width="1400" height="770" viewBox="0 0 1400 770">
<path
d="M 262.9,252.2 C 210.1,338.2 212.6,487.6 288.8,553.9 372.2,626.5 511.2,517.8 620.3,536.3 750.6,558.4 860.3,723 987.3,686.5 1089,657.3 1168,534.7 1173,429.2 1178,313.7 1096,189.1 995.1,130.7 852.1,47.07 658.8,78.95 498.1,119.2 410.7,141.1 322.6,154.8 262.9,252.2 Z" />
</svg>
</div>
Here is the css
/* SVG Morph */
.morph-wrap {
position: fixed;
top: 0;
left: 0;
bottom: 0;
width: 100%;
overflow: hidden;
display: flex;
align-items: center;
justify-content: center;
pointer-events: none;
}
.morph {
position: relative;
height: 100%;
fill: rgb(33, 33, 33);
flex: none;
animation: animate 5s linear infinite;
}
#keyframes animate {
0% {
transform: scale(1) translate(10px, -30px);
}
38% {
transform: scale(0.8, 1) translate(80vw, 30vh) rotate(160deg);
}
40% {
transform: scale(0.8, 1) translate(80vw, 30vh) rotate(160deg);
}
78% {
transform: scale(1.3) translate(0vw, 50vh) rotate(-20deg);
}
80% {
transform: scale(1.3) translate(0vw, 50vh) rotate(-20deg);
}
100% {
transform: scale(1) translate(10px, -30px);
}
}

How can I animate several elements on the same orbital path in sequence?

I want to create an animation showing a few circles moving one after another in orbit. Currently, I created three circles but they appear on separate lines and thus move in a circular movement, but as a line. How can I change the code to achieve the movement that I want? Here's a codepen with the current status.
Here's the code that I use:
* {
box-sizing: border-box;
margin: 0;
padding: 0;
}
body {
font-family: 'Lato', sans-serif;
font-size: 18px;
line-height: 1.6;
background-image: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
display: flex;
align-items: center;
justify-content: center;
flex-direction: column;
min-height: 100vh;
}
.loader {
height: 50px;
animation: rotate 6s linear infinite;
}
.circle {
display: inline-block;
background-color: purple;
height: 40px;
width: 40px;
border-radius: 50%;
transform: scale(0);
animation: grow 1.5s linear infinite;
margin: -20p;
}
.circle:nth-child(2) {
background-color: palevioletred;
transform: scale(0);
animation-delay: 0.20s;
}
#keyframes rotate {
to {
transform: rotate(360deg)
}
}
#keyframes grow {
50% {
transform: scale(1);
}
}
<div class="loader">
<div class="circle"></div>
<div class="circle"></div>
<div class="circle"></div>
</div>
I'm creating full-size "plates" which I can set to an initial rotation point. The circles end up as pseudo-elements on the plates (to avoid extra markup). Modify the initial rotation values to bring the circles closer together.
.loader {
width: 100px;
height: 100px;
animation: rotate 6s linear infinite;
position: relative;
}
.plate {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
}
.plate:nth-child(2) {
transform: rotate(120deg);
}
.plate:nth-child(3) {
transform: rotate(240deg);
}
.plate:before {
content: '';
position: absolute;
background-color: red;
height: 40px;
width: 40px;
border-radius: 50%;
transform: scale(0);
animation: grow 1.5s linear infinite;
}
.plate:nth-child(2):before {
background: green;
}
.plate:nth-child(3):before {
background: blue;
}
#keyframes rotate {
to {
transform: rotate(360deg);
}
}
#keyframes grow {
50% {
transform: scale(1);
}
}
* {
box-sizing: bordr-box;
margin: 0;
padding: 0;
}
body {
font-family: "Lato", sans-serif;
font-size: 18px;
line-height: 1.6;
background-image: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
display: flex;
align-items: center;
justify-content: center;
flex-direction: column;
min-height: 100vh;
}
<body>
<div class="loader">
<div class="plate"></div>
<div class="plate"></div>
<div class="plate"></div>
</div>
</body>
#isherwood provided a great solution that's easily workable in most modern browsers. But let's say you want more complex motion, like an elliptical orbit.
SVG Animation
You could build the whole thing into an SVG since that supports lots of cool animation while being quite performant. But building SVGs and animating them from scratch is kinda complicated. Luckily, there are tools to help. Here's a few examples: Snapsvg (code library), SVGGator (Web-based animation tool) or Bodymovin (After Effects workflow).
But let's say you want to stick with what can be done in HTML/CSS.
CSS Motion Path
Sadly support is, not great as of Summer 2019 but it will likely be improving. If your audience is using the right browsers (Chrome, Opera, Edge or Chromium based mobile browsers). It's actually pretty easy to use but there are some gotchas. For example, it appears that only the path() property works right now. So you can't use shape keywords like circle() or ellipse() though they're in the spec.
main {
position: relative;
margin: 20px;
}
main,svg {
width: 100px;
height: 100px;
}
path {
stroke-width: 1px;
}
svg {
position:absolute;
opacity: 0.5;
}
#c1 {
stroke: red;
}
#c2 {
stroke: blue;
}
#c3 {
stroke: green;
}
div[class*="c"] {
width: 15px;
height: 15px;
border-radius: 50%;
position: absolute;
box-shadow: 5px 5px 10px 0 rgba(0,0,0,0.3);
}
.c1 {
background-color: red;
offset-path: path('M50,2 C78.2166667,2 98,22.2364005 98,50.5 C98,78.7635995 75.5694444,99 50,99 C24.4305556,99 2,76.5476997 2,50.5 C2,24.4523003 21.7833333,2 50,2 Z');
animation: moveme 5s ease-in-out infinite;
}
.c2 {
background-color: blue;
offset-path: path('M55,13 C80.2774306,13 98,30.9415509 98,56 C98,81.0584491 77.9059606,99 55,99 C32.0940394,99 12,79.0938368 12,56 C12,32.9061632 29.7225694,13 55,13 Z');
animation: moveme 5.25s linear infinite;
}
.c3{
background-color: green;
offset-path: path('M36.0041619,30.5873511 C61.3414991,12.7718541 90.4202796,4.99194919 98.2799065,16.2635432 C106.139533,27.5351371 85.805943,52.9370587 62.845696,69.0811471 C39.885449,85.2252355 7.31148243,93.0730731 1.30061213,84.4528052 C-4.71025818,75.8325372 10.6668246,48.4028481 36.0041619,30.5873511 Z');
animation: moveme 5.5s linear infinite;
}
#keyframes moveme {
100% {
motion-offset: 100%;
offset-distance: 100%;
}
}
<main>
<!-- paths for example -->
<svg viewBox="0 0 100 100" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<g id="orbit" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
<path d="M50,2 C78.2166667,2 98,22.2364005 98,50.5 C98,78.7635995 75.5694444,99 50,99 C24.4305556,99 2,76.5476997 2,50.5 C2,24.4523003 21.7833333,2 50,2 Z" id="c1"></path>
<path d="M55,13 C80.2774306,13 98,30.9415509 98,56 C98,81.0584491 77.9059606,99 55,99 C32.0940394,99 12,79.0938368 12,56 C12,32.9061632 29.7225694,13 55,13 Z" id="c2"></path>
<path d="M36.0041619,30.5873511 C61.3414991,12.7718541 90.4202796,4.99194919 98.2799065,16.2635432 C106.139533,27.5351371 85.805943,52.9370587 62.845696,69.0811471 C39.885449,85.2252355 7.31148243,93.0730731 1.30061213,84.4528052 C-4.71025818,75.8325372 10.6668246,48.4028481 36.0041619,30.5873511 Z" id="c3"></path>
</g>
</svg>
<div class="c1"></div>
<div class="c2"></div>
<div class="c3"></div>
</main>

Scaled svg path on hover is not centered

I have an svg <path> that I want scaled on mouse hover. The scaled path should be centered on top of its original location. I have read other similar posts but could not get it done.
I tried using transform-origin: 50% 50%;, transform-origin: 0 0;, and transform-origin: center; and also tried removing transform-origin all throughout, but none of them works as intended since the scaled path has an offset of several pixels:
path {
fill: #f00
}
path:hover {
fill: #000;
transform: scale(2);
-ms-transform: scale(2);
-webkit-transform: scale(2);
transform-origin: 50% 50%;
}
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 881 571" pointer-events="fill" fill="none" fill-opacity="1">
<path d="M447 263h1-1 1v-1 1h1-1 1-1 1v1h1-1 2v1h1v1h-1 1-1v1h1v1h1-1v1h-1v1-1 1h-1v1h-1v3h-1v-1h-2v-1h-1v-1h-2v-2h-1v-3h-1v-1h1-1 1v-1h1v-2h1-1v1-2 1h1v1h1v-1h1v1h1z"/>
</svg>
Your SVG artbox seems enormous, and I believe this is part of the issue. I tried cleaning it up a bit to fit the content of the SVG, and I wrapped the element inside of a div.
Here's the SVG with a more proportionate artbox:
svg {
display: block;
width: 100%;
height: auto;
}
div {
fill: #f00;
width:127px;
height:150px;
margin-left: 50px;
margin-top: 50px;
}
div:hover {
fill: #000;
transform: scale(2);
-ms-transform: scale(2);
-webkit-transform: scale(2);
transform-origin: 50% 50%;
}
<div>
<svg xmlns="http://www.w3.org/2000/svg"><path d="M65.5 23.583h10.583H65.5h10.583V13v10.583h10.584-10.584 10.584-10.584 10.584v10.584H97.25 86.667h21.166V44.75h10.584v10.583h-10.584 10.584-10.584v10.584h10.584V76.5H129h-10.583v10.583h-10.584v10.584-10.584 10.584H97.25v10.583H86.667V140H76.083v-10.583H54.917v-10.584H44.333V108.25H23.167V87.083H12.583v-31.75H2V44.75h10.583H2h10.583V34.167h10.584V13H33.75 23.167v10.583V2.417 13H33.75v10.583h10.583V13h10.584v10.583H65.5z"/>
</svg>
</div>
Hope it helps!

"Filling Water" effect with infinite repeat wrapping

I've been trying to achieve the effect seen here for one wave in a circle:
http://www.jquery-az.com/css/demo.php?ex=131.0_1
Unfortunately, I've been unable to get the animation to repeat smoothly with my own svg, seen here: http://jsbin.com/diserekigo/1/edit?html,css,output. You'll also notice that the bottom "rectangle" part isn't filled either.
My css is as follows:
.circle {
border-radius: 100%;
border: 1px solid black;
width: 200px;
height: 200px;
overflow: hidden;
position: relative;
perspective: 1px;
}
.liquid {
position: absolute;
left: 0;
top: 0;
z-index: 2;
width: 100%;
height: 100%;
-webkit-transform: translate(0, 80%);
transform: translate(0, 80%);
}
.wave {
left: 0;
width: 400%;
position: absolute;
bottom: 100%;
margin-bottom: -1px;
-webkit-animation: wave-front .7s infinite linear;
animation: wave-front 0.7s infinite linear;
}
#-webkit-keyframes wave-front {
100% {
-webkit-transform: translate(-100%, 0);
transform: translate(-100%, 0);
}
}
#keyframes wave-front {
100% {
-webkit-transform: translate(-100%, 0);
transform: translate(-100%, 0);
}
}
How can I improve the repeating behavior, as well as make the wave fill up the entire space beneath it?
You're missing a lot from the original demo. Why not just copy and paste and make whatever local changes to the size and position you wanted? Most of your issues are a result of not having all the SVG elements - the original demo has 3, not just 1. I've added them into your jsbin to get it to work:
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" style="display: none;">
<symbol id="wave">
<path d="M420,20c21.5-0.4,38.8-2.5,51.1-4.5c13.4-2.2,26.5-5.2,27.3-5.4C514,6.5,518,4.7,528.5,2.7c7.1-1.3,17.9-2.8,31.5-2.7c0,0,0,0,0,0v20H420z"></path>
<path d="M420,20c-21.5-0.4-38.8-2.5-51.1-4.5c-13.4-2.2-26.5-5.2-27.3-5.4C326,6.5,322,4.7,311.5,2.7C304.3,1.4,293.6-0.1,280,0c0,0,0,0,0,0v20H420z"></path>
<path d="M140,20c21.5-0.4,38.8-2.5,51.1-4.5c13.4-2.2,26.5-5.2,27.3-5.4C234,6.5,238,4.7,248.5,2.7c7.1-1.3,17.9-2.8,31.5-2.7c0,0,0,0,0,0v20H140z"></path>
<path d="M140,20c-21.5-0.4-38.8-2.5-51.1-4.5c-13.4-2.2-26.5-5.2-27.3-5.4C46,6.5,42,4.7,31.5,2.7C24.3,1.4,13.6-0.1,0,0c0,0,0,0,0,0l0,20H140z"></path>
</symbol>
</svg>
<div class="circle">
<div class="liquid"></div>
<div id="water" class="water">
<svg viewBox="0 0 560 20" class="water_wave water_wave_back">
<use xlink:href="#wave"></use>
</svg>
<svg viewBox="0 0 560 20" class="water_wave water_wave_front">
<use xlink:href="#wave"></use>
</svg>
</div>
</div>
You also need JavaScript to get the water to fill.
http://jsbin.com/pinowufeqe/edit?html,css,js,output

Making a Field Appear on Top of CSS Styling

Hello ive managed to create a star with css but it is hiding the field that i wat to show on front of the star. I was wondering if anyone coud point me i the right direction to what i should do to fix it. thanks
<div class="views-field views-field-field-freebetamount">
<div class="field-content">
<div id="star12">£200</div>
</div>
</div>
css
.views-field-field-freebetamount {
color:white;
}
#star12 {
background: blue;
width: 40px;
height: 40px;
position: relative;
}
#star12:before, #star12:after {
content: "";
position: absolute;
top: 0;
left: 0;
height: 40px;
width: 40px;
background: blue;
}
#star12:before {
-webkit-transform: rotate(30deg);
-moz-transform: rotate(30deg);
-ms-transform: rotate(30deg);
-o-transform: rotate(30deg);
}
#star12:after {
-webkit-transform: rotate(60deg);
-moz-transform: rotate(60deg);
-ms-transform: rotate(60deg);
-o-transform: rotate(60deg);
}
the freebetamount field should hopefully appear on top of the star. my limited css skills has lead me to try z-indexs but to no avail.
Anyone?
thanks
you have to define the negative z-index value in :before and :after pseudo element.
#star12 {
background: blue;
width: 40px;
height: 40px;
position: relative;
font-size:1.3em;
}
#star12:before, #star12:after {
content: "";
position: absolute;
top: 0;
left: 0;
height: 40px;
width: 40px;
background: blue;
z-index:-1;
}
Check the Demo.
With css u need to set z-index: 100 or something like that to place something on top of the others
You're going to want to take a look at z-index. Whichever element you want to appear on top of another needs to have a higher CSS z-index number.
in css file;
#yourID {
z-index: 99;
}

Resources