Rewrite UI for user profile page

This commit is contained in:
cuom1999 2021-07-22 22:54:48 -05:00
parent ef218ccef0
commit 988a96b3dd
19 changed files with 32010 additions and 49 deletions

View file

@ -4,7 +4,7 @@ from django.views.generic import FormView
from django.views.generic.detail import SingleObjectMixin
from judge.utils.diggpaginator import DiggPaginator
from django.utils.html import mark_safe
def class_view_decorator(function_decorator):
"""Convert a function based decorator into a class based decorator usable

View file

@ -74,6 +74,11 @@ class UserPage(TitleMixin, UserMixin, DetailView):
return (_('My account') if self.request.user == self.object.user else
_('User %s') % self.object.user.username)
def get_content_title(self):
username = self.object.user.username
css_class = self.object.css_class
return mark_safe(f'<span class="{css_class}">{username}</span>')
# TODO: the same code exists in problem.py, maybe move to problems.py?
@cached_property
def profile(self):
@ -126,6 +131,28 @@ EPOCH = datetime(1970, 1, 1, tzinfo=timezone.utc)
class UserAboutPage(UserPage):
template_name = 'user/user-about.html'
def get_awards(self, ratings):
result = {}
sorted_ratings = sorted(ratings,
key=lambda x: (x.rank, -x.contest.end_time.timestamp()))
result['medals'] = [{
'label': rating.contest.name,
'ranking': rating.rank,
'link': reverse('contest_ranking', args=(rating.contest.key,)) + '#!' + self.object.username,
'date': date_format(rating.contest.end_time, _('M j, Y')),
} for rating in sorted_ratings if rating.rank <= 3]
num_awards = 0
for i in result:
num_awards += len(result[i])
if num_awards == 0:
result = None
return result
def get_context_data(self, **kwargs):
context = super(UserAboutPage, self).get_context_data(**kwargs)
ratings = context['ratings'] = self.object.ratings.order_by('-contest__end_time').select_related('contest') \
@ -142,6 +169,8 @@ class UserAboutPage(UserPage):
'height': '%.3fem' % rating_progress(rating.rating),
} for rating in ratings]))
context['awards'] = self.get_awards(ratings)
if ratings:
user_data = self.object.ratings.aggregate(Min('rating'), Max('rating'))
global_data = Rating.objects.aggregate(Min('rating'), Max('rating'))