Question: Apply effect of button as per the attached screemshot on hover

Here i attached the screenshot of the button when on hover take a effect like.
https://prnt.sc/xJSqNRU-IqdQ
I am try with skew effect but it doesnt work. I am also trying with skew effect but this doesn't work with button here. Let me provide the solution here.


.skew-button {
  display: inline-block;
  padding: 10px 20px;
  background-color: #333;
  color: #fff;
  border: none;
  font-size: 16px;
  transition: all 0.3s;
  position: relative;
  overflow: hidden;
}

.skew-button:before {
  content: "";
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  background-color: red;
  transform-origin: top left;
  transform: skewX(-20deg);
  transition: all 0.3s;
  z-index: -1;
  opacity: 0;
}

.skew-button:hover {
  background-color: red;
}

.skew-button:hover:before {
  left: -100%;
  opacity: 1;
  transform-origin: top right;
  transform: skewX(0deg);
}
<button class="skew-button">Hover Me</button>





Answer:
The easiest way to do this, that I can think of, is the following. There are explanatory comments in the code:


/* simple reset to remove default margins and padding, and to
   force all browsers to use the same algorithm for sizing
   elements: */
*,
::before,
::after {
  box-sizing: border-box;
  margin: 0;
  padding: 0;
}

body {
  background-image: radial-gradient(circle at 0 0, currentColor, slategray);
  block-size: 100vh;
}

main {
  /* to take all available space on the block-axis: */
  block-size: 100%;
  /* just an easy means of centering the content
     visually, in both the block and inline axes: */
  display: grid;
  place-content: center;
}

button {
  /* overriding the default background-color of the
     <button> element: */
  background-color: transparent;
  /* removing the default border: */
  border: 0 none transparent;
  font-size: 2rem;
  /* creates a stacking context so that the pseudo-
     elements are positioned "within" this element
     and can't be positioned "behind," or lower-than,
     the <button>: */
  isolation: isolate;
  padding-block: 1em;
  padding-inline: 2em;
  /* in order to position the pseudo-elements in
     relation to this element: */
  position: relative;
}

button::before,
button::after {
  /* custom CSS property for consistency across
     the demo: */
  --offset: 2em;
  /* setting the background-color of both
     pseudo-elements to the --background CSS
     custom property (this is declared later)
     or to the default color of white (#fff): */
  background-color: var(--background, #fff);
  /* required in order to render the pseudo-elements
     to the page: */
  content: '';
  /* using clip-path to control the shape, rather
     than using transforms; this is the initial state,
     the simple rectangle: */
  clip-path: polygon(0 0, 100% 0, 100% 100%, 0 100%);
  position: absolute;
  /* using inset to position the pseudo-elements with
     an offset of 0 on the top, right, bottom and left;
     this means the element takes all available space: */
  inset: 0;
  /* transitioning the clip-path: */
  transition: clip-path 0.3s linear;
}

button::before {
  /* declaring the custom --background property: */
  --background: red;
  /* positioning the element lower down the 'stack'
     than the parent element (the use of isolation: isolate
     was to keep the pseudo-elements in front of any
     background-color property that might be set on
     the <button>, despite a lower z-index): */
  z-index: -1;
}

button::after {
  --background: yellow;
  z-index: -2;
}

/* here we update the clip-path, using the --offset variable,
   var() and calc(), to set the clipping to create the
   parallelogram shape */
button:hover::before {
  clip-path: polygon( var(--offset) 0, 100% 0, calc(100% - var(--offset)) 100%, 0 100%);
}

button:hover::after {
  clip-path: polygon( 0 0, calc(100% - var(--offset)) 0, 100% 100%, var(--offset) 100%);
}
<main>
  <button>Some generic text</button>
</main>



JS Fiddle demo.
References:

background-color.
border.
box-sizing.
block-size.
calc().
content.
clip-path.
display.
font-size.
inline-size.
inset.
isolation.
margin.
padding.
padding-block.
padding-inline.
place-content.
position.
transition.
var().
z-index.