Source code
import tkinter as tk
from tkinter import messagebox
class FinanceHelper:
def init (self, root):
[Link] = root
[Link]("Finance Helper")
[Link]("600x700")
self.user_name = ""
[Link] = 0
self.period_type = ""
[Link] = 0
self.total_budget = 0
self.money_spent = 0 # New variable to track money spent
[Link] = [] # List of tuples: (category, subject, money_spent)
self.budget_goals = {}
self.initial_investment = 0
self.periodic_investment = 0
self.investment_growth_rate = 0
self.investment_periods = 0
self.create_widgets()
def create_widgets(self):
[Link] = [Link]([Link], text="Welcome to Finance Helper!",
font=("Arial", 16, "bold"))
[Link](pady=20, anchor="center")
self.name_label = [Link]([Link], text="Enter your name:",
font=("Arial", 12))
self.name_label.pack(pady=10, anchor="center")
self.name_entry = [Link]([Link], font=("Arial", 12), width=30,
justify="center")
self.name_entry.pack(pady=10)
self.submit_button = [Link]([Link], text="Submit", font=("Arial",
12), width=15, command=self.submit_name)
self.submit_button.pack(pady=15)
def submit_name(self):
self.user_name = self.name_entry.get().strip()
if not self.user_name:
[Link]("Error", "Name cannot be empty!")
return
[Link](text=f"Welcome, {self.user_name}!")
self.name_label.pack_forget()
self.name_entry.pack_forget()
self.submit_button.pack_forget()
self.choose_period()
def choose_period(self):
self.period_label = [Link]([Link], text="Choose your budget period:",
font=("Arial", 14, "bold"))
self.period_label.pack(pady=15, anchor="center")
self.month_button = [Link]([Link], text="By Months",
font=("Arial", 12), width=15, command=lambda: self.start_budget("month"))
self.month_button.pack(pady=10)
self.year_button = [Link]([Link], text="By Years", font=("Arial",
12), width=15, command=lambda: self.start_budget("year"))
self.year_button.pack(pady=10)
def start_budget(self, period_type):
self.period_type = period_type
self.period_label.pack_forget()
self.month_button.pack_forget()
self.year_button.pack_forget()
self.income_label = [Link]([Link], text=f"Enter your {period_type}ly
income:", font=("Arial", 12))
self.income_label.pack(pady=10, anchor="center")
self.income_entry = [Link]([Link], font=("Arial", 12), width=25,
justify="center")
self.income_entry.pack(pady=10)
self.period_count_label = [Link]([Link], text=f"Enter the number of
{period_type}s:", font=("Arial", 12))
self.period_count_label.pack(pady=10, anchor="center")
self.period_count_entry = [Link]([Link], font=("Arial", 12),
width=25, justify="center")
self.period_count_entry.pack(pady=10)
self.start_button = [Link]([Link], text="Set Income", font=("Arial",
12), width=15, command=self.setup_budget_goals)
self.start_button.pack(pady=15)
def setup_budget_goals(self):
try:
[Link] = float(self.income_entry.get().strip())
[Link] = int(self.period_count_entry.get().strip())
if [Link] <= 0 or [Link] <= 0:
raise ValueError("Income and periods must be positive numbers")
except ValueError as e:
[Link]("Error", str(e))
return
for widget in [self.income_label,
self.income_entry, self.period_count_label,
self.period_count_entry, self.start_button]:
widget.pack_forget()
total_budget = [Link] * [Link]
self.budget_label = [Link]([Link],
text=f"Total Budget Available: rs{total_budget:,.2f}",
font=("Arial", 14, "bold"))
self.budget_label.pack(pady=20, anchor="center")
# Show budget summary first
budget_summary = f"Budget Summary:\n\n"
budget_summary += f"Income per {self.period_type}:
rs{[Link]:,.2f}\n"
budget_summary += f"Number of {self.period_type}s: {[Link]}\n"
budget_summary += f"Total Budget: rs{total_budget:,.2f}"
self.summary_label = [Link]([Link], text=budget_summary,
font=("Arial", 12), justify="left")
self.summary_label.pack(pady=20, anchor="center")
# Then show goal setting options
self.goal_label = [Link]([Link], text="Set your budget goals for
different categories:",
font=("Arial", 12))
self.goal_label.pack(pady=15, anchor="center")
self.category_label = [Link]([Link], text="Category Name:",
font=("Arial", 12))
self.category_label.pack(pady=10, anchor="center")
self.category_entry = [Link]([Link], font=("Arial", 12), width=25,
justify="center")
self.category_entry.pack(pady=10)
self.goal_amount_label = [Link]([Link], text="Budget Goal (rs):",
font=("Arial", 12))
self.goal_amount_label.pack(pady=10, anchor="center")
self.goal_amount_entry = [Link]([Link], font=("Arial", 12),
width=25, justify="center")
self.goal_amount_entry.pack(pady=10)
self.add_goal_button = [Link]([Link], text="Add Goal",
font=("Arial", 12), width=15,
command=self.save_budget_goal)
self.add_goal_button.pack(pady=10)
self.finish_goals_button = [Link]([Link], text="Finish Setting
Goals",
font=("Arial", 12), width=20,
command=self.setup_expenses)
self.finish_goals_button.pack(pady=15)
self.goals_display = [Link]([Link], text="Current Goals:",
font=("Arial", 12, "bold"))
self.goals_display.pack(pady=15, anchor="center")
def save_budget_goal(self):
category = self.category_entry.get().strip()
try:
goal_amount = float(self.goal_amount_entry.get().strip())
if goal_amount <= 0:
raise ValueError("Budget goal must be a positive number")
if goal_amount > ([Link] * [Link]):
raise ValueError("Goal amount cannot be greater than total
budget")
except ValueError as e:
[Link]("Error", str(e))
return
if not category:
[Link]("Error", "Category cannot be empty!")
return
self.budget_goals[category] = goal_amount
# Update goals display with percentage of total budget
total_budget = [Link] * [Link]
goals_text = "Current Goals:\n\n"
total_allocated = 0
for cat, amount in self.budget_goals.items():
percentage = (amount / total_budget) * 100
goals_text += f"{cat}: rs{amount:,.2f} ({percentage:.1f}% of budget)\n"
total_allocated += amount
remaining_budget = total_budget - total_allocated
remaining_percentage = (remaining_budget / total_budget) * 100
goals_text += f"\nRemaining Unallocated: rs{remaining_budget:,.2f}
({remaining_percentage:.1f}% of budget)"
self.goals_display.config(text=goals_text)
[Link]("Success", f"Added goal: {category} -
rs{goal_amount:,.2f}")
self.category_entry.delete(0, [Link])
self.goal_amount_entry.delete(0, [Link])
def setup_expenses(self):
if not self.budget_goals:
[Link]("Error", "Please add at least one budget
goal!")
return
for widget in [self.goal_label, self.category_label, self.category_entry,
self.goal_amount_label, self.goal_amount_entry,
self.add_goal_button, self.finish_goals_button,
self.goals_display]:
widget.pack_forget()
self.budget_label.pack(pady=20, anchor="center")
categories_text = "Budget Categories:"
for category, goal in self.budget_goals.items():
categories_text += f"\n{category}: rs{goal:,.2f}"
self.categories_label = [Link]([Link], text=categories_text,
font=("Arial", 10))
self.categories_label.pack(pady=4, anchor="center")
self.expenses_label = [Link]([Link], text="Enter your expenses:",
font=("Arial", 10, "bold"))
self.expenses_label.pack(pady=4, anchor="center")
self.expense_category_label = [Link]([Link], text="Select Category:",
font=("Arial", 10))
self.expense_category_label.pack(pady=3, anchor="center")
self.expense_category_var = [Link]([Link])
self.expense_category_var.set("Select Category") # default value
self.expense_category_menu = [Link]([Link],
self.expense_category_var, *self.budget_goals.keys())
self.expense_category_menu.config(font=("Arial", 10))
self.expense_category_menu.pack(pady=3)
self.expense_item_label = [Link]([Link], text="Subject Name:",
font=("Arial", 10))
self.expense_item_label.pack(pady=3, anchor="center")
self.expense_item_entry = [Link]([Link], font=("Arial", 10),
width=25, justify="center")
self.expense_item_entry.pack(pady=3)
self.expense_cost_label = [Link]([Link], text="Money Spent (rs):",
font=("Arial", 10))
self.expense_cost_label.pack(pady=3, anchor="center")
self.expense_cost_entry = [Link]([Link], font=("Arial", 10),
width=25, justify="center")
self.expense_cost_entry.pack(pady=3)
self.add_expense_button = [Link]([Link], text="Add Expense",
font=("Arial", 10), width=15, command=self.save_expense)
self.add_expense_button.pack(pady=4)
self.finish_expenses_button = [Link]([Link], text="Finish & Show
Summary",
font=("Arial", 10), width=20,
command=self.show_summary)
self.finish_expenses_button.pack(pady=4)
self.investment_button = [Link]([Link], text="Investment
Planning",
font=("Arial", 10), width=20,
command=self.open_investment_window)
self.investment_button.pack(pady=4)
def save_expense(self):
category = self.expense_category_var.get()
subject = self.expense_item_entry.get().strip()
try:
money_spent = float(self.expense_cost_entry.get().strip())
if money_spent <= 0:
raise ValueError("Money spent must be a positive number")
except ValueError as e:
[Link]("Error", str(e))
return
if category == "Select Category":
[Link]("Error", "Please select a category!")
return
if not subject:
[Link]("Error", "Subject name cannot be empty!")
return
[Link]((category, subject, money_spent))
self.money_spent += money_spent
remaining = ([Link] * [Link]) - self.money_spent
[Link]("Success", f"Added expense: {subject} ({category})
- rs{money_spent:,.2f}\nRemaining Money: rs{remaining:,.2f}")
self.expense_category_var.set("Select Category")
self.expense_item_entry.delete(0, [Link])
self.expense_cost_entry.delete(0, [Link])
self.budget_label.config(text=f"Remaining Money: rs{remaining:,.2f}")
def open_investment_window(self):
self.investment_window = [Link]([Link])
self.investment_window.title("Investment Planning")
self.investment_window.geometry("400x400")
self.investment_label = [Link](self.investment_window, text="Enter
your investment details:", font=("Arial", 12))
self.investment_label.pack(pady=10, anchor="center")
self.initial_investment_label = [Link](self.investment_window,
text="Initial Investment (rs):", font=("Arial", 12))
self.initial_investment_label.pack(pady=10, anchor="center")
self.initial_investment_entry = [Link](self.investment_window,
font=("Arial", 12), width=20, justify="center")
self.initial_investment_entry.pack(pady=10)
self.periodic_investment_label = [Link](self.investment_window,
text="Periodic Investment (rs):", font=("Arial", 12))
self.periodic_investment_label.pack(pady=10, anchor="center")
self.periodic_investment_entry = [Link](self.investment_window,
font=("Arial", 12), width=20, justify="center")
self.periodic_investment_entry.pack(pady=10)
self.growth_rate_label = [Link](self.investment_window,
text="Investment Growth Rate (% per year):", font=("Arial", 12))
self.growth_rate_label.pack(pady=10, anchor="center")
self.growth_rate_entry = [Link](self.investment_window, font=("Arial",
12), width=20, justify="center")
self.growth_rate_entry.pack(pady=10)
self.investment_period_label = [Link](self.investment_window,
text="Number of Years:", font=("Arial", 12))
self.investment_period_label.pack(pady=10, anchor="center")
self.investment_period_entry = [Link](self.investment_window,
font=("Arial", 12), width=20, justify="center")
self.investment_period_entry.pack(pady=10)
self.save_investment_button = [Link](self.investment_window,
text="Save Investment Plan", font=("Arial", 12), width=20,
command=self.save_investment_plan)
self.save_investment_button.pack(pady=15)
def save_investment_plan(self):
try:
self.initial_investment =
float(self.initial_investment_entry.get().strip())
self.periodic_investment =
float(self.periodic_investment_entry.get().strip())
self.investment_growth_rate =
float(self.growth_rate_entry.get().strip())
self.investment_periods =
int(self.investment_period_entry.get().strip())
if any(x <= 0 for x in [self.initial_investment,
self.periodic_investment, self.investment_periods]):
raise ValueError("All investment values must be positive
numbers")
if self.investment_growth_rate < 0:
raise ValueError("Growth rate cannot be negative")
except ValueError as e:
[Link]("Error", str(e))
return
[Link]("Success", "Investment plan saved successfully!")
self.investment_window.destroy()
self.calculate_investment_plan()
def calculate_investment_plan(self):
final_amount = self.initial_investment
for _ in range(self.investment_periods):
final_amount += self.periodic_investment
final_amount *= (1 + self.investment_growth_rate / 100)
investment_summary = f"Initial Investment:
rs{self.initial_investment:,.2f}\n"
investment_summary += f"Periodic Investment:
rs{self.periodic_investment:,.2f}\n"
investment_summary += f"Growth Rate:
{self.investment_growth_rate:.2f}% per year\n"
investment_summary += f"Final Amount after {self.investment_periods}
years: rs{final_amount:,.2f}"
summary_window = [Link]([Link])
summary_window.title("Investment Summary")
summary_window.geometry("400x300")
[Link](summary_window, text="Investment Summary", font=("Arial",
14, "bold")).pack(pady=15, anchor="center")
[Link](summary_window, text=investment_summary, font=("Arial",
12)).pack(pady=10, anchor="center")
def show_summary(self):
for widget in [Link].winfo_children():
widget.pack_forget()
main_frame = [Link]([Link])
main_frame.pack(fill=[Link], expand=1)
canvas = [Link](main_frame)
[Link](side=[Link], fill=[Link], expand=1)
scrollbar = [Link](main_frame, orient=[Link],
command=[Link])
[Link](side=[Link], fill=tk.Y)
[Link](yscrollcommand=[Link])
[Link]('<Configure>', lambda e:
[Link](scrollregion=[Link]("all")))
summary_frame = [Link](canvas)
canvas.create_window((0, 0), window=summary_frame, anchor="nw")
summary_label = [Link](summary_frame, text="Budget Summary",
font=("Arial", 16, "bold"))
summary_label.pack(pady=20, anchor="center")
total_salary = [Link] * [Link]
remaining_money = total_salary - self.money_spent
[Link](summary_frame, text=f"Total Income: rs{total_salary:,.2f}",
font=("Arial", 14, "bold")).pack(pady=15, anchor="center")
subject_expenses = {}
for _, subject, money_spent in [Link]:
if subject in subject_expenses:
subject_expenses[subject] += money_spent
else:
subject_expenses[subject] = money_spent
if subject_expenses:
[Link](summary_frame, text="Money Spent by Subject:",
font=("Arial", 14, "bold")).pack(pady=15, anchor="center")
for subject, total_spent in subject_expenses.items():
expense_text = f"{subject}: rs{total_spent:,.2f}"
[Link](summary_frame, text=expense_text, font=("Arial",
12)).pack(padx=20, anchor="center")
for category, goal in self.budget_goals.items():
category_frame = [Link](summary_frame, relief=[Link],
bd=2)
category_frame.pack(fill=tk.X, padx=20, pady=10)
category_expenses = [(subject, money_spent) for cat, subject,
money_spent in [Link] if cat == category]
total_category_spent = sum(money_spent for _, money_spent in
category_expenses)
summary_text = f"{category} (Goal: rs{goal:,.2f}, Total Spent:
rs{total_category_spent:,.2f})"
summary_color = "green" if total_category_spent <= goal else "red"
[Link](category_frame, text=summary_text, font=("Arial", 12,
"bold"),
fg=summary_color).pack(pady=10, anchor="center")
if category_expenses:
for subject, money_spent in category_expenses:
expense_text = f"• {subject}: rs{money_spent:,.2f}"
[Link](category_frame, text=expense_text, font=("Arial",
11)).pack(padx=30, pady=5, anchor="center")
else:
[Link](category_frame, text="No expenses recorded",
font=("Arial", 11, "italic")).pack(padx=30, pady=5, anchor="center")
[Link](summary_frame, height=1, bg="gray").pack(fill=tk.X,
padx=20, pady=5)
[Link](summary_frame, text=f"Money Spent:
rs{self.money_spent:,.2f}",
font=("Arial", 14, "bold")).pack(pady=15, anchor="center")
remaining_color = "blue" if remaining_money >= 0 else "red"
[Link](summary_frame, text=f"Remaining Money:
rs{remaining_money:,.2f}",
font=("Arial", 14, "bold"), fg=remaining_color).pack(pady=15,
anchor="center")
if total_salary > 0:
savings_percentage = (remaining_money / total_salary) * 100
savings_text = f"Savings: {savings_percentage:.1f}% of income"
savings_color = "green" if savings_percentage >= 20 else "orange" if
savings_percentage >= 10 else "red"
[Link](summary_frame, text=savings_text, font=("Arial", 14, "bold"),
fg=savings_color).pack(pady=15, anchor="center")
if name == " main ":
root = [Link]()
app = FinanceHelper(root)
[Link]()