Animating the scale of an element while also adjusting its border-radius using CSS

I'm currently working on an animation that involves scaling a box with a rounded border of 8px. The issue I'm facing is that the rounded angle looks strange when the box is expanded, and I'm trying to avoid changing the width in the keyframes to scale it correctly. Is there a way to properly scale a rounded box with a rounded border?

#box {
  position: relative;
  width: 55px;
  height: 55px;
  background: #aaa;
  margin: 0 auto;
  border-radius: 8px;
  animation-name: singleRevert;
  animation-duration: 3s;
  animation-fill-mode: forwards;
}

#box:hover {
  animation-name: singleExpend;
  animation-duration: 3s;
  animation-fill-mode: forwards;
}

@keyframes singleRevert {
  0% {
    transform: scaleX(7.5) scaleY(0.46)
  }
  50% {
    transform: scaleX(1) scaleY(0.46)
  }
  100% {
    transform: scaleX(1) scaleY(1)
  }
}

@keyframes singleExpend {
  0% {
    transform: scaleX(1) scaleY(1)
  }
  50% {
    transform: scaleX(1) scaleY(0.46)
  }
  100% {
    transform: scaleX(7.5) scaleY(0.46)
  }
}
<div id="box"></div>

Answer №1

To achieve the desired effect, it is important to adjust the border radius of your box to match its scale.

For instance, if the radius of your box is 8px and you scale the box by 8 times, the border radius should be 1px at the scaled size. Similarly, if the box is scaled by 0.5, the border should be 16px.

Another approach is to animate the width and height of the box. This method maintains the borders without requiring any adjustments.

Here is an updated version:

#box {
  position: relative;
  width: 55px;
  height: 55px;
  background: #aaa;
  margin: 0 auto;
  border-radius: 8px;
  animation-name: singleRevert;
  animation-duration: 3s;
  animation-fill-mode: forwards;
}

#box:hover {
  animation-name: singleExpend;
  animation-duration: 3s;
  animation-fill-mode: forwards;
}

@keyframes singleRevert {
  0% {
    transform: scaleX(8) scaleY(0.5);
    border-radius: 1px;
  }
  50% {
    transform: scaleX(1) scaleY(0.5)
    border-radius: 8px;
  }
  100% {
    transform: scaleX(1) scaleY(1)
    border-radius: 8px;
  }
}

@keyframes singleExpend {
  0% {
    transform: scaleX(1) scaleY(1)
    border-radius: 8px;
  }
  50% {
    transform: scaleX(1) scaleY(0.5)
    border-radius: 8px;
  }
  100% {
    transform: scaleX(8) scaleY(0.5)
    border-radius: 1px;
  }
}
<div id="box"></div>

Here is a simplified version:

#box {
  position: relative;
  width: 55px;
  height: 55px;
  background: #aaa;
  margin: 0 auto;
  border-radius: 8px;
  animation-name: singleRevert;
  animation-duration: 3s;
  animation-fill-mode: forwards;
}

#box:hover {
  animation-name: singleExpend;
  animation-duration: 3s;
  animation-fill-mode: forwards;
}

@keyframes singleRevert {
  0% {
    width: 400px;
    height: 40px;
  }
  50% {
    width: 55px;
    height: 40px;
  }
  100% {
    width: 55px;
    height: 55px;
  }
}
@keyframes singleExpend {
  0% {
    width: 55px;
    height: 55px;
  }
  50% {
    width: 55px;
    height: 40px;
  }
  100% {
    width: 400px;
    height: 40px;
  }
}
<div id="box"></div>

Answer №2

Using the transform property to animate an element can cause issues with stretching the element, including its border-radius. Instead, consider animating the height and width separately to maintain a consistent border-radius throughout the animation:

@keyframes expandElement {
  0% {
    width: 50px;
    height: 50px;
  }
  50% {
    width: 50px;
    height: 30px;
  }
  100% {
    width: 300px;
    height: 30px;
  }
}

Best of luck with your animation!

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Retrieve information from the database and showcase it in a competitive ranking system

Here is the HTML and CSS code for a leaderboard: /* CSS code for the leaderboard */ To display the top 5 in the leaderboard, PHP can be used to fetch data from the database: <?php // PHP code to retrieve data from the database ?> The current ou ...

Troubleshooting a JQuery accordion malfunction within a table

I am populating the data dynamically. However, the Accordion feature is not functioning correctly. JSFiddle link http://jsfiddle.net/aff4vL5g/360/ Please note: I am unable to modify the HTML structure. Current table Desired output The first accordio ...

How to Efficiently Organize OpenAI AI Responses Using TypeScript/JavaScript and CSS

I'm using a Next.js framework to connect to the OpenAI API, and I've integrated it seamlessly with an AI npm package. The functionality is incredible, but I've encountered an issue regarding line breaks in the responses. You can find the AI ...

Trouble Arising from the Lack of Coordination Between CSS Transition and JavaScript Update Triggered by Element

I'm currently working on a web development project that involves a list of clickable elements. When one of these elements is clicked, it should become active and trigger a CSS transition (such as a transform) with a duration of 200ms. Additionally, I ...

Resizing a damaged HTML table to fit within a designated width using CSS

Here is a challenge - I have some broken HTML that I can't touch, and don't want to use JavaScript to fix. My goal is to make it fit within a specific width: http://jsfiddle.net/P7A9m/2/ <div id="main"> <table> <tr> ...

Adding a translucent background image across the entire page in Angular: What's the best method?

I need the background image to extend across the entire page, including covering the Material Data Table. The background should be transparent so that the content of the table remains readable. What is the most effective method to achieve this? Here is th ...

The "Splash Screen Div" page displayed during transitions and page loading

Creating a "Splash Screen Div" for a loading page involves waiting until everything is loaded and then hiding or moving the div off screen. Below is an example: index.html <div id="loading-Div"> <div id="bear-Logo"> < ...

Centering an item using Bootstrap

I am using bootstrap in reactjs and attempting to center a text in the middle of the screen, but it seems to not be working. Can someone please point out what I am doing wrong? <div className="h-100 d-flex align-self-center justify-content-center&q ...

Can someone assist me with positioning an HTML child element to appear behind a parent element using CSS?

I need help displaying an HTML element behind a fixed header in my webpage. I want the div element (which is a child of the header) to appear beneath the header like a dropdown menu. However, I've tried adjusting the z-index and position properties wi ...

What could be causing my border to spill over into the adjacent div?

Trying to set up the contact section of my portfolio but running into an issue where the border of one div is overflowing into the next. Here's a snippet of the code: //CSS .contact-cont { padding: 4rem 12rem 0rem; height: 90vh; ...

Disable the moving of the DIV button with a left-margin of 0px

Having a bit of a challenge here. I'm attempting to craft my own slider using jQuery along with some css and javascript. I've managed to get my slider functioning, moving a Div 660px to the left and right upon button clicks. However, I'm h ...

Close the ionicPopup by tapping anywhere

Currently, I have implemented an ionicPopup that automatically closes after a certain time limit. However, I am wondering if there is a way to configure it to close with a single or double tap anywhere on the screen instead. While I am aware that setting a ...

Position items at the center of the grid in material UI

I am having difficulty centering the grid items of material UI. I have tried using the justifyItems and alignItems props as mentioned in the documentation, but I'm still unable to achieve the desired result. Can anyone provide some guidance? Below is ...

Reduce the flexbox container to match the dimensions of its child elements

I have a set of blocks with fixed dimensions that I want to arrange in a grid layout. Using flex-wrap: wrap, I can distribute as many blocks as possible in each row. However, I need the entire wrapped column to be centered on the page, similar to this: ht ...

Convert and transfer CSS image data encoded in Base-64 to Asp.Net MVC/WebApi

Regarding the query. I successfully displayed a base-64 encoded image on the client side. .even { background: #fff url(data:image/gif;base64,R0lGODlhBgASALMAAOfn5+rq6uvr6+zs7O7u7vHx8fPz8/b29vj4+P39/f///wAAAAAAAAAAAAAAAAAAACwAAAAABgASAAAIMAAVCBxIsKDBgwgTDk ...

CSS - Struggling to center an element with absolute positioning in IE

I have created a layout with 3 div elements. The first parent div has a css property of position relative and is taking up the full width of the viewport. The second child div has an absolute position to cover the entire area of the parent. The third child ...

Angular2 - Incorporating a New Attribute

I am working with the following Angular2 code: <ngx-datatable-column prop="id" name="ID"> <template ngx-datatable-cell-template let-row="row" let-value="value"> <a [routerLink]="['/devicedtls',r ...

Counting the number of visible 'li' elements on a search list: A guide

In the following code snippet, I am attempting to create a simple search functionality. The goal is to count the visible 'li' elements in a list and display the total in a div called "totalClasses." Additionally, when the user searches for a spec ...

Exploring query options in jQuery for searching text using the :contains selector

Why is the if statement below not giving me the expected results? Every time it just turns the paragraph yellow, even when the word doesn't match the :contains expression. Here's the query I'm using. $(document).ready(function() { if ($ ...

Detecting collisions with other objects in HTML/CSS/JavaScript while animating objects

Does anyone know how to create a dynamic character using css, html, and javascript, and detect collisions with other elements? Any suggestions or guidance would be greatly appreciated. ...