Animate a div to gracefully soar to a new position within the DOM

https://i.sstatic.net/SQDeE.png

I need to relocate an image (which is an octopus) from a large gray container (#large) to a small orange box (#small) below it using the following jQuery code:

$(document).on("click", "#large > img", function() {
  $(this).appendTo("#small");
});

The current functionality works perfectly, but I want to enhance it by adding a smooth transition effect to make the octopus 'fly' over smoothly with gradually changing size and position.

I attempted to include a CSS transition property like this:

img { transition: all 3s; }

However, this method doesn't work because the image is actually reinserted into the DOM instead of simply being moved. Can anyone suggest how to achieve such an animation effect?

Link to JS Fiddle for reference

Answer №1

Using the jQuery .append method does not have the capability to animate the element between two different states.

Instead, you can create an animation using CSS transition and the scale() function. To see an example of this in action, check out this demo on JSFiddle.

$(document).on("click", "img", function() {
  $(this).toggleClass("big");
});
div {
  margin: 20px;
  padding: 10px;
}

#large {
  width: 600px;
  height: 400px;
  background-color: gray;
}

#small {
  width: 120px;
  height: 90px;
  background-color: orange;
}

img {
  width: 100%;
  height: 100%;
  transition: transform .3s ease-out;
  transform-origin: 0 129px;
}

img.big {
  transform: scaleX(5) scaleY(4.4);
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="large">

</div>
<div id="small">
  <img src="https://ak.picdn.net/assets/cms/5bb580387901a83212e3028ab5a2fa8fb1153d7b-img_offset_2x.jpg" />
</div>

Note:

  • If you want to support multiple browsers, remember to add vendor prefixes for the transition, transform, and transform-origin properties.
  • This technique uses hard-coded pixel values. While it is possible to make it responsive by using percentage values, it would require more complex calculations.

Answer №2

After much deliberation, I have crafted a responsive solution (I believe) using JQuery. Feel free to explore the code below or check it out live on jsFiddle.

To keep things tidy and clear, I started by caching all the essential selectors.

The value of -20 is due to the div having a margin-top of 20px. My calculations involved determining the top offset of both divs in relation to the document, as well as capturing the width and height of the smaller div.

In the click function, my first step was to fetch the image's top offset so that I could compare it with the small div's offset.

If the image's distance from the top is less than the small div's distance from the top, it indicates that the image resides within the large div. In this case, I translated the image using transform:translate, setting its Y-axis value equal to the top offset of the small div, aligning the image with the same top position as the small div.

I also adjusted the width and height of the image to match those of the small div.

On the other hand, if the image's top offset is equal to or greater than that of the small div, it implies that the image is not in the large div. Consequently, I returned the image to the top offset of the large div and set its width and height to 100%.

I sincerely hope that my interpretation and explanation are accurate. Please don't hesitate to reach out if you find this helpful.

Answer №3

In order to achieve the desired effect, you must first determine the current dimensions of the image, the target dimensions, and then calculate the necessary transformation.

For simplicity, I will handle the transformation required to make the new element (the clone) appear as though it is still in its original position.

Subsequently, a standard animation that resets the scale and position will complete the task.

I made a deliberate choice to avoid utilizing jQuery so that the solution can be easily transferred.

function adjustSize(target) {
    var image = document.getElementById('image');
    var current = image.parentNode;
    var rectImage = current.getBoundingClientRect();
    var rectTarget = target.getBoundingClientRect();
    evaluateRectangles(rectImage);
    evaluateRectangles(rectTarget);

    var scaleX = rectImage.width / rectTarget.width;
    var scaleY = rectImage.height / rectTarget.height;
    var translateX = rectImage.centerX - rectTarget.centerX;
    var translateY = rectImage.centerY - rectTarget.centerY;

    var duplicate = image.cloneNode();
    var scaleTransform = 'scale(' + scaleX + ', ' + scaleY + ') '; 
    var translateTransform = 'translate(' + translateX + 'px, ' + translateY + 'px) ';
    target.appendChild(duplicate);
    duplicate.style.transform = translateTransform + scaleTransform;
    current.removeChild(image);
}

function evaluateRectangles(rect) {
    rect.centerX = rect.left + rect.width * 0.5;
    rect.centerY = rect.top + rect.height * 0.5;
}
.container {
  border: solid 1px black;
  position: relative;
  display: inline-block;
}

#container1 {
  width: 200px;
  height: 100px;
}

#container2 {
  width: 400px;
  height: 200px;
}

#container3 {
  width: 200px;
  height: 200px;
}

#image {
  background: linear-gradient(45deg, yellow, tomato);
  width: 100%;
  height: 100%;
  position: absolute;
  left: 0px;
  top: 0px;
  animation: adjustSizeAnimation 1s forwards;
}

@keyframes adjustSizeAnimation {
  to {transform: translate(0px, 0px);}
}
<div id="container1" class="container" onclick="adjustSize(this)">click me
    <div id="image"></div>
</div>
<div id="container2" class="container" onclick="adjustSize(this)">click me</div>
<div id="container3" class="container" onclick="adjustSize(this)">click me</div>

Answer №4

Although appendTo does not support animations, this question could provide some insight for you

Learn more about appendTo() animation here

Answer №5

Simply incorporate a transition and adjust the size and position to align with the target. Once the transitionend event occurs, insert the image into the target element.

// After the transition is complete
$('img').on('webkitTransitionEnd otransitionend oTransitionEnd msTransitionEnd transitionend', function(){
  // Insert into container
  $('#target').append($('img'));
  // Position at corner of container
  $('img').css({
    top: '0',
    left: '0'
  });
});

// Position in corner of target and match size
$('img').css({
position: 'absolute',
  top: $('#target').offset().top + 'px',
  left: $('#target').offset().left + 'px',
  height: $('#target').css('height'),
  width: $('#target').css('width')
});
#target {
  height: 150px;
  width: 150px;
  border: 1px solid grey;
  position: absolute;
  top: 350px;
  left: 5px;
  z-index: 1;
}

img {
  position: absolute;
  top: 0;
  left: 5px;
  transition: all 1s;
  height: 300px;
  width: 300px;
  z-index: 5;
}
<script src="https://code.jquery.com/jquery-3.2.1.min.js" integrity="sha256-hwg4gsxgFZhOsEEamdOYGBf13FyQuiTwlAQgxVSNgt4=" crossorigin="anonymous"></script>
<img src="https://placeholdit.imgix.net/~text?txtsize=33&txt=300%C3%97300&w=300&h=300" />
<div id="target">
</div>

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

Managing errors in API requests with React

Looking for some guidance on error handling in React. I have my fetch request within an async function that is imported into my App.js file from another folder. I'm exploring testing with mock service workers and read that keeping requests separate c ...

Reloading nested Iframe with Selenium automation script

Currently, I am facing a challenge while working on an application that contains nested Iframes within the user interface. Some of these Iframes undergo refreshing during the test execution process. Is there any approach that allows us to simulate the refr ...

Steer clear of pre-made CSS divs when incorporating them into your

I have created a CSS file that includes the following styles for div elements: div { height:auto; float:left; padding:0px; margin:0px; overflow:hidden; text-align:left; width:auto; } img { border:none; } ul { padding:0; margin:0; } ...

Creating an IF statement within a jQuery / Ajax request when using PHP

Does anyone know how to implement an IF statement inside jQuery? I am currently working with two rows of data in a database that have different statuses. https://i.sstatic.net/N27y1.png My main file for displaying the data is index.php. Here is a snipp ...

Steps to include a fresh string into an array within a json document

I'm currently working on a Discord bot that uses a profile.json file. My goal is to have a specific command that allows users to add input arguments to an array within the file, like this: {"Profile_name":"id":"idhere", "array":["item_1"]} The ultim ...

What causes the `global.require` function to return undefined when running as a nodejs script?

When piping a script to node and logging global.require, it appears as a function. However, when running the script passed to node directly, it is undefined... ➜ Desktop cat req.js console.log(global.require) ➜ Desktop cat req.js | node { [Functi ...

Guide on incorporating Vue components: implementing component 2 within the template of component 1

I'm a Vue beginner and struggling with how to use one component within the template of another or how to combine them in HTML. I've tried looking through the documentation and Stack Overflow but can't seem to figure it out. Currently, I am ...

Top guidelines for validating inherited props within React applications

Exploring a component called <Section /> which requires 3 props to function: color size title The color and size props are used for styling purposes, while the title prop is passed down to its child component <SectionTitle />. Here's an ...

What is the best way to retrieve the document DOM object within an EJS template?

I am attempting to display a list of participants when the user clicks on the button. However, every time I try, I encounter an error stating "document is not defined". (Please refrain from suggesting the use of jQuery!). <% var btn = document.getEle ...

Is it possible to delete XHR cache data from the client side?

Is it possible to clear cached XHR data on the client using JavaScript or its libraries? I am looking to test my app on multiple local hosts and would like to clear XML HTTP Requests on the client side instead of on the server. Is there a way to do this? ...

How to delete an element in jQuery based on a specific data attribute

Hello everyone, I seem to be stuck in a simple situation. My goal is to delete the <li> elements within certain <ul> based on their data-* attribute. I've already attempted coding this, but for some reason, it's not working as expect ...

Implementing JavaScript templates to display images: A step-by-step guide

I am facing an issue with displaying images on my page. The data for name and address is showing up, but the image is not being displayed. Here is the snippet of my code: var JSONObject = [{ name: 'Nyonya', ...

What should be done when HTML5 anchor tag downloads fail due to a long base64 string in the src attribute?

batchDownloadImages() { const aTagDownload = [ { download:'foo', href:'HD image base64 string from canvas.toDataUrl()' }, { download:'bar', href:'HD image base64 string from canvas.to ...

"Learn how to extract the image URL from the configuration file (config.json) within the assets folder, and then seamlessly display it within

In my Angular project, I have a configuration file located in the assets folder: { "brandConfig": "brand1", "brand1": {"urlPath": "http://192.168.168.60:8081/mantle-services", " ...

Learn how to use React.js props in your index.html file to

Issue: Unable to locate React props I am currently facing difficulties in accessing React props on the index.html page. This is the main page where I need to render meta tags properties that are fetched from the backend. I need to access my store data on ...

The JSON response may be missing, but the URL is still echoing the correct information

On a webpage with multiple forms, I'm utilizing jQuery to AJAX a form. Here's the function I'm using, which is basically a wrapper for the $.ajax function: function do_json_get(uri){ var ret = ''; var url = AJAX_URL + uri; ...

Enhance Your Contact Form with jQuery Validation Engine

I have implemented a contact form with added features of jQuery fadeLabel and validationEngine to enhance its appearance on the page. The file containing this code is either index.php or .html, which I have not yet determined. Here is the script from my i ...

Using jQuery's AJAX function to redirect upon successful completion to a specific URL stored

After making an ajax call successfully, I want the current page the user is on to refresh. However, despite trying multiple approaches, nothing seems to be working. There are no errors or network activity showing in the Chrome debug. get[1] = "module=tick ...

Eliminating an element from an array depending on the value of its properties

I need to remove an object from my List array by matching its properties value with the event target ID. Currently, I am using findIndex method to locate the index ID that matches the event.target.id. Below is an example of one of the objects in my list a ...

JavaScript - analyzing multiple arrays against a single array

Can anyone help me determine whether 'buns' or 'duns' has the most elements in common with 'me'? I need a method to accomplish this task. var buns = ['bap', 'bun', 'bop']; var duns = ['dap&a ...