如何用Tkinter建立一个货币转换器GUI

如何用Tkinter建立一个货币转换器GUI

Tkinter 是一个内置的 Python 库,用于创建图形用户界面 (GUI)。它提供了一套用于建立窗口、框架、按钮、文本框和其他GUI元素的工具。

它很容易使用,而且广泛可用,使它成为在Python中构建GUI应用程序的热门选择。它也是高度可定制的,允许开发者创建独特的、具有视觉吸引力的用户界面。

在本教程中,你将使用Tkinter构建一个货币转换器GUI应用程序。

下面是你的最终结果的样子:

货币转换器GUI应用程序

你可以在这个资源库中找到该教程的代码。

先决条件

要继续学习本教程并构建应用程序,你应该具备以下条件:

  • 具有Python编程语言的基本知识
  • 在你的系统上安装了Python 3.8以上版本
  • 熟悉Tkinter和Requests库

如何设置你的虚拟环境

在你开始编码之前,你需要确保你安装了所有必要的工具和库。为了确保你有一个干净和隔离的环境,你将使用venv创建一个虚拟环境。

创建一个项目目录并在终端导航到它:

mkdir currency-converter
cd currency-converter

使用以下命令创建一个名为 env 的虚拟环境:

python -m venv env

现在Python带有预装的 venv 库,用于创建虚拟环境。

像这样激活虚拟环境:

source env/bin/activate

注意:如果你在Windows上,你需要使用 source env/Scripts/activate 来激活这个环境。

你应该在你的终端提示中看到 (env) ,表明虚拟环境已经被激活。

如何安装库

现在你已经创建了虚拟环境,你可以安装以下库:

  • requests: 该库帮助你在API端点上发送请求。
  • python-decouple: 该库帮助你读取环境变量的值。
  • pillow: 该库帮助你读取环境变量的值: 该库为你的Python解释器增加了图像处理能力。

要安装这些库,请运行以下命令:

pip install requests python-decouple pillow

如何构建货币转换器的实用功能

在本节中,你将开始构建我们的货币转换器GUI的核心功能。你将创建两个实用函数,用于转换货币和从JSON文件中检索货币代码。

为了定义这些实用功能,你将在项目中创建一个名为 utils.py 的新文件。这个文件将包含你的货币转换器GUI的所有实用函数。

从JSON文件中获取货币代码的实用函数

这个实用函数将从JSON文件中获取货币代码。这个函数将允许你用用户可以选择的可用货币列表来填充GUI。

创建一个 currency.json 文件,包括各种货币的货币代码和名称。该JSON文件有以下结构:

[
{ "AED": "United Arab Emirates Dirham" },
{ "AFN": "Afghan Afghani" },
{ "ALL": "Albanian Lek" },
...
]

You can obtain the content of the currency.json file from this link and copy it into the currency.json file in your project.

Add the following code to define the first utility function:

你可以从这个链接中获得 currency.json 文件的内容,并将其复制到你的项目中的 currency.json 文件。

添加以下代码来定义第一个实用函数:

import json
def get_currencies() -> list:
currency_codes = []
with open('currency.json') as f:
currency_data = json.load(f)
for currency in currency_data:
code, _ = list(currency.items())[0]
currency_codes.append(code)
return sorted(currency_codes

在上面的代码中,你定义了一个 get_currencies() 函数,用来返回一个货币代码的列表。在该函数中,你创建了一个名为 currency_codes 的空列表,你将用它来存储货币代码。然后,在读取模式下打开 currency.json 文件,使用 json.load() 方法将该文件的内容加载到一个叫做 currency_data 的 Python 字典中。

接下来,使用 for 循环遍历 currency_data 字典中的每个项目。currency_data 字典中的每个项目本身就是一个字典,有一个代表货币代码及其名称的键值对。在 for 循环中,你使用 list() 函数将每种货币的键值对转换为一个列表。

由于每个 dictionary 只包含一个键值对,我们可以使用 items() 方法将 dictionary 转换为包含键值对的元组列表。

然后你使用元组解包,将列表中的第一个元素分配给 code 变量,并使用 _ 忽略第二个元素。

最后,你将代表货币代码的 code 变量追加到 currency_codes 列表中。在循环浏览 currency_data 中的所有货币后,使用 sorted() 函数将 currency_codes 列表按升序排序,并从该函数中返回。

如果你调用该函数并打印其结果,你将得到以下输出:

['ADA', 'AED', 'AFN', 'ALL', 'AMD', 'ANG', 'AOA', 'ARS', 'AUD', 'AVAX', 'AWG', 'AZN', 'BAM', 'BBD', 'BDT', 'BGN', 'BHD', 'BIF', 'BMD', 'BNB', 'BND', 'BOB', 'BRL', 'BSD', 'BTC', 'BTN', 'BWP', 'BYN', 'BYR', 'BZD', 'CAD', 'CDF', 'CHF', 'CLF', 'CLP', 'CNY', 'COP', 'CRC', 'CUC', 'CUP', 'CVE', 'CZK', 'DJF', 'DKK', 'DOP', 'DOT', 'DZD', 'EGP', 'ERN', 'ETB', 'ETH', 'EUR', 'FJD', 'FKP', 'GBP', 'GEL', 'GGP', 'GHS', 'GIP', 'GMD', 'GNF', 'GTQ', 'GYD', 'HKD', 'HNL', 'HRK', 'HTG', 'HUF', 'IDR', 'ILS', 'IMP', 'INR', 'IQD', 'IRR', 'ISK', 'JEP', 'JMD', 'JOD', 'JPY', 'KES', 'KGS', 'KHR', 'KMF', 'KPW', 'KRW', 'KWD', 'KYD', 'KZT', 'LAK', 'LBP', 'LKR', 'LRD', 'LSL', 'LTC', 'LTL', 'LVL', 'LYD', 'MAD', 'MATIC', 'MDL', 'MGA', 'MKD', 'MMK', 'MNT', 'MOP', 'MRO', 'MUR', 'MVR', 'MWK', 'MXN', 'MYR', 'MZN', 'NAD', 'NGN', 'NIO', 'NOK', 'NPR', 'NZD', 'OMR', 'PAB', 'PEN', 'PGK', 'PHP', 'PKR', 'PLN', 'PYG', 'QAR', 'RON', 'RSD', 'RUB', 'RWF', 'SAR', 'SBD', 'SCR', 'SDG', 'SEK', 'SGD', 'SHP', 'SLL', 'SOL', 'SOS', 'SRD', 'STD', 'SVC', 'SYP', 'SZL', 'THB', 'TJS', 'TMT', 'TND', 'TOP', 'TRY', 'TTD', 'TWD', 'TZS', 'UAH', 'UGX', 'USD', 'UYU', 'UZS', 'VEF', 'VND', 'VUV', 'WST', 'XAF', 'XAG', 'XAU', 'XCD', 'XDR', 'XOF', 'XPF', 'XRP', 'YER', 'ZAR', 'ZMK', 'ZMW', 'ZWL']

转换货币的实用函数

为了建立货币转换器,你需要一个可以将一种货币转换成另一种货币的实用函数。为此,你将使用一个外部API来获取最新的货币兑换值。虽然有许多货币兑换API可用,如API ForexForex API等,但你要使用Currency Conversion API

你可以通过使用 requests 模块或其自身的 currencyapi-python 库将该API集成到你的代码中。如前所述,你将在本教程中使用请求模块。

要使用该API,你需要注册一个API密钥。你可以在 https://app.currencyapi.com/register 注册一个免费账户。一旦你注册了,你可以在仪表板页面上找到你的API密钥(用黑色突出显示)。

currencyapi网站截图

创建一个 .env 文件并添加以下代码来设置环境变量:

export API_KEY='your-api-key-here'

从仪表板上复制你的API密钥,并在上述文件中替换 your-api-key-here 。然后运行以下命令来设置环境变量:

source .env

然后你在Python代码中使用 python-decouple 库来读取API密钥值。

接下来,在同一个 utils.py 文件中,添加以下代码:

import requests
from decouple import config
API_KEY = config('API_KEY')
API_ENDPOINT = 'https://api.currencyapi.com/v3/latest'
def convert_currency(from_currency: str, to_currency: str, amount: float) -> float:
query_params = {
'apikey': API_KEY,
'base_currency': from_currency,
'currencies': to_currency
}
response = requests.get(API_ENDPOINT, params=query_params)
currency_data = response.json()
exchange_rate = currency_data['data'][to_currency]['value']
exchanged_value = exchange_rate * amount
return exchanged_value

convert_currency 函数需要三个参数:from_currencyto_currency, 和 amount。 from_currency 和 to_currency 是被转换货币的ISO货币代码,amount 是你要转换的 from_currency 的金额。

该函数向 API_ENDPOINT URL发送一个GET请求,将 API_KEYfrom_currency, 和 to_currency 作为查询参数。requests 模块的 requests.get() 函数被用来发送请求,params 参数被用来传递查询参数。

一旦收到响应,我们使用 response 对象的 json() 方法将其转换成 Python 字典。一个成功的响应样本看起来像这样:

{
"meta":{
"last_updated_at":"2023-03-30T23:59:59Z"
},
"data":{
"INR":{
"code":"INR",
"value":82.100841
}
}
}

然后从响应字典中提取汇率,用 amount 和 exchange_rate计算出交换值。最后,你返回交换的值。

如何用Tkinter设计货币转换器的GUI

现在你已经准备好了实用功能,你可以用Tkinter设计GUI。下面是这个应用程序的样子:

设计货币转换器的GUI

该设计包括一个300 X 320尺寸的窗口,有一个顶框和一个主框。顶部框架包含应用程序的图标和标题。主框架包括标签、组合框、输入小部件和货币转换按钮。

让我们一步一步地建立这个应用程序。在项目目录下创建一个 main.py 文件。首先,导入必要的模块和函数,以及定义一些颜色常数。

from tkinter import *
from tkinter import Tk, ttk
from PIL import Image, ImageTk
from utils import convert_currency, get_currencies
# Colors
WHITE_COLOR = "#FFFFFF"
BLACK_COLOR = "#333333"
BLUE_COLOR = "#0000FF"

如何创建窗口

当用Tkinter创建一个GUI应用程序时,第一步是创建一个具有特定大小和标题的窗口。在本例中,窗口的大小应该被设置为300×320,标题应该是 “Currency Converter(货币转换器)”。默认情况下,窗口的背景颜色是白色的,而且它不应该是可调整大小的。下面是代码:

# Window Configuration
window = Tk()
window.geometry("300x320")
window.title("Currency Converter")
window.configure(bg=WHITE_COLOR)
window.resizable(height=FALSE, width=FALSE)

如何创建框架

如前所述,你需要创建两个框架–一个顶部框架和一个主框架。顶层框架将包含应用程序的图标和标题,而主框架将包括基本部件,如标签、输入部件、组合框和转换按钮。下面的代码完成了这个任务:

# Create top and main frames
top_frame = Frame(window, width=300, height=60, bg=BLUE_COLOR)
top_frame.grid(row=0, column=0)
main_frame = Frame(window, width=300, height=260, bg=WHITE_COLOR)
main_frame.grid(row=1, column=0)

这里,Frame() 函数被用来创建两个框架。第一个参数是父窗口(本例中是 window ),然后是框架的宽度、高度和背景颜色。然后,你可以使用 grid() 方法,通过指定框架的行和列的位置,把它们放在窗口中。

你把 top_frame  widget放在网格的第一行和第一列,而把 main_frame widget放在网格的第二行和第一列。

如何在顶部框架中添加Widget

之后,你可以创建属于顶框的小部件。如前所述,顶层框架应该有一个应用程序图标和应用程序标题。你可以从Icons8(或从这里)获得一个图标,并将其保存在你的项目目录下,名称为 icon.png

# Top Frame Widgets
icon_image = Image.open('icon.png')
icon_image = icon_image.resize((40, 40))
icon_image = ImageTk.PhotoImage(icon_image)
app_name_label = Label(top_frame, image=icon_image, compound=LEFT, text="Currency Converter", height=3, padx=13, pady=30, anchor=CENTER, font=('Arial 16 bold'), bg=BLUE_COLOR, fg=WHITE_COLOR)
app_name_label.place(x=0, y=0)

该代码首先使用PIL(Python图像库)模块的 Image 类打开图像文件 icon.png。然后使用 resize() 方法将图像的大小调整为40×40。接下来,它使用 ImageTk 模块的 PhotoImage 类将图像转换为可以在GUI中显示的格式。

下一行创建了一个显示应用程序图标和标题的 Label 小部件。你在顶层框架内创建这个部件。该小组件需要几个参数来配置它的外观。

这些参数包括以下内容:

  • 应用程序图标的 image
  • 要显示的 text(”Currency Converter”)。
  • 标签的 height(设置为3)
  • 左侧和顶部的填充(分别设置为13和30)
  • 标签的锚点(设置为中心)。
  • 字体风格 (Arial 16 bold)
  • 背景颜色 (设置为 BLUE_COLOR)
  • 前景颜色 (设置为 WHITE_COLOR)

最后,我们使用 place() 方法来设置标签在顶部框架中的位置。

如何在主框架中添加小工具

如前所述,主框架将包含基本的小工具。让我们一步一步地创建它们。

下面的代码在 main_frame 框架内创建了一个名为 result_label 的标签小部件。这个标签将显示货币转换的结果。

result_label = Label(main_frame, text=" ", width=15, height=2, pady=7, padx=0, anchor=CENTER, font=('Ivy 16 bold'), bg=WHITE_COLOR, fg=BLACK_COLOR, relief=SOLID)
result_label.place(x=50, y=10)

该标签的文本设置为空字符串(” “),宽度为15,高度为2行,Y轴上的填充物为7像素,X轴上的填充物为0像素。文本将使用 anchor=CENTER 选项居中,使用的字体是 Ivy 16 bold。标签的背景颜色被设置为白色(bg=WHITE_COLOR),文本颜色为黑色(fg=BLACK_COLOR)。relief 选项被设置为SOLID,以使标签具有边界。最后,使用 place() 方法将标签放在坐标(50, 10)处。

接下来,在应用程序的设计中,有两个标签–“From “和 “To”,每个标签的下面都有一个 ComboBox

from_label = Label(main_frame, text="From", width=8, height=1, pady=0, padx=0, anchor=NW, font=('Ivy 10 bold'), bg=WHITE_COLOR, fg=BLACK_COLOR, relief=FLAT)
from_label.place(x=48, y=90)
from_combo = ttk.Combobox(main_frame, width=8, justify=CENTER, font=('Ivy 12 bold'),)
from_combo['values'] = (get_currencies())
from_combo.current(0)
from_combo.place(x=50, y=115)
to_label = Label(main_frame, text="To", width=8, height=1, pady=0, padx=0, anchor=NW, font=('Ivy 10 bold'), bg=WHITE_COLOR, fg=BLACK_COLOR, relief=FLAT)
to_label.place(x=158, y=90)
to_combo = ttk.Combobox(main_frame, width=8, justify=CENTER, font=('Ivy 12 bold'),)
to_combo['values'] = (get_currencies())
to_combo.current(1)
to_combo.place(x=160, y=115)

第一个 Label 和 ComboBox 是用来转换货币的。你使用 Label() 函数创建标签,并指定文本、宽度、高度、填充、字体和颜色设置。然后使用place()函数将Label放置在主框架的指定坐标处。

然后使用 ttk.Combobox() 函数创建一个 ComboBox,并指定宽度、字体和对齐方式。使用 get_currencies() 函数(从 utils.py 导入)设置 ComboBox 的可用值,使用 current() 函数将默认值设置为列表中的第一个项目。使用 place() 函数,ComboBox 也被放置在主框架的指定坐标处。

第二个Label和ComboBox是用来转换货币的。Label和ComboBox的创建和放置方式与第一个Label和ComboBox类似,唯一的区别是文本和放置坐标。

应用程序设计中的最后两个部件是输入字段和转换按钮。你可以使用 Entry() 方法来创建输入字段。它需要几个参数,包括 widthjustifyfont, 和 relief。然后使用place()方法将创建的部件以特定的坐标放在主框架上。

同样地,转换按钮也是用 Button() 方法创建的。它需要几个参数,如 textwidthheightbgfgfont, 和 command。然后使用 place() 方法将创建的按钮放在主框架的特定坐标上。

下面是创建输入栏和转换按钮的代码:

amount_entry = Entry(main_frame, width=22, justify=CENTER,
font=('Ivy 12 bold'), relief=SOLID)
amount_entry.place(x=50, y=155)
convert_button = Button(main_frame, text="Convert", width=19, padx=5,
height=1, bg=BLUE_COLOR, fg=WHITE_COLOR, font=('Ivy 12 bold'), command=convert)
convert_button.place(x=50, y=210)

convert_button 部件中的 command 参数需要一个函数名称。在这种情况下,它被设置为 convert。但是 convert 函数还没有被定义。要定义它,你可以在窗口被定义之前添加以下代码:

def convert():
amount = float(amount_entry.get())
from_currency = from_combo.get()
to_currency = to_combo.get()
converted_amount = convert_currency(from_currency, to_currency, amount)
result_label['text'] = f'{to_currency} {converted_amount:.2f}'

convert 函数从 amount_entry 部件中获取用户输入,从 from_combo 和 to_combo 部件中获取选定的货币,并将它们传递给 convert_currency 函数(从 utils.py) 中导入)以获得转换后的金额。然后,它将 text 的值设置为 result_label 部件中的兑换值。

最后,你在文件的最后调用 mainloop() 方法。该方法负责运行应用程序,不断检查用户事件,如鼠标点击、键盘输入和窗口大小的调整,并在必要时更新窗口。

一旦 mainloop() 方法被调用,程序就进入事件循环,开始等待用户事件。窗口将保持开放和活跃,直到用户关闭窗口或程序被终止。

# Mainloop
window.mainloop()

最终代码

这里是你一直在构建的货币转换器GUI应用程序的最终代码。这段代码包含了我们到目前为止讨论过的所有不同的组件,包括创建框架、标签、组合框、输入字段和按钮。

from tkinter import *
from tkinter import Tk, ttk
from PIL import Image, ImageTk
from utils import convert_currency, get_currencies
# Colors
WHITE_COLOR = "#FFFFFF"
BLACK_COLOR = "#333333"
BLUE_COLOR = "#0000FF"
def convert():
amount = float(amount_entry.get())
from_currency = from_combo.get()
to_currency = to_combo.get()
converted_amount = convert_currency(from_currency, to_currency, amount)
result_label['text'] = f'{to_currency} {converted_amount:.2f}'
# Window Configuration
window = Tk()
window.geometry("300x320")
window.title("Currency Converter")
window.configure(bg=WHITE_COLOR)
window.resizable(height=FALSE, width=FALSE)
# Frames
top_frame = Frame(window, width=300, height=60, bg=BLUE_COLOR)
top_frame.grid(row=0, column=0)
main_frame = Frame(window, width=300, height=260, bg=WHITE_COLOR)
main_frame.grid(row=1, column=0)
# Top Frame Widgets
icon_image = Image.open('icon.png')
icon_image = icon_image.resize((40, 40))
icon_image = ImageTk.PhotoImage(icon_image)
app_name_label = Label(top_frame, image=icon_image, compound=LEFT, text="Currency Converter", height=3, padx=13, pady=30, anchor=CENTER, font=('Arial 16 bold'), bg=BLUE_COLOR, fg=WHITE_COLOR)
app_name_label.place(x=0, y=0)
# Main Frame Widgets
result_label = Label(main_frame, text=" ", width=15, height=2, pady=7, padx=0, anchor=CENTER, font=('Ivy 16 bold'), bg=WHITE_COLOR, fg=BLACK_COLOR, relief=SOLID)
result_label.place(x=50, y=10)
from_label = Label(main_frame, text="From", width=8, height=1, pady=0, padx=0, anchor=NW, font=('Ivy 10 bold'), bg=WHITE_COLOR, fg=BLACK_COLOR, relief=FLAT)
from_label.place(x=48, y=90)
from_combo = ttk.Combobox(main_frame, width=8, justify=CENTER, font=('Ivy 12 bold'),)
from_combo['values'] = (get_currencies())
from_combo.current(0)
from_combo.place(x=50, y=115)
to_label = Label(main_frame, text="To", width=8, height=1, pady=0, padx=0, anchor=NW, font=('Ivy 10 bold'), bg=WHITE_COLOR, fg=BLACK_COLOR, relief=FLAT)
to_label.place(x=158, y=90)
to_combo = ttk.Combobox(main_frame, width=8, justify=CENTER, font=('Ivy 12 bold'),)
to_combo['values'] = (get_currencies())
to_combo.current(1)
to_combo.place(x=160, y=115)
amount_entry = Entry(main_frame, width=22, justify=CENTER,
font=('Ivy 12 bold'), relief=SOLID)
amount_entry.place(x=50, y=155)
convert_button = Button(main_frame, text="Convert", width=19, padx=5,
height=1, bg=BLUE_COLOR, fg=WHITE_COLOR, font=('Ivy 12 bold'), command=convert)
convert_button.place(x=50, y=210)
# Mainloop
window.mainloop()

你终于可以运行应用程序并开始转换货币了!

小结

在本教程中,你学会了如何使用Python和Tkinter创建一个简单的货币转换器应用程序。我们涵盖了一些主题,如创建框架、标签、输入部件、组合框和按钮。你还创建了一个函数来根据用户的输入转换货币。

有几种方法可以改进这个应用程序。你可以改进用户界面,使其看起来更有吸引力,增加一个保存转换历史的功能,以及更多。

评论留言