From 91c5b8824856cfce0f0084964850e38d4bc000fa Mon Sep 17 00:00:00 2001 From: Matthew Mongeau Date: Mon, 27 Aug 2012 16:21:12 -0400 Subject: [PATCH 001/364] Initial sidebar --- .../django_comment_client/forum/views.py | 1 + lms/static/sass/_discussion.scss | 206 +++++++++++++++--- lms/templates/discussion/index.html | 31 ++- 3 files changed, 202 insertions(+), 36 deletions(-) diff --git a/lms/djangoapps/django_comment_client/forum/views.py b/lms/djangoapps/django_comment_client/forum/views.py index 62055f0ab7..4cb1acdb2b 100644 --- a/lms/djangoapps/django_comment_client/forum/views.py +++ b/lms/djangoapps/django_comment_client/forum/views.py @@ -168,6 +168,7 @@ def forum_form_discussion(request, course_id): 'recent_active_threads': recent_active_threads, 'trending_tags': trending_tags, 'staff_access' : has_access(request.user, course, 'staff'), + 'threads': threads, } # print "start rendering.." return render_to_response('discussion/index.html', context) diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index 6c1988684e..b91603a3e6 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -1,3 +1,141 @@ +.discussion-wrapper { + display: table; + table-layout: fixed; + width: 100%; + height: 500px; + background: #fff; + border-radius: 3px; + border: 1px solid #aaa; + box-shadow: 0 1px 2px rgba(0, 0, 0, 0.05); + ul { + list-style: none; + margin: 0; + padding: 0; + border: 0; + outline: 0; + font-size: 100%; + font: inherit; + vertical-align: baseline; + } +} + +.discussion-sidebar { + display: table-cell; + vertical-align: top; + width: 27.7%; + background: #f6f6f6; + border-radius: 3px 0 0 3px; + border-right: 3px solid #bcbcbc; +} + +.board-drop-btn { + display: block; + height: 60px; + border-bottom: 1px solid #a3a3a3; + border-radius: 3px 0 0 0; + background: -webkit-linear-gradient(top, #ebebeb, #d9d9d9); + font-size: 16px; + font-weight: 700; + line-height: 58px; + text-align: center; + color: #333; + text-shadow: 0 1px 0 rgba(255, 255, 255, .8); +} + +.sort-bar { + height: 27px; + border-bottom: 1px solid #a3a3a3; + background: -webkit-linear-gradient(top, #cdcdcd, #b6b6b6); + box-shadow: 0 1px 0 rgba(255, 255, 255, .4) inset; + + a { + display: block; + float: right; + height: 27px; + margin-right: 10px; + font-size: 11px; + font-weight: bold; + line-height: 23px; + color: #333; + text-shadow: 0 1px 0 rgba(255, 255, 255, .5); + + .sort-label { + font-size: 9px; + text-transform: uppercase; + } + } +} +.post-list { + a { + display: block; + height: 36px; + padding: 0 10px; + border-bottom: 1px solid #ddd; + background: #fff; + font-size: 13px; + font-weight: 700; + line-height: 34px; + color: #333; + + &.read .title { + font-weight: 400; + color: #737373; + } + } + + .title { + display: block; + float: left; + width: 70%; + white-space: nowrap; + text-overflow: ellipsis; + overflow: hidden; + } + + .votes, + .comments { + display: block; + float: right; + width: 32px; + height: 16px; + margin-top: 9px; + border-radius: 2px; + background: -webkit-linear-gradient(top, #d4d4d4, #dfdfdf); + font-size: 9px; + font-weight: 700; + line-height: 16px; + text-align: center; + color: #767676; + } + + .comments { + position: relative; + margin-left: 4px; + + &:after { + content: '◥'; + display: block; + position: absolute; + top: 11px; + right: 3px; + font-size: 6px; + color: #dfdfdf; + } + + &.new { + background: -webkit-linear-gradient(top, #84d7fe, #99e0fe); + color: #333; + + &:after { + color: #99e0fe; + } + } + } +} + + + +/*** OLD STUFF ***/ /*** Variables ***/ $comment-margin-left: 30px; @@ -57,10 +195,10 @@ $tag-text-color: #5b614f; /*** Sidebar ***/ - .sidebar-module { + .sidebar-module { @include clearfix; padding: 0 26px 24px; - margin-bottom: 24px; + margin-bottom: 24px; border-bottom: 1px solid #d3d3d3; font-size: 13px; @@ -115,7 +253,7 @@ $tag-text-color: #5b614f; border: none; } - a { + a { @include standard-discussion-link; background: none; @@ -169,7 +307,7 @@ $tag-text-color: #5b614f; } .sidebar-threads-count, .sidebar-comments-count { - + span { font-size: 1.5em; font-weight: bold; @@ -218,12 +356,12 @@ $tag-text-color: #5b614f; } a { - display: block; + display: block; height: 25px; padding-left: 25px; border-radius: 50%; background: url(../images/admin-actions-sprite.png) no-repeat; - font-size: .8em; + font-size: .8em; line-height: 25px; color: #b8b8b8; @include transition(color, .1s); @@ -233,7 +371,7 @@ $tag-text-color: #5b614f; } &.admin-endorse { - background-position: 0 0; + background-position: 0 0; &:hover { color: #63b141; @@ -307,7 +445,7 @@ $tag-text-color: #5b614f; /*** thread ***/ - + .thread { //display: none; @@ -360,12 +498,12 @@ $tag-text-color: #5b614f; margin-right: 1em; } - .show-comments-wrapper { + .show-comments-wrapper { display: inline; margin-right: 20px; } - .discussion-actions { + .discussion-actions { display: inline; margin: 0; padding: 0; @@ -538,7 +676,7 @@ $tag-text-color: #5b614f; background-color: #959595; @include background-image(linear-gradient(top, #959595, #7B7B7B)); border: 1px solid #6F6F6F; - @include box-shadow(inset 0 1px 0 #A2A2A2, 0 0 3px #CCC); + @include box-shadow(inset 0 1px 0 #A2A2A2, 0 0 3px #CCC); color: white; display: inline-block; font-size: inherit; @@ -569,8 +707,8 @@ $tag-text-color: #5b614f; margin-top: 18px; text-align: center; - .discussion-vote { - display: block; + .discussion-vote { + display: block; width: 50px; height: 17px; margin: auto; @@ -584,7 +722,7 @@ $tag-text-color: #5b614f; .discussion-vote-up { margin-bottom: 5px; - background-position: -50px -3px; + background-position: -50px -3px; &:hover { background-position: -50px -5px; @@ -612,7 +750,7 @@ $tag-text-color: #5b614f; color: #1C71DD; @include transition-duration(0); } - } + } .discussion-vote-count { @include discussion-font; @@ -625,12 +763,12 @@ $tag-text-color: #5b614f; color: #9a9a9a; } } - - + + /*** new post ***/ - + .new-post-form, .discussion-thread-edit { - + .title-input, .body-input { display: block !important; font: inherit; @@ -646,11 +784,11 @@ $tag-text-color: #5b614f; margin-top: 1%; padding: 1% 1.5%; } - + .hide-similar-posts { float: right; } - + .new-post-similar-posts { font: inherit; .similar-post { @@ -690,7 +828,7 @@ $tag-text-color: #5b614f; .discussion-content-edit, .discussion-reply-new, .new-post-form { margin: 10px 0 10px 0; - + .discussion-errors { color: #8F0E0E; display: block; @@ -700,7 +838,7 @@ $tag-text-color: #5b614f; margin-left: -3%; padding-left: 2em; } - + a:hover { color: #1C71DD; text-decoration: none; @@ -757,7 +895,7 @@ $tag-text-color: #5b614f; .discussion-cancel-post { margin-right: 1.5%; - } + } } .reply-post-control { @@ -766,7 +904,7 @@ $tag-text-color: #5b614f; margin-right: 1.5%; } } - + .edit-post-control { margin-top: 1%; @@ -786,7 +924,7 @@ $tag-text-color: #5b614f; font-weight: bold; text-decoration: none; width: inherit; - + &:hover { color: white; } @@ -810,7 +948,7 @@ $tag-text-color: #5b614f; } .discussion-reply-new { - + .discussion-auto-watch { margin-left: 2%; } @@ -900,7 +1038,7 @@ $tag-text-color: #5b614f; .wmd-button-bar { width: 100%; - background-color: Silver; + background-color: Silver; } .wmd-input { @@ -947,25 +1085,25 @@ $tag-text-color: #5b614f; } .wmd-button-row { - position: relative; + position: relative; margin-left: 5px; margin-right: 5px; margin-bottom: 5px; margin-top: 10px; - padding: 0px; + padding: 0px; height: 20px; overflow: hidden; @include transition(all, .2s, easeOut); } .wmd-spacer { - width: 1px; - height: 20px; + width: 1px; + height: 20px; margin-left: 14px; - + position: absolute; background-color: Silver; - display: inline-block; + display: inline-block; list-style: none; } diff --git a/lms/templates/discussion/index.html b/lms/templates/discussion/index.html index 1160a14d90..9721a20957 100644 --- a/lms/templates/discussion/index.html +++ b/lms/templates/discussion/index.html @@ -15,11 +15,38 @@ <%include file="../courseware/course_navigation.html" args="active_page='discussion'" /> + +
+ + +
+
From 5d67e01f1c9cb22660f35cbc98481a73a23d42b0 Mon Sep 17 00:00:00 2001 From: Matthew Mongeau Date: Mon, 27 Aug 2012 16:41:52 -0400 Subject: [PATCH 002/364] Style fixes --- lms/static/sass/_discussion.scss | 256 ++++++++++++++++--------------- 1 file changed, 130 insertions(+), 126 deletions(-) diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index b91603a3e6..7d0ccc354e 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -1,133 +1,136 @@ -.discussion-wrapper { - display: table; - table-layout: fixed; - width: 100%; - height: 500px; - background: #fff; - border-radius: 3px; - border: 1px solid #aaa; - box-shadow: 0 1px 2px rgba(0, 0, 0, 0.05); - ul { - list-style: none; - margin: 0; - padding: 0; - border: 0; - outline: 0; - font-size: 100%; - font: inherit; - vertical-align: baseline; - } -} - -.discussion-sidebar { - display: table-cell; - vertical-align: top; - width: 27.7%; - background: #f6f6f6; - border-radius: 3px 0 0 3px; - border-right: 3px solid #bcbcbc; -} - -.board-drop-btn { - display: block; - height: 60px; - border-bottom: 1px solid #a3a3a3; - border-radius: 3px 0 0 0; - background: -webkit-linear-gradient(top, #ebebeb, #d9d9d9); - font-size: 16px; - font-weight: 700; - line-height: 58px; - text-align: center; - color: #333; - text-shadow: 0 1px 0 rgba(255, 255, 255, .8); -} - -.sort-bar { - height: 27px; - border-bottom: 1px solid #a3a3a3; - background: -webkit-linear-gradient(top, #cdcdcd, #b6b6b6); - box-shadow: 0 1px 0 rgba(255, 255, 255, .4) inset; - - a { - display: block; - float: right; - height: 27px; - margin-right: 10px; - font-size: 11px; - font-weight: bold; - line-height: 23px; - color: #333; - text-shadow: 0 1px 0 rgba(255, 255, 255, .5); - - .sort-label { - font-size: 9px; - text-transform: uppercase; - } - } -} -.post-list { - a { - display: block; - height: 36px; - padding: 0 10px; - border-bottom: 1px solid #ddd; +.container { + .discussion-wrapper { + display: table; + table-layout: fixed; + width: 100%; + height: 500px; background: #fff; - font-size: 13px; - font-weight: 700; - line-height: 34px; - color: #333; - - &.read .title { - font-weight: 400; - color: #737373; - } - } - - .title { - display: block; - float: left; - width: 70%; - white-space: nowrap; - text-overflow: ellipsis; - overflow: hidden; - } - - .votes, - .comments { - display: block; - float: right; - width: 32px; - height: 16px; - margin-top: 9px; - border-radius: 2px; - background: -webkit-linear-gradient(top, #d4d4d4, #dfdfdf); - font-size: 9px; - font-weight: 700; - line-height: 16px; - text-align: center; - color: #767676; - } - - .comments { - position: relative; - margin-left: 4px; - - &:after { - content: '◥'; - display: block; - position: absolute; - top: 11px; - right: 3px; - font-size: 6px; - color: #dfdfdf; + border-radius: 3px; + border: 1px solid #aaa; + box-shadow: 0 1px 2px rgba(0, 0, 0, 0.05); + ul { + list-style: none; + margin: 0; + padding: 0; + border: 0; + outline: 0; + font-size: 100%; + font: inherit; + vertical-align: baseline; } - &.new { - background: -webkit-linear-gradient(top, #84d7fe, #99e0fe); - color: #333; + .discussion-sidebar { - &:after { - color: #99e0fe; + display: table-cell; + vertical-align: top; + width: 27.7%; + background: #f6f6f6; + border-radius: 3px 0 0 3px; + border-right: 3px solid #bcbcbc; + + .sort-bar { + height: 27px; + border-bottom: 1px solid #a3a3a3; + background: -webkit-linear-gradient(top, #cdcdcd, #b6b6b6); + box-shadow: 0 1px 0 rgba(255, 255, 255, .4) inset; + + a { + display: block; + float: right; + height: 27px; + margin-right: 10px; + font-size: 11px; + font-weight: bold; + line-height: 23px; + color: #333; + text-shadow: 0 1px 0 rgba(255, 255, 255, .5); + + .sort-label { + font-size: 9px; + text-transform: uppercase; + } + } + } + + .board-drop-btn { + display: block; + height: 60px; + border-bottom: 1px solid #a3a3a3; + border-radius: 3px 0 0 0; + background: -webkit-linear-gradient(top, #ebebeb, #d9d9d9); + font-size: 16px; + font-weight: 700; + line-height: 58px; + text-align: center; + color: #333 !important; + text-shadow: 0 1px 0 rgba(255, 255, 255, .8); + } + } + .post-list { + a { + display: block; + height: 36px; + padding: 0 10px; + border-bottom: 1px solid #ddd; + background: #fff; + font-size: 13px; + font-weight: 700; + line-height: 34px; + color: #333; + + &.read .title { + font-weight: 400; + color: #737373; + } + } + + .title { + display: block; + float: left; + width: 70%; + white-space: nowrap; + text-overflow: ellipsis; + overflow: hidden; + } + + .votes, + .comments { + display: block; + float: right; + width: 32px; + height: 16px; + margin-top: 9px; + border-radius: 2px; + background: -webkit-linear-gradient(top, #d4d4d4, #dfdfdf); + font-size: 9px; + font-weight: 700; + line-height: 16px; + text-align: center; + color: #767676; + } + + .comments { + position: relative; + margin-left: 4px; + + &:after { + content: '◥'; + display: block; + position: absolute; + top: 11px; + right: 3px; + font-size: 6px; + color: #dfdfdf; + } + + &.new { + background: -webkit-linear-gradient(top, #84d7fe, #99e0fe); + color: #333; + + &:after { + color: #99e0fe; + } + } } } } @@ -135,6 +138,7 @@ + /*** OLD STUFF ***/ /*** Variables ***/ From 82c9d045cd163c2c35d85f2c4ddb58d364df9027 Mon Sep 17 00:00:00 2001 From: Matthew Mongeau Date: Mon, 27 Aug 2012 17:24:05 -0400 Subject: [PATCH 003/364] Initial work on single thread view. --- .../django_comment_client/forum/views.py | 4 +++ lms/static/sass/_discussion.scss | 22 +++++++++++++++ lms/templates/discussion/_single_thread.html | 4 ++- lms/templates/discussion/index.html | 5 ++-- lms/templates/discussion/single_thread.html | 27 +++++++++++++++++++ 5 files changed, 59 insertions(+), 3 deletions(-) diff --git a/lms/djangoapps/django_comment_client/forum/views.py b/lms/djangoapps/django_comment_client/forum/views.py index 4cb1acdb2b..48f130f107 100644 --- a/lms/djangoapps/django_comment_client/forum/views.py +++ b/lms/djangoapps/django_comment_client/forum/views.py @@ -176,6 +176,7 @@ def forum_form_discussion(request, course_id): def render_single_thread(request, discussion_id, course_id, thread_id): thread = cc.Thread.find(thread_id).retrieve(recursive=True).to_dict() + threads, query_params = get_threads(request, course_id) user_info = cc.User.from_django_user(request.user).to_dict() @@ -188,6 +189,7 @@ def render_single_thread(request, discussion_id, course_id, thread_id): 'course_id': course_id, 'request': request, 'discussion_data': json.dumps({ discussion_id: [utils.safe_content(thread)] }), + 'threads': threads, } return render_to_string('discussion/_single_thread.html', context) @@ -209,6 +211,7 @@ def single_thread(request, course_id, discussion_id, thread_id): else: course = get_course_with_access(request.user, course_id, 'load') + threads, query_params = get_threads(request, course_id) recent_active_threads = cc.search_recent_active_threads( course_id, @@ -229,6 +232,7 @@ def single_thread(request, course_id, discussion_id, thread_id): 'recent_active_threads': recent_active_threads, 'trending_tags': trending_tags, 'course_id': course.id, + 'threads': threads, } return render_to_response('discussion/single_thread.html', context) diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index 7d0ccc354e..aff05d21a1 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -19,6 +19,28 @@ vertical-align: baseline; } + .discussion { + display: table-cell; + vertical-align: top; + width: 72.3%; + padding: 40px; + + h1 { + font-size: 28px; + font-weight: 700; + } + + .posted-details { + font-size: 12px; + font-style: italic; + color: #737373; + } + + p + p { + margin-top: 20px; + } + } + .discussion-sidebar { display: table-cell; diff --git a/lms/templates/discussion/_single_thread.html b/lms/templates/discussion/_single_thread.html index bfbf7b069e..ccf106a6df 100644 --- a/lms/templates/discussion/_single_thread.html +++ b/lms/templates/discussion/_single_thread.html @@ -1,10 +1,12 @@ <%namespace name="renderer" file="_content_renderer.html"/>
- Discussion + ${thread['title'] | h} +

sometime by Foo

${renderer.render_content_with_comments(thread)}
<%include file="_js_data.html" /> + diff --git a/lms/templates/discussion/index.html b/lms/templates/discussion/index.html index 9721a20957..948fa8dd9d 100644 --- a/lms/templates/discussion/index.html +++ b/lms/templates/discussion/index.html @@ -1,3 +1,4 @@ +<%! import django_comment_client.helpers as helpers %> <%inherit file="../main.html" /> <%namespace name='static' file='../static_content.html'/> <%block name="bodyclass">discussion @@ -30,13 +31,13 @@
- Oh + This page intentionally left blank
diff --git a/lms/templates/discussion/single_thread.html b/lms/templates/discussion/single_thread.html index 3c46b337b3..1e05475762 100644 --- a/lms/templates/discussion/single_thread.html +++ b/lms/templates/discussion/single_thread.html @@ -1,3 +1,4 @@ +<%! import django_comment_client.helpers as helpers %> <%inherit file="../main.html" /> <%namespace name='static' file='../static_content.html'/> <%block name="bodyclass">discussion @@ -15,6 +16,32 @@ <%include file="../courseware/course_navigation.html" args="active_page='discussion'" /> +
+
+ +
+ ${content.decode('utf-8')} +
+
+ +
+
From e1113d9ca9afc9384dfe1ce6ca4d5017ecaf4c80 Mon Sep 17 00:00:00 2001 From: Matthew Mongeau Date: Tue, 28 Aug 2012 11:31:27 -0400 Subject: [PATCH 004/364] Get voting hooked up --- :w | 453 ++++++ .../django_comment_client/forum/views.py | 10 + .../coffee/src/discussion/content.coffee | 11 +- lms/static/coffee/src/discussion/main.coffee | 88 +- lms/static/images/endorse-icon.png | Bin 0 -> 1448 bytes lms/static/images/follow-dog-ear.png | Bin 0 -> 4246 bytes lms/static/images/following-flag.png | Bin 0 -> 1217 bytes lms/static/images/moderator-delete-icon.png | Bin 0 -> 1077 bytes lms/static/images/moderator-edit-icon.png | Bin 0 -> 1027 bytes lms/static/images/new-post-icon.png | Bin 0 -> 1168 bytes lms/static/sass/_discussion.scss | 1447 +++++------------ lms/templates/discussion/_single_thread.html | 33 +- lms/templates/discussion/single_thread.html | 60 +- 13 files changed, 967 insertions(+), 1135 deletions(-) create mode 100644 :w create mode 100644 lms/static/images/endorse-icon.png create mode 100644 lms/static/images/follow-dog-ear.png create mode 100644 lms/static/images/following-flag.png create mode 100644 lms/static/images/moderator-delete-icon.png create mode 100644 lms/static/images/moderator-edit-icon.png create mode 100644 lms/static/images/new-post-icon.png diff --git a/:w b/:w new file mode 100644 index 0000000000..f433df211c --- /dev/null +++ b/:w @@ -0,0 +1,453 @@ +if Backbone? + class @Content extends Backbone.Model + + template: -> DiscussionUtil.getTemplate('_content') + + actions: + editable: '.admin-edit' + can_reply: '.discussion-reply' + can_endorse: '.admin-endorse' + can_delete: '.admin-delete' + can_openclose: '.admin-openclose' + + urlMappers: {} + + urlFor: (name) -> + @urlMappers[name].apply(@) + + can: (action) -> + DiscussionUtil.getContentInfo @id, action + + updateInfo: (info) -> + @set('ability', info.ability) + @set('voted', info.voted) + @set('subscribed', info.subscribed) + + addComment: (comment, options) -> + options ||= {} + if not options.silent + thread = @get('thread') + comments_count = parseInt(thread.get('comments_count')) + thread.set('comments_count', comments_count + 1) + @get('children').push comment + model = new Comment $.extend {}, comment, { thread: @get('thread') } + @get('comments').add model + model + + removeComment: (comment) -> + thread = @get('thread') + comments_count = parseInt(thread.get('comments_count')) + thread.set('comments_count', comments_count - 1 - comment.getCommentsCount()) + + resetComments: (children) -> + @set 'children', [] + @set 'comments', new Comments() + for comment in (children || []) + @addComment comment, { silent: true } + + initialize: -> + DiscussionUtil.addContent @id, @ + @resetComments(@get('children')) + + + class @ContentView extends Backbone.View + + $: (selector) -> + @$local.find(selector) + + partial: + endorsed: (endorsed) -> + if endorsed + @$el.addClass("endorsed") + else + @$el.removeClass("endorsed") + + closed: (closed) -> # we should just re-render the whole thread, or update according to new abilities + if closed + @$el.addClass("closed") + @$(".admin-openclose").text "Re-open Thread" + else + @$el.removeClass("closed") + @$(".admin-openclose").text "Close Thread" + + voted: (voted) -> + @$(".discussion-vote-up").removeClass("voted") if voted != "up" + @$(".discussion-vote-down").removeClass("voted") if voted != "down" + @$(".discussion-vote-#{voted}").addClass("voted") if voted in ["up", "down"] + + votes_point: (votes_point) -> + @$(".discussion-votes-point").html(votes_point) + + comments_count: (comments_count) -> + @$(".comments-count").html(comments_count) + + subscribed: (subscribed) -> + if subscribed + @$(".discussion-follow-thread").addClass("discussion-unfollow-thread").html("Unfollow") + else + @$(".discussion-follow-thread").removeClass("discussion-unfollow-thread").html("Follow") + + ability: (ability) -> + for action, elemSelector of @model.actions + if not ability[action] + @$(elemSelector).parent().hide() + else + @$(elemSelector).parent().show() + + $discussionContent: -> + @_discussionContent ||= @$el.children(".discussion-content") + + $showComments: -> + @_showComments ||= @$(".discussion-show-comments") + + updateShowComments: -> + if @showed + @$showComments().html @$showComments().html().replace "Show", "Hide" + else + @$showComments().html @$showComments().html().replace "Hide", "Show" + + retrieved: -> + @$showComments().hasClass("retrieved") + + hideSingleThread: (event) -> + @$el.children(".comments").hide() + @showed = false + @updateShowComments() + + showSingleThread: (event) -> + if @retrieved() + @$el.children(".comments").show() + @showed = true + @updateShowComments() + else + $elem = $.merge @$(".thread-title"), @$showComments() + url = @model.urlFor('retrieve') + DiscussionUtil.safeAjax + $elem: $elem + $loading: @$(".discussion-show-comments") + type: "GET" + url: url + success: (response, textStatus) => + @showed = true + @updateShowComments() + @$showComments().addClass("retrieved") + @$el.children(".comments").replaceWith response.html + @model.resetComments response.content.children + @initCommentViews() + DiscussionUtil.bulkUpdateContentInfo response.annotated_content_info + + toggleSingleThread: (event) -> + if @showed + @hideSingleThread(event) + else + @showSingleThread(event) + + initCommentViews: -> + @$el.children(".comments").children(".comment").each (index, elem) => + model = @model.get('comments').find $(elem).attr("_id") + if not model.view + commentView = new CommentView el: elem, model: model + + reply: -> + if @model.get('type') == 'thread' + @showSingleThread() + $replyView = @$(".discussion-reply-new") + if $replyView.length + $replyView.show() + else + view = {} + view.id = @model.id + view.showWatchCheckbox = not @model.get('thread').get('subscribed') + html = Mustache.render DiscussionUtil.getTemplate('_reply'), view + @$discussionContent().append html + DiscussionUtil.makeWmdEditor @$el, $.proxy(@$, @), "reply-body" + @$(".discussion-submit-post").click $.proxy(@submitReply, @) + @$(".discussion-cancel-post").click $.proxy(@cancelReply, @) + @$(".discussion-reply").hide() + @$(".discussion-edit").hide() + + submitReply: (event) -> + url = @model.urlFor('reply') + + body = DiscussionUtil.getWmdContent @$el, $.proxy(@$, @), "reply-body" + + anonymous = false || @$(".discussion-post-anonymously").is(":checked") + autowatch = false || @$(".discussion-auto-watch").is(":checked") + + DiscussionUtil.safeAjax + $elem: $(event.target) + $loading: $(event.target) if event + url: url + type: "POST" + dataType: 'json' + data: + body: body + anonymous: anonymous + auto_subscribe: autowatch + error: DiscussionUtil.formErrorHandler @$(".discussion-errors") + success: (response, textStatus) => + DiscussionUtil.clearFormErrors @$(".discussion-errors") + $comment = $(response.html) + @$el.children(".comments").prepend $comment + DiscussionUtil.setWmdContent @$el, $.proxy(@$, @), "reply-body", "" + comment = @model.addComment response.content + commentView = new CommentView el: $comment[0], model: comment + comment.updateInfo response.annotated_content_info + if autowatch + @model.get('thread').set('subscribed', true) + @cancelReply() + + cancelReply: -> + $replyView = @$(".discussion-reply-new") + if $replyView.length + $replyView.hide() + @$(".discussion-reply").show() + @$(".discussion-edit").show() + + unvote: (event) -> + url = @model.urlFor('unvote') + $elem = @$(".discussion-vote") + DiscussionUtil.safeAjax + $elem: $elem + url: url + type: "POST" + success: (response, textStatus) => + @model.set('voted', '') + @model.set('votes_point', response.votes.point) + + vote: (event, value) -> + url = @model.urlFor("#{value}vote") + $elem = @$(".discussion-vote") + DiscussionUtil.safeAjax + $elem: $elem + url: url + type: "POST" + success: (response, textStatus) => + @model.set('voted', value) + @model.set('votes_point', response.votes.point) + + toggleVote: (event) -> + console.log("HERE") + $elem = $(event.target) + value = $elem.attr("value") + $elem.toggleClass("is-cast") + return false + # if @model.get("voted") == value + # @unvote(event) + # else + # @vote(event, value) + + toggleEndorse: (event) -> + $elem = $(event.target) + url = @model.urlFor('endorse') + endorsed = @model.get('endorsed') + data = { endorsed: not endorsed } + DiscussionUtil.safeAjax + $elem: $elem + url: url + data: data + type: "POST" + success: (response, textStatus) => + @model.set('endorsed', not endorsed) + + toggleFollow: (event) -> + $elem = $(event.target) + subscribed = @model.get('subscribed') + if subscribed + url = @model.urlFor('unfollow') + else + url = @model.urlFor('follow') + DiscussionUtil.safeAjax + $elem: $elem + url: url + type: "POST" + success: (response, textStatus) => + @model.set('subscribed', not subscribed) + + toggleClosed: (event) -> + $elem = $(event.target) + url = @model.urlFor('close') + closed = @model.get('closed') + data = { closed: not closed } + DiscussionUtil.safeAjax + $elem: $elem + url: url + type: "POST" + data: data + success: (response, textStatus) => + @model.set('closed', not closed) + @model.set('ability', response.ability) + + edit: (event) -> + @$(".discussion-content-wrapper").hide() + $editView = @$(".discussion-content-edit") + if $editView.length + $editView.show() + else + view = {} + view.id = @model.id + if @model.get('type') == 'thread' + view.title = @model.get('title') + view.body = @model.get('body') + view.tags = @model.get('tags') + else + view.body = @model.get('body') + @$discussionContent().append Mustache.render DiscussionUtil.getTemplate("_edit_#{@model.get('type')}"), view + DiscussionUtil.makeWmdEditor @$el, $.proxy(@$, @), "#{@model.get('type')}-body-edit" + @$(".thread-tags-edit").tagsInput DiscussionUtil.tagsInputOptions() + @$(".discussion-submit-update").unbind("click").click $.proxy(@submitEdit, @) + @$(".discussion-cancel-update").unbind("click").click $.proxy(@cancelEdit, @) + + submitEdit: (event) -> + + url = @model.urlFor('update') + data = {} + if @model.get('type') == 'thread' + data.title = @$(".thread-title-edit").val() + data.body = DiscussionUtil.getWmdContent @$el, $.proxy(@$, @), "thread-body-edit" + data.tags = @$(".thread-tags-edit").val() + else + data.body = DiscussionUtil.getWmdContent @$el, $.proxy(@$, @), "comment-body-edit" + DiscussionUtil.safeAjax + $elem: $(event.target) + $loading: $(event.target) if event + url: url + type: "POST" + dataType: 'json' + data: data + error: DiscussionUtil.formErrorHandler @$(".discussion-update-errors") + success: (response, textStatus) => + DiscussionUtil.clearFormErrors @$(".discussion-update-errors") + @$discussionContent().replaceWith(response.html) + if @model.get('type') == 'thread' + @model = new Thread response.content + else + @model = new Comment $.extend {}, response.content, { thread: @model.get('thread') } + @reconstruct() + @model.updateInfo response.annotated_content_info, { forceUpdate: true } + + cancelEdit: (event) -> + @$(".discussion-content-edit").hide() + @$(".discussion-content-wrapper").show() + + delete: (event) -> + url = @model.urlFor('delete') + if @model.get('type') == 'thread' + c = confirm "Are you sure to delete thread \"#{@model.get('title')}\"?" + else + c = confirm "Are you sure to delete this comment? " + if not c + return + $elem = $(event.target) + DiscussionUtil.safeAjax + $elem: $elem + url: url + type: "POST" + success: (response, textStatus) => + @$el.remove() + if @model.get('type') == 'comment' + @model.get('thread').removeComment(@model) + + events: + "click .discussion-follow-thread": "toggleFollow" + "click .thread-title": "toggleSingleThread" + "click .discussion-show-comments": "toggleSingleThread" + "click .discussion-reply-thread": "reply" + "click .discussion-reply-comment": "reply" + "click .discussion-cancel-reply": "cancelReply" + "click .discussion-vote-up": "toggleVote" + "click .discussion-vote-down": "toggleVote" + "click .admin-endorse": "toggleEndorse" + "click .admin-openclose": "toggleClosed" + "click .admin-edit": "edit" + "click .admin-delete": "delete" + + initLocal: -> + @$local = @$el.children(".local") + @$delegateElement = @$local + + initTitle: -> + $contentTitle = @$(".thread-title") + if $contentTitle.length + $contentTitle.html DiscussionUtil.unescapeHighlightTag DiscussionUtil.stripLatexHighlight $contentTitle.html() + + initBody: -> + $contentBody = @$(".content-body") + $contentBody.html DiscussionUtil.postMathJaxProcessor DiscussionUtil.markdownWithHighlight $contentBody.html() + MathJax.Hub.Queue ["Typeset", MathJax.Hub, $contentBody.attr("id")] + + initTimeago: -> + @$("span.timeago").timeago() + + renderPartial: -> + for attr, value of @model.changedAttributes() + if @partial[attr] + @partial[attr].apply(@, [value]) + + initBindings: -> + @model.view = @ + @model.bind('change', @renderPartial, @) + + initialize: -> + @initBindings() + @initLocal() + @initTimeago() + @initTitle() + @initBody() + @initCommentViews() + + reconstruct: -> + @initBindings() + @initLocal() + @initTimeago() + @initTitle() + @initBody() + @delegateEvents() + + class @Thread extends @Content + urlMappers: + 'retrieve' : -> DiscussionUtil.urlFor('retrieve_single_thread', @discussion.id, @id) + 'reply' : -> DiscussionUtil.urlFor('create_comment', @id) + 'unvote' : -> DiscussionUtil.urlFor("undo_vote_for_#{@get('type')}", @id) + 'upvote' : -> DiscussionUtil.urlFor("upvote_#{@get('type')}", @id) + 'downvote' : -> DiscussionUtil.urlFor("downvote_#{@get('type')}", @id) + 'close' : -> DiscussionUtil.urlFor('openclose_thread', @id) + 'update' : -> DiscussionUtil.urlFor('update_thread', @id) + 'delete' : -> DiscussionUtil.urlFor('delete_thread', @id) + 'follow' : -> DiscussionUtil.urlFor('follow_thread', @id) + 'unfollow' : -> DiscussionUtil.urlFor('unfollow_thread', @id) + + initialize: -> + @set('thread', @) + super() + + class @ThreadView extends @ContentView + + class @Comment extends @Content + urlMappers: + 'reply': -> DiscussionUtil.urlFor('create_sub_comment', @id) + 'unvote': -> DiscussionUtil.urlFor("undo_vote_for_#{@get('type')}", @id) + 'upvote': -> DiscussionUtil.urlFor("upvote_#{@get('type')}", @id) + 'downvote': -> DiscussionUtil.urlFor("downvote_#{@get('type')}", @id) + 'endorse': -> DiscussionUtil.urlFor('endorse_comment', @id) + 'update': -> DiscussionUtil.urlFor('update_comment', @id) + 'delete': -> DiscussionUtil.urlFor('delete_comment', @id) + + getCommentsCount: -> + count = 0 + @get('comments').each (comment) -> + count += comment.getCommentsCount() + 1 + count + + class @CommentView extends @ContentView + + class @Comments extends Backbone.Collection + + model: Comment + + initialize: -> + @bind "add", (item) => + item.collection = @ + + find: (id) -> + _.first @where(id: id) diff --git a/lms/djangoapps/django_comment_client/forum/views.py b/lms/djangoapps/django_comment_client/forum/views.py index 48f130f107..ed09f1cfdb 100644 --- a/lms/djangoapps/django_comment_client/forum/views.py +++ b/lms/djangoapps/django_comment_client/forum/views.py @@ -182,6 +182,7 @@ def render_single_thread(request, discussion_id, course_id, thread_id): annotated_content_info = utils.get_annotated_content_infos(course_id, thread=thread, user=request.user, user_info=user_info) + log.debug(annotated_content_info) context = { 'discussion_id': discussion_id, 'thread': thread, @@ -191,6 +192,7 @@ def render_single_thread(request, discussion_id, course_id, thread_id): 'discussion_data': json.dumps({ discussion_id: [utils.safe_content(thread)] }), 'threads': threads, } + return render_to_string('discussion/_single_thread.html', context) def single_thread(request, course_id, discussion_id, thread_id): @@ -223,10 +225,18 @@ def single_thread(request, course_id, discussion_id, thread_id): course_id, ) + + user_info = cc.User.from_django_user(request.user).to_dict() + thread = cc.Thread.find(thread_id).retrieve(recursive=True) + annotated_content_info = utils.get_annotated_content_infos(course_id, thread=thread, user=request.user, user_info=user_info) + + context = { 'discussion_id': discussion_id, 'csrf': csrf(request)['csrf_token'], 'init': '', + 'thread': json.dumps(utils.safe_content(thread)), + 'annotated_content_info': json.dumps(annotated_content_info), 'content': render_single_thread(request, discussion_id, course_id, thread_id), 'course': course, 'recent_active_threads': recent_active_threads, diff --git a/lms/static/coffee/src/discussion/content.coffee b/lms/static/coffee/src/discussion/content.coffee index 73c3688c2a..f433df211c 100644 --- a/lms/static/coffee/src/discussion/content.coffee +++ b/lms/static/coffee/src/discussion/content.coffee @@ -227,12 +227,15 @@ if Backbone? @model.set('votes_point', response.votes.point) toggleVote: (event) -> + console.log("HERE") $elem = $(event.target) value = $elem.attr("value") - if @model.get("voted") == value - @unvote(event) - else - @vote(event, value) + $elem.toggleClass("is-cast") + return false + # if @model.get("voted") == value + # @unvote(event) + # else + # @vote(event, value) toggleEndorse: (event) -> $elem = $(event.target) diff --git a/lms/static/coffee/src/discussion/main.coffee b/lms/static/coffee/src/discussion/main.coffee index 023345c5da..783ab9a3d5 100644 --- a/lms/static/coffee/src/discussion/main.coffee +++ b/lms/static/coffee/src/discussion/main.coffee @@ -1,21 +1,81 @@ -$ -> +class @DiscussionUser + constructor: (content_info) -> + @content_info = content_info + following: (thread) -> + @content_info[thread.id]['subscribed'] == true + + voted: (thread) -> + @content_info[thread.id]['voted'] == 'up' + +class @DiscussionThreadView extends Backbone.View + events: + "click .discussion-vote-up": "toggleVote" + "click .dogear": "toggleFollowing" + initialize: (options) -> + @user = options['user'] + @model.bind "change", @updateModelDetails + + updateModelDetails: => + @$(".votes-count-number").html(@model.get("votes")["up_count"]) + + render: -> + if @user.following(@model) + @$(".dogear").addClass("is-followed") + + if @user.voted(@model) + @$(".vote-btn").addClass("is-cast") + + toggleVote: -> + @$(".vote-btn").toggleClass("is-cast") + if @$(".vote-btn").hasClass("is-cast") + @vote() + else + @unvote() + + toggleFollowing: -> + @$(".dogear").toggleClass("is-followed") + + vote: -> + url = @model.urlFor("upvote") + @$(".votes-count-number").html(parseInt(@$(".votes-count-number").html()) + 1) + DiscussionUtil.safeAjax + $elem: @$(".discussion-vote") + url: url + type: "POST" + success: (response, textStatus) => + if textStatus == 'success' + @model.set(response) + + unvote: -> + url = @model.urlFor("unvote") + @$(".votes-count-number").html(parseInt(@$(".votes-count-number").html()) - 1) + DiscussionUtil.safeAjax + $elem: @$(".discussion-vote") + url: url + type: "POST" + success: (response, textStatus) => + if textStatus == 'success' + @model.set(response) + +$ -> window.$$contents = {} window.$$discussions = {} - $(".discussion-module").each (index, elem) -> - view = new DiscussionModuleView(el: elem) + # $(".discussion-module").each (index, elem) -> + # view = new DiscussionModuleView(el: elem) - $("section.discussion").each (index, elem) -> - discussionData = DiscussionUtil.getDiscussionData($(elem).attr("_id")) - discussion = new Discussion() - discussion.reset(discussionData, {silent: false}) - view = new DiscussionView(el: elem, model: discussion) + # $("section.discussion").each (index, elem) -> + # discussionData = DiscussionUtil.getDiscussionData($(elem).attr("_id")) + # discussion = new Discussion() + # discussion.reset(discussionData, {silent: false}) + # view = new DiscussionView(el: elem, model: discussion) - if window.$$annotated_content_info? - DiscussionUtil.bulkUpdateContentInfo(window.$$annotated_content_info) + # if window.$$annotated_content_info? + # DiscussionUtil.bulkUpdateContentInfo(window.$$annotated_content_info) + + # $userProfile = $(".discussion-sidebar>.user-profile") + # if $userProfile.length + # console.log "initialize user profile" + # view = new DiscussionUserProfileView(el: $userProfile[0]) - $userProfile = $(".discussion-sidebar>.user-profile") - if $userProfile.length - console.log "initialize user profile" - view = new DiscussionUserProfileView(el: $userProfile[0]) diff --git a/lms/static/images/endorse-icon.png b/lms/static/images/endorse-icon.png new file mode 100644 index 0000000000000000000000000000000000000000..4dc5c6e204c8b80b9721a698ad0a4b3bf6b48a3e GIT binary patch literal 1448 zcmeAS@N?(olHy`uVBq!ia0vp@KrF$*1|$_fl!pK*$r9IylHmNblJdl&R0hYC{G?O` z&)mfH)S%SFl*+=BsWuD@%qp275hW46K32*3xq68pHF_1f1wh>l3^w)^1&PVosU-?Y zsp*+{wo31J?^jaDOtDo8H}y5}EpSfF$n>ZxN)4{^3rViZPPR-@vbR&PsjvbXkegbP zs8ErclUHn2VXFi-*9yo63F|81#=KlDb#X~hD#E>34K5C;EJ)Q4 zN-fSWElLJPT$(b-ssbzLqSVBa{GyQj{2W*)24v)y-fM)1rW~Nv<8#pYY1xM#k^0+WPAL{`$ZQ(}N}+ z9v&NvfS~5zpP7s+4BJ>e9fc>{V%+ji!i-lTAua9OiGv3pvffZz&?F})IPuYYpuV5K zzOJ?oh!crzUball!&!QQ<>a4_kM~bpv}n;@CnqN!8ylM(`?^0I&mTPKII@)SNcx|j zpO?R$XIm|1U-KhCMup*v2D68u9&duL!*j#Ge}8YUdVX&1O@m&8247|$;f`Y$RxDlm z^~AkW4JM9;m*?BpXKl;7`|HtxMrQuTKPD=cB0X~cJ`VPwMuvua**2v=?6S|9 z$j!yL=VZ&o8C%p>q`yCZ;)DF0Z}(!YTrA#lzP$Ofn8SO0n)u|jzeTU_tg^5F|H!}E zfcMWWu{AtBK0Nku_K81=K9}$aPZFNhaDyw7c{zs@Gslr%l{Qtib@D228AZPoXlIE3 z|NY_D>F@pP?>0WvI;E+#d6xfWnRSXsoPGxuZxOb*C&5~pt6Vwd%k;w2s|^4A|2+HQ z<*Ul^5;Jbz6g2z8o^_!yn?drxpKlL!PyUXVyd$^g*MY+)j+{B5r*-(4qTX?y&5Boq zLYZye{{8oPyH)wQZEu>xNjmomm>MAmdKI;Vst0A`dTRsaA1 literal 0 HcmV?d00001 diff --git a/lms/static/images/follow-dog-ear.png b/lms/static/images/follow-dog-ear.png new file mode 100644 index 0000000000000000000000000000000000000000..af3bb4544ace2b65e6d50f0e0be6ed1cd83e309f GIT binary patch literal 4246 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 literal 0 HcmV?d00001 diff --git a/lms/static/images/following-flag.png b/lms/static/images/following-flag.png new file mode 100644 index 0000000000000000000000000000000000000000..ac95c4cfeaf20a601e9299bf4067df84d8f6c3bf GIT binary patch literal 1217 zcmeAS@N?(olHy`uVBq!ia0vp^JU}eL!3HGH8OdY;DajJoh?3y^w370~qErUQl>DSr z1<%~X^wgl##FWaylc_cg49qH-ArU1JzCKpT`MG+DAT@dwxdlMo3=B5*6$OdO*{LN8 zNvY|XdA3ULckfqH$V{%1*XSQL?vFu&J;D8jzb> zlBiITo0C^;Rbi_HHrEQs1_|pcDS(xfWZNo192Makpx~Tel&WB=XRMoSU}&gdW~OIo zVrph)sH0$HU}&Uo07PcGh9*{~W>!Y#3Q(W~w5=#5%__*n4QdyVXRDM^Qc_^0uU}qX zu2*iXmtT~wZ)j<02{OaTNEfI=x41H|B(Xv_uUHvof=g;~a#3bMNoIbY0?5R~r2Ntn zTP2`NAzsKWfE$}v3=Jk=fazBx7U&!58GyV5Q|Rl9UukYGTy=3tP%6T`SPd=?sVqp< z4@xc0FD*(2MqHXQ$f^P>=c3falKi5O{QMkPC z!8&|>tvvIJOA_;vQ$1a5m4IgGWoD*WSsEF-nwlCqy0{s*85+78TAG-fS{hrLn7Fwa z8M~S}!}Pl3Czs}?=9R$orXch>;nWLC47mkBn_W_iGRsm^+=}vZ6~Lah%Eav!3!LUb z^`_uzw$978H@ zO_^jJbl8EX?W@6e&#I^$+^Kv5`!BWgy>sHO)thql+5N2_)_DFoU@VoHTdVzY`>Ml7 ze+fMLnB}5q6wAEFRU*~dqph5ySm(Lyb)}M3EbM(#_HZ56kaiMkop}7imwnTvdYexr}0H;SQL9qhuGVam9|}mdD{-F zZn^sUxqtq_K1S~p#hDWo`956KnXf$Ugg~>>&#LNmu1}W;M48N-pb%E!c6pNR6;I|3 ztDgkyXO(JayOPu7WxCCweA7Co{*w5nwE8mdKI;Vst010fO?f?J) literal 0 HcmV?d00001 diff --git a/lms/static/images/moderator-delete-icon.png b/lms/static/images/moderator-delete-icon.png new file mode 100644 index 0000000000000000000000000000000000000000..966ff2f9c236e9ba193632bedfcf10f018a3c087 GIT binary patch literal 1077 zcmaJ=U1-x#6i%5;tyBj(v_8lslVV{_n*L-YtZr?x+JYIQ>$IS-rO90zw)~jf+H5Lp z17#D0u~!*_3^!2(pG5q7nV`=;xraUYut#MGW8j0{Z0qKOHC%GfJ)G}5=iKw%xq<#m z0smP)K@fp_PAuTvvyUEW#s6bZ-kro-5cQSNpgD@_vJHu}YL+3$>v9DapsY^Z_zb%V zqUF3+ETNKgnO97mlD!zp)h&!Bi0&TOl9e%tKp9pvBSrpr^MM4Knj)_zrKn^Hu&U)I zZ8$jDUsNW?6iy|3E`n~C#{@b=GH~^A!{OZ&xx>q2+jG+-*a<;nDRQ@{k~9DW(}o~P z#Uo0TVF1fgOd`p$Oecs%nHU|#i;XY|KFRX2F0l8JIGe4G@&z%wmkXa#WECNcr|EjV zPSxX-X;)~5<2a8a7K`ABh%;dz*^L-ZM}t9xj$&&T(o6$*jB?qmp%jTL-EBd)_Gt}g z@0#$1(XMRK3>EcSY6MEs|3h_sKiWYBcu?;@iJjtv1?d8G%$lv>!Hsr!sVrWwp^Qws zXqw}VTO6pG$aJcv1%yEsT##f%GdxFl2O&v(-f)m?C@?RkNX$WLn#v2&Ou8!(%ZS-1 z$1r^im*`4zaW0X_W@GU_R%l>FQ>p3DKn<*VfEAizJu&DO&MZP(y9w2-ZR%jBXCEXND<6>xUw117d;lldy%zfeF!@l&Pf%R@wY{%2F$p|+nw z`!AvWsc-Yv%G~d?|53}!j)iZ5-2Lm*+nt~Mp_L)F{_oXfdRg R`AWch$oam0@kM52<`1!;RaF20 literal 0 HcmV?d00001 diff --git a/lms/static/images/moderator-edit-icon.png b/lms/static/images/moderator-edit-icon.png new file mode 100644 index 0000000000000000000000000000000000000000..7e28eedf42aedd281d50679d71f7a1c75f821438 GIT binary patch literal 1027 zcmaJ=PiWIn7|)y(S2mf7L&pw}Y=*^C~>FoEq7G)0X~1g>r@Lk!Ar$#T;4kC(4#V3}$9MndB>Hw&xQ^qL13 z)@F;w+Om-{>4|YL7RZFahFAxIz2f+CkfxiwGOl8 z`6|N5uOb&@7bGyO>4xQmjw?-srpbB7$GT&{yppB~2V+^LoaLr6Nl{2DDwpE<9G?=C ziBvo#imEEab5gd2Rgh7$p@Umk^9Vb7A~qZb+a;M5=vlX*sd~r;&7x)NI4$C6a!M2h zC8uVN*K&Y0Pu3!xsD&kB*s!(#w7TUY^Anow!6k?G=tGChyGI7Q@xAvsc@(w0k|_qC z%Oea^dEN1;5nSz^qxPT9bZ@Ws_ilFn90wmOyZVPHxE?9bfp4exSNaCFPCXv&z8hQr z9l3Be$KC0Db9?g7!>&y_GCa|>r|&))j+p0XsIPkuCI=dG=iVtBTZ>VB@!|_wRn_gG a$wmjI>|A>ECGx8;e3tp#tnzGXapNz6s6S@_ literal 0 HcmV?d00001 diff --git a/lms/static/images/new-post-icon.png b/lms/static/images/new-post-icon.png new file mode 100644 index 0000000000000000000000000000000000000000..bf16b9da89a995c6910490dab30bc68b066159df GIT binary patch literal 1168 zcmeAS@N?(olHy`uVBq!ia0vp^0zfRt!3HF+tk*dLq$EpRBT9nv(@M${i&7aJQ}UBi z6+Ckj(^G>|6H_V+Po~;1FfglRhD4M^`1)8S=jZArg4F0$^BXQ!4Z zB&DWj=GiK}-@RW+Av48RDcsc8z_-9TH6zobswg$M$}c3jDm&RSMakYy!KT6rXh3di zNuokUZcbjYRfVk**jy_h8zii+qySb@l5ML5aa4qFfP!;=QL2Kep0RGSfuW&-nVFuU ziK&^Hp^k!)fuWJU0T7w#8k$&{npqi{D?ot~(6*wKG^-#NH>h1eo~=?wNlAf~zJ7Um zxn8-kUVc%!zM-Y1CCCgTBVC{h-Qvo;lEez#ykcdT2`;I{$wiq3C7Jno3Lp~`lk!VT zY?Xj6g?J&i0B&qvF*KNf0j6J(SfFpHX8`gNOrftYexnUy@&(kzb(T9Bihb;hUJ8nFkWk z1ncniwerj>E=kNwPW5!LRRWr!mzkLY3`|Eu7dK;L7guK&Lqk_XOA~WbOJhqD6E`;_ zV^=e0m|mCsATTy#-3XckuB&U{zq9cGQCte z+hfteM)t^WXSW{~Q0gd-OItRBcbV3?5TOfQk8eEH&t+|?*yuN7o=Ly$`Rv)tEc+Lo znEw5BjDtkmx^=IGS=OAs5x!^N=G@)c633J{n64MjxhdUnv@WY^mE}$56n%wR%Xka# zhX_9rEeoBj`0wcVzk+Ap{LEuixSSJtjq91)rs?b_Ocozl+R>Z*T>3#=iW`4>KEu_T zurn%W|EM#ZF~2&e$^N|QDS_l11^eVPfnOXglm7g57G8Y+%f|SH_MxX0reFHcIpvU- e=E`@92N-Tl*ZU&*X}u|^jPP{zb6Mw<&;$Sjg_G(4 literal 0 HcmV?d00001 diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index aff05d21a1..01380faa77 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -1,99 +1,148 @@ -.container { - .discussion-wrapper { - display: table; - table-layout: fixed; - width: 100%; - height: 500px; - background: #fff; - border-radius: 3px; - border: 1px solid #aaa; - box-shadow: 0 1px 2px rgba(0, 0, 0, 0.05); - ul { - list-style: none; - margin: 0; - padding: 0; - border: 0; - outline: 0; - font-size: 100%; - font: inherit; - vertical-align: baseline; +@mixin blue-button { + display: block; + height: 33px; + margin: 12px; + padding: 0 15px; + border-radius: 3px; + border: 1px solid #4697c1; + background: -webkit-linear-gradient(top, #6dccf1, #38a8e5); + font-size: 13px; + font-weight: 700; + line-height: 30px; + color: #fff; + text-shadow: 0 1px 0 rgba(0, 0, 0, .4); + box-shadow: 0 1px 0 rgba(255, 255, 255, 0.4) inset, 0 1px 1px rgba(0, 0, 0, .15); + + &:hover { + border-color: #297095; + background: -webkit-linear-gradient(top, #4fbbe4, #2090d0); + } +} + +.discussion-body { + + .vote-btn { + float: right; + display: block; + height: 27px; + padding: 0 8px; + border-radius: 5px; + border: 1px solid #b2b2b2; + background: -webkit-linear-gradient(top, #fff 35%, #ebebeb); + box-shadow: 0 1px 1px rgba(0, 0, 0, .15); + font-size: 12px; + font-weight: 700; + line-height: 25px; + color: #333; + + .plus-icon { + float: left; + margin-right: 6px; + font-size: 18px; + color: #17b429; } - .discussion { - display: table-cell; - vertical-align: top; - width: 72.3%; - padding: 40px; + &.is-cast { + border-color: #379a42; + background: -webkit-linear-gradient(top, #50cc5e, #3db84b); + color: #fff; + text-shadow: 0 1px 0 rgba(0, 0, 0, .3); + box-shadow: 0 1px 0 rgba(255, 255, 255, .4) inset, 0 1px 2px rgba(0, 0, 0, .2); - h1 { - font-size: 28px; - font-weight: 700; - } - - .posted-details { - font-size: 12px; - font-style: italic; - color: #737373; - } - - p + p { - margin-top: 20px; - } - } - - .discussion-sidebar { - - display: table-cell; - vertical-align: top; - width: 27.7%; - background: #f6f6f6; - border-radius: 3px 0 0 3px; - border-right: 3px solid #bcbcbc; - - .sort-bar { - height: 27px; - border-bottom: 1px solid #a3a3a3; - background: -webkit-linear-gradient(top, #cdcdcd, #b6b6b6); - box-shadow: 0 1px 0 rgba(255, 255, 255, .4) inset; - - a { - display: block; - float: right; - height: 27px; - margin-right: 10px; - font-size: 11px; - font-weight: bold; - line-height: 23px; - color: #333; - text-shadow: 0 1px 0 rgba(255, 255, 255, .5); - - .sort-label { - font-size: 9px; - text-transform: uppercase; - } - } - } - - .board-drop-btn { - display: block; - height: 60px; - border-bottom: 1px solid #a3a3a3; - border-radius: 3px 0 0 0; - background: -webkit-linear-gradient(top, #ebebeb, #d9d9d9); - font-size: 16px; - font-weight: 700; - line-height: 58px; - text-align: center; - color: #333 !important; - text-shadow: 0 1px 0 rgba(255, 255, 255, .8); + .plus-icon { + color: #336a39; + text-shadow: 0 1px 0 rgba(255, 255, 255, .4); } } + } + + + .new-post-btn { + @include blue-button; + float: right; + } + + .new-post-icon { + display: block; + float: left; + width: 16px; + height: 17px; + margin: 7px 7px 0 0; + background: url(../images/new-post-icon.png) no-repeat; + } + + .post-search { + float: right; + } + + .post-search-field { + width: 280px; + height: 30px; + padding: 0 15px 0 30px; + margin-top: 14px; + border: 1px solid #acacac; + border-radius: 30px; + box-shadow: 0 1px 3px rgba(0, 0, 0, .1) inset, 0 1px 0 rgba(255, 255, 255, .5); + background: url(../images/search-icon.png) no-repeat 8px center #fff; + font-family: 'Open Sans', sans-serif; + font-weight: 400; + font-size: 13px; + line-height: 30px; + color: #333; + outline: 0; + -webkit-transition: border-color .1s; + + &:focus { + border-color: #4697c1; + } + } + + h1, ul, li, a, ol { + margin: 0; + padding: 0; + border: 0; + outline: 0; + font-size: 100%; + font: inherit; + vertical-align: baseline; + } + ul, li { + list-style-type: none; + } + a { + text-decoration: none; + color: #009fe2; + } + + display: table; + table-layout: fixed; + width: 100%; + height: 500px; + background: #fff; + border-radius: 3px; + border: 1px solid #aaa; + box-shadow: 0 1px 2px rgba(0, 0, 0, 0.05); + + .sidebar { + display: table-cell; + vertical-align: top; + width: 27.7%; + background: #f6f6f6; + border-radius: 3px 0 0 3px; + border-right: 1px solid #bcbcbc; .post-list { + background-color: #ddd; + + li:last-child a { + border-bottom: 1px solid #ddd; + } + a { + position: relative; display: block; height: 36px; padding: 0 10px; - border-bottom: 1px solid #ddd; + margin-bottom: 1px; background: #fff; font-size: 13px; font-weight: 700; @@ -104,6 +153,40 @@ font-weight: 400; color: #737373; } + + &.followed:after { + content: ''; + position: absolute; + top: 0; + right: 0; + width: 12px; + height: 12px; + background: url(../images/following-flag.png) no-repeat; + } + + &.active { + background: -webkit-linear-gradient(top, #96e0fd, #61c7fc); + border-color: #4697c1; + box-shadow: 0 1px 0 #4697c1, 0 -1px 0 #4697c1; + + .title { + color: #333; + } + + .votes-count, + .comments-count { + background: -webkit-linear-gradient(top, #3994c7, #4da7d3); + color: #fff; + + &:after { + color: #4da7d3; + } + } + + &.followed:after { + background-position: 0 -12px; + } + } } .title { @@ -115,8 +198,8 @@ overflow: hidden; } - .votes, - .comments { + .votes-count, + .comments-count { display: block; float: right; width: 32px; @@ -131,7 +214,7 @@ color: #767676; } - .comments { + .comments-count { position: relative; margin-left: 4px; @@ -156,898 +239,41 @@ } } } -} - - - -/*** OLD STUFF ***/ -/*** Variables ***/ - -$comment-margin-left: 30px; -$discussion-title-size: 1.6em; -$comment-title-size: 1.0em; -$post-font-size: 0.9em; -$comment-info-size: 0.75em; -$comment-font-size: 0.8em; -$discussion-input-width: 100%; - -$tag-background-color: #e7ecdd; -$tag-border-color: #babdb3; -$tag-text-color: #5b614f; - - - -/*** Mixins ***/ - -@mixin discussion-font { - font-family: inherit; -} - -@mixin discussion-clickable { - color: black; - &:hover { - text-decoration: none; - } -} - -@mixin standard-discussion-link { - text-decoration: none; - &:hover { - color: #1C71DD; - text-decoration: none; - } -} - -.discussion-loading { - background-image: url(../images/discussion/loading.gif); - width: 15px; - height: 15px; - margin-left: 2px; - display: inline-block; -} - -/*** Discussions ***/ - -.discussion { - - #open_close_accordion { - display: none; + .board-drop-btn { + display: block; + height: 60px; + border-bottom: 1px solid #a3a3a3; + border-radius: 3px 0 0 0; + background: -webkit-linear-gradient(top, #ebebeb, #d9d9d9); + font-size: 16px; + font-weight: 700; + line-height: 58px; + text-align: center; + color: #333; + text-shadow: 0 1px 0 rgba(255, 255, 255, .8); } - p + p, ul + p, ol + p { - margin-top: 0; - } - - /*** Sidebar ***/ - - .sidebar-module { - @include clearfix; - padding: 0 26px 24px; - margin-bottom: 24px; - border-bottom: 1px solid #d3d3d3; - font-size: 13px; - - header { - margin-bottom: 14px; - @include clearfix; - } - - h4 { - float: left; - font-size: 15px; - font-weight: bold; - } - - .sidebar-new-post-button, .sidebar-promote-moderator-button { - @include button; - } - - .sidebar-revoke-moderator-button { - @include button(simple, gray); - } - - .sidebar-new-post-button, .sidebar-promote-moderator-button, .sidebar-revoke-moderator-button { - display: block; - box-sizing: border-box; - width: 100%; - margin: 20px 0; - padding: 11px; - font-size: 1.1em; - text-align: center; - - &:hover { - text-decoration: none; - } - } - - .sidebar-new-post-button { - margin: 40px 0 20px 0; - } - - .sidebar-view-all { - float: right; - font-size: 13px; - line-height: 1.6em; - @include standard-discussion-link; - } - - .discussion-sidebar-following-list { - li { - @include clearfix; - margin-bottom: 8px; - border: none; - } - - a { - @include standard-discussion-link; - background: none; - - span { - line-height: 1.3; - } - } - } - - .discussion-sidebar-tags-list li { - @include clearfix; - border-bottom: none; - } - - .sidebar-tag-count { - color: #9a9a9a; - font-size: .85em; - line-height: 3em; - } - - .sidebar-following-name { - float: left; - width: 80%; - } - - .sidebar-vote-count { - float: right; - width: 20%; - text-align: right; - color: #9a9a9a; - } - -//user profile - - .user-profile { - @extend .sidebar; - margin-top: 24px; - } - - .sidebar-username { - font-size: 1.5em; - font-weight: bold; - line-height: 1.5em; - margin-top: 20px; - } - - .sidebar-user-roles { - color: darkGray; - font-style: italic; - margin-bottom: 15px; - } - - .sidebar-threads-count, .sidebar-comments-count { - - span { - font-size: 1.5em; - font-weight: bold; - line-height: 1.5em; - margin-right: 10px; - } - } - } - - .discussion-non-content { - margin-left: flex-gutter(); - } - - /*** Post ***/ - - .discussion-title { - @include discussion-font; - @include discussion-clickable; - display: inline-block; - font-size: $discussion-title-size; - font-weight: bold; - margin-bottom: flex-gutter(6); - } - - .discussion-title-wrapper { - .discussion-watch-discussion, .discussion-unwatch-discussion { - @include discussion-font; - display: none; - font-size: $comment-info-size; - margin-left: 5px; - } - } - - .discussion-right-wrapper { - min-height: 40px; - margin: 24px 0 24px 68px; - } - - .admin-actions { - float: right; - margin: 0.4em 1em 0 2em; - padding: 0; - - li { - margin-bottom: 6px !important; - } + .sort-bar { + height: 27px; + border-bottom: 1px solid #a3a3a3; + background: -webkit-linear-gradient(top, #cdcdcd, #b6b6b6); + box-shadow: 0 1px 0 rgba(255, 255, 255, .4) inset; a { display: block; - height: 25px; - padding-left: 25px; - border-radius: 50%; - background: url(../images/admin-actions-sprite.png) no-repeat; - font-size: .8em; - line-height: 25px; - color: #b8b8b8; - @include transition(color, .1s); - - &:hover { - text-decoration: none; - } - - &.admin-endorse { - background-position: 0 0; - - &:hover { - color: #63b141; - background-position: 0 -75px; - } - } - - &.admin-edit { - background-position: 0 -25px; - - &:hover { - color: #009fe2; - background-position: 0 -100px; - } - } - - &.admin-delete { - background-position: 0 -50px; - - &:hover { - color: #d45050; - background-position: 0 -125px; - } - } - } - } - - .comments { - .admin-actions { - margin-top: 0; - - li { - margin-bottom: 2px !important; - } - - a { - width: 20px; - height: 20px; - padding-left: 0; - overflow: hidden; - text-indent: -9999px; - - &.admin-endorse { - background-position: 0 -150px; - - &:hover { - background-position: 0 -225px; - } - } - - &.admin-edit { - background-position: 0 -175px; - - &:hover { - background-position: 0 -250px; - } - } - - &.admin-delete { - background-position: 0 -200px; - - &:hover { - background-position: 0 -275px; - } - } - } - } - } - - - - - /*** thread ***/ - - .thread { - //display: none; - - .search-highlight { - display: inline; - font-weight: bold; - background-color: lightyellow; - } - - .thread-title { - @include discussion-font; - @include discussion-clickable; - display: block; - margin-bottom: 1em; - font-size: $comment-title-size; - font-weight: bold; - line-height: 1.4em; - } - - .thread-body, .content-body { - @include discussion-font; - font-size: $post-font-size; - margin-bottom: 4px; - margin-top: 3px; - - p { - @include discussion-font; - } - } - - .thread-tags { - display: inline-block; - } - - .info { - @include discussion-font; - color: gray; - font-size: $comment-info-size; - font-style: italic; - margin-top: 1em; - - a:hover { - text-decoration: none; - color: #1C71DD; - } - - .comment-time { - display: inline; - float: right; - margin-right: 1em; - } - - .show-comments-wrapper { - display: inline; - margin-right: 20px; - } - - .discussion-actions { - display: inline; - margin: 0; - padding: 0; - - li { - display: inline; - margin-right: 20px; - } - } - - .discussion-link { - @include discussion-font; - color: #1d9dd9; - display: inline; - - &.discussion-unfollow-thread { - color: #dea03e; - } - } - } - - .discussion-content { - border-top: lightgray 1px solid; - overflow: hidden; - // padding: 1.5% 0; - - .discussion-reply-new { - @include discussion-font; - margin-left: 68px; - - .reply-body { - @include discussion-font; - display: block; - font-size: $post-font-size; - margin-top: 10px; - width: 95%; - } - - .reply-post-control { - margin-top: 1%; - } - } - } - - //COMMENT STYLES - .comments { - overflow: hidden; - - .discussion-votes { - margin-top: 8px; - } - - .discussion-right-wrapper { - margin: 10px 0 10px 68px; - } - - .comment { - margin-left: 68px; - .comment-body, .content-body { - @include discussion-font; - color: black; - display: block; - font-size: $comment-font-size; - margin-top: 3px; - } - - &.endorsed { - > .discussion-content { - background-color: #fcfcea; - } - } - } - } - } - - - - - /*** Sorting ***/ - - .discussion-sort { - float: right; - font-size: 0.8em; - margin-top: -36px; - - .discussion-label { - display: block; - float: left; - padding: 0 14px; - line-height: 34px; - } - - .discussion-sort-link { - display: block; - float: left; - padding: 0 14px; - line-height: 34px; - - &:hover { - color: #1C71DD; - text-decoration: none; - } - } - - .discussion-sort-link.sorted { - color: #000; - border-bottom: 2px solid #000; - } - } - - /*** Search ***/ - - .search-wrapper-inline { - display: inline-block; - margin-top: 3%; - width: 80%; - } - - .search-wrapper { - margin-bottom: 50px; - margin-left: .5%; - } - - .discussion-search-form { - display: inline-block; - margin-bottom: 1%; - width: flex-grid(12); - - .discussion-link { - @include button(simple, #999); - color: white; - display: inline-block; - font-size: inherit; - font-weight: bold; - margin-left: 1%; - padding-top: 9px; - text-decoration: none; - } - - .discussion-search-text { - @include discussion-font; - } - - .search-input { - float: left; - font: inherit; - font-style: normal; - // width: 72%; - width: flex-grid(8); - margin-left: flex-grid(1); - } - } - - .search-within { - display: block; - margin-bottom: 3%; - } - - .discussion-search-within-board { - font: inherit; - font-size: $post-font-size; - font-style: normal; - } - - /*** buttons ***/ - - .control-button { - @include button; - @include discussion-font; - background-color: #959595; - @include background-image(linear-gradient(top, #959595, #7B7B7B)); - border: 1px solid #6F6F6F; - @include box-shadow(inset 0 1px 0 #A2A2A2, 0 0 3px #CCC); - color: white; - display: inline-block; - font-size: inherit; - font-weight: bold; - margin-bottom: 3%; - padding-top: 9px; - width: inherit; - text-decoration: none; - text-shadow: none; - - &:hover { - background-color: #A2A2A2; - @include background-image(linear-gradient(top, #A2A2A2, #7B7B7B)); - border: 1px solid #555; - @include box-shadow(inset 0 1px 0 #BBB, 0 0 3px #CCC); - } - } - - .follow-wrapper { - display: inline; - } - - /*** votes ***/ - - .discussion-votes { - float: left; - width: 60px; - margin-top: 18px; - text-align: center; - - .discussion-vote { - display: block; - width: 50px; - height: 17px; - margin: auto; - background: url(../images/vote-arrows.png) no-repeat; - font-size: 15px; - font-weight: bold; - color: black; - @include hide-text; - @include transition(all, 0, easeOut); - } - - .discussion-vote-up { - margin-bottom: 5px; - background-position: -50px -3px; - - &:hover { - background-position: -50px -5px; - @include transition-duration(0.05s); - } - - &.voted { - background-position: 0 -3px; - color: #1C71DD; - @include transition-duration(0); - } - } - - .discussion-vote-down { - margin-top: 7px; - background-position: -50px -30px; - - &:hover { - background-position: -50px -28px; - @include transition-duration(0.05s); - } - - &.voted { - background-position: 0 -30px; - color: #1C71DD; - @include transition-duration(0); - } - } - - .discussion-vote-count { - @include discussion-font; - font-size: $post-font-size; - } - - .discussion-votes-point { - font-size: 1.1em; - font-weight: bold; - color: #9a9a9a; - } - } - - - /*** new post ***/ - - .new-post-form, .discussion-thread-edit { - - .title-input, .body-input { - display: block !important; - font: inherit; - font-style: normal; - //width: $discussion-input-width !important; - } - - .new-post-similar-posts-wrapper { - @include border-radius(3px); - border: 1px solid #EEE; - font-size: $post-font-size; - line-height: 150%; - margin-top: 1%; - padding: 1% 1.5%; - } - - .hide-similar-posts { float: right; - } - - .new-post-similar-posts { - font: inherit; - .similar-post { - display: block; - line-height: 150%; - } - } - - .discussion-errors { - color: #8F0E0E; - display: block; - margin-left: -5%; - } - - .new-post-body { - } - - .tagsinput { - background: #FAFAFA; - border: 1px solid #C8C8C8; - -webkit-border-radius: 3px; - -moz-border-radius: 3px; - -ms-border-radius: 3px; - -o-border-radius: 3px; - border-radius: 3px; - -webkit-box-shadow: 0 1px 0 0 rgba(255, 255, 255, 0.6), inset 0 0 3px 0 rgba(0, 0, 0, 0.1); - -moz-box-shadow: 0 1px 0 0 rgba(255, 255, 255, 0.6), inset 0 0 3px 0 rgba(0, 0, 0, 0.1); - box-shadow: 0 1px 0 0 rgba(255, 255, 255, 0.6), inset 0 0 3px 0 rgba(0, 0, 0, 0.1); - -webkit-box-sizing: border-box; - -moz-box-sizing: border-box; - box-sizing: border-box; - margin-top: flex-gutter(); - vertical-align: top; - -webkit-font-smoothing: antialiased; - } - } - - .discussion-content-edit, .discussion-reply-new, .new-post-form { - margin: 10px 0 10px 0; - - .discussion-errors { - color: #8F0E0E; - display: block; - font: inherit; - font-size: $post_font_size; - list-style: none; - margin-left: -3%; - padding-left: 2em; - } - - a:hover { - color: #1C71DD; - text-decoration: none; - } - - .new-post-title { - display: block; - padding: 5px 12px; - border-width: 1px; - width: 100%; - } - - .thread-title-edit { - width: 100%; - } - - &.collapsed { - .new-post-title { - display: none; - visibility: hidden; - } - - .wmd-button-row { - height: 0; - } - - .wmd-input { - height: 100px; - @include border-radius(3px); - } - - .wmd-preview { - height: 0; - padding: 0; - border-width: 0; - } - - .post-options { - height: 0; - } - - .post-control { - display: none; - } - - .tagsinput { - display: none; - } - } - - .new-post-control { - margin-left: 75%; - margin-top: 1%; - - .discussion-cancel-post { - margin-right: 1.5%; - } - } - - .reply-post-control { - - .discussion-cancel-post { - margin-right: 1.5%; - } - } - - .edit-post-control { - margin-top: 1%; - - .discussion-cancel-update { - margin-right: 1.5%; - } - } - - .control-button { - @include button; - @include discussion-font; - margin-right: 16px; - padding-top: 9px; - color: white; - display: inline-block; - font-size: inherit; + height: 27px; + margin-right: 10px; + font-size: 11px; font-weight: bold; - text-decoration: none; - width: inherit; + line-height: 23px; + color: #333; + text-shadow: 0 1px 0 rgba(255, 255, 255, .5); - &:hover { - color: white; - } - } - - label { - display: inline; - font-family: $sans-serif; - font-size: .8em; - font-style: normal; - font-weight: 400; - } - } - - .discussion-content-edit { - margin: 3%; - } - - .new-post-form { - margin: 10px 0 40px 0; - } - - .discussion-reply-new { - - .discussion-auto-watch { - margin-left: 2%; - } - } - - .thread-tag { - background: $tag-background-color; - border: 1px solid $tag-border-color; - -moz-border-radius: 2px; - -webkit-border-radius: 2px; - color: $tag-text-color; - float: left; - font-size: 13px; - margin: 5px 7px 5px 0; - padding: 5px 7px; - text-decoration: none; - - &:hover { - border-color: #7b8761; - color: #2f381c; - text-decoration: none; - } - } - - /*** pagination ***/ - - .discussion-paginator { - font-size: $post-font-size; - margin-bottom: 10px; - margin-top: 20px; - text-align: center; - - div { - display: inline-block; - font-weight: bold; - margin: 0 5px; - - a { - background: #EEE; - -webkit-border-radius: 3px; - -moz-border-radius: 3px; - -ms-border-radius: 3px; - -o-border-radius: 3px; - border-radius: 3px; - color: black; - font-weight: normal; - padding: 4px 10px; - text-decoration: none; - - &:hover { - background: #DDD; - } - } - } - } - - &.inline-discussion, .forum-discussion, .user-discussion { - .new-post-form { - margin: 24px 60px; - - .post-options { - margin: 8px 0 16px 0; - overflow: hidden; - - label { - margin-right: 15px; - display: inline; - } - } - - .post-control { - overflow: hidden; - margin: 0 0 5% 0; + .sort-label { + font-size: 9px; + text-transform: uppercase; } } } @@ -1055,138 +281,197 @@ $tag-text-color: #5b614f; -/*** base editor styles ***/ -.wmd-panel { - width: 100%; - min-width: 500px; + + + + + + + + +.global-discussion-actions { + height: 60px; + background: -webkit-linear-gradient(top, #ebebeb, #d9d9d9); + border-radius: 0 3px 0 0; + border-bottom: 1px solid #bcbcbc; } -.wmd-button-bar { - width: 100%; - background-color: Silver; -} -.wmd-input { - height: 150px; - width: 100%; - background-color: #e9e9e9; - border: 1px solid #c8c8c8; - font-family: Monaco, 'Lucida Console', monospace; - font-style: normal; - font-size: 0.8em; - line-height: 1.6em; - @include border-radius(3px 3px 0 0); - &::-webkit-input-placeholder { + + + + + + + + +.discussion-article { + position: relative; + display: table-cell; + vertical-align: top; + width: 72.3%; + padding: 40px; + + h1 { + font-size: 28px; + font-weight: 700; + } + + .posted-details { + font-size: 12px; + font-style: italic; color: #888; } + + p + p { + margin-top: 20px; + } + + .dogear { + display: block; + position: absolute; + top: 0; + right: -1px; + width: 52px; + height: 51px; + background: url(../images/follow-dog-ear.png) 0 -51px no-repeat; + + &.is-followed { + background-position: 0 0; + } + } } -.wmd-preview { - position: relative; - font-family: $sans-serif; - padding: 25px 20px 10px 20px; - margin-bottom: 5px; - box-sizing: border-box; - border: 1px solid #c8c8c8; - border-top-width: 0; - @include border-radius(0 0 3px 3px); - overflow: hidden; - @include transition(all, .2s, easeOut); +.discussion-post header, +.responses li header { + margin-bottom: 20px; +} - &:before { - content: 'PREVIEW'; - position: absolute; - top: 3px; - left: 5px; - font-size: 11px; - color: #bbb; +.responses { + margin-top: 40px; + + > li { + margin: 0 -10px; + padding: 30px; + border-radius: 3px; + border: 1px solid #b2b2b2; + box-shadow: 0 1px 3px rgba(0, 0, 0, .15); + } + + .posted-by { + font-weight: 700; + } +} + +.endorse-btn { + display: block; + float: right; + width: 27px; + height: 27px; + margin-right: 10px; + border-radius: 27px; + border: 1px solid #a0a0a0; + background: -webkit-linear-gradient(top, #fff 35%, #ebebeb); + box-shadow: 0 1px 1px rgba(0, 0, 0, .1); + + .check-icon { + display: block; + width: 13px; + height: 12px; + margin: 8px auto; + background: url(../images/endorse-icon.png) no-repeat; + } + + &.is-endorsed { + border: 1px solid #4697c1; + background: -webkit-linear-gradient(top, #6dccf1, #38a8e5); + box-shadow: 0 1px 1px rgba(0, 0, 0, 0.1), 0 1px 0 rgba(255, 255, 255, .4) inset; + + .check-icon { + background-position: 0 -12px; + } + } +} + +.comments { + margin-top: 20px; + border-top: 1px solid #ddd; + + li { + background: #f6f6f6; + border-bottom: 1px solid #ddd; } p { - font-family: $sans-serif; + font-size: 13px; + padding: 10px 20px; + + .posted-details { + font-size: 11px; + white-space: nowrap; + } } - background-color: #fafafa; } -.wmd-button-row { - position: relative; - margin-left: 5px; - margin-right: 5px; - margin-bottom: 5px; - margin-top: 10px; - padding: 0px; - height: 20px; - overflow: hidden; - @include transition(all, .2s, easeOut); +.comment-form { + padding: 8px 20px; } -.wmd-spacer { - width: 1px; - height: 20px; - margin-left: 14px; +.comment-form-input { + width: 100%; + height: 31px; + padding: 0 10px; + box-sizing: border-box; + border: 1px solid #b2b2b2; + border-radius: 3px; + box-shadow: 0 1px 3px rgba(0, 0, 0, .1) inset; + -webkit-transition: border-color .1s; + outline: 0; - position: absolute; - background-color: Silver; - display: inline-block; - list-style: none; + &:focus { + border-color: #4697c1; + } } -.wmd-button { - width: 20px; - height: 20px; - padding-left: 2px; - padding-right: 3px; - position: absolute; - display: inline-block; - list-style: none; - cursor: pointer; -} +.moderator-actions { + margin-top: 20px; + @include clearfix; -.wmd-button > span { - background-image: url('/static/images/wmd-buttons.png'); - background-repeat: no-repeat; - background-position: 0px 0px; - width: 20px; - height: 20px; - display: inline-block; -} + li { + float: left; + margin-right: 8px; + } -.wmd-spacer1 { - left: 50px; -} -.wmd-spacer2 { - left: 175px; -} + a { + display: block; + height: 26px; + padding: 0 12px; + border-radius: 3px; + border: 1px solid #b2b2b2; + background: -webkit-linear-gradient(top, #fff 35%, #ebebeb); + font-size: 13px; + line-height: 24px; + color: #737373; + box-shadow: 0 1px 1px rgba(0, 0, 0, 0.1); -.wmd-spacer3 { - left: 300px; -} + .delete-icon { + display: block; + float: left; + width: 10px; + height: 10px; + margin: 8px 4px 0 0; + background: url(../images/moderator-delete-icon.png) no-repeat; + } -.wmd-prompt-background { - background-color: Black; -} - -.wmd-prompt-dialog { - border: 1px solid #999999; - background-color: #F5F5F5; -} - -.wmd-prompt-dialog > div { - font-size: 0.8em; - font-family: arial, helvetica, sans-serif; -} - - -.wmd-prompt-dialog > form > input[type="text"] { - border: 1px solid #999999; - color: black; -} - -.wmd-prompt-dialog > form > input[type="button"] { - border: 1px solid #888888; - font-family: trebuchet MS, helvetica, sans-serif; - font-size: 0.8em; - font-weight: bold; + .edit-icon { + display: block; + float: left; + width: 10px; + height: 10px; + margin: 7px 4px 0 0; + background: url(../images/moderator-edit-icon.png) no-repeat; + } + } } diff --git a/lms/templates/discussion/_single_thread.html b/lms/templates/discussion/_single_thread.html index ccf106a6df..1939bfd753 100644 --- a/lms/templates/discussion/_single_thread.html +++ b/lms/templates/discussion/_single_thread.html @@ -1,12 +1,33 @@ <%namespace name="renderer" file="_content_renderer.html"/> -
- ${thread['title'] | h} -

sometime by Foo

-
- ${renderer.render_content_with_comments(thread)} +
+
    + % for reply in thread.get("children", []): +
  1. +
    ${reply['body']}
    +
      + % for comment in reply.get("children", []): +
    1. ${comment['body']}

    2. + % endfor +
    +
  2. + % endfor +
+ <%include file="_js_data.html" /> diff --git a/lms/templates/discussion/single_thread.html b/lms/templates/discussion/single_thread.html index 1e05475762..3024198750 100644 --- a/lms/templates/discussion/single_thread.html +++ b/lms/templates/discussion/single_thread.html @@ -1,4 +1,5 @@ <%! import django_comment_client.helpers as helpers %> +<%! from django.template.defaultfilters import escapejs %> <%inherit file="../main.html" /> <%namespace name='static' file='../static_content.html'/> <%block name="bodyclass">discussion @@ -16,48 +17,47 @@ <%include file="../courseware/course_navigation.html" args="active_page='discussion'" /> -
- + +
+
+ New Post +
+ +
+
+ ${content.decode('utf-8')} -
+ +
+ -
- -
-
-
- -
- -
- ${content.decode('utf-8')} -
-
-
+ From a5b1abb2a8dfb5e5a8e9d25b27e204cf89e7c397 Mon Sep 17 00:00:00 2001 From: Matthew Mongeau Date: Wed, 29 Aug 2012 10:23:17 -0400 Subject: [PATCH 005/364] Remove log --- lms/djangoapps/django_comment_client/forum/views.py | 1 - 1 file changed, 1 deletion(-) diff --git a/lms/djangoapps/django_comment_client/forum/views.py b/lms/djangoapps/django_comment_client/forum/views.py index ed09f1cfdb..6d74a966d2 100644 --- a/lms/djangoapps/django_comment_client/forum/views.py +++ b/lms/djangoapps/django_comment_client/forum/views.py @@ -182,7 +182,6 @@ def render_single_thread(request, discussion_id, course_id, thread_id): annotated_content_info = utils.get_annotated_content_infos(course_id, thread=thread, user=request.user, user_info=user_info) - log.debug(annotated_content_info) context = { 'discussion_id': discussion_id, 'thread': thread, From 19b14f446b81b44dad87b47dbb3e9df18bfa359c Mon Sep 17 00:00:00 2001 From: Matthew Mongeau Date: Wed, 29 Aug 2012 10:28:02 -0400 Subject: [PATCH 006/364] Follow a thread --- lms/static/coffee/src/discussion/main.coffee | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/lms/static/coffee/src/discussion/main.coffee b/lms/static/coffee/src/discussion/main.coffee index 783ab9a3d5..3cf696ab96 100644 --- a/lms/static/coffee/src/discussion/main.coffee +++ b/lms/static/coffee/src/discussion/main.coffee @@ -33,8 +33,18 @@ class @DiscussionThreadView extends Backbone.View else @unvote() - toggleFollowing: -> + toggleFollowing: (event) -> + $elem = $(event.target) @$(".dogear").toggleClass("is-followed") + url = null + if @$(".dogear").hasClass("is-followed") + url = @model.urlFor("follow") + else + url = @model.urlFor("unfollow") + DiscussionUtil.safeAjax + $elem: $elem + url: url + type: "POST" vote: -> url = @model.urlFor("upvote") From 46d0d4c4f2cc1b4f5ee97ff4f66b1a81b8b2bbc9 Mon Sep 17 00:00:00 2001 From: Matthew Mongeau Date: Wed, 29 Aug 2012 11:19:29 -0400 Subject: [PATCH 007/364] Hook up list to voting. --- .../django_comment_client/forum/views.py | 3 ++- lms/static/coffee/src/discussion/main.coffee | 17 +++++++++++++++++ lms/templates/discussion/single_thread.html | 18 ++++++++++++------ 3 files changed, 31 insertions(+), 7 deletions(-) diff --git a/lms/djangoapps/django_comment_client/forum/views.py b/lms/djangoapps/django_comment_client/forum/views.py index 6d74a966d2..37cce1ada4 100644 --- a/lms/djangoapps/django_comment_client/forum/views.py +++ b/lms/djangoapps/django_comment_client/forum/views.py @@ -241,7 +241,8 @@ def single_thread(request, course_id, discussion_id, thread_id): 'recent_active_threads': recent_active_threads, 'trending_tags': trending_tags, 'course_id': course.id, - 'threads': threads, + 'thread_id': thread_id, + 'threads': json.dumps(threads), } return render_to_response('discussion/single_thread.html', context) diff --git a/lms/static/coffee/src/discussion/main.coffee b/lms/static/coffee/src/discussion/main.coffee index 3cf696ab96..0daa0ebdf3 100644 --- a/lms/static/coffee/src/discussion/main.coffee +++ b/lms/static/coffee/src/discussion/main.coffee @@ -8,6 +8,23 @@ class @DiscussionUser voted: (thread) -> @content_info[thread.id]['voted'] == 'up' +class @ThreadListItemView extends Backbone.View + tagName: "li" + template: _.template($("#thread-list-item-template").html()) + initialize: -> + @model.on "change", @render + render: => + @$el.html(@template(@model.toJSON())) + @ + +class @DiscussionThreadListView extends Backbone.View + render: -> + @collection.each @renderThreadListItem + renderThreadListItem: (thread) => + view = new ThreadListItemView(model: thread) + view.render() + @$el.append(view.el) + class @DiscussionThreadView extends Backbone.View events: "click .discussion-vote-up": "toggleVote" diff --git a/lms/templates/discussion/single_thread.html b/lms/templates/discussion/single_thread.html index 3024198750..59882a2443 100644 --- a/lms/templates/discussion/single_thread.html +++ b/lms/templates/discussion/single_thread.html @@ -30,9 +30,6 @@
@@ -51,13 +48,22 @@ + + From fb1368afa956afa8f59fbe9d5f1605653351143d Mon Sep 17 00:00:00 2001 From: Matthew Mongeau Date: Wed, 29 Aug 2012 11:43:09 -0400 Subject: [PATCH 008/364] Move views and models out. --- .../django_comment_client/forum/views.py | 1 - lms/static/coffee/src/discussion/main.coffee | 108 ------------------ .../discussion/models/discussion_user.coffee | 10 ++ .../views/discussion_thread_list_view.coffee | 8 ++ .../views/discussion_thread_view.coffee | 61 ++++++++++ .../views/thread_list_item_view.coffee | 8 ++ 6 files changed, 87 insertions(+), 109 deletions(-) create mode 100644 lms/static/coffee/src/discussion/models/discussion_user.coffee create mode 100644 lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee create mode 100644 lms/static/coffee/src/discussion/views/discussion_thread_view.coffee create mode 100644 lms/static/coffee/src/discussion/views/thread_list_item_view.coffee diff --git a/lms/djangoapps/django_comment_client/forum/views.py b/lms/djangoapps/django_comment_client/forum/views.py index 37cce1ada4..8050dbce7c 100644 --- a/lms/djangoapps/django_comment_client/forum/views.py +++ b/lms/djangoapps/django_comment_client/forum/views.py @@ -234,7 +234,6 @@ def single_thread(request, course_id, discussion_id, thread_id): 'discussion_id': discussion_id, 'csrf': csrf(request)['csrf_token'], 'init': '', - 'thread': json.dumps(utils.safe_content(thread)), 'annotated_content_info': json.dumps(annotated_content_info), 'content': render_single_thread(request, discussion_id, course_id, thread_id), 'course': course, diff --git a/lms/static/coffee/src/discussion/main.coffee b/lms/static/coffee/src/discussion/main.coffee index 0daa0ebdf3..e69de29bb2 100644 --- a/lms/static/coffee/src/discussion/main.coffee +++ b/lms/static/coffee/src/discussion/main.coffee @@ -1,108 +0,0 @@ -class @DiscussionUser - constructor: (content_info) -> - @content_info = content_info - - following: (thread) -> - @content_info[thread.id]['subscribed'] == true - - voted: (thread) -> - @content_info[thread.id]['voted'] == 'up' - -class @ThreadListItemView extends Backbone.View - tagName: "li" - template: _.template($("#thread-list-item-template").html()) - initialize: -> - @model.on "change", @render - render: => - @$el.html(@template(@model.toJSON())) - @ - -class @DiscussionThreadListView extends Backbone.View - render: -> - @collection.each @renderThreadListItem - renderThreadListItem: (thread) => - view = new ThreadListItemView(model: thread) - view.render() - @$el.append(view.el) - -class @DiscussionThreadView extends Backbone.View - events: - "click .discussion-vote-up": "toggleVote" - "click .dogear": "toggleFollowing" - initialize: (options) -> - @user = options['user'] - @model.bind "change", @updateModelDetails - - updateModelDetails: => - @$(".votes-count-number").html(@model.get("votes")["up_count"]) - - render: -> - if @user.following(@model) - @$(".dogear").addClass("is-followed") - - if @user.voted(@model) - @$(".vote-btn").addClass("is-cast") - - toggleVote: -> - @$(".vote-btn").toggleClass("is-cast") - if @$(".vote-btn").hasClass("is-cast") - @vote() - else - @unvote() - - toggleFollowing: (event) -> - $elem = $(event.target) - @$(".dogear").toggleClass("is-followed") - url = null - if @$(".dogear").hasClass("is-followed") - url = @model.urlFor("follow") - else - url = @model.urlFor("unfollow") - DiscussionUtil.safeAjax - $elem: $elem - url: url - type: "POST" - - vote: -> - url = @model.urlFor("upvote") - @$(".votes-count-number").html(parseInt(@$(".votes-count-number").html()) + 1) - DiscussionUtil.safeAjax - $elem: @$(".discussion-vote") - url: url - type: "POST" - success: (response, textStatus) => - if textStatus == 'success' - @model.set(response) - - unvote: -> - url = @model.urlFor("unvote") - @$(".votes-count-number").html(parseInt(@$(".votes-count-number").html()) - 1) - DiscussionUtil.safeAjax - $elem: @$(".discussion-vote") - url: url - type: "POST" - success: (response, textStatus) => - if textStatus == 'success' - @model.set(response) - -$ -> - window.$$contents = {} - window.$$discussions = {} - - # $(".discussion-module").each (index, elem) -> - # view = new DiscussionModuleView(el: elem) - - # $("section.discussion").each (index, elem) -> - # discussionData = DiscussionUtil.getDiscussionData($(elem).attr("_id")) - # discussion = new Discussion() - # discussion.reset(discussionData, {silent: false}) - # view = new DiscussionView(el: elem, model: discussion) - - # if window.$$annotated_content_info? - # DiscussionUtil.bulkUpdateContentInfo(window.$$annotated_content_info) - - # $userProfile = $(".discussion-sidebar>.user-profile") - # if $userProfile.length - # console.log "initialize user profile" - # view = new DiscussionUserProfileView(el: $userProfile[0]) - diff --git a/lms/static/coffee/src/discussion/models/discussion_user.coffee b/lms/static/coffee/src/discussion/models/discussion_user.coffee new file mode 100644 index 0000000000..c12006494f --- /dev/null +++ b/lms/static/coffee/src/discussion/models/discussion_user.coffee @@ -0,0 +1,10 @@ +class @DiscussionUser + constructor: (content_info) -> + @content_info = content_info + + following: (thread) -> + @content_info[thread.id]['subscribed'] == true + + voted: (thread) -> + @content_info[thread.id]['voted'] == 'up' + diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee new file mode 100644 index 0000000000..c22db5bb5b --- /dev/null +++ b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee @@ -0,0 +1,8 @@ +class @DiscussionThreadListView extends Backbone.View + render: -> + @collection.each @renderThreadListItem + @ + renderThreadListItem: (thread) => + view = new ThreadListItemView(model: thread) + view.render() + @$el.append(view.el) diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee new file mode 100644 index 0000000000..925e12ff73 --- /dev/null +++ b/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee @@ -0,0 +1,61 @@ +class @DiscussionThreadView extends Backbone.View + events: + "click .discussion-vote-up": "toggleVote" + "click .dogear": "toggleFollowing" + initialize: (options) -> + @user = options['user'] + @model.bind "change", @updateModelDetails + + updateModelDetails: => + @$(".votes-count-number").html(@model.get("votes")["up_count"]) + + render: -> + if @user.following(@model) + @$(".dogear").addClass("is-followed") + + if @user.voted(@model) + @$(".vote-btn").addClass("is-cast") + + @ + + toggleVote: -> + @$(".vote-btn").toggleClass("is-cast") + if @$(".vote-btn").hasClass("is-cast") + @vote() + else + @unvote() + + toggleFollowing: (event) -> + $elem = $(event.target) + @$(".dogear").toggleClass("is-followed") + url = null + if @$(".dogear").hasClass("is-followed") + url = @model.urlFor("follow") + else + url = @model.urlFor("unfollow") + DiscussionUtil.safeAjax + $elem: $elem + url: url + type: "POST" + + vote: -> + url = @model.urlFor("upvote") + @$(".votes-count-number").html(parseInt(@$(".votes-count-number").html()) + 1) + DiscussionUtil.safeAjax + $elem: @$(".discussion-vote") + url: url + type: "POST" + success: (response, textStatus) => + if textStatus == 'success' + @model.set(response) + + unvote: -> + url = @model.urlFor("unvote") + @$(".votes-count-number").html(parseInt(@$(".votes-count-number").html()) - 1) + DiscussionUtil.safeAjax + $elem: @$(".discussion-vote") + url: url + type: "POST" + success: (response, textStatus) => + if textStatus == 'success' + @model.set(response) diff --git a/lms/static/coffee/src/discussion/views/thread_list_item_view.coffee b/lms/static/coffee/src/discussion/views/thread_list_item_view.coffee new file mode 100644 index 0000000000..28afbdc668 --- /dev/null +++ b/lms/static/coffee/src/discussion/views/thread_list_item_view.coffee @@ -0,0 +1,8 @@ +class @ThreadListItemView extends Backbone.View + tagName: "li" + template: _.template($("#thread-list-item-template").html()) + initialize: -> + @model.on "change", @render + render: => + @$el.html(@template(@model.toJSON())) + @ From d75bb87bdd0d7f806c3e2fdb53cc9aa8ce9734bd Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Wed, 29 Aug 2012 13:22:55 -0400 Subject: [PATCH 009/364] started adding updated styles --- lms/static/images/browse-icon.png | Bin 0 -> 1298 bytes lms/static/images/follow-dog-ear.png | Bin 4246 -> 4362 bytes lms/static/images/nested-icon.png | Bin 0 -> 1038 bytes lms/static/images/sidebar-resolved-icons.png | Bin 0 -> 1077 bytes lms/static/images/vote-plus-icon.png | Bin 0 -> 1101 bytes lms/static/sass/_discussion-old.scss | 477 ++++++++ lms/static/sass/_discussion.scss | 1065 ++++++++++++------ lms/static/sass/base/_base.scss | 1 + lms/templates/discussion/single_thread.html | 49 +- 9 files changed, 1213 insertions(+), 379 deletions(-) create mode 100644 lms/static/images/browse-icon.png create mode 100644 lms/static/images/nested-icon.png create mode 100644 lms/static/images/sidebar-resolved-icons.png create mode 100644 lms/static/images/vote-plus-icon.png create mode 100644 lms/static/sass/_discussion-old.scss diff --git a/lms/static/images/browse-icon.png b/lms/static/images/browse-icon.png new file mode 100644 index 0000000000000000000000000000000000000000..25df634b4a9293210ed71a2031aa5e356027741a GIT binary patch literal 1298 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 b{{m(a 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 literal 0 HcmV?d00001 diff --git a/lms/static/images/sidebar-resolved-icons.png b/lms/static/images/sidebar-resolved-icons.png new file mode 100644 index 0000000000000000000000000000000000000000..4ade554454070aa681459b9de0218843a748fc5f GIT binary patch literal 1077 zcmaJ=O-$2J94~?jD27Br)L?v8jm)^U9jx0L1{>=pOXxDo)Ezw7wGY-nKWrava8N)G zV1jxvlIX>ch$aR-c{Im+`Tg-z5~xauJmM2*!HmM3 z+BIy!p5bI#9`2We3fa*P+6o*d&>)gPK^xF*t`H&@csaax%oGV0Tu^_AEQ!hpDG)U* z2z;Ivw@fn(U|A2->SI}EKk(9wm!k2@x|vqa$8ugjSbRtv%~EZ6!oFz9f2y>9H`wuf{i72LYLtIWVdTeegasfG?5Mk#9yq7aFdmQv8n zC0gBHEE6smRgg@I@z736Wk*5yzpJJ#dD}>Y%X(KNw$noNgO-dN*SpIJWpYsq zO31L%hA~jCVk&1K!_FBdi1x6cS&(E^cMPrtgdlJU-A0lw!vr59F^5N06)w(1Xm23O z#)2%vFfk^;`&mA~`h6|lmOz{dma)7c4{A_HWvsG{^{5s>PzRs1kl(5PQT1waey(*T%VkoDz|FpVn!t>*7mj)LfmPQ}yc-}2M z*l$1ldWSE?bb^nh3m>yrI!?7$ZkkT}`n&_gUWWgy*|+ob3{k9bJ*p_4>#9B2 zFx$WY*U>XGMAeqb$;sQBlXIdd-ZOts?71>EI<@&mbwl#SXr^lXb+%@@{=(&RWKH|C r#*Obc?45f4iTH8&)^+*K^BOQq?3|EqTEXmJw9vk}${vlZ` literal 0 HcmV?d00001 diff --git a/lms/static/images/vote-plus-icon.png b/lms/static/images/vote-plus-icon.png new file mode 100644 index 0000000000000000000000000000000000000000..1b9f87ad19973028abe4213978d03a20ad6c94a9 GIT binary patch literal 1101 zcmaJ=O-$2J9Ix^bnWDt_eetCrQDkeov9dMHf$JtqEWvH+j0acR2Q<(R+lMP$LAb-?|mW_a8d%nviIa^%e-?s@Mh-P?Womj=(yC zD5y|UX_OZBa+0okL?N^YAniX z)LV;X30AQFuR zS%zVvOn|Rt`2bt%_j!GR7!%BKd0pyKp@wo?d5Ig#%XNl9HLzzMn#wUK$4p%Xb4hbb z{#YV;^%l5t{#f|DTnYz6Ij#Mx)j1QMA7{HbxcIO*`cT93ZsNf{HC*`-Uy7kP-;lCD zw3JL%y(Egy&NfUPFD}gVGnc?v_*zYQfvf(r?}U(%`!DwwmTfuo?r!~qRX4tdA9R76 z>9Jvc-uFUv{X@F1==aIV0s7pJ@RRB91(o)u>ocoIxNAkTC0Abbjqdx|JkarY z=nGqZAiBJ2*q-1Cy6VxL-mAa1Ho9)Ro^9JT(YqV3JP-?R z*qQleC7XCKqiwrzYklLlixr0lN7uY+U0dI~jF>9rmL)&+4muY+9&O_9@6Po70groS A=>Px# literal 0 HcmV?d00001 diff --git a/lms/static/sass/_discussion-old.scss b/lms/static/sass/_discussion-old.scss new file mode 100644 index 0000000000..01380faa77 --- /dev/null +++ b/lms/static/sass/_discussion-old.scss @@ -0,0 +1,477 @@ +@mixin blue-button { + display: block; + height: 33px; + margin: 12px; + padding: 0 15px; + border-radius: 3px; + border: 1px solid #4697c1; + background: -webkit-linear-gradient(top, #6dccf1, #38a8e5); + font-size: 13px; + font-weight: 700; + line-height: 30px; + color: #fff; + text-shadow: 0 1px 0 rgba(0, 0, 0, .4); + box-shadow: 0 1px 0 rgba(255, 255, 255, 0.4) inset, 0 1px 1px rgba(0, 0, 0, .15); + + &:hover { + border-color: #297095; + background: -webkit-linear-gradient(top, #4fbbe4, #2090d0); + } +} + +.discussion-body { + + .vote-btn { + float: right; + display: block; + height: 27px; + padding: 0 8px; + border-radius: 5px; + border: 1px solid #b2b2b2; + background: -webkit-linear-gradient(top, #fff 35%, #ebebeb); + box-shadow: 0 1px 1px rgba(0, 0, 0, .15); + font-size: 12px; + font-weight: 700; + line-height: 25px; + color: #333; + + .plus-icon { + float: left; + margin-right: 6px; + font-size: 18px; + color: #17b429; + } + + &.is-cast { + border-color: #379a42; + background: -webkit-linear-gradient(top, #50cc5e, #3db84b); + color: #fff; + text-shadow: 0 1px 0 rgba(0, 0, 0, .3); + box-shadow: 0 1px 0 rgba(255, 255, 255, .4) inset, 0 1px 2px rgba(0, 0, 0, .2); + + .plus-icon { + color: #336a39; + text-shadow: 0 1px 0 rgba(255, 255, 255, .4); + } + } + } + + + .new-post-btn { + @include blue-button; + float: right; + } + + .new-post-icon { + display: block; + float: left; + width: 16px; + height: 17px; + margin: 7px 7px 0 0; + background: url(../images/new-post-icon.png) no-repeat; + } + + .post-search { + float: right; + } + + .post-search-field { + width: 280px; + height: 30px; + padding: 0 15px 0 30px; + margin-top: 14px; + border: 1px solid #acacac; + border-radius: 30px; + box-shadow: 0 1px 3px rgba(0, 0, 0, .1) inset, 0 1px 0 rgba(255, 255, 255, .5); + background: url(../images/search-icon.png) no-repeat 8px center #fff; + font-family: 'Open Sans', sans-serif; + font-weight: 400; + font-size: 13px; + line-height: 30px; + color: #333; + outline: 0; + -webkit-transition: border-color .1s; + + &:focus { + border-color: #4697c1; + } + } + + h1, ul, li, a, ol { + margin: 0; + padding: 0; + border: 0; + outline: 0; + font-size: 100%; + font: inherit; + vertical-align: baseline; + } + ul, li { + list-style-type: none; + } + a { + text-decoration: none; + color: #009fe2; + } + + display: table; + table-layout: fixed; + width: 100%; + height: 500px; + background: #fff; + border-radius: 3px; + border: 1px solid #aaa; + box-shadow: 0 1px 2px rgba(0, 0, 0, 0.05); + + .sidebar { + display: table-cell; + vertical-align: top; + width: 27.7%; + background: #f6f6f6; + border-radius: 3px 0 0 3px; + border-right: 1px solid #bcbcbc; + .post-list { + background-color: #ddd; + + li:last-child a { + border-bottom: 1px solid #ddd; + } + + a { + position: relative; + display: block; + height: 36px; + padding: 0 10px; + margin-bottom: 1px; + background: #fff; + font-size: 13px; + font-weight: 700; + line-height: 34px; + color: #333; + + &.read .title { + font-weight: 400; + color: #737373; + } + + &.followed:after { + content: ''; + position: absolute; + top: 0; + right: 0; + width: 12px; + height: 12px; + background: url(../images/following-flag.png) no-repeat; + } + + &.active { + background: -webkit-linear-gradient(top, #96e0fd, #61c7fc); + border-color: #4697c1; + box-shadow: 0 1px 0 #4697c1, 0 -1px 0 #4697c1; + + .title { + color: #333; + } + + .votes-count, + .comments-count { + background: -webkit-linear-gradient(top, #3994c7, #4da7d3); + color: #fff; + + &:after { + color: #4da7d3; + } + } + + &.followed:after { + background-position: 0 -12px; + } + } + } + + .title { + display: block; + float: left; + width: 70%; + white-space: nowrap; + text-overflow: ellipsis; + overflow: hidden; + } + + .votes-count, + .comments-count { + display: block; + float: right; + width: 32px; + height: 16px; + margin-top: 9px; + border-radius: 2px; + background: -webkit-linear-gradient(top, #d4d4d4, #dfdfdf); + font-size: 9px; + font-weight: 700; + line-height: 16px; + text-align: center; + color: #767676; + } + + .comments-count { + position: relative; + margin-left: 4px; + + &:after { + content: '◥'; + display: block; + position: absolute; + top: 11px; + right: 3px; + font-size: 6px; + color: #dfdfdf; + } + + &.new { + background: -webkit-linear-gradient(top, #84d7fe, #99e0fe); + color: #333; + + &:after { + color: #99e0fe; + } + } + } + } + } + + .board-drop-btn { + display: block; + height: 60px; + border-bottom: 1px solid #a3a3a3; + border-radius: 3px 0 0 0; + background: -webkit-linear-gradient(top, #ebebeb, #d9d9d9); + font-size: 16px; + font-weight: 700; + line-height: 58px; + text-align: center; + color: #333; + text-shadow: 0 1px 0 rgba(255, 255, 255, .8); + } + + .sort-bar { + height: 27px; + border-bottom: 1px solid #a3a3a3; + background: -webkit-linear-gradient(top, #cdcdcd, #b6b6b6); + box-shadow: 0 1px 0 rgba(255, 255, 255, .4) inset; + + a { + display: block; + float: right; + height: 27px; + margin-right: 10px; + font-size: 11px; + font-weight: bold; + line-height: 23px; + color: #333; + text-shadow: 0 1px 0 rgba(255, 255, 255, .5); + + .sort-label { + font-size: 9px; + text-transform: uppercase; + } + } + } +} + + + + + + + + + + + + +.global-discussion-actions { + height: 60px; + background: -webkit-linear-gradient(top, #ebebeb, #d9d9d9); + border-radius: 0 3px 0 0; + border-bottom: 1px solid #bcbcbc; +} + + + + + + + + + + + +.discussion-article { + position: relative; + display: table-cell; + vertical-align: top; + width: 72.3%; + padding: 40px; + + h1 { + font-size: 28px; + font-weight: 700; + } + + .posted-details { + font-size: 12px; + font-style: italic; + color: #888; + } + + p + p { + margin-top: 20px; + } + + .dogear { + display: block; + position: absolute; + top: 0; + right: -1px; + width: 52px; + height: 51px; + background: url(../images/follow-dog-ear.png) 0 -51px no-repeat; + + &.is-followed { + background-position: 0 0; + } + } +} + +.discussion-post header, +.responses li header { + margin-bottom: 20px; +} + +.responses { + margin-top: 40px; + + > li { + margin: 0 -10px; + padding: 30px; + border-radius: 3px; + border: 1px solid #b2b2b2; + box-shadow: 0 1px 3px rgba(0, 0, 0, .15); + } + + .posted-by { + font-weight: 700; + } +} + +.endorse-btn { + display: block; + float: right; + width: 27px; + height: 27px; + margin-right: 10px; + border-radius: 27px; + border: 1px solid #a0a0a0; + background: -webkit-linear-gradient(top, #fff 35%, #ebebeb); + box-shadow: 0 1px 1px rgba(0, 0, 0, .1); + + .check-icon { + display: block; + width: 13px; + height: 12px; + margin: 8px auto; + background: url(../images/endorse-icon.png) no-repeat; + } + + &.is-endorsed { + border: 1px solid #4697c1; + background: -webkit-linear-gradient(top, #6dccf1, #38a8e5); + box-shadow: 0 1px 1px rgba(0, 0, 0, 0.1), 0 1px 0 rgba(255, 255, 255, .4) inset; + + .check-icon { + background-position: 0 -12px; + } + } +} + +.comments { + margin-top: 20px; + border-top: 1px solid #ddd; + + li { + background: #f6f6f6; + border-bottom: 1px solid #ddd; + } + + p { + font-size: 13px; + padding: 10px 20px; + + .posted-details { + font-size: 11px; + white-space: nowrap; + } + } +} + +.comment-form { + padding: 8px 20px; +} + +.comment-form-input { + width: 100%; + height: 31px; + padding: 0 10px; + box-sizing: border-box; + border: 1px solid #b2b2b2; + border-radius: 3px; + box-shadow: 0 1px 3px rgba(0, 0, 0, .1) inset; + -webkit-transition: border-color .1s; + outline: 0; + + &:focus { + border-color: #4697c1; + } +} + +.moderator-actions { + margin-top: 20px; + @include clearfix; + + li { + float: left; + margin-right: 8px; + } + + a { + display: block; + height: 26px; + padding: 0 12px; + border-radius: 3px; + border: 1px solid #b2b2b2; + background: -webkit-linear-gradient(top, #fff 35%, #ebebeb); + font-size: 13px; + line-height: 24px; + color: #737373; + box-shadow: 0 1px 1px rgba(0, 0, 0, 0.1); + + .delete-icon { + display: block; + float: left; + width: 10px; + height: 10px; + margin: 8px 4px 0 0; + background: url(../images/moderator-delete-icon.png) no-repeat; + } + + .edit-icon { + display: block; + float: left; + width: 10px; + height: 10px; + margin: 7px 4px 0 0; + background: url(../images/moderator-edit-icon.png) no-repeat; + } + } +} diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index 01380faa77..62c56cd921 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -1,14 +1,13 @@ @mixin blue-button { display: block; - height: 33px; - margin: 12px; + height: 35px; padding: 0 15px; border-radius: 3px; - border: 1px solid #4697c1; + border: 1px solid #2d81ad; background: -webkit-linear-gradient(top, #6dccf1, #38a8e5); font-size: 13px; font-weight: 700; - line-height: 30px; + line-height: 32px; color: #fff; text-shadow: 0 1px 0 rgba(0, 0, 0, .4); box-shadow: 0 1px 0 rgba(255, 255, 255, 0.4) inset, 0 1px 1px rgba(0, 0, 0, .15); @@ -19,7 +18,523 @@ } } + + + +body.discussion { + .new-post-btn { + @include blue-button; + } + + .new-post-icon { + display: block; + float: left; + width: 16px; + height: 17px; + margin: 8px 7px 0 0; + background: url(../images/new-post-icon.png) no-repeat; + } +} + .discussion-body { + line-height: 1.4; + + .sidebar { + display: table-cell; + vertical-align: top; + width: 27.7%; + background: #f6f6f6; + border-radius: 3px 0 0 3px; + border-right: 1px solid #bcbcbc; + } + + .browse-search { + display: block; + position: relative; + height: 60px; + border-bottom: 1px solid #a3a3a3; + border-radius: 3px 0 0 0; + + + .browse, + .search { + position: relative; + float: left; + width: 20%; + height: 100%; + background: -webkit-linear-gradient(top, rgba(255, 255, 255, .5), rgba(255, 255, 255, 0)) #dcdcdc; + -webkit-transition: all .2s ease-out; + + &:hover { + background-color: #e9e9e9; + } + + &.is-open { + width: 80%; + } + } + + .browse { + border-radius: 3px 0 0 0; + box-shadow: -1px 0 0 #aaa inset; + + &.is-open { + .board-drop-btn span { + opacity: 1; + } + + .board-drop-icon { + opacity: 0; + } + + &.is-dropped { + .board-drop-btn { + color: #fff; + text-shadow: none; + border-color: #4b4b4b; + } + } + } + + &.is-dropped { + .board-drop-btn { + background-color: #616161; + } + } + + &.is-dropped { + .board-drop-icon { + background-position: 0 -16px; + } + } + } + + .search { + cursor: pointer; + + &.is-open { + cursor: auto; + + .post-search { + padding: 0 10px; + max-width: 1000px; + } + + .post-search-field { + cursor: text; + pointer-events: auto; + + &::-webkit-input-placeholder { + opacity: 1; + } + } + } + } + + .board-drop-btn { + display: block; + position: absolute; + top: -1px; + left: -1px; + z-index: 50; + width: 100%; + height: 100%; + border-radius: 3px 0 0 0; + border: 1px solid transparent; + text-align: center; + overflow: hidden; + + .current-board { + white-space: nowrap; + } + + span { + font-size: 16px; + font-weight: 700; + line-height: 58px; + color: #333; + text-shadow: 0 1px 0 rgba(255, 255, 255, .8); + opacity: 0; + -webkit-transition: opacity .2s; + } + } + + .board-drop-icon { + display: block; + position: absolute; + top: 21px; + left: 50%; + z-index: 100; + width: 29px; + height: 16px; + margin-left: -12px; + background: url(../images/browse-icon.png) no-repeat; + opacity: 1; + -webkit-transition: opacity .2s; + } + + .board-drop-menu { + display: none; + position: absolute; + top: 60px; + left: -1px; + z-index: 9999; + width: 100%; + background: #737373; + border: 1px solid #4b4b4b; + border-radius: 0 0 3px 3px; + + > li:first-child a { + border-top: none; + } + + a { + display: block; + height: 50px; + padding: 0 20px; + border-top: 1px solid #5f5f5f; + font-size: 14px; + font-weight: 700; + line-height: 48px; + color: #fff; + + &:hover { + background-color: #636363; + } + + .unread { + float: right; + padding: 0 5px; + margin-top: 13px; + font-size: 11px; + line-height: 22px; + border-radius: 2px; + background: -webkit-linear-gradient(top, #4c4c4c, #5a5a5a); + } + } + + li li { + a { + padding-left: 44px; + background: url(../images/nested-icon.png) no-repeat 22px 14px; + } + } + + li li li { + a { + padding-left: 68px; + background: url(../images/nested-icon.png) no-repeat 46px 14px; + } + } + } + + .post-search { + width: 100%; + max-width: 30px; + margin: auto; + box-sizing: border-box; + -webkit-transition: all .2s; + } + + .post-search-field { + display: block; + width: 100%; + height: 30px; + padding: 0; + margin: 14px auto; + box-sizing: border-box; + border: 1px solid #acacac; + border-radius: 30px; + box-shadow: 0 1px 3px rgba(0, 0, 0, .1) inset, 0 1px 0 rgba(255, 255, 255, .5); + background: url(../images/search-icon.png) no-repeat 7px center #fff; + font-family: 'Open Sans', sans-serif; + font-weight: 400; + font-size: 13px; + line-height: 20px; + text-indent: 30px; + color: #333; + outline: 0; + cursor: pointer; + pointer-events: none; + -webkit-transition: all .2s ease-out; + + &::-webkit-input-placeholder { + opacity: 0; + -webkit-transition: opacity .2s; + } + + &:focus { + border-color: #4697c1; + } + } + } + + .sort-bar { + height: 27px; + border-bottom: 1px solid #a3a3a3; + background: -webkit-linear-gradient(top, rgba(255, 255, 255, .3), rgba(255, 255, 255, 0)) #aeaeae; + box-shadow: 0 1px 0 rgba(255, 255, 255, .2) inset; + font-size: 9px; + font-weight: bold; + line-height: 25px; + color: #333; + text-transform: uppercase; + text-shadow: 0 1px 0 rgba(255, 255, 255, .4); + + .sort-label { + display: block; + float: left; + margin: 0 10px; + } + + li { + float: left; + margin: 4px 4px 0 0; + } + + a { + display: block; + height: 18px; + padding: 0 9px; + border-radius: 19px; + color: #333; + line-height: 17px; + + &:hover { + background: -webkit-linear-gradient(top, rgba(255, 255, 255, .4), rgba(255, 255, 255, .2)); + } + + &.active { + background: -webkit-linear-gradient(top, rgba(0, 0, 0, .3), rgba(0, 0, 0, 0)) #999; + color: #fff; + text-shadow: 0 -1px 0 rgba(0, 0, 0, .3); + box-shadow: 0 1px 0 rgba(255, 255, 255, 0.2), 0 1px 1px rgba(0, 0, 0, .2) inset; + } + } + } + + .post-list { + background-color: #ddd; + + li:last-child a { + border-bottom: 1px solid #ddd; + } + + a { + position: relative; + display: block; + height: 36px; + padding: 0 10px; + margin-bottom: 1px; + background: #fff; + font-size: 13px; + font-weight: 700; + line-height: 34px; + color: #333; + + &.read .title { + font-weight: 400; + color: #737373; + } + + &.resolved:before { + content: ''; + position: absolute; + top: 12px; + right: 75px; + width: 9px; + height: 8px; + background: url(../images/sidebar-resolved-icons.png) no-repeat; + } + + &.followed:after { + content: ''; + position: absolute; + top: 0; + right: 0; + width: 12px; + height: 12px; + background: url(../images/following-flag.png) no-repeat; + } + + &.active { + background: -webkit-linear-gradient(top, #96e0fd, #61c7fc); + border-color: #4697c1; + box-shadow: 0 1px 0 #4697c1, 0 -1px 0 #4697c1; + + .title { + color: #333; + } + + .votes-count, + .comments-count { + background: -webkit-linear-gradient(top, #3994c7, #4da7d3); + color: #fff; + + &:after { + color: #4da7d3; + } + } + + &.followed:after { + background-position: 0 -12px; + } + + &.resolved:before { + background-position: 0 -8px; + } + } + } + + .title { + display: block; + float: left; + width: 70%; + white-space: nowrap; + text-overflow: ellipsis; + overflow: hidden; + } + + .votes-count, + .comments-count { + display: block; + float: right; + width: 32px; + height: 16px; + margin-top: 9px; + border-radius: 2px; + background: -webkit-linear-gradient(top, #d4d4d4, #dfdfdf); + font-size: 9px; + font-weight: 700; + line-height: 16px; + text-align: center; + color: #767676; + } + + .comments-count { + position: relative; + width: 25px; + margin-left: 4px; + + &:after { + content: '◥'; + display: block; + position: absolute; + top: 11px; + right: 3px; + font-size: 6px; + color: #dfdfdf; + } + + &.new { + background: -webkit-linear-gradient(top, #84d7fe, #99e0fe); + color: #333; + + &:after { + color: #99e0fe; + } + } + } + } + + + + + .discussion-column { + display: table-cell; + vertical-align: top; + width: 72.3%; + } + + .discussion-article { + position: relative; + padding: 40px; + + h1 { + margin-bottom: 10px; + font-size: 28px; + font-weight: 700; + line-height: 1.2; + } + + .posted-details { + font-size: 12px; + font-style: italic; + color: #888; + } + + p + p { + margin-top: 20px; + } + + .dogear { + display: block; + position: absolute; + top: -1px; + right: -1px; + width: 52px; + height: 51px; + background: url(../images/follow-dog-ear.png) 0 -52px no-repeat; + @include transition(none); + + &.is-followed { + background-position: 0 0; + } + } + } + + .discussion-post { + padding: 10px 20px; + + > header .vote-btn { + margin-top: 5px; + } + } + + .discussion-post header, + .responses li header { + margin-bottom: 20px; + } + + .responses { + list-style: none; + margin-top: 40px; + padding: 0; + + > li { + position: relative; + margin: 0 -10px 30px; + padding: 26px 30px 30px; + border-radius: 3px; + border: 1px solid #b2b2b2; + box-shadow: 0 1px 3px rgba(0, 0, 0, .15); + + &.staff { + padding-top: 38px; + border-color: #009fe2; + } + + .staff-banner { + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 14px; + padding: 1px 5px; + box-sizing: border-box; + border-radius: 2px 2px 0 0; + background: #009fe2; + font-size: 9px; + font-weight: 700; + color: #fff; + text-transform: uppercase; + } + } + + .posted-by { + font-weight: 700; + } + } .vote-btn { float: right; @@ -37,9 +552,15 @@ .plus-icon { float: left; - margin-right: 6px; + display: block; + width: 10px; + height: 10px; + margin: 8px 6px 0 0; + background: url(../images/vote-plus-icon.png) no-repeat; font-size: 18px; + text-indent: -9999px; color: #17b429; + overflow: hidden; } &.is-cast { @@ -50,233 +571,203 @@ box-shadow: 0 1px 0 rgba(255, 255, 255, .4) inset, 0 1px 2px rgba(0, 0, 0, .2); .plus-icon { + background-position: 0 -10px; color: #336a39; text-shadow: 0 1px 0 rgba(255, 255, 255, .4); } } } - - .new-post-btn { - @include blue-button; - float: right; - } - - .new-post-icon { + .endorse-btn { display: block; - float: left; - width: 16px; - height: 17px; - margin: 7px 7px 0 0; - background: url(../images/new-post-icon.png) no-repeat; - } - - .post-search { float: right; + width: 27px; + height: 27px; + margin-right: 10px; + border-radius: 27px; + border: 1px solid #a0a0a0; + background: -webkit-linear-gradient(top, #fff 35%, #ebebeb); + box-shadow: 0 1px 1px rgba(0, 0, 0, .1); + + .check-icon { + display: block; + width: 13px; + height: 12px; + margin: 8px auto; + background: url(../images/endorse-icon.png) no-repeat; + } + + &.is-endorsed { + border: 1px solid #4697c1; + background: -webkit-linear-gradient(top, #6dccf1, #38a8e5); + box-shadow: 0 1px 1px rgba(0, 0, 0, 0.1), 0 1px 0 rgba(255, 255, 255, .4) inset; + + .check-icon { + background-position: 0 -12px; + } + } } - .post-search-field { - width: 280px; - height: 30px; - padding: 0 15px 0 30px; - margin-top: 14px; - border: 1px solid #acacac; - border-radius: 30px; - box-shadow: 0 1px 3px rgba(0, 0, 0, .1) inset, 0 1px 0 rgba(255, 255, 255, .5); - background: url(../images/search-icon.png) no-repeat 8px center #fff; - font-family: 'Open Sans', sans-serif; - font-weight: 400; - font-size: 13px; - line-height: 30px; - color: #333; - outline: 0; + .comments { + list-style: none; + margin-top: 20px; + padding: 0; + border-top: 1px solid #ddd; + + li { + background: #f6f6f6; + border-bottom: 1px solid #ddd; + + &.new-comment-form { + background: #eee; + } + } + + p { + font-size: 13px; + padding: 10px 20px; + + .posted-details { + font-size: 11px; + white-space: nowrap; + } + } + + .staff-label { + margin-left: 2px; + padding: 0 4px; + border-radius: 2px; + background: #009FE2; + font-size: 9px; + font-weight: 700; + font-style: normal; + color: white; + text-transform: uppercase; + } + } + + .comment-form { + padding: 8px 20px; + } + + .comment-form-input { + width: 100%; + height: 31px; + padding: 0 10px; + box-sizing: border-box; + border: 1px solid #b2b2b2; + border-radius: 3px; + box-shadow: 0 1px 3px rgba(0, 0, 0, .1) inset; -webkit-transition: border-color .1s; + outline: 0; &:focus { border-color: #4697c1; } } - h1, ul, li, a, ol { - margin: 0; - padding: 0; - border: 0; - outline: 0; - font-size: 100%; - font: inherit; - vertical-align: baseline; - } - ul, li { - list-style-type: none; - } - a { - text-decoration: none; - color: #009fe2; - } + .moderator-actions { + margin-top: 20px; + @include clearfix; - display: table; - table-layout: fixed; - width: 100%; - height: 500px; - background: #fff; - border-radius: 3px; - border: 1px solid #aaa; - box-shadow: 0 1px 2px rgba(0, 0, 0, 0.05); - - .sidebar { - display: table-cell; - vertical-align: top; - width: 27.7%; - background: #f6f6f6; - border-radius: 3px 0 0 3px; - border-right: 1px solid #bcbcbc; - .post-list { - background-color: #ddd; - - li:last-child a { - border-bottom: 1px solid #ddd; - } - - a { - position: relative; - display: block; - height: 36px; - padding: 0 10px; - margin-bottom: 1px; - background: #fff; - font-size: 13px; - font-weight: 700; - line-height: 34px; - color: #333; - - &.read .title { - font-weight: 400; - color: #737373; - } - - &.followed:after { - content: ''; - position: absolute; - top: 0; - right: 0; - width: 12px; - height: 12px; - background: url(../images/following-flag.png) no-repeat; - } - - &.active { - background: -webkit-linear-gradient(top, #96e0fd, #61c7fc); - border-color: #4697c1; - box-shadow: 0 1px 0 #4697c1, 0 -1px 0 #4697c1; - - .title { - color: #333; - } - - .votes-count, - .comments-count { - background: -webkit-linear-gradient(top, #3994c7, #4da7d3); - color: #fff; - - &:after { - color: #4da7d3; - } - } - - &.followed:after { - background-position: 0 -12px; - } - } - } - - .title { - display: block; - float: left; - width: 70%; - white-space: nowrap; - text-overflow: ellipsis; - overflow: hidden; - } - - .votes-count, - .comments-count { - display: block; - float: right; - width: 32px; - height: 16px; - margin-top: 9px; - border-radius: 2px; - background: -webkit-linear-gradient(top, #d4d4d4, #dfdfdf); - font-size: 9px; - font-weight: 700; - line-height: 16px; - text-align: center; - color: #767676; - } - - .comments-count { - position: relative; - margin-left: 4px; - - &:after { - content: '◥'; - display: block; - position: absolute; - top: 11px; - right: 3px; - font-size: 6px; - color: #dfdfdf; - } - - &.new { - background: -webkit-linear-gradient(top, #84d7fe, #99e0fe); - color: #333; - - &:after { - color: #99e0fe; - } - } - } + li { + float: left; + margin-right: 8px; } - } - - .board-drop-btn { - display: block; - height: 60px; - border-bottom: 1px solid #a3a3a3; - border-radius: 3px 0 0 0; - background: -webkit-linear-gradient(top, #ebebeb, #d9d9d9); - font-size: 16px; - font-weight: 700; - line-height: 58px; - text-align: center; - color: #333; - text-shadow: 0 1px 0 rgba(255, 255, 255, .8); - } - - .sort-bar { - height: 27px; - border-bottom: 1px solid #a3a3a3; - background: -webkit-linear-gradient(top, #cdcdcd, #b6b6b6); - box-shadow: 0 1px 0 rgba(255, 255, 255, .4) inset; a { display: block; - float: right; - height: 27px; - margin-right: 10px; - font-size: 11px; - font-weight: bold; - line-height: 23px; - color: #333; - text-shadow: 0 1px 0 rgba(255, 255, 255, .5); + height: 26px; + padding: 0 12px; + border-radius: 3px; + border: 1px solid #b2b2b2; + background: -webkit-linear-gradient(top, #fff 35%, #ebebeb); + font-size: 13px; + line-height: 24px; + color: #737373; + box-shadow: 0 1px 1px rgba(0, 0, 0, 0.1); - .sort-label { - font-size: 9px; - text-transform: uppercase; + .delete-icon { + display: block; + float: left; + width: 10px; + height: 10px; + margin: 8px 4px 0 0; + background: url(../images/moderator-delete-icon.png) no-repeat; + } + + .edit-icon { + display: block; + float: left; + width: 10px; + height: 10px; + margin: 7px 4px 0 0; + background: url(../images/moderator-edit-icon.png) no-repeat; } } } + + + + + + .tooltip { + position: absolute; + top: 0; + left: 0; + z-index: 99999; + padding: 0 10px; + border-radius: 3px; + background: rgba(0, 0, 0, .85); + font-size: 11px; + font-weight: 400; + line-height: 26px; + color: #fff; + pointer-events: none; + opacity: 0; + -webkit-transition: opacity .1s; + + &:after { + content: '▾'; + display: block; + position: absolute; + bottom: -14px; + left: 50%; + margin-left: -7px; + font-size: 20px; + color: rgba(0, 0, 0, .85); + } + } + + + + + .main-article.new { + display: none; + padding: 50px; + } + + .new-post-form { + margin-top: 20px; + @include clearfix; + } + + .new-post-form .submit { + @include blue-button; + float: left; + margin-top: 10px; + padding-bottom: 2px; + } + + .new-post-form .options { + float: right; + margin-top: 20px; + font-size: 14px; + + label { + margin-left: 4px; + } + } } @@ -288,8 +779,6 @@ - - .global-discussion-actions { height: 60px; background: -webkit-linear-gradient(top, #ebebeb, #d9d9d9); @@ -307,171 +796,11 @@ -.discussion-article { - position: relative; - display: table-cell; - vertical-align: top; - width: 72.3%; - padding: 40px; - h1 { - font-size: 28px; - font-weight: 700; - } - .posted-details { - font-size: 12px; - font-style: italic; - color: #888; - } - p + p { - margin-top: 20px; - } - .dogear { - display: block; - position: absolute; - top: 0; - right: -1px; - width: 52px; - height: 51px; - background: url(../images/follow-dog-ear.png) 0 -51px no-repeat; - &.is-followed { - background-position: 0 0; - } - } -} -.discussion-post header, -.responses li header { - margin-bottom: 20px; -} -.responses { - margin-top: 40px; - > li { - margin: 0 -10px; - padding: 30px; - border-radius: 3px; - border: 1px solid #b2b2b2; - box-shadow: 0 1px 3px rgba(0, 0, 0, .15); - } - - .posted-by { - font-weight: 700; - } -} - -.endorse-btn { - display: block; - float: right; - width: 27px; - height: 27px; - margin-right: 10px; - border-radius: 27px; - border: 1px solid #a0a0a0; - background: -webkit-linear-gradient(top, #fff 35%, #ebebeb); - box-shadow: 0 1px 1px rgba(0, 0, 0, .1); - - .check-icon { - display: block; - width: 13px; - height: 12px; - margin: 8px auto; - background: url(../images/endorse-icon.png) no-repeat; - } - - &.is-endorsed { - border: 1px solid #4697c1; - background: -webkit-linear-gradient(top, #6dccf1, #38a8e5); - box-shadow: 0 1px 1px rgba(0, 0, 0, 0.1), 0 1px 0 rgba(255, 255, 255, .4) inset; - - .check-icon { - background-position: 0 -12px; - } - } -} - -.comments { - margin-top: 20px; - border-top: 1px solid #ddd; - - li { - background: #f6f6f6; - border-bottom: 1px solid #ddd; - } - - p { - font-size: 13px; - padding: 10px 20px; - - .posted-details { - font-size: 11px; - white-space: nowrap; - } - } -} - -.comment-form { - padding: 8px 20px; -} - -.comment-form-input { - width: 100%; - height: 31px; - padding: 0 10px; - box-sizing: border-box; - border: 1px solid #b2b2b2; - border-radius: 3px; - box-shadow: 0 1px 3px rgba(0, 0, 0, .1) inset; - -webkit-transition: border-color .1s; - outline: 0; - - &:focus { - border-color: #4697c1; - } -} - -.moderator-actions { - margin-top: 20px; - @include clearfix; - - li { - float: left; - margin-right: 8px; - } - - a { - display: block; - height: 26px; - padding: 0 12px; - border-radius: 3px; - border: 1px solid #b2b2b2; - background: -webkit-linear-gradient(top, #fff 35%, #ebebeb); - font-size: 13px; - line-height: 24px; - color: #737373; - box-shadow: 0 1px 1px rgba(0, 0, 0, 0.1); - - .delete-icon { - display: block; - float: left; - width: 10px; - height: 10px; - margin: 8px 4px 0 0; - background: url(../images/moderator-delete-icon.png) no-repeat; - } - - .edit-icon { - display: block; - float: left; - width: 10px; - height: 10px; - margin: 7px 4px 0 0; - background: url(../images/moderator-edit-icon.png) no-repeat; - } - } -} diff --git a/lms/static/sass/base/_base.scss b/lms/static/sass/base/_base.scss index ba0f47de52..ee46c08361 100644 --- a/lms/static/sass/base/_base.scss +++ b/lms/static/sass/base/_base.scss @@ -43,6 +43,7 @@ p { span { font: normal 1em/1.6em $sans-serif; } + /* Fix for CodeMirror: prevent top-level span from affecting deeply-embedded span in CodeMirror */ .CodeMirror span { font: inherit; diff --git a/lms/templates/discussion/single_thread.html b/lms/templates/discussion/single_thread.html index 59882a2443..757b33cf3a 100644 --- a/lms/templates/discussion/single_thread.html +++ b/lms/templates/discussion/single_thread.html @@ -17,16 +17,49 @@ <%include file="../courseware/course_navigation.html" args="active_page='discussion'" /> + +
-
+
+
    +
    +
    + Submit +
    From 1559b86e2788a562471931ac4134da1714daf3c3 Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 30 Aug 2012 11:37:50 -0400 Subject: [PATCH 022/364] added new post markup, style and basic interactions --- lms/static/images/new-post-icons.png | Bin 0 -> 4118 bytes lms/static/js/discussions-temp.js | 44 ++++ lms/static/sass/_discussion.scss | 218 ++++++++++++++++++++ lms/templates/discussion/single_thread.html | 50 +++++ 4 files changed, 312 insertions(+) create mode 100644 lms/static/images/new-post-icons.png diff --git a/lms/static/images/new-post-icons.png b/lms/static/images/new-post-icons.png new file mode 100644 index 0000000000000000000000000000000000000000..9a916c05f22a2910a90b81d2dae556fd9d067143 GIT binary patch literal 4118 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 literal 0 HcmV?d00001 diff --git a/lms/static/js/discussions-temp.js b/lms/static/js/discussions-temp.js index b7fcf5b6ac..d740c82fc4 100644 --- a/lms/static/js/discussions-temp.js +++ b/lms/static/js/discussions-temp.js @@ -9,6 +9,8 @@ var $newPost; var $thread; var $sidebar; var $sidebarWidthStyles; +var $formTopicDropBtn; +var $formTopicDropMenu; var sidebarWidth; var tooltipTimer; var tooltipCoords; @@ -22,7 +24,10 @@ $(document).ready(function() { $topicDrop = $('.board-drop-menu'); $currentBoard = $('.current-board'); $tooltip = $('
    '); + $newPost = $('.new-post-article'); $sidebar = $('.sidebar'); + $formTopicDropBtn = $('.new-post-article .topic-drop-btn'); + $formTopicDropMenu = $('.new-post-article .topic-drop-menu'); $sidebarWidthStyles = $(''); $body.append($sidebarWidthStyles); @@ -31,6 +36,9 @@ $(document).ready(function() { $browse.bind('click', showTopicDrop); $search.bind('click', showSearch); $topicDrop.bind('click', setTopic); + $formTopicDropBtn.bind('click', showFormTopicDrop); + $formTopicDropMenu.bind('click', setFormTopic); + $('.new-post-btn').bind('click', newPost); $('[data-tooltip]').bind({ 'mouseover': showTooltip, @@ -145,4 +153,40 @@ function updateSidebarWidth(e) { var titleWidth = sidebarWidth - 115; console.log(titleWidth); $sidebarWidthStyles.html('.discussion-body .post-list a .title { width: ' + titleWidth + 'px !important; }'); +} + +function newPost(e) { + $newPost.slideDown(300); +} + +function showFormTopicDrop(e) { + $formTopicDropBtn.addClass('is-dropped'); + $formTopicDropMenu.show(); + $formTopicDropBtn.unbind('click', showFormTopicDrop); + $formTopicDropBtn.bind('click', hideFormTopicDrop); + + setTimeout(function() { + $body.bind('click', hideFormTopicDrop); + }, 0); + +} + +function hideFormTopicDrop(e) { + $formTopicDropBtn.removeClass('is-dropped'); + $formTopicDropMenu.hide(); + $body.unbind('click', hideFormTopicDrop); + $formTopicDropBtn.unbind('click', hideFormTopicDrop); + $formTopicDropBtn.bind('click', showFormTopicDrop); +} + +function setFormTopic(e) { + $formTopicDropBtn.removeClass('is-dropped'); + hideFormTopicDrop(); + + var $item = $(e.target); + var boardName = $item.html(); + $item.parents('ul').not('.topic-drop-menu').each(function(i) { + boardName = $(this).siblings('a').html() + ' / ' + boardName; + }); + $formTopicDropBtn.html(boardName + ' '); } \ No newline at end of file diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index d3b7e7ef56..b842dbe6eb 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -18,6 +18,25 @@ } } +@mixin white-button { + display: block; + height: 35px; + padding: 0 15px; + border-radius: 3px; + border: 1px solid #444; + background: -webkit-linear-gradient(top, #eee, #ccc); + font-size: 13px; + font-weight: 700; + line-height: 32px; + color: #333; + text-shadow: 0 1px 0 rgba(255, 255, 255, 0.6); + box-shadow: 0 1px 0 rgba(255, 255, 255, 0.4) inset, 0 1px 1px rgba(0, 0, 0, .15); + + &:hover { + background: -webkit-linear-gradient(top, #fff, #ddd); + } +} + @@ -39,6 +58,205 @@ body.discussion { background: url(../images/new-post-icon.png) no-repeat; } } + + .new-post-article { + display: none; + margin-top: 20px; + + .inner-wrapper { + max-width: 1180px; + min-width: 760px; + margin: auto; + } + + .left-column { + float: left; + width: 32%; + padding: 40px; + box-sizing: border-box; + + label { + font-size: 22px; + font-weight: 700; + color: #fff; + text-shadow: none; + } + + .topic-drop { + position: relative; + + ul { + list-style: none; + margin: 0; + padding: 0; + } + } + + .topic-drop-btn { + position: relative; + z-index: 10000; + @include white-button; + height: 40px; + margin-top: 15px; + line-height: 36px; + + .drop-arrow { + float: right; + color: #999; + line-height: 36px; + } + } + + .topic-drop-menu { + display: none; + position: absolute; + top: 40px; + left: 0; + z-index: 9999; + width: 100%; + box-sizing: border-box; + background: #737373; + border: 1px solid #333; + box-shadow: 0 2px 50px rgba(0, 0, 0, .4); + + a { + display: block; + padding: 10px 15px; + border-top: 1px solid #5f5f5f; + font-size: 14px; + font-weight: 700; + color: #eee; + + &:hover { + background-color: #666; + } + } + + li li { + a { + padding-left: 39px; + background: url(../images/nested-icon.png) no-repeat 17px 10px; + } + } + + li li li { + a { + padding-left: 63px; + background: url(../images/nested-icon.png) no-repeat 41px 10px; + } + } + } + } + + .right-column { + float: left; + width: 68%; + padding: 40px; + box-sizing: border-box; + } + } + + .new-post-form { + width: 100%; + margin-bottom: 20px; + border-radius: 3px; + background: rgba(0, 0, 0, .55); + color: #fff; + box-shadow: 0 1px 2px rgba(0, 0, 0, .5) inset, 0 1px 0 rgba(255, 255, 255, .5); + @include clearfix; + + .form-row { + margin-bottom: 20px; + } + + .new-post-body { + position: relative; + width: 100%; + height: 200px; + z-index: 1; + padding: 10px; + box-sizing: border-box; + border: 1px solid #333; + border-radius: 3px 3px 0 0; + background: #fff; + font-family: 'Monaco', monospace; + font-size: 13px; + line-height: 1.6; + box-shadow: 0 1px 3px rgba(0, 0, 0, 0.3) inset; + } + + .new-post-preview { + position: relative; + width: 100%; + height: 50px; + margin-top: -1px; + padding: 10px; + box-sizing: border-box; + border: 1px solid #333; + border-radius: 0 0 3px 3px; + background: #e6e6e6; + color: #333; + box-shadow: 0 1px 3px rgba(0, 0, 0, 0.3) inset; + } + + .new-post-preview-label { + position: absolute; + top: 4px; + left: 4px; + font-size: 11px; + color: #aaa; + text-transform: uppercase; + } + + .new-post-title, + .new-post-tags { + width: 100%; + height: 40px; + padding: 0 10px; + box-sizing: border-box; + border-radius: 3px; + border: 1px solid #333; + font-size: 16px; + font-family: 'Open Sans', sans-serif; + color: #333; + box-shadow: 0 1px 3px rgba(0, 0, 0, 0.3) inset; + } + + .new-post-title { + font-weight: 700; + } + + .submit { + @include blue-button; + float: left; + height: 37px; + margin-top: 10px; + padding-bottom: 2px; + border-color: #333; + + &:hover { + border-color: #222; + } + } + + .new-post-cancel { + @include white-button; + float: left; + margin: 10px 0 0 15px; + } + + .options { + margin-top: 40px; + + label { + display: inline; + margin-left: 8px; + font-size: 15px; + color: #fff; + text-shadow: none; + } + } + } } .discussion-body { diff --git a/lms/templates/discussion/single_thread.html b/lms/templates/discussion/single_thread.html index 38c742e221..75edb281e5 100644 --- a/lms/templates/discussion/single_thread.html +++ b/lms/templates/discussion/single_thread.html @@ -52,6 +52,56 @@
    + +
    - -
    - + <%include file="_filter_dropdown.html" /> - \ No newline at end of file + From f6ca91a5045bae21975c0533d19b5e7d700dcefe Mon Sep 17 00:00:00 2001 From: Ibrahim Awwal Date: Fri, 31 Aug 2012 23:42:32 -0700 Subject: [PATCH 049/364] Refactor some things more and make the forum index sort of work, although the sticky sidebar is broken, probably because there's no content in the thread view pane. --- .../django_comment_client/forum/views.py | 19 ++++--- .../coffee/src/discussion/discussion.coffee | 1 - lms/static/coffee/src/discussion/main.coffee | 16 ++++++ lms/static/coffee/src/discussion/utils.coffee | 7 --- lms/templates/discussion/index.html | 55 ++++--------------- lms/templates/discussion/single_thread.html | 18 +----- 6 files changed, 41 insertions(+), 75 deletions(-) diff --git a/lms/djangoapps/django_comment_client/forum/views.py b/lms/djangoapps/django_comment_client/forum/views.py index 98ca7b1f7d..77883ae898 100644 --- a/lms/djangoapps/django_comment_client/forum/views.py +++ b/lms/djangoapps/django_comment_client/forum/views.py @@ -18,7 +18,7 @@ from django_comment_client.utils import merge_dict, extract, strip_none, strip_b import json import django_comment_client.utils as utils import comment_client as cc - +import xml.sax.saxutils as saxutils THREADS_PER_PAGE = 50000 PAGES_NEARBY_DELTA = 2 @@ -143,9 +143,10 @@ def render_search_bar(request, course_id, discussion_id=None, text=''): def forum_form_discussion(request, course_id): course = get_course_with_access(request.user, course_id, 'load') + category_map = utils.get_discussion_category_map(course) threads, query_params = get_threads(request, course_id) content = render_forum_discussion(request, course_id, threads, discussion_id=_general_discussion_id(course_id), query_params=query_params) - + user_info = cc.User.from_django_user(request.user).to_dict() if request.is_ajax(): return utils.JsonResponse({ 'html': content, @@ -161,6 +162,7 @@ def forum_form_discussion(request, course_id): trending_tags = cc.search_trending_tags( course_id, ) + escapedict = {'"': '"'} context = { 'csrf': csrf(request)['csrf_token'], 'course': course, @@ -168,7 +170,10 @@ def forum_form_discussion(request, course_id): 'recent_active_threads': recent_active_threads, 'trending_tags': trending_tags, 'staff_access' : has_access(request.user, course, 'staff'), - 'threads': threads, + 'threads': saxutils.escape(json.dumps(threads),escapedict), + 'user_info': saxutils.escape(json.dumps(user_info),escapedict), + 'course_id': course.id, + 'category_map': category_map, } # print "start rendering.." return render_to_response('discussion/index.html', context) @@ -197,7 +202,7 @@ def render_single_thread(request, discussion_id, course_id, thread_id): def single_thread(request, course_id, discussion_id, thread_id): if request.is_ajax(): - + user_info = cc.User.from_django_user(request.user).to_dict() thread = cc.Thread.find(thread_id).retrieve(recursive=True) annotated_content_info = utils.get_annotated_content_infos(course_id, thread, request.user, user_info=user_info) @@ -226,19 +231,19 @@ def single_thread(request, course_id, discussion_id, thread_id): ) user_info = cc.User.from_django_user(request.user).to_dict() - + escapedict = {'"': '"'} context = { 'discussion_id': discussion_id, 'csrf': csrf(request)['csrf_token'], 'init': '', - 'user_info': json.dumps(user_info), + 'user_info': saxutils.escape(json.dumps(user_info),escapedict), 'content': render_single_thread(request, discussion_id, course_id, thread_id), 'course': course, 'recent_active_threads': recent_active_threads, 'trending_tags': trending_tags, 'course_id': course.id, 'thread_id': thread_id, - 'threads': json.dumps(threads), + 'threads': saxutils.escape(json.dumps(threads), escapedict), 'category_map': category_map, } diff --git a/lms/static/coffee/src/discussion/discussion.coffee b/lms/static/coffee/src/discussion/discussion.coffee index bb7a405840..0737aaed0c 100644 --- a/lms/static/coffee/src/discussion/discussion.coffee +++ b/lms/static/coffee/src/discussion/discussion.coffee @@ -3,7 +3,6 @@ if Backbone? model: Thread initialize: -> - DiscussionUtil.addDiscussion @id, @ @bind "add", (item) => item.discussion = @ @comparator = @sortByDate diff --git a/lms/static/coffee/src/discussion/main.coffee b/lms/static/coffee/src/discussion/main.coffee index e69de29bb2..e1f651ddb2 100644 --- a/lms/static/coffee/src/discussion/main.coffee +++ b/lms/static/coffee/src/discussion/main.coffee @@ -0,0 +1,16 @@ +DiscussionApp = + start: (elem)-> + # TODO: Perhaps eliminate usage of global variables when possible + element = $(elem) + window.$$contents = {} + window.$$course_id = element.data("course-id") + user_info = element.data("user-info") + threads = element.data("threads") + window.user = new DiscussionUser(user_info) + discussion = new Discussion(threads) + new DiscussionRouter({discussion: discussion}) + Backbone.history.start({pushState: true, root: "/courses/#{$$course_id}/discussion/forum/"}) + +$ -> + $("section.discussion").each (index, elem) -> + DiscussionApp.start(elem) diff --git a/lms/static/coffee/src/discussion/utils.coffee b/lms/static/coffee/src/discussion/utils.coffee index 0990f0c87c..1c6fe2590e 100644 --- a/lms/static/coffee/src/discussion/utils.coffee +++ b/lms/static/coffee/src/discussion/utils.coffee @@ -13,16 +13,9 @@ class @DiscussionUtil @getTemplate: (id) -> $("script##{id}").html() - @getDiscussionData: (id) -> - return $$discussion_data[id] - @addContent: (id, content) -> window.$$contents[id] = content @getContent: (id) -> window.$$contents[id] - - @addDiscussion: (id, discussion) -> window.$$discussions[id] = discussion - - @getDiscussion: (id) -> window.$$discussions[id] @bulkUpdateContentInfo: (infos) -> for id, info of infos diff --git a/lms/templates/discussion/index.html b/lms/templates/discussion/index.html index 948fa8dd9d..ed8cb765f2 100644 --- a/lms/templates/discussion/index.html +++ b/lms/templates/discussion/index.html @@ -1,4 +1,7 @@ <%! import django_comment_client.helpers as helpers %> +<%! from django.template.defaultfilters import escapejs %> +<%! from django.core.urlresolvers import reverse %> + <%inherit file="../main.html" /> <%namespace name='static' file='../static_content.html'/> <%block name="bodyclass">discussion @@ -16,51 +19,15 @@ <%include file="../courseware/course_navigation.html" args="active_page='discussion'" /> +<%include file="_new_post.html" /> -
    -
    - -
    - This page intentionally left blank -
    -
    + +
    +
    + +
    +
    -
    -
    -
    - -
    - -
    - ${content.decode('utf-8')} -
    -
    -
    +<%include file="_underscore_templates.html" /> \ No newline at end of file diff --git a/lms/templates/discussion/single_thread.html b/lms/templates/discussion/single_thread.html index cab4502dcf..84767eabb3 100644 --- a/lms/templates/discussion/single_thread.html +++ b/lms/templates/discussion/single_thread.html @@ -18,21 +18,7 @@ <%static:js group='discussion'/> @@ -71,11 +57,11 @@ <%include file="_new_post.html" /> -
    +
    -
    +
    <%include file="_underscore_templates.html" /> From 8d3a70df46d8772e67d920993a04e68a7f7e7210 Mon Sep 17 00:00:00 2001 From: Ibrahim Awwal Date: Fri, 31 Aug 2012 23:44:32 -0700 Subject: [PATCH 050/364] Remove empty script tag. --- lms/templates/discussion/single_thread.html | 2 -- 1 file changed, 2 deletions(-) diff --git a/lms/templates/discussion/single_thread.html b/lms/templates/discussion/single_thread.html index 84767eabb3..ee1ef9c269 100644 --- a/lms/templates/discussion/single_thread.html +++ b/lms/templates/discussion/single_thread.html @@ -17,9 +17,7 @@ <%include file="_js_body_dependencies.html" /> <%static:js group='discussion'/> -
    + + ## For now, ocw links are the only thing that goes in additional resources + % if get_course_about_section(course, "ocw_links"):

    Additional Resources

    @@ -159,13 +162,10 @@

    MITOpenCourseware

    - + ${get_course_about_section(course, "ocw_links")}
    + %endif From a152041ef80de936541be7947f70d97ffc256fdd Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 13 Sep 2012 10:25:10 -0400 Subject: [PATCH 282/364] fixed inline thread replace error --- .../src/discussion/views/discussion_thread_show_view.coffee | 3 ++- lms/templates/discussion/mustache/_inline_thread.mustache | 4 ++-- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_show_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_show_view.coffee index 17a852e8a5..8bb01196d0 100644 --- a/lms/static/coffee/src/discussion/views/discussion_thread_show_view.coffee +++ b/lms/static/coffee/src/discussion/views/discussion_thread_show_view.coffee @@ -125,7 +125,8 @@ class @DiscussionThreadShowView extends DiscussionContentView @model.set('endorsed', not endorsed) highlight: (el) -> - el.html(el.html().replace(/<mark>/g, "").replace(/<\/mark>/g, "")) + if el.html() + el.html(el.html().replace(/<mark>/g, "").replace(/<\/mark>/g, "")) class @DiscussionThreadInlineShowView extends DiscussionThreadShowView renderTemplate: -> diff --git a/lms/templates/discussion/mustache/_inline_thread.mustache b/lms/templates/discussion/mustache/_inline_thread.mustache index a874b728ce..743e06ba9d 100644 --- a/lms/templates/discussion/mustache/_inline_thread.mustache +++ b/lms/templates/discussion/mustache/_inline_thread.mustache @@ -6,10 +6,10 @@

    {{title}}

    {{#user}} - {{username}} + {{username}} {{/user}} {{^user}} - anonymous + anonymous {{/user}} {{created_at}} From 3496e4ee056b592b0a9374210323dac32cd5a530 Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 13 Sep 2012 10:47:50 -0400 Subject: [PATCH 283/364] added sidebar load more styles --- lms/static/sass/_discussion.scss | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index 090e5eecf2..83ebcc9301 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -1034,6 +1034,18 @@ body.discussion { } } + .more a { + background: #eee; + font-size: 12px; + line-height: 33px; + text-align: center; + + &:hover { + background-image: none; + background-color: #e6e6e6; + } + } + a { position: relative; display: block; From 6e217b315d94a840c864ba3ca408ca74d52165fa Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 13 Sep 2012 10:59:47 -0400 Subject: [PATCH 284/364] added conditional to render tags wrapper only if there are tags --- .../coffee/src/discussion/views/discussion_thread_view.coffee | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee index 756864d319..49e55f0c5b 100644 --- a/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee +++ b/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee @@ -34,8 +34,10 @@ if Backbone? @responsesRequest.abort() renderTags: -> - tags = $('

    ') + tags for tag in @model.get("tags") + if !tags + tags = $('
    ') tags.append("#{tag}") @$(".post-body").after(tags) From cb1db861002b6fa022e740fa66797eb022b973f6 Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 13 Sep 2012 11:01:42 -0400 Subject: [PATCH 285/364] additional margins for thread-tags --- lms/static/sass/_discussion.scss | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index 83ebcc9301..6802c3bf17 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -1997,7 +1997,7 @@ body.discussion { } .thread-tags { - margin-top: 20px; + margin: 20px 0; } .thread-tag { @@ -2299,7 +2299,7 @@ body.discussion { } } .thread-tags { - margin-top: 20px; + margin: 20px 0; } .thread-tag { From a55f37cd9dde8419c4dbfb786658923c6f9e0328 Mon Sep 17 00:00:00 2001 From: kimth Date: Thu, 13 Sep 2012 11:04:37 -0400 Subject: [PATCH 286/364] Problem js runs MathJax only over its own contents rather than full page --- common/lib/xmodule/xmodule/js/src/capa/display.coffee | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/common/lib/xmodule/xmodule/js/src/capa/display.coffee b/common/lib/xmodule/xmodule/js/src/capa/display.coffee index 54ffd4dafa..c152c382ff 100644 --- a/common/lib/xmodule/xmodule/js/src/capa/display.coffee +++ b/common/lib/xmodule/xmodule/js/src/capa/display.coffee @@ -11,7 +11,8 @@ class @Problem $(selector, @el) bind: => - MathJax.Hub.Queue ["Typeset", MathJax.Hub] + @el.find('.problem > div').each (index, element) => + MathJax.Hub.Queue ["Typeset", MathJax.Hub, element] window.update_schematics() @@ -267,7 +268,9 @@ class @Problem showMethod = @inputtypeShowAnswerMethods[cls] showMethod(inputtype, display, answers) if showMethod? - MathJax.Hub.Queue ["Typeset", MathJax.Hub] + @el.find('.problem > div').each (index, element) => + MathJax.Hub.Queue ["Typeset", MathJax.Hub, element] + @$('.show').val 'Hide Answer' @el.addClass 'showed' @updateProgress response From d2d1ac71fe5510af61b788491aa0c31871388944 Mon Sep 17 00:00:00 2001 From: kimth Date: Thu, 13 Sep 2012 11:12:41 -0400 Subject: [PATCH 287/364] Use Coffeescript existential operator --- common/lib/xmodule/xmodule/js/src/capa/display.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/common/lib/xmodule/xmodule/js/src/capa/display.coffee b/common/lib/xmodule/xmodule/js/src/capa/display.coffee index c152c382ff..7376418dff 100644 --- a/common/lib/xmodule/xmodule/js/src/capa/display.coffee +++ b/common/lib/xmodule/xmodule/js/src/capa/display.coffee @@ -344,7 +344,7 @@ class @Problem preprocessorClassName = data.data('preprocessor') preprocessorClass = window[preprocessorClassName] - if typeof(preprocessorClass) == 'undefined' + if not preprocessorClass? return false else preprocessor = new preprocessorClass() From ffd60fbd7e1e66db1a943bd15ed1aa233dfdfde7 Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 13 Sep 2012 11:19:57 -0400 Subject: [PATCH 288/364] added margin to tags --- .../coffee/src/discussion/views/discussion_thread_view.coffee | 2 +- lms/static/sass/_discussion.scss | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee index 49e55f0c5b..6ea4b09e35 100644 --- a/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee +++ b/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee @@ -34,7 +34,7 @@ if Backbone? @responsesRequest.abort() renderTags: -> - tags + # tags for tag in @model.get("tags") if !tags tags = $('
    ') diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index 6802c3bf17..3798dbf278 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -456,6 +456,7 @@ body.discussion { } .thread-tag { + margin-right: 5px; padding: 3px 10px 6px; border-radius: 3px; color: #333; From 7812dd68fea5f028d4f5d739acf74839798b2e32 Mon Sep 17 00:00:00 2001 From: Kyle Fiedler Date: Thu, 13 Sep 2012 10:45:39 -0400 Subject: [PATCH 289/364] Added more padding for detailed answer --- common/lib/xmodule/xmodule/css/capa/display.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/common/lib/xmodule/xmodule/css/capa/display.scss b/common/lib/xmodule/xmodule/css/capa/display.scss index 7c296b4bdb..75ea25236a 100644 --- a/common/lib/xmodule/xmodule/css/capa/display.scss +++ b/common/lib/xmodule/xmodule/css/capa/display.scss @@ -436,7 +436,7 @@ section.problem { .detailed-solution { border: 1px solid #ddd; - padding: 9px 9px 20px; + padding: 9px 15px 20px; margin-bottom: 10px; background: #FFF; position: relative; From 5548e252c6fd11caa37b646cd2fc530b2227afee Mon Sep 17 00:00:00 2001 From: Kyle Fiedler Date: Thu, 13 Sep 2012 10:46:16 -0400 Subject: [PATCH 290/364] Hide list style for video elements --- common/lib/xmodule/xmodule/css/video/display.scss | 2 ++ 1 file changed, 2 insertions(+) diff --git a/common/lib/xmodule/xmodule/css/video/display.scss b/common/lib/xmodule/xmodule/css/video/display.scss index 504d5df8cf..e8aba4d671 100644 --- a/common/lib/xmodule/xmodule/css/video/display.scss +++ b/common/lib/xmodule/xmodule/css/video/display.scss @@ -157,6 +157,7 @@ div.video { opacity: 1; padding: 0; margin: 0; + list-style: none; } } @@ -411,6 +412,7 @@ div.video { width: flex-grid(3, 9); margin: 0; font-size: 14px; + list-style: none; li { border: 0; From d107370b11ede31abe292a3cff9215ce4e40c52e Mon Sep 17 00:00:00 2001 From: Kyle Fiedler Date: Thu, 13 Sep 2012 10:51:42 -0400 Subject: [PATCH 291/364] Made min width smaller for dynomath --- common/lib/xmodule/xmodule/css/capa/display.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/common/lib/xmodule/xmodule/css/capa/display.scss b/common/lib/xmodule/xmodule/css/capa/display.scss index 75ea25236a..0591a01843 100644 --- a/common/lib/xmodule/xmodule/css/capa/display.scss +++ b/common/lib/xmodule/xmodule/css/capa/display.scss @@ -158,7 +158,7 @@ section.problem { border: 1px solid #e3e3e3; @include inline-block; @include border-radius(4px); - min-width: 300px; + min-width: 30px; } } } From 5c76a1fbaf6fbb49e98950b0722e7b89a5ad001f Mon Sep 17 00:00:00 2001 From: Kyle Fiedler Date: Thu, 13 Sep 2012 11:23:57 -0400 Subject: [PATCH 292/364] Added fix for sequence nav in vertical --- lms/static/sass/course/courseware/_courseware.scss | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/lms/static/sass/course/courseware/_courseware.scss b/lms/static/sass/course/courseware/_courseware.scss index 9ce81a0057..6f95db64ee 100644 --- a/lms/static/sass/course/courseware/_courseware.scss +++ b/lms/static/sass/course/courseware/_courseware.scss @@ -98,6 +98,10 @@ div.course-wrapper { } } + nav.sequence-nav ul li.prev { + left: 4px; + } + nav.sequence-bottom { ul { list-style: none; From bcb7ad343c46ad66adfec7ae5e1684024de4eef3 Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 13 Sep 2012 11:25:55 -0400 Subject: [PATCH 293/364] fixed anonymous inline bug --- .../mustache/_inline_thread.mustache | 29 ++----------------- 1 file changed, 2 insertions(+), 27 deletions(-) diff --git a/lms/templates/discussion/mustache/_inline_thread.mustache b/lms/templates/discussion/mustache/_inline_thread.mustache index 743e06ba9d..150625bfae 100644 --- a/lms/templates/discussion/mustache/_inline_thread.mustache +++ b/lms/templates/discussion/mustache/_inline_thread.mustache @@ -1,32 +1,7 @@
    - + \ No newline at end of file From 9fb53465717df15de36c3129a3d974f2b50fd61b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Carlos=20Andr=C3=A9s=20Rocha?= Date: Thu, 13 Sep 2012 11:26:52 -0400 Subject: [PATCH 294/364] Temporary fix to set the speed of video player to 1.0 regardless of previous state --- common/lib/xmodule/xmodule/js/src/video/display.coffee | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/common/lib/xmodule/xmodule/js/src/video/display.coffee b/common/lib/xmodule/xmodule/js/src/video/display.coffee index 3880091661..cc3ce5d8d1 100644 --- a/common/lib/xmodule/xmodule/js/src/video/display.coffee +++ b/common/lib/xmodule/xmodule/js/src/video/display.coffee @@ -33,11 +33,7 @@ class @Video @speeds = ($.map @videos, (url, speed) -> speed).sort() setSpeed: (newSpeed) -> - if @videos[newSpeed] != undefined - @speed = newSpeed - $.cookie('video_speed', "#{newSpeed}", expires: 3650, path: '/') - else - @speed = '1.0' + @speed = '1.0' embed: -> @player = new VideoPlayer video: this From 991e3fd1b7b3ca154c055b649aaf96c9dc9b74bd Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 13 Sep 2012 11:37:08 -0400 Subject: [PATCH 295/364] fixed sidebar height glitch --- .../src/discussion/views/discussion_thread_list_view.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee index e0502d892a..096c076f45 100644 --- a/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee +++ b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee @@ -65,7 +65,7 @@ if Backbone? amount = Math.max(topOffset - discussionBottomOffset, 0) sidebarHeight = sidebarHeight - @sidebar_padding - amount - sidebarHeight = Math.min(Math.max(sidebarHeight, 400), discussionBody.outerHeight()) + sidebarHeight = Math.min(sidebarHeight, discussionBody.outerHeight()) sidebar.css 'height', sidebarHeight postListWrapper = @$('.post-list-wrapper') From b4142246fe7ca5d98ba39375f22f5561fc5f1acb Mon Sep 17 00:00:00 2001 From: Bridger Maxwell Date: Thu, 13 Sep 2012 11:39:32 -0400 Subject: [PATCH 296/364] Added ie fixes stylesheet to main_django.html. Cleaned up whitespace to more closely match main.html. --- lms/templates/main_django.html | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/lms/templates/main_django.html b/lms/templates/main_django.html index 20514b4ce4..f5ee06d280 100644 --- a/lms/templates/main_django.html +++ b/lms/templates/main_django.html @@ -3,34 +3,37 @@ {% block title %}edX{% endblock %} + {% compressed_css 'application' %} {% compressed_js 'main_vendor' %} - {% block headextra %}{% endblock %} {% render_block "css" %} - + + + - {% include "navigation.html" %} -
    {% block body %}{% endblock %} - {% block bodyextra %}{% endblock %}
    + {% include "footer.html" %} {% compressed_js 'application' %} {% compressed_js 'module-js' %} + {% render_block "js" %} From f253186e3125b8fa7465dbaee0cf20069b78b4e0 Mon Sep 17 00:00:00 2001 From: Kyle Fiedler Date: Thu, 13 Sep 2012 11:57:46 -0400 Subject: [PATCH 297/364] Added right style for label --- lms/static/sass/shared/_modal.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lms/static/sass/shared/_modal.scss b/lms/static/sass/shared/_modal.scss index 409c6088ec..1685487b89 100644 --- a/lms/static/sass/shared/_modal.scss +++ b/lms/static/sass/shared/_modal.scss @@ -147,7 +147,7 @@ } label { - display: none; + color: #999; &.field-error { display: block; From a3760d484ddae8d75148fc50a9219a48209782f5 Mon Sep 17 00:00:00 2001 From: Bridger Maxwell Date: Thu, 13 Sep 2012 12:38:28 -0400 Subject: [PATCH 298/364] Added call to load schematics on wiki pages. --- lms/templates/wiki/base.html | 3 +++ lms/templates/wiki/preview_inline.html | 4 ++++ 2 files changed, 7 insertions(+) diff --git a/lms/templates/wiki/base.html b/lms/templates/wiki/base.html index 8a9686f546..22b107104b 100644 --- a/lms/templates/wiki/base.html +++ b/lms/templates/wiki/base.html @@ -31,6 +31,9 @@ {% addtoblock 'js' %} {% comment %} These scripts load at the bottom of the body {% endcomment %} + diff --git a/lms/templates/wiki/preview_inline.html b/lms/templates/wiki/preview_inline.html index a5c6668d16..2f09d21bd3 100644 --- a/lms/templates/wiki/preview_inline.html +++ b/lms/templates/wiki/preview_inline.html @@ -41,6 +41,10 @@ {% compressed_js 'application' %} {% compressed_js 'module-js' %} + + {% with mathjax_mode='wiki' %} {% include "mathjax_include.html" %} {% endwith %} From c17a9b78f8c86b59b9eb0944198cfdc8073a846b Mon Sep 17 00:00:00 2001 From: Kyle Fiedler Date: Thu, 13 Sep 2012 13:52:47 -0400 Subject: [PATCH 299/364] fixed empty space below accordion nav items that dont have a subtitle --- lms/static/sass/course/courseware/_sidebar.scss | 6 +++++- lms/templates/courseware/courseware.html | 16 +++++++++------- 2 files changed, 14 insertions(+), 8 deletions(-) diff --git a/lms/static/sass/course/courseware/_sidebar.scss b/lms/static/sass/course/courseware/_sidebar.scss index 8ce963fd5f..4e893d2455 100644 --- a/lms/static/sass/course/courseware/_sidebar.scss +++ b/lms/static/sass/course/courseware/_sidebar.scss @@ -125,8 +125,12 @@ section.course-index { font-weight: normal; display: block; margin: 0; + + &:empty { + display: none; + } } - } + } &:hover { background: rgba(0, 0, 0, .1); diff --git a/lms/templates/courseware/courseware.html b/lms/templates/courseware/courseware.html index a446460d36..9c0ad9dd99 100644 --- a/lms/templates/courseware/courseware.html +++ b/lms/templates/courseware/courseware.html @@ -41,15 +41,17 @@ $(".ui-accordion-header a, .ui-accordion-content .subtitle").each(function() { var wordArray = $(this).text().split(" "); var finalTitle = ""; - for (i=0;i<=wordArray.length-1;i++) { - finalTitle += wordArray[i]; - if (i == (wordArray.length-2)) { - finalTitle += " "; - } else { - finalTitle += " "; + if (wordArray.isEmptyObject()) { + for (i=0;i<=wordArray.length-1;i++) { + finalTitle += wordArray[i]; + if (i == (wordArray.length-2)) { + finalTitle += " "; + } else { + finalTitle += " "; + } } + $(this).html(finalTitle); } - $(this).html(finalTitle); }); }); From d2c6ae9391ab7045bdeba70abdc635d14a1501cb Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 13 Sep 2012 15:01:54 -0400 Subject: [PATCH 300/364] tweaked inline tag styles; added href to tags --- .../coffee/src/discussion/views/discussion_thread_view.coffee | 2 +- lms/static/sass/_discussion.scss | 3 +++ 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee index 6ea4b09e35..dd695d39d8 100644 --- a/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee +++ b/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee @@ -38,7 +38,7 @@ if Backbone? for tag in @model.get("tags") if !tags tags = $('
    ') - tags.append("#{tag}") + tags.append("#{tag}") @$(".post-body").after(tags) tagSelected: (e) -> diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index 3798dbf278..4bc1474c96 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -2003,6 +2003,7 @@ body.discussion { .thread-tag { padding: 3px 10px 6px; + margin-right: 5px; border-radius: 3px; color: #333; background: #c5eeff; @@ -2299,12 +2300,14 @@ body.discussion { } } } + .thread-tags { margin: 20px 0; } .thread-tag { padding: 3px 10px 6px; + margin-right: 5px; border-radius: 3px; color: #333; background: #c5eeff; From b43da7463aaab47dc0ec8205477d064fa702c9f7 Mon Sep 17 00:00:00 2001 From: kimth Date: Thu, 13 Sep 2012 15:12:18 -0400 Subject: [PATCH 301/364] Do variable substitution for detailed solutions --- common/lib/capa/capa/capa_problem.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/common/lib/capa/capa/capa_problem.py b/common/lib/capa/capa/capa_problem.py index f386c9fe24..268206c639 100644 --- a/common/lib/capa/capa/capa_problem.py +++ b/common/lib/capa/capa/capa_problem.py @@ -265,7 +265,7 @@ class LoncapaProblem(object): # include solutions from ... stanzas for entry in self.tree.xpath("//" + "|//".join(solution_types)): answer = etree.tostring(entry) - if answer: answer_map[entry.get('id')] = answer + if answer: answer_map[entry.get('id')] = contextualize_text(answer, self.context) log.debug('answer_map = %s' % answer_map) return answer_map From 15ffd7e01d7cec0759da84e739253a426c5f9028 Mon Sep 17 00:00:00 2001 From: Kyle Fiedler Date: Thu, 13 Sep 2012 15:12:05 -0400 Subject: [PATCH 302/364] Better styles for updates --- lms/static/images/calendar-icon.png | Bin 0 -> 101 bytes lms/static/sass/course/_info.scss | 52 +++++++++++++++++++--------- 2 files changed, 36 insertions(+), 16 deletions(-) create mode 100644 lms/static/images/calendar-icon.png diff --git a/lms/static/images/calendar-icon.png b/lms/static/images/calendar-icon.png new file mode 100644 index 0000000000000000000000000000000000000000..367e4fef0ae203425bd2d0ef40f0837418f23b48 GIT binary patch literal 101 zcmeAS@N?(olHy`uVBq!ia0vp^JV4CN!3HF~3v%Ltl#Zv1V@SoVy?q-w85lSY@7eZ$ zenPsqE+ccJUgNaDN8tr2Y*A+XKU76Fcz5znxT>&LtMLC?pgsmqS3j3^P6 ul { + padding-left: 0; + + > li { + list-style: none; + } + + > ul { + list-style-type: disc; + } + } li { margin-bottom: lh(.5); } - - p { - &:last-child { - margin-bottom: 0; - } - } } } } From cb9697ba583627607eacea4b04d311d4296539fe Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 13 Sep 2012 15:16:17 -0400 Subject: [PATCH 303/364] fixed jump to top bug on edit form cancel button click --- .../src/discussion/views/discussion_thread_view.coffee | 1 + lms/static/sass/_discussion.scss | 6 +++++- 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee index dd695d39d8..f99118f8fb 100644 --- a/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee +++ b/lms/static/coffee/src/discussion/views/discussion_thread_view.coffee @@ -170,6 +170,7 @@ if Backbone? @renderSubView(@showView) cancelEdit: (event) => + event.preventDefault() @createShowView() @renderShowView() diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index 4bc1474c96..1d9c80cdd1 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -272,10 +272,14 @@ body.discussion { .edit-post-form { width: 100%; - margin-bottom: 20px; + margin-bottom: 40px; @include clearfix; @include box-sizing(border-box); + h1 { + font-size: 20px; + } + .form-row { margin-top: 20px; } From e0e94ee1f1469c88db5673c142a589e7140bc917 Mon Sep 17 00:00:00 2001 From: Kyle Fiedler Date: Thu, 13 Sep 2012 15:23:46 -0400 Subject: [PATCH 304/364] A little more space for each list --- lms/static/sass/course/_info.scss | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lms/static/sass/course/_info.scss b/lms/static/sass/course/_info.scss index 4fafc99c9f..6232a68055 100644 --- a/lms/static/sass/course/_info.scss +++ b/lms/static/sass/course/_info.scss @@ -22,8 +22,8 @@ div.info-wrapper { @extend .clearfix; border-bottom: 1px solid lighten($border-color, 10%); list-style-type: disk; - margin-bottom: lh(); - padding-bottom: lh(.5); + margin-bottom: lh(1.5); + padding-bottom: lh(.75); ol, ul { ol,ul { From 6c481b8aa38be637b20b06feaf7de12bf0e39a1c Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 13 Sep 2012 15:41:25 -0400 Subject: [PATCH 305/364] fixed post list sort active state bug --- .../src/discussion/views/discussion_thread_list_view.coffee | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee index 096c076f45..2da5667380 100644 --- a/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee +++ b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee @@ -130,8 +130,8 @@ if Backbone? @trigger("thread:removed", thread_id) setActiveThread: (thread_id) -> - @$("a[data-id!='#{thread_id}']").removeClass("active") - @$("a[data-id='#{thread_id}']").addClass("active") + @$(".post-list a[data-id!='#{thread_id}']").removeClass("active") + @$(".post-list a[data-id='#{thread_id}']").addClass("active") showSearch: -> @$(".browse").removeClass('is-dropped') From 81e01c8c72efd5605aa8aedcfcfcd5aca3246f30 Mon Sep 17 00:00:00 2001 From: kimth Date: Thu, 13 Sep 2012 16:46:19 -0400 Subject: [PATCH 306/364] Bring back bullets in lists --- lms/static/sass/course/_info.scss | 10 +--------- 1 file changed, 1 insertion(+), 9 deletions(-) diff --git a/lms/static/sass/course/_info.scss b/lms/static/sass/course/_info.scss index 6232a68055..20e75dbe0d 100644 --- a/lms/static/sass/course/_info.scss +++ b/lms/static/sass/course/_info.scss @@ -62,15 +62,7 @@ div.info-wrapper { } > ul { - padding-left: 0; - - > li { - list-style: none; - } - - > ul { - list-style-type: disc; - } + list-style-type: disc; } li { From 031a7d4e28dd6ba35645228c6949a7a5693730ab Mon Sep 17 00:00:00 2001 From: Tom Giannattasio Date: Thu, 13 Sep 2012 17:01:15 -0400 Subject: [PATCH 307/364] firefox border-box bug fix --- lms/static/sass/_discussion.scss | 38 ++++++++++++++++---------------- 1 file changed, 19 insertions(+), 19 deletions(-) diff --git a/lms/static/sass/_discussion.scss b/lms/static/sass/_discussion.scss index 1d9c80cdd1..d9aea37371 100644 --- a/lms/static/sass/_discussion.scss +++ b/lms/static/sass/_discussion.scss @@ -61,7 +61,7 @@ height: 240px; margin-top: 0; padding: 10px; - box-sizing: border-box; + @include box-sizing(border-box); border: 1px solid #aaa; border-radius: 3px 3px 0 0; background: #fff; @@ -75,7 +75,7 @@ width: 100%; min-height: 40px; padding: 25px 20px 10px 20px; - box-sizing: border-box; + @include box-sizing(border-box); border: 1px solid #aaa; border-top: none; border-radius: 0 0 3px 3px; @@ -150,7 +150,7 @@ body.discussion { float: left; width: 32%; padding: 40px; - box-sizing: border-box; + @include box-sizing(border-box); label { font-size: 22px; @@ -192,7 +192,7 @@ body.discussion { left: 0; z-index: 9999; width: 100%; - box-sizing: border-box; + @include box-sizing(border-box); background: #737373; border: 1px solid #333; box-shadow: 0 2px 50px rgba(0, 0, 0, .4); @@ -242,7 +242,7 @@ body.discussion { width: 100%; height: 30px; padding: 0 15px; - box-sizing: border-box; + @include box-sizing(border-box); border-radius: 30px; border: 1px solid #333; box-shadow: 0 1px 3px rgba(0, 0, 0, .25) inset; @@ -258,7 +258,7 @@ body.discussion { float: left; width: 68%; padding: 40px; - box-sizing: border-box; + @include box-sizing(border-box); } .wmd-button { @@ -306,7 +306,7 @@ body.discussion { width: 100%; height: 40px; padding: 0 10px; - box-sizing: border-box; + @include box-sizing(border-box); border-radius: 3px; border: 1px solid #aaa; font-size: 16px; @@ -352,7 +352,7 @@ body.discussion { height: 200px; z-index: 1; padding: 10px; - box-sizing: border-box; + @include box-sizing(border-box); border: 1px solid #333; border-radius: 3px 3px 0 0; background: #fff; @@ -364,7 +364,7 @@ body.discussion { .tagsinput { padding: 10px; - box-sizing: border-box; + @include box-sizing(border-box); border: 1px solid #333; border-radius: 3px; background: #fff; @@ -385,7 +385,7 @@ body.discussion { //height: 50px; margin-top: -1px; padding: 25px 20px 10px 20px; - box-sizing: border-box; + @include box-sizing(border-box); border: 1px solid #333; border-radius: 0 0 3px 3px; background: #e6e6e6; @@ -407,7 +407,7 @@ body.discussion { width: 100%; height: 40px; padding: 0 10px; - box-sizing: border-box; + @include box-sizing(border-box); border-radius: 3px; border: 1px solid #333; font-size: 16px; @@ -554,7 +554,7 @@ body.discussion { font-family: $sans-serif; padding: 25px 20px 10px 20px; margin-bottom: 5px; - box-sizing: border-box; + @include box-sizing(border-box); border: 1px solid #c8c8c8; border-top-width: 0; @include border-radius(0 0 3px 3px); @@ -916,7 +916,7 @@ body.discussion { width: 100%; height: 30px; padding: 0 15px; - box-sizing: border-box; + @include box-sizing(border-box); border-radius: 30px; border: 1px solid #333; box-shadow: 0 1px 3px rgba(0, 0, 0, .25) inset; @@ -1900,7 +1900,7 @@ body.discussion { height: 200px; z-index: 1; padding: 10px; - box-sizing: border-box; + @include box-sizing(border-box); border: 1px solid #333; border-radius: 3px 3px 0 0; background: #fff; @@ -1917,7 +1917,7 @@ body.discussion { //height: 50px; margin-top: -1px; padding: 25px 20px 10px 20px; - box-sizing: border-box; + @include box-sizing(border-box); border: 1px solid #333; border-radius: 0 0 3px 3px; background: #e6e6e6; @@ -1939,7 +1939,7 @@ body.discussion { width: 100%; height: 40px; padding: 0 10px; - box-sizing: border-box; + @include box-sizing(border-box); border-radius: 3px; border: 1px solid #333; font-size: 16px; @@ -1954,7 +1954,7 @@ body.discussion { .tagsinput { padding: 10px; - box-sizing: border-box; + @include box-sizing(border-box); border: 1px solid #333; border-radius: 3px; background: #fff; @@ -2106,7 +2106,7 @@ body.discussion { font-family: $sans-serif; padding: 25px 20px 10px 20px; margin-bottom: 5px; - box-sizing: border-box; + @include box-sizing(border-box); border: 1px solid #c8c8c8; border-top-width: 0; @include border-radius(0 0 3px 3px); @@ -2279,7 +2279,7 @@ body.discussion { width: 100%; height: 40px; padding: 0 10px; - box-sizing: border-box; + @include box-sizing(border-box); border-radius: 3px; border: 1px solid #aaa; font-size: 16px; From 5b9967e5a0ef0a9292c66988e0aa6df8f0efc9ad Mon Sep 17 00:00:00 2001 From: Matthew Mongeau Date: Thu, 13 Sep 2012 17:33:52 -0400 Subject: [PATCH 308/364] Paging wip --- .../django_comment_client/forum/views.py | 3 ++- .../coffee/src/discussion/discussion.coffee | 22 +++++++++++++++- lms/static/coffee/src/discussion/main.coffee | 3 ++- lms/static/coffee/src/discussion/utils.coffee | 1 + .../views/discussion_thread_list_view.coffee | 25 ++++++++++++++++--- lms/templates/discussion/index.html | 2 +- 6 files changed, 49 insertions(+), 7 deletions(-) diff --git a/lms/djangoapps/django_comment_client/forum/views.py b/lms/djangoapps/django_comment_client/forum/views.py index b41cb8e3ab..1b7b7b12a0 100644 --- a/lms/djangoapps/django_comment_client/forum/views.py +++ b/lms/djangoapps/django_comment_client/forum/views.py @@ -22,7 +22,7 @@ import django_comment_client.utils as utils import comment_client as cc import xml.sax.saxutils as saxutils -THREADS_PER_PAGE = 200 +THREADS_PER_PAGE = 2 INLINE_THREADS_PER_PAGE = 5 PAGES_NEARBY_DELTA = 2 escapedict = {'"': '"'} @@ -224,6 +224,7 @@ def forum_form_discussion(request, course_id): #'trending_tags': trending_tags, 'staff_access' : has_access(request.user, course, 'staff'), 'threads': saxutils.escape(json.dumps(threads),escapedict), + 'thread_pages': query_params['num_pages'], 'user_info': saxutils.escape(json.dumps(user_info),escapedict), 'annotated_content_info': saxutils.escape(json.dumps(annotated_content_info),escapedict), 'course_id': course.id, diff --git a/lms/static/coffee/src/discussion/discussion.coffee b/lms/static/coffee/src/discussion/discussion.coffee index bf51f354ff..ecf5ee6f1d 100644 --- a/lms/static/coffee/src/discussion/discussion.coffee +++ b/lms/static/coffee/src/discussion/discussion.coffee @@ -2,7 +2,9 @@ if Backbone? class @Discussion extends Backbone.Collection model: Thread - initialize: -> + initialize: (models, options)-> + @pages = options['pages'] || 1 + @current_page = 1 @bind "add", (item) => item.discussion = @ @comparator = @sortByDateRecentFirst @@ -12,12 +14,30 @@ if Backbone? find: (id) -> _.first @where(id: id) + hasMorePages: -> + @current_page < @pages + addThread: (thread, options) -> options ||= {} model = new Thread thread @add model model + retrieveAnotherPage: -> + @current_page += 1 + url = DiscussionUtil.urlFor 'threads' + data = { page: @current_page } + DiscussionUtil.safeAjax + $elem: @$el + url: url + data: data + dataType: 'json' + success: (response, textStatus) => + models = @models + new_threads = [new Thread(data) for data in response.discussion_data][0] + new_collection = _.union(models, new_threads) + @reset new_collection + sortByDate: (thread) -> thread.get("created_at") diff --git a/lms/static/coffee/src/discussion/main.coffee b/lms/static/coffee/src/discussion/main.coffee index dfd9d086a0..c0ca520113 100644 --- a/lms/static/coffee/src/discussion/main.coffee +++ b/lms/static/coffee/src/discussion/main.coffee @@ -7,10 +7,11 @@ if Backbone? window.$$course_id = element.data("course-id") user_info = element.data("user-info") threads = element.data("threads") + thread_pages = element.data("thread-pages") content_info = element.data("content-info") window.user = new DiscussionUser(user_info) Content.loadContentInfos(content_info) - discussion = new Discussion(threads) + discussion = new Discussion(threads, pages: thread_pages) new DiscussionRouter({discussion: discussion}) Backbone.history.start({pushState: true, root: "/courses/#{$$course_id}/discussion/forum/"}) DiscussionProfileApp = diff --git a/lms/static/coffee/src/discussion/utils.coffee b/lms/static/coffee/src/discussion/utils.coffee index 056778a0df..fb0c393f09 100644 --- a/lms/static/coffee/src/discussion/utils.coffee +++ b/lms/static/coffee/src/discussion/utils.coffee @@ -66,6 +66,7 @@ class @DiscussionUtil permanent_link_thread : "/courses/#{$$course_id}/discussion/forum/#{param}/threads/#{param1}" permanent_link_comment : "/courses/#{$$course_id}/discussion/forum/#{param}/threads/#{param1}##{param2}" user_profile : "/courses/#{$$course_id}/discussion/forum/users/#{param}" + threads : "/courses/#{$$course_id}/discussion/forum" }[name] @safeAjax: (params) -> diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee index 2da5667380..a8f1466011 100644 --- a/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee +++ b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee @@ -7,11 +7,20 @@ if Backbone? "click .sort-bar a": "sortThreads" "click .browse-topic-drop-menu": "filterTopic" "click .browse-topic-drop-search-input": "ignoreClick" - "click .post-list a": "threadSelected" + "click .post-list .list-item a": "threadSelected" + "click .post-list .more-pages a": "loadMorePages" initialize: -> - @displayedCollection = new Discussion(@collection.models) + @displayedCollection = new Discussion(@collection.models, pages: @collection.pages) @collection.on "change", @reloadDisplayedCollection + @collection.on "reset", (discussion) => + board = $(".current-board").html() + @displayedCollection.current_page = discussion.current_page + @displayedCollection.reset discussion.models + # TODO: filter correctly + # target = _.filter($("a.topic:contains('#{board}')"), (el) -> el.innerText == "General" || el.innerHTML == "General") + # if target.length > 0 + # @filterTopic($.Event("filter", {'target': target[0]})) @collection.on "add", @addAndSelectThread @sidebar_padding = 10 @sidebar_header_height = 87 @@ -96,11 +105,21 @@ if Backbone? for thread in @displayedCollection.models content = @renderThread(thread) rendered.append content - content.wrap("
  • ") + content.wrap("
  • ") @$(".post-list").html(rendered.html()) + @renderMorePages() @trigger "threads:rendered" + renderMorePages: -> + if @displayedCollection.hasMorePages() + @$(".post-list").append("
  • Load more
  • ") + + loadMorePages: -> + @$(".more-pages").html('
    ') + @$(".more-pages").addClass("loading") + @collection.retrieveAnotherPage() + renderThread: (thread) => content = $(_.template($("#thread-list-item-template").html())(thread.toJSON())) if thread.get('subscribed') diff --git a/lms/templates/discussion/index.html b/lms/templates/discussion/index.html index a0cdcdcb44..70e224c78c 100644 --- a/lms/templates/discussion/index.html +++ b/lms/templates/discussion/index.html @@ -23,7 +23,7 @@ -
    +
    From a9b03483aa452a741778181a27b2c0347a2c4ea3 Mon Sep 17 00:00:00 2001 From: kimth Date: Thu, 13 Sep 2012 17:38:20 -0400 Subject: [PATCH 309/364] Fix widow js --- lms/templates/courseware/courseware.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lms/templates/courseware/courseware.html b/lms/templates/courseware/courseware.html index 9c0ad9dd99..15e4dead9a 100644 --- a/lms/templates/courseware/courseware.html +++ b/lms/templates/courseware/courseware.html @@ -41,7 +41,7 @@ $(".ui-accordion-header a, .ui-accordion-content .subtitle").each(function() { var wordArray = $(this).text().split(" "); var finalTitle = ""; - if (wordArray.isEmptyObject()) { + if ($.isEmptyObject(wordArray)) { for (i=0;i<=wordArray.length-1;i++) { finalTitle += wordArray[i]; if (i == (wordArray.length-2)) { From cf9130a8112f62596e6e915aca6c5a6140056c90 Mon Sep 17 00:00:00 2001 From: kimth Date: Thu, 13 Sep 2012 17:51:25 -0400 Subject: [PATCH 310/364] Widow prevention should be active when there are actual words --- lms/templates/courseware/courseware.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lms/templates/courseware/courseware.html b/lms/templates/courseware/courseware.html index 15e4dead9a..9dc0fa2a55 100644 --- a/lms/templates/courseware/courseware.html +++ b/lms/templates/courseware/courseware.html @@ -41,7 +41,7 @@ $(".ui-accordion-header a, .ui-accordion-content .subtitle").each(function() { var wordArray = $(this).text().split(" "); var finalTitle = ""; - if ($.isEmptyObject(wordArray)) { + if (!($.isEmptyObject(wordArray))) { for (i=0;i<=wordArray.length-1;i++) { finalTitle += wordArray[i]; if (i == (wordArray.length-2)) { From 5dbc0b7e7aabf0f2775313a890fc1c48eeb70fe2 Mon Sep 17 00:00:00 2001 From: kimth Date: Thu, 13 Sep 2012 18:02:46 -0400 Subject: [PATCH 311/364] Fix widow prevent logic --- lms/templates/courseware/courseware.html | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/lms/templates/courseware/courseware.html b/lms/templates/courseware/courseware.html index 9dc0fa2a55..ee6460ffec 100644 --- a/lms/templates/courseware/courseware.html +++ b/lms/templates/courseware/courseware.html @@ -39,7 +39,8 @@ $(function(){ $(".ui-accordion-header a, .ui-accordion-content .subtitle").each(function() { - var wordArray = $(this).text().split(" "); + var elemText = $(this).text().replace(/^\s+|\s+$/g,''); // Strip leading and trailing whitespace + var wordArray = elemText.split(" "); var finalTitle = ""; if (!($.isEmptyObject(wordArray))) { for (i=0;i<=wordArray.length-1;i++) { @@ -50,8 +51,8 @@ finalTitle += " "; } } - $(this).html(finalTitle); } + $(this).html(finalTitle); }); }); From a40e8eaefbb73544c7033a9f85b1d6cc5abe3a54 Mon Sep 17 00:00:00 2001 From: kimth Date: Thu, 13 Sep 2012 18:10:11 -0400 Subject: [PATCH 312/364] Clean up widow prevention logic --- lms/templates/courseware/courseware.html | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/lms/templates/courseware/courseware.html b/lms/templates/courseware/courseware.html index ee6460ffec..761237fd76 100644 --- a/lms/templates/courseware/courseware.html +++ b/lms/templates/courseware/courseware.html @@ -42,11 +42,13 @@ var elemText = $(this).text().replace(/^\s+|\s+$/g,''); // Strip leading and trailing whitespace var wordArray = elemText.split(" "); var finalTitle = ""; - if (!($.isEmptyObject(wordArray))) { + if (wordArray.length > 0) { for (i=0;i<=wordArray.length-1;i++) { finalTitle += wordArray[i]; if (i == (wordArray.length-2)) { finalTitle += " "; + } else if (i == (wordArray.length-1)) { + // Do nothing } else { finalTitle += " "; } From 5ce16738fbe0b0a0b21dae13c561f8f7b5504e1f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Carlos=20Andr=C3=A9s=20Rocha?= Date: Thu, 13 Sep 2012 18:38:48 -0400 Subject: [PATCH 313/364] Reverting to original video player --- .../xmodule/js/src/video/display.coffee | 6 +++- .../js/src/video/display/video_player.coffee | 28 ++++++++++++++----- lms/templates/video.html | 2 -- 3 files changed, 26 insertions(+), 10 deletions(-) diff --git a/common/lib/xmodule/xmodule/js/src/video/display.coffee b/common/lib/xmodule/xmodule/js/src/video/display.coffee index cc3ce5d8d1..3880091661 100644 --- a/common/lib/xmodule/xmodule/js/src/video/display.coffee +++ b/common/lib/xmodule/xmodule/js/src/video/display.coffee @@ -33,7 +33,11 @@ class @Video @speeds = ($.map @videos, (url, speed) -> speed).sort() setSpeed: (newSpeed) -> - @speed = '1.0' + if @videos[newSpeed] != undefined + @speed = newSpeed + $.cookie('video_speed', "#{newSpeed}", expires: 3650, path: '/') + else + @speed = '1.0' embed: -> @player = new VideoPlayer video: this diff --git a/common/lib/xmodule/xmodule/js/src/video/display/video_player.coffee b/common/lib/xmodule/xmodule/js/src/video/display/video_player.coffee index b83cda80d6..4b265d20c8 100644 --- a/common/lib/xmodule/xmodule/js/src/video/display/video_player.coffee +++ b/common/lib/xmodule/xmodule/js/src/video/display/video_player.coffee @@ -24,13 +24,27 @@ class @VideoPlayer extends Subview @toggleFullScreen(event) render: -> - params = { allowScriptAccess: "always" }; - atts = { id: @videoid }; - youtubeId = @video.youtubeId() - - swfobject.embedSWF("https://www.youtube.com/v/#{youtubeId}?enablejsapi=1&version=3&playerapiid=ytplayer&rel=0&modestbranding=1&showsearch=0&showinfo=0", - @video.id, "425", "356", "9", null, null, params, atts ) - + @control = new VideoControl el: @$('.video-controls') + @caption = new VideoCaption + el: @el + youtubeId: @video.youtubeId('1.0') + currentSpeed: @currentSpeed() + captionDataDir: @video.caption_data_dir + unless onTouchBasedDevice() + @volumeControl = new VideoVolumeControl el: @$('.secondary-controls') + @speedControl = new VideoSpeedControl el: @$('.secondary-controls'), speeds: @video.speeds, currentSpeed: @currentSpeed() + @progressSlider = new VideoProgressSlider el: @$('.slider') + @player = new YT.Player @video.id, + playerVars: + controls: 0 + wmode: 'transparent' + rel: 0 + showinfo: 0 + enablejsapi: 1 + videoId: @video.youtubeId() + events: + onReady: @onReady + onStateChange: @onStateChange addToolTip: -> @$('.add-fullscreen, .hide-subtitles').qtip diff --git a/lms/templates/video.html b/lms/templates/video.html index 25652e51fa..bd3ec77fbe 100644 --- a/lms/templates/video.html +++ b/lms/templates/video.html @@ -2,8 +2,6 @@

    ${display_name}

    % endif - -
    From 8bad4c8dbc9046e26c323df2755f17b87f0aa5ed Mon Sep 17 00:00:00 2001 From: Arjun Singh Date: Thu, 13 Sep 2012 16:00:48 -0700 Subject: [PATCH 314/364] Allow for course subscriptions --- lms/lib/comment_client/user.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lms/lib/comment_client/user.py b/lms/lib/comment_client/user.py index eea6fda407..a892216605 100644 --- a/lms/lib/comment_client/user.py +++ b/lms/lib/comment_client/user.py @@ -8,7 +8,7 @@ class User(models.Model): accessible_fields = ['username', 'email', 'follower_ids', 'upvoted_ids', 'downvoted_ids', 'id', 'external_id', 'subscribed_user_ids', 'children', 'course_id', 'subscribed_thread_ids', 'subscribed_commentable_ids', - 'threads_count', 'comments_count', 'default_sort_key' + 'subscribed_course_ids', 'threads_count', 'comments_count', 'default_sort_key' ] updatable_fields = ['username', 'external_id', 'email', 'default_sort_key'] From a83b9322aec20f8131571d3d5f5c4d330ddca0c7 Mon Sep 17 00:00:00 2001 From: Arjun Singh Date: Thu, 13 Sep 2012 16:03:19 -0700 Subject: [PATCH 315/364] Allow for course subscriptions --- lms/djangoapps/django_comment_client/permissions.py | 3 ++- lms/lib/comment_client/user.py | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/lms/djangoapps/django_comment_client/permissions.py b/lms/djangoapps/django_comment_client/permissions.py index 9b064a7fef..352d4cc187 100644 --- a/lms/djangoapps/django_comment_client/permissions.py +++ b/lms/djangoapps/django_comment_client/permissions.py @@ -5,7 +5,8 @@ from student.models import CourseEnrollment import logging from util.cache import cache - +from django.core import cache +cache = cache.get_cache('default') def cached_has_permission(user, permission, course_id=None): """ diff --git a/lms/lib/comment_client/user.py b/lms/lib/comment_client/user.py index a892216605..9813e9a199 100644 --- a/lms/lib/comment_client/user.py +++ b/lms/lib/comment_client/user.py @@ -8,7 +8,8 @@ class User(models.Model): accessible_fields = ['username', 'email', 'follower_ids', 'upvoted_ids', 'downvoted_ids', 'id', 'external_id', 'subscribed_user_ids', 'children', 'course_id', 'subscribed_thread_ids', 'subscribed_commentable_ids', - 'subscribed_course_ids', 'threads_count', 'comments_count', 'default_sort_key' + 'subscribed_course_ids', 'threads_count', 'comments_count', + 'default_sort_key' ] updatable_fields = ['username', 'external_id', 'email', 'default_sort_key'] From a32d9686aeed8e17f4c476336cdb1d1ac314248a Mon Sep 17 00:00:00 2001 From: Kyle Fiedler Date: Thu, 13 Sep 2012 19:21:55 -0400 Subject: [PATCH 316/364] One more IE fix and added comments so there is some explination of what is there --- lms/static/sass/ie.scss | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/lms/static/sass/ie.scss b/lms/static/sass/ie.scss index a22d3935fd..1a58110563 100644 --- a/lms/static/sass/ie.scss +++ b/lms/static/sass/ie.scss @@ -2,12 +2,14 @@ @import "base/variables"; // These are all quick solutions for IE please rewrite +//Make overlay white because ie doesn't like rgba .highlighted-courses .courses .course header.course-preview, .find-courses .courses .course header.course-preview, .home .highlighted-courses > h2, .home .highlighted-courses > section.outside-app h1, section.outside-app .home .highlighted-courses > h1, header.global { background: #FFF; } +// hide all actions .home > header .title .actions, .home > header .title:hover .actions { display: none; @@ -34,10 +36,12 @@ header.global { } } +// because ie doesn't like :last .last { margin-right: 0 !important; } +// make partners not animate .home .university-partners .partners a { .name { position: static; @@ -61,7 +65,6 @@ header.global { } - .home .university-partners .partners { width: 660px; @@ -74,6 +77,7 @@ header.global { } } +// make animations on homepage not animate and show everything .highlighted-courses .courses .course, .find-courses .courses .course { .meta-info { display: none; @@ -126,17 +130,24 @@ header.global { } } +// make overlay flat black since IE cant handle rgba #lean_overlay { background: #000; } +// active navigation nav.course-material ol.course-tabs li a.active, nav.course-material .xmodule_SequenceModule nav.sequence-nav ol.course-tabs li a.seq_video.active, .xmodule_SequenceModule nav.sequence-nav nav.course-material ol.course-tabs li a.seq_video.active { background-color: #333; background-color: rgba(0, 0, 0, .4); } +// make dropdown user consistent size header.global ol.user > li.primary a.dropdown { padding-top: 6px; padding-bottom: 6px; } +// always hide arrow in IE +.dashboard .my-courses .my-course .cover .arrow { + display: none; +} From 236756e4cab7401767a5187fd7ee717d9ec1b02f Mon Sep 17 00:00:00 2001 From: Ibrahim Awwal Date: Thu, 13 Sep 2012 17:53:30 -0700 Subject: [PATCH 317/364] Default argument value for options in Discussion so that inline discussions can still work without modification. Eventually we'll want to switch the pagination there to match the pagination on the main forum though. --- lms/static/coffee/src/discussion/discussion.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lms/static/coffee/src/discussion/discussion.coffee b/lms/static/coffee/src/discussion/discussion.coffee index ecf5ee6f1d..b62770ca8a 100644 --- a/lms/static/coffee/src/discussion/discussion.coffee +++ b/lms/static/coffee/src/discussion/discussion.coffee @@ -2,7 +2,7 @@ if Backbone? class @Discussion extends Backbone.Collection model: Thread - initialize: (models, options)-> + initialize: (models, options={})-> @pages = options['pages'] || 1 @current_page = 1 @bind "add", (item) => From d92a070ab1a3670acdc5d85c090f40f49a7a25b3 Mon Sep 17 00:00:00 2001 From: Ibrahim Awwal Date: Thu, 13 Sep 2012 18:34:01 -0700 Subject: [PATCH 318/364] Obey current search query and sort order when retrieving additional pages. --- lms/static/coffee/src/discussion/discussion.coffee | 7 +++++-- .../views/discussion_thread_list_view.coffee | 13 ++++++++----- 2 files changed, 13 insertions(+), 7 deletions(-) diff --git a/lms/static/coffee/src/discussion/discussion.coffee b/lms/static/coffee/src/discussion/discussion.coffee index b62770ca8a..91083c94e3 100644 --- a/lms/static/coffee/src/discussion/discussion.coffee +++ b/lms/static/coffee/src/discussion/discussion.coffee @@ -23,10 +23,13 @@ if Backbone? @add model model - retrieveAnotherPage: -> + retrieveAnotherPage: (search_text="", commentable_id="", sort_key="")-> + # TODO: Obey dropdown filter (commentable_id) @current_page += 1 url = DiscussionUtil.urlFor 'threads' - data = { page: @current_page } + data = { page: @current_page, text: search_text } + if sort_key + data['sort_key'] = sort_key DiscussionUtil.safeAjax $elem: @$el url: url diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee index a8f1466011..90bd7c4978 100644 --- a/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee +++ b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee @@ -13,6 +13,7 @@ if Backbone? initialize: -> @displayedCollection = new Discussion(@collection.models, pages: @collection.pages) @collection.on "change", @reloadDisplayedCollection + @sortBy = "date" @collection.on "reset", (discussion) => board = $(".current-board").html() @displayedCollection.current_page = discussion.current_page @@ -116,9 +117,10 @@ if Backbone? @$(".post-list").append("
  • Load more
  • ") loadMorePages: -> + # TODO: Obey dropdown filter @$(".more-pages").html('
    ') @$(".more-pages").addClass("loading") - @collection.retrieveAnotherPage() + @collection.retrieveAnotherPage(@current_search, "", @sortBy) renderThread: (thread) => content = $(_.template($("#thread-list-item-template").html())(thread.toJSON())) @@ -242,12 +244,12 @@ if Backbone? sortThreads: (event) -> @$(".sort-bar a").removeClass("active") $(event.target).addClass("active") - sortBy = $(event.target).data("sort") - if sortBy == "date" + @sortBy = $(event.target).data("sort") + if @sortBy == "date" @displayedCollection.comparator = @displayedCollection.sortByDateRecentFirst - else if sortBy == "votes" + else if @sortBy == "votes" @displayedCollection.comparator = @displayedCollection.sortByVotes - else if sortBy == "comments" + else if @sortBy == "comments" @displayedCollection.comparator = @displayedCollection.sortByComments @displayedCollection.sort() @@ -278,6 +280,7 @@ if Backbone? callback.apply @, [value] success: (response, textStatus) => if textStatus == 'success' + # TODO: Augment existing collection? @collection.reset(response.discussion_data) Content.loadContentInfos(response.content_info) # TODO: Perhaps reload user info so that votes can be updated. From e4c7a5ea972485cded48c5d73fb849651cced675 Mon Sep 17 00:00:00 2001 From: Arjun Singh Date: Thu, 13 Sep 2012 19:41:07 -0700 Subject: [PATCH 319/364] Fix courseware context links; filter out unstarted topics. --- .../django_comment_client/forum/views.py | 10 +-- lms/djangoapps/django_comment_client/utils.py | 89 +++++++++++++++---- .../discussion/_underscore_templates.html | 4 +- 3 files changed, 75 insertions(+), 28 deletions(-) diff --git a/lms/djangoapps/django_comment_client/forum/views.py b/lms/djangoapps/django_comment_client/forum/views.py index 1b7b7b12a0..2d1c1add45 100644 --- a/lms/djangoapps/django_comment_client/forum/views.py +++ b/lms/djangoapps/django_comment_client/forum/views.py @@ -79,8 +79,7 @@ def render_discussion(request, course_id, threads, *args, **kwargs): for thread in threads: courseware_context = get_courseware_context(thread, course) if courseware_context: - thread['courseware_location'] = courseware_context['courseware_location'] - thread['courseware_title'] = courseware_context['courseware_title'] + thread.update(courseware_context) context = { 'threads': map(utils.safe_content, threads), @@ -199,8 +198,7 @@ def forum_form_discussion(request, course_id): for thread in threads: courseware_context = get_courseware_context(thread, course) if courseware_context: - thread['courseware_location'] = courseware_context['courseware_location'] - thread['courseware_title'] = courseware_context['courseware_title'] + thread.update(courseware_context) if request.is_ajax(): return utils.JsonResponse({ 'discussion_data': threads, # TODO: Standardize on 'discussion_data' vs 'threads' @@ -273,8 +271,7 @@ def single_thread(request, course_id, discussion_id, thread_id): for thread in threads: courseware_context = get_courseware_context(thread, course) if courseware_context: - thread['courseware_location'] = courseware_context['courseware_location'] - thread['courseware_title'] = courseware_context['courseware_title'] + thread.update(courseware_context) threads = [utils.safe_content(thread) for thread in threads] @@ -290,7 +287,6 @@ def single_thread(request, course_id, discussion_id, thread_id): user_info = cc.User.from_django_user(request.user).to_dict() - def infogetter(thread): return utils.get_annotated_content_infos(course_id, thread, request.user, user_info) diff --git a/lms/djangoapps/django_comment_client/utils.py b/lms/djangoapps/django_comment_client/utils.py index 4ceea6b82c..9ebae79fa2 100644 --- a/lms/djangoapps/django_comment_client/utils.py +++ b/lms/djangoapps/django_comment_client/utils.py @@ -1,9 +1,12 @@ +import time from collections import defaultdict from importlib import import_module + from courseware.models import StudentModuleCache from courseware.module_render import get_module from xmodule.modulestore import Location from xmodule.modulestore.django import modulestore +from xmodule.modulestore.search import path_to_location from django.http import HttpResponse from django.utils import simplejson from django.db import connection @@ -74,7 +77,44 @@ def get_discussion_category_map(course): global _DISCUSSIONINFO if not _DISCUSSIONINFO: initialize_discussion_info(course) - return _DISCUSSIONINFO['category_map'] + return filter_unstarted_categories(_DISCUSSIONINFO['category_map']) + +def filter_unstarted_categories(category_map): + + now = time.gmtime() + + result_map = {} + + unfiltered_queue = [category_map] + filtered_queue = [result_map] + + while len(unfiltered_queue) > 0: + + unfiltered_map = unfiltered_queue.pop() + filtered_map = filtered_queue.pop() + + filtered_map["children"] = [] + filtered_map["entries"] = {} + filtered_map["subcategories"] = {} + + for child in unfiltered_map["children"]: + if child in unfiltered_map["entries"]: + if unfiltered_map["entries"][child]["start_date"] < now: + filtered_map["children"].append(child) + filtered_map["entries"][child] = {} + for key in unfiltered_map["entries"][child]: + if key != "start_date": + filtered_map["entries"][child][key] = unfiltered_map["entries"][child][key] + else: + print "filtering %s" % child, unfiltered_map["entries"][child]["start_date"] + else: + if unfiltered_map["subcategories"][child]["start_date"] < now: + filtered_map["children"].append(child) + filtered_map["subcategories"][child] = {} + unfiltered_queue.append(unfiltered_map["subcategories"][child]) + filtered_queue.append(filtered_map["subcategories"][child]) + + return result_map def sort_map_entries(category_map): things = [] @@ -109,32 +149,49 @@ def initialize_discussion_info(course): discussion_id_map[id] = {"location": location, "title": title} category = " / ".join([x.strip() for x in category.split("/")]) unexpanded_category_map[category].append({"title": title, "id": id, - "sort_key": sort_key}) + "sort_key": sort_key, "start_date": module.start}) category_map = {"entries": defaultdict(dict), "subcategories": defaultdict(dict)} for category_path, entries in unexpanded_category_map.items(): node = category_map["subcategories"] path = [x.strip() for x in category_path.split("/")] + + # Find the earliest start date for the entries in this category + category_start_date = None + for entry in entries: + if category_start_date is None or entry["start_date"] < category_start_date: + category_start_date = entry["start_date"] + for level in path[:-1]: if level not in node: node[level] = {"subcategories": defaultdict(dict), "entries": defaultdict(dict), - "sort_key": level} + "sort_key": level, + "start_date": category_start_date} + else: + if node[level]["start_date"] > category_start_date: + node[level]["start_date"] = category_start_date node = node[level]["subcategories"] level = path[-1] if level not in node: node[level] = {"subcategories": defaultdict(dict), "entries": defaultdict(dict), - "sort_key": level} + "sort_key": level, + "start_date": category_start_date} + else: + if node[level]["start_date"] > category_start_date: + node[level]["start_date"] = category_start_date + for entry in entries: node[level]["entries"][entry["title"]] = {"id": entry["id"], - "sort_key": entry["sort_key"]} + "sort_key": entry["sort_key"], + "start_date": entry["start_date"]} for topic, entry in course.metadata.get('discussion_topics', {}).items(): category_map['entries'][topic] = {"id": entry["id"], - "sort_key": entry.get("sort_key", topic)} - + "sort_key": entry.get("sort_key", topic), + "start_date": time.gmtime()} sort_map_entries(category_map) _DISCUSSIONINFO = {} @@ -142,16 +199,6 @@ def initialize_discussion_info(course): _DISCUSSIONINFO['id_map'] = discussion_id_map _DISCUSSIONINFO['category_map'] = category_map -def get_courseware_context(content, course): - id_map = get_discussion_id_map(course) - id = content['commentable_id'] - content_info = None - if id in id_map: - location = id_map[id]["location"].url() - title = id_map[id]["title"] - content_info = { "courseware_location": location, "courseware_title": title} - return content_info - class JsonResponse(HttpResponse): def __init__(self, data=None): content = simplejson.dumps(data) @@ -270,10 +317,14 @@ def get_courseware_context(content, course): if id in id_map: location = id_map[id]["location"].url() title = id_map[id]["title"] - content_info = { "courseware_location": location, "courseware_title": title} + (course_id, chapter, section, position) = path_to_location(modulestore(), course.id, location) + url = reverse('courseware_position', kwargs={"course_id":course_id, + "chapter":chapter, + "section":section, + "position":position}) + content_info = {"courseware_url": url, "courseware_title": title} return content_info - def safe_content(content): fields = [ 'id', 'title', 'body', 'course_id', 'anonymous', 'endorsed', diff --git a/lms/templates/discussion/_underscore_templates.html b/lms/templates/discussion/_underscore_templates.html index 9638c93ad9..d6011e75c0 100644 --- a/lms/templates/discussion/_underscore_templates.html +++ b/lms/templates/discussion/_underscore_templates.html @@ -39,9 +39,9 @@
    ${'<%- body %>'}
    - ${'<% if (obj.courseware_location) { %>'} + ${'<% if (obj.courseware_url) { %>'}
    - (this post is about ${'<%- courseware_title %>'}) + (this post is about ${'<%- courseware_title %>'})
    ${'<% } %>'} From 4d59013955b10d9b3f456c03e7f8a6a8929d5de4 Mon Sep 17 00:00:00 2001 From: Ibrahim Awwal Date: Thu, 13 Sep 2012 19:58:17 -0700 Subject: [PATCH 320/364] Remove dead code. --- .../django_comment_client/forum/views.py | 62 ------------------- 1 file changed, 62 deletions(-) diff --git a/lms/djangoapps/django_comment_client/forum/views.py b/lms/djangoapps/django_comment_client/forum/views.py index 2d1c1add45..e11de15844 100644 --- a/lms/djangoapps/django_comment_client/forum/views.py +++ b/lms/djangoapps/django_comment_client/forum/views.py @@ -48,66 +48,6 @@ def render_accordion(request, course, discussion_id): return render_to_string('discussion/_accordion.html', context) -def render_discussion(request, course_id, threads, *args, **kwargs): - discussion_id = kwargs.get('discussion_id') - user_id = kwargs.get('user_id') - discussion_type = kwargs.get('discussion_type', 'inline') - query_params = kwargs.get('query_params', {}) - - template = { - 'inline': 'discussion/_inline.html', - 'forum': 'discussion/_forum.html', - 'user': 'discussion/_user_active_threads.html', - }[discussion_type] - - base_url = { - 'inline': (lambda: reverse('django_comment_client.forum.views.inline_discussion', args=[course_id, discussion_id])), - 'forum': (lambda: reverse('django_comment_client.forum.views.forum_form_discussion', args=[course_id])), - 'user': (lambda: reverse('django_comment_client.forum.views.user_profile', args=[course_id, user_id])), - }[discussion_type]() - - user_info = cc.User.from_django_user(request.user).to_dict() - - def infogetter(thread): - return utils.get_annotated_content_infos(course_id, thread, request.user, user_info) - - annotated_content_info = reduce(merge_dict, map(infogetter, threads), {}) - - if discussion_type != 'inline': - course = get_course_with_access(request.user, course_id, 'load') - - for thread in threads: - courseware_context = get_courseware_context(thread, course) - if courseware_context: - thread.update(courseware_context) - - context = { - 'threads': map(utils.safe_content, threads), - 'discussion_id': discussion_id, - 'user_id': user_id, - 'course_id': course_id, - 'request': request, - 'performed_search': _should_perform_search(request), - 'pages_nearby_delta': PAGES_NEARBY_DELTA, - 'discussion_type': discussion_type, - 'base_url': base_url, - 'query_params': strip_blank(strip_none(extract(query_params, ['page', 'sort_key', 'sort_order', 'tags', 'text']))), - 'annotated_content_info': json.dumps(annotated_content_info), - #'discussion_data': json.dumps({ (discussion_id or user_id): map(utils.safe_content, threads) }) - # TODO: Delete the above, nothing uses this - } - context = dict(context.items() + query_params.items()) - return render_to_string(template, context) - -def render_inline_discussion(*args, **kwargs): - return render_discussion(discussion_type='inline', *args, **kwargs) - -def render_forum_discussion(*args, **kwargs): - return render_discussion(discussion_type='forum', *args, **kwargs) - -def render_user_discussion(*args, **kwargs): - return render_discussion(discussion_type='user', *args, **kwargs) - def get_threads(request, course_id, discussion_id=None, per_page=THREADS_PER_PAGE): """ This may raise cc.utils.CommentClientError or @@ -326,8 +266,6 @@ def user_profile(request, course_id, user_id): query_params['page'] = page query_params['num_pages'] = num_pages -# content = render_user_discussion(request, course_id, threads, user_id=user_id, query_params=query_params) - if request.is_ajax(): return utils.JsonResponse({ 'html': content, From 6b8e2c78abc75ae1ec2466dd1c88e5c5548ee255 Mon Sep 17 00:00:00 2001 From: Arjun Singh Date: Thu, 13 Sep 2012 21:58:59 -0700 Subject: [PATCH 321/364] Allow students to delete threads / respones; prepare for edit view for response comments (but not complete) --- .../django_comment_client/permissions.py | 4 +- .../views/response_comment_view.coffee | 49 +++++++++---------- .../discussion/_underscore_templates.html | 2 +- 3 files changed, 25 insertions(+), 30 deletions(-) diff --git a/lms/djangoapps/django_comment_client/permissions.py b/lms/djangoapps/django_comment_client/permissions.py index 352d4cc187..bc51b14eb5 100644 --- a/lms/djangoapps/django_comment_client/permissions.py +++ b/lms/djangoapps/django_comment_client/permissions.py @@ -76,12 +76,12 @@ def check_conditions_permissions(user, permissions, course_id, **kwargs): VIEW_PERMISSIONS = { 'update_thread' : ['edit_content', ['update_thread', 'is_open', 'is_author']], 'create_comment' : [["create_comment", "is_open"]], - 'delete_thread' : ['delete_thread'], + 'delete_thread' : ['delete_thread', ['update_thread', 'is_author']], 'update_comment' : ['edit_content', ['update_comment', 'is_open', 'is_author']], 'endorse_comment' : ['endorse_comment'], 'openclose_thread' : ['openclose_thread'], 'create_sub_comment': [['create_sub_comment', 'is_open']], - 'delete_comment' : ['delete_comment'], + 'delete_comment' : ['delete_comment', ['update_comment', 'is_open', 'is_author']], 'vote_for_comment' : [['vote', 'is_open']], 'undo_vote_for_comment': [['unvote', 'is_open']], 'vote_for_thread' : [['vote', 'is_open']], diff --git a/lms/static/coffee/src/discussion/views/response_comment_view.coffee b/lms/static/coffee/src/discussion/views/response_comment_view.coffee index 3de715692b..f0bb9757d8 100644 --- a/lms/static/coffee/src/discussion/views/response_comment_view.coffee +++ b/lms/static/coffee/src/discussion/views/response_comment_view.coffee @@ -2,35 +2,30 @@ if Backbone? class @ResponseCommentView extends DiscussionContentView tagName: "li" - initLocal: -> - # TODO .response-local is the parent of the comments so @$local is null, not sure what was intended here... - @$local = @$el.find(".response-local") - @$delegateElement = @$local + $: (selector) -> + @$el.find(selector) + + initialize: -> + super() + @createShowView() render: -> - @template = _.template($("#response-comment-template").html()) - params = @model.toJSON() - params['deep'] = @model.hasOwnProperty('parent') - if @model.hasOwnProperty('parent') - params['parent_id'] = @model.parent.id - params['parent_username'] = @model.parent.get('username') - @$el.html(@template(params)) - @initLocal() - @delegateEvents() - @renderAttrs() - @markAsStaff() - @$el.find(".timeago").timeago() - @convertMath() + @renderShowView() @ - convertMath: -> - body = @$el.find(".response-body") - body.html DiscussionUtil.postMathJaxProcessor DiscussionUtil.markdownWithHighlight body.html() - # This removes paragraphs so that comments are more compact - body.children("p").each (index, elem) -> - $(elem).replaceWith($(elem).html()) - MathJax.Hub.Queue ["Typeset", MathJax.Hub, body[0]] + createShowView: () -> - markAsStaff: -> - if DiscussionUtil.isStaff(@model.get("user_id")) - @$el.find("a.profile-link").after('staff') + if @editView? + @editView.undelegateEvents() + @editView.$el.empty() + @editView = null + + @showView = new ResponseCommentShowView(model: @model) + + renderSubView: (view) -> + view.setElement(@$el) + view.render() + view.delegateEvents() + + renderShowView: () -> + @renderSubView(@showView) diff --git a/lms/templates/discussion/_underscore_templates.html b/lms/templates/discussion/_underscore_templates.html index d6011e75c0..5fc84c6676 100644 --- a/lms/templates/discussion/_underscore_templates.html +++ b/lms/templates/discussion/_underscore_templates.html @@ -93,7 +93,7 @@ - + + + + From 7c86f324ea43b4784d278c68add239b8e777c153 Mon Sep 17 00:00:00 2001 From: Arjun Singh Date: Fri, 14 Sep 2012 22:55:45 -0700 Subject: [PATCH 360/364] Fixes the one broken thread in prod; it had no lettters in its ID, so the id was being cast to a number. --- .../src/discussion/views/discussion_thread_list_view.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee index 11e8168012..d4c144f808 100644 --- a/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee +++ b/lms/static/coffee/src/discussion/views/discussion_thread_list_view.coffee @@ -106,7 +106,7 @@ if Backbone? for thread in @displayedCollection.models content = @renderThread(thread) rendered.append content - content.wrap("
  • ") + content.wrap("
  • ") @$(".post-list").html(rendered.html()) @renderMorePages() From c47f0ffb47e93797042fd98f7273e53a8437a8a7 Mon Sep 17 00:00:00 2001 From: Ibrahim Awwal Date: Sat, 15 Sep 2012 00:30:52 -0700 Subject: [PATCH 361/364] Hopefully fix code formatting showing up on comments? But it doesn't seem to happen everywhere... --- lms/templates/discussion/_underscore_templates.html | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/lms/templates/discussion/_underscore_templates.html b/lms/templates/discussion/_underscore_templates.html index bf1eb596d4..cf5c10e595 100644 --- a/lms/templates/discussion/_underscore_templates.html +++ b/lms/templates/discussion/_underscore_templates.html @@ -120,9 +120,7 @@