eldoc/app.py

149 lines
5.9 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import gi
import os
gi.require_version('Gtk', '3.0')
from gi.repository import Gtk, GObject
from mods.db import Patient, store_patient_index, search_patients, db
from datetime import date
import peewee
resource_dir = os.path.join(os.path.dirname(os.path.abspath(__file__)), 'res')
ui_dir = os.path.join(resource_dir, 'ui')
main_win_file = os.path.join(ui_dir, 'main_win.glade')
new_patient_win_file = os.path.join(ui_dir, 'new_patient_win.glade')
builder = Gtk.Builder()
class PatientFilter:
def __init__(self):
self.reset()
def filter(self, query):
if query != self.fstr:
self.fstr = query
self.ids = list(map(lambda x: x.id, search_patients(query)))
return self.ids
def reset(self):
self.fstr = ''
self.ids = []
patient_filter = PatientFilter()
class PatientRow(Gtk.ListBoxRow):
@GObject.Property
def db_id(self):
return self._db_id
@db_id.setter
def my_custom_property(self, value):
self._db_id = value
class MainWinHandler:
def main_win_close(self, *args):
Gtk.main_quit()
def show_new_patient_win(self, button):
new_patient_win = create_new_patient_win()
new_patient_win.show_all()
def patient_filter_changed(self, filter_widget):
pl = builder.get_object('patient_list')
pl.unselect_all()
pl.invalidate_filter()
'''pl = builder.get_object('patient_list')
for r in pl.get_children():
pl.remove(r)
fstr = builder.get_object('patient_filter').get_text().strip()
if not fstr:
for p in Patient.select():
pl.add(build_patient_row(p))
else:
patients = search_patients(fstr)
for p in patients:
pl.add(build_patient_row(p))
pl.show_all()'''
def build_patient_row(patient):
row = PatientRow()
row.props.db_id = patient.id
label = Gtk.Label(f'{" ".join([patient.last_name, patient.first_name, patient.middle_name])}, {patient.birth_date}', xalign=0)
row.add(label)
return row
def patient_sort_func(row1, row2, *a):
text1 = row1.get_children()[0].get_text()
text2 = row2.get_children()[0].get_text()
return (text1 > text2) - (text1 < text2)
def patient_filter_func(row):
fstr = builder.get_object('patient_filter').get_text().strip()
if not fstr:
patient_filter.reset()
return True
return row.props.db_id in patient_filter.filter(fstr)
builder.add_from_file(main_win_file)
builder.connect_signals(MainWinHandler())
patient_list = builder.get_object('patient_list')
patient_list.set_sort_func(patient_sort_func)
patient_list.set_filter_func(patient_filter_func)
with db.atomic():
for p in Patient.select():
patient_list.add(build_patient_row(p))
def show_msg(text, sec_text='', level='info'):
msg_win_file = os.path.join(ui_dir, f'{level}_win.glade')
b = Gtk.Builder()
b.add_from_file(msg_win_file)
w = b.get_object(level)
w.set_property('text',text)
w.set_property('secondary_text',sec_text)
w.run()
w.close()
def create_new_patient_win():
b = Gtk.Builder()
class NewPatienWinHandler:
def only_digits(self, entry):
text = entry.get_text()
text = ''.join(filter(lambda x: x.isdigit(), text))
entry.set_text(text)
def save_patient(self, *args):
l_name = b.get_object('last_name').get_text().replace(' ', '')
f_name = b.get_object('first_name').get_text().replace(' ', '')
m_name = b.get_object('middle_name').get_text().replace(' ', '')
if '' in (l_name, f_name):
return show_msg('Не указаны имя или фамилия', 'Данные поля должны быть заполнены', level='warn')
try:
birth_d = int(b.get_object('birth_day').get_text())
if birth_d < 1 or birth_d > 31:
return show_msg('Неверный день месяца', 'Укажите число в диапазоне 1-31', level='warn')
birth_m = int(b.get_object('birth_month').get_text())
if birth_m < 1 or birth_m > 12:
return show_msg('Неверный номер месяца', 'Укажите число в диапазоне 1-12', level='warn')
birth_y = int(b.get_object('birth_year').get_text())
except ValueError:
return show_msg('Неверно указана дата рождения', 'Все поля даты должны быть заполнены', level='warn')
gender = b.get_object('gender').get_active_id()
if not gender:
return show_msg('Не выбран пол', level='warn')
birth_date = date(birth_y, birth_m, birth_d)
with db.atomic():
try:
patient = Patient.create(
last_name=l_name,
first_name=f_name,
middle_name=m_name,
birth_date=birth_date,
gender=gender
)
except peewee.IntegrityError:
return show_msg('Данный пациент уже существует', 'Пациент с указанными фамилией, именем\nи датой рождения уже есть с базе данных', level='warn')
store_patient_index(patient)
row = build_patient_row(patient)
patient_list.add(row)
patient_list.select_row(row)
patient_list.show_all()
b.get_object('new_patient_window').close()
b.add_from_file(new_patient_win_file)
b.connect_signals(NewPatienWinHandler())
w = b.get_object('new_patient_window')
return w
main_win = builder.get_object('main_window')
main_win.show_all()
Gtk.main()