/**
* A class representing classrooms.
*
* @Constructor
*
* @example
* var classroomExample = {
* classroomCode: "43",
* selected: 1,
* horas_aula: 0,
* vagas_ofertadas: 0,
* vagas_ocupadas: 0,
* alunos_especiais: 0,
* saldo_vagas: 0,
* pedidos_sem_vaga: 0,
* teachers: [
* "First Guy",
* "Second Son",
* "third Weird"
* ],
* schedules: [{@link Schedule}],
* htmlElement: div.classroom-info
* }
*
* @see UI#createClassroomInfo
*/
// IMPORTANT: the 'ui' variable must be already set up!
function Classroom(jsonObj, parentLecture) {
this.parent = parentLecture;
this.teachers = new Array();
this.schedules = new Array();
if (jsonObj) {
this.classroomCode = jsonObj.classroomCode;
this.horas_aula = jsonObj.horas_aula;
this.vagas_ofertadas = jsonObj.vagas_ofertadas;
this.vagas_ocupadas = jsonObj.vagas_ocupadas;
this.alunos_especiais = jsonObj.alunos_especiais;
this.saldo_vagas = jsonObj.saldo_vagas;
this.pedidos_sem_vaga = jsonObj.pedidos_sem_vaga;
this.selected = jsonObj.selected;
// Array.slice(0) copies the _entire_ array.
this.teachers = jsonObj.teachers.slice(0);
for (var i = 0; i < jsonObj.schedules.length; i++) {
this.schedules.push(new Schedule(jsonObj.schedules[i], this));
}
this.htmlElement = ui.createClassroomInfo(this, parentLecture.code);
if (this.selected) {
addClass(this.htmlElement, 'classroom-selected');
}
this.addEventListeners();
} else {
this.classroomCode = null;
this.horas_aula = null;
this.vagas_ofertadas = null;
this.vagas_ocupadas = null;
this.alunos_especiais = null;
this.saldo_vagas = null;
this.pedidos_sem_vaga = null;
this.selected = null;
this.htmlElement = null;
}
}
/**
*
*/
// Doesn't need to remove htmlElement because parent Lecture will
// remove the entire div.lecture-info
Classroom.prototype.delete = function() {
for (var i = 0; i < this.schedules.length; i++) {
this.schedules[i].delete();
}
}
/**
*
*/
Classroom.prototype.addClassInSchedules = function(className) {
for (var i = 0; i < this.schedules.length; i++) {
addClass(this.schedules[i].htmlElement, className);
}
};
/**
*
*/
Classroom.prototype.removeClassInSchedules = function(className) {
for (var i = 0; i < this.schedules.length; i++) {
removeClass(this.schedules[i].htmlElement, className);
}
};
/**
*
*/
Classroom.prototype.showBox = function() {
this.addClassInSchedules('schedule-box-show');
};
/**
*
*/
Classroom.prototype.hideBox = function() {
this.removeClassInSchedules('schedule-box-show');
};
/**
*
*/
// TODO mudar aqui quando tiver plan.activeCombination e lecture.activeClassroom
Classroom.prototype.setHighlight = function() {
var lecture = this.parent;
var activeClassroom = null;
if (lecture.activeClassroomIndex != null) {
// There is an active classroom for this lecture.
activeClassroom = lecture.classrooms[lecture.activeClassroomIndex];
activeClassroom.hideBox();
}
this.addClassInSchedules('schedule-box-highlight');
// Look for conflicting schedules. The active classroom doesn't have any
// conflicts because it is active (obviously). Also there are only conflicts
// if there is a combination being displayed.
if (this != activeClassroom && lecture.parent.activeCombinationIndex != null) {
var activeCombination = lecture.parent.combinations[lecture.parent.activeCombinationIndex];
if (activeCombination.length == 0) {
// This happens when there are at least one lecture displayed on the screen
// but no lecture is selected (div#lecture-schedule is graphically empty).
// However, in this situation there may be various lectures included,
// i.e. plan.lectures.length >>> 0.
// So there is no conflict, we can return.
return
}
var lecturesClassroom = activeCombination.lecturesClassroom;
for (var i = 0; i < lecturesClassroom.length; i++) {
if (this.parent == lecturesClassroom[i].parent) {
// Same lecture, skip.
continue;
}
// Iterate over every schedule on this classroom and every active classroom
// on the current active combination.
for (var j = 0; j < this.schedules.length; j++) {
for (var k = 0; k < lecturesClassroom[i].schedules.length; k++) {
if (schedulesConflict(this.schedules[j], lecturesClassroom[i].schedules[k])) {
// This schedule (one of many for this classroom) conflicts with some other
// schedule from an active classroom. Set conflict highlight.
addClass(this.schedules[j].htmlElement, 'schedule-box-highlight-conflict');
}
}
}
}
}
}
/**
*
*/
Classroom.prototype.unsetHighlight = function() {
var lecture = this.parent;
if (lecture.activeClassroomIndex != null) {
// There is an active classroom for this lecture.
var activeClassroom = lecture.classrooms[lecture.activeClassroomIndex];
activeClassroom.showBox();
}
this.removeClassInSchedules('schedule-box-highlight');
this.removeClassInSchedules('schedule-box-highlight-conflict');
}
/**
*
*/
Classroom.prototype.toggleClassroomSelection = function() {
toggleClass(this.htmlElement, 'classroom-selected');
this.selected = !this.selected;
var thisLecture = this.parent;
var noClassroomSelected = true;
for (var i = 0; i < thisLecture.classrooms.length; i++) {
if (thisLecture.classrooms[i].selected) {
noClassroomSelected = false;
}
}
if (noClassroomSelected) {
thisLecture.selected = false;
thisLecture.activeClassroomIndex = null;
} else {
thisLecture.selected = true;
}
// Update this plan.
thisLecture.parent.update(this);
}
/**
* This function adds event listeners to 'mouseenter', 'mouseleave' and 'click'
*
* @see Classroom#setHighlight
* @see Classroom#unsetHighlight
* @see Classroom#toggleClassroomSelection
*/
Classroom.prototype.addEventListeners = function() {
this.htmlElement.addEventListener('mouseenter', this.setHighlight.bind(this));
this.htmlElement.addEventListener('mouseleave', this.unsetHighlight.bind(this));
this.htmlElement.addEventListener('click', this.toggleClassroomSelection.bind(this));
};