UI redesign for teams page

This commit is contained in:
Corban-Lee 2023-05-09 22:11:01 +01:00
parent bb721f2894
commit b8ed427cf9
6 changed files with 141 additions and 33 deletions

View File

@ -6,7 +6,7 @@
{% block content %}
<div class="bg-body p-4">
<a href="{% url 'index' %}" class="btn btn-primary px-4">Back</a>
<a href="{% url 'index' %}" class="btn btn-company px-4">Back</a>
</div>
<div class="container my-4 p-4 pb-0 bg-body rounded">
@ -16,43 +16,43 @@
</div>
<div class="col-sm-3 col-md-6 col-xl-4 mb-3 mb-sm-0">
<div class="input-group justify-content-xl-end">
<button class="btn btn-outline-secondary border-secondary-subtle" id="addMember" data-bs-toggle="tooltip" data-bs-title="Add Member">
<button class="btn border-secondary-subtle btn-outline-company" id="addMember" data-bs-toggle="tooltip" data-bs-title="Add Member">
<i class="bi bi-person"></i>
</button>
<button class="btn btn-outline-secondary border-secondary-subtle" id="addTeam" data-bs-toggle="tooltip" data-bs-title="Add Team">
<button class="btn border-secondary-subtle btn-outline-company" id="addTeam" data-bs-toggle="tooltip" data-bs-title="Add Team">
<i class="bi bi-people"></i>
</button>
</div>
</div>
<div class="col-sm-9 col-md-6 col-xl-4">
<div class="input-group dropdown">
<button type="button" data-bs-toggle="dropdown" class="btn btn-outline-secondary border-secondary-subtle">
<button type="button" data-bs-toggle="dropdown" class="btn btn-outline-company border-secondary-subtle">
<i class="bi bi-sort-up"></i>
</button>
<input type="search" class="form-control border-secondary-subtle shadow-none" placeholder="Search Members" id="search">
<button type="button" class="btn btn-outline-secondary border-secondary-subtle rounded-end" id="searchButton"><i class="bi bi-search"></i></button>
<button type="button" class="btn btn-outline-company border-secondary-subtle rounded-end" id="searchButton"><i class="bi bi-search"></i></button>
<form id="sortForm">
<ul class="dropdown-menu w-100 py-3 text-body-secondary border-secondary-subtle shadow-sm" onclick="event.stopPropagation()">
<ul class="dropdown-menu py-3 text-body-secondary bg-body-tertiary border border-light-subtle shadow-sm justify-self-center mt-2" onclick="event.stopPropagation()">
<li class="px-4">
<h3 class="h6 mb-3">Sort teams by</h3>
<h3 class="h6 mb-3">Sort groups by</h3>
<div>
<div class="d-inline-block form-check">
<input type="radio" class="form-check-input" checked value="team_number" name="sortTeams" id="sortTeamsName">
<label for="sortTeamsName" class="form-check-label">Team Number</label>
<label for="sortTeamsName" class="form-check-label">Teams</label>
</div>
<div class="d-inline-block form-check ms-4">
<input type="radio" class="form-check-input" value="section_letter" name="sortTeams" id="sortTeamsSection">
<label for="sortTeamsSection" class="form-check-label">Section Letter</label>
<label for="sortTeamsSection" class="form-check-label">Sections</label>
</div>
</div>
</li>
<li class="dropdown-divider my-3"></li>
<li class="dropdown-divider my-3 mx-4 bg-light-subtle"></li>
<li class="px-4">
<h3 class="h6 mb-3">Sort members by</h3>
<div>
<div class="d-inline-block form-check">
<input type="radio" class="form-check-input" value="first_name" name="sortMembers" id="sortMembersName">
<label for="sortMembersName" class="form-check-label">Member Name</label>
<label for="sortMembersName" class="form-check-label">Name</label>
</div>
<div class="d-inline-block form-check ms-4">
<input type="radio" class="form-check-input" checked value="peg_number" name="sortMembers" id="sortMembersPeg">

View File

@ -75,7 +75,8 @@ def get_teams(request):
"last": member.last_name,
"id": member.id,
"team": team.team_number,
"peg": member.peg_number
"peg": member.peg_number,
"section": team.section_letter if team.section_letter else None
}
for member in team.members.order_by(sort_members).all()
]

View File

@ -39,4 +39,83 @@
.team-column {
opacity: 0;
transition: 5s opacity ease-in;
}
.fixed-badge {
min-width: 22px;
height: 22px;
}
.font-montserrat {
font-family: Montserrat;
}
.font-raleway {
font-family: Raleway;
}
.font-ssp {
font-family: "Source Sans Pro";
}
.pencil-btn {
width: 32px;
height: 32px;
}
.force-contents-center {
display: flex;
justify-content: center;
align-items: center;
}
.md-shadow-on-hover:hover {
box-shadow: rgba(0, 0, 0, 0.15) 0px 8px 16px 0px !important;
}
.text-company {
color: #04385c;
}
.company-bg {
background-color: #04385c !important;
}
.underline-company {
text-decoration: underline solid #04385c;
}
.border-company {
border-color: #04385c !important;
}
.btn-company {
color: white;
background-color: #04385c;
}
.btn-company:hover {
color: white;
background-color: #002d51;
}
.btn-outline-company {
border: 1px solid #04385c;
}
.btn-outline-company:hover {
color: white;
background-color: #04385c;
border: 1px solid #04385c;
}
.hover-only-bg:not(:hover) {
background-color: transparent !important;
}
input[type='radio']:checked {
background-color: #04385c;
border: 1px solid #04385c;
box-shadow: none;
}

View File

@ -1,6 +1,6 @@
body {
/* body {
background-color: #0d5979;
}
} */
.bd-placeholder-img {
font-size: 1.125rem;

View File

@ -5,18 +5,45 @@
$(document).ready(() => {
activateTooltips();
pageLoadMotionEffects();
});
function activateTooltips() {
// Enable all tooltips on the page
const tooltipTriggerList = document.querySelectorAll('[data-bs-toggle="tooltip"]')
const tooltipList = [...tooltipTriggerList].map(tooltipTriggerEl => new bootstrap.Tooltip(tooltipTriggerEl))
});
}
/**
* Returns boolean if the string is empty or only contains whitespace.
*
* @param {string} string - The string to check against.
* @returns {boolean} - The result as boolean
*/
*/
function isEmptyOrSpaces(string) {
return string === null || string.match(/^ *$/) !== null;
}
function pageLoadMotionEffects() {
var useMotion = localStorage.getItem("motion");
if (useMotion === null) {
useMotion = true
}
setMotionEffects(useMotion);
}
function setMotionEffects(enable) {
localStorage.setItem("motion", enable)
if (enable) {
$(".fluid-hover-zoom-off").addClass("fluid-hover-zoom").removeClass("fluid-hover-zoom-off");
}
else {
$(".fluid-hover-zoom").addClass("fluid-hover-zoom-off").removeClass("fluid-hover-zoom");
}
}

View File

@ -87,7 +87,7 @@ function loadTeams(teams, highlightText="") {
$("#teamsContainer").append(
`<div class='col-12 col-md-6 col-xl-4 mb-4'>
<div
class='team px-4 py-3 bg-body-secondary bg-gradient rounded h-100 fluid-hover-zoom shadow-sm shadow-on-hover'
class='team px-4 py-3 bg-body-tertiary bg-gradient rounded h-100 fluid-hover-zoom shadow-sm md-shadow-on-hover'
data-number='${team.team_number}'
data-section='${team.section_letter}'>
<h3>
@ -95,11 +95,7 @@ function loadTeams(teams, highlightText="") {
<span class='fs-6'>TEAM</span>
${team.team_number}
</span>
<span class='fs-5 text-secondary'>
<span class='fs-6'>SECTION</span>
${team.section_letter}
</span>
<button class='btn btn-sm btn-outline-secondary float-end border-0 me-1'>
<button class='btn btn-sm btn-light float-end border-0 me-1'>
<i class='bi bi-gear fs-6'></i>
</button>
</h3>
@ -114,7 +110,7 @@ function loadTeams(teams, highlightText="") {
const fullname = member.first + " " + member.last;
$("#teamsContainer").find(".team-members").last().append(
`<li class='bg-body-tertiary mb-3 rounded w-100'>
`<li class='mb-3 rounded w-100 fluid-hover-zoom'>
<div
class='team-member d-flex'
data-first='${member.first}'
@ -122,15 +118,18 @@ function loadTeams(teams, highlightText="") {
data-member-id='${member.id}'
data-team-number='${member.team}'
data-peg-number='${member.peg}'>
<div class='px-3 py-2'>
<span class='text-secondary me-2'>
<div class='px-3 py-2 w-100'>
<div class='badge bg-secondary-subtle text-body fixed-badge' data-bs-title='Peg ${member.peg}' data-bs-toggle='tooltip'>
${member.peg}
</span>
<span class='team-member-fullname'>
</div>
<div class='badge bg-secondary-subtle text-body fixed-badge' data-bs-title='Section ${member.section}' data-bs-toggle='tooltip'>
${member.section}
</div>
<div class='d-inline-block ms-2 team-member-fullname'>
${fullname}
</span>
</div>
</div>
<button type='button' class='ms-auto btn btn-outline-secondary border-0 btn-sm fs-6 m-1' style="max-height: 32px;">
<button type='button' class='ms-auto btn btn-light border-0 fs-6 pencil-btn align-self-center me-1 force-contents-center'>
<i class='bi bi-pencil'></i>
</button>
</div>
@ -139,11 +138,13 @@ function loadTeams(teams, highlightText="") {
});
});
activateTooltips(); // activate the new tooltips
// Highlight all instances where the text matches the search critera
if (!isEmptyOrSpaces(highlightText)) {
$("#teamsContainer").find('.team-member-fullname').each(function() {
var regex = new RegExp(highlightText, 'gi');
$(this).html($(this).text().replace(regex, '<span class="text-primary fw-bold">$&</span>'));
$(this).html($(this).text().replace(regex, '<span class="text-company fw-bolder border-2 border-bottom border-company">$&</span>'));
});
}
@ -185,7 +186,7 @@ function fetchAndLoadTeams(search="", sortTeams="", sortMembers="") {
"sortTeams": sortTeams,
"sortMembers": sortMembers
},
error: (xhr, textStatus, errorThrown) => { alert(errorThrown); },
error: (xhr, textStatus, errorThrown) => { alert(xhr + " " + textStatus + " " + errorThrown); },
success: (result) => {
teamsLoading(false);
loadTeams(result.teams, search);
@ -294,7 +295,7 @@ function saveEditMemberModal(memberId) {
"pegNumber": pegNumber,
"search": !isEmptyOrSpaces(search) ? search : null
},
error: (xhr, textStatus, errorThrown) => { alert(errorThrown); },
error: (xhr, textStatus, errorThrown) => { alert(xhr + " " + textStatus + " " + errorThrown); },
success: (result) => {
teamsLoading(false);
loadTeams(result.teams, search);