diff --git a/libs/openchallenges/challenge/src/lib/_challenge-theme.scss b/libs/openchallenges/challenge/src/lib/_challenge-theme.scss index f249285579..adfa951cb3 100644 --- a/libs/openchallenges/challenge/src/lib/_challenge-theme.scss +++ b/libs/openchallenges/challenge/src/lib/_challenge-theme.scss @@ -45,18 +45,18 @@ color: #000; &.active { - border-color: #71c663; - background-color: #d0fedd; + color: #1C5E2A; + background-color: #D0FEDD; } &.completed { - border-color: #ffb6c1; - background-color: #ffdde2; + color: map.get($figma, dl-color-default-navbardark); + background-color: map.get($primary, 100); } &.upcoming { - border-color: #ffc56d; - background-color: #fff1bf; + color: #E1861F; + background-color: #FFF5D1; } } diff --git a/libs/openchallenges/challenge/src/lib/challenge.component.html b/libs/openchallenges/challenge/src/lib/challenge.component.html index e245cf2c53..d42f738ead 100644 --- a/libs/openchallenges/challenge/src/lib/challenge.component.html +++ b/libs/openchallenges/challenge/src/lib/challenge.component.html @@ -7,13 +7,13 @@

{{ challenge.name }}

-

@{{ challenge.slug }}

+

@{{ challenge.slug }}

- {{ challenge.status }} + {{ challenge.status | titlecase }}
diff --git a/libs/openchallenges/themes/src/_palettes.scss b/libs/openchallenges/themes/src/_palettes.scss index 24d13674eb..815a96839d 100644 --- a/libs/openchallenges/themes/src/_palettes.scss +++ b/libs/openchallenges/themes/src/_palettes.scss @@ -126,7 +126,7 @@ $figma-collection: ( dl-color-default-navbardark: map.get($dark-blue-palette, 800), dl-color-default-secondary1: map.get($light-blue-palette, 300), dl-color-default-secondary2: map.get($accent-purple-palette, 300), - dl-color-default-darkaccent1: map.get($accent-green-palette, 600), + dl-color-default-darkaccent1: map.get($accent-green-palette, 700), dl-color-default-darkaccent2: map.get($accent-purple-palette, 200), dl-color-gray-black: #000000, dl-color-gray-white: #ffffff, diff --git a/libs/openchallenges/ui/src/lib/challenge-card/_challenge-card-theme.scss b/libs/openchallenges/ui/src/lib/challenge-card/_challenge-card-theme.scss index 759ec8cc1f..8612a5408f 100644 --- a/libs/openchallenges/ui/src/lib/challenge-card/_challenge-card-theme.scss +++ b/libs/openchallenges/ui/src/lib/challenge-card/_challenge-card-theme.scss @@ -16,37 +16,29 @@ border-color: transparent; background-color: map.get($figma, dl-color-default-hover1); } - .star-icon { - border-color: transparent; - color: map.get($figma, dl-color-default-primary1); - } + .star-icon, .card-icon { border-color: transparent; color: map.get($figma, dl-color-default-primary1); } - .status-tag { - border-color: map.get($figma, dl-color-default-primary2); - background-color: map.get($figma, dl-color-default-hover1); - color: #000; - - &.active { - border-color: #71c663; - background-color: #d0fedd; + .card-status{ + .active { + color: #71C663; } - - &.completed { - border-color: #ffb6c1; - background-color: #ffdde2; + .completed { + color: map.get($figma, dl-color-default-primary1) } - - &.upcoming { - border-color: #ffc56d; - background-color: #fff1bf; + .upcoming { + color: #FFC56D; } } } -@mixin typography($theme) { } +@mixin typography($theme) { + .card-status span { + font-size: 21px; + } +} @mixin theme($theme) { $color-config: mat.get-color-config($theme); diff --git a/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.html b/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.html index 7e98480faa..5cdc3832af 100644 --- a/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.html +++ b/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.html @@ -18,19 +18,19 @@

{{ challenge.name }}

-

- {{ platform.name }} -

+
+
{{ status | titlecase }}
+
+ {{ time_info }} +
+

{{ desc }}

diff --git a/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.scss b/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.scss index 4f88800c67..6a43e1a748 100644 --- a/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.scss +++ b/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.scss @@ -13,11 +13,23 @@ cursor: pointer; } .card-body { - min-height: 160px; + min-height: 190px; } .card-banner { height: 100%; } +.card-status { + div:first-child { + margin-right: 5px; + } + min-height: 58px; + display: flex; + flex-direction: column; + flex-basis: 100%; + box-sizing: border-box; + align-items: center; + justify-content: flex-start; +} // FOOTER .difficulty-tag { @@ -26,17 +38,3 @@ flex: 1; @include general.line-clamp(2); } -.status-tag { - max-width: 110px; - margin-left: 6px; - padding: 4px 0; - display: flex; - flex-direction: column; - flex-basis: 100%; - box-sizing: border-box; - align-items: center; - justify-content: center; - border-width: 1px; - border-style: solid; - border-radius: constants.$dl-radius-radius-radius16; -} diff --git a/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.ts b/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.ts index 5f278484f5..0fcb870101 100644 --- a/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.ts +++ b/libs/openchallenges/ui/src/lib/challenge-card/challenge-card.component.ts @@ -4,8 +4,6 @@ import { MatIconModule } from '@angular/material/icon'; import { RouterModule } from '@angular/router'; import { Challenge, - ChallengePlatformService, - SimpleChallengePlatform, Image, ImageService, } from '@sagebionetworks/openchallenges/api-client-angular'; @@ -22,17 +20,14 @@ import { Observable } from 'rxjs'; export class ChallengeCardComponent implements OnInit { @Input({ required: true }) challenge!: Challenge; banner$: Observable | undefined; - platform!: SimpleChallengePlatform; status!: string | undefined; desc!: string; incentives!: string; statusClass!: string; + time_info!: string | number; // difficulty!: string | undefined; - constructor( - private challengePlatformService: ChallengePlatformService, - private imageService: ImageService - ) {} + constructor(private imageService: ImageService) {} ngOnInit(): void { if (this.challenge) { @@ -41,7 +36,6 @@ export class ChallengeCardComponent implements OnInit { // this.difficulty = this.challenge.difficulty // ? startCase(this.challenge.difficulty.replace('-', '')) // : undefined; - this.platform = this.challenge.platform; this.desc = this.challenge.headline ? this.challenge.headline : this.challenge.description; @@ -63,6 +57,48 @@ export class ChallengeCardComponent implements OnInit { : this.imageService.getImage({ objectKey: 'banner-default.svg', }); + if (this.challenge.endDate && this.status === 'completed') { + const timeSince = this.calcTimeDiff(this.challenge.endDate); + if (timeSince) { + this.time_info = `Ended ${timeSince} ago`; + } + } else if (this.challenge.endDate && this.status === 'active') { + this.time_info = `Ends in ${this.calcTimeDiff(this.challenge.endDate)}`; + } else if (this.challenge.startDate && this.status === 'upcoming') { + this.time_info = `Starts in ${this.calcTimeDiff( + this.challenge.startDate + )}`; + } } } + + calcTimeDiff(date: string) { + const pattern = /\d{4}-\d{2}-\d{2}/; + if (!pattern.test(date)) { + return ''; + } + const refDate: any = new Date(date + ' 00:00:00'); + const now: any = new Date(); + const diffMs = Math.abs(refDate - now); + + // Calculate the time difference in years, months, weeks, days, and hours. + const timeDiff = { + month: Math.floor(diffMs / 2_629_746_000), + week: Math.floor(diffMs / 604_800_000), + day: Math.floor(diffMs / 86_400_000), + hour: Math.floor(diffMs / 3_600_000), + }; + + // Find the largest unit of time and return in human-readable format. + let timeDiffString = ''; + for (const [unit, value] of Object.entries(timeDiff)) { + if (unit === 'month' && value > 3) { + break; + } else if (value > 0) { + timeDiffString = `${value} ${unit}` + (value > 1 ? 's' : ''); + break; + } + } + return timeDiffString; + } }