python 의 Tkinter 모듈을 사용해서 To Do List를 만들어보자 - 1

박재욱·2022년 7월 19일
0

Tkinter_ToDoList

목록 보기
2/2

1. Tkinter으로 달력 만들기

실행화면

code전문

from curses import window
from tkinter import *
import datetime 
import calendar


class button_sort():
    #화살표를 눌러 초기화해야할 경우 원래있던 버튼을 삭제하는 작업 필요함.
    def calendars(self,yyyy,mm):
        monthrange = calendar.monthrange(yyyy, mm)
        weekday = datetime.date(yyyy,mm,1).weekday()
        weekstack = 0

        day = list(range(32))
        for i in range(1, monthrange[1] + 1):
            day[i] = Button(window, text = i, width=7, height= 2)
            day[i].grid(row = 6 + weekstack, column= weekday)
            weekday += 1
            if weekday == 7:
                weekday = 0
                weekstack += 1



now = datetime.datetime.now()

window = Tk() #Tkinter 의 객체 생성
window.title("To Do List")
window.geometry("410x600")

years = Label(window, height =3, text = str(now.year) + "년", font = ("bold", 14))
years.grid(row = 0, column= 0, columnspan= 7)


pastbutton = Button(window, text = "←")
pastbutton.grid(row = 2, column= 2)

months = Label(window, height = 1, text= str(now.month) + "월", font = ("bold", 14))
months.grid(row = 2, column= 3)

futerbutton = Button(window, text="→")
futerbutton.grid(row = 2, column= 4)


mon = Label(window,text = "MON",width=7)
mon.grid(row= 5, column = 0)

tue = Label(window,text = "TUE",width=7)
tue.grid(row= 5, column = 1)

wed = Label(window,text = "WED",width=7)
wed.grid(row= 5, column = 2)

thu = Label(window,text = "THU",width=7)
thu.grid(row= 5, column = 3)

fri = Label(window,text = "FRI",width=7)
fri.grid(row= 5, column = 4)

sat = Label(window,text = "SAT",width=7)
sat.grid(row= 5, column = 5)

sun = Label(window,text = "SUN",width=7)
sun.grid(row= 5, column = 6)


cal = button_sort()
cal.calendars(now.year, now.month)

window.mainloop()

1. code설명

1-1. 참조부분

from tkinter import * #tkinter를 참조해서 gui를 쓰는것이 목적
import datetime #calendar 모듈과 함께 현재 또는 특정 날짜의 년 월 일 정보를 추출하기 위해서 참조
import calendar

1-2. main부분

1-2-1 년, 월 부분
years = Label(window, height =3, text = str(now.year) + "년", font = ("bold", 14))
years.grid(row = 0, column= 0, columnspan= 7)


pastbutton = Button(window, text = "←")
pastbutton.grid(row = 2, column= 2)

months = Label(window, height = 1, text= str(now.month) + "월", font = ("bold", 14))
months.grid(row = 2, column= 3)

futerbutton = Button(window, text="→")
futerbutton.grid(row = 2, column= 4)

요 부분에서 많이 헤매었는데, Tkinter의 위젯(라벨,버튼 등)의 배치 방식이 3가지가 있고, 저는 일단 아무거나 써도 정렬이 될 거라 생각했습니다. 그런데 그렇지가 않았고 프로그램의 완성되어질 모습을 생각하면서 선택하니 grid 메서드를 이용하는게 지금 만들 달력과 같은 표를 작성할 때는 적절하다는 결론이 나왔고 적용해 봤습니다.

위젯 배치 3method

1.pack()
pack 메서드는 다른 인자가 있지 않는 한 사용되어지는 순서대로 세로로 정렬되어집니다.
많은 위젯이 필요없고 세밀한 배치가 필요없을때 사용할 듯 합니다.

2.place()
place 메서드는 인자로 x,y 좌표값을 받아서 위젯을 배치합니다.
정말 세밀한 배치가 필요한 프로그램을 만들 때 사용할 것 같습니다.

3.grid()
grid 메서드는 인자로 row, column 값을 받아서 위젯을 베치합니다.
표를 작성할 때 편리하고 위젯을 배치할 때 다른 위젯과의 상대적인 위치를 생각하면서 배치하면 되기 때문에 편리하고 place를 사용할 때 나타나는 문제점인 각 위젯이 겹치지 않는 점이 편했습니다.

둘째 줄을 보면 row, column 외에 columnspan = 7을 쓴 것을 볼 수 있는데, 라벨이라 경계선이 보이지 않지만 7개의 열을 합쳐서 년도를 중앙으로 정렬하려고 한 것입니다.
밑의 화살표와 월 을 표시하는 부분은 위젯을 합치면 안되므로 각 column값에 3,4,5를 넣어 정렬했습니다.
밑의 요일표시 부분은 같은 메커니즘 이므로 설명은 생략하겠습니다.

1-3 Button_sort함수 부분

class button_sort():
    #화살표를 눌러 초기화해야할 경우 원래있던 버튼을 삭제하는 작업 필요함.
    def calendars(self,yyyy,mm):
        monthrange = calendar.monthrange(yyyy, mm)
        weekday = datetime.date(yyyy,mm,1).weekday()
        weekstack = 0

        day = list(range(30))
        for i in range(1, monthrange[1] + 1):
            day[i] = Button(window, text = i, width=7, height= 2)
            day[i].grid(row = 6 + weekstack, column= weekday)
            weekday += 1
            if weekday == 7:
                weekday = 0
                weekstack += 1

오늘 하면서 제일 힘들었던 부분입니다. 그냥 달력만들기 였다면 많이 생각할 부분은 없었을 텐데 To Do List를 만들기 위해서는 여기서 추가해야할 부분이 많다고 판단했습니다. 일단 지금 구현한 부분만 설명하겠습니다.

이 함수의 calendars메서드는 인자로 년도와 월 을 받습니다. 달력을 작성하기 위해서 필요한 값은 특정 년도의 어느 달의 첫 날짜의 요일과, 마지막 날짜 입니다. 그러기위해서 calendar함수의 monthrange메서드와 datetime의 weekday메서드를 이용했습니다.

monthrange메서드는 인자로 년도와 월을 받고 해당 월의 첫 날짜와 마지막 날짜를 tuple 형식으로 반환합니다 예를들어 2022, 7을 인자로하면 (1,31) 을 반환하게 됩니다.

weekday메서드는 datetime의 객체 date(년,월,일 을 객체로 가지고 있는) 에 사용되는 메서드로 해당 년, 월, 일에 해당하는 요일을 0~6 의 숫자로 return 한다. (0부터 월요일 ~ 6 = 일요일)

나는 달력의 각 날짜를 button으로 만들 계획이므로, day리스트 객체를 만들어서 버튼을 배치하고자 위와 같은 반복문을 만들었다. 반복 범위는 1부터 해당 달의 마지막 날짜인 monthrange[1] + 1 그리고 일요일에서 월요일로 넘어갈 때 다음 행으로 이동해서 작성해야 하므로 if문을 사용하고, weekstack 변수를 만들어 처리했다.

2. 다음에 구현할 것

  1. 화살표 클릭 시 달력을 초기화 하고 달력을 새로 만드는 것
  2. 날짜 버튼을 눌렀을때 하단부분에 텍스트박스를 띄우고 작성하면 데이터베이스에 저장하는 것
  3. 프로그램이 실행 되었을 때 와 화살표 버튼을 클릭해 달력이 초기화 될 때 데이터베이스에서 해당 달에 할당되있는 데이터를 가져오는 것

0개의 댓글