Skip to content

Commit

Permalink
Merge pull request #2471 from edx/jbau/timed-capa
Browse files Browse the repository at this point in the history
HACKED TOGETHER time limit for DB class midterm
  • Loading branch information
jbau committed Feb 5, 2014
2 parents 18d6d41 + ef2f20a commit 25524f5
Show file tree
Hide file tree
Showing 2 changed files with 58 additions and 3 deletions.
41 changes: 39 additions & 2 deletions common/lib/xmodule/xmodule/capa_module.py
Original file line number Diff line number Diff line change
Expand Up @@ -141,7 +141,9 @@ class CapaFields(object):
student_answers = Dict(help="Dictionary with the current student responses", scope=Scope.user_state)
done = Boolean(help="Whether the student has answered the problem", scope=Scope.user_state)
seed = Integer(help="Random seed for this student", scope=Scope.user_state)

minutes_allowed = Integer(help="EXPERIMENTAL FEATURE: DO NOT USE. Number of minutes allowed to finish this assessment. Set 0 for no time-limit",
default=0, scope=Scope.settings)
time_started = Date(help="time student started this assessment", scope=Scope.user_state)
last_submission_time = Date(help="Last submission time", scope=Scope.user_state)
submission_wait_seconds = Integer(
display_name="Timer Between Attempts",
Expand Down Expand Up @@ -311,6 +313,12 @@ def set_state_from_lcp(self):
self.student_answers = lcp_state['student_answers']
self.seed = lcp_state['seed']

def set_time_started(self):
"""
Sets the time when the student started the module.
"""
self.time_started = datetime.datetime.now(UTC())

def set_last_submission_time(self):
"""
Set the module's last submission time (when the problem was checked)
Expand Down Expand Up @@ -551,13 +559,30 @@ def get_problem_html(self, encapsulate=True):
else:
check_button = False

problem_is_timed = self.minutes_allowed > 0

if problem_is_timed and not self.time_started:
self.set_time_started()

end_time_to_display = (self.time_started + datetime.timedelta(minutes=self.minutes_allowed)
if problem_is_timed
else None)

# because we use self.due and not self.close_date below, this is not the actual end_time, but the
# end_time we want to display to the user
if self.due and end_time_to_display:
end_time_to_display = min(self.due, end_time_to_display)

content = {'name': self.display_name_with_default,
'html': html,
'weight': self.weight,
}

context = {'problem': content,
'id': self.id,
'problem_is_timed': problem_is_timed,
'start_time': self.time_started,
'end_time_to_display': end_time_to_display,
'check_button': check_button,
'reset_button': self.should_show_reset_button(),
'save_button': self.should_show_save_button(),
Expand Down Expand Up @@ -642,6 +667,17 @@ def handle_ajax(self, dispatch, data):

return json.dumps(result, cls=ComplexEncoder)

def exceeded_time_limit(self):
"""
Has student used up allotted time, if set
"""
if self.minutes_allowed <= 0 or not self.time_started:
return False
now = datetime.datetime.now(UTC())
# built in hardcoded grace period of 5 min
time_limit_end = self.time_started + datetime.timedelta(minutes=(self.minutes_allowed + 5))
return now > time_limit_end

def is_past_due(self):
"""
Is it now past this problem's due date, including grace period?
Expand All @@ -657,7 +693,8 @@ def closed(self):
return True
if self.is_past_due():
return True

if self.exceeded_time_limit():
return True
return False

def is_submitted(self):
Expand Down
20 changes: 19 additions & 1 deletion lms/templates/problem.html
Original file line number Diff line number Diff line change
@@ -1,4 +1,8 @@
<%! from django.utils.translation import ugettext as _ %>
<%!
from django.utils.translation import ugettext as _
from xmodule.util.date_utils import get_time_display
from django.conf import settings
%>

<%namespace name='static' file='static_content.html'/>
<h2 class="problem-header">
Expand All @@ -8,6 +12,20 @@ <h2 class="problem-header">
<section class="problem-progress">
</section>

% if problem_is_timed:
<section class="time_limit">
<p>
${_("At {start_time}, you started this exam.").format(
start_time=get_time_display(start_time, coerce_tz=settings.TIME_ZONE))}
<br />
<b>
${_("By {end_time}, you must manually click the 'Final Submit' button below!").format(
end_time=get_time_display(end_time_to_display, coerce_tz=settings.TIME_ZONE))}
</b>
</p>
</section>
% endif

<section class="problem">
${ problem['html'] }

Expand Down

0 comments on commit 25524f5

Please sign in to comment.