Description:
wip
Commit status:
[Not Reviewed]
References:
Comments:
0 Commit comments 0 Inline Comments
Unresolved TODOs:
There are no unresolved TODOs
Add another comment

r880:31e27f513ce9 - - 9 files changed: 191 inserted, 160 deleted

@@ -148,6 +148,9
148
148
149 @summary = { attempt: user.count, solve: 0 }
149 @summary = { attempt: user.count, solve: 0 }
150 user.each_value { |v| @summary[:solve] += 1 if v == 1 }
150 user.each_value { |v| @summary[:solve] += 1 if v == 1 }
151 +
152 + #for new graph
153 + @chart_dataset = @problem.get_jschart_history.to_json.html_safe
151 end
154 end
152
155
153 def manage
156 def manage
@@ -248,7 +248,7
248 #@histogram = { data: Array.new(range,0), summary: {} }
248 #@histogram = { data: Array.new(range,0), summary: {} }
249 @summary = {count: 0, solve: 0, attempt: 0}
249 @summary = {count: 0, solve: 0, attempt: 0}
250 user = Hash.new(0)
250 user = Hash.new(0)
251 - Submission.where(problem_id: @problem.id).find_each do |sub|
251 + Submission.where(problem_id: @problem.id).includes(:language).each do |sub|
252 #histogram
252 #histogram
253 d = (DateTime.now.in_time_zone - sub.submitted_at) / 24 / 60 / 60
253 d = (DateTime.now.in_time_zone - sub.submitted_at) / 24 / 60 / 60
254 #@histogram[:data][d.to_i] += 1 if d < range
254 #@histogram[:data][d.to_i] += 1 if d < range
@@ -257,7 +257,8
257 @summary[:count] += 1
257 @summary[:count] += 1
258 user[sub.user_id] = [user[sub.user_id], (sub.points >= @problem.full_score) ? 1 : 0].max
258 user[sub.user_id] = [user[sub.user_id], (sub.points >= @problem.full_score) ? 1 : 0].max
259
259
260 - lang = Language.find_by_id(sub.language_id)
260 + #lang = Language.find_by_id(sub.language_id)
261 + lang = sub.language
261 next unless lang
262 next unless lang
262 next unless sub.points >= @problem.full_score
263 next unless sub.points >= @problem.full_score
263
264
@@ -130,27 +130,21
130
130
131 def stat
131 def stat
132 @user = User.find(params[:id])
132 @user = User.find(params[:id])
133 - @submission = Submission.joins(:problem).where(user_id: params[:id])
133 + @submission = Submission.joins(:problem).includes(:problem).includes(:language).where(user_id: params[:id])
134 @submission = @submission.where('problems.available = true') unless current_user.admin?
134 @submission = @submission.where('problems.available = true') unless current_user.admin?
135
135
136 - range = 120
137 - @histogram = { data: Array.new(range,0), summary: {} }
138 @summary = {count: 0, solve: 0, attempt: 0}
136 @summary = {count: 0, solve: 0, attempt: 0}
139 problem = Hash.new(0)
137 problem = Hash.new(0)
140
138
141 @submission.find_each do |sub|
139 @submission.find_each do |sub|
142 - #histogram
143 - d = (DateTime.now.in_time_zone - sub.submitted_at) / 24 / 60 / 60
144 - @histogram[:data][d.to_i] += 1 if d < range
145 -
146 @summary[:count] += 1
140 @summary[:count] += 1
147 next unless sub.problem
141 next unless sub.problem
148 problem[sub.problem] = [problem[sub.problem], ( (sub.try(:points) || 0) >= sub.problem.full_score) ? 1 : 0].max
142 problem[sub.problem] = [problem[sub.problem], ( (sub.try(:points) || 0) >= sub.problem.full_score) ? 1 : 0].max
149 end
143 end
150
144
151 - @histogram[:summary][:max] = [@histogram[:data].max,1].max
152 @summary[:attempt] = problem.count
145 @summary[:attempt] = problem.count
153 problem.each_value { |v| @summary[:solve] += 1 if v == 1 }
146 problem.each_value { |v| @summary[:solve] += 1 if v == 1 }
147 + @chart_dataset = @user.get_jschart_user_sub_history.to_json.html_safe
154 end
148 end
155
149
156 def toggle_activate
150 def toggle_activate
@@ -314,6 +314,21
314 User.update_all(:last_ip => nil)
314 User.update_all(:last_ip => nil)
315 end
315 end
316
316
317 + def get_jschart_user_sub_history
318 + start = 4.month.ago.beginning_of_day
319 + start_date = start.to_date
320 + count = Submission.where(user: self).where('submitted_at >= ?', start).group('DATE(submitted_at)').count
321 + i = 0
322 + label = []
323 + value = []
324 + while (start_date + i < Time.zone.now.to_date)
325 + label << (start_date+i).strftime("%d-%b")
326 + value << (count[start_date+i] || 0)
327 + i+=1
328 + end
329 + return {labels: label,datasets: [label:'sub',data: value, backgroundColor: 'rgba(54, 162, 235, 0.2)', borderColor: 'rgb(75, 192, 192)']}
330 + end
331 +
317 #create multiple user, one per lines of input
332 #create multiple user, one per lines of input
318 def self.create_from_list(lines)
333 def self.create_from_list(lines)
319 error_logins = []
334 error_logins = []
@@ -3,21 +3,21
3 - else
3 - else
4 - if local_assigns[:show_id]
4 - if local_assigns[:show_id]
5 .row
5 .row
6 - .col-3.text-secondary
6 + .col-3.fw-bold
7 - Sub ID:
7 + Sub ID
8 - %strong.col-9= submission.id
8 + .col-9.text-secondary-x= submission.id
9 - unless submission.graded_at
9 - unless submission.graded_at
10 .row
10 .row
11 - .col-3.text-secondary= t 'main.submitted_at'
11 + .col-3.fw-bold= t 'main.submitted_at'
12 - %strong.col-9= format_full_time_ago(submission.submitted_at.localtime)
12 + .col-9.text-secondary-x= format_full_time_ago(submission.submitted_at.localtime)
13 - else
13 - else
14 .row
14 .row
15 - .col-3.text-secondary= t 'main.graded_at'
15 + .col-3.fw-bold= t 'main.graded_at'
16 - %strong.col-9= format_full_time_ago(submission.graded_at.localtime)
16 + .col-9.text-secondary-x= format_full_time_ago(submission.graded_at.localtime)
17 - if GraderConfiguration['ui.show_score']
17 - if GraderConfiguration['ui.show_score']
18 .row
18 .row
19 - .col-3.text-secondary=t 'main.score'
19 + .col-3.fw-bold=t 'main.score'
20 - %strong.col-9
20 + .col-9.text-secondary-x
21 = (submission.points*100/submission.problem.full_score).to_i
21 = (submission.points*100/submission.problem.full_score).to_i
22 %tt.grader-comment
22 %tt.grader-comment
23 = " [#{submission.grader_comment}]"
23 = " [#{submission.grader_comment}]"
@@ -2,51 +2,29
2 = stylesheet_link_tag 'problems'
2 = stylesheet_link_tag 'problems'
3 = javascript_include_tag 'local_jquery'
3 = javascript_include_tag 'local_jquery'
4
4
5 - :javascript
6 - $(document).ready( function() {
7 - function shiftclick(start,stop,value) {
8 - $('tr input').each( function(id,input) {
9 - var $input=$(input);
10 - var iid=parseInt($input.attr('id').split('-')[2]);
11 - if(iid>=start&&iid<=stop){
12 - $input.prop('checked',value)
13 - }
14 - });
15 - }
16 -
17 - $('tr input').click( function(e) {
18 - if (e.shiftKey) {
19 - stop = parseInt($(this).attr('id').split('-')[2]);
20 - var orig_stop = stop
21 - if (typeof start !== 'undefined') {
22 - if (start > stop) {
23 - var tmp = start;
24 - start = stop;
25 - stop = tmp;
26 - }
27 - shiftclick(start,stop,$(this).is(':checked') )
28 - }
29 - start = orig_stop
30 - } else {
31 - start = parseInt($(this).attr('id').split('-')[2]);
32 - }
33 - });
34 - });
35
5
36
6
37 %h1 Manage problems
7 %h1 Manage problems
38
8
39 %p= link_to '[Back to problem list]', problems_path
9 %p= link_to '[Back to problem list]', problems_path
40
10
41 - = form_tag :action=>'do_manage' do
11 + = form_with url: do_manage_problems_path do |f|
42 - .panel.panel-primary
12 + .card.border-primary.mb-2
43 - .panel-heading
13 + .card-header.text-bg-primary.border-primary
44 Action
14 Action
45 - .panel-body
15 + .card-body
46 .submit-box
16 .submit-box
47 What do you want to do to the selected problem?
17 What do you want to do to the selected problem?
48 %br/
18 %br/
49 (You can shift-click to select a range of problems)
19 (You can shift-click to select a range of problems)
20 + .row
21 + .col-md-auto
22 + = f.check_box :change_date_added, class: 'form-check-input'
23 + .col-md-auto
24 + .form-check-label
25 + Change "Date added" to
26 + .col-md-auto
27 +
50 %ul.form-inline
28 %ul.form-inline
51 %li
29 %li
52 Change "Date added" to
30 Change "Date added" to
@@ -107,13 +85,45
107 = "(#{contest.name} [#{link_to 'x', :action => 'remove_contest', :id => problem.id, :contest_id => contest.id }])"
85 = "(#{contest.name} [#{link_to 'x', :action => 'remove_contest', :id => problem.id, :contest_id => contest.id }])"
108
86
109 :javascript
87 :javascript
110 - $('.input-group.date').datetimepicker({
88 +
111 - format: 'DD/MMM/YYYY',
89 + $(document).on('import-map-loaded', function() {
112 - showTodayButton: true,
90 + function shiftclick(start,stop,value) {
113 - locale: 'en',
91 + $('tr input').each( function(id,input) {
114 - widgetPositioning: {horizontal: 'auto', vertical: 'bottom'},
92 + var $input=$(input);
93 + var iid=parseInt($input.attr('id').split('-')[2]);
94 + if(iid>=start&&iid<=stop){
95 + $input.prop('checked',value)
96 + }
97 + });
98 + }
115
99
100 + $('tr input').click( function(e) {
101 + if (e.shiftKey) {
102 + stop = parseInt($(this).attr('id').split('-')[2]);
103 + var orig_stop = stop
104 + if (typeof start !== 'undefined') {
105 + if (start > stop) {
106 + var tmp = start;
107 + start = stop;
108 + stop = tmp;
109 + }
110 + shiftclick(start,stop,$(this).is(':checked') )
111 + }
112 + start = orig_stop
113 + } else {
114 + start = parseInt($(this).attr('id').split('-')[2]);
115 + }
116 + });
117 +
118 + $('.input-group.date').datetimepicker({
119 + format: 'DD/MMM/YYYY',
120 + showTodayButton: true,
121 + locale: 'en',
122 + widgetPositioning: {horizontal: 'auto', vertical: 'bottom'},
123 +
124 + });
125 +
126 + $('.datatable').DataTable({
127 + paging: false
128 + });
116 });
129 });
117 - $('.datatable').DataTable({
118 - paging: false
119 - });
@@ -4,28 +4,34
4 }
4 }
5
5
6 %h1 Problem stat: #{@problem.name}
6 %h1 Problem stat: #{@problem.name}
7 - %h2 Overview
7 +
8 + .row.mb-3
9 + .col-md-8
10 + .card
11 + .card-body
12 + %h2.card-title Submission History
13 + %canvas#chart{height: '50px'}
8
14
9 - .row
15 + .col-md-4
10 - .col-md-2
16 + .card
11 - %strong Name:
17 + .card-body
12 - .col-md-10
18 + %h2.card-title General Info
13 - = @problem.full_name #in_place_editor_field :problem, :full_name, {}, :rows=>1
19 + .row
14 - = link_to_description_if_any "[#{t 'main.problem_desc'}] <span class='glyphicon glyphicon-file'></span>".html_safe, @problem
20 + .col-sm-6
15 - .row
21 + Name
16 - .col-md-2.strong
22 + .col-sm-6
17 - %strong Submissions:
23 + = @problem.full_name #in_place_editor_field :problem, :full_name, {}, :rows=>1
18 - .col-md-10
24 + = link_to_description_if_any "[#{t 'main.problem_desc'}] <span class='glyphicon glyphicon-file'></span>".html_safe, @problem
19 - = @submissions.count
25 + .row
20 - .row
26 + .col-sm-6
21 - .col-md-2.strong
27 + Subs
22 - %strong Solved/Attemped User
28 + .col-sm-6
23 - .col-md-10
29 + = @submissions.count
24 - #{@summary[:solve]}/#{@summary[:attempt]} (#{(@summary[:solve]*100.0/@summary[:attempt]).round(1)}%)
30 + .row
25 -
31 + .col-sm-6
26 -
32 + Solved/Attempted User
27 - %h2 Submissions Count
33 + .col-sm-6
28 - = render partial: 'application/bar_graph', locals: { histogram: @histogram }
34 + #{@summary[:solve]}/#{@summary[:attempt]} (#{(@summary[:solve]*100.0/@summary[:attempt]).round(1)}%)
29
35
30 %h2 Submissions
36 %h2 Submissions
31 - if @submissions and @submissions.count > 0
37 - if @submissions and @submissions.count > 0
@@ -58,6 +64,27
58 No submission
64 No submission
59
65
60 :javascript
66 :javascript
61 - $("#main_table").DataTable({
67 + $(document).on('import-map-loaded',(e) => {
62 - paging: false
68 + //init datatable
69 + $("#main_table").DataTable({
70 + paging: false
71 + });
72 +
73 + //history graph
74 + data = #{@chart_dataset}
75 + config = {
76 + type: 'bar',
77 + data: data,
78 + options: {
79 + plugins: {
80 + legend: {
81 + display: false
82 + },
83 + },
84 + }
85 + }
86 + Chart.defaults.font.size = 15
87 + //Chart.defaults.font.family = 'Sarabun Light'
88 + chart = new Chart($('#chart'),config)
63 });
89 });
90 +
@@ -1,42 +1,46
1 - - content_for :header do
2 - = javascript_include_tag 'local_jquery'
3 -
4 - :javascript
5 - $(function () {
6 - $('#submission_table').tablesorter({widgets: ['zebra']});
7 - });
8
1
9 :css
2 :css
10 .fix-width {
3 .fix-width {
11 font-family: Droid Sans Mono,Consolas, monospace, mono, Courier New, Courier;
4 font-family: Droid Sans Mono,Consolas, monospace, mono, Courier New, Courier;
12 }
5 }
13
6
14 - %h1= @user.full_name
7 + %h1 User stats
8 + %h5.text-secondary= @user.login
9 +
10 + .row.my-3
11 + .col-md-8
12 + .card
13 + .card-body
14 + %h2.card-title Sub Info
15 + %canvas#chart{height: '50px'}
15
16
16 - <b>Login:</b> #{@user.login} <br/>
17 + .col-md-4
17 - <b>Full name:</b> #{@user.full_name} <br />
18 + .card
19 + .card-body
20 + %h2.card-title General Info
21 + .row
22 + .col-sm-6.fw-bold
23 + Login
24 + .col-sm-6
25 + = @user.login
26 + .row
27 + .col-sm-6.fw-bold
28 + Full name
29 + .col-sm-6
30 + = @user.full_name
31 + .row
32 + .col-sm-6.fw-bold
33 + Subs
34 + .col-sm-6
35 + = @summary[:count]
36 + .row
37 + .col-sm-6.fw-bold
38 + Solved/Attempted Problem
39 + .col-sm-6
40 + #{@summary[:solve]}/#{@summary[:attempt]} (#{(@summary[:solve]*100.0/@summary[:attempt]).round(1)}%)
18
41
19
42
20 - %h2 Problem Stat
43 + %table#main_table.table.table-striped
21 - %table.info
22 - %thead
23 - %tr.info-head
24 - %th Stat
25 - %th Value
26 - %tbody
27 - %tr{class: cycle('info-even','info-odd')}
28 - %td.info_param Submissions
29 - %td= @summary[:count]
30 - %tr{class: cycle('info-even','info-odd')}
31 - %td.info_param Solved/Attempted Problem
32 - %td #{@summary[:solve]}/#{@summary[:attempt]} (#{(@summary[:solve]*100.0/@summary[:attempt]).round(1)}%)
33 -
34 - %h2 Submission History
35 -
36 - =render partial: 'application/bar_graph', locals: {histogram: @histogram, param: {bar_width: 7}}
37 -
38 -
39 - %table#submission_table.table.table-striped
40 %thead
44 %thead
41 %tr
45 %tr
42 %th ID
46 %th ID
@@ -65,6 +69,27
65
69
66
70
67 :javascript
71 :javascript
68 - $("#submission_table").DataTable({
72 + $(document).on('import-map-loaded',(e) => {
69 - paging: false
73 + //init datatable
74 + $("#main_table").DataTable({
75 + paging: false
76 + });
77 +
78 + //history graph
79 + data = #{@chart_dataset}
80 + config = {
81 + type: 'bar',
82 + data: data,
83 + options: {
84 + plugins: {
85 + legend: {
86 + display: false
87 + },
88 + },
89 + }
90 + }
91 + Chart.defaults.font.size = 15
92 + //Chart.defaults.font.family = 'Sarabun Light'
93 + chart = new Chart($('#chart'),config)
70 });
94 });
95 +
deleted file
You need to be logged in to leave comments. Login now