mirror of
https://github.com/aaronleetw/Attendance.git
synced 2024-11-14 19:11:39 -08:00
Day 2, added homeroom vie, date selection, and signatures (pending homeroom confirmation)
This commit is contained in:
parent
f2f280de6b
commit
a47d69a954
6 changed files with 499 additions and 99 deletions
260
app.py
260
app.py
|
@ -1,14 +1,15 @@
|
||||||
from flask import *
|
from flask import *
|
||||||
import pyrebase
|
import pyrebase
|
||||||
from datetime import datetime
|
from datetime import datetime
|
||||||
|
import time
|
||||||
import pytz
|
import pytz
|
||||||
from sendgrid import SendGridAPIClient
|
from sendgrid import SendGridAPIClient
|
||||||
from sendgrid.helpers.mail import Mail
|
from sendgrid.helpers.mail import Mail
|
||||||
import csv
|
import csv
|
||||||
import os
|
import os
|
||||||
# from dotenv import load_dotenv
|
from dotenv import load_dotenv
|
||||||
# from pprint import pprint
|
from pprint import pprint
|
||||||
# load_dotenv()
|
load_dotenv()
|
||||||
app = Flask(__name__)
|
app = Flask(__name__)
|
||||||
|
|
||||||
app.config['SECRET_KEY'] = os.environ.get('SECRET_KEY')
|
app.config['SECRET_KEY'] = os.environ.get('SECRET_KEY')
|
||||||
|
@ -34,6 +35,158 @@ def check_login_status():
|
||||||
(datetime.now(tz) - session['loginTime']).total_seconds() > 3600)
|
(datetime.now(tz) - session['loginTime']).total_seconds() > 3600)
|
||||||
|
|
||||||
|
|
||||||
|
def manageProcess(fCommand, fData):
|
||||||
|
# this is to fix a bug where pyrebase doesnt load the first request
|
||||||
|
db.child("Users").child(
|
||||||
|
session['uid']).child("permission").get().val()
|
||||||
|
# end bug fix
|
||||||
|
pl = db.child("Users").child(
|
||||||
|
session['uid']).child("permission").get().val()
|
||||||
|
print(pl)
|
||||||
|
print(db.child("Users").child(
|
||||||
|
'DRZqqSSpg3OkPSCuWkv417dv0vh1').child("permission").get().val())
|
||||||
|
print(fCommand, fData, session['uid'], pl)
|
||||||
|
if pl == 'admin':
|
||||||
|
return pl
|
||||||
|
elif pl == 'group':
|
||||||
|
classes = db.child("Users").child(
|
||||||
|
session['uid']).child("class").get().val()
|
||||||
|
cclass = {}
|
||||||
|
for i in classes:
|
||||||
|
cclass = {
|
||||||
|
"name": db.child("Classes").child(i).child(
|
||||||
|
"Class").child(classes[i]).child("name").get().val(),
|
||||||
|
"category": i,
|
||||||
|
"class_id": classes[i]
|
||||||
|
}
|
||||||
|
print("got class")
|
||||||
|
students = db.child("Classes").child(cclass['category']).child(
|
||||||
|
"Class").child(cclass['class_id']).child("Students").get().val()
|
||||||
|
print(students['9']['11'])
|
||||||
|
all_stud_list = {}
|
||||||
|
for grade in students:
|
||||||
|
print(grade)
|
||||||
|
all_stud_list[grade] = {}
|
||||||
|
print(type(students[grade]))
|
||||||
|
for homeroom in students[grade]:
|
||||||
|
print(homeroom)
|
||||||
|
roomData = db.child("Homerooms").child(
|
||||||
|
grade).child(homeroom).get().val()
|
||||||
|
all_stud_list[grade][homeroom] = {}
|
||||||
|
if type(students[grade][homeroom]) == list:
|
||||||
|
i = 0
|
||||||
|
for student in students[grade][homeroom]:
|
||||||
|
if student == 0:
|
||||||
|
all_stud_list[grade][homeroom][i] = {
|
||||||
|
"name": roomData[str(i)]["name"],
|
||||||
|
"eng_name": roomData[str(i)]["eng_name"]
|
||||||
|
}
|
||||||
|
i += 1
|
||||||
|
else:
|
||||||
|
for student in students[grade][homeroom]:
|
||||||
|
print(student)
|
||||||
|
all_stud_list[grade][homeroom][student] = {
|
||||||
|
"name": roomData[student]["name"],
|
||||||
|
"eng_name": roomData[student]["eng_name"]
|
||||||
|
}
|
||||||
|
print("got students")
|
||||||
|
dates = db.child("Classes").child(
|
||||||
|
cclass['category']).child("Dates").get().val()
|
||||||
|
status = 0
|
||||||
|
attendance = {}
|
||||||
|
|
||||||
|
if fCommand == 'date':
|
||||||
|
currDate = fData
|
||||||
|
if cclass['class_id'] in dates[currDate]:
|
||||||
|
status = 1
|
||||||
|
for grade in dates[currDate]['Absent']:
|
||||||
|
attendance[grade] = {}
|
||||||
|
for homeroom in dates[currDate]['Absent'][grade]:
|
||||||
|
attendance[grade][homeroom] = {}
|
||||||
|
for student in dates[currDate]['Absent'][grade][homeroom]:
|
||||||
|
attendance[grade][homeroom][student] = 0
|
||||||
|
else:
|
||||||
|
for i in dates:
|
||||||
|
if i >= datetime.now(tz).strftime("%Y-%m-%d"):
|
||||||
|
currDate = i
|
||||||
|
if cclass['class_id'] in dates[currDate]:
|
||||||
|
status = 1
|
||||||
|
for grade in dates[currDate]['Absent']:
|
||||||
|
attendance[grade] = {}
|
||||||
|
for homeroom in dates[currDate]['Absent'][grade]:
|
||||||
|
attendance[grade][homeroom] = {}
|
||||||
|
for student in dates[currDate]['Absent'][grade][homeroom]:
|
||||||
|
attendance[grade][homeroom][student] = 0
|
||||||
|
break
|
||||||
|
dates[i].pop('placeholder')
|
||||||
|
print("got dates")
|
||||||
|
return render_template('group_teach.html', cclass=cclass, all_stud_list=all_stud_list, dates=dates, currDate=currDate, status=status, attendance=attendance)
|
||||||
|
elif pl == 'homeroom':
|
||||||
|
homeroom = db.child("Users").child(
|
||||||
|
session['uid']).child("homeroom").get().val()
|
||||||
|
homeroomCode = homeroom.split('^')
|
||||||
|
homeroom = db.child("Homerooms").child(
|
||||||
|
homeroomCode[0]).child(homeroomCode[1]).get().val()
|
||||||
|
categories = homeroom['Categories'].split('^')
|
||||||
|
currCategory = categories[0]
|
||||||
|
currDate = ""
|
||||||
|
gpClasses = db.child("Classes").child(currCategory).get().val()
|
||||||
|
dates = gpClasses['Dates']
|
||||||
|
confirmedClasses = []
|
||||||
|
status = 0
|
||||||
|
|
||||||
|
if fCommand == 'date':
|
||||||
|
currDate = fData
|
||||||
|
tmp1 = 0
|
||||||
|
tmp2 = 0
|
||||||
|
for k in gpClasses['Class']:
|
||||||
|
if k in dates[currDate]:
|
||||||
|
confirmedClasses.append(k)
|
||||||
|
tmp2 += 1
|
||||||
|
tmp1 += 1
|
||||||
|
if tmp1 == tmp2:
|
||||||
|
status = 1
|
||||||
|
else:
|
||||||
|
for i in dates:
|
||||||
|
if i >= datetime.now(tz).strftime("%Y-%m-%d"):
|
||||||
|
currDate = i
|
||||||
|
tmp1 = 0
|
||||||
|
tmp2 = 0
|
||||||
|
for k in gpClasses['Class']:
|
||||||
|
if k in dates[currDate]:
|
||||||
|
confirmedClasses.append(k)
|
||||||
|
tmp2 += 1
|
||||||
|
tmp1 += 1
|
||||||
|
if tmp1 == tmp2:
|
||||||
|
status = 1
|
||||||
|
break
|
||||||
|
print("got dates")
|
||||||
|
db.child("Classes").child(currCategory).child("Dates")
|
||||||
|
homeroom.pop('Categories')
|
||||||
|
all_stud_list = {}
|
||||||
|
for i in homeroom:
|
||||||
|
all_stud_list[i] = {}
|
||||||
|
all_stud_list[i]['name'] = homeroom[i]['name']
|
||||||
|
all_stud_list[i]['eng_name'] = homeroom[i]['eng_name']
|
||||||
|
all_stud_list[i]['gpClass'] = homeroom[i]['Classes'][currCategory]
|
||||||
|
if all_stud_list[i]['gpClass'] in confirmedClasses:
|
||||||
|
if (homeroomCode[0] in gpClasses['Dates'][currDate]['Absent'] and
|
||||||
|
homeroomCode[1] in gpClasses['Dates'][currDate]['Absent'][homeroomCode[0]] and
|
||||||
|
i in gpClasses['Dates'][currDate]['Absent'][homeroomCode[0]][homeroomCode[1]]):
|
||||||
|
# confirmed by teacher and absent
|
||||||
|
all_stud_list[i]['status'] = 2
|
||||||
|
else:
|
||||||
|
# confirmed by teacher and not absent
|
||||||
|
all_stud_list[i]['status'] = 1
|
||||||
|
else:
|
||||||
|
all_stud_list[i]['status'] = 0 # not yet confirmed by teacher
|
||||||
|
return render_template('homeroom.html', all_stud_list=all_stud_list, currDate=currDate, dates=dates, gpClasses=gpClasses, confirmedClasses=confirmedClasses,
|
||||||
|
currCategory=currCategory, categories=categories, homeroomCode=homeroomCode, status=status)
|
||||||
|
|
||||||
|
else:
|
||||||
|
return redirect('/')
|
||||||
|
|
||||||
|
|
||||||
@ app.route('/', methods=['GET', 'POST'])
|
@ app.route('/', methods=['GET', 'POST'])
|
||||||
def index():
|
def index():
|
||||||
if request.method == 'GET':
|
if request.method == 'GET':
|
||||||
|
@ -60,13 +213,16 @@ def index():
|
||||||
|
|
||||||
@app.route('/manage', methods=['GET'])
|
@app.route('/manage', methods=['GET'])
|
||||||
def manage():
|
def manage():
|
||||||
pl = db.child("Users").child(
|
return manageProcess("", "")
|
||||||
session['uid']).child("permission").get().val()
|
|
||||||
print(pl)
|
|
||||||
s = str(pl)
|
@app.route('/manage/date', methods=['POST'])
|
||||||
if pl == 'admin':
|
def manage_date():
|
||||||
return s
|
return manageProcess("date", request.form['date'])
|
||||||
elif pl == 'group':
|
|
||||||
|
|
||||||
|
@app.route('/manage/group_teach_publish', methods=['POST'])
|
||||||
|
def group_teach_publish():
|
||||||
classes = db.child("Users").child(
|
classes = db.child("Users").child(
|
||||||
session['uid']).child("class").get().val()
|
session['uid']).child("class").get().val()
|
||||||
cclass = {}
|
cclass = {}
|
||||||
|
@ -78,57 +234,25 @@ def manage():
|
||||||
"class_id": classes[i]
|
"class_id": classes[i]
|
||||||
}
|
}
|
||||||
print("got class")
|
print("got class")
|
||||||
students = db.child("Classes").child(cclass['category']).child(
|
cDate = ""
|
||||||
"Class").child(cclass['class_id']).child("Students").get().val()
|
for key in request.form.keys():
|
||||||
all_stud_list = {}
|
print(type(key), key)
|
||||||
for homeroom in students:
|
if key == 'date':
|
||||||
print(homeroom)
|
print('here')
|
||||||
all_stud_list[homeroom] = {}
|
cDate = request.form[key]
|
||||||
if type(students[homeroom]) == list:
|
db.child("Classes").child(cclass['category']).child(
|
||||||
i = 0
|
"Dates").child(request.form[key]).update({'confirmed': 0})
|
||||||
for student in students[homeroom]:
|
db.child("Classes").child(cclass['category']).child(
|
||||||
if student == 0:
|
"Dates").child(request.form[key]).update({cclass['class_id']: request.form['signatureData']})
|
||||||
# print(i)
|
elif key == 'signatureData':
|
||||||
# print(db.child("Homerooms").child(
|
pass
|
||||||
# homeroom).child(i).child("name").get().val())
|
|
||||||
all_stud_list[homeroom][i] = {
|
|
||||||
"name": db.child("Homerooms").child(homeroom).child(i).child("name").get().val(),
|
|
||||||
"eng_name": db.child("Homerooms").child(homeroom).child(i).child("eng_name").get().val(),
|
|
||||||
}
|
|
||||||
i += 1
|
|
||||||
else:
|
else:
|
||||||
for student in students[homeroom]:
|
# spilt string
|
||||||
all_stud_list[homeroom][student] = {
|
id = key.split('^')
|
||||||
"name": db.child("Homerooms").child(homeroom).child(student).child("name").get().val(),
|
print(id)
|
||||||
"eng_name": db.child("Homerooms").child(homeroom).child(student).child("eng_name").get().val(),
|
db.child("Classes").child(cclass['category']).child("Dates").child(
|
||||||
}
|
cDate).child("Absent").child(id[0]).child(id[1]).update({id[2]: 1})
|
||||||
|
return "Success!"
|
||||||
print("got students")
|
|
||||||
# for homeroom in all_stud_list:
|
|
||||||
# for student in all_stud_list[homeroom]:
|
|
||||||
# print("homeroom: ", homeroom)
|
|
||||||
# print("student: ", student)
|
|
||||||
# print("all_stud_list['homeroom']['student']['name']: ",
|
|
||||||
# all_stud_list['homeroom']['student']['name'])
|
|
||||||
# print("all_stud_list['homeroom']['student']['eng_name']: ",
|
|
||||||
# all_stud_list['homeroom']['student']['eng_name'])
|
|
||||||
# get dates
|
|
||||||
dates = db.child("Classes").child(
|
|
||||||
cclass['category']).child("Dates").get().val()
|
|
||||||
for i in dates:
|
|
||||||
dates[i].pop('placeholder')
|
|
||||||
if i >= datetime.now(tz).strftime("%Y-%m-%d"):
|
|
||||||
currDate = i
|
|
||||||
break
|
|
||||||
print("got dates")
|
|
||||||
return render_template('group_teach.html', cclass=cclass, all_stud_list=all_stud_list, dates=dates, currDate=currDate)
|
|
||||||
elif pl == 'homeroom':
|
|
||||||
homeroom = db.child("Users").child(
|
|
||||||
session['uid']).child("homeroom").get().val()
|
|
||||||
s += " " + homeroom # 912
|
|
||||||
return s
|
|
||||||
else:
|
|
||||||
return "no permission"
|
|
||||||
|
|
||||||
|
|
||||||
@ app.route('/upload/homeroom', methods=['GET', 'POST'])
|
@ app.route('/upload/homeroom', methods=['GET', 'POST'])
|
||||||
|
@ -138,6 +262,7 @@ def upload_homeroom():
|
||||||
elif request.method == 'POST':
|
elif request.method == 'POST':
|
||||||
try:
|
try:
|
||||||
# get csv
|
# get csv
|
||||||
|
gradec = request.form['gradeCode']
|
||||||
classc = request.form['classcode']
|
classc = request.form['classcode']
|
||||||
csv_file = request.files['csv']
|
csv_file = request.files['csv']
|
||||||
filepath = os.path.join('./temp', csv_file.filename)
|
filepath = os.path.join('./temp', csv_file.filename)
|
||||||
|
@ -145,14 +270,14 @@ def upload_homeroom():
|
||||||
with open(filepath) as file:
|
with open(filepath) as file:
|
||||||
csv_dict = csv.DictReader(file)
|
csv_dict = csv.DictReader(file)
|
||||||
for row in csv_dict:
|
for row in csv_dict:
|
||||||
db.child("Homerooms").child(
|
db.child("Homerooms").child(gradec).child(
|
||||||
classc).child(row['number']).set(row)
|
classc).child(row['number']).set(row)
|
||||||
# row['class'] row['number'] row['name'] row['eng_name']
|
# row['class'] row['number'] row['name'] row['eng_name']
|
||||||
os.remove(filepath)
|
os.remove(filepath)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
os.remove(filepath)
|
os.remove(filepath)
|
||||||
return "Error. Please try again\n("+str(e)+")"
|
return "Error. Please try again\n("+str(e)+")"
|
||||||
return "Successfully uploaded " + classc
|
return "Successfully uploaded " + gradec + "-" + classc
|
||||||
|
|
||||||
|
|
||||||
@ app.route('/upload/stud_in_group', methods=['GET', 'POST'])
|
@ app.route('/upload/stud_in_group', methods=['GET', 'POST'])
|
||||||
|
@ -161,6 +286,7 @@ def upload_stud_in_group():
|
||||||
return render_template('uploadcsv.html', title="Student in Group List", url="/upload/stud_in_group")
|
return render_template('uploadcsv.html', title="Student in Group List", url="/upload/stud_in_group")
|
||||||
elif request.method == 'POST':
|
elif request.method == 'POST':
|
||||||
try:
|
try:
|
||||||
|
gradec = request.form['gradeCode']
|
||||||
classc = request.form['classcode']
|
classc = request.form['classcode']
|
||||||
csv_file = request.files['csv']
|
csv_file = request.files['csv']
|
||||||
filepath = os.path.join('./temp', csv_file.filename)
|
filepath = os.path.join('./temp', csv_file.filename)
|
||||||
|
@ -171,16 +297,16 @@ def upload_stud_in_group():
|
||||||
headers = headers[1:]
|
headers = headers[1:]
|
||||||
for row in csv_dict:
|
for row in csv_dict:
|
||||||
for h in headers:
|
for h in headers:
|
||||||
db.child("Homerooms").child(classc).child(
|
db.child("Homerooms").child(gradec).child(classc).child(
|
||||||
row['number']).child("Classes").child(h).set(row[h])
|
row['number']).child("Classes").child(h).set(row[h])
|
||||||
db.child("Classes").child(h).child("Class").child(row[h]).child(
|
db.child("Classes").child(h).child("Class").child(row[h]).child(
|
||||||
"Students").child(classc).update({str(row['number']): 0})
|
"Students").child(gradec).child(classc).update({str(row['number']): 0})
|
||||||
|
|
||||||
os.remove(filepath)
|
os.remove(filepath)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
os.remove(filepath)
|
os.remove(filepath)
|
||||||
return "Error. Please try again\n("+str(e)+")"
|
return "Error. Please try again\n("+str(e)+")"
|
||||||
return "Successfully uploaded " + classc
|
return "Successfully uploaded " + gradec + "-" + classc
|
||||||
|
|
||||||
|
|
||||||
# @ app.route('/upload/rm_all_data_of_class', methods=['GET', "POST"])
|
# @ app.route('/upload/rm_all_data_of_class', methods=['GET', "POST"])
|
||||||
|
@ -202,5 +328,5 @@ def logout():
|
||||||
return redirect('/')
|
return redirect('/')
|
||||||
|
|
||||||
|
|
||||||
# if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
# app.run(debug=True)
|
app.run(debug=True)
|
||||||
|
|
|
@ -1,3 +1,47 @@
|
||||||
div.col .row .col {
|
div.col .row .col {
|
||||||
border: 1px solid black;
|
border: 1px solid black;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
div.signatures {
|
||||||
|
margin-top: 30px;
|
||||||
|
}
|
||||||
|
|
||||||
|
div.signatures .col .row {
|
||||||
|
border: 1px solid black;
|
||||||
|
}
|
||||||
|
|
||||||
|
div.forSign {
|
||||||
|
border: 1px solid black;
|
||||||
|
margin-left: 10%;
|
||||||
|
margin-right: 10%;
|
||||||
|
width: 80%;
|
||||||
|
height: 300px;
|
||||||
|
position: relative;
|
||||||
|
-webkit-box-flex: 1;
|
||||||
|
-ms-flex: 1;
|
||||||
|
flex: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
div.forSign canvas {
|
||||||
|
position: absolute;
|
||||||
|
left: 0;
|
||||||
|
top: 0;
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
p.highlightAbs {
|
||||||
|
margin-bottom: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
p.highlightAbs.n-1 {
|
||||||
|
color: blue;
|
||||||
|
}
|
||||||
|
|
||||||
|
p.highlightAbs.n-2 {
|
||||||
|
color: red;
|
||||||
|
}
|
||||||
|
|
||||||
|
div.classlist {
|
||||||
|
text-align: left;
|
||||||
|
}
|
1
temp/placeholderfile.txt
Normal file
1
temp/placeholderfile.txt
Normal file
|
@ -0,0 +1 @@
|
||||||
|
this is just so that /temp doesn't disappear
|
|
@ -13,30 +13,102 @@
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body>
|
<body>
|
||||||
|
<div class="container">
|
||||||
<h1>Group_Teach_View</h1>
|
<h1>Group_Teach_View</h1>
|
||||||
<h2>{{cclass['category']}}: {{cclass['class_id']}}: {{cclass['name']}}</h2>
|
<h2>{{cclass['category']}}: {{cclass['class_id']}}: {{cclass['name']}}</h2>
|
||||||
|
<h2>Status: {{status}} ({{currDate}})</h2>
|
||||||
|
<form action="/manage/date" id="dateSelForm" method="post">
|
||||||
|
<select name="date" id="date" class="form-select" onchange="chgDate(this);">
|
||||||
|
{% for date in dates %}
|
||||||
|
{% if date == currDate %}
|
||||||
|
<option value="{{date}}" selected="selected">{{date}}</option>
|
||||||
|
{% else %}
|
||||||
|
<option value="{{date}}">{{date}}</option>
|
||||||
|
{% endif %}
|
||||||
|
{% endfor %}
|
||||||
|
</select>
|
||||||
|
</form>
|
||||||
|
{% if status == 1 %}
|
||||||
|
<div class="alert alert-warning" role="alert">
|
||||||
|
Already Sumitted!
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
{% if status == 0 %}
|
||||||
|
<form action="/manage/group_teach_publish" id="attendanceData" method="post">
|
||||||
|
<input type="hidden" name="date" value="{{currDate}}">
|
||||||
|
<input type="hidden" name="signatureData" value="">
|
||||||
<div class="col">
|
<div class="col">
|
||||||
<div class="row title">
|
<div class="row title">
|
||||||
|
<div class="col">Grade</div>
|
||||||
<div class="col">Class Code</div>
|
<div class="col">Class Code</div>
|
||||||
<div class="col">Number</div>
|
<div class="col">Number</div>
|
||||||
<div class="col">Name</div>
|
<div class="col">Name</div>
|
||||||
<div class="col">Eng Name</div>
|
<div class="col">Eng Name</div>
|
||||||
<div class="col">Attendance</div>
|
<div class="col">Attendance (Check Absent)</div>
|
||||||
</div>
|
</div>
|
||||||
{% if data != None %}
|
{% if data != None %}
|
||||||
{% for homeroom in all_stud_list %}
|
{% for grade in all_stud_list %}
|
||||||
{% for student in all_stud_list[homeroom] %}
|
{% for homeroom in all_stud_list[grade] %}
|
||||||
|
{% for student in all_stud_list[grade][homeroom] %}
|
||||||
<div class="row">
|
<div class="row">
|
||||||
|
<div class="col">{{grade}}</div>
|
||||||
<div class="col">{{homeroom}}</div>
|
<div class="col">{{homeroom}}</div>
|
||||||
<div class="col">{{ student }}</div>
|
<div class="col">{{ student }}</div>
|
||||||
<div class="col">{{ all_stud_list[homeroom][student]['name'] }}</div>
|
<div class="col">{{ all_stud_list[grade][homeroom][student]['name'] }}</div>
|
||||||
<div class="col">{{ all_stud_list[homeroom][student]['eng_name'] }}</div>
|
<div class="col">{{ all_stud_list[grade][homeroom][student]['eng_name'] }}</div>
|
||||||
<div class="col"><input type="checkbox" id="{{homeroom}}^{{student}}"></div>
|
<div class="col"><input type="checkbox" name="{{grade}}^{{homeroom}}^{{student}}"></div>
|
||||||
</div>
|
</div>
|
||||||
{% endfor %}
|
{% endfor %}
|
||||||
{% endfor %}
|
{% endfor %}
|
||||||
|
{% endfor %}
|
||||||
{% endif %}
|
{% endif %}
|
||||||
|
<h3>Please Sign Below</h3>
|
||||||
|
<div class="forSign"><canvas id="signature_pad"></canvas></div>
|
||||||
|
<button class="btn btn-secondary" type="button" onclick="signaturePad.clear()">Clear Signature</button>
|
||||||
|
<button class="btn btn-primary" type="button" onclick="submitForm()">Submit</button>
|
||||||
</div>
|
</div>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
|
<script src="https://cdn.jsdelivr.net/npm/signature_pad@2.3.2/dist/signature_pad.min.js"></script>
|
||||||
|
<script>
|
||||||
|
var canvas = document.getElementById("signature_pad");
|
||||||
|
var signaturePad = new SignaturePad(canvas);
|
||||||
|
function resizeCanvas() {
|
||||||
|
var ratio = Math.max(window.devicePixelRatio || 1, 1);
|
||||||
|
canvas.width = canvas.offsetWidth * ratio;
|
||||||
|
canvas.height = canvas.offsetHeight * ratio;
|
||||||
|
canvas.getContext("2d").scale(ratio, ratio);
|
||||||
|
signaturePad.clear(); // otherwise isEmpty() might return incorrect value
|
||||||
|
}
|
||||||
|
window.addEventListener("resize", resizeCanvas);
|
||||||
|
resizeCanvas();
|
||||||
|
function submitForm() {
|
||||||
|
if (!signaturePad.isEmpty()) {
|
||||||
|
signaturePad.off();
|
||||||
|
var data = signaturePad.toDataURL('image/png');
|
||||||
|
document.getElementsByName('signatureData')[0].value = data;
|
||||||
|
document.getElementById('attendanceData').submit();
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
alert("Please sign first");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
{% endif %}
|
||||||
|
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.6.2/jquery.min.js"></script>
|
||||||
|
<div id="loading" style="text-align:center; width:100%; display:none;"><img src="/static/loading.gif" alt=""
|
||||||
|
style="height:100%;" />
|
||||||
|
</div>
|
||||||
|
<script>
|
||||||
|
function loadingAnimation() {
|
||||||
|
$("div.container").hide();
|
||||||
|
$('#loading').show();
|
||||||
|
}
|
||||||
|
function chgDate(sel) {
|
||||||
|
loadingAnimation();
|
||||||
|
document.getElementById('dateSelForm').submit();
|
||||||
|
}
|
||||||
|
</script>
|
||||||
</body>
|
</body>
|
||||||
|
|
||||||
</html>
|
</html>
|
|
@ -0,0 +1,152 @@
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html>
|
||||||
|
|
||||||
|
<head>
|
||||||
|
<meta charset="utf-8">
|
||||||
|
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||||
|
<title>Homeroom_View</title>
|
||||||
|
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.1.1/dist/css/bootstrap.min.css" rel="stylesheet"
|
||||||
|
integrity="sha384-F3w7mX95PdgyTmZZMECAngseQB83DfGTowi0iMjiWaeVhAn4FJkqJByhZMI3AhiU" crossorigin="anonymous">
|
||||||
|
<link rel="stylesheet" href="/static/allpages.css">
|
||||||
|
<link rel="stylesheet" href="/static/login.css">
|
||||||
|
</head>
|
||||||
|
|
||||||
|
<body>
|
||||||
|
<div class="container">
|
||||||
|
<h1>Homeroom_View</h1>
|
||||||
|
<h2>{{homeroomCode[0]}}: {{homeroomCode[1]}}</h2>
|
||||||
|
<h2>Status: ({{currDate}})</h2>
|
||||||
|
<form action="/manage/date" id="dateSelForm" method="post">
|
||||||
|
<select name="date" id="date" class="form-select" onchange="chgDate();">
|
||||||
|
{% for date in dates %}
|
||||||
|
{% if date == currDate %}
|
||||||
|
<option value="{{date}}" selected="selected">{{date}}</option>
|
||||||
|
{% else %}
|
||||||
|
<option value="{{date}}">{{date}}</option>
|
||||||
|
{% endif %}
|
||||||
|
{% endfor %}
|
||||||
|
</select>
|
||||||
|
</form>
|
||||||
|
<form action="/manage/homeroom_confirm" id="homeroom_confirm" method="post">
|
||||||
|
<input type="hidden" name="date" value="{{currDate}}">
|
||||||
|
<input type="hidden" name="category" value="{{currCategory}}">
|
||||||
|
<input type="hidden" name="signatureData" value="">
|
||||||
|
</form>
|
||||||
|
<div class="col">
|
||||||
|
<div class="row title">
|
||||||
|
<div class="col">Homeroom</div>
|
||||||
|
<div class="col">Number</div>
|
||||||
|
<div class="col">Name</div>
|
||||||
|
<div class="col">Eng Name</div>
|
||||||
|
<div class="col">GP_Class</div>
|
||||||
|
<div class="col">Attendance (Here=V, Abs=X)</div>
|
||||||
|
</div>
|
||||||
|
{% if data != None %}
|
||||||
|
{% for i in all_stud_list %}
|
||||||
|
<div class="row">
|
||||||
|
<div class="col">{{homeroomCode[0]}}{{homeroomCode[1]}}</div>
|
||||||
|
<div class="col">{{i}}</div>
|
||||||
|
<div class="col">{{ all_stud_list[i]['name'] }}</div>
|
||||||
|
<div class="col">{{ all_stud_list[i]['eng_name'] }}</div>
|
||||||
|
<div class="col">{{ all_stud_list[i]['gpClass'] }}:
|
||||||
|
{{gpClasses['Class'][all_stud_list[i]['gpClass']]['name']}}</div>
|
||||||
|
<div class="col">
|
||||||
|
<p class="highlightAbs n-{{all_stud_list[i]['status']}}">
|
||||||
|
{% if all_stud_list[i]['status'] == 1 %}
|
||||||
|
V
|
||||||
|
{% elif all_stud_list[i]['status'] == 2 %}
|
||||||
|
X
|
||||||
|
{% endif %}
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% endfor %}
|
||||||
|
{% endif %}
|
||||||
|
<!-- show signature of confirmed classes -->
|
||||||
|
{% for c in range(confirmedClasses|length) %}
|
||||||
|
{% if c % 2 == 0 %}
|
||||||
|
<div class="row signatures">
|
||||||
|
{% endif %}
|
||||||
|
<div class="col half">
|
||||||
|
<div class="row">{{confirmedClasses[c]}}: {{gpClasses['Class'][confirmedClasses[c]]['name']}}
|
||||||
|
</div>
|
||||||
|
<div class="row"><img src="{{gpClasses['Dates'][currDate][confirmedClasses[c]]}}" alt=""></div>
|
||||||
|
</div>
|
||||||
|
{% if c % 2 == 1 %}
|
||||||
|
</div>
|
||||||
|
{% endif %}
|
||||||
|
{% endfor %}
|
||||||
|
<!-- Show Class Data -->
|
||||||
|
<div class="classlist">
|
||||||
|
<h2>Classes in {{currCategory}}</h2>
|
||||||
|
<ul>
|
||||||
|
{% for c in gpClasses['Class'] %}
|
||||||
|
<li>
|
||||||
|
<h3>{{c}}: {{gpClasses['Class'][c]['name']}}</h3>
|
||||||
|
</li>
|
||||||
|
<ul>
|
||||||
|
<li>
|
||||||
|
<h4>Classroom: {{ gpClasses['Class'][c]['classroom'] }}</h4>
|
||||||
|
</li>
|
||||||
|
<li>
|
||||||
|
<h4>Teacher: {{ gpClasses['Class'][c]['teacher'] }}</h4>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
{% endfor %}
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
{% if status == 1 %}
|
||||||
|
<h3>Please Sign Below</h3>
|
||||||
|
<div class="forSign"><canvas id="signature_pad"></canvas></div>
|
||||||
|
<button class="btn btn-secondary" type="button" onclick="signaturePad.clear()">Clear Signature</button>
|
||||||
|
<button class="btn btn-primary" type="button" onclick="submitForm()">Submit</button>
|
||||||
|
{% else %}
|
||||||
|
<h3>Please wait for all {{currCategory}} teachers to enter data.</h3>
|
||||||
|
{% endif %}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{% if status == 1 %}
|
||||||
|
<script src="https://cdn.jsdelivr.net/npm/signature_pad@2.3.2/dist/signature_pad.min.js"></script>
|
||||||
|
<script>
|
||||||
|
var canvas = document.getElementById("signature_pad");
|
||||||
|
var signaturePad = new SignaturePad(canvas);
|
||||||
|
function resizeCanvas() {
|
||||||
|
var ratio = Math.max(window.devicePixelRatio || 1, 1);
|
||||||
|
canvas.width = canvas.offsetWidth * ratio;
|
||||||
|
canvas.height = canvas.offsetHeight * ratio;
|
||||||
|
canvas.getContext("2d").scale(ratio, ratio);
|
||||||
|
signaturePad.clear(); // otherwise isEmpty() might return incorrect value
|
||||||
|
}
|
||||||
|
window.addEventListener("resize", resizeCanvas);
|
||||||
|
resizeCanvas();
|
||||||
|
function submitForm() {
|
||||||
|
if (!signaturePad.isEmpty()) {
|
||||||
|
signaturePad.off();
|
||||||
|
var data = signaturePad.toDataURL('image/png');
|
||||||
|
document.getElementsByName('signatureData')[0].value = data;
|
||||||
|
document.getElementsByTagName('form')[0].submit();
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
alert("Please sign first");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
{% endif %}
|
||||||
|
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.6.2/jquery.min.js"></script>
|
||||||
|
<div id="loading" style="text-align:center; width:100%; display:none;"><img src="/static/loading.gif" alt=""
|
||||||
|
style="height:100%;" />
|
||||||
|
</div>
|
||||||
|
<script>
|
||||||
|
function loadingAnimation() {
|
||||||
|
$('.container').hide();
|
||||||
|
$('#loading').show();
|
||||||
|
}
|
||||||
|
function chgDate() {
|
||||||
|
loadingAnimation();
|
||||||
|
document.getElementById('dateSelForm').submit();
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
</body>
|
||||||
|
|
||||||
|
</html>
|
|
@ -20,6 +20,11 @@
|
||||||
<!-- upload csv -->
|
<!-- upload csv -->
|
||||||
<form action="{{url}}" method="post" enctype="multipart/form-data">
|
<form action="{{url}}" method="post" enctype="multipart/form-data">
|
||||||
<!-- input class code -->
|
<!-- input class code -->
|
||||||
|
<div class="form-group">
|
||||||
|
<label for="gradeCode">Grade Code</label>
|
||||||
|
<input type="text" class="form-control" id="gradeCode" name="gradeCode"
|
||||||
|
placeholder="Enter Grade Code">
|
||||||
|
</div>
|
||||||
<div class="form-group">
|
<div class="form-group">
|
||||||
<label for="classcode">Class Code</label>
|
<label for="classcode">Class Code</label>
|
||||||
<input type="text" class="form-control" id="classcode" name="classcode"
|
<input type="text" class="form-control" id="classcode" name="classcode"
|
||||||
|
|
Loading…
Reference in a new issue