Move date rendering, nested records, icons, profile page into toolkit
This commit is contained in:
parent
67f3430751
commit
a1e219f015
|
@ -9,6 +9,7 @@ build = "src/build.rs"
|
|||
|
||||
[dependencies]
|
||||
mime = "0.3.16"
|
||||
chrono = "0.4.19"
|
||||
|
||||
[build-dependencies]
|
||||
ructe = { version = "0.13.0", features = ["mime03", "sass"] }
|
||||
|
|
|
@ -4,6 +4,7 @@ $white: #fff;
|
|||
$border-light: #e5e5e5;
|
||||
$light-background: #f5f5f5;
|
||||
$lighter-background: #f9f9f9;
|
||||
$light-banner-background: #bbb;
|
||||
$primary: #c92a60;
|
||||
$primary-shadow: #c92a603b;
|
||||
$primary-border: #9d2a60;
|
||||
|
@ -38,6 +39,13 @@ body {
|
|||
}
|
||||
}
|
||||
|
||||
img {
|
||||
display: block;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
object-fit: scale-down;
|
||||
}
|
||||
|
||||
.toolkit-bar {
|
||||
background-color: $border-light;
|
||||
color: $dark;
|
||||
|
@ -63,6 +71,93 @@ body {
|
|||
}
|
||||
}
|
||||
|
||||
.toolkit-icon--link {
|
||||
display: block;
|
||||
width: 128px;
|
||||
height: 128px;
|
||||
margin-right: 16px;
|
||||
|
||||
.toolkit-icon {
|
||||
border-color: $border-light;
|
||||
background-color: $lighter-background;
|
||||
}
|
||||
&.toolkit-dark .toolkit-icon {
|
||||
border-color: $dark-heading;
|
||||
background-color: $dark;
|
||||
}
|
||||
|
||||
.toolkit-icon {
|
||||
border-radius: 64px;
|
||||
border-width: 3px;
|
||||
border-style: solid;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
&__small {
|
||||
width: 64px;
|
||||
height: 64px;
|
||||
margin-right: 8px;
|
||||
|
||||
.toolkit-icon {
|
||||
border-radius: 32px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.toolkit-banner {
|
||||
height: 300px;
|
||||
width: 100%;
|
||||
background-color: $light-banner-background;
|
||||
|
||||
&.toolkit-dark {
|
||||
background-color: $dark-heading;
|
||||
}
|
||||
|
||||
img {
|
||||
object-fit: cover;
|
||||
}
|
||||
}
|
||||
|
||||
.toolkit-profile {
|
||||
background-color: $border-light;
|
||||
color: $dark;
|
||||
|
||||
&.toolkit-dark {
|
||||
background-color: $dark-border;
|
||||
color: $light-background;
|
||||
}
|
||||
|
||||
.toolkit-profile--content {
|
||||
padding-bottom: 16px;
|
||||
}
|
||||
|
||||
.toolkit-profile--content--top {
|
||||
margin-top: -86px;
|
||||
display: flex;
|
||||
justify-content: flex-start;
|
||||
align-items: flex-start;
|
||||
flex-wrap: wrap;
|
||||
padding: 0 16px;
|
||||
}
|
||||
|
||||
.toolkit-profile--meta {
|
||||
padding-top: 20px;
|
||||
color: $light-background;
|
||||
text-shadow: 1px 1px 1px $dark;
|
||||
}
|
||||
|
||||
.toolkit-profile--meta--display {
|
||||
font-weight: 600;
|
||||
font-size: 20px;
|
||||
}
|
||||
|
||||
.toolkit-profile--description {
|
||||
padding: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
.toolkit-link {
|
||||
color: $primary;
|
||||
&.toolkit-plain {
|
||||
|
@ -171,7 +266,7 @@ body {
|
|||
|
||||
.toolkit-centered {
|
||||
width: 100%;
|
||||
max-width: 700px;
|
||||
max-width: 900px;
|
||||
margin: 0 auto;
|
||||
}
|
||||
|
||||
|
@ -351,6 +446,96 @@ body {
|
|||
}
|
||||
}
|
||||
|
||||
.toolkit-time__long {
|
||||
display: inline;
|
||||
}
|
||||
.toolkit-time__short {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.toolkit-nested {
|
||||
.toolkit-nested--children,
|
||||
.toolkit-nested--node {
|
||||
border-color: $border-light;
|
||||
}
|
||||
&.toolkit-dark .toolkit-nested--children,
|
||||
&.toolkit-dark .toolkit-nested--node {
|
||||
border-color: $dark-border;
|
||||
}
|
||||
|
||||
.toolkit-nested--node {
|
||||
border-top-width: 1px;
|
||||
border-top-style: solid;
|
||||
padding: 16px 0;
|
||||
|
||||
&:last-child {
|
||||
padding-bottom: 0;
|
||||
}
|
||||
}
|
||||
.toolkit-nested--children {
|
||||
padding-top: 16px;
|
||||
margin-bottom: 16px;
|
||||
}
|
||||
|
||||
> .toolkit-nested--children {
|
||||
padding-top: 0;
|
||||
margin-bottom: 0;
|
||||
|
||||
> .toolkit-nested--node:first-child {
|
||||
border-top-width: 0;
|
||||
padding-top: 0;
|
||||
}
|
||||
}
|
||||
|
||||
> .toolkit-nested--children > .toolkit-nested--children,
|
||||
> .toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children,
|
||||
|
||||
> .toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children,
|
||||
|
||||
> .toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children,
|
||||
|
||||
> .toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children,
|
||||
|
||||
> .toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children,
|
||||
|
||||
> .toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children,
|
||||
|
||||
> .toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children,
|
||||
|
||||
> .toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children,
|
||||
|
||||
> .toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children {
|
||||
border-left-width: 4px;
|
||||
border-left-style: solid;
|
||||
padding-left: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 1300px) {
|
||||
.toolkit-banner {
|
||||
height: 233px;
|
||||
}
|
||||
|
||||
.toolkit-centered {
|
||||
max-width: 700px;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 700px) {
|
||||
.toolkit-input {
|
||||
width: 100%;
|
||||
|
@ -382,3 +567,126 @@ body {
|
|||
align-items: center;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 700px) {
|
||||
.toolkit-time__long {
|
||||
display: none;
|
||||
}
|
||||
.toolkit-time__short {
|
||||
display: inline;
|
||||
}
|
||||
|
||||
.toolkit-banner {
|
||||
height: 33vw;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 680px) {
|
||||
.toolkit-nested > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children {
|
||||
border-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 660px) {
|
||||
.toolkit-nested > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children {
|
||||
border-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 640px) {
|
||||
.toolkit-nested > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children {
|
||||
border-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 620px) {
|
||||
.toolkit-nested > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children {
|
||||
border-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 600px) {
|
||||
.toolkit-nested > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children {
|
||||
border-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 580px) {
|
||||
.toolkit-nested > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children {
|
||||
border-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 560px) {
|
||||
.toolkit-nested > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children > .toolkit-nested--children {
|
||||
border-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 540px) {
|
||||
.toolkit-nested > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children > .toolkit-nested--children {
|
||||
border-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 520px) {
|
||||
.toolkit-nested > .toolkit-nested--children > .toolkit-nested--children >
|
||||
.toolkit-nested--children {
|
||||
border-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 500px) {
|
||||
.toolkit-nested > .toolkit-nested--children > .toolkit-nested--children {
|
||||
border-left: 0;
|
||||
padding-left: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@media(max-width: 400px) {
|
||||
.toolkit-profile {
|
||||
.toolkit-profile--content--top {
|
||||
margin-top: -66px;
|
||||
}
|
||||
|
||||
.toolkit-profile--meta {
|
||||
padding-top: 12px;
|
||||
}
|
||||
}
|
||||
|
||||
.toolkit-icon--link {
|
||||
width: 96px;
|
||||
height: 96px;
|
||||
|
||||
&__small {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -15,3 +15,81 @@ pub use self::{
|
|||
link::Link,
|
||||
text_input::TextInput,
|
||||
};
|
||||
|
||||
use chrono::{DateTime, Utc};
|
||||
|
||||
fn time_ago_long(time: DateTime<Utc>) -> String {
|
||||
let duration = chrono::Utc::now() - time;
|
||||
if let Some(years) =
|
||||
duration
|
||||
.num_days()
|
||||
.checked_div(365)
|
||||
.and_then(|years| if years > 0 { Some(years) } else { None })
|
||||
{
|
||||
if years == 1 {
|
||||
format!("{} year ago", years)
|
||||
} else {
|
||||
format!("{} years ago", years)
|
||||
}
|
||||
} else if duration.num_weeks() > 0 {
|
||||
if duration.num_weeks() == 1 {
|
||||
format!("{} week ago", duration.num_weeks())
|
||||
} else {
|
||||
format!("{} weeks ago", duration.num_weeks())
|
||||
}
|
||||
} else if duration.num_days() > 0 {
|
||||
if duration.num_days() == 1 {
|
||||
format!("{} day ago", duration.num_days())
|
||||
} else {
|
||||
format!("{} days ago", duration.num_days())
|
||||
}
|
||||
} else if duration.num_hours() > 0 {
|
||||
if duration.num_hours() == 1 {
|
||||
format!("{} hour ago", duration.num_hours())
|
||||
} else {
|
||||
format!("{} hours ago", duration.num_hours())
|
||||
}
|
||||
} else if duration.num_minutes() > 0 {
|
||||
if duration.num_minutes() == 1 {
|
||||
format!("{} minute ago", duration.num_minutes())
|
||||
} else {
|
||||
format!("{} minutes ago", duration.num_minutes())
|
||||
}
|
||||
} else if duration.num_seconds() > 0 {
|
||||
if duration.num_seconds() == 1 {
|
||||
format!("{} second ago", duration.num_seconds())
|
||||
} else {
|
||||
format!("{} seconds ago", duration.num_seconds())
|
||||
}
|
||||
} else {
|
||||
"now".to_owned()
|
||||
}
|
||||
}
|
||||
|
||||
fn time_ago_short(time: DateTime<Utc>) -> String {
|
||||
let duration = chrono::Utc::now() - time;
|
||||
if let Some(years) =
|
||||
duration
|
||||
.num_days()
|
||||
.checked_div(365)
|
||||
.and_then(|years| if years > 0 { Some(years) } else { None })
|
||||
{
|
||||
format!("{}y", years)
|
||||
} else if duration.num_weeks() > 0 {
|
||||
format!("{}w", duration.num_weeks())
|
||||
} else if duration.num_days() > 0 {
|
||||
format!("{}d", duration.num_days())
|
||||
} else if duration.num_hours() > 0 {
|
||||
format!("{}h", duration.num_hours())
|
||||
} else if duration.num_minutes() > 0 {
|
||||
format!("{}m", duration.num_minutes())
|
||||
} else if duration.num_seconds() > 0 {
|
||||
format!("{}s", duration.num_seconds())
|
||||
} else {
|
||||
"now".to_owned()
|
||||
}
|
||||
}
|
||||
|
||||
fn time(time: chrono::DateTime<chrono::Utc>) -> String {
|
||||
time.format("%B %d, %Y, %I:%M %P").to_string()
|
||||
}
|
||||
|
|
15
toolkit/templates/ago.rs.html
Normal file
15
toolkit/templates/ago.rs.html
Normal file
|
@ -0,0 +1,15 @@
|
|||
@use chrono::{DateTime, Utc};
|
||||
@use crate::{Link, templates::link};
|
||||
|
||||
@(time: DateTime<Utc>, dark: bool)
|
||||
|
||||
<span class="toolkit-time__long">
|
||||
@:link(&Link::current_tab("#").title(&crate::time(time)).plain(true).dark(dark), {
|
||||
@crate::time_ago_long(time)
|
||||
})
|
||||
</span>
|
||||
<span class="toolkit-time__short">
|
||||
@:link(&Link::current_tab("#").title(&crate::time(time)).plain(true).dark(dark), {
|
||||
@crate::time_ago_short(time)
|
||||
})
|
||||
</span>
|
11
toolkit/templates/banner.rs.html
Normal file
11
toolkit/templates/banner.rs.html
Normal file
|
@ -0,0 +1,11 @@
|
|||
@(dark: bool, img: Content)
|
||||
|
||||
@if dark {
|
||||
<div class="toolkit-banner toolkit-dark">
|
||||
@:img()
|
||||
</div>
|
||||
} else {
|
||||
<div class="toolkit-banner">
|
||||
@:img()
|
||||
</div>
|
||||
}
|
31
toolkit/templates/icon.rs.html
Normal file
31
toolkit/templates/icon.rs.html
Normal file
|
@ -0,0 +1,31 @@
|
|||
@(href: &str, small: bool, dark: bool, picture: Content)
|
||||
|
||||
@if small {
|
||||
@if dark {
|
||||
<a href="@href" class="toolkit-icon--link toolkit-icon--link__small toolkit-dark">
|
||||
<div class="toolkit-icon">
|
||||
@:picture()
|
||||
</div>
|
||||
</a>
|
||||
} else {
|
||||
<a href="@href" class="toolkit-icon--link toolkit-icon--link__small">
|
||||
<div class="toolkit-icon">
|
||||
@:picture()
|
||||
</div>
|
||||
</a>
|
||||
}
|
||||
} else {
|
||||
@if dark {
|
||||
<a href="@href" class="toolkit-icon--link toolkit-dark">
|
||||
<div class="toolkit-icon">
|
||||
@:picture()
|
||||
</div>
|
||||
</a>
|
||||
} else {
|
||||
<a href="@href" class="toolkit-icon--link">
|
||||
<div class="toolkit-icon">
|
||||
@:picture()
|
||||
</div>
|
||||
</a>
|
||||
}
|
||||
}
|
11
toolkit/templates/nested.rs.html
Normal file
11
toolkit/templates/nested.rs.html
Normal file
|
@ -0,0 +1,11 @@
|
|||
@(dark: bool, body: Content)
|
||||
|
||||
@if dark {
|
||||
<div class="toolkit-nested toolkit-dark">
|
||||
@:body()
|
||||
</div>
|
||||
} else {
|
||||
<div class="toolkit-nested">
|
||||
@:body()
|
||||
</div>
|
||||
}
|
5
toolkit/templates/nested_children.rs.html
Normal file
5
toolkit/templates/nested_children.rs.html
Normal file
|
@ -0,0 +1,5 @@
|
|||
@(body: Content)
|
||||
|
||||
<div class="toolkit-nested--children">
|
||||
@:body()
|
||||
</div>
|
5
toolkit/templates/nested_node.rs.html
Normal file
5
toolkit/templates/nested_node.rs.html
Normal file
|
@ -0,0 +1,5 @@
|
|||
@(body: Content)
|
||||
|
||||
<div class="toolkit-nested--node">
|
||||
@:body()
|
||||
</div>
|
49
toolkit/templates/profile.rs.html
Normal file
49
toolkit/templates/profile.rs.html
Normal file
|
@ -0,0 +1,49 @@
|
|||
@use crate::templates::{icon, banner};
|
||||
|
||||
@(view_path: &str, display_name: Option<&str>, handle: &str, description: Option<&str>, dark: bool, icon_img: Content, banner_img: Content)
|
||||
|
||||
@if dark {
|
||||
<div class="toolkit-profile toolkit-dark">
|
||||
@:banner(dark, { @:banner_img() })
|
||||
<div class="toolkit-profile--content">
|
||||
<div class="toolkit-profile--content--top">
|
||||
@:icon(view_path, false, dark, { @:icon_img() })
|
||||
<div class="toolkit-profile--meta">
|
||||
<div class="toolkit-profile--meta--display">
|
||||
@if let Some(display_name) = display_name {
|
||||
@display_name
|
||||
} else {
|
||||
|
||||
}
|
||||
</div>
|
||||
<div class="toolkit-profile--meta--handle">@handle</div>
|
||||
</div>
|
||||
</div>
|
||||
@if let Some(description) = description {
|
||||
<div class="toolkit-profile--description">@description</div>
|
||||
}
|
||||
</div>
|
||||
</div>
|
||||
} else {
|
||||
<div class="toolkit-profile">
|
||||
@:banner(dark, { @:banner_img() })
|
||||
<div class="toolkit-profile--content">
|
||||
<div class="toolkit-profile--content--top">
|
||||
@:icon(view_path, false, dark, { @:icon_img() })
|
||||
<div class="toolkit-profile--meta">
|
||||
<div class="toolkit-profile--meta--display">
|
||||
@if let Some(display_name) = display_name {
|
||||
@display_name
|
||||
} else {
|
||||
|
||||
}
|
||||
</div>
|
||||
<div class="toolkit-profile--meta--handle">@handle</div>
|
||||
</div>
|
||||
</div>
|
||||
@if let Some(description) = description {
|
||||
<div class="toolkit-profile--description">@description</div>
|
||||
}
|
||||
</div>
|
||||
</div>
|
||||
}
|
Loading…
Reference in a new issue