Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions bases/rsptx/assignment_server_api/routers/student.py
Original file line number Diff line number Diff line change
Expand Up @@ -201,6 +201,7 @@ def sort_key(assignment):
lti1p1=is_lti1p1_course,
now=now,
visibility_map=visibility_map,
term_start_date=course.term_start_date,
settings=settings,
base_url=construct_course_url(course),
activity_info="{}",
Expand Down Expand Up @@ -1020,6 +1021,7 @@ async def doAssignment(
questions_score=questions_score,
readings_score=readings_score,
user=user,
term_start_date=course.term_start_date,
user_id=user.username, # _base.html for ptx student pages needs user_id
base_course=course.base_course,
# gradeRecordingUrl=URL('assignments', 'record_grade'),
Expand Down
1 change: 1 addition & 0 deletions bases/rsptx/interactives/ptxrs-bootstrap.less
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
border-radius: 5px;
height: 20px;
position: relative;
margin: 10px auto;
}


Expand Down
8 changes: 5 additions & 3 deletions bases/rsptx/interactives/public/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -235,9 +235,11 @@ <h2>


<div id="scprogresscontainer">
You have attempted <span id="scprogresstotal"></span> of
<span id="scprogressposs"></span> activities on this page
<div id="subchapterprogress"></div>
<div id="scprogress-activity-count">
You have attempted <span id="scprogresstotal"></span> of
<span id="scprogressposs"></span> activities on this page.
</div>
<div id="subchapterprogress" aria-label="Page progress"></div>
</div>


Expand Down
7 changes: 7 additions & 0 deletions bases/rsptx/interactives/runestone/common/css/runestone.css
Original file line number Diff line number Diff line change
Expand Up @@ -1432,4 +1432,11 @@ legend {

.autopermalink {
display: none;
}


.course-not-started-warning {
margin-bottom: 20px;
margin-top: 20px;
padding: 15px;
}
56 changes: 56 additions & 0 deletions bases/rsptx/interactives/runestone/common/js/bookfuncs.js
Original file line number Diff line number Diff line change
Expand Up @@ -348,6 +348,25 @@ export const NON_CONTENT_PAGES = [
"search.html",
];

export function isCourseStarted() {
let startDate = eBookConfig.termStartDate; // format is "2026-09-22"
if (!startDate) {
return false;
}
let today = new Date();
let start = new Date(startDate);
return today >= start;
}

function courseNotStartedMessage() {
const formattedDate = new Date(eBookConfig.termStartDate).toLocaleDateString(undefined, {
year: 'numeric',
month: 'long',
day: 'numeric'
});
return ("Course has not started yet. Progress will be tracked starting on " + formattedDate);
}

/** True when pathname names one of the NON_CONTENT_PAGES. */
export function isNonContentPage(pathname = window.location.pathname) {
let page = pathname.split("/").pop().toLowerCase();
Expand Down Expand Up @@ -440,6 +459,11 @@ export class PageProgressBar {
} catch (e) {
value = 0;
}
let progressText = document.getElementById("scprogress-activity-count");
// Warn if course not started
if(progressText && !isCourseStarted()) {
progressText.appendChild(document.createTextNode(courseNotStartedMessage()));
}
Comment on lines +462 to +466
// Replace #subchapterprogress div with a native <progress> element if not already done
let subchapterprogress = document.getElementById("subchapterprogress");
if (subchapterprogress && subchapterprogress.tagName !== "PROGRESS") {
Expand Down Expand Up @@ -1080,6 +1104,22 @@ async function handlePageSetup() {
}
}
}

// PTX generated pages may have stale HTML. Forcibly re-render the content
// of the progress container. Any logic that modifies the progress container
// should be done after this point, or it will be overwritten.
const scprogresscontainer = document.getElementById(
"scprogresscontainer",
);
if (scprogresscontainer)
scprogresscontainer.innerHTML = `
<div id="scprogress-activity-count">
You have attempted <span id="scprogresstotal"></span> of
<span id="scprogressposs"></span> activities on this page.
</div>
<div id="subchapterprogress" aria-label="Page progress"></div>
`;

console.log(`This page served by ${eBookConfig.served_by}`);
if (eBookConfig.isLoggedIn) {
mess = `username: ${eBookConfig.username}`;
Expand All @@ -1094,7 +1134,23 @@ async function handlePageSetup() {
}
}
document.dispatchEvent(new Event("runestone:login"));

addReadingList();

// Warn if the course has not started yet
if (!isCourseStarted()) {
const ptxContent = document.getElementById("ptx-content");
if (ptxContent) {
const warningContainer = document.createElement("div");
warningContainer.className = "ptx-runestone-container";
const warningDiv = document.createElement("div");
warningDiv.className = "course-not-started-warning alert alert-danger";
warningDiv.textContent = courseNotStartedMessage();
warningContainer.appendChild(warningDiv);
ptxContent.insertBefore(warningContainer, ptxContent.firstChild);
}
}

// Only show the StudyClues widget for certain base courses and when the path includes "/ns/books/".
// This is a temporary measure to limit the widget to courses that are known to work well with it and to avoid showing it on non-book pages where it may not be as useful.
if (shouldShowStudyCluesWidget()) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -400,7 +400,11 @@ <h4>Before you keep reading...</h4>
{% endif %}

<div id="scprogresscontainer">
You have attempted <span id="scprogresstotal"></span> of <span id="scprogressposs"></span> activities on this page <div id="subchapterprogress" aria-label="Page progress"></div>
<div id="scprogress-activity-count">
You have attempted <span id="scprogresstotal"></span> of
<span id="scprogressposs"></span> activities on this page.
</div>
<div id="subchapterprogress" aria-label="Page progress"></div>
</div>

{% include "subchapter.html" %}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,9 +22,11 @@ import {
/** The markup a book emits for the progress bar. */
function progressMarkup() {
return `
<div id="scprogresscontainer">You have attempted
<span id="scprogresstotal"></span> of <span id="scprogressposs"></span>
activities on this page.
<div id="scprogresscontainer">
<div id="scprogress-activity-count">
You have attempted <span id="scprogresstotal"></span> of
<span id="scprogressposs"></span> activities on this page.
</div>
<div id="subchapterprogress" aria-label="Page progress"></div>
</div>`;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ <h3>{{ course.course_name }}</h3>
<div class="settingsbox">
<label for="start_date">Term Start Date</label>
<input type="text" id="start_date" value="{{ start_date }}" onchange="updateCourse(this, 'new_date')">
<div class="setting-description">Set the start date for your course term</div>
<div class="setting-description">Set this to the first day students will be able to do work in the course. Student work before this date will not be counted.</div>
</div>

<div class="settingsbox">
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -147,7 +147,8 @@ <h4 class="book-section">{{ section }}</h4>
<label><input type="checkbox" name="allowpairs" value="true" {% if submitted is defined and submitted.allowpairs == 'true' %}checked{% endif %}> Enable <strong>experimental</strong> pair programming features.</label><br>
<label><input type="checkbox" name="instructor" value="yes" {% if submitted is defined and submitted.instructor == 'yes' %}checked{% else %}checked{% endif %}> Make me the Instructor of this course.</label><br>
<label for="startdate">Term start date</label>
<input type="date" name="startdate" id="startdate" class="form-control" required value="{{ submitted.startdate if submitted is defined else current_date }}">
<input type="date" name="startdate" id="startdate" class="form-control" required value="{{ submitted.startdate if submitted is defined else current_date }}" aria-describedby="startdate-hint">
<small class="form-text text-muted" id="startdate-hint">Set this to the first day students will be able to do work in the course. Student work before this date will not be counted.</small>
</div>
<div class="form-section">
<div class="step-title">Step 6: (Optional !!): Support Runestone Academy</div>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,11 @@
{% endblock %}

{% block content %}

{% if using_ptx_base != "true" %}
{% include 'common/ebook_config.html' %}
{% endif %}

<section class="assignment-page">
<h1 class="heading">Choose Assignment</h1>

Expand Down
1 change: 1 addition & 0 deletions components/rsptx/templates/common/ebook_config.html
Original file line number Diff line number Diff line change
Expand Up @@ -32,4 +32,5 @@
eBookConfig.authorServerUrl = "{{settings.author_server_url}}";
eBookConfig.websocketUrl = "{{settings.websocket_url}}"
eBookConfig.enableDebug = true ? "{{settings.debug}}" == "True" : false;
eBookConfig.termStartDate = "{{ course.term_start_date | default('', true) }}";
</script>
Loading