Merge remote-tracking branch 'origin/feature/cale/cms-master' into

feature/dhm/cms-settings

Conflicts:
	cms/djangoapps/contentstore/course_info_model.py
	cms/djangoapps/contentstore/views.py
	cms/static/js/models/course_info.js
	cms/static/js/template_loader.js
	cms/static/js/views/course_info_edit.js
	cms/templates/base.html
	cms/templates/course_info.html
	cms/urls.py
This commit is contained in:
Don Mitchell
2012-12-11 10:55:10 -05:00
70 changed files with 2175 additions and 449 deletions

View File

@@ -0,0 +1,19 @@
<a href="#" class="edit-button"><span class="edit-icon"></span>Edit</a>
<h2>Course Handouts</h2>
<%if (model.get('data') != null) { %>
<div class="handouts-content">
<%= model.get('data') %>
</div>
<% } else {%>
<p>You have no handouts defined</p>
<% } %>
<form class="edit-handouts-form" style="display: block;">
<div class="row">
<textarea class="handouts-content-editor text-editor"></textarea>
</div>
<div class="row">
<a href="#" class="save-button">Save</a>
<a href="#" class="cancel-button">Cancel</a>
</div>
</form>

View File

@@ -0,0 +1,29 @@
<li name="<%- updateModel.cid %>">
<!-- FIXME what style should we use for initially hidden? --> <!-- TODO decide whether this should use codemirror -->
<form class="new-update-form">
<div class="row">
<label class="inline-label">Date:</label>
<!-- TODO replace w/ date widget and actual date (problem is that persisted version is "Month day" not an actual date obj -->
<input type="text" class="date" value="<%= updateModel.get('date') %>">
</div>
<div class="row">
<textarea class="new-update-content text-editor"><%= updateModel.get('content') %></textarea>
</div>
<div class="row">
<!-- cid rather than id b/c new ones have cid's not id's -->
<a href="#" class="save-button" name="<%= updateModel.cid %>">Save</a>
<a href="#" class="cancel-button" name="<%= updateModel.cid %>">Cancel</a>
</div>
</form>
<div class="post-preview">
<div class="post-actions">
<a href="#" class="edit-button" name="<%- updateModel.cid %>"><span class="edit-icon"></span>Edit</a>
<a href="#" class="delete-button" name="<%- updateModel.cid %>"><span class="delete-icon"></span>Delete</a>
</div>
<h2>
<span class="calendar-icon"></span><span class="date-display"><%=
updateModel.get('date') %></span>
</h2>
<div class="update-contents"><%= updateModel.get('content') %></div>
</div>
</li>

View File

@@ -0,0 +1,14 @@
<!-- In order to enable better debugging of templates, put them in
the script tag section.
TODO add lazy load fn to load templates as needed (called
from backbone view initialize to set this.template of the view)
-->
<%block name="jsextra">
<script type="text/javascript" charset="utf-8">
// How do I load an html file server side so I can
// Precompiling your templates can be a big help when debugging errors you can't reproduce. This is because precompiled templates can provide line numbers and a stack trace, something that is not possible when compiling templates on the client. The source property is available on the compiled template function for easy precompilation.
// <script>CMS.course_info_update = <%= _.template(jstText).source %>;</script>
</script>
</%block>

Binary file not shown.

Before

Width:  |  Height:  |  Size: 970 B

After

Width:  |  Height:  |  Size: 2.8 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.0 KiB

After

Width:  |  Height:  |  Size: 2.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 951 B

View File

@@ -11,6 +11,11 @@ $(document).ready(function() {
$body = $('body');
$modal = $('.history-modal');
$modalCover = $('<div class="modal-cover">');
// cdodge: this looks funny, but on AWS instances, this base.js get's wrapped in a separate scope as part of Django static
// pipelining (note, this doesn't happen on local runtimes). So if we set it on window, when we can access it from other
// scopes (namely the course-info tab)
window.$modalCover = $modalCover;
$body.append($modalCover);
$newComponentItem = $('.new-component-item');
$newComponentTypePicker = $('.new-component');
@@ -93,7 +98,7 @@ $(document).ready(function() {
// section name editing
$('.section-name').bind('click', editSectionName);
$('.edit-section-name-cancel').bind('click', cancelEditSectionName);
$('.edit-section-name-save').bind('click', saveEditSectionName);
// $('.edit-section-name-save').bind('click', saveEditSectionName);
// section date setting
$('.set-publish-date').bind('click', setSectionScheduleDate);
@@ -585,33 +590,44 @@ function hideToastMessage(e) {
$(this).closest('.toast-notification').remove();
}
function addNewSection(e) {
function addNewSection(e, isTemplate) {
e.preventDefault();
var $newSection = $($('#new-section-template').html());
var $cancelButton = $newSection.find('.new-section-name-cancel');
$('.new-courseware-section-button').after($newSection);
$newSection.find('.new-section-name').focus().select();
$newSection.find('.new-section-name-save').bind('click', saveNewSection);
$newSection.find('.new-section-name-cancel').bind('click', cancelNewSection);
$newSection.find('.section-name-form').bind('submit', saveNewSection);
$cancelButton.bind('click', cancelNewSection);
$body.bind('keyup', { $cancelButton: $cancelButton }, checkForCancel);
}
function checkForCancel(e) {
if(e.which == 27) {
$body.unbind('keyup', checkForCancel);
e.data.$cancelButton.click();
}
}
function saveNewSection(e) {
e.preventDefault();
parent = $(this).data('parent');
template = $(this).data('template');
var $saveButton = $(this).find('.new-section-name-save');
var parent = $saveButton.data('parent');
var template = $saveButton.data('template');
var display_name = $(this).find('.new-section-name').val();
display_name = $(this).prev('.new-section-name').val();
$.post('/clone_item',
{'parent_location' : parent,
'template' : template,
'display_name': display_name,
},
function(data) {
$.post('/clone_item', {
'parent_location' : parent,
'template' : template,
'display_name': display_name,
},
function(data) {
if (data.id != undefined)
location.reload();
});
location.reload();
}
);
}
function cancelNewSection(e) {
@@ -619,44 +635,44 @@ function cancelNewSection(e) {
$(this).parents('section.new-section').remove();
}
function addNewCourse(e) {
e.preventDefault();
var $newCourse = $($('#new-course-template').html());
var $cancelButton = $newCourse.find('.new-course-cancel');
$('.new-course-button').after($newCourse);
$newCourse.find('.new-course-name').focus().select();
$newCourse.find('.new-course-save').bind('click', saveNewCourse);
$newCourse.find('.new-course-cancel').bind('click', cancelNewCourse);
$newCourse.find('form').bind('submit', saveNewCourse);
$cancelButton.bind('click', cancelNewCourse);
$body.bind('keyup', { $cancelButton: $cancelButton }, checkForCancel);
}
function saveNewCourse(e) {
e.preventDefault();
var $newCourse = $(this).closest('.new-course');
template = $(this).data('template');
org = $newCourse.find('.new-course-org').val();
number = $newCourse.find('.new-course-number').val();
display_name = $newCourse.find('.new-course-name').val();
var template = $(this).find('.new-course-save').data('template');
var org = $newCourse.find('.new-course-org').val();
var number = $newCourse.find('.new-course-number').val();
var display_name = $newCourse.find('.new-course-name').val();
if (org == '' || number == '' || display_name == ''){
alert('You must specify all fields in order to create a new course.');
return;
}
$.post('/create_new_course',
{ 'template' : template,
'org' : org,
'number' : number,
'display_name': display_name,
},
function(data) {
if (data.id != undefined)
location.reload();
else if (data.ErrMsg != undefined)
$.post('/create_new_course', {
'template' : template,
'org' : org,
'number' : number,
'display_name': display_name,
},
function(data) {
if (data.id != undefined) {
window.location = '/' + data.id.replace(/.*:\/\//, '');
} else if (data.ErrMsg != undefined) {
alert(data.ErrMsg);
});
}
});
}
function cancelNewCourse(e) {
@@ -672,35 +688,37 @@ function addNewSubsection(e) {
$section.find('.new-subsection-name-input').focus().select();
var $saveButton = $newSubsection.find('.new-subsection-name-save');
$saveButton.bind('click', saveNewSubsection);
var $cancelButton = $newSubsection.find('.new-subsection-name-cancel');
parent = $(this).parents("section.branch").data("id");
var parent = $(this).parents("section.branch").data("id");
$saveButton.data('parent', parent)
$saveButton.data('template', $(this).data('template'));
$newSubsection.find('.new-subsection-name-cancel').bind('click', cancelNewSubsection);
$newSubsection.find('.new-subsection-form').bind('submit', saveNewSubsection);
$cancelButton.bind('click', cancelNewSubsection);
$body.bind('keyup', { $cancelButton: $cancelButton }, checkForCancel);
}
function saveNewSubsection(e) {
e.preventDefault();
parent = $(this).data('parent');
template = $(this).data('template');
var parent = $(this).find('.new-subsection-name-save').data('parent');
var template = $(this).find('.new-subsection-name-save').data('template');
var display_name = $(this).find('.new-subsection-name-input').val();
display_name = $(this).prev('.subsection-name').find('.new-subsection-name-input').val()
$.post('/clone_item',
{'parent_location' : parent,
'template' : template,
'display_name': display_name,
},
function(data) {
$.post('/clone_item', {
'parent_location' : parent,
'template' : template,
'display_name': display_name
},
function(data) {
if (data.id != undefined) {
location.reload();
}
});
}
);
}
function cancelNewSubsection(e) {
@@ -710,22 +728,30 @@ function cancelNewSubsection(e) {
function editSectionName(e) {
e.preventDefault();
$(this).children('div.section-name-edit').show();
$(this).children('span.section-name-span').hide();
$(this).unbind('click', editSectionName);
$(this).children('.section-name-edit').show();
$(this).find('.edit-section-name').focus();
$(this).children('.section-name-span').hide();
$(this).find('.section-name-edit').bind('submit', saveEditSectionName);
$(this).find('.edit-section-name-cancel').bind('click', cancelNewSection);
$body.bind('keyup', { $cancelButton: $(this).find('.edit-section-name-cancel') }, checkForCancel);
}
function cancelEditSectionName(e) {
e.preventDefault();
$(this).parent().hide();
$(this).parent().siblings('span.section-name-span').show();
$(this).parent().siblings('.section-name-span').show();
$(this).closest('.section-name').bind('click', editSectionName);
e.stopPropagation();
}
function saveEditSectionName(e) {
e.preventDefault();
id = $(this).closest("section.courseware-section").data("id");
display_name = $.trim($(this).prev('.edit-section-name').val());
$(this).closest('.section-name').unbind('click', editSectionName);
var id = $(this).closest('.courseware-section').data('id');
var display_name = $.trim($(this).find('.edit-section-name').val());
$(this).closest('.courseware-section .section-name').append($spinner);
$spinner.show();
@@ -746,10 +772,10 @@ function saveEditSectionName(e) {
}).success(function()
{
$spinner.delay(250).fadeOut(250);
$_this.parent().siblings('span.section-name-span').html(display_name);
$_this.parent().siblings('span.section-name-span').show();
$_this.parent().hide();
e.stopPropagation();
$_this.closest('h3').find('.section-name-span').html(display_name).show();
$_this.hide();
$_this.closest('.section-name').bind('click', editSectionName);
e.stopPropagation();
});
}

View File

@@ -15,7 +15,7 @@ CMS.Models.CourseInfo = Backbone.Model.extend({
// course update -- biggest kludge here is the lack of a real id to map updates to originals
CMS.Models.CourseUpdate = Backbone.Model.extend({
defaults: {
"date" : $.datepicker.formatDate('MM d', new Date()),
"date" : $.datepicker.formatDate('MM d, yy', new Date()),
"content" : ""
}
});
@@ -29,6 +29,8 @@ CMS.Models.CourseUpdateCollection = Backbone.Collection.extend({
model : CMS.Models.CourseUpdate
});

View File

@@ -0,0 +1,10 @@
CMS.Models.ModuleInfo = Backbone.Model.extend({
url: function() {return "/module_info/" + this.id;},
defaults: {
"id": null,
"data": null,
"metadata" : null,
"children" : null
},
});

View File

@@ -5,7 +5,7 @@
if (typeof window.templateLoader == 'function') return;
var templateLoader = {
templateVersion: "0.0.3",
templateVersion: "0.0.8",
templates: {},
loadRemoteTemplate: function(templateName, filename, callback) {
if (!this.templates[templateName]) {

View File

@@ -13,7 +13,11 @@ CMS.Views.CourseInfoEdit = Backbone.View.extend({
el: this.$('#course-update-view'),
collection: this.model.get('updates')
});
// TODO instantiate the handouts view
new CMS.Views.ClassInfoHandoutsView({
el: this.$('#course-handouts-view'),
model: this.model.get('handouts')
});
return this;
}
});
@@ -34,11 +38,11 @@ CMS.Views.ClassInfoUpdateView = Backbone.View.extend({
// instantiates an editor template for each update in the collection
window.templateLoader.loadRemoteTemplate("course_info_update",
// TODO Where should the template reside? how to use the static.url to create the path?
"/static/coffee/src/client_templates/course_info_update.html",
function (raw_template) {
"/static/client_templates/course_info_update.html",
function (raw_template) {
self.template = _.template(raw_template);
self.render();
}
self.render();
}
);
},
@@ -53,28 +57,47 @@ CMS.Views.ClassInfoUpdateView = Backbone.View.extend({
$(updateEle).append(newEle);
});
this.$el.find(".new-update-form").hide();
this.$el.find('.date').datepicker({ 'dateFormat': 'MM d, yy' });
return this;
},
onNew: function(event) {
var self = this;
// create new obj, insert into collection, and render this one ele overriding the hidden attr
var newModel = new CMS.Models.CourseUpdate();
this.collection.add(newModel, {at : 0});
var newForm = this.template({ updateModel : newModel });
var $newForm = $(this.template({ updateModel : newModel }));
var $textArea = $newForm.find(".new-update-content").first();
if (this.$codeMirror == null ) {
this.$codeMirror = CodeMirror.fromTextArea($textArea.get(0), {
mode: "text/html",
lineNumbers: true,
lineWrapping: true,
});
}
var updateEle = this.$el.find("#course-update-list");
$(updateEle).append(newForm);
$(newForm).find(".new-update-form").show();
$(updateEle).prepend($newForm);
$newForm.addClass('editing');
this.$currentPost = $newForm.closest('li');
window.$modalCover.show();
window.$modalCover.bind('click', function() {
self.closeEditor(self, true);
});
$('.date').datepicker('destroy');
$('.date').datepicker({ 'dateFormat': 'MM d, yy' });
},
onSave: function(event) {
var targetModel = this.eventModel(event);
targetModel.set({ date : this.dateEntry(event).val(), content : this.contentEntry(event).val() });
// push change to display, hide the editor, submit the change
$(this.dateDisplay(event)).val(targetModel.get('date'));
$(this.contentDisplay(event)).val(targetModel.get('content'));
$(this.editor(event)).hide();
console.log(this.contentEntry(event).val());
targetModel.set({ date : this.dateEntry(event).val(), content : this.$codeMirror.getValue() });
// push change to display, hide the editor, submit the change
this.closeEditor(this);
targetModel.save();
},
@@ -82,14 +105,31 @@ CMS.Views.ClassInfoUpdateView = Backbone.View.extend({
// change editor contents back to model values and hide the editor
$(this.editor(event)).hide();
var targetModel = this.eventModel(event);
$(this.dateEntry(event)).val(targetModel.get('date'));
$(this.contentEntry(event)).val(targetModel.get('content'));
this.closeEditor(this, !targetModel.id);
},
onEdit: function(event) {
var self = this;
this.$currentPost = $(event.target).closest('li');
this.$currentPost.addClass('editing');
$(this.editor(event)).show();
var $textArea = this.$currentPost.find(".new-update-content").first();
if (this.$codeMirror == null ) {
this.$codeMirror = CodeMirror.fromTextArea($textArea.get(0), {
mode: "text/html",
lineNumbers: true,
lineWrapping: true,
});
}
window.$modalCover.show();
var targetModel = this.eventModel(event);
window.$modalCover.bind('click', function() {
self.closeEditor(self);
});
},
onDelete: function(event) {
// TODO ask for confirmation
// remove the dom element and delete the model
@@ -101,6 +141,24 @@ CMS.Views.ClassInfoUpdateView = Backbone.View.extend({
}
});
},
closeEditor: function(self, removePost) {
var targetModel = self.collection.getByCid(self.$currentPost.attr('name'));
if(removePost) {
self.$currentPost.remove();
}
// close the modal and insert the appropriate data
self.$currentPost.removeClass('editing');
self.$currentPost.find('.date-display').html(targetModel.get('date'));
self.$currentPost.find('.date').val(targetModel.get('date'));
self.$currentPost.find('.update-contents').html(targetModel.get('content'));
self.$currentPost.find('.new-update-content').val(targetModel.get('content'));
self.$currentPost.find('form').hide();
window.$modalCover.unbind('click');
window.$modalCover.hide();
},
// Dereferencing from events to screen elements
eventModel: function(event) {
@@ -119,7 +177,7 @@ CMS.Views.ClassInfoUpdateView = Backbone.View.extend({
dateEntry: function(event) {
var li = $(event.currentTarget).closest("li");
if (li) return $(li).find("#date-entry").first();
if (li) return $(li).find(".date").first();
},
contentEntry: function(event) {
@@ -135,4 +193,83 @@ CMS.Views.ClassInfoUpdateView = Backbone.View.extend({
}
});
// the handouts view is dumb right now; it needs tied to a model and all that jazz
CMS.Views.ClassInfoHandoutsView = Backbone.View.extend({
// collection is CourseUpdateCollection
events: {
"click .save-button" : "onSave",
"click .cancel-button" : "onCancel",
"click .edit-button" : "onEdit"
},
initialize: function() {
var self = this;
this.model.fetch(
{
complete: function() {
window.templateLoader.loadRemoteTemplate("course_info_handouts",
"/static/client_templates/course_info_handouts.html",
function (raw_template) {
self.template = _.template(raw_template);
self.render();
}
);
}
}
);
},
render: function () {
var updateEle = this.$el;
var self = this;
this.$el.html(
$(this.template( {
model: this.model
})
)
);
this.$preview = this.$el.find('.handouts-content');
this.$form = this.$el.find(".edit-handouts-form");
this.$editor = this.$form.find('.handouts-content-editor');
this.$form.hide();
return this;
},
onEdit: function(event) {
var self = this;
this.$editor.val(this.$preview.html());
this.$form.show();
if (this.$codeMirror == null) {
this.$codeMirror = CodeMirror.fromTextArea(this.$editor.get(0), {
mode: "text/html",
lineNumbers: true,
lineWrapping: true,
});
}
window.$modalCover.show();
window.$modalCover.bind('click', function() {
self.closeEditor(self);
});
},
onSave: function(event) {
this.model.set('data', this.$codeMirror.getValue());
this.render();
this.model.save();
this.$form.hide();
this.closeEditor(this);
},
onCancel: function(event) {
this.$form.hide();
this.closeEditor(this);
},
closeEditor: function(self) {
this.$form.hide();
window.$modalCover.unbind('click');
window.$modalCover.hide();
}
});

View File

@@ -181,6 +181,11 @@ code {
padding: 20px;
}
.details {
margin-bottom: 30px;
font-size: 14px;
}
h4 {
padding: 6px 14px;
border-bottom: 1px solid #cbd1db;
@@ -338,4 +343,29 @@ body.show-wip {
content: '';
@extend .spinner-icon;
}
}
.new-button {
@include grey-button;
padding: 20px 0;
text-align: center;
&.big {
display: block;
}
}
.edit-button.standard,
.delete-button.standard {
float: left;
@include white-button;
padding: 3px 10px 4px;
margin-left: 7px;
font-size: 12px;
font-weight: 400;
.edit-icon,
.delete-icon {
margin-right: 4px;
}
}

View File

@@ -51,14 +51,14 @@
@include button;
border: 1px solid $darkGrey;
border-radius: 3px;
@include linear-gradient(top, rgba(255, 255, 255, 0.8), rgba(255, 255, 255, 0) 60%);
@include linear-gradient(top, rgba(255, 255, 255, 0.6), rgba(255, 255, 255, 0));
background-color: #dfe5eb;
@include box-shadow(0 1px 0 rgba(255, 255, 255, .3) inset);
color: #5d6779;
color: #778192;
&:hover {
background-color: #f2f6f9;
color: #5d6779;
color: #778192;
}
}

View File

@@ -1,77 +1,179 @@
body.updates {
.course-info {
h2 {
margin-bottom: 24px;
font-size: 22px;
font-weight: 300;
}
.course-info-wrapper {
display: table;
width: 100%;
clear: both;
}
.main-column,
.course-handouts {
float: none;
display: table-cell;
}
.main-column {
border-radius: 3px 0 0 3px;
border-right-color: $mediumGrey;
}
.CodeMirror {
border: 1px solid #3c3c3c;
background: #fff;
color: #3c3c3c;
}
}
.course-updates {
padding: 30px 40px;
margin: 0;
li {
padding: 24px 0 32px;
.update-list > li {
padding: 34px 0 42px;
border-top: 1px solid #cbd1db;
}
h3 {
margin-bottom: 18px;
font-size: 14px;
font-weight: 700;
color: #646464;
letter-spacing: 1px;
text-transform: uppercase;
&.editing {
position: relative;
z-index: 1001;
padding: 0;
border-top: none;
border-radius: 3px;
background: #fff;
.post-preview {
display: none;
}
}
h1 {
float: none;
font-size: 24px;
font-weight: 300;
}
h2 {
margin-bottom: 18px;
font-size: 14px;
font-weight: 700;
line-height: 30px;
color: #646464;
letter-spacing: 1px;
text-transform: uppercase;
}
h3 {
margin: 34px 0 11px;
font-size: 16px;
font-weight: 700;
}
}
.update-contents {
padding-left: 30px;
p {
font-size: 14px;
line-height: 18px;
font-size: 16px;
line-height: 25px;
}
p + p {
margin-top: 18px;
margin-top: 25px;
}
.primary {
border: 1px solid #ddd;
background: #f6f6f6;
padding: 20px;
}
}
.new-update-button {
@include grey-button;
@include blue-button;
display: block;
text-align: center;
padding: 12px 0;
padding: 18px 0;
margin-bottom: 28px;
}
.new-update-form {
@include edit-box;
margin-bottom: 24px;
padding: 30px;
border: none;
textarea {
height: 180px;
}
}
.post-actions {
float: right;
.edit-button,
.delete-button{
float: left;
@include white-button;
padding: 3px 10px 4px;
margin-left: 7px;
font-size: 12px;
font-weight: 400;
.edit-icon,
.delete-icon {
margin-right: 4px;
}
}
}
}
.course-handouts {
padding: 15px 20px;
width: 30%;
padding: 20px 30px;
margin: 0;
border-radius: 0 3px 3px 0;
border-left: none;
background: $lightGrey;
.new-handout-button {
@include grey-button;
display: block;
text-align: center;
padding: 12px 0;
margin-bottom: 28px;
h2 {
font-size: 18px;
font-weight: 700;
}
li {
margin-bottom: 10px;
.edit-button {
float: right;
@include white-button;
padding: 3px 10px 4px;
margin-left: 7px;
font-size: 12px;
font-weight: 400;
.edit-icon,
.delete-icon {
margin-right: 4px;
}
}
.handouts-content {
font-size: 14px;
}
.new-handout-form {
@include edit-box;
margin-bottom: 24px;
.treeview-handoutsnav li {
margin-bottom: 12px;
}
}
.edit-handouts-form {
@include edit-box;
position: absolute;
right: 0;
z-index: 10001;
width: 800px;
padding: 30px;
textarea {
height: 300px;
}
}

View File

@@ -5,12 +5,7 @@ input.courseware-unit-search-input {
}
.courseware-overview {
.new-courseware-section-button {
@include grey-button;
display: block;
text-align: center;
padding: 12px 0;
}
}
.courseware-section {
@@ -146,18 +141,18 @@ input.courseware-unit-search-input {
.section-name-edit {
input {
font-size: 16px;
font-size: 16px;
}
.save-button {
@include blue-button;
padding: 7px 20px 7px;
padding: 10px 20px;
margin-right: 5px;
}
.cancel-button {
@include white-button;
padding: 7px 20px 7px;
padding: 10px 20px;
}
}
@@ -205,7 +200,7 @@ input.courseware-unit-search-input {
.new-section-name-save,
.new-subsection-name-save {
@include blue-button;
padding: 2px 20px 5px;
padding: 6px 20px 8px;
margin: 0 5px;
color: #fff !important;
}
@@ -213,7 +208,7 @@ input.courseware-unit-search-input {
.new-section-name-cancel,
.new-subsection-name-cancel {
@include white-button;
padding: 2px 20px 5px;
padding: 6px 20px 8px;
color: #8891a1 !important;
}

View File

@@ -89,6 +89,7 @@
.new-course-save {
@include blue-button;
// padding: ;
}
.new-course-cancel {

View File

@@ -137,6 +137,10 @@
height: 11px;
margin-right: 8px;
background: url(../img/plus-icon.png) no-repeat;
&.white {
background: url(../img/plus-icon-white.png) no-repeat;
}
}
.plus-icon-small {

69
cms/static/sass/_lms.scss Normal file
View File

@@ -0,0 +1,69 @@
.component {
font-family: 'Open Sans', Verdana, Arial, Helvetica, sans-serif;
font-size: 16px;
line-height: 1.6;
color: #3c3c3c;
a {
color: #1d9dd9;
text-decoration: none;
}
p {
font-size: 16px;
line-height: 1.6;
}
h1 {
float: none;
}
h2 {
color: #646464;
font-size: 19px;
font-weight: 300;
letter-spacing: 1px;
margin-bottom: 15px;
margin-left: 0;
text-transform: uppercase;
}
h3 {
font-size: 19px;
font-weight: 400;
}
h4 {
background: none;
padding: 0;
border: none;
@include box-shadow(none);
font-size: 16px;
font-weight: 400;
}
code {
margin: 0 2px;
padding: 0px 5px;
border-radius: 3px;
border: 1px solid #eaeaea;
white-space: nowrap;
font-family: Monaco, monospace;
font-size: 14px;
background-color: #f8f8f8;
}
p + h2, ul + h2, ol + h2, p + h3 {
margin-top: 40px;
}
p + p, ul + p, ol + p {
margin-top: 20px;
}
p {
color: #3c3c3c;
font: normal 1em/1.6em;
margin: 0px;
}
}

View File

@@ -6,6 +6,72 @@
padding: 12px 0;
}
.unit-body {
padding: 30px 40px;
}
.components > li {
margin: 0;
border-radius: 0;
&.new-component-item {
margin-top: 20px;
}
}
.component {
border: 1px solid $mediumGrey;
border-top: none;
&:first-child {
border-top: 1px solid $mediumGrey;
}
&:hover {
border: 1px solid $mediumGrey;
border-top: none;
&:first-child {
border-top: 1px solid $mediumGrey;
}
.drag-handle {
background: url(../img/drag-handles.png) center no-repeat $lightGrey;
}
}
.drag-handle {
top: 0;
right: 0;
z-index: 11;
width: 35px;
border: none;
background: url(../img/drag-handles.png) center no-repeat $lightGrey;
&:hover {
background: url(../img/drag-handles.png) center no-repeat $lightGrey;
}
}
.component-actions {
top: 26px;
right: 44px;
}
}
.component.editing {
.xmodule_display {
display: none;
}
}
.xmodule_display {
padding: 20px 20px 22px;
font-size: 24px;
font-weight: 300;
background: $lightGrey;
}
.static-page-item {
position: relative;
margin: 10px 0;

View File

@@ -4,6 +4,7 @@
}
.main-column {
clear: both;
float: left;
width: 70%;
}
@@ -54,94 +55,11 @@
position: relative;
z-index: 10;
margin: 20px 40px;
border: 1px solid #d1ddec;
border-radius: 3px;
background: #fff;
@include transition(none);
&:hover {
border-color: #6696d7;
.drag-handle,
.component-actions a {
background-color: $blue;
}
.drag-handle {
border-color: $blue;
}
}
&.editing {
border-color: #6696d7;
.drag-handle,
.component-actions {
display: none;
}
}
&.component-placeholder {
border-color: #6696d7;
}
.xmodule_display {
padding: 40px 20px 20px;
}
.component-actions {
position: absolute;
top: 4px;
right: 4px;
@include transition(opacity .15s);
}
.edit-button,
.delete-button {
float: left;
padding: 3px 10px 4px;
margin-left: 3px;
border: 1px solid #fff;
border-radius: 3px;
background: #d1ddec;
font-size: 12px;
color: #fff;
@include transition(all .15s);
&:hover {
background-color: $blue;
color: #fff;
}
.edit-icon,
.delete-icon {
margin-right: 4px;
}
}
.drag-handle {
position: absolute;
display: block;
top: -1px;
right: -16px;
z-index: -1;
width: 15px;
height: 100%;
border-radius: 0 3px 3px 0;
border: 1px solid #d1ddec;
background: url(../img/white-drag-handles.png) center no-repeat #d1ddec;
cursor: move;
@include transition(all .15s);
}
&.new-component-item {
padding: 0;
border: 1px solid #8891a1;
border-radius: 3px;
@include linear-gradient(top, rgba(255, 255, 255, .3), rgba(255, 255, 255, 0));
background-color: #d1dae3;
@include box-shadow(0 1px 0 rgba(255, 255, 255, .2) inset);
@include transition(background-color .15s, border-color .15s);
border: none;
border-radius: 0;
&.adding {
background-color: $blue;
@@ -223,8 +141,63 @@
}
}
.component {
border: 1px solid #d1ddec;
border-radius: 3px;
background: #fff;
@include transition(none);
&:hover {
border-color: #6696d7;
.drag-handle {
background-color: $blue;
border-color: $blue;
}
}
&.editing {
border-color: #6696d7;
.drag-handle,
.component-actions {
display: none;
}
}
&.component-placeholder {
border-color: #6696d7;
}
.component-actions {
position: absolute;
top: 7px;
right: 9px;
@include transition(opacity .15s);
a {
color: $darkGrey;
}
}
.drag-handle {
position: absolute;
display: block;
top: -1px;
right: -16px;
z-index: -1;
width: 15px;
height: 100%;
border-radius: 0 3px 3px 0;
border: 1px solid #d1ddec;
background: url(../img/white-drag-handles.png) center no-repeat #d1ddec;
cursor: move;
@include transition(all .15s);
}
}
.xmodule_display {
padding: 10px 20px;
padding: 40px 20px 20px;
}
.component-editor {

View File

@@ -2,11 +2,6 @@
.user-overview {
@extend .window;
padding: 30px 40px;
.details {
margin-bottom: 20px;
font-size: 14px;
}
}
.new-user-button {

View File

@@ -25,6 +25,7 @@
@import "modal";
@import "alerts";
@import "login";
@import "lms";
@import 'jquery-ui-calendar';
@import 'content-types';