AutorÃa | Ultima modificación | Ver Log |
// This file is part of the Zoom plugin for Moodle - http://moodle.org/
//
// Moodle is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Moodle is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Moodle. If not, see <http://www.gnu.org/licenses/>.
/**
* Populates or de-populates password field based on whether the
* password is required or not.
*
* @copyright 2018 UC Regents
* @author Kubilay Agi
* @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
define(['jquery', 'core/form-autocomplete', 'core/str', 'core/notification'], function($, autocomplete, str, notification) {
/**
* CSS selectors used throughout the file.
*
* @type {object}
*/
var SELECTORS = {
REPEAT_SELECT: 'select[name="recurrence_type"]',
REPEAT_INTERVAL: '.repeat_interval',
REPEAT_INTERVAL_DAILY: '#interval_daily',
REPEAT_INTERVAL_WEEKLY: '#interval_weekly',
REPEAT_INTERVAL_MONTHLY: '#interval_monthly',
REPEAT_INTERVAL_OPTIONS: 'select[name="repeat_interval"] option',
START_TIME: 'select[name*="start_time"]',
DURATION: '*[name*="duration"]',
RECURRING: 'input[name="recurring"][type!="hidden"]',
OPTION_JBH: 'input[name="option_jbh"][type!="hidden"]',
OPTION_WAITING_ROOM: 'input[name="option_waiting_room"][type!="hidden"]'
};
/**
* Repeat interval options.
*
* @type {object}
*/
var REPEAT_OPTIONS = {
REPEAT_OPTION_NONE: 0,
REPEAT_OPTION_DAILY: 1,
REPEAT_OPTION_WEEKLY: 2,
REPEAT_OPTION_MONTHLY: 3
};
/**
* The max values for each repeat option.
*
* @type {object}
*/
var REPEAT_MAX_OPTIONS = {
REPEAT_OPTION_DAILY: 90,
REPEAT_OPTION_WEEKLY: 12,
REPEAT_OPTION_MONTHLY: 3
};
/**
* The init function.
*/
var init = function() {
var optionJoinBeforeHost = $(SELECTORS.OPTION_JBH);
var optionWaitingRoom = $(SELECTORS.OPTION_WAITING_ROOM);
optionJoinBeforeHost.change(function() {
if (optionJoinBeforeHost.is(':checked') === true) {
optionWaitingRoom.prop('checked', false);
}
});
optionWaitingRoom.change(function() {
if (optionWaitingRoom.is(':checked') === true) {
optionJoinBeforeHost.prop('checked', false);
}
});
// First toggle the values based on initial selections.
toggleStartTimeDuration();
toggleRepeatIntervalText();
limitRepeatValues();
// Add listerner to "Repeat Every" drop-down.
$(SELECTORS.REPEAT_SELECT).change(function() {
toggleStartTimeDuration();
toggleRepeatIntervalText();
limitRepeatValues();
});
// Add listener for the "Recurring" checkbox
$(SELECTORS.RECURRING).change(function() {
toggleStartTimeDuration();
});
var breakoutroomsEditor = new BreakoutroomsEditor();
breakoutroomsEditor.init();
};
/**
* Toggle start time and duration elements.
*/
var toggleStartTimeDuration = function() {
// Disable start time and duration if "No Fixed Time" recurring meeting/webinar selected.
var disabled = false;
var repeatVal = parseInt($(SELECTORS.REPEAT_SELECT).val(), 10);
if ($(SELECTORS.RECURRING).prop('checked') && repeatVal === REPEAT_OPTIONS.REPEAT_OPTION_NONE) {
disabled = true;
}
$(SELECTORS.START_TIME).prop('disabled', disabled);
$(SELECTORS.DURATION).prop('disabled', disabled);
};
/**
* Toggle the text based on repeat type.
* To show either Days, Weeks or Months
*/
var toggleRepeatIntervalText = function() {
$(SELECTORS.REPEAT_INTERVAL).hide();
var repeatSelectVal = parseInt($(SELECTORS.REPEAT_SELECT).val(), 10);
if (repeatSelectVal === REPEAT_OPTIONS.REPEAT_OPTION_DAILY) {
$(SELECTORS.REPEAT_INTERVAL_DAILY).show();
} else if (repeatSelectVal === REPEAT_OPTIONS.REPEAT_OPTION_WEEKLY) {
$(SELECTORS.REPEAT_INTERVAL_WEEKLY).show();
} else if (repeatSelectVal === REPEAT_OPTIONS.REPEAT_OPTION_MONTHLY) {
$(SELECTORS.REPEAT_INTERVAL_MONTHLY).show();
}
};
/**
* Limit the options shown in the drop-down based on repeat type selected.
* Max value for daily meeting is 90.
* Max value for weekly meeting is 12.
* Max value for monthly meeting is 3.
*/
var limitRepeatValues = function() {
var selectedValue = parseInt($(SELECTORS.REPEAT_SELECT).val(), 10);
// Restrict options if weekly or monthly option selected.
$(SELECTORS.REPEAT_INTERVAL_OPTIONS).each(function() {
if (selectedValue === REPEAT_OPTIONS.REPEAT_OPTION_WEEKLY) {
if (this.value > REPEAT_MAX_OPTIONS.REPEAT_OPTION_WEEKLY) {
$(this).hide();
}
} else if (selectedValue === REPEAT_OPTIONS.REPEAT_OPTION_MONTHLY) {
if (this.value > REPEAT_MAX_OPTIONS.REPEAT_OPTION_MONTHLY) {
$(this).hide();
}
} else {
$(this).show();
}
});
};
/**
* Tabs component.
* @param {object} tabsColumn
* @param {object} tabsContentColumn
* @param {int} initialTabsCount
* @param {object} emptyAlert
*/
var TabsComponent = function(tabsColumn, tabsContentColumn, initialTabsCount, emptyAlert) {
this.tabsColumn = tabsColumn;
this.tabsContentColumn = tabsContentColumn;
this.emptyAlert = emptyAlert;
this.countTabs = initialTabsCount;
/**
* Build tab
* @param {object} item
* @returns {object} tab element
*/
this.buildTab = function(item) {
var tab = item.tab.element;
var tabLink = $(".nav-link", tab);
// Setting tab id.
tab.attr('id', 'tab-' + this.countTabs);
// Setting tab name.
$(".tab-name", tabLink).text(item.tab.name);
// Setting tab href.
tabLink.attr('href', '#link' + this.countTabs);
// Activating tab
$("li a", this.tabsColumn).removeClass('active');
tabLink.addClass('active');
return tab;
};
/**
* Build tab content.
* @param {object} item
* @returns {object} content of tab element
*/
this.buildTabContent = function(item) {
var tabContent = item.tabContent.element;
// Setting tabContent id.
tabContent.attr('id', 'link' + this.countTabs);
// Activating tabContent.
$(".tab-pane", this.tabsContentColumn).removeClass('active');
tabContent.addClass('active');
return tabContent;
};
/**
* Add tab
* @param {object} item
* @returns {object} tab element
*/
this.addTab = function(item) {
var tab = this.buildTab(item);
var tabContent = this.buildTabContent(item);
this.emptyAlert.addClass('hidden');
$("ul", this.tabsColumn).append(tab);
$(".tab-content", this.tabsContentColumn).append(tabContent);
return {"element": tab, "content": tabContent};
};
/**
* Delete tab
* @param {object} item
*/
this.deleteTab = function(item) {
var tab = item;
var tabContent = $($('a', tab).attr('href'));
tab.remove();
tabContent.remove();
var countTabs = $("li", this.tabsColumn).length;
if (!countTabs) {
this.emptyAlert.removeClass('hidden');
} else {
var countActiveTabs = $("li a.active", this.tabsColumn).length;
if (!countActiveTabs) {
$("li:first-child a", this.tabsColumn).trigger('click');
}
}
};
};
/**
* Breakout rooms editor.
*/
var BreakoutroomsEditor = function() {
this.roomsListColumn = $("#mod-zoom-meeting-rooms-list");
this.roomsList = $("ul", this.roomsListColumn);
this.addBtn = $("#add-room", this.roomsListColumn);
this.emptyAlert = $(".empty-alert", this.roomsListColumn);
this.deleteBtn = $(".delete-room", this.roomsListColumn);
this.roomsDataColumn = $("#mod-zoom-meeting-rooms-data");
this.roomItemToClone = $('#rooms-list-item').html();
this.roomItemDataToClone = $('#rooms-list-item-data').html();
this.initialRoomsCount = parseInt(this.roomsListColumn.attr('data-initial-rooms-count'));
this.tabsComponent = new TabsComponent(this.roomsListColumn, this.roomsDataColumn, this.initialRoomsCount, this.emptyAlert);
// Add room event.
this.init = function() {
var stringkeys = [{key: 'room', component: 'zoom'}];
str.get_strings(stringkeys).then(function() {
return null;
}).fail(notification.exception);
this.addRoomEvent();
this.deleteRoomEvent();
var countRooms = $("li", this.roomsListColumn).length;
if (countRooms) {
this.changeRoomNameEvent();
this.buildAutocompleteComponents();
} else {
this.emptyAlert.removeClass('hidden');
}
};
// Add room event.
this.addRoomEvent = function() {
var thisObject = this;
// Adding addroom button click event.
thisObject.addBtn.click(function() {
thisObject.tabsComponent.countTabs++;
var newRoomName = M.util.get_string('room', 'zoom') + ' ' + thisObject.tabsComponent.countTabs;
var newRoomElement = $(thisObject.roomItemToClone);
var newRoomDataElement = $(thisObject.roomItemDataToClone);
var newRoomIndex = thisObject.tabsComponent.countTabs;
// Setting new room name.
var roomNameInputId = 'room-name-' + newRoomIndex;
$("input[type=text]", newRoomDataElement).prev().attr('for', roomNameInputId);
$("input[type=text]", newRoomDataElement).attr('id', roomNameInputId);
$("input[type=text]", newRoomDataElement).attr('name', roomNameInputId);
$("input[type=text]", newRoomDataElement).val(newRoomName);
$("input[type=text]", newRoomDataElement).next().attr('name', 'rooms[' + newRoomIndex + ']');
$("input[type=text]", newRoomDataElement).next().val(newRoomName);
// Setting new room participants select id/name.
var roomParticipantsSelectId = 'participants-' + newRoomIndex;
$(".room-participants", newRoomDataElement).attr('id', roomParticipantsSelectId);
$(".room-participants", newRoomDataElement).attr('name', 'roomsparticipants[' + newRoomIndex + '][]');
// Setting new room participant groups select id/name.
var roomGroupsSelectId = 'groups-' + newRoomIndex;
$(".room-groups", newRoomDataElement).attr('id', roomGroupsSelectId);
$(".room-groups", newRoomDataElement).attr('name', 'roomsgroups[' + newRoomIndex + '][]');
// Add new room tab
var newRoom = {"tab": {"name": newRoomName, "element": newRoomElement},
"tabContent": {"element": newRoomDataElement}};
var addedTab = thisObject.tabsComponent.addTab(newRoom);
// Adding new room tab delete button click event.
$("li:last .delete-room", thisObject.roomsList).click(function() {
var thisItem = $(this).closest('li');
thisObject.tabsComponent.deleteTab(thisItem);
});
// Adding new room change name event.
$("input[type=text]", addedTab.content).on("change keyup paste", function() {
var newHiddenValue = this.value;
$(this).next().val(newHiddenValue);
$(".tab-name", addedTab.element).text(this.value);
});
// Convert select dropdowns to autocomplete component.
thisObject.buildAutocompleteComponent(roomParticipantsSelectId, 'addparticipant');
thisObject.buildAutocompleteComponent(roomGroupsSelectId, 'addparticipantgroup');
});
};
// Delete room event.
this.deleteRoomEvent = function() {
var thisObject = this;
// Adding deleteroom button click event.
thisObject.deleteBtn.click(function() {
var thisItem = $(this).closest('li');
thisObject.tabsComponent.deleteTab(thisItem);
});
};
// Change room name event.
this.changeRoomNameEvent = function() {
var thisObject = this;
$("li", this.roomsListColumn).each(function() {
var tabIdArr = $(this).attr('id').split('-');
var tabIndex = tabIdArr[1];
$('input[name="room-name-' + tabIndex + '"]', thisObject.roomsDataColumn).on("change keyup paste", function() {
var newHiddenValue = this.value;
$(this).next().val(newHiddenValue);
$("#tab-" + tabIndex + " .tab-name").text(this.value);
});
});
};
/**
* Build autocomplete components.
*/
this.buildAutocompleteComponents = function() {
var thisObject = this;
$(".room-participants", thisObject.roomsDataColumn).each(function() {
var thisItemId = $(this).attr('id');
thisObject.buildAutocompleteComponent(thisItemId, 'addparticipant');
});
$(".room-groups", thisObject.roomsDataColumn).each(function() {
var thisItemId = $(this).attr('id');
thisObject.buildAutocompleteComponent(thisItemId, 'addparticipantgroup');
});
};
/**
* Build autocomplete component.
* @param {string} id
* @param {string} placeholder
*/
this.buildAutocompleteComponent = function(id, placeholder) {
var stringkeys = [{key: placeholder, component: 'zoom'}, {key: 'selectionarea', component: 'zoom'}];
str.get_strings(stringkeys).then(function(langstrings) {
var placeholderString = langstrings[0];
var noSelectionString = langstrings[1];
autocomplete.enhance('#' + id, false, '', placeholderString, false, true, noSelectionString, true);
return null;
}).fail(notification.exception);
};
};
return {
init: init
};
});