tkinterでDateEntryを作ってみました

オリジナルの DateEntry を作成してみました

<h2>customtkinter ver</h2>

```python
import customtkinter
import re


class DateEntry(customtkinter.CTkEntry):
    def __init__(self, parent):
        super().__init__(parent)
        self.insert(0, "1990/01/01")
        self.bind('<Escape>', self.entry_escape)
        self.bind('<BackSpace>', self.entry_backspace)
        self.bind('<KeyRelease>', self.after_entry_char)


    def entry_backspace(self, event):
        index_deleting_char = self.index(customtkinter.INSERT) - 1
        if index_deleting_char < 0:
            return
        if self.get()[index_deleting_char] == "/":
            self.insert(index_deleting_char, '/')


    def entry_escape(self, event):
        self.delete(0, "end")
        self.insert(0, "//")


    def after_entry_char(self, event):
        if event.keysym == "Right":
            self.press_right()
            return
        if event.keysym == "Left":
            self.press_left()
            return

        if event.keysym == "slash":
            self.delete(self.index(customtkinter.INSERT) - 1)
            return

        entried_text = self.get()
        if len(re.findall(r"[^\d/]", entried_text)) > 0:
            self.delete(0, "end")
            self.insert(0, re.sub(r"[^\d/]", "", entried_text))

        if len(entried_text) == 0:
            self.insert(0, '//')
            self.icursor(0)


    def press_right(self):
        index_cursor = self.index(customtkinter.INSERT)
        entred_text = self.get()
        if index_cursor < len(entred_text) and re.search(r'^/\d', entred_text[index_cursor-1:]):
            self.icursor(index_cursor+1)


    def press_left(self):
        index_previous_cursor = self.index(customtkinter.INSERT) - 1
        entred_text = self.get()
        if index_previous_cursor > 0 and re.search(r'^/\d', entred_text[index_previous_cursor:]):
            self.icursor(index_previous_cursor)
```

<h2> tkinter ver</h2>

```python
from tkinter import ttk
import tkinter as tk
import re



class DateEntry(ttk.Entry):
    def __init__(self, parent):
        super().__init__(parent)
        self.insert(0, "1990/01/01")
        self.bind('<Escape>', self.entry_escape)
        self.bind('<BackSpace>', self.entry_backspace)
        self.bind('<KeyRelease>', self.after_entry_char)


    def entry_backspace(self, event):
        index_deleting_char = self.index(tk.INSERT) - 1
        if index_deleting_char < 0:
            return
        if self.get()[index_deleting_char] == "/":
            self.insert(index_deleting_char, '/')


    def entry_escape(self, event):
        self.delete(0, "end")
        self.insert(0, "//")


    def after_entry_char(self, event):
        if event.keysym == "Right":
            self.press_right()
            return
        if event.keysym == "Left":
            self.press_left()
            return

        if event.keysym == "slash":
            self.delete(self.index(tk.INSERT) - 1)
            return

        entried_text = self.get()
        if len(re.findall(r"[^\d/]", entried_text)) > 0:
            self.delete(0, "end")
            self.insert(0, re.sub(r"[^\d/]", "", entried_text))

        if len(entried_text) == 0:
            self.insert(0, '//')
            self.icursor(0)


    def press_right(self):
        index_cursor = self.index(tk.INSERT)
        entred_text = self.get()
        if index_cursor < len(entred_text) and re.search(r'^/\d', entred_text[index_cursor-1:]):
            self.icursor(index_cursor+1)


    def press_left(self):
        index_previous_cursor = self.index(tk.INSERT) - 1
        entred_text = self.get()
        if index_previous_cursor > 0 and re.search(r'^/\d', entred_text[index_previous_cursor:]):
            self.icursor(index_previous_cursor)
```

作成してみて、変数名や関数名、関数の使い方など気になる点は多々あるのですが
bind や カーソルなどの理解を深めることができたかなと思います。

<h3>追記</h3>
バグがあったので修正しました...

<h2>参考資料</h2>
<a href="https://docs.python.org/ja/3/library/tkinter.html">
 tkinter document
</a>
<br>
<a href="https://dob-kids.com/2021/03/18/python-tkcalender1/">
PythonのTkinterでカレンダー(datepicker)を使用する
</a>
<br>
<a href="https://www.tutorialspoint.com/getting-the-cursor-position-in-tkinter-entry-widget">
Getting the Cursor position in Tkinter Entry widget
</a>
<br>
<a href="https://stackoverflow.com/questions/28467285/how-do-i-bind-the-escape-key-to-close-this-window">
How do I bind the escape key to close this window
</a>
<br>