Splitting apart CSS elements along with the background

Ok. Yes I got rid of the shadow once it was animated as it seemed odd to me :slight_smile:

The code that was worked out was able to keep the box-shadow with the code, and not have it be removed.

1 Like

Would this be done using 2 svgs, 4svgs, or 8 svgs?

To split the play image in 4 quarters?

You’d have to repeat it 4 times and show only a quarter of it each time much in the same way that we did for the background with 4 quarters.

It’s the same logic as the split in half version except you have to split the area into four and position everything accordingly so only the correct part shows.

1 Like

How would it be set up if I wanted the animation to change to something different on hover or when the play image is clicked?

From this animation
https://jsfiddle.net/thcedkpy/

To this on hover or click???
https://jsfiddle.net/ynkhwa3u/


.triangle path {
  fill: none;
  stroke: #fff;
  stroke-miterlimit: 10;
  stroke-width: 4px;
}

.triangle path {
  stroke: #08f9ff;
  stroke-dasharray: 150;
  stroke-dashoffset: 1500;
  -webkit-animation: flicker-1 2s linear 2s infinite both;
  animation: flicker-1 2s linear 2s infinite both;
}

@keyframes flicker-1 {
  0% {
    opacity: 0;
  }
  10% {
    opacity: 0;
  }
  10.1% {
    opacity: 1;
  }
  10.2% {
    opacity: 0;
  }
  20% {
    opacity: 0;
  }
  20.1% {
    opacity: 1;
  }
  20.6% {
    opacity: 0;
  }
  30% {
    opacity: 0;
  }
  30.1% {
    opacity: 1;
  }
  30.5% {
    opacity: 1;
  }
  30.6% {
    opacity: 0;
  }
  45% {
    opacity: 0;
  }
  45.1% {
    opacity: 1;
  }
  50% {
    opacity: 1;
  }
  55% {
    opacity: 1;
  }
  55.1% {
    opacity: 0;
  }
  57% {
    opacity: 0;
  }
  57.1% {
    opacity: 1;
  }
  60% {
    opacity: 1;
  }
  60.1% {
    opacity: 0;
  }
  65% {
    opacity: 0;
  }
  65.1% {
    opacity: 1;
  }
  75% {
    opacity: 1;
  }
  75.1% {
    opacity: 0;
  }
  77% {
    opacity: 0;
  }
  77.1% {
    opacity: 1;
  }
  85% {
    opacity: 1;
  }
  85.1% {
    opacity: 0;
  }
  86% {
    opacity: 0;
  }
  86.1% {
    opacity: 1;
  }
  100% {
    opacity: 1;
  }
}
<svg class="triangle" width="198" height="198" viewBox="0 0 47.96 51.66">
  <path d="M2,25.83V4.11A2.11,2.11,0,0,1,5.13,2.27L44.88,24.45a2.11,2.11,0,0,1,0,3.7L5.1,49.41A2.11,2.11,0,0,1,2,47.55V25.83"/>
</svg>

You would change the svg path to use your flicker effect when hovered (or when you add the class).

e.g. Add this to the end of your fiddle for testing.

.curtain:hover .jacketa .coversvg .front {
  fill: none;
  stroke: #fff;
  stroke-miterlimit: 10;
  stroke-width: 4px;
  stroke: #08f9ff;
  stroke-dasharray: 150;
  stroke-dashoffset: 1500;
  animation: flicker-2 2s linear 0s infinite both;
}

@keyframes flicker-2 {
  0% {
    opacity: 0;
  }
  10% {
    opacity: 0;
  }
  10.1% {
    opacity: 1;
  }
  10.2% {
    opacity: 0;
  }
  20% {
    opacity: 0;
  }
  20.1% {
    opacity: 1;
  }
  20.6% {
    opacity: 0;
  }
  30% {
    opacity: 0;
  }
  30.1% {
    opacity: 1;
  }
  30.5% {
    opacity: 1;
  }
  30.6% {
    opacity: 0;
  }
  45% {
    opacity: 0;
  }
  45.1% {
    opacity: 1;
  }
  50% {
    opacity: 1;
  }
  55% {
    opacity: 1;
  }
  55.1% {
    opacity: 0;
  }
  57% {
    opacity: 0;
  }
  57.1% {
    opacity: 1;
  }
  60% {
    opacity: 1;
  }
  60.1% {
    opacity: 0;
  }
  65% {
    opacity: 0;
  }
  65.1% {
    opacity: 1;
  }
  75% {
    opacity: 1;
  }
  75.1% {
    opacity: 0;
  }
  77% {
    opacity: 0;
  }
  77.1% {
    opacity: 1;
  }
  85% {
    opacity: 1;
  }
  85.1% {
    opacity: 0;
  }
  86% {
    opacity: 0;
  }
  86.1% {
    opacity: 1;
  }
  100% {
    opacity: 1;
  }
}
1 Like

I got it.
https://jsfiddle.net/mhL140uy/4/

1 Like

Working Switch changed to .jacketa
https://jsfiddle.net/m7Lone51/1/

My attempt of splitting it:
https://jsfiddle.net/rpegjLt0/3/

I was also trying to get the toggle thing to change, didn’t figure that out.

I got the button half working here:

https://jsfiddle.net/m8Lwyv3k/1/

<div class="curtain">

  <div class="split-wrap ">
    <div class="j1">
      <div class="jacketa" title="[ Enjoy The Music ]">

        <div class="button">
          <div class="light"></div>
          <div class="dots"></div>
          <div class="characters"></div>
          <div class="shine"></div>
          <div class="shadow"></div>
        </div>

      </div>
    </div>
    <div class="j2">
      <div class="jacketa" title="[ Enjoy The Music ]">

        <div class="button">
          <div class="light"></div>
          <div class="dots"></div>
          <div class="characters"></div>
          <div class="shine"></div>
          <div class="shadow"></div>
        </div>

      </div>

    </div>
  </div>
</div>

Something would get changed here I think.

.split-wrap {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  width: 150px;
  height: 195px;
  margin: auto;
  transition: 0.5s ease;
}

.j1 {
  position: absolute;
  left: 0;
  top: 0;
  width: 50%;
  height: 100%;
  overflow: hidden;
  transition: 5s ease;
}
.j2 {
  position: absolute;
  left: 50%;
  top: 0;
  width: 50%;
  height: 100%;
  overflow: hidden;
  transition: 5s ease;
}
.j2 .jacketa {
  right: 0;
  left: auto;
}

You don’t need to add a class of on for this to work. You are already adding a class of .slide to a common parent (as mentioned a number of times). You can use that common class to activate the buttons without adding more classes.

e.g.

html,
body {
  height: 100%;
  margin: 0;
  padding: 0;
}

body {
  background: #353198;
}

.curtain {
  position: relative;
  width: 100%;
  height: 100%;
}



.jacketa {
  position: absolute;
  top: 0;
  left: 0;
  bottom: 0;
  right: 0;
  margin: auto;
  background-color: black;
  width: 150px;
  height: 195px;
  box-shadow: 0 0 10px 2px rgba(0, 0, 0, 0.2), 0 0 1px 2px black,
    inset 0 2px 2px -2px white, inset 0 0 2px 15px #47434c,
    inset 0 0 2px 22px black;
  border-radius: 5px;
  padding: 20px;
  perspective: 700px;
   display: block !important;
}


.slide .jacketa .button {
  transform: translateZ(20px) rotateX(25deg);
  box-shadow: 0 -10px 20px #ff1818;
}


.slide .jacketa .button .light {
  animation: flicker 0.2s infinite 0.3s;
}


.slide .jacketa .button .shine {
  opacity: 1;
}

.slide .jacketa .button .shadow {
  opacity: 0;
}

.jacketa .button {
  transition: all 0.3s cubic-bezier(1, 0, 1, 1);
  transform-origin: center center -20px;
  transform: translateZ(20px) rotateX(-25deg);
  transform-style: preserve-3d;
  background-color: #9b0621;
  width: 100%;
  height: 100%;
  position: relative;
  cursor: pointer;
  background: linear-gradient(
    #980000 0%,
    #6f0000 30%,
    #6f0000 70%,
    #980000 100%
  );
  background-repeat: no-repeat;
}

.jacketa .button::before {
  content: "";
  background: linear-gradient(
        rgba(255, 255, 255, 0.8) 10%,
        rgba(255, 255, 255, 0.3) 30%,
        #650000 75%,
        #320000
      )
      50% 50%/97% 97%,
    #b10000;
  background-repeat: no-repeat;
  width: 100%;
  height: 50px;
  transform-origin: top;
  transform: rotateX(-90deg);
  position: absolute;
  top: 0;
}

.jacketa .button::after {
  content: "";
  background-image: linear-gradient(#650000, #320000);
  width: 100%;
  height: 50px;
  transform-origin: top;
  transform: translateY(50px) rotateX(-90deg);
  position: absolute;
  bottom: 0;
  box-shadow: 0 50px 8px 0px black, 0 80px 20px 0px rgba(0, 0, 0, 0.5);
}

.jacketa .light {
  opacity: 0;
  animation: light-off 1s;
  position: absolute;
  width: 100%;
  height: 100%;
  background-image: radial-gradient(#ffc97e, #ff1818 40%, transparent 70%);
}

.jacketa .dots {
  position: absolute;
  width: 100%;
  height: 100%;
  background-image: radial-gradient(transparent 30%, rgba(101, 0, 0, 0.7) 70%);
  background-size: 10px 10px;
}

.jacketa .characters {
  position: absolute;
  width: 100%;
  height: 100%;
  background: linear-gradient(white, white) 50% 20%/5% 20%,
    radial-gradient(
        circle,
        transparent 50%,
        white 52%,
        white 70%,
        transparent 72%
      )
      50% 80%/33% 25%;
  background-repeat: no-repeat;
}

.jacketa .shine {
  transition: all 0.3s cubic-bezier(1, 0, 1, 1);
  opacity: 0.3;
  position: absolute;
  width: 100%;
  height: 100%;
  background: linear-gradient(white, transparent 3%) 50% 50%/97% 97%,
    linear-gradient(
        rgba(255, 255, 255, 0.5),
        transparent 50%,
        transparent 80%,
        rgba(255, 255, 255, 0.5)
      )
      50% 50%/97% 97%;
  background-repeat: no-repeat;
}

.jacketa .shadow {
  transition: all 0.3s cubic-bezier(1, 0, 1, 1);
  opacity: 1;
  position: absolute;
  width: 100%;
  height: 100%;
  background: linear-gradient(transparent 70%, rgba(0, 0, 0, 0.8));
  background-repeat: no-repeat;
}

@keyframes flicker {
  0% {
    opacity: 1;
  }

  80% {
    opacity: 0.8;
  }

  100% {
    opacity: 1;
  }
}

@keyframes light-off {
  0% {
    opacity: 1;
  }

  80% {
    opacity: 0;
  }
}

.split-wrap {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  width: 150px;
  height: 195px;
  margin: auto;
  transition: 0.5s ease;
}

.j1 {
  position: absolute;
  left: 0;
  top: 0;
  width: 50%;
  height: 100%;
  overflow: hidden;
  transition: 5s ease;
}
.j2 {
  position: absolute;
  left: 50%;
  top: 0;
  width: 50%;
  height: 100%;
  overflow: hidden;
  transition: 5s ease;
}
.j2 .jacketa {
  right: 0;
  left: auto;
}
  
  
  
.curtain.slide .j1 {
  transform: translateX(-50%);
}

.curtain.slide .j2 {
 transform: translateX(50%);
}

.hide {
  display: none;
}

remove this:
// onOffButton.classList.add("on");

You probably also need to increase the width of split-wrap to show the half of the button properly.

.split-wrap {
    position: absolute;
    top: 0;
    left: 0;
    right: 0;
    bottom: 0;
    width: 188px;
    height: 195px;
    margin: auto;
    transition: 0.5s ease;
}

I used 188px but that was just by eye and couldn’t be bothered to work it out exactly. :slight_smile:

Screen Shot 2021-07-27 at 12.02.11

1 Like

How come I got a negative margin?
https://jsfiddle.net/ftm9q6yu/

.j1 .jacketa {
  left: 2px;
}

.j2 .jacketa {
  left: -96px;
}

Box shadow does not form part of the box dimensions so when you hide the overflow then box-shadow will also get cut off. As the box-shadow is an important part of that button design you need to leave room for it to show so must be included in your calculations.

2 Likes

How come the flicker effect after click is working here:
https://jsfiddle.net/3gk1unod/

But not here?
https://jsfiddle.net/mkn0xg7s/1/

I put everything in the same way.

You are adding the slide class with js to .outer and not .curtain so the css needs to reflect this.

.outer.slide .jacketa .coversvg .front

1 Like

Can an element that is in the html be slit apart, or does it have to be in the css?

Adding this:

https://jsfiddle.net/qngsozyr/

<svg xmlns="http://www.w3.org/2000/svg">
    <filter id="filter">
        <feTurbulence baseFrequency="0.01 0.0001" numOctaves="5"/>
        <feColorMatrix values="1 0 0 0 0
                               0 0 0 0 0
                               0 0 0 0 0
                               0 0 0 0 1"/>
    </filter>
    <rect width="100%" height="100%" filter="url(#filter)"/>
</svg>

To this code:
https://jsfiddle.net/twxy4m9o/

This worked:
https://jsfiddle.net/6ohtLrke/

.panel-left::before,
.panel-right::before {
  content: "";
  position: absolute;
  height: 100%;
  width: 200%;
  top: 0;
  left: 0;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg'%3E%3Cfilter id='filter'%3E%3CfeTurbulence baseFrequency='0.01 0.0001' numOctaves='5'/%3E%3CfeColorMatrix values='1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23filter)'/%3E%3C/svg%3E");
  background-size: auto;
  background-repeat: repeat;
  background-position: 0 0;
}
1 Like

When 2 images are being used here, how should this be set up?
https://jsfiddle.net/f72jm18a/

This does not seem right.

Try making the browser window smaller and larger.

The images fall into each other.

Shouldn’t it be as if both images were glued together?

Right?

.panel-left {
  left: 0%;
  background: url("https://i.imgur.com/Gy397ZF.jpg");
  background-size: cover;
  background-repeat: no-repeat;
  background-position: 0 0;
}

.panel-right {
  left: 50%;
  background: url("https://i.imgur.com/Gy397ZF.jpg");
  background-size: cover;
  background-repeat: no-repeat;
  background-position: 0 0;
}

I already gave you examples of how to do that when you first started asking about curtain images. You should still have examples somewhere.

You need to put the image into a pseudo element (:before) and then size the pseudo element to be twice the size of the half panel. Do that for both sides and hide the overflow on the parent and set the background-position of the right pseudo element to the right. In that way you only see the left half of the left panel and the right half of the right panel which join together to make a perfect whole panel.

If you don’t care about squashing the image you can do it with your current code like this.

.panel-left {
  left: 0%;
  background: url("https://i.imgur.com/Gy397ZF.jpg");
  background-size: 200% 100%;
  background-repeat: no-repeat;
  background-position: 0 0;
}

.panel-right {
  left: 50%;
  background: url("https://i.imgur.com/Gy397ZF.jpg");
  background-size: 200% 100%;
  background-repeat: no-repeat;
  background-position: 100% 0;
}

I have this example, where would I put the 2nd image url?
https://jsfiddle.net/j0wc53La/

I have a question about this code also.

When the browser window is resized, the image is fixed and doesn’t change at all.

Shouldn’t it change?
or no?

.panel-left,
.panel-right {
  position: absolute;
  height: 100%;
  width: 50%;
  top: 0%;
  transition: all ease 5s;

  /*background-image: url("https://picsum.photos/600");
  background-size: cover;
  background-repeat: no-repeat;
  background-position: center;*/
  overflow: hidden;
}

.panel-left {
  left: 0;
  /*background-color: rgb(91, 96, 106);*/
}

.panel-right {
  right: 0;
  /*background-color: rgb(229, 211, 211);*/
}

.panel-left::before,
.panel-right::before {
  content: "";
  position: absolute;
  height: 100%;
  width: 200%;
  top: 0;
  left: 0;
  background-image: url("https://picsum.photos/1920/1080");
  background-size: auto;
  background-repeat: no-repeat;
  background-position: 0 0;
}

.panel-right::before {
  left: -100%;
}

.curtain.slide .panel-left {
  transform: translateX(-100%);
}

.curtain.slide .panel-right {
  transform: translateX(100%);
}

You haven’t told it to do anything as you specified auto and not cover.

1 Like

How would this code work with 2 image urls?

Would the code be written differently to do that?