Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
165 changes: 116 additions & 49 deletions assets/css/v2/style.css
Original file line number Diff line number Diff line change
Expand Up @@ -1199,77 +1199,144 @@ h6:has(a):hover {
color: oklch(var(--color-brand));
}

/* Landing page cards */
.text-content .card-layout {
/* Product landing page cards */
.card-brand-icon {
margin: 0;
}

.card[data-grid="half"] {
grid-column: 1;
}

.card[data-grid="wide"] {
grid-column: 1;
}

@media (min-width: 55rem) {
.card[data-grid="half"] {
grid-column: span 6;
}

.card[data-grid="wide"] {
grid-column: 1 / -1;
}
}

.card-layout {
display: flex;
flex-direction: column;
gap: 1.5rem;

.card-section {
display: flex;
flex-direction: column;
gap: 1rem;

strong {
font-weight: 500;
}
gap: 1.5rem;

/* Hide all the cards past 3 if it is a featured card section */
&.featured-section {
.card-section-content.card-grid
> *:nth-child(n + 4 of div.card-container) {
/* Hide all the cards past 3 if it is a featured card section */
.card-section-content > *:nth-child(n + 4 of a.card) {
display: none;
}
}
}
}

/* Optional grid layout */
.card-grid {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(33%, 1fr));
gap: 1.5rem;
.card-section-title {
font-weight: 500;
font-size: var(--font-step-2);
display: block;
}

.card-container {
border: 1px solid oklch(var(--color-codeblock-border));
box-shadow: 3px 3px 0px oklch(var(--color-shadow));
padding: 1rem;
.card-section-content {
display: flex;
flex-direction: column;
gap: 1rem;

&.featured-card {
/* If there is a featured card, only the featured card should be full length */
grid-column: 1 / -1;
&.card-grid {
display: grid;
grid-template-columns: repeat(12, 1fr);
gap: 1.5rem;

@media (max-width: 55rem) {
grid-template-columns: 1fr;
}

/* If there is a featured card AND two cards, the last one should be full length */
~ .card-container:nth-child(2n):last-child {
grid-column: 1 / -1;
.card {
border: 1px solid oklch(var(--color-codeblock-border));
box-shadow: 3px 3px 0px oklch(var(--color-shadow));
padding: 1rem;
order: 2;
}
}
}
}

/* If there is no featured card, last card that is the 3rd one should be full width */
&:not(:has(.featured-card)) *:nth-child(n + 3 of div.card-container) {
grid-column: 1 / -1;
.card {
color: oklch(var(--color-foreground));
text-decoration: none;

.card-container {
display: flex;
flex-direction: column;
gap: 0.5rem;
}

.card-header {
display: flex;
flex-direction: row;
gap: 1rem;
align-items: center;
color: oklch(var(--color-brand));

img.card-brand-icon {
height: 1.5rem;
width: auto;
}

h2 {
padding: 0;
margin: 0;
font-size: var(--font-step-1);
}
}
}
}
}
}

.card-container {
display: flex;
flex-direction: column;
gap: 0.5rem;
margin-bottom: 1rem;
/* Home landing page cards */
.homepage .card-layout {
margin-block-end: 3rem;
gap: 3rem;

.card-header {
display: flex;
flex-direction: row;
gap: 0.5rem;
.card-section {
.card-section-content.card-grid {
grid-template-columns: 1fr;

.card-brand-icon {
height: 20px;
width: auto;
}
@media (min-width: 70rem) {
grid-template-columns: repeat(12, 1fr);
grid-auto-rows: 1fr;
}

h2 {
padding: 0;
margin: 0;
font-size: 1rem;
.card {
padding: 1rem 2rem 2rem 2rem;

.card-container {
height: 7rem;
justify-content: space-around;

.card-header {
justify-content: flex-start;

.card-brand-icon {
height: 40px;
width: auto;
}
}
}

&:hover {
box-shadow: 3px 3px 0px oklch(var(--color-brand) / 0.4);
text-decoration-color: oklch(var(--color-background));
border: 1px solid oklch(var(--color-brand) / 0.8);
}
}
}
}
}
Expand Down
4 changes: 2 additions & 2 deletions exampleSite/content/test-product/_index.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ cascade:
---
{{<card-layout>}}
{{<card-section showAsCards="true">}}
{{<card title="Everything" titleUrl="everything" icon="circle-dot-dashed">}}
{{<card title="Everything" titleUrl="everything" icon="circle-dot-dashed" isFullSize="true">}}
All shortcodes in one page.
{{</card >}}
{{<card title="Call Out usages" titleUrl="call-out/all-callouts/" icon="message-square">}}
Expand All @@ -29,7 +29,7 @@ cascade:
[//]: # "Provide any sort of additional supporting content you may want customers to see as well (e.g. more cards, diagrams, changelogs, etc.)"
{{<card-layout>}}
{{<card-section title="NGINX" showAsCards="true" >}}
{{<card title="NGINX Plus" titleUrl="/nginx/" brandIcon="NGINX-Plus-product-icon-RGB" >}}
{{<card title="NGINX Plus" titleUrl="/nginx/" brandIcon="NGINX-Plus-product-icon-RGB.png" >}}
Installing NGINX
{{</card >}}
{{</card-section >}}
Expand Down
2 changes: 1 addition & 1 deletion layouts/shortcodes/card-layout.html
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
<!-- Render the main content first with modifications, then render the custom content -->
<div class="card-layout">{{ .Inner | markdownify }}</div>
<div class="card-layout" data-testid="card-layout">{{- .Inner | markdownify -}}</div>
11 changes: 8 additions & 3 deletions layouts/shortcodes/card-section.html
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
{{ $title := .Get "title" }}
{{ $isFeaturedSectionParam := .Get "isFeaturedSection" | default "false" }}
{{ $showAsCardsParam := .Get "showAsCards" | default "false"}}

{{- /* Validate the parameter strictly */ -}}
{{- if not (in (slice "true" "false") $showAsCardsParam) -}}
{{- warnf "The '<card-section>' Shortcode parameter 'showAsCards' must be 'true' or 'false', but got: '%s'. This will now default to 'false'" $showAsCardsParam -}}
Expand All @@ -15,14 +16,18 @@
{{- end -}}
{{- $isFeaturedSection := cond (eq $isFeaturedSectionParam "true") "true" "false" -}}
{{- $class := "card-grid" -}}

{{- /* Get number of cards */ -}}
{{ $cardCount := len (findRE "<div\\s+class=\"card\"[\\s\\S]*?>" .Inner) }}

{{- /* Validate that the parent is card-layout */ -}}
{{ if eq .Parent.Name "card-layout"}}
<div class="card-section {{if eq $isFeaturedSection "true"}}featured-section{{ end }}" data-mf="true" style="display: none;">
<div class="card-section{{if eq $isFeaturedSection "true"}} featured-section{{ end }}" data-testid="{{if eq $isFeaturedSection "true"}}card-section__featured-section{{else}}card-section{{ end }}" data-mf="true" style="display: none;">
{{- if $title -}}
<strong class="card-section-title">{{- $title -}}</strong>
<div class="card-section-content{{ if eq $showAsCards "true" }} {{ $class }} {{ end }}">{{- .Inner -}}</div>
<div class="card-section-content{{ if eq $showAsCards "true" }} {{ $class }}{{ end }}" data-testid="{{ if eq $showAsCards "true" }}card-section-content__card-grid{{else}}card-section-content{{ end }}">{{ .Inner }}</div>
{{ else }}
<div class="card-section-content{{ if eq $showAsCards "true" }} {{ $class }} {{ end }}">{{ .Inner }}</div>
<div class="card-section-content{{ if eq $showAsCards "true" }} {{ $class }}{{ end }}" data-testid="{{ if eq $showAsCards "true" }}card-section-content__card-grid{{else}}card-section-content{{ end }}">{{ .Inner }}</div>
{{ end }}
</div>
<div class="row" data-mf="false">
Expand Down
89 changes: 54 additions & 35 deletions layouts/shortcodes/card.html
Original file line number Diff line number Diff line change
Expand Up @@ -2,55 +2,74 @@
{{- $titleUrl := .Get "titleUrl" | default "/" -}}
{{- $icon := .Get "icon" | default "book-open" -}}
{{- $brandIcon := .Get "brandIcon" -}}
{{- $isFeaturedParam := .Get "isFeatured" | default "false" }}
{{- $isFullSizeParam := .Get "isFullSize" | default "false" -}}
{{- $isLandingParam := .Get "isLanding" | default "false" }}

{{- /* Validate the parameter strictly */ -}}
{{- if not (in (slice "true" "false") $isFeaturedParam) -}}
{{- warnf "The '<card>' Shortcode parameter 'isFeatured' must be 'true' or 'false', but got: '%s'. This will now default to 'false'" $isFeaturedParam -}}
{{- if not (in (slice "true" "false") $isFullSizeParam) -}}
{{- warnf "The '<card>' Shortcode parameter 'isFullSize' must be 'true' or 'false', but got: '%s'. This will now default to 'false'" $isFullSizeParam -}}
{{- end -}}
{{- $isFeatured := cond (eq $isFeaturedParam "true") "true" "false" -}}
{{- $current := .Page.Scratch.Get "cards" | default (slice) -}}
{{- $newCard := dict "title" ($title) "content" (.Inner) -}}
{{- .Page.Scratch.Set "cards" ($current | append $newCard) -}}
{{- $isFullSize := cond (eq $isFullSizeParam "true") "true" "false" -}}

{{- if not (in (slice "true" "false") $isLandingParam) -}}
{{- warnf "The '<card>' Shortcode parameter 'isLanding' must be 'true' or 'false', but got: '%s'. This will now default to 'false'" $isLandingParam -}}
{{- end -}}
{{- $isLanding := cond (eq $isLandingParam "true") "true" "false" -}}

{{- /* Set up the positioning */ -}}
{{ $dataGrid := "" }}
{{ if eq $isFullSize "true" }}
{{ $dataGrid = "wide"}}
{{ else if (eq $isLanding "true") }}
{{ $dataGrid = "third"}}
{{ else }}
{{ $dataGrid = "half"}}
{{ end }}

{{- /* Build the url */ -}}
{{ $url := printf "%s%s" .Page.Permalink $titleUrl }}
{{ if eq (substr $titleUrl 0 1) "/" }}
{{ $url = printf "%s%s" .Site.BaseURL (substr $titleUrl 1) }}
{{ else if (strings.Contains $titleUrl "https") }}
{{ $url = $titleUrl }}
{{ end }}

{{- /* Validate that the parent is card-section and under 3 cards */ -}}
{{- if (eq .Parent.Name "card-section") -}}
<div class="card-container {{ if eq $isFeatured "true" }}featured-card{{ end }}" data-mf="true" style="display: none;">
<a href="{{- $url -}}" alt="{{- $title -}}" class="card" data-grid="{{ $dataGrid }}" data-testid="card" data-mf="true" style="display: none;">
<div class="card-container">
{{- if $title -}}
<div class="card-header">
{{- if $brandIcon -}}
<img class="card-brand-icon" src="/images/icons/{{ $brandIcon }}.svg">
{{- else -}}
{{- if $icon -}}
{{ partial "lucide" (dict "context" . "icon" $icon) }}
{{- end -}}
{{- end -}}
{{- if $titleUrl -}}
<h2 class="card-title"><a href="{{- $titleUrl -}}">{{- $title -}}</a></h2>
{{- else -}}
<h2 class="card-title">{{- $title -}}</h2>
<img class="card-brand-icon" src="/images/icons/{{ $brandIcon }}">
{{- else if $icon -}}
{{ partial "lucide" (dict "context" . "icon" $icon) }}
{{- end -}}
<h2 class="card-title">{{- $title -}}</h2>
</div>
{{- else -}}
{{ errorf "Mainframe: Missing param 'title'" }}
{{- end -}}
<p>{{- .Inner -}}</p>
<div class="card-content">{{ .Inner }}</div>
</div>
<div class="col-md-5 card" data-mf="false">
<div class="card-body">
<h3 class="card-title" style="display: flex; align-items: center; gap: 5px;">
{{- if $brandIcon -}}
<img class="card-img-top" src="{{ .Site.BaseURL }}/images/icons/{{ $brandIcon }}.png"/>
{{- else -}}
<i class="fas fa-file-alt fa-lg card-img-top"></i>
{{- end -}}
{{- if ($title) -}}
<a href="{{- $titleUrl -}}">{{- $title -}}</a>
{{- else -}}
{{ errorf "Old theme: Missing param 'title'" }}
{{- end -}}
</h3>
<p>{{- .Inner -}}</p>
</div>
</a>
<div class="col-md-5 card" data-mf="false">
<div class="card-body">
<h3 class="card-title" style="display: flex; align-items: center; gap: 5px;">
{{- if $brandIcon -}}
<img class="card-img-top" src="{{ .Site.BaseURL }}/images/icons/{{ $brandIcon }}"/>
{{- else -}}
<i class="fas fa-file-alt fa-lg card-img-top"></i>
{{- end -}}
{{- if ($title) -}}
<a href="{{- $titleUrl -}}">{{- $title -}}</a>
{{- else -}}
{{ errorf "Old theme: Missing param 'title'" }}
{{- end -}}
</h3>
<p>{{- .Inner -}}</p>
</div>
</div>
{{- else -}}
{{ errorf "The '<card>' must be nested directly inside the shortcode '<card-section>'. Please see the exampleSite for an example of usage." }}
{{- end -}}
Loading