Zoeken...  ⌘K GitHub

FooterMega Footer

Uitgebreide donkere footer met accent featured-strip, merk-kolom met socials + nieuwsbrief en meerdere link-kolommen.

/footer-mega
src/components/footer/FooterMega.astro
---
/**
 * FooterMega — uitgebreide donkere footer: accent featured-strip bovenaan, een
 * merk-kolom met socials + nieuwsbrief, meerdere link-kolommen, en een
 * copyright-band onderaan.
 *
 * Props:
 * - featured?: { label: string; desc: string; cta: { label: string; href: string } } | null
 * - logo?: string
 * - logoHref?: string
 * - tagline?: string
 * - socials?: { network: 'instagram'|'linkedin'|'twitter'; href: string }[]
 * - newsletterLabel?: string
 * - newsletterPlaceholder?: string
 * - columns?: { title: string; links: { label: string; href: string }[] }[]
 * - copyright?: string         (default: "© {jaar}")
 * - bottomLinks?: { label: string; href: string }[]
 * - background?: string
 * - accent?: string
 */
interface FooterColumn { title: string; links: { label: string; href: string }[] }
interface Social { network: 'instagram' | 'linkedin' | 'twitter'; href: string }
interface Featured { label: string; desc: string; cta: { label: string; href: string } }
interface Props {
  featured?: Featured | null;
  logo?: string;
  logoHref?: string;
  tagline?: string;
  socials?: Social[];
  newsletterLabel?: string;
  newsletterPlaceholder?: string;
  columns?: FooterColumn[];
  copyright?: string;
  bottomLinks?: { label: string; href: string }[];
  background?: string;
  accent?: string;
}

const {
  featured = { label: 'Nieuw: AI Automations', desc: 'Automatiseer je marketing met onze nieuwe AI agents.', cta: { label: 'Meer weten →', href: '#' } },
  logo = 'Merk',
  logoHref = '/',
  tagline = 'Online marketing die werkt voor ambitieuze bedrijven.',
  socials = [
    { network: 'instagram', href: '#' },
    { network: 'linkedin', href: '#' },
    { network: 'twitter', href: '#' },
  ],
  newsletterLabel = 'Nieuwsbrief',
  newsletterPlaceholder = 'Jouw e-mailadres',
  columns = [
    { title: 'Diensten', links: [
      { label: 'Google Ads', href: '#' },
      { label: 'Meta Ads', href: '#' },
      { label: 'SEO', href: '#' },
      { label: 'Webdesign', href: '#' },
    ] },
    { title: 'Bedrijf', links: [
      { label: 'Over ons', href: '#' },
      { label: 'Cases', href: '#' },
      { label: 'Blog', href: '#' },
      { label: 'Vacatures', href: '#' },
    ] },
    { title: 'Contact', links: [
      { label: 'Gratis gesprek', href: '#' },
      { label: 'Mail ons', href: '#' },
      { label: 'Bel ons', href: '#' },
    ] },
  ],
  copyright,
  bottomLinks = [
    { label: 'Privacybeleid', href: '#' },
    { label: 'Algemene voorwaarden', href: '#' },
  ],
  background = 'var(--color-primary, #0a0a0a)',
  accent = 'var(--color-accent, #6366f1)',
} = Astro.props;

const year = new Date().getFullYear();
const copyrightText = copyright ?? `© ${year}`;

const ICONS: Record<Social['network'], string> = {
  instagram: 'M12 2.163c3.204 0 3.584.012 4.85.07 3.252.148 4.771 1.691 4.919 4.919.058 1.265.069 1.645.069 4.849 0 3.205-.012 3.584-.069 4.849-.149 3.225-1.664 4.771-4.919 4.919-1.266.058-1.644.07-4.85.07-3.204 0-3.584-.012-4.849-.07-3.26-.149-4.771-1.699-4.919-4.92-.058-1.265-.07-1.644-.07-4.849 0-3.204.013-3.583.07-4.849.149-3.227 1.664-4.771 4.919-4.919 1.266-.057 1.645-.069 4.849-.069zm0-2.163c-3.259 0-3.667.014-4.947.072-4.358.2-6.78 2.618-6.98 6.98-.059 1.281-.073 1.689-.073 4.948 0 3.259.014 3.668.072 4.948.2 4.358 2.618 6.78 6.98 6.98 1.281.058 1.689.072 4.948.072 3.259 0 3.668-.014 4.948-.072 4.354-.2 6.782-2.618 6.979-6.98.059-1.28.073-1.689.073-4.948 0-3.259-.014-3.667-.072-4.947-.196-4.354-2.617-6.78-6.979-6.98-1.281-.059-1.69-.073-4.949-.073zm0 5.838c-3.403 0-6.162 2.759-6.162 6.162s2.759 6.163 6.162 6.163 6.162-2.759 6.162-6.163c0-3.403-2.759-6.162-6.162-6.162zm0 10.162c-2.209 0-4-1.79-4-4 0-2.209 1.791-4 4-4s4 1.791 4 4c0 2.21-1.791 4-4 4zm6.406-11.845c-.796 0-1.441.645-1.441 1.44s.645 1.44 1.441 1.44c.795 0 1.439-.645 1.439-1.44s-.644-1.44-1.439-1.44z',
  linkedin: 'M20.447 20.452h-3.554v-5.569c0-1.328-.027-3.037-1.852-3.037-1.853 0-2.136 1.445-2.136 2.939v5.667H9.351V9h3.414v1.561h.046c.477-.9 1.637-1.85 3.37-1.85 3.601 0 4.267 2.37 4.267 5.455v6.286zM5.337 7.433c-1.144 0-2.063-.926-2.063-2.065 0-1.138.92-2.063 2.063-2.063 1.14 0 2.064.925 2.064 2.063 0 1.139-.925 2.065-2.064 2.065zm1.782 13.019H3.555V9h3.564v11.452zM22.225 0H1.771C.792 0 0 .774 0 1.729v20.542C0 23.227.792 24 1.771 24h20.451C23.2 24 24 23.227 24 22.271V1.729C24 .774 23.2 0 22.222 0h.003z',
  twitter: 'M18.244 2.25h3.308l-7.227 8.26 8.502 11.24H16.17l-4.714-6.231-5.401 6.231H2.744l7.737-8.835L1.254 2.25H8.08l4.259 5.633 5.905-5.633zm-1.161 17.52h1.833L7.084 4.126H5.117z',
};
---

<footer class="bl-section fm" style={`--fm-bg:${background};--fm-ac:${accent}`}>
  {featured && (
    <div class="fm__featured">
      <div class="bl-inner fm__featured-inner">
        <div class="fm__featured-text">
          <p class="fm__featured-label"><span aria-hidden="true">→ </span>{featured.label}</p>
          <p class="fm__featured-desc">{featured.desc}</p>
        </div>
        <a href={featured.cta.href} class="fm__featured-cta">{featured.cta.label}</a>
      </div>
    </div>
  )}
  <div class="fm__body">
    <div class="bl-inner fm__inner">
      <div class="fm__brand">
        <a href={logoHref} class="fm__logo"><span class="fm__logo-text">{logo}</span></a>
        {tagline && <p class="fm__tagline">{tagline}</p>}
        {socials.length > 0 && (
          <div class="fm__socials">
            {socials.map(s => (
              <a href={s.href} class="fm__social" target="_blank" rel="noopener" aria-label={s.network}>
                <svg width="18" height="18" viewBox="0 0 24 24" fill="currentColor"><path d={ICONS[s.network]}></path></svg>
              </a>
            ))}
          </div>
        )}
        {newsletterLabel && (
          <div class="fm__newsletter">
            <p class="fm__newsletter-label">{newsletterLabel}</p>
            <form class="fm__newsletter-form">
              <input type="email" placeholder={newsletterPlaceholder} class="fm__newsletter-input" aria-label={newsletterLabel} />
              <button type="submit" class="fm__newsletter-btn" aria-label="Inschrijven">→</button>
            </form>
          </div>
        )}
      </div>
      {columns.map(col => (
        <div class="fm__col">
          <h3 class="fm__col-heading">{col.title}</h3>
          <ul class="fm__col-links">
            {col.links.map(l => <li><a href={l.href} class="fm__col-link">{l.label}</a></li>)}
          </ul>
        </div>
      ))}
    </div>
  </div>
  <div class="fm__bottom">
    <div class="bl-inner fm__bottom-inner">
      <p class="fm__copyright">{copyrightText}</p>
      {bottomLinks.length > 0 && (
        <div class="fm__bottom-links">
          {bottomLinks.map(l => <a href={l.href} class="fm__bottom-link">{l.label}</a>)}
        </div>
      )}
    </div>
  </div>
</footer>

<style>
.fm{background:var(--fm-bg);color:#aaa;padding-block:0}
.fm__featured{background:var(--fm-ac)}
.fm__featured-inner{padding-block:1.25rem;display:flex;align-items:center;justify-content:space-between;gap:1rem;flex-wrap:wrap}
.fm__featured-label{font-weight:700;color:#fff;font-size:.9375rem;margin:0}
.fm__featured-desc{font-size:.875rem;color:#ffffffe6;margin:.15rem 0 0}
.fm__featured-cta{display:inline-block;background:#ffffff29;color:#fff;padding:.5rem 1.25rem;border-radius:.5rem;text-decoration:none;font-weight:700;font-size:.875rem;white-space:nowrap;transition:background .2s}
.fm__featured-cta:hover{background:#ffffff40}
.fm__body{border-bottom:1px solid rgba(255,255,255,.08)}
.fm__inner{padding-block:4rem;display:grid;grid-template-columns:1.75fr 1fr 1fr 1fr;gap:3rem}
.fm__logo{text-decoration:none;display:inline-block;margin-bottom:1rem}
.fm__logo-text{font-size:1.25rem;font-weight:800;color:#fff;letter-spacing:-.03em}
.fm__tagline{font-size:1rem;line-height:1.65;margin-bottom:1.5rem;max-width:28ch;color:#aaa}
.fm__socials{display:flex;gap:.625rem;margin-bottom:1.75rem}
.fm__social{width:36px;height:36px;background:#ffffff1f;border-radius:.5rem;display:flex;align-items:center;justify-content:center;color:#e8e8e8;text-decoration:none;transition:background .15s,color .15s}
.fm__social:hover{background:var(--fm-ac);color:#fff}
.fm__newsletter-label{font-size:.8125rem;font-weight:600;color:#999;margin-bottom:.625rem;text-transform:uppercase;letter-spacing:.06em}
.fm__newsletter-form{display:flex;gap:0;border:1px solid rgba(255,255,255,.18);border-radius:.5rem;overflow:hidden}
.fm__newsletter-input{flex:1;background:#ffffff14;border:none;padding:.625rem .875rem;color:#fff;font-size:.9375rem;outline:none}
.fm__newsletter-input::placeholder{color:#999}
.fm__newsletter-btn{background:var(--fm-ac);border:none;color:#fff;padding:.625rem 1rem;cursor:pointer;font-size:1rem;transition:filter .15s}
.fm__newsletter-btn:hover{filter:brightness(1.15)}
.fm__col-heading{font-size:.75rem;font-weight:700;letter-spacing:.08em;text-transform:uppercase;color:#999;margin-bottom:1rem}
.fm__col-links{list-style:none;padding:0;margin:0;display:flex;flex-direction:column;gap:.5rem}
.fm__col-link{font-size:.9375rem;color:#aaa;text-decoration:none;transition:color .15s}
.fm__col-link:hover{color:#fff}
.fm__bottom-inner{padding-block:1.25rem;display:flex;align-items:center;justify-content:space-between;gap:1rem;flex-wrap:wrap}
.fm__copyright{font-size:.8125rem;color:#999;margin:0}
.fm__bottom-links{display:flex;gap:1.5rem}
.fm__bottom-link{font-size:.8125rem;color:#999;text-decoration:none;transition:color .15s}
.fm__bottom-link:hover{color:#fff}
@media(max-width:860px){.fm__inner{grid-template-columns:1fr 1fr}.fm__brand{grid-column:1 / -1}}
@media(max-width:520px){.fm__inner{grid-template-columns:1fr}.fm__bottom-inner{flex-direction:column;align-items:flex-start}}
</style>

Props

Prop Type Default Beschrijving
featured { label; desc; cta: { label; href } } | null - Accent featured-strip bovenaan
logo string 'Merk' Merknaam
tagline string - Korte omschrijving
socials { network: 'instagram'|'linkedin'|'twitter'; href }[] - Social-media links met SVG-icoon
newsletterLabel string 'Nieuwsbrief' Label boven het nieuwsbrief-formulier
newsletterPlaceholder string - Placeholder e-mailveld
columns { title; links: { label; href }[] }[] - Link-kolommen
bottomLinks { label; href }[] - Secundaire links onderaan
copyright string '© {jaar}' Copyright-regel
background string - Achtergrondkleur
accent string - Accent-kleur (strip, hover, knop)

* = verplicht