Tkinter Button with resizable svg background image

I made this code to use an svg image as background of a button that fits the button size and that is also resizable.

So this code go a button with:

Let’s see what the code looks like:

import tkinter as tk
from PIL import Image, ImageTk
from svglib.svglib import svg2rlg
from reportlab.graphics import renderPM
from io import BytesIO


root = tk.Tk()
root.title("")
root.geometry("400x400")

def iterateimages1(event):
    global img
    b.configure(image=imgToButton("nice.svg"))

def iterateimages2(event):
    global img
    b.configure(image=imgToButton("nice2.svg"))

b = tk.Button(
    root,
    compound="center",
    bg="red",
    font="arial 20",
    text="CLICK ME",
    command=None,
    activeforeground="red",
    activebackground="black",
    )
b.bind("<ButtonPress-1>", iterateimages2)
b.bind("<ButtonRelease-1>", iterateimages1)
root.columnconfigure(0, weight=1)
root.rowconfigure(0, weight=1)
b.grid(row=0, column=0, sticky="nswe")

def imgToButton(image):
    global img
    b.update()
    bw = b.winfo_width()
    bh = b.winfo_height()
    # SVG CONVERT
    svgfile = svg2rlg(image)
    bytespng = BytesIO()
    renderPM.drawToFile(svgfile, bytespng, fmt="PNG")

    img = Image.open(bytespng)
    img = img.resize((bw, bh), Image.ANTIALIAS)
    img.image = img
    img = ImageTk.PhotoImage(img)
    return img


def resize(event):
    b.configure(image=imgToButton("nice.svg"))

root.bind("<Configure>", resize)



root.mainloop()

Video

New version of the code

Some adjustment to make the code more readable, eventually.

import tkinter as tk
from PIL import Image, ImageTk
from svglib.svglib import svg2rlg
from reportlab.graphics import renderPM
from io import BytesIO


def iterateimages1(event):
    global img
    b.configure(image=fit_svg_to_button("nice.svg"))


def iterateimages2(event):
    global img
    b.configure(image=fit_svg_to_button("nice2.svg"))


def button_update():
    b.update()
    bw = b.winfo_width()
    bh = b.winfo_height()
    return bw, bh


def svg_png(image):
    "svg -> png -> memory -> PIL -> fit button -> Tkinter"

    bw, bh = button_update()
    svgfile = svg2rlg(image)
    bytespng = BytesIO()
    renderPM.drawToFile(svgfile, bytespng, fmt="PNG")
    img = Image.open(bytespng)
    img = img.resize((bw, bh), Image.ANTIALIAS)
    img.image = img
    img = ImageTk.PhotoImage(img)
    return img


def fit_svg_to_button(image):
    "Fit text to button and calls svg_png to fit image"
    global img
    bw = button_update()[0]
    b.configure(font="arial " + str(bw // 10))
    # SVG CONVERT
    img = svg_png(image)
    return img


def resize(event):
    b.configure(image=fit_svg_to_button("nice.svg"))


def main():
    global b

    root = tk.Tk()
    root.title("")
    root.geometry("400x400")
    root.bind("<Configure>", resize)

    fsize = 20 
    b = tk.Button(
        root,
        compound="center",
        bg="red",
        font="arial " + str(fsize),
        text="CLICK ME",
        command=None,
        activeforeground="red",
        activebackground="black",
    )
    b.bind("<ButtonPress-1>", iterateimages2)
    b.bind("<ButtonRelease-1>", iterateimages1)
    root.columnconfigure(0, weight=1)
    root.rowconfigure(0, weight=1)
    b.grid(row=0, column=0, sticky="nswe")

    root.mainloop()

main()

 


Subscribe to the newsletter for updates
Tkinter templates
My youtube channel

Twitter: @pythonprogrammi - python_pygame

Videos

Speech recognition game

Pygame's Platform Game

Other Pygame's posts