Commit b00d59ed by Christina Roberts

Merge pull request #1354 from edx/christina/overview-modal

Pull modal cover and date utils into their own files.
parents d14e81cf 52f4f6af
...@@ -54,17 +54,14 @@ define ["js/views/course_info_handout", "js/views/course_info_update", "js/model ...@@ -54,17 +54,14 @@ define ["js/views/course_info_handout", "js/views/course_info_update", "js/model
@courseInfoEdit.$el.find('.save-button').click() @courseInfoEdit.$el.find('.save-button').click()
@cancelNewCourseInfo = (useCancelButton) -> @cancelNewCourseInfo = (useCancelButton) ->
spyOn(@courseInfoEdit.$modalCover, 'show').andCallThrough()
spyOn(@courseInfoEdit.$modalCover, 'hide').andCallThrough()
@courseInfoEdit.onNew(@event) @courseInfoEdit.onNew(@event)
expect(@courseInfoEdit.$modalCover.show).toHaveBeenCalled() spyOn(@courseInfoEdit.$modalCover, 'hide').andCallThrough()
spyOn(@courseInfoEdit.$codeMirror, 'getValue').andReturn('unsaved changes') spyOn(@courseInfoEdit.$codeMirror, 'getValue').andReturn('unsaved changes')
model = @collection.at(0) model = @collection.at(0)
spyOn(model, "save").andCallThrough() spyOn(model, "save").andCallThrough()
cancelEditingUpdate(useCancelButton) cancelEditingUpdate(@courseInfoEdit, @courseInfoEdit.$modalCover, useCancelButton)
expect(@courseInfoEdit.$modalCover.hide).toHaveBeenCalled() expect(@courseInfoEdit.$modalCover.hide).toHaveBeenCalled()
expect(model.save).not.toHaveBeenCalled() expect(model.save).not.toHaveBeenCalled()
...@@ -73,28 +70,25 @@ define ["js/views/course_info_handout", "js/views/course_info_update", "js/model ...@@ -73,28 +70,25 @@ define ["js/views/course_info_handout", "js/views/course_info_update", "js/model
@cancelExistingCourseInfo = (useCancelButton) -> @cancelExistingCourseInfo = (useCancelButton) ->
@createNewUpdate('existing update') @createNewUpdate('existing update')
spyOn(@courseInfoEdit.$modalCover, 'show').andCallThrough()
spyOn(@courseInfoEdit.$modalCover, 'hide').andCallThrough()
@courseInfoEdit.$el.find('.edit-button').click() @courseInfoEdit.$el.find('.edit-button').click()
expect(@courseInfoEdit.$modalCover.show).toHaveBeenCalled() spyOn(@courseInfoEdit.$modalCover, 'hide').andCallThrough()
spyOn(@courseInfoEdit.$codeMirror, 'getValue').andReturn('modification') spyOn(@courseInfoEdit.$codeMirror, 'getValue').andReturn('modification')
model = @collection.at(0) model = @collection.at(0)
spyOn(model, "save").andCallThrough() spyOn(model, "save").andCallThrough()
model.id = "saved_to_server"
cancelEditingUpdate(useCancelButton) cancelEditingUpdate(@courseInfoEdit, @courseInfoEdit.$modalCover, useCancelButton)
expect(@courseInfoEdit.$modalCover.hide).toHaveBeenCalled() expect(@courseInfoEdit.$modalCover.hide).toHaveBeenCalled()
expect(model.save).not.toHaveBeenCalled() expect(model.save).not.toHaveBeenCalled()
previewContents = @courseInfoEdit.$el.find('.update-contents').html() previewContents = @courseInfoEdit.$el.find('.update-contents').html()
expect(previewContents).toEqual('existing update') expect(previewContents).toEqual('existing update')
cancelEditingUpdate = (update, useCancelButton) -> cancelEditingUpdate = (update, modalCover, useCancelButton) ->
if useCancelButton if useCancelButton
update.$el.find('.cancel-button').click() update.$el.find('.cancel-button').click()
else else
$('.modal-cover').click() modalCover.click()
afterEach -> afterEach ->
@xhrRestore() @xhrRestore()
......
define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base", "date", "jquery.timepicker"], define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base", "date", "jquery.timepicker"],
(OverviewDragger, Notification, sinon) -> (Overview, Notification, sinon) ->
describe "Course Overview", -> describe "Course Overview", ->
beforeEach -> beforeEach ->
...@@ -62,9 +62,9 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -62,9 +62,9 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
</ol> </ol>
""" """
spyOn(window, 'saveSetSectionScheduleDate').andCallThrough() spyOn(Overview, 'saveSetSectionScheduleDate').andCallThrough()
# Have to do this here, as it normally gets bound in document.ready() # Have to do this here, as it normally gets bound in document.ready()
$('a.save-button').click(saveSetSectionScheduleDate) $('a.save-button').click(Overview.saveSetSectionScheduleDate)
$('a.delete-section-button').click(deleteSection) $('a.delete-section-button').click(deleteSection)
$(".edit-subsection-publish-settings .start-date").datepicker() $(".edit-subsection-publish-settings .start-date").datepicker()
...@@ -75,7 +75,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -75,7 +75,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
requests = @requests = [] requests = @requests = []
@xhr.onCreate = (req) -> requests.push(req) @xhr.onCreate = (req) -> requests.push(req)
OverviewDragger.makeDraggable( Overview.overviewDragger.makeDraggable(
'.unit', '.unit',
'.unit-drag-handle', '.unit-drag-handle',
'ol.sortable-unit-list', 'ol.sortable-unit-list',
...@@ -90,7 +90,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -90,7 +90,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
it "should save model when save is clicked", -> it "should save model when save is clicked", ->
$('a.edit-button').click() $('a.edit-button').click()
$('a.save-button').click() $('a.save-button').click()
expect(saveSetSectionScheduleDate).toHaveBeenCalled() expect(Overview.saveSetSectionScheduleDate).toHaveBeenCalled()
it "should show a confirmation on save", -> it "should show a confirmation on save", ->
$('a.edit-button').click() $('a.edit-button').click()
...@@ -120,7 +120,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -120,7 +120,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
$ele.offset( $ele.offset(
top: $ele.offset().top + 10, left: $ele.offset().left top: $ele.offset().top + 10, left: $ele.offset().left
) )
destination = OverviewDragger.findDestination($ele, 1) destination = Overview.overviewDragger.findDestination($ele, 1)
expect(destination.ele).toBe($('#unit-2')) expect(destination.ele).toBe($('#unit-2'))
expect(destination.attachMethod).toBe('before') expect(destination.attachMethod).toBe('before')
...@@ -130,7 +130,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -130,7 +130,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
top: $('#unit-4').offset().top + 8 top: $('#unit-4').offset().top + 8
left: $ele.offset().left left: $ele.offset().left
) )
destination = OverviewDragger.findDestination($ele, 1) destination = Overview.overviewDragger.findDestination($ele, 1)
expect(destination.ele).toBe($('#unit-4')) expect(destination.ele).toBe($('#unit-4'))
# Dragging down into first element, we have a fudge factor makes it easier to drag at beginning. # Dragging down into first element, we have a fudge factor makes it easier to drag at beginning.
expect(destination.attachMethod).toBe('before') expect(destination.attachMethod).toBe('before')
...@@ -139,7 +139,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -139,7 +139,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
top: $('#unit-4').offset().top + 12 top: $('#unit-4').offset().top + 12
left: $ele.offset().left left: $ele.offset().left
) )
destination = OverviewDragger.findDestination($ele, 1) destination = Overview.overviewDragger.findDestination($ele, 1)
expect(destination.ele).toBe($('#unit-4')) expect(destination.ele).toBe($('#unit-4'))
expect(destination.attachMethod).toBe('after') expect(destination.attachMethod).toBe('after')
...@@ -149,7 +149,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -149,7 +149,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
top: $('#unit-3').offset().bottom + 4 top: $('#unit-3').offset().bottom + 4
left: $ele.offset().left left: $ele.offset().left
) )
destination = OverviewDragger.findDestination($ele, -1) destination = Overview.overviewDragger.findDestination($ele, -1)
expect(destination.ele).toBe($('#unit-3')) expect(destination.ele).toBe($('#unit-3'))
# Dragging down up into last element, we have a fudge factor makes it easier to drag at beginning. # Dragging down up into last element, we have a fudge factor makes it easier to drag at beginning.
expect(destination.attachMethod).toBe('after') expect(destination.attachMethod).toBe('after')
...@@ -158,7 +158,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -158,7 +158,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
top: $('#unit-3').offset().top + 4 top: $('#unit-3').offset().top + 4
left: $ele.offset().left left: $ele.offset().left
) )
destination = OverviewDragger.findDestination($ele, -1) destination = Overview.overviewDragger.findDestination($ele, -1)
expect(destination.ele).toBe($('#unit-3')) expect(destination.ele).toBe($('#unit-3'))
expect(destination.attachMethod).toBe('before') expect(destination.attachMethod).toBe('before')
...@@ -168,7 +168,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -168,7 +168,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
top: $('#subsection-3').offset().top + 10 top: $('#subsection-3').offset().top + 10
left: $ele.offset().left left: $ele.offset().left
) )
destination = OverviewDragger.findDestination($ele, 1) destination = Overview.overviewDragger.findDestination($ele, 1)
expect(destination.ele).toBe($('#subsection-list-3')) expect(destination.ele).toBe($('#subsection-list-3'))
expect(destination.attachMethod).toBe('prepend') expect(destination.attachMethod).toBe('prepend')
...@@ -177,7 +177,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -177,7 +177,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
$ele.offset( $ele.offset(
top: $ele.offset().top + 200, left: $ele.offset().left top: $ele.offset().top + 200, left: $ele.offset().left
) )
destination = OverviewDragger.findDestination($ele, 1) destination = Overview.overviewDragger.findDestination($ele, 1)
expect(destination).toEqual( expect(destination).toEqual(
ele: null ele: null
attachMethod: "" attachMethod: ""
...@@ -190,21 +190,21 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -190,21 +190,21 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
top: $('#subsection-2').offset().top + 3 top: $('#subsection-2').offset().top + 3
left: $ele.offset().left left: $ele.offset().left
) )
destination = OverviewDragger.findDestination($ele, 1) destination = Overview.overviewDragger.findDestination($ele, 1)
expect(destination.ele).toBe($('#subsection-list-2')) expect(destination.ele).toBe($('#subsection-list-2'))
expect(destination.parentList).toBe($('#subsection-2')) expect(destination.parentList).toBe($('#subsection-2'))
expect(destination.attachMethod).toBe('prepend') expect(destination.attachMethod).toBe('prepend')
describe "onDragStart", -> describe "onDragStart", ->
it "sets the dragState to its default values", -> it "sets the dragState to its default values", ->
expect(OverviewDragger.dragState).toEqual({}) expect(Overview.overviewDragger.dragState).toEqual({})
# Call with some dummy data # Call with some dummy data
OverviewDragger.onDragStart( Overview.overviewDragger.onDragStart(
{element: $('#unit-1')}, {element: $('#unit-1')},
null, null,
null null
) )
expect(OverviewDragger.dragState).toEqual( expect(Overview.overviewDragger.dragState).toEqual(
dropDestination: null, dropDestination: null,
attachMethod: '', attachMethod: '',
parentList: null, parentList: null,
...@@ -214,7 +214,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -214,7 +214,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
it "collapses expanded elements", -> it "collapses expanded elements", ->
expect($('#subsection-1')).not.toHaveClass('collapsed') expect($('#subsection-1')).not.toHaveClass('collapsed')
OverviewDragger.onDragStart( Overview.overviewDragger.onDragStart(
{element: $('#subsection-1')}, {element: $('#subsection-1')},
null, null,
null null
...@@ -233,7 +233,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -233,7 +233,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
$ele.offset( $ele.offset(
top: dragY, left: dragX top: dragY, left: dragX
) )
OverviewDragger.onDragMove( Overview.overviewDragger.onDragMove(
{element: $ele, dragPoint: {element: $ele, dragPoint:
{y: dragY}}, '', {clientX: dragX} {y: dragY}}, '', {clientX: dragX}
) )
...@@ -246,7 +246,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -246,7 +246,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
$ele.offset( $ele.offset(
top: dragY, left: $ele.offset().left top: dragY, left: $ele.offset().left
) )
OverviewDragger.onDragMove( Overview.overviewDragger.onDragMove(
{element: $ele, dragPoint: {element: $ele, dragPoint:
{y: dragY}}, '', {clientX: $ele.offset().left - 3} {y: dragY}}, '', {clientX: $ele.offset().left - 3}
) )
...@@ -254,33 +254,33 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -254,33 +254,33 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
expect($ele).not.toHaveClass('valid-drop') expect($ele).not.toHaveClass('valid-drop')
it "scrolls up if necessary", -> it "scrolls up if necessary", ->
OverviewDragger.onDragMove( Overview.overviewDragger.onDragMove(
{element: $('#unit-1')}, '', {clientY: 2} {element: $('#unit-1')}, '', {clientY: 2}
) )
expect(@scrollSpy).toHaveBeenCalledWith(0, -10) expect(@scrollSpy).toHaveBeenCalledWith(0, -10)
it "scrolls down if necessary", -> it "scrolls down if necessary", ->
OverviewDragger.onDragMove( Overview.overviewDragger.onDragMove(
{element: $('#unit-1')}, '', {clientY: (window.innerHeight - 5)} {element: $('#unit-1')}, '', {clientY: (window.innerHeight - 5)}
) )
expect(@scrollSpy).toHaveBeenCalledWith(0, 10) expect(@scrollSpy).toHaveBeenCalledWith(0, 10)
describe "onDragEnd", -> describe "onDragEnd", ->
beforeEach -> beforeEach ->
@reorderSpy = spyOn(OverviewDragger, 'handleReorder') @reorderSpy = spyOn(Overview.overviewDragger, 'handleReorder')
afterEach -> afterEach ->
@reorderSpy.reset() @reorderSpy.reset()
it "calls handleReorder on a successful drag", -> it "calls handleReorder on a successful drag", ->
OverviewDragger.dragState.dropDestination = $('#unit-2') Overview.overviewDragger.dragState.dropDestination = $('#unit-2')
OverviewDragger.dragState.attachMethod = "before" Overview.overviewDragger.dragState.attachMethod = "before"
OverviewDragger.dragState.parentList = $('#subsection-1') Overview.overviewDragger.dragState.parentList = $('#subsection-1')
$('#unit-1').offset( $('#unit-1').offset(
top: $('#unit-1').offset().top + 10 top: $('#unit-1').offset().top + 10
left: $('#unit-1').offset().left left: $('#unit-1').offset().left
) )
OverviewDragger.onDragEnd( Overview.overviewDragger.onDragEnd(
{element: $('#unit-1')}, {element: $('#unit-1')},
null, null,
{clientX: $('#unit-1').offset().left} {clientX: $('#unit-1').offset().left}
...@@ -288,15 +288,15 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -288,15 +288,15 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
expect(@reorderSpy).toHaveBeenCalled() expect(@reorderSpy).toHaveBeenCalled()
it "clears out the drag state", -> it "clears out the drag state", ->
OverviewDragger.onDragEnd( Overview.overviewDragger.onDragEnd(
{element: $('#unit-1')}, {element: $('#unit-1')},
null, null,
null null
) )
expect(OverviewDragger.dragState).toEqual({}) expect(Overview.overviewDragger.dragState).toEqual({})
it "sets the element to the correct position", -> it "sets the element to the correct position", ->
OverviewDragger.onDragEnd( Overview.overviewDragger.onDragEnd(
{element: $('#unit-1')}, {element: $('#unit-1')},
null, null,
null null
...@@ -308,7 +308,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -308,7 +308,7 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
it "expands an element if it was collapsed on drag start", -> it "expands an element if it was collapsed on drag start", ->
$('#subsection-1').addClass('collapsed') $('#subsection-1').addClass('collapsed')
$('#subsection-1').addClass('expand-on-drop') $('#subsection-1').addClass('expand-on-drop')
OverviewDragger.onDragEnd( Overview.overviewDragger.onDragEnd(
{element: $('#subsection-1')}, {element: $('#subsection-1')},
null, null,
null null
...@@ -318,10 +318,10 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -318,10 +318,10 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
it "expands a collapsed element when something is dropped in it", -> it "expands a collapsed element when something is dropped in it", ->
$('#subsection-2').addClass('collapsed') $('#subsection-2').addClass('collapsed')
OverviewDragger.dragState.dropDestination = $('#list-2') Overview.overviewDragger.dragState.dropDestination = $('#list-2')
OverviewDragger.dragState.attachMethod = "prepend" Overview.overviewDragger.dragState.attachMethod = "prepend"
OverviewDragger.dragState.parentList = $('#subsection-2') Overview.overviewDragger.dragState.parentList = $('#subsection-2')
OverviewDragger.onDragEnd( Overview.overviewDragger.onDragEnd(
{element: $('#unit-1')}, {element: $('#unit-1')},
null, null,
{clientX: $('#unit-1').offset().left} {clientX: $('#unit-1').offset().left}
...@@ -344,15 +344,15 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base ...@@ -344,15 +344,15 @@ define ["js/views/overview", "js/views/feedback_notification", "sinon", "js/base
@clock.restore() @clock.restore()
it "should send an update on reorder", -> it "should send an update on reorder", ->
OverviewDragger.dragState.dropDestination = $('#unit-4') Overview.overviewDragger.dragState.dropDestination = $('#unit-4')
OverviewDragger.dragState.attachMethod = "after" Overview.overviewDragger.dragState.attachMethod = "after"
OverviewDragger.dragState.parentList = $('#subsection-2') Overview.overviewDragger.dragState.parentList = $('#subsection-2')
# Drag Unit 1 from Subsection 1 to the end of Subsection 2. # Drag Unit 1 from Subsection 1 to the end of Subsection 2.
$('#unit-1').offset( $('#unit-1').offset(
top: $('#unit-4').offset().top + 10 top: $('#unit-4').offset().top + 10
left: $('#unit-4').offset().left left: $('#unit-4').offset().left
) )
OverviewDragger.onDragEnd( Overview.overviewDragger.onDragEnd(
{element: $('#unit-1')}, {element: $('#unit-1')},
null, null,
{clientX: $('#unit-1').offset().left} {clientX: $('#unit-1').offset().left}
......
define ["backbone", "jquery", "underscore", "gettext", "xblock/runtime.v1", define ["backbone", "jquery", "underscore", "gettext", "xblock/runtime.v1",
"js/views/feedback_notification", "js/views/metadata", "js/collections/metadata" "js/views/feedback_notification", "js/views/metadata", "js/collections/metadata"
"jquery.inputnumber", "xmodule"], "js/utils/modal", "jquery.inputnumber", "xmodule"],
(Backbone, $, _, gettext, XBlock, NotificationView, MetadataView, MetadataCollection) -> (Backbone, $, _, gettext, XBlock, NotificationView, MetadataView, MetadataCollection, ModalUtils) ->
class ModuleEdit extends Backbone.View class ModuleEdit extends Backbone.View
tagName: 'li' tagName: 'li'
className: 'component' className: 'component'
...@@ -89,7 +89,7 @@ define ["backbone", "jquery", "underscore", "gettext", "xblock/runtime.v1", ...@@ -89,7 +89,7 @@ define ["backbone", "jquery", "underscore", "gettext", "xblock/runtime.v1",
id: _this.model.id id: _this.model.id
data.metadata = _.extend(data.metadata || {}, @changedMetadata()) data.metadata = _.extend(data.metadata || {}, @changedMetadata())
@hideModal() ModalUtils.hideModalCover()
saving = new NotificationView.Mini saving = new NotificationView.Mini
title: gettext('Saving&hellip;') title: gettext('Saving&hellip;')
saving.show() saving.show()
...@@ -104,17 +104,12 @@ define ["backbone", "jquery", "underscore", "gettext", "xblock/runtime.v1", ...@@ -104,17 +104,12 @@ define ["backbone", "jquery", "underscore", "gettext", "xblock/runtime.v1",
event.preventDefault() event.preventDefault()
@$el.removeClass('editing') @$el.removeClass('editing')
@$component_editor().slideUp(150) @$component_editor().slideUp(150)
@hideModal() ModalUtils.hideModalCover()
hideModal: ->
$modalCover = $(".modal-cover")
$modalCover.hide()
$modalCover.removeClass('is-fixed')
clickEditButton: (event) -> clickEditButton: (event) ->
event.preventDefault() event.preventDefault()
@$el.addClass('editing') @$el.addClass('editing')
$(".modal-cover").show().addClass('is-fixed') ModalUtils.showModalCover(true)
@$component_editor().slideDown(150) @$component_editor().slideDown(150)
@loadEdit() @loadEdit()
......
require(["domReady", "jquery", "underscore", "gettext", "js/views/feedback_notification", "js/views/feedback_prompt", require(["domReady", "jquery", "underscore", "gettext", "js/views/feedback_notification", "js/views/feedback_prompt",
"js/utils/cancel_on_escape", "jquery.ui", "jquery.timepicker", "jquery.leanModal", "jquery.form", "jquery.smoothScroll"], "js/utils/get_date", "jquery.ui", "jquery.leanModal", "jquery.form", "jquery.smoothScroll"],
function(domReady, $, _, gettext, NotificationView, PromptView, CancelOnEscape) { function(domReady, $, _, gettext, NotificationView, PromptView, DateUtils) {
var $body; var $body;
var $modal;
var $modalCover;
var $newComponentItem; var $newComponentItem;
var $changedInput; var $changedInput;
var $spinner; var $spinner;
...@@ -14,8 +12,6 @@ var $newComponentButton; ...@@ -14,8 +12,6 @@ var $newComponentButton;
domReady(function() { domReady(function() {
$body = $('body'); $body = $('body');
$modal = $('.history-modal');
$modalCover = $('.modal-cover');
$newComponentItem = $('.new-component-item'); $newComponentItem = $('.new-component-item');
$newComponentTypePicker = $('.new-component'); $newComponentTypePicker = $('.new-component');
...@@ -23,12 +19,6 @@ domReady(function() { ...@@ -23,12 +19,6 @@ domReady(function() {
$newComponentButton = $('.new-component-button'); $newComponentButton = $('.new-component-button');
$spinner = $('<span class="spinner-in-field-icon"></span>'); $spinner = $('<span class="spinner-in-field-icon"></span>');
$('.expand-collapse-icon').bind('click', toggleSubmodules);
$('.visibility-options').bind('change', setVisibility);
$modal.bind('click', hideModal);
$modalCover.bind('click', hideModal);
$body.on('click', '.embeddable-xml-input', function() { $body.on('click', '.embeddable-xml-input', function() {
$(this).select(); $(this).select();
}); });
...@@ -70,7 +60,7 @@ domReady(function() { ...@@ -70,7 +60,7 @@ domReady(function() {
$('.nav-dd .nav-item .wrapper-nav-sub').removeClass('is-shown'); $('.nav-dd .nav-item .wrapper-nav-sub').removeClass('is-shown');
$title.addClass('is-selected'); $title.addClass('is-selected');
$subnav.addClass('is-shown'); $subnav.addClass('is-shown');
// if propogation is not stopped, the event will bubble up to the // if propagation is not stopped, the event will bubble up to the
// body element, which will close the dropdown. // body element, which will close the dropdown.
e.stopPropagation(); e.stopPropagation();
} }
...@@ -94,14 +84,6 @@ domReady(function() { ...@@ -94,14 +84,6 @@ domReady(function() {
// tender feedback window scrolling // tender feedback window scrolling
$('a.show-tender').bind('click', smoothScrollTop); $('a.show-tender').bind('click', smoothScrollTop);
// toggling overview section details
$(function() {
if ($('.courseware-section').length > 0) {
$('.toggle-button-sections').addClass('is-shown');
}
});
$('.toggle-button-sections').bind('click', toggleSections);
// autosave when leaving input field // autosave when leaving input field
$body.on('change', '.subsection-display-name-input', saveSubsection); $body.on('change', '.subsection-display-name-input', saveSubsection);
$('.subsection-display-name-input').each(function() { $('.subsection-display-name-input').each(function() {
...@@ -113,12 +95,8 @@ domReady(function() { ...@@ -113,12 +95,8 @@ domReady(function() {
// expand/collapse methods for optional date setters // expand/collapse methods for optional date setters
$('.set-date').bind('click', showDateSetter); $('.set-date').bind('click', showDateSetter);
$('.remove-date').bind('click', removeDateSetter); $('.remove-date').bind('click', removeDateSetter);
// add new/delete section
$('.new-courseware-section-button').bind('click', addNewSection);
$('.delete-section-button').bind('click', deleteSection);
// add new/delete subsection $('.delete-section-button').bind('click', deleteSection);
$('.new-subsection-item').bind('click', addNewSubsection);
$('.delete-subsection-button').bind('click', deleteSubsection); $('.delete-subsection-button').bind('click', deleteSubsection);
$('.sync-date').bind('click', syncReleaseDate); $('.sync-date').bind('click', syncReleaseDate);
...@@ -126,12 +104,7 @@ domReady(function() { ...@@ -126,12 +104,7 @@ domReady(function() {
// section date setting // section date setting
$('.set-publish-date').bind('click', setSectionScheduleDate); $('.set-publish-date').bind('click', setSectionScheduleDate);
$('.edit-section-start-cancel').bind('click', cancelSetSectionScheduleDate); $('.edit-section-start-cancel').bind('click', cancelSetSectionScheduleDate);
$('.edit-section-start-save').bind('click', saveSetSectionScheduleDate);
$body.on('click', '.section-published-date .edit-button', editSectionPublishDate);
$body.on('click', '.section-published-date .schedule-button', editSectionPublishDate);
$body.on('click', '.edit-subsection-publish-settings .save-button', saveSetSectionScheduleDate);
$body.on('click', '.edit-subsection-publish-settings .cancel-button', hideModal);
$body.on('change', '.edit-subsection-publish-settings .start-date', function() { $body.on('change', '.edit-subsection-publish-settings .start-date', function() {
if ($('.edit-subsection-publish-settings').find('.start-time').val() == '') { if ($('.edit-subsection-publish-settings').find('.start-time').val() == '') {
$('.edit-subsection-publish-settings').find('.start-time').val('12:00am'); $('.edit-subsection-publish-settings').find('.start-time').val('12:00am');
...@@ -171,44 +144,6 @@ function linkNewWindow(e) { ...@@ -171,44 +144,6 @@ function linkNewWindow(e) {
e.preventDefault(); e.preventDefault();
} }
function toggleSections(e) {
e.preventDefault();
$section = $('.courseware-section');
sectionCount = $section.length;
$button = $(this);
$labelCollapsed = $('<i class="icon-arrow-up"></i> <span class="label">' +
gettext('Collapse All Sections') + '</span>');
$labelExpanded = $('<i class="icon-arrow-down"></i> <span class="label">' +
gettext('Expand All Sections') + '</span>');
var buttonLabel = $button.hasClass('is-activated') ? $labelCollapsed : $labelExpanded;
$button.toggleClass('is-activated').html(buttonLabel);
if ($button.hasClass('is-activated')) {
$section.addClass('collapsed');
// first child in order to avoid the icons on the subsection lists which are not in the first child
$section.find('header .expand-collapse-icon').removeClass('collapse').addClass('expand');
} else {
$section.removeClass('collapsed');
// first child in order to avoid the icons on the subsection lists which are not in the first child
$section.find('header .expand-collapse-icon').removeClass('expand').addClass('collapse');
}
}
function editSectionPublishDate(e) {
e.preventDefault();
$modal = $('.edit-subsection-publish-settings').show();
$modal.attr('data-id', $(this).attr('data-id'));
$modal.find('.start-date').val($(this).attr('data-date'));
$modal.find('.start-time').val($(this).attr('data-time'));
if ($modal.find('.start-date').val() == '' && $modal.find('.start-time').val() == '') {
$modal.find('.save-button').hide();
}
$modal.find('.section-name').html('"' + $(this).closest('.courseware-section').find('.section-name-span').text() + '"');
$modalCover.show();
}
function syncReleaseDate(e) { function syncReleaseDate(e) {
e.preventDefault(); e.preventDefault();
$(this).closest('.notice').hide(); $(this).closest('.notice').hide();
...@@ -216,21 +151,6 @@ function syncReleaseDate(e) { ...@@ -216,21 +151,6 @@ function syncReleaseDate(e) {
$("#start_time").val(""); $("#start_time").val("");
} }
function getDatetime(datepickerInput, timepickerInput) {
// given a pair of inputs (datepicker and timepicker), return a JS Date
// object that corresponds to the datetime that they represent. Assume
// UTC timezone, NOT the timezone of the user's browser.
var date = $(datepickerInput).datepicker("getDate");
var time = $(timepickerInput).timepicker("getTime");
if(date && time) {
return new Date(Date.UTC(
date.getFullYear(), date.getMonth(), date.getDate(),
time.getHours(), time.getMinutes()
));
} else {
return null;
}
}
function autosaveInput(e) { function autosaveInput(e) {
var self = this; var self = this;
...@@ -272,7 +192,7 @@ function saveSubsection() { ...@@ -272,7 +192,7 @@ function saveSubsection() {
// get datetimes for start and due, stick into metadata // get datetimes for start and due, stick into metadata
_(["start", "due"]).each(function(name) { _(["start", "due"]).each(function(name) {
var datetime = getDatetime( var datetime = DateUtils(
document.getElementById(name+"_date"), document.getElementById(name+"_date"),
document.getElementById(name+"_time") document.getElementById(name+"_time")
); );
...@@ -381,30 +301,6 @@ function _deleteItem($el, type) { ...@@ -381,30 +301,6 @@ function _deleteItem($el, type) {
confirm.show(); confirm.show();
} }
function hideModal(e) {
if (e) {
e.preventDefault();
}
// Unit editors do not want the modal cover to hide when users click outside
// of the editor. Users must press Cancel or Save to exit the editor.
// module_edit adds and removes the "is-fixed" class.
if (!$modalCover.hasClass("is-fixed")) {
$(".modal, .edit-subsection-publish-settings").hide();
$modalCover.hide();
}
}
function toggleSubmodules(e) {
e.preventDefault();
$(this).toggleClass('expand').toggleClass('collapse');
$(this).closest('.branch, .window').toggleClass('collapsed');
}
function setVisibility(e) {
$(this).find('.checked').removeClass('checked');
$(e.target).closest('.option').addClass('checked');
}
function showDateSetter(e) { function showDateSetter(e) {
e.preventDefault(); e.preventDefault();
var $block = $(this).closest('.due-date-input'); var $block = $(this).closest('.due-date-input');
...@@ -422,7 +318,6 @@ function removeDateSetter(e) { ...@@ -422,7 +318,6 @@ function removeDateSetter(e) {
$block.find('.time').val(''); $block.find('.time').val('');
} }
function hideNotification(e) { function hideNotification(e) {
(e).preventDefault(); (e).preventDefault();
$(this).closest('.wrapper-notification').removeClass('is-shown').addClass('is-hiding').attr('aria-hidden', 'true'); $(this).closest('.wrapper-notification').removeClass('is-shown').addClass('is-hiding').attr('aria-hidden', 'true');
...@@ -433,101 +328,6 @@ function hideAlert(e) { ...@@ -433,101 +328,6 @@ function hideAlert(e) {
$(this).closest('.wrapper-alert').removeClass('is-shown'); $(this).closest('.wrapper-alert').removeClass('is-shown');
} }
function addNewSection(e) {
e.preventDefault();
$(e.target).addClass('disabled');
var $newSection = $($('#new-section-template').html());
var $cancelButton = $newSection.find('.new-section-name-cancel');
$('.courseware-overview').prepend($newSection);
$newSection.find('.new-section-name').focus().select();
$newSection.find('.section-name-form').bind('submit', saveNewSection);
$cancelButton.bind('click', cancelNewSection);
CancelOnEscape($cancelButton);
}
function saveNewSection(e) {
e.preventDefault();
var $saveButton = $(this).find('.new-section-name-save');
var parent = $saveButton.data('parent');
var category = $saveButton.data('category');
var display_name = $(this).find('.new-section-name').val();
analytics.track('Created a Section', {
'course': course_location_analytics,
'display_name': display_name
});
$.post('/create_item', {
'parent_location': parent,
'category': category,
'display_name': display_name
},
function(data) {
if (data.id != undefined) location.reload();
});
}
function cancelNewSection(e) {
e.preventDefault();
$('.new-courseware-section-button').removeClass('disabled');
$(this).parents('section.new-section').remove();
}
function addNewSubsection(e) {
e.preventDefault();
var $section = $(this).closest('.courseware-section');
var $newSubsection = $($('#new-subsection-template').html());
$section.find('.subsection-list > ol').append($newSubsection);
$section.find('.new-subsection-name-input').focus().select();
var $saveButton = $newSubsection.find('.new-subsection-name-save');
var $cancelButton = $newSubsection.find('.new-subsection-name-cancel');
var parent = $(this).parents("section.branch").data("id");
$saveButton.data('parent', parent);
$saveButton.data('category', $(this).data('category'));
$newSubsection.find('.new-subsection-form').bind('submit', saveNewSubsection);
$cancelButton.bind('click', cancelNewSubsection);
CancelOnEscape($cancelButton);
}
function saveNewSubsection(e) {
e.preventDefault();
var parent = $(this).find('.new-subsection-name-save').data('parent');
var category = $(this).find('.new-subsection-name-save').data('category');
var display_name = $(this).find('.new-subsection-name-input').val();
analytics.track('Created a Subsection', {
'course': course_location_analytics,
'display_name': display_name
});
$.post('/create_item', {
'parent_location': parent,
'category': category,
'display_name': display_name
},
function(data) {
if (data.id != undefined) {
location.reload();
}
});
}
function cancelNewSubsection(e) {
e.preventDefault();
$(this).parents('li.branch').remove();
}
function setSectionScheduleDate(e) { function setSectionScheduleDate(e) {
e.preventDefault(); e.preventDefault();
$(this).closest("h4").hide(); $(this).closest("h4").hide();
...@@ -540,65 +340,6 @@ function cancelSetSectionScheduleDate(e) { ...@@ -540,65 +340,6 @@ function cancelSetSectionScheduleDate(e) {
$(this).parent().siblings("h4").show(); $(this).parent().siblings("h4").show();
} }
function saveSetSectionScheduleDate(e) {
e.preventDefault();
var datetime = getDatetime(
$('.edit-subsection-publish-settings .start-date'),
$('.edit-subsection-publish-settings .start-time')
);
var id = $modal.attr('data-id');
analytics.track('Edited Section Release Date', {
'course': course_location_analytics,
'id': id,
'start': datetime
});
var saving = new NotificationView.Mini({
title: gettext("Saving&hellip;")
});
saving.show();
// call into server to commit the new order
$.ajax({
url: "/save_item",
type: "POST",
dataType: "json",
contentType: "application/json",
data: JSON.stringify({
'id': id,
'metadata': {
'start': datetime
}
})
}).success(function() {
var pad2 = function(number) {
// pad a number to two places: useful for formatting months, days, hours, etc
// when displaying a date/time
return (number < 10 ? '0' : '') + number;
};
var $thisSection = $('.courseware-section[data-id="' + id + '"]');
var html = _.template(
'<span class="published-status">' +
'<strong>' + gettext("Will Release:") + '&nbsp;</strong>' +
gettext("{month}/{day}/{year} at {hour}:{minute} UTC") +
'</span>' +
'<a href="#" class="edit-button" data-date="{month}/{day}/{year}" data-time="{hour}:{minute}" data-id="{id}">' +
gettext("Edit") +
'</a>',
{year: datetime.getUTCFullYear(), month: pad2(datetime.getUTCMonth() + 1), day: pad2(datetime.getUTCDate()),
hour: pad2(datetime.getUTCHours()), minute: pad2(datetime.getUTCMinutes()),
id: id},
{interpolate: /\{(.+?)\}/g});
$thisSection.find('.section-published-date').html(html);
hideModal();
saving.hide();
});
}
// Add to window object for unit test (overview_spec).
window.saveSetSectionScheduleDate = saveSetSectionScheduleDate;
window.deleteSection = deleteSection; window.deleteSection = deleteSection;
}); // end require() }); // end require()
define(["jquery", "jquery.ui", "jquery.timepicker"], function($) {
var getDate = function (datepickerInput, timepickerInput) {
// given a pair of inputs (datepicker and timepicker), return a JS Date
// object that corresponds to the datetime.js that they represent. Assume
// UTC timezone, NOT the timezone of the user's browser.
var date = $(datepickerInput).datepicker("getDate");
var time = $(timepickerInput).timepicker("getTime");
if(date && time) {
return new Date(Date.UTC(
date.getFullYear(), date.getMonth(), date.getDate(),
time.getHours(), time.getMinutes()
));
} else {
return null;
}
};
return getDate;
});
define(["jquery"], function($) {
/**
* Hides the modal and modal cover, using the standard selectors.
* Note though that the class "is-fixed" on the modal cover
* prevents the closing operation.
*/
var hideModal = function(e) {
if (e) {
e.preventDefault();
}
var $modalCover = getModalCover();
// Unit editors (module_edit) do not want the modal cover to hide when users click outside
// of the editor. Users must press Cancel or Save to exit the editor.
if (!$modalCover.hasClass("is-fixed")) {
getModal().hide();
hideModalCover($modalCover);
}
};
/**
* Hides just the modal cover. Caller can pass in a specific
* element as the modal cover, otherwise the standard selector will be used.
*
* This method also unbinds the click handler on the modal cover.
*/
var hideModalCover = function (modalCover) {
if (modalCover == undefined) {
modalCover = getModalCover();
}
modalCover.hide();
modalCover.removeClass("is-fixed");
modalCover.unbind('click');
};
/**
* Shows the modal and modal cover, using the standard selectors.
*/
var showModal = function () {
getModal().show();
showModalCover();
};
/**
* Shows just the modal cover. The caller can optionally choose
* to have the class "is-fixed" added to the cover, and
* the user can also choose to specify a custom click handler
* for the modal cover.
*
* This method returns the modal cover element.
*/
var showModalCover = function(addFixed, clickHandler) {
var $modalCover = getModalCover();
$modalCover.show();
if (addFixed) {
$modalCover.addClass("is-fixed");
}
$modalCover.unbind('click');
if (clickHandler) {
$modalCover.bind('click', clickHandler);
}
else {
$modalCover.bind('click', hideModal);
}
return $modalCover;
};
var getModalCover = function () {
return $('.modal-cover');
};
var getModal = function () {
return $(".modal, .showAsModal");
};
return {
showModal: showModal,
hideModal: hideModal,
showModalCover: showModalCover,
hideModalCover: hideModalCover
};
});
define(["backbone", "underscore", "codemirror", "js/views/feedback_notification", "js/views/course_info_helper"], define(["backbone", "underscore", "codemirror", "js/views/feedback_notification", "js/views/course_info_helper", "js/utils/modal"],
function(Backbone, _, CodeMirror, NotificationView, CourseInfoHelper) { function(Backbone, _, CodeMirror, NotificationView, CourseInfoHelper, ModalUtils) {
var $modalCover = $(".modal-cover");
// the handouts view is dumb right now; it needs tied to a model and all that jazz // the handouts view is dumb right now; it needs tied to a model and all that jazz
var CourseInfoHandoutsView = Backbone.View.extend({ var CourseInfoHandoutsView = Backbone.View.extend({
// collection is CourseUpdateCollection // collection is CourseUpdateCollection
...@@ -47,10 +46,7 @@ define(["backbone", "underscore", "codemirror", "js/views/feedback_notification" ...@@ -47,10 +46,7 @@ define(["backbone", "underscore", "codemirror", "js/views/feedback_notification"
this.$codeMirror = CourseInfoHelper.editWithCodeMirror( this.$codeMirror = CourseInfoHelper.editWithCodeMirror(
self.model, 'data', self.options['base_asset_url'], this.$editor.get(0)); self.model, 'data', self.options['base_asset_url'], this.$editor.get(0));
$modalCover.show(); ModalUtils.showModalCover(false, function() { self.closeEditor() });
$modalCover.bind('click', function() {
self.closeEditor();
});
}, },
onSave: function(event) { onSave: function(event) {
...@@ -81,8 +77,7 @@ define(["backbone", "underscore", "codemirror", "js/views/feedback_notification" ...@@ -81,8 +77,7 @@ define(["backbone", "underscore", "codemirror", "js/views/feedback_notification"
closeEditor: function() { closeEditor: function() {
this.$form.hide(); this.$form.hide();
$modalCover.unbind('click'); ModalUtils.hideModalCover();
$modalCover.hide();
this.$form.find('.CodeMirror').remove(); this.$form.find('.CodeMirror').remove();
this.$codeMirror = null; this.$codeMirror = null;
} }
......
define(["backbone", "underscore", "codemirror", "js/models/course_update", define(["backbone", "underscore", "codemirror", "js/models/course_update",
"js/views/feedback_prompt", "js/views/feedback_notification", "js/views/course_info_helper"], "js/views/feedback_prompt", "js/views/feedback_notification", "js/views/course_info_helper", "js/utils/modal"],
function(Backbone, _, CodeMirror, CourseUpdateModel, PromptView, NotificationView, CourseInfoHelper) { function(Backbone, _, CodeMirror, CourseUpdateModel, PromptView, NotificationView, CourseInfoHelper, ModalUtils) {
var CourseInfoUpdateView = Backbone.View.extend({ var CourseInfoUpdateView = Backbone.View.extend({
// collection is CourseUpdateCollection // collection is CourseUpdateCollection
...@@ -17,8 +17,6 @@ define(["backbone", "underscore", "codemirror", "js/models/course_update", ...@@ -17,8 +17,6 @@ define(["backbone", "underscore", "codemirror", "js/models/course_update",
this.render(); this.render();
// when the client refetches the updates as a whole, re-render them // when the client refetches the updates as a whole, re-render them
this.listenTo(this.collection, 'reset', this.render); this.listenTo(this.collection, 'reset', this.render);
this.$modalCover = $(".modal-cover");
}, },
render: function () { render: function () {
...@@ -64,9 +62,9 @@ define(["backbone", "underscore", "codemirror", "js/models/course_update", ...@@ -64,9 +62,9 @@ define(["backbone", "underscore", "codemirror", "js/models/course_update",
$newForm.addClass('editing'); $newForm.addClass('editing');
this.$currentPost = $newForm.closest('li'); this.$currentPost = $newForm.closest('li');
this.$modalCover.show(); // Variable stored for unit test.
this.$modalCover.bind('click', function() { this.$modalCover = ModalUtils.showModalCover(false, function() {
self.closeEditor(true); self.closeEditor(true)
}); });
$('.date').datepicker('destroy'); $('.date').datepicker('destroy');
...@@ -91,7 +89,7 @@ define(["backbone", "underscore", "codemirror", "js/models/course_update", ...@@ -91,7 +89,7 @@ define(["backbone", "underscore", "codemirror", "js/models/course_update",
ele.remove(); ele.remove();
} }
}); });
this.closeEditor(); this.closeEditor(false);
analytics.track('Saved Course Update', { analytics.track('Saved Course Update', {
'course': course_location_analytics, 'course': course_location_analytics,
...@@ -121,10 +119,12 @@ define(["backbone", "underscore", "codemirror", "js/models/course_update", ...@@ -121,10 +119,12 @@ define(["backbone", "underscore", "codemirror", "js/models/course_update",
this.$codeMirror = CourseInfoHelper.editWithCodeMirror( this.$codeMirror = CourseInfoHelper.editWithCodeMirror(
targetModel, 'content', self.options['base_asset_url'], $textArea.get(0)); targetModel, 'content', self.options['base_asset_url'], $textArea.get(0));
this.$modalCover.show(); // Variable stored for unit test.
this.$modalCover.bind('click', function() { this.$modalCover = ModalUtils.showModalCover(false,
self.closeEditor(false); function() {
}); self.closeEditor(false)
}
);
}, },
onDelete: function(event) { onDelete: function(event) {
...@@ -198,8 +198,7 @@ define(["backbone", "underscore", "codemirror", "js/models/course_update", ...@@ -198,8 +198,7 @@ define(["backbone", "underscore", "codemirror", "js/models/course_update",
this.$currentPost.find('.CodeMirror').remove(); this.$currentPost.find('.CodeMirror').remove();
} }
this.$modalCover.unbind('click'); ModalUtils.hideModalCover(this.$modalCover);
this.$modalCover.hide();
this.$codeMirror = null; this.$codeMirror = null;
}, },
......
define(["domReady", "jquery", "jquery.ui", "gettext", "js/views/feedback_notification", "draggabilly"], define(["domReady", "jquery", "jquery.ui", "underscore", "gettext", "js/views/feedback_notification", "draggabilly",
function (domReady, $, ui, gettext, NotificationView, Draggabilly) { "js/utils/modal", "js/utils/cancel_on_escape", "js/utils/get_date"],
function (domReady, $, ui, _, gettext, NotificationView, Draggabilly, ModalUtils, CancelOnEscape, DateUtils) {
var modalSelector = '.edit-subsection-publish-settings';
var toggleSections = function(e) {
e.preventDefault();
var $section = $('.courseware-section');
var $button = $(this);
var $labelCollapsed = $('<i class="icon-arrow-up"></i> <span class="label">' +
gettext('Collapse All Sections') + '</span>');
var $labelExpanded = $('<i class="icon-arrow-down"></i> <span class="label">' +
gettext('Expand All Sections') + '</span>');
var buttonLabel = $button.hasClass('is-activated') ? $labelCollapsed : $labelExpanded;
$button.toggleClass('is-activated').html(buttonLabel);
if ($button.hasClass('is-activated')) {
$section.addClass('collapsed');
// first child in order to avoid the icons on the subsection lists which are not in the first child
$section.find('header .expand-collapse-icon').removeClass('collapse').addClass('expand');
} else {
$section.removeClass('collapsed');
// first child in order to avoid the icons on the subsection lists which are not in the first child
$section.find('header .expand-collapse-icon').removeClass('expand').addClass('collapse');
}
};
var toggleSubmodules = function(e) {
e.preventDefault();
$(this).toggleClass('expand').toggleClass('collapse');
$(this).closest('.branch, .window').toggleClass('collapsed');
};
var editSectionPublishDate = function (e) {
e.preventDefault();
var $modal = $(modalSelector);
$modal.attr('data-id', $(this).attr('data-id'));
$modal.find('.start-date').val($(this).attr('data-date'));
$modal.find('.start-time').val($(this).attr('data-time'));
if ($modal.find('.start-date').val() == '' && $modal.find('.start-time').val() == '') {
$modal.find('.save-button').hide();
}
$modal.find('.section-name').html('"' + $(this).closest('.courseware-section').find('.section-name-span').text() + '"');
ModalUtils.showModal();
};
var saveSetSectionScheduleDate = function (e) {
e.preventDefault();
var datetime = DateUtils(
$('.edit-subsection-publish-settings .start-date'),
$('.edit-subsection-publish-settings .start-time')
);
var id = $(modalSelector).attr('data-id');
analytics.track('Edited Section Release Date', {
'course': course_location_analytics,
'id': id,
'start': datetime
});
var saving = new NotificationView.Mini({
title: gettext("Saving&hellip;")
});
saving.show();
// call into server to commit the new order
$.ajax({
url: "/save_item",
type: "POST",
dataType: "json",
contentType: "application/json",
data: JSON.stringify({
'id': id,
'metadata': {
'start': datetime
}
})
}).success(function() {
var pad2 = function(number) {
// pad a number to two places: useful for formatting months, days, hours, etc
// when displaying a date/time
return (number < 10 ? '0' : '') + number;
};
var $thisSection = $('.courseware-section[data-id="' + id + '"]');
var html = _.template(
'<span class="published-status">' +
'<strong>' + gettext("Will Release:") + '&nbsp;</strong>' +
gettext("{month}/{day}/{year} at {hour}:{minute} UTC") +
'</span>' +
'<a href="#" class="edit-button" data-date="{month}/{day}/{year}" data-time="{hour}:{minute}" data-id="{id}">' +
gettext("Edit") +
'</a>',
{year: datetime.getUTCFullYear(), month: pad2(datetime.getUTCMonth() + 1), day: pad2(datetime.getUTCDate()),
hour: pad2(datetime.getUTCHours()), minute: pad2(datetime.getUTCMinutes()),
id: id},
{interpolate: /\{(.+?)\}/g});
$thisSection.find('.section-published-date').html(html);
ModalUtils.hideModal();
saving.hide();
});
};
var addNewSection = function (e) {
e.preventDefault();
$(e.target).addClass('disabled');
var $newSection = $($('#new-section-template').html());
var $cancelButton = $newSection.find('.new-section-name-cancel');
$('.courseware-overview').prepend($newSection);
$newSection.find('.new-section-name').focus().select();
$newSection.find('.section-name-form').bind('submit', saveNewSection);
$cancelButton.bind('click', cancelNewSection);
CancelOnEscape($cancelButton);
};
var saveNewSection = function (e) {
e.preventDefault();
var $saveButton = $(this).find('.new-section-name-save');
var parent = $saveButton.data('parent');
var category = $saveButton.data('category');
var display_name = $(this).find('.new-section-name').val();
analytics.track('Created a Section', {
'course': course_location_analytics,
'display_name': display_name
});
$.post('/create_item', {
'parent_location': parent,
'category': category,
'display_name': display_name
},
function(data) {
if (data.id != undefined) location.reload();
});
};
var cancelNewSection = function (e) {
e.preventDefault();
$('.new-courseware-section-button').removeClass('disabled');
$(this).parents('section.new-section').remove();
};
var addNewSubsection = function (e) {
e.preventDefault();
var $section = $(this).closest('.courseware-section');
var $newSubsection = $($('#new-subsection-template').html());
$section.find('.subsection-list > ol').append($newSubsection);
$section.find('.new-subsection-name-input').focus().select();
var $saveButton = $newSubsection.find('.new-subsection-name-save');
var $cancelButton = $newSubsection.find('.new-subsection-name-cancel');
var parent = $(this).parents("section.branch").data("id");
$saveButton.data('parent', parent);
$saveButton.data('category', $(this).data('category'));
$newSubsection.find('.new-subsection-form').bind('submit', saveNewSubsection);
$cancelButton.bind('click', cancelNewSubsection);
CancelOnEscape($cancelButton);
};
var saveNewSubsection = function (e) {
e.preventDefault();
var parent = $(this).find('.new-subsection-name-save').data('parent');
var category = $(this).find('.new-subsection-name-save').data('category');
var display_name = $(this).find('.new-subsection-name-input').val();
analytics.track('Created a Subsection', {
'course': course_location_analytics,
'display_name': display_name
});
$.post('/create_item', {
'parent_location': parent,
'category': category,
'display_name': display_name
},
function(data) {
if (data.id != undefined) {
location.reload();
}
});
};
var cancelNewSubsection = function (e) {
e.preventDefault();
$(this).parents('li.branch').remove();
};
var overviewDragger = { var overviewDragger = {
droppableClasses: 'drop-target drop-target-prepend drop-target-before drop-target-after', droppableClasses: 'drop-target drop-target-prepend drop-target-before drop-target-after',
...@@ -295,6 +494,24 @@ define(["domReady", "jquery", "jquery.ui", "gettext", "js/views/feedback_notific ...@@ -295,6 +494,24 @@ define(["domReady", "jquery", "jquery.ui", "gettext", "js/views/feedback_notific
}; };
domReady(function() { domReady(function() {
// toggling overview section details
$(function() {
if ($('.courseware-section').length > 0) {
$('.toggle-button-sections').addClass('is-shown');
}
});
$('.toggle-button-sections').bind('click', toggleSections);
$('.expand-collapse-icon').bind('click', toggleSubmodules);
var $body = $('body');
$body.on('click', '.section-published-date .edit-button', editSectionPublishDate);
$body.on('click', '.section-published-date .schedule-button', editSectionPublishDate);
$body.on('click', '.edit-subsection-publish-settings .save-button', saveSetSectionScheduleDate);
$body.on('click', '.edit-subsection-publish-settings .cancel-button', ModalUtils.hideModal);
$('.new-courseware-section-button').bind('click', addNewSection);
$('.new-subsection-item').bind('click', addNewSubsection);
// Section // Section
overviewDragger.makeDraggable( overviewDragger.makeDraggable(
'.courseware-section', '.courseware-section',
...@@ -318,5 +535,8 @@ define(["domReady", "jquery", "jquery.ui", "gettext", "js/views/feedback_notific ...@@ -318,5 +535,8 @@ define(["domReady", "jquery", "jquery.ui", "gettext", "js/views/feedback_notific
); );
}); });
return overviewDragger; return {
overviewDragger: overviewDragger,
saveSetSectionScheduleDate: saveSetSectionScheduleDate
};
}); });
...@@ -18,29 +18,25 @@ ...@@ -18,29 +18,25 @@
<script type="text/javascript"> <script type="text/javascript">
require(["domReady", "jquery", "gettext", "js/models/asset", "js/collections/asset", require(["domReady", "jquery", "gettext", "js/models/asset", "js/collections/asset",
"js/views/assets", "js/views/feedback_prompt", "js/views/assets", "js/views/feedback_prompt",
"js/views/feedback_notification", "jquery.fileupload"], "js/views/feedback_notification", "js/utils/modal", "jquery.fileupload"],
function(domReady, $, gettext, AssetModel, AssetCollection, AssetsView, PromptView, NotificationView) { function(domReady, $, gettext, AssetModel, AssetCollection, AssetsView, PromptView, NotificationView, ModalUtils) {
var assets = new AssetCollection(${asset_list}); var assets = new AssetCollection(${asset_list});
assets.url = "${update_asset_callback_url}"; assets.url = "${update_asset_callback_url}";
var assetsView = new AssetsView({collection: assets, el: $('#asset_table_body')}); var assetsView = new AssetsView({collection: assets, el: $('#asset_table_body')});
var $modal = $(".upload-modal");
var $modalCover = $(".modal-cover");
var hideModal = function (e) { var hideModal = function (e) {
if (e) { if (e) {
e.preventDefault(); e.preventDefault();
} }
$('.file-input').unbind('change.startUpload'); $('.file-input').unbind('change.startUpload');
$modal.hide(); ModalUtils.hideModal();
$modalCover.hide(); };
}
var showUploadModal = function (e) { var showUploadModal = function (e) {
e.preventDefault(); e.preventDefault();
resetUploadModal(); resetUploadModal();
$modal.show(); ModalUtils.showModal();
$('.file-input').bind('change', startUpload); $('.file-input').bind('change', startUpload);
$('.upload-modal .file-chooser').fileupload({ $('.upload-modal .file-chooser').fileupload({
dataType: 'json', dataType: 'json',
...@@ -63,8 +59,6 @@ require(["domReady", "jquery", "gettext", "js/models/asset", "js/collections/ass ...@@ -63,8 +59,6 @@ require(["domReady", "jquery", "gettext", "js/models/asset", "js/collections/ass
} }
}); });
$modalCover.show();
}; };
var showFileSelectionMenu = function(e) { var showFileSelectionMenu = function(e) {
......
...@@ -225,7 +225,7 @@ require(["domReady!", "jquery", "js/models/location", "js/models/section", "js/v ...@@ -225,7 +225,7 @@ require(["domReady!", "jquery", "js/models/location", "js/models/section", "js/v
</div> </div>
<footer></footer> <footer></footer>
<div class="edit-subsection-publish-settings"> <div class="edit-subsection-publish-settings showAsModal">
<div class="settings"> <div class="settings">
<h3>${_("Section Release Date")}</h3> <h3>${_("Section Release Date")}</h3>
<div class="picker datepair"> <div class="picker datepair">
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment