Ernie Peters
Ernie Peters

Reputation: 697

ttk.OptionMenu has no outline/border

I am using ttk.Optionmenu() in my GUI but am annoyed that when there is no mouse-over condition, the menu/button does not have any visuals showing its border. It is not giving me any element_options to see if I can change specific styling for this widget.

I would love it if there was a way for the button to look like a button all the time instead of just when it gets focus... otherwise it looks sort of blaghh.

import tkinter as tk
from tkinter import ttk

root = tk.Tk()

var = tk.StringVar(root)
opmenu = ttk.OptionMenu(root, var, 'One', 'Two', 'Three')
opmenu.pack()

root.mainloop()

I know how to change the style for the widgets but none address its at-rest appearance. I've tried 'googling' in hopes to find a solution but to no avail. Using Python 3.5.2 and tkinter 8.6

Upvotes: 1

Views: 2356

Answers (2)

Toroid
Toroid

Reputation: 127

I found a solution for permanently showing the border of the vista style:

import tkinter as tk
from tkinter import ttk

# Always show the active style
def alwaysActiveStyle(widget):
    widget.config(state="active")
    widget.bind("<Leave>", lambda e: "break")

root = tk.Tk()

var = tk.StringVar(root)
opmenu = ttk.OptionMenu(root, var, 'One', 'Two', 'Three')
alwaysActiveStyle(opmenu)
opmenu.pack()

root.mainloop()

I hope that it solves some problems.

Upvotes: 0

Mike - SMT
Mike - SMT

Reputation: 15226

Update:

After some digging it looks like you can force the style to be claimed away from windows. It does not look as good however I think you may be able to set up your style to look the way you want after you have used theme_use('clam')

Take a look at this example:

import tkinter as tk
from tkinter import ttk

root = tk.Tk()

var1 = tk.StringVar()
var1.set("One")

s = ttk.Style(root)
s.theme_use('clam')
s.configure('raised.TMenubutton', borderwidth=1)

opmenu = ttk.OptionMenu(root, var1, "One", "One", "Two", "Three",
                        style = 'raised.TMenubutton')

opmenu.pack()

root.mainloop()

In response to your comment on using a button with a popup menu you could do something like this:

import tkinter as tk
from tkinter import ttk

root = tk.Tk()

popup = tk.Menu(root, tearoff=0)
popup.add_command(label="One", command= lambda: update_btn("One"))
popup.add_command(label="Two", command= lambda: update_btn("Two"))
popup.add_command(label="Three", command= lambda: update_btn("Three"))

btn = ttk.Button(root, text="One")
btn.pack()

def update_btn(x):
    btn.config(text=x)

def btn_popup(event):
    try:
        popup.tk_popup(event.x_root, event.y_root, 0)
    finally:
        popup.grab_release()

btn.bind("<Button-1>", btn_popup)

root.mainloop()

Upvotes: 1

Related Questions