Skip to content

Commit

Permalink
feat(KUI-1149): redesign of course page (#360)
Browse files Browse the repository at this point in the history
* feat(KUI-1149): add Tabs component (based on tabs from headless-ui)

* feat(KUI-1149): add main structure with round dropdown to new semester tabs

* feat(KUI-1149): add new RoundInformation component (will replace most of RoundInformationOneCol)

* fix(KUI-1149): fix reset bug in useSemesterRoundState and simplified DropdownRounds

* feat(KUI-1149): add new RoundApplicationButton component (and remove old)

* feat(KUI-1149): move syllabys pdf section to own component

* feat(KUI-1149): remove old RoundInformationOneCol and rewrite/add tests for RoundInformation

* fix(KUI-1149): remove use of deprecated defaultProps in Alert

* feat(KUI-1149): moved main couse info to seperate component, added special case for courses without course rounds

* test(KUI-1149): fixed course page test cases

* feat(KUI-1149): replace tabs implementation with radio buttons

* feat(KUI-1149): remove tab component

* feat(KUI-1149): add media query style

* feat(KUI-1149): update translation texts

* fix: npm audit fix

* feat(KUI-1149): update style of semester selector ("tabs"/radio buttons)
  • Loading branch information
karlandindrakryggen authored Aug 16, 2024
1 parent b1f5777 commit 2e663d1
Show file tree
Hide file tree
Showing 39 changed files with 1,037 additions and 1,109 deletions.
15 changes: 4 additions & 11 deletions i18n/messages.en.js
Original file line number Diff line number Diff line change
Expand Up @@ -54,14 +54,12 @@ module.exports = {
header_no_syllabus: 'Course syllabus and course offering missing',
label_no_syllabus:
'Course syllabus missing, showing available course information. Course offering also missing for current semester as well as for previous and coming semesters',
label_syllabus_missing: 'Course syllabus missing',
syllabus_marker_aria_label: 'Retrieved from course syllabus',
label_programme_year: 'year ',
label_postgraduate_course: 'Postgraduate courses at ',
label_course_cancelled: 'This course has been cancelled.',
label_last_exam: 'Last planned examination: ',
label_edit: 'Administer About course',
header_no_rounds: 'Course offering missing',
lable_no_rounds: 'Course offerings are missing for current or upcoming semesters.',
label_course_memo: 'Course memo',
label_link_course_memo: 'Link to course memo',
Expand All @@ -81,8 +79,9 @@ module.exports = {
CANCELLED: 'This offering is cancelled',
FULL: 'This offering is full',
},
header_dropdown_menu_navigation: 'Choose semester and course offering for page content',
header_dropdown_menue: 'Valid for',
header_dropdown_menu_navigation:
'Choose semester and course offering to see current information and more about the course, such as course syllabus, study period, and application information.',
header_dropdown_menue: 'Information per course offering',
header_dropdown_menu_aria_label: 'Information about choosing semester and course offering',
header_course_info: 'Course information',
header_content: 'Content and learning outcomes',
Expand All @@ -92,15 +91,11 @@ module.exports = {
header_statistics: 'Course statistics',
header_syllabuses: 'Course syllabuses archive',
header_further: 'Further information',
header_select_course: 'Application',
header_postgraduate_course: 'Postgraduate course ',
no_schedule: 'No schedule',
no_schedule_published: 'Schedule is not published',
no_memo_published: 'Course memo is not published',
no_memo_connection: 'Course memo cannot be displayed',
header_no_round_selected: 'Choose semester and course offering',
no_round_selected:
'Choose semester and course offering to see current information and more about the course, such as course syllabus, study period, and application information.',
round_seats_default_info:
'Course offering may be cancelled if number of admitted are less than minimum of places. If there are more applicants than number of places selection will be made.',
round_seats_info: 'The selection results are based on:',
Expand Down Expand Up @@ -174,9 +169,7 @@ module.exports = {
course_application_info: 'Information for research students about course offerings',
},
courseRoundInformation: {
header_round: 'About course offering',
round_information_aria_label: 'Information about course offering',
round_header: 'For course offering',
round_header: 'Information for',
round_application_code: 'Application code',
round_max_seats: 'Number of places',
round_no_seats_limit: 'Places are not limited',
Expand Down
15 changes: 4 additions & 11 deletions i18n/messages.se.js
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,6 @@ module.exports = {
header_no_syllabus: 'Kursplan och kursomgångar saknas',
label_no_syllabus:
'Kursplan saknas, kursinformationen som visas är övrig kursinformation. Även kursomgångar saknas för tidigare och kommande terminer, samt innevarande termin.',
label_syllabus_missing: 'Kursplan saknas',
syllabus_marker_aria_label: 'Informationen tillhör kursplan',
label_programme_year: 'Åk ',
label_postgraduate_course: 'Forskarkurser på ',
Expand All @@ -64,7 +63,6 @@ module.exports = {
label_edit: 'Administrera Om kursen',
label_course_memo: 'Kurs-PM',
label_link_course_memo: 'Länk till kurs-PM',
header_no_rounds: 'Kursomgångar saknas',
lable_no_rounds: 'Kursomgångar saknas för aktuella eller kommande terminer.',
label_schedule: 'Schema',
label_link_schedule: 'Länk till Schema',
Expand All @@ -83,8 +81,9 @@ module.exports = {
CANCELLED: 'Kursomgång inställd',
FULL: 'Kursomgång fullsatt',
},
header_dropdown_menu_navigation: 'Välj termin och kursomgång för innehållet på sidan',
header_dropdown_menue: 'Gäller för',
header_dropdown_menu_navigation:
'Välj termin och kursomgång för att se aktuell information och mer om kursen, såsom kursplan, studieperiod och anmälningsinformation.',
header_dropdown_menue: 'Information per kursomgång',
header_dropdown_menu_aria_label: 'Information om val av termin och kursomgång',
header_course_info: 'Kursinformation',
header_content: 'Innehåll och lärandemål',
Expand All @@ -94,15 +93,11 @@ module.exports = {
header_examination: 'Examination och slutförande',
header_contact: 'Kontakt',
header_further: 'Ytterligare information',
header_select_course: 'Kursval',
header_postgraduate_course: 'Forskarkurs ',
no_memo_published: 'Kurs-PM är inte publicerat',
no_schedule: 'Schema saknas',
no_schedule_published: 'Schema är inte publicerat',
no_memo_connection: 'Kurs-pm kan inte visas',
header_no_round_selected: 'Välj termin och kursomgång',
no_round_selected:
'Välj termin och kursomgång för att se aktuell information och mer om kursen, såsom kursplan, studieperiod och anmälningsinformation.',
round_seats_default_info:
'Kursomgången kan komma att ställas in om antalet antagna understiger minimiantalet platser. Vid fler sökande än platser kommer urval att ske.',
round_seats_info: 'Urvalet sker baserat på:',
Expand Down Expand Up @@ -176,9 +171,7 @@ module.exports = {
course_application_info: 'Information för forskarstuderande om när kursen ges',
},
courseRoundInformation: {
header_round: 'Om kursomgång',
round_information_aria_label: 'Information för kursomgång',
round_header: 'Gäller för kursomgång',
round_header: 'Information för',
round_application_code: 'Anmälningskod',
round_max_seats: 'Antal platser',
round_no_seats_limit: 'Ingen platsbegränsning',
Expand Down
7 changes: 3 additions & 4 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

35 changes: 0 additions & 35 deletions public/css/_sidebar.scss

This file was deleted.

128 changes: 117 additions & 11 deletions public/css/kursinfo-web.scss
Original file line number Diff line number Diff line change
Expand Up @@ -22,16 +22,126 @@
@use '~@kth/style/scss/components/kpm.scss';

@import 'shared';
@import 'sidebar';

#kursinfo-main-page {
#columnContainer {
// Side panel first in mobile...
flex-direction: row;
.roundSelector {
fieldset legend,
label:has(+ .select-wrapper) {
margin-top: 1.5rem;
margin-bottom: 0.25rem;
display: block;
padding: 0;
@include typography.font-heading-xs;
}

fieldset {
border: 0;
padding: 0;
margin: 0;
min-width: 0;

input[type='radio'] {
opacity: 0;
position: absolute;
}

input[type='radio'] + label {
color: var(--color-primary);
cursor: pointer;
padding-top: 0.5rem;
padding-bottom: 0.5rem;
}

input[type='radio']:focus-visible + label,
input[type='radio']:hover + label {
&:hover {
color: var(--color-primary-hover);
text-decoration: underline;
text-decoration-thickness: 0.25rem;
text-underline-offset: 0.5rem;
}
}

input[type='radio']:focus-visible + label {
outline: 5px auto Highlight;
outline: 5px auto -webkit-focus-ring-color;
outline-offset: 3px;
}

input[type='radio']:not(:checked) + label {
@include typography.font-default;
}

input[type='radio']:checked + label {
@include typography.font-heading-xs;
text-decoration: underline;
text-decoration-thickness: 0.25rem;
text-underline-offset: 0.5rem;
}

div {
display: flex;
flex-wrap: wrap;
gap: 1.5rem;
}
}

.roundSelector__selectAndApplicationButton {
margin-top: 1.5rem;
margin-bottom: 1.5rem;
display: flex;
justify-content: space-between;
gap: 1rem;

flex-direction: column;
align-items: flex-start;

@media (min-width: 768px) {
flex-direction: row;
align-items: flex-end;
}
}
}

.roundInformation {
padding: 20px;
margin-bottom: 30px;
background-color: var(--color-background-alt);

h3 {
margin-block-end: 1rem;
}

.roundInformation__infoGrid,
.roundInformation__contacts {
display: grid;
gap: 1rem;
grid-template-columns: 1fr;

@media (min-width: 768px) {
// ...but to the right (reverse order) on desktop
flex-direction: row-reverse;
grid-template-columns: repeat(2, 1fr);
}
@media (min-width: 1200px) {
grid-template-columns: repeat(3, 1fr);
}

dt {
@include typography.font-heading-s-fluid;
margin-block-end: 0.25rem;
}
dd {
p + p {
margin-top: 0.25rem;
}
}
}

.kth-alert,
.roundInformation__infoGrid {
margin-bottom: 1.5rem;
}

.kth-alert {
background-color: var(--color-background);
}
}

Expand Down Expand Up @@ -90,10 +200,6 @@
}
}

.bankIdAlert {
margin: 1rem 0 0 0;
}

.ul-no-padding {
padding-left: 20px;
}
Expand Down
19 changes: 11 additions & 8 deletions public/js/app/components-shared/Alert.jsx
Original file line number Diff line number Diff line change
@@ -1,10 +1,17 @@
// https://intra.kth.se/style/en/components/alert

/**
* https://intra.kth.se/style/en/components/alert
*
* Changelog:
* - 2024-04- - initial version (release of kth-style 10 public apps)
* - 2024-05-31 - add aria-live="polite" as default and add {...rest} to allow adding extra props (as test-ids) to Alert root element
* - 2024-06-03 - add support for classname prop
* - 2024-07-25 - remove use of deprecated "defaultProps" from prop-types
*/
import React from 'react'
import PropTypes from 'prop-types'

const Alert = ({ type, header, children }) => (
<div className={`kth-alert ${type}`} role="alert">
const Alert = ({ type = 'info', header, children, className, ...rest }) => (
<div className={`kth-alert ${type} ${className ?? ''}`} role="alert" aria-live="polite" {...rest}>
{header && <h4>{header}</h4>}
<div>{children}</div>
</div>
Expand All @@ -16,8 +23,4 @@ Alert.propTypes = {
type: PropTypes.oneOf(['info', 'warning', 'success']).isRequired,
}

Alert.defaultProps = {
type: 'info',
}

export default Alert
14 changes: 6 additions & 8 deletions public/js/app/components/BankIdAlert.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,27 +2,25 @@ import React from 'react'
import Alert from '../components-shared/Alert'
import { useLanguage } from '../hooks/useLanguage'

const BankIdAlert = ({ tutoringForm, fundingType, roundSpecified }) => {
const BankIdAlert = ({ tutoringForm, fundingType }) => {
const { isEnglish, translation } = useLanguage()
const distanceCourse = tutoringForm === 'DST'

const standaloneCourse = fundingType === 'LL'

// Svenska sidan + fristående kurser som ges på distans
const case1 = !isEnglish && distanceCourse && standaloneCourse && roundSpecified
const case1 = !isEnglish && distanceCourse && standaloneCourse

// Engelska sidan + fristående kurser
const case2 = isEnglish && standaloneCourse && roundSpecified
const case2 = isEnglish && standaloneCourse

const showAlert = case1 || case2

return (
showAlert && (
<section className="bankIdAlert">
<Alert type="info">
<p dangerouslySetInnerHTML={{ __html: translation.bankIdAlertText }}></p>
</Alert>
</section>
<Alert type="info">
<p dangerouslySetInnerHTML={{ __html: translation.bankIdAlertText }}></p>
</Alert>
)
)
}
Expand Down
Loading

0 comments on commit 2e663d1

Please sign in to comment.