menu

Questions & Answers

What is the correct way to create a hover effect for and svg in an <img> tag?

What is the correct way to add a hover effect for an SVG that is embedded in an ing tag? Can this purely be achieved by CSS?

If not, what is the correct HTML semantic way to embed SVG icons with hover effects?

Thanks

Comments:
2023-01-19 00:20:09
Consider using <svg> tag by itself, not embed inside of <img> tag
2023-01-19 00:20:09
Thank you, for accesbility of a navigation icon what is the preferred tag?
2023-01-19 00:20:09
What's the problem. You can hover the entire image. Is it that you want to hover things within the image, if so, you can't do that.
2023-01-19 00:20:09
You can't, the IMG tag is a locked container you can't style the inside of. For alternatives you can load the SVG file and inject it in your document
Answers(2) :

If the svg icon is made using an embedded image in the format data:image/png;base64 then to change color on hover: you can use svg filter feColorMatrix:

.R1:hover {
filter:url(#RedFilter);
} 

.G1:hover {
filter:url(#GreenFilter);
}
.B1:hover {
filter:url(#BlueFilter);
}
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="400" height="150" viewBox="0 -30 400 150" style="border:1px solid grey;"> 

  <defs>
 <filter id="RedFilter" x="-20" y="-20" width="150" height="150">
        <feColorMatrix in="SourceGraphic" type="matrix"
                values="0 0 0 1 0
                        0 0 0 0 0
                        0 0 0 0 0
                        0 0 0 1 0
                "/>
    </filter> 
    <filter id="GreenFilter" x="-20" y="-20" width="140" height="140">
        <feColorMatrix in="SourceGraphic" type="matrix"
                values="0 0 0 0 0
                        0 0 0 1 0
                        0 0 0 0 0
                        0 0 0 1 0
                "/>
    </filter> 
    
    <filter id="BlueFilter" x="-20" y="-20" width="140" height="140">
        <feColorMatrix in="SourceGraphic" type="matrix"
                values="0 0 0 0 0
                        0 0 0 0 0
                        0 0 0 1 0
                        0 0 0 1 0
                "/>
    </filter> 
    
    <filter id="WhiteFilter" x="-20" y="-20" width="140" height="140">
        <feColorMatrix in="SourceGraphic" type="matrix"
                values="0 0 0 1 0
                        0 0 0 1 0
                        0 0 0 1 0
                        0 0 0 1 0
                "/>
    </filter>
 


   <image id="Building" width="100" height="100"  xlink:href="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAGQAAABcCAYAAACYyxCUAAAABGdBTUEAA1teXP8meAAABqhJREFUeAHtXc+LHUUQ3qhIREFFRA9GV8QfyAp78JYg8eZlwaN6yf4H6kGQnHKQ4M38AR5yih48CHvxZPaw3jws6EEPgiQS4g/wiYoiMfH7wtbwvXLeTL95Mz09u1XQTFV3dXd1ffOqpntmk2NrZdK7MIvF6C4w95pwiK43sJY/dT13qBD8+B4IQMbHYM6CAGTOHeMLjM0l0t0wSnPGsRKN7MGmO90610oFhL/cUm3rAYdqCN5oc+uMkFX5pgwmACkDh8qKuZ9LVVs+8xVMPOvM/MPJ90BmjDY6D+YFE3C9hPKRyP+C/0tk9uUYSjsqgKcNtMWI/TmOEXMhixHnpx0LaaqA/IYV7blVzZx8H2RdH/soXYWgY3CTpqCyL8doIoKhY7A/xzE6DoYlmSJkJbsqj2IAksfPybMEIMmuyqMYgOTxc/IsAUiyq/IoBiB5/Jw8iz4WJncqQPF+2HDK2aGPrGzy+xD2UToBQcdI2Ydof/K6r6Gcsg+h3uToHCy+dRRLhKzC7tUApDBApppDeAyiZ0h0qx5ZUOZZlL5HYbzXPHIFMosRQ6SeQ7GvnoVRT3MOZdqgRzLsz3GMeMPrTc/5fd4x3dvXqQJCR2zNrWRtre0sawf66lAeLL4vYxBQfTCgb/xZ1q+iT5aHi3tS13aWxflpx0JS9BYqRUM+DwQg+XydNFMAkuSmfEoBSD5fJ80UgCS5KZ9SAJLP10kzBSBJbsqnNNV9CDdX/nme+wiluo2htr8O4aRUpGwMRf02yw8Wlt0Y+jHm5KkCwh2vbvLmFpUoPA49llWocdfdZeAIWV28NmCfAGRA53YZeqohi2dZ8aFcF8QH6sNEqod6nKbtcFGTL/XjQzl6IajZA5FDmv2TvTUlh2zDqvUGy75H20VpJ8j6gbE0Vew/4G5WUjCVB1IAOQPt01WP/zO7qLoo1QSk7QNjbuICEHGasRGyzBOFXAOQQoAwM1JClunalfGfxehvMDpO64t86HMfoY+h/uMAG3vRte7oRN+Hs98kP5RTRy5avK/ni/7rUvkjeP0YgOc7F6S9jn0LlfvS4D8OkKZatu5wsVaxofINtLGsQo1/DdVl4AhZXbw2YJ8AZEDndhk6JWTxA2KNzz9A/kYm+xn8psjPgtcQJk0VSx0ln1P4WKxz8t2G/gEm8w/7KKW8D2HuMboChsUo5X2IP/L3dvtcyBteb/rW/JoCyDUM+p1ZjesnKB+LvAFecwbBeEra69h3UKkOr8spOqcfk47YcgPPnMw+ur4dyOrQ+FDOOSzEGg/oz6mmOapyeyAAye3xlvk0xi5S5QfJjMdGr4L51ARcfXyXpoWszzEfQlNzCnMU5zHaAPOeCbhqfpHq6bPxCykMwwAkACnMA4WZo39hZKb5QznuGXQj9wzkp00ZV79pk6Zk1v/16rfoqZvPnyB/LqM9Cv4Vkck+5GTapevj+dckN4ZciCb7JyA/h2JEZ2iSt/pVrroL5ziPoagNX0NmMWLbiyYcXGnnMsSP5FhWIYLcK0UO6dWdqw8WgKzuw15HYIz14edN1GmOeAnywzIrP2BgGZL8S7BfMNkXMuF18J+JTPaGk30uPI92DTGXIPM8y4gHg8xlRnW5kedhSmch8FzNyOdC7yvOTzsWEmOxxmoqEoxNMgdEMDxo1jbU1S+E82zIZHT+lyKTnTmZNuva9A0lVa+i7JE5II6pm1P2bVs3wdAx2F9vjOOQWZIpQlayq/IoBiB5/Jw8C3+WrzltPuLy0daI4WNsog1q0/OQt51RF5w8SbEOEG4CHyhsNQTkEbGJ/wz5tshkDwUgEbIcqmOLAcjYCLj5GbL2Xd3vkPVxbxPy2CFs5uzk8/41FKV1FcA/iaL/w4KeY1H1BMopMgeUsg8xXbvqvoZ1KfsQ61t71cO3WgVUXkY5vagxU/0u5nm5Za5zrv0M5HVXV7wYIaswiAKQwgBhDpkiMacxtymtqwB+qSML13c0caqAEAzmtkNHEbIKgzQACUAK80Bh5hylX8gWfP+gFL7A4j5smaL9ye+h9EpHCZBeHTfUYAHIUJ7tOG4A0tFxQ3UbYh+yD2PfbjH4A7T7jV1Ll5WbefCn78xvdhhR+7M7DyR7pSEAmcHC3RYrqZOb6Dz9AKHL/L7/rS6DNPWJkNXknRHaApARnN40ZQDS5J0R2gKQEZzeNGUA0uSdEdoCkBGc3jRlANLknRHaApARnN40ZQDS5J0R2gKQEZzeNGXK0QnPppahFP0UHZ3T68/QuKsKCTz79E3erpXH/w/ZozT+IeSLqwAAAABJRU5ErkJggg"/>   
   </defs> 
    
   <use class="R1" id="BuildingRed" xlink:href="#Building" x="20" y="0"   ></use> 
   <use class="G1" id="BuildingGreen" xlink:href="#Building" x="150" y="0"  ></use> 
    <use class="B1" id="BuildingBlue" xlink:href="#Building" x="280" y="0"  ></use>

Update

When adding an SVG file to HTML using the img tag, the image loses the ability to be styled using simple fill, stroke, etc.
But you can use SVG or CSS filters to change the color on hover.

img:not(:hover) {
  transition: 2s;
  filter: saturate(0%);
  -webkit-filter: saturate(0%);
  }
img:hover {
  transition: 1s;
}
<img width=200 src="https://upload.wikimedia.org/wikipedia/commons/0/02/SVG_logo.svg">

Another example where the Barrett Sonntag`s utility is used to generate any color using CSS filters.

<style>
.img:hover{
filter: invert(12%) sepia(83%) saturate(5841%) hue-rotate(244deg) brightness(87%) contrast(153%);
 -webkit-filter: invert(12%) sepia(83%) saturate(5841%) hue-rotate(244deg) brightness(87%) contrast(153%);
}
</style>
<img class="img"  src="https://dev.w3.org/SVG/tools/svgweb/samples/svg-files/beacon.svg" width="300" height="300" >

Comments:
2023-01-19 00:20:09
Interesting, I haven't seen a solution like this before. Thanks!
2023-01-19 00:20:09
What is the approach if the SVG is not PNG based? These are SVGs exported from Illustrator as pure SVGs.
2023-01-19 00:20:09
@TanookiMario I'll try to give an additional answer with pure SVG added to the HTML using the img tag
2023-01-19 00:20:09
@TanookiMario Added an edit to the response to your comment

You must use <svg> tag instead <img>.

You can check SVG Vectors for your desired type of SVG here.

Sharing an hover example for you.

.html

<div>
  
  <svg width="24" height="24" viewBox="0 0 24 24">
    <path d="M 10,30
       A 20,20 0,0,1 50,30
       A 20,20 0,0,1 90,30
       Q 90,60 50,90
       Q 10,60 10,30 z">
    </path>
  </svg>
  
</div>

.css

svg {
  width: 70px;
  height: 70px;
}
svg:hover {
  fill: red;
}

body {
  display: grid;
  height: 100vh;
  margin: 0;
  place-items: center center;
}

Gives you desired type of output.

enter image description here