footers
This commit is contained in:
parent
7dc7c9720b
commit
e7095aaa66
3 changed files with 153 additions and 1 deletions
80
src/blocks/Skills/Component.ts
Normal file
80
src/blocks/Skills/Component.ts
Normal file
|
|
@ -0,0 +1,80 @@
|
||||||
|
import React from 'react'
|
||||||
|
import { cn } from '@/utilities/ui'
|
||||||
|
|
||||||
|
type SkillCategory = {
|
||||||
|
title: string
|
||||||
|
icon: string
|
||||||
|
tags: { tag: string }[]
|
||||||
|
}
|
||||||
|
|
||||||
|
type SkillsBlockProps = {
|
||||||
|
heading?: string
|
||||||
|
keySkills?: { skill: string }[]
|
||||||
|
categories?: SkillCategory[]
|
||||||
|
}
|
||||||
|
|
||||||
|
export function SkillsBlock({ heading, keySkills, categories }: SkillsBlockProps) {
|
||||||
|
return (
|
||||||
|
<section className="w-full px-6 py-16">
|
||||||
|
{/* Heading */}
|
||||||
|
{heading && (
|
||||||
|
<p className="text-center text-xs tracking-widest uppercase text-white/30 mb-6">
|
||||||
|
{heading}
|
||||||
|
</p>
|
||||||
|
)}
|
||||||
|
|
||||||
|
{/* Key skills pills */}
|
||||||
|
{Array.isArray(keySkills) && keySkills.length > 0 && (
|
||||||
|
<div className="flex justify-center gap-3 flex-wrap mb-12">
|
||||||
|
{keySkills.map(({ skill }, i) => (
|
||||||
|
<span
|
||||||
|
key={i}
|
||||||
|
className="text-xs text-white/70 border border-white/25 rounded-full px-4 py-1.5"
|
||||||
|
>
|
||||||
|
{skill}
|
||||||
|
</span>
|
||||||
|
))}
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
|
||||||
|
{/* Categories grid */}
|
||||||
|
{Array.isArray(categories) && categories.length > 0 && (
|
||||||
|
<div
|
||||||
|
className="border border-white/8 rounded-xl overflow-hidden"
|
||||||
|
style={{
|
||||||
|
display: 'grid',
|
||||||
|
gridTemplateColumns: 'repeat(3, 1fr)',
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{categories.map((cat, i) => {
|
||||||
|
const isLastRow = i >= categories.length - (categories.length % 3 || 3)
|
||||||
|
const isLastCol = (i + 1) % 3 === 0
|
||||||
|
return (
|
||||||
|
<div
|
||||||
|
key={i}
|
||||||
|
className={cn(
|
||||||
|
'p-6 flex flex-col gap-3',
|
||||||
|
!isLastCol && 'border-r border-white/8',
|
||||||
|
!isLastRow && 'border-b border-white/8',
|
||||||
|
)}
|
||||||
|
>
|
||||||
|
<i className={`ti ${cat.icon} text-white/40`} style={{ fontSize: 20 }} aria-hidden="true" />
|
||||||
|
<p className="text-sm font-medium text-white/85">{cat.title}</p>
|
||||||
|
<div className="flex flex-wrap gap-1.5">
|
||||||
|
{Array.isArray(cat.tags) && cat.tags.map(({ tag }, j) => (
|
||||||
|
<span
|
||||||
|
key={j}
|
||||||
|
className="text-xs text-white/35 border border-white/10 rounded-full px-2.5 py-0.5"
|
||||||
|
>
|
||||||
|
{tag}
|
||||||
|
</span>
|
||||||
|
))}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
})}
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
</section>
|
||||||
|
)
|
||||||
|
}
|
||||||
71
src/blocks/Skills/config.ts
Normal file
71
src/blocks/Skills/config.ts
Normal file
|
|
@ -0,0 +1,71 @@
|
||||||
|
import type { Block } from 'payload'
|
||||||
|
|
||||||
|
export const SkillsBlock: Block = {
|
||||||
|
slug: 'skills',
|
||||||
|
labels: {
|
||||||
|
singular: 'Skills Section',
|
||||||
|
plural: 'Skills Sections',
|
||||||
|
},
|
||||||
|
fields: [
|
||||||
|
{
|
||||||
|
name: 'heading',
|
||||||
|
type: 'text',
|
||||||
|
defaultValue: 'what i bring to the table',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'keySkills',
|
||||||
|
type: 'array',
|
||||||
|
label: 'Key skills (pills at top)',
|
||||||
|
fields: [
|
||||||
|
{
|
||||||
|
name: 'skill',
|
||||||
|
type: 'text',
|
||||||
|
required: true,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'categories',
|
||||||
|
type: 'array',
|
||||||
|
label: 'Skill categories',
|
||||||
|
fields: [
|
||||||
|
{
|
||||||
|
name: 'title',
|
||||||
|
type: 'text',
|
||||||
|
required: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'icon',
|
||||||
|
type: 'select',
|
||||||
|
label: 'Icon (Tabler icon name)',
|
||||||
|
defaultValue: 'ti-layout',
|
||||||
|
options: [
|
||||||
|
{ label: 'Layout', value: 'ti-layout' },
|
||||||
|
{ label: 'Server', value: 'ti-server' },
|
||||||
|
{ label: 'Design / Pen', value: 'ti-vector-pen' },
|
||||||
|
{ label: 'Briefcase', value: 'ti-briefcase' },
|
||||||
|
{ label: 'Globe', value: 'ti-world' },
|
||||||
|
{ label: 'Camera', value: 'ti-camera' },
|
||||||
|
{ label: 'Tools', value: 'ti-tools' },
|
||||||
|
{ label: 'Sparkles', value: 'ti-sparkles' },
|
||||||
|
{ label: 'Mobile', value: 'ti-device-mobile' },
|
||||||
|
{ label: 'Code', value: 'ti-code' },
|
||||||
|
{ label: 'Chart', value: 'ti-chart-bar' },
|
||||||
|
{ label: 'Star', value: 'ti-star' },
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: 'tags',
|
||||||
|
type: 'array',
|
||||||
|
fields: [
|
||||||
|
{
|
||||||
|
name: 'tag',
|
||||||
|
type: 'text',
|
||||||
|
required: true,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
}
|
||||||
|
|
@ -7,6 +7,7 @@ import { CallToAction } from '../../blocks/CallToAction/config'
|
||||||
import { Content } from '../../blocks/Content/config'
|
import { Content } from '../../blocks/Content/config'
|
||||||
import { FormBlock } from '../../blocks/Form/config'
|
import { FormBlock } from '../../blocks/Form/config'
|
||||||
import { MediaBlock } from '../../blocks/MediaBlock/config'
|
import { MediaBlock } from '../../blocks/MediaBlock/config'
|
||||||
|
import { SkillsBlock } from '../../blocks/Skills/config'
|
||||||
import { hero } from '@/heros/config'
|
import { hero } from '@/heros/config'
|
||||||
import { slugField } from 'payload'
|
import { slugField } from 'payload'
|
||||||
import { populatePublishedAt } from '../../hooks/populatePublishedAt'
|
import { populatePublishedAt } from '../../hooks/populatePublishedAt'
|
||||||
|
|
@ -72,7 +73,7 @@ export const Pages: CollectionConfig<'pages'> = {
|
||||||
{
|
{
|
||||||
name: 'layout',
|
name: 'layout',
|
||||||
type: 'blocks',
|
type: 'blocks',
|
||||||
blocks: [CallToAction, Content, MediaBlock, Archive, FormBlock],
|
blocks: [CallToAction, Content, MediaBlock, Archive, FormBlock, SkillsBlock],
|
||||||
required: true,
|
required: true,
|
||||||
admin: {
|
admin: {
|
||||||
initCollapsed: true,
|
initCollapsed: true,
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue