Transition on Position and left

.whamburger {
	position: relative;
	align-items: center;
	display: flex;
	z-index: 500;		
	gap: 20px;
	transition: position 0.7s, left 0.7s;
}
body.clicked .whamburger {
	position: fixed;
	left: 10px;
}

I was trying something in the time delay, but this is not working: transition: position 0.7s, left 0.7s; are not affecting the transition.

First off, you don’t need to transition the position property. There is no visual effect for an element to go from relative to fixed position.

Next, to get this to work you need to set an initial value for left in .whamburger so the browser explicitly know what value to transition from.

This works for me

.whamburger {
    position: relative;
    align-items: center;
    display: flex;
    z-index: 500;		
    gap: 20px;
    transition: left 0.7s; /** <- removed position **/
    left: 0; /** <- added this line **/
}
body.click .whamburger {
    position: fixed;
    left: 10px;
}
1 Like

As @rpkamp said you need to transition from a left position as position itself is not an animatable property. However left:0 on a relative element has no bearing on a left position of a fixed element unless they just happens to live in the same place.

Usually you would avoid transitions by position values as they are jerky because they cause the page to be redrawn. Instead it is much better to use transforms when you animate as they have no impact on the flow and are much smoother. Use translate instead when you want to slide something into position.

Usually you position the element where you want it and then use a transform to move it off screen. Then you can just transform it back to where it should be.

It does depend on situation but if possible you should avoid transitioning position values.

5 Likes

Interesting, didn’t know that :slight_smile:

I really should brush up my CSS. I’ve been ignoring it for a few years and see where it got me :wink:

So, you mean like this?

.whamburger {
    position: relative;
    align-items: center;
    display: flex;
    z-index: 500;		
    gap: 20px;
    transition: transform 0.7s;
}
body.click .whamburger {
    position: fixed;
    transform: translateX(10px);
}
2 Likes

I already tried that day back, though I was not clear about their technical complication.

I was facing two problems with this:

  1. In a real-life scenario logos height will not be the same, so the total height of the header will not be the same, so how can I ensure that in the real-life scenario when the height of same this could be ready:
.nhamburger p {
	margin-top: 60px;
}

Here p is just the metamorphic symbolic of all the items of menus or anything else that will come later, and will probably be replaced by div later.

  1. Secondly, I was trying, and wanted that only once those 3 bars have done full opening and closing should anything move or hide.

This was easy just make the transition time more as compared to other, and it works.

The hamburger and the content are both in the fixed div so why do you need to position fix the second hamburger? You are covering where the original hamburger was so just slide in the new ‘X’ in the nornal flow of that sidebar. You won’t then need the margin-top:60px on the p element.

Just put a delay before the panel slides.

.nhamburger {
    transition: transform 0.7s 1s;
}

You seem to be making it a little harder than it should be :slight_smile:

Just slide in the new panel with its own hamburger. You don’t want to match the position of the original hamburger in the header because the user may not have scrolled it down fully before clicking it.

Also when the panel is open you want to hide the overflow on the body otherwise the content can be scrolled underneath which is annoying so probably better to put pointer-events:none on the content underneath when side panel is open.

1 Like

Yes basically that except that going from relative to fixed is not a good idea because the position of that element could be anywhere especially when its aligned with flex.

But yes the technique is to use transform to move the element into view. For a fixed positoned sidebar you’d have the default of left:0 and top:0 and a default of transform:translate(-100%);. When you want to see it you set transform:translate(0%).

Its much smoother as transforms don’t cause anything else to be redrawn and I believe they are harrdware accelerated.

3 Likes

Hi there, Actually I tried that one also. I have uploaded it here.

I was facing some issues in JS. The JS part is working. I have to re-write the whole thing

The 2nd part of JS is we-written:

I initially tried it by the || operator to get the options click event Of in one const hamburger, but it didn’t work as I have shown in the black arrow.

If I do not introduce the new class as I did here .nwhamburger then the one in top from bottom to down could only be clicked.

w/o writing the whole JS, this could have done like this also:
useJS

Does it need to be that complicated?

Just add a new extra class to each hamburger and iterate through the new class and then It can all be done in one go.

e.g.

(function (evt) {
  const heyBody = document.querySelector("body");
  const theBurger = document.querySelectorAll(".theBurger");

  for (let i = 0; i < theBurger.length; i++) {
    theBurger[i].addEventListener("click", function () {
      heyBody.classList.toggle("clicked");
    });
  }
})(document);
1 Like

Thanks, I will remember this.

1 Like

Hi There,

The general syntax is → transition: [property] [duration] [timing-function] [delay];

When, instead of 4, Three properties are used, then out of these there what are incorporated here: [duration] [timing-function] [delay]?

As with other shorthand properties any omitted value will revert to its default value.

For example the default for transition timing is ‘ease’ so if you omit to specify anything different you get the ease function by default. If you omit to say what property is being transitioned then you get ‘all’.

You could just say transition:1s and then you get all the defaults for the other values.

If you just had transition:1s 1s then you get a 1 second animation after a 1s delay. The browser works out which values to apply when there are values missing and inserts the defaults. Generally there is no conflict but occasionally a shorthand may need explicit values but I can’t remember an example off the top of my head :slight_smile:

You already do this with the background property because when you say background: red you are in fact setting all the background properties to their defaults.

To find out what a default property is going to be would you would need to look at the specs for that property and see what it says for initial value. Generally you can work it out as things like background-image would default to none and background-color would be transparent.

1 Like