web-dev-qa-db-ja.com

ウィジェットのフォントファミリ/サイズを知らずにウィジェットのフォントスタイルを変更する方法

Tkinterウィジェットのフォントスタイルを変更する方法はありますか?

ユースケース:標準のTkinterウィジェット(LabelEntryTextなど)を使用してUIを作成します。アプリケーションの実行中に、.config()メソッドを使用して、これらのウィジェットのフォントスタイルを太字または斜体に動的に変更することができます。残念ながら、フォントのファミリとサイズを指定せずにフォント仕様を指定する方法はないようです。

以下は、私たちがやりたいことの例ですが、どちらの例も機能しません:

widget.config(font='bold')

または

widget.config(font=( None, None, 'bold' ))
42
Malcolm

特に目標がウィジェットのグループ全体(またはすべてのウィジェット)のフォントを変更することである場合は、.config()を使用してアプリケーションフォントを変更するよりもはるかに優れた方法があります。

Tkの本当に素晴らしい機能の1つは、「名前付きフォント」の概念です。名前付きフォントの美しさは、フォントを更新すると、そのフォントを使用するすべてのウィジェットが自動的に更新されることです。そのため、これらのカスタムフォントを使用するようにウィジェットを一度構成し、属性の変更は簡単です。

以下に簡単な例を示します。

try:
    import Tkinter as tk
    import tkFont
#    import ttk  # not used here
except ImportError:  # Python 3
    import tkinter as tk
    import tkinter.font as tkFont
#    import tkinter.ttk as ttk  # not used here

class App:
    def __init__(self):
        root=tk.Tk()
        # create a custom font
        self.customFont = tkFont.Font(family="Helvetica", size=12)

        # create a couple widgets that use that font
        buttonframe = tk.Frame()
        label = tk.Label(root, text="Hello, world", font=self.customFont)
        text = tk.Text(root, width=20, height=2, font=self.customFont)
        buttonframe.pack(side="top", fill="x")
        label.pack()
        text.pack()
        text.insert("end","press +/- buttons to change\nfont size")

        # create buttons to adjust the font
        bigger = tk.Button(root, text="+", command=self.OnBigger)
        smaller = tk.Button(root, text="-", command=self.OnSmaller)
        bigger.pack(in_=buttonframe, side="left")
        smaller.pack(in_=buttonframe, side="left")

        root.mainloop()

    def OnBigger(self):
        '''Make the font 2 points bigger'''
        size = self.customFont['size']
        self.customFont.configure(size=size+2)

    def OnSmaller(self):
        '''Make the font 2 points smaller'''
        size = self.customFont['size']
        self.customFont.configure(size=size-2)

app=App()

そのアプローチが気に入らない場合、またはデフォルトのフォントに基づいてカスタムフォントを作成する場合、または状態を示すために1つまたは2つのフォントを変更するだけの場合は、font.actual特定のウィジェットのフォントの実際のサイズを取得します。例えば:

import Tkinter as tk
import tkFont

root = tk.Tk()
label = tk.Label(root, text="Hello, world")
font = tkFont.Font(font=label['font'])
print font.actual()

上記を実行すると、次の出力が得られます。

{'family': 'Lucida Grande', 
 'weight': 'normal', 
 'slant': 'roman', 
 'overstrike': False, 
 'underline': False, 
 'size': 13}
50
Bryan Oakley

1つのラベルだけでさらに短く:

from Tkinter import *
import Tkinter as tk
root = tk.Tk()

# font="-weight bold" does your thing
example = Label(root, text="This is a bold example.", font="-weight bold")
example.pack()

root.mainloop()
26
user4226334

特定のウィジェットの基本属性を使用するだけで、ラベルのフォントを変更したいとします。次の構文を使用できます。

mlabel = Label(text="Your text", font=("Name of your font",size))

このコードはpython 3.4

4
kybrdbnd

名前付きフォントを使用している場合、いくつかのステートメントを使用して必要なものを取得できます。

import tkFont
wfont = tkFont.nametofont(widget['font'])
wfont.config(weight='bold')

編集済み B.オークリーのコメントを組み込む。

4
Brandon

ウィジェットに触れたり、ウィジェットを持たずにデフォルトのフォントを取得するには、デフォルトのフォントの一般名を使用できます。

#!/usr/bin/env python3
import tkinter
import tkinter.font  # Python3!

tkinter.Tk()
default_font = tkinter.font.Font(font='TkDefaultFont')
print(default_font.actual())
0
buhtz

このQが尋ねられてからかなりの時間が経ちましたが、最近、これに対する解決策を実装する必要がありました。関数widget_font_config(...)は、Python 2および3で実行されます。

本質的に、ウィジェットのフォントの「現在の値」が取得され、変更されてから元に戻されます。名前付きフォントがサポートされており、デフォルトのinplace_fTrueは、名前付きフォントが保持され、その場で変更されることを意味します。ただし、フラグをFalseに設定することもできます。これにより、ユーザーがウィジェットのフォントの変更を浸透させたくない場合に、名前付きフォントが別の名前付きフォントに置き換えられます。名前付きフォントを使用する他のすべてのウィジェットに。

def widget_font_config(widget, inplace_f = True, **kwargs):
    import sys
    if sys.version_info[0] is 2:
        import tkFont
    else:
        import tkinter.font as tkFont
    inplace_f = kwargs.pop('inplace', inplace_f)
    font = None    
    if widget and 'font' in widget.config():
        font_config = widget.config()['font']
        current_font = font_config[4] #grabs current value
        namedfont_f = False
        try:
            font = tkFont.nametofont(current_font)
            namedfont_f = True
        except:
            font = current_font
        if namedfont_f and inplace_f:
            font.config(**kwargs)
        else:
            font_d = tkFont.Font(font=font).actual()
            font_d.update(**kwargs)
            font = tkFont.Font(**font_d)
            widget.config(font=font)
        widget.update_idletasks()
    return font

if __== '__main__':
    import sys
    pyVers = sys.version_info.major
    if pyVers is 2:
        import Tkinter as Tk, tkFont
    else:
        import tkinter as Tk, tkinter.font as tkFont
    def go():
        print(widget_font_config(root.label,  slant='roman', underline=1).actual())
        print(widget_font_config(root.button, overstrike=1).actual())
    root = Tk.Tk()
    font_s = 'Courier 20 italic'
    font_d = dict(family='Courier', size=10, weight='normal', slant='italic')
    font = tkFont.Font(**font_d)
    root.label = Tk.Label(text='Label {}'.format(font_s), font=font_s)
    root.label.pack()
    root.button = Tk.Button(text='Button {}'.format(font), font=font, command=go)
    root.button.pack()
    root.mainloop()
0
Gary02127

上記の情報の多くを1つのコードスニペットに要約するには:

lbl = ttk.Label(blah, blah)   # Make a label
font = tkFont(lbl['font'])    # Get its font
font.config(weight='bold')    # Modify font attributes
lbl['font'] = font            # Tell the label to use the modified font

これにより、使用中のフォントに関係なくフォント属性を変更できます(フォントがその属性をサポートしている限り)。

これをオンザフライで実行して、本当に吐き気を催すようなフォント効果を作成することもできます。

0
user3712955