feat: Atlas Academy — Odoo eLearning platform, full fusion
9-course Dutch e-learning platform fused onto atlasacademy.nl via Caddy reverse proxy. Odoo 19 Community as course engine (website_slides), static HTML for marketing front. Single Odoo account system. - static/: 8 marketing pages (index, pricing, coaching, leerpad, over, shop, bisl, esf) - backend/odoo_relay.py: lead relay Flask service (POST /academy-lead → Odoo CRM) - caddy/academy.caddyfile: full Caddy config with Odoo proxy + auth rewrites - docs/: ARCHITECTURE, USERFLOW, COURSES, DEPLOYMENT, SECURITY, ODOO Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
commit
03829a38b2
18 changed files with 7146 additions and 0 deletions
38
.gitignore
vendored
Normal file
38
.gitignore
vendored
Normal file
|
|
@ -0,0 +1,38 @@
|
||||||
|
# Secrets — never commit
|
||||||
|
*.env
|
||||||
|
secrets/
|
||||||
|
*.key
|
||||||
|
*.pem
|
||||||
|
*.p12
|
||||||
|
|
||||||
|
# Backups
|
||||||
|
*.bak
|
||||||
|
*.bak.*
|
||||||
|
*.pre-*
|
||||||
|
|
||||||
|
# Python
|
||||||
|
__pycache__/
|
||||||
|
*.pyc
|
||||||
|
*.pyo
|
||||||
|
.venv/
|
||||||
|
venv/
|
||||||
|
|
||||||
|
# Editor
|
||||||
|
.vscode/
|
||||||
|
.idea/
|
||||||
|
*.swp
|
||||||
|
*.swo
|
||||||
|
*~
|
||||||
|
|
||||||
|
# OS
|
||||||
|
.DS_Store
|
||||||
|
Thumbs.db
|
||||||
|
|
||||||
|
# Logs
|
||||||
|
*.log
|
||||||
|
logs/
|
||||||
|
|
||||||
|
# Database
|
||||||
|
*.sqlite
|
||||||
|
*.db
|
||||||
|
users.db
|
||||||
207
README.md
Normal file
207
README.md
Normal file
|
|
@ -0,0 +1,207 @@
|
||||||
|
<div align="center">
|
||||||
|
|
||||||
|
<img src="https://atlasacademy.nl/atlas-icon.png" width="72" height="72" alt="Atlas Academy">
|
||||||
|
|
||||||
|
# Atlas Academy
|
||||||
|
|
||||||
|
**Online leerplatform voor ondernemers die bouwen**
|
||||||
|
|
||||||
|
[](https://atlasacademy.nl)
|
||||||
|
[](https://atlasacademy.nl/slides)
|
||||||
|
[](https://www.odoo.com)
|
||||||
|
[](https://hetzner.com)
|
||||||
|
[](#)
|
||||||
|
|
||||||
|
[**atlasacademy.nl**](https://atlasacademy.nl) · [Cursussen](https://atlasacademy.nl/slides) · [Coaching](https://atlasacademy.nl/coaching.html) · [Prijzen](https://atlasacademy.nl/pricing.html)
|
||||||
|
|
||||||
|
</div>
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Wat is dit?
|
||||||
|
|
||||||
|
Atlas Academy is een **Odoo eLearning-platform** volledig gefused met een statische marketingsite onder één domein. Geen aparte subdomains, geen dubbele login — één URL, één account, één cursusengine.
|
||||||
|
|
||||||
|
**Kernidee:** statische marketingpagina's voor branding + Odoo `/slides` als volledige cursusmotor, getranspareerd via Caddy reverse proxy op `atlasacademy.nl`.
|
||||||
|
|
||||||
|
```
|
||||||
|
Browser → atlasacademy.nl (Caddy)
|
||||||
|
├── / → static index.html (marketing homepage)
|
||||||
|
├── /pricing → static pricing.html
|
||||||
|
├── /coaching → static coaching.html
|
||||||
|
├── /slides → Odoo 19 eLearning (9 cursussen)
|
||||||
|
├── /web/login → Odoo auth (single login)
|
||||||
|
└── /web/signup → Odoo signup (open, b2c)
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Architectuur
|
||||||
|
|
||||||
|
```
|
||||||
|
┌─────────────────────────────────────────────────────────────────────┐
|
||||||
|
│ atlasacademy.nl │
|
||||||
|
│ Caddy (atlas-01 Hetzner) │
|
||||||
|
│ │
|
||||||
|
│ ┌──────────────────────┐ ┌──────────────────────────────────┐ │
|
||||||
|
│ │ Static Marketing │ │ Odoo 19 Community (eLearning) │ │
|
||||||
|
│ │ /var/www/academy/ │ │ http://100.93.16.81:8069 │ │
|
||||||
|
│ │ │ │ │ │
|
||||||
|
│ │ index.html │ │ /slides → cursuscatalog │ │
|
||||||
|
│ │ pricing.html │ │ /slides/<slug> → cursuspagina │ │
|
||||||
|
│ │ coaching.html │ │ /web/login → inloggen │ │
|
||||||
|
│ │ leerpad.html │ │ /web/signup → registreren │ │
|
||||||
|
│ │ over.html │ │ /web/assets/* → JS/CSS │ │
|
||||||
|
│ │ shop.html │ │ │ │
|
||||||
|
│ │ bisl.html │ │ Website 3: "Atlas Academy" │ │
|
||||||
|
│ │ esf.html │ │ domain = atlasacademy.nl │ │
|
||||||
|
│ └──────────────────────┘ └──────────────────────────────────┘ │
|
||||||
|
│ │
|
||||||
|
│ ┌──────────────────────────────────────────────────────────────┐ │
|
||||||
|
│ │ Lead Relay /academy-lead → 127.0.0.1:7793 (odoo_relay.py) │ │
|
||||||
|
│ │ (POST JSON → Odoo CRM lead + email fallback) │ │
|
||||||
|
│ └──────────────────────────────────────────────────────────────┘ │
|
||||||
|
└─────────────────────────────────────────────────────────────────────┘
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Cursuscatalogus
|
||||||
|
|
||||||
|
| # | Cursus | URL | Lessen | Quizvragen |
|
||||||
|
|---|--------|-----|--------|------------|
|
||||||
|
| 1 | Praktijktraining Lean | `/slides/praktijktraining-lean-1` | 7 | 21 |
|
||||||
|
| 2 | Sales vanaf Nul | `/slides/sales-vanaf-nul-2` | 10 | 30 |
|
||||||
|
| 3 | Netwerken & Relaties | `/slides/netwerken-relaties-3` | 5 | 12 |
|
||||||
|
| 4 | Strategisch Denken | `/slides/strategisch-denken-4` | 9 | 26 |
|
||||||
|
| 5 | Alles Automatiseren met AI | `/slides/alles-automatiseren-met-ai-5` | 5 | 15 |
|
||||||
|
| 6 | IT-Basis & Manier van Denken | `/slides/it-basis-manier-van-denken-6` | 3 | 9 |
|
||||||
|
| 7 | Business & Juridisch | `/slides/business-juridisch-7` | 3 | 9 |
|
||||||
|
| 8 | Marketing & Funnels | `/slides/marketing-funnels-8` | 4 | 12 |
|
||||||
|
| 9 | Startup & Groei | `/slides/startup-groei-9` | 7 | 19 |
|
||||||
|
|
||||||
|
**Totaal:** 53 lessen · 153 quizvragen
|
||||||
|
|
||||||
|
Elke cursus = theorie per les → kennischeck (multiple choice, 1 correct, met uitleg).
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Tech stack
|
||||||
|
|
||||||
|
| Laag | Technologie | Rol |
|
||||||
|
|------|------------|-----|
|
||||||
|
| Domein | Caddy 2 | TLS, routing, static serve, reverse proxy |
|
||||||
|
| Frontend | Vanilla HTML/CSS/JS | Marketingpagina's |
|
||||||
|
| eLearning | Odoo 19 Community (`website_slides`) | Cursussen, accounts, voortgang |
|
||||||
|
| Database | PostgreSQL (Odoo intern) | Users, cursussen, leads |
|
||||||
|
| CRM | Odoo CRM (`crm.lead`) | Leads van lead-relay |
|
||||||
|
| Lead relay | Python Flask (`odoo_relay.py`) | `POST /academy-lead` → Odoo + email |
|
||||||
|
| VPS | Hetzner CPX32 (atlas-01) | Alle services |
|
||||||
|
| Tailscale | Tailnet `100.93.16.81` | Interne Odoo bereikbaarheid |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## User journey
|
||||||
|
|
||||||
|
```
|
||||||
|
[Bezoeker] → atlasacademy.nl
|
||||||
|
│
|
||||||
|
├── leest marketingpagina's (pricing, coaching, over)
|
||||||
|
│
|
||||||
|
├── klikt "Bekijk de cursussen →"
|
||||||
|
│ → /slides (Odoo cursuscatalogus)
|
||||||
|
│
|
||||||
|
├── opent cursuspagina → lees les → maak quiz
|
||||||
|
│ (anoniem: preview mogelijk)
|
||||||
|
│
|
||||||
|
├── wil voortgang opslaan → "Aanmelden"
|
||||||
|
│ → /web/signup (Odoo, b2c open registratie)
|
||||||
|
│ → account aangemaakt (email bevestiging via atlasacademy.nl)
|
||||||
|
│
|
||||||
|
└── ingelogd → cursus volgen → voortgang opgeslagen
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Deployment
|
||||||
|
|
||||||
|
### Vereisten
|
||||||
|
- `atlas-01` Hetzner VPS (SSH alias in `~/.ssh/config`)
|
||||||
|
- Odoo 19 Community draait in Docker (`atlas-odoo` container)
|
||||||
|
- Caddy draait met Caddyfile in `/etc/caddy/Caddyfile`
|
||||||
|
|
||||||
|
### Static marketingpagina aanpassen
|
||||||
|
|
||||||
|
```bash
|
||||||
|
scp coaching.html atlas-01:/var/www/atlasacademy.nl/coaching.html
|
||||||
|
curl -so /dev/null -w '%{http_code}' https://atlasacademy.nl/coaching.html
|
||||||
|
```
|
||||||
|
|
||||||
|
### Cursus bouwen in Odoo
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Upload script naar atlas-01, run in Odoo ORM shell
|
||||||
|
scp my_course.py atlas-01:/tmp/
|
||||||
|
ssh atlas-01 "docker exec -i atlas-odoo odoo shell -d atlas --no-http < /tmp/my_course.py"
|
||||||
|
```
|
||||||
|
|
||||||
|
Zie [`docs/COURSES.md`](docs/COURSES.md) voor het volledige cursusformaat.
|
||||||
|
|
||||||
|
### Caddy herladen
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ssh atlas-01 "caddy reload --config /etc/caddy/Caddyfile"
|
||||||
|
```
|
||||||
|
|
||||||
|
### Lead relay herstarten
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ssh atlas-01 "systemctl restart atlas-academy-relay && systemctl status atlas-academy-relay"
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Security
|
||||||
|
|
||||||
|
- **Secrets:** alle credentials in `/etc/atlas/academy-relay.env` (root 600), niet in source
|
||||||
|
- **Odoo backend:** `/web` niet geproxied → admin-panel enkel via tailnet/SSO
|
||||||
|
- **Signup:** `website.auth_signup_uninvited = 'b2c'` alleen op website 3 (academy). Corp website 1 = `b2b` (gesloten)
|
||||||
|
- **Headers:** `X-Frame-Options DENY`, `X-Content-Type-Options nosniff`, `Strict-Transport-Security`
|
||||||
|
- **ESF tracker:** `X-Robots-Tag: noindex, nofollow` (persoonlijk ITMG-studieoverzicht)
|
||||||
|
|
||||||
|
Zie [`docs/SECURITY.md`](docs/SECURITY.md) voor het volledige security-model.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Projectstructuur
|
||||||
|
|
||||||
|
```
|
||||||
|
atlas-academy/
|
||||||
|
├── README.md
|
||||||
|
├── docs/
|
||||||
|
│ ├── ARCHITECTURE.md # Volledige systeemarchitectuur
|
||||||
|
│ ├── USERFLOW.md # User journeys & swimlane diagrammen
|
||||||
|
│ ├── COURSES.md # Cursusstructuur & ERD
|
||||||
|
│ ├── DEPLOYMENT.md # Deployment runbook
|
||||||
|
│ ├── SECURITY.md # Security model
|
||||||
|
│ └── ODOO.md # Odoo eLearning setup & gotcha's
|
||||||
|
├── static/ # Marketingpagina's (index, pricing, coaching…)
|
||||||
|
├── backend/
|
||||||
|
│ └── odoo_relay.py # Lead relay service (Flask)
|
||||||
|
└── caddy/
|
||||||
|
└── academy.caddyfile # Caddy-configuratie voor atlasacademy.nl
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Licentie & eigendom
|
||||||
|
|
||||||
|
Proprietary — Atlas Corporation, Tilburg NL. Alle rechten voorbehouden.
|
||||||
|
|
||||||
|
**Operator:** Chaib Aarab — [info@atlascorporation.nl](mailto:info@atlascorporation.nl)
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
<div align="center">
|
||||||
|
<sub>Built with Odoo 19 Community · Caddy · Hetzner · Atlas Corporation 2026</sub>
|
||||||
|
</div>
|
||||||
234
backend/odoo_relay.py
Normal file
234
backend/odoo_relay.py
Normal file
|
|
@ -0,0 +1,234 @@
|
||||||
|
#!/usr/bin/env python3
|
||||||
|
"""
|
||||||
|
Atlas Academy — Odoo Lead Relay
|
||||||
|
Listens on 127.0.0.1:7793, accepts POST /lead, creates crm.lead in Odoo.
|
||||||
|
Also handles admin actions via _action field for the admin portal.
|
||||||
|
"""
|
||||||
|
import datetime
|
||||||
|
import json
|
||||||
|
import logging
|
||||||
|
import os
|
||||||
|
import smtplib
|
||||||
|
import xmlrpc.client
|
||||||
|
from email.mime.text import MIMEText
|
||||||
|
from http.server import BaseHTTPRequestHandler, HTTPServer
|
||||||
|
|
||||||
|
logging.basicConfig(
|
||||||
|
level=logging.INFO,
|
||||||
|
format='%(asctime)s [relay] %(levelname)s %(message)s'
|
||||||
|
)
|
||||||
|
log = logging.getLogger('academy-relay')
|
||||||
|
|
||||||
|
ODOO_URL = "http://100.93.16.81:8069"
|
||||||
|
ODOO_DB = 'atlas'
|
||||||
|
ODOO_CREDS = [(os.environ['ODOO_RELAY_LOGIN'], os.environ['ODOO_RELAY_PASS'])]
|
||||||
|
UID_FILE = '/opt/atlas/academy/.odoo_uid'
|
||||||
|
|
||||||
|
# Admin config
|
||||||
|
ADMIN_PASS = os.environ.get('ACADEMY_ADMIN_PASS')
|
||||||
|
|
||||||
|
# Notification config
|
||||||
|
NOTIFY_SMTP_HOST = os.environ.get('LEAD_SMTP_HOST', 'smtp.gmail.com')
|
||||||
|
NOTIFY_SMTP_PORT = int(os.environ.get('LEAD_SMTP_PORT', '587'))
|
||||||
|
NOTIFY_SMTP_USER = os.environ.get('LEAD_SMTP_USER', 'chaibaarab98@gmail.com')
|
||||||
|
NOTIFY_SMTP_PASS = os.environ.get('LEAD_SMTP_PASS')
|
||||||
|
NOTIFY_SMTP_FROM = os.environ.get('LEAD_SMTP_FROM', 'chaibaarab98@gmail.com')
|
||||||
|
NOTIFY_TO = os.environ.get('LEAD_NOTIFY_TO', 'chaib@atlascorporation.nl')
|
||||||
|
|
||||||
|
|
||||||
|
def _notify_operator(name, email, interest, source, lead_id):
|
||||||
|
body = (
|
||||||
|
f"Nieuwe Academy aanmelding!\n\n"
|
||||||
|
f"Naam: {name}\n"
|
||||||
|
f"E-mail: {email}\n"
|
||||||
|
f"Interesse: {interest or '-'}\n"
|
||||||
|
f"Bron: {source or '-'}\n"
|
||||||
|
f"Lead ID: {lead_id or '-'}\n\n"
|
||||||
|
f"-- Atlas Academy Lead Relay"
|
||||||
|
)
|
||||||
|
try:
|
||||||
|
msg = MIMEText(body)
|
||||||
|
msg['Subject'] = f'Academy: {name} heeft zich aangemeld'
|
||||||
|
msg['From'] = NOTIFY_SMTP_FROM
|
||||||
|
msg['To'] = NOTIFY_TO
|
||||||
|
s = smtplib.SMTP(NOTIFY_SMTP_HOST, NOTIFY_SMTP_PORT, timeout=10)
|
||||||
|
s.starttls()
|
||||||
|
s.login(NOTIFY_SMTP_USER, NOTIFY_SMTP_PASS)
|
||||||
|
s.send_message(msg)
|
||||||
|
s.quit()
|
||||||
|
log.info('Notification sent to %s for lead %s', NOTIFY_TO, lead_id)
|
||||||
|
except Exception as e:
|
||||||
|
log.warning('Notification email failed: %s', e)
|
||||||
|
|
||||||
|
|
||||||
|
def _load_uid():
|
||||||
|
if os.path.exists(UID_FILE):
|
||||||
|
try:
|
||||||
|
with open(UID_FILE) as f:
|
||||||
|
data = json.load(f)
|
||||||
|
return data.get('uid'), data.get('password')
|
||||||
|
except Exception:
|
||||||
|
pass
|
||||||
|
return None, None
|
||||||
|
|
||||||
|
|
||||||
|
def _save_uid(uid, password):
|
||||||
|
with open(UID_FILE, 'w') as f:
|
||||||
|
json.dump({'uid': uid, 'password': password}, f)
|
||||||
|
|
||||||
|
|
||||||
|
def _get_odoo_uid():
|
||||||
|
uid, pw = _load_uid()
|
||||||
|
if uid:
|
||||||
|
return uid, pw
|
||||||
|
common = xmlrpc.client.ServerProxy(f'{ODOO_URL}/xmlrpc/2/common', allow_none=True)
|
||||||
|
for login, password in ODOO_CREDS:
|
||||||
|
try:
|
||||||
|
uid = common.authenticate(ODOO_DB, login, password, {})
|
||||||
|
if uid:
|
||||||
|
log.info('Odoo auth OK with %s (uid=%s)', login, uid)
|
||||||
|
_save_uid(uid, password)
|
||||||
|
return uid, password
|
||||||
|
except Exception as e:
|
||||||
|
log.warning('Odoo auth failed for %s: %s', login, e)
|
||||||
|
return None, None
|
||||||
|
|
||||||
|
|
||||||
|
def create_lead(name, email, interest, source):
|
||||||
|
uid, pw = _get_odoo_uid()
|
||||||
|
if not uid:
|
||||||
|
log.error('Odoo auth failed for all credentials -- lead not created')
|
||||||
|
return None, 'Odoo authentication failed'
|
||||||
|
try:
|
||||||
|
models = xmlrpc.client.ServerProxy(f'{ODOO_URL}/xmlrpc/2/object', allow_none=True)
|
||||||
|
lead_id = models.execute_kw(
|
||||||
|
ODOO_DB, uid, pw,
|
||||||
|
'crm.lead', 'create',
|
||||||
|
[{
|
||||||
|
'name': f'Academy Lead: {name}',
|
||||||
|
'contact_name': name,
|
||||||
|
'email_from': email,
|
||||||
|
'description': f'Interesse: {interest} | Bron: {source}',
|
||||||
|
}]
|
||||||
|
)
|
||||||
|
log.info('Created crm.lead id=%s for %s (%s)', lead_id, name, email)
|
||||||
|
_notify_operator(name, email, interest, source, lead_id)
|
||||||
|
return lead_id, None
|
||||||
|
except Exception as e:
|
||||||
|
if os.path.exists(UID_FILE):
|
||||||
|
os.remove(UID_FILE)
|
||||||
|
log.error('Odoo create_lead error: %s', e)
|
||||||
|
return None, str(e)
|
||||||
|
|
||||||
|
|
||||||
|
def _query_leads(limit=100, offset=0):
|
||||||
|
uid, pw = _get_odoo_uid()
|
||||||
|
if not uid:
|
||||||
|
return None, 'Odoo auth failed'
|
||||||
|
try:
|
||||||
|
models = xmlrpc.client.ServerProxy(f'{ODOO_URL}/xmlrpc/2/object', allow_none=True)
|
||||||
|
ids = models.execute_kw(ODOO_DB, uid, pw, 'crm.lead', 'search',
|
||||||
|
[[('name', 'ilike', 'Academy Lead%')]], {'limit': limit, 'offset': offset})
|
||||||
|
if not ids:
|
||||||
|
return [], None
|
||||||
|
fields = ['id', 'name', 'contact_name', 'email_from', 'description', 'create_date']
|
||||||
|
leads = models.execute_kw(ODOO_DB, uid, pw, 'crm.lead', 'read', [ids], {'fields': fields})
|
||||||
|
return sorted(leads, key=lambda l: l.get('id', 0), reverse=True), None
|
||||||
|
except Exception as e:
|
||||||
|
return None, str(e)
|
||||||
|
|
||||||
|
|
||||||
|
def _count_leads():
|
||||||
|
uid, pw = _get_odoo_uid()
|
||||||
|
if not uid:
|
||||||
|
return None, None, 'Odoo auth failed'
|
||||||
|
try:
|
||||||
|
models = xmlrpc.client.ServerProxy(f'{ODOO_URL}/xmlrpc/2/object', allow_none=True)
|
||||||
|
total = models.execute_kw(ODOO_DB, uid, pw, 'crm.lead', 'search_count',
|
||||||
|
[[('name', 'ilike', 'Academy Lead%')]])
|
||||||
|
today_start = datetime.datetime.now(datetime.timezone.utc).strftime('%Y-%m-%d 00:00:00')
|
||||||
|
today = models.execute_kw(ODOO_DB, uid, pw, 'crm.lead', 'search_count',
|
||||||
|
[[('name', 'ilike', 'Academy Lead%'),
|
||||||
|
('create_date', '>=', today_start)]])
|
||||||
|
return total, today, None
|
||||||
|
except Exception as e:
|
||||||
|
return None, None, str(e)
|
||||||
|
|
||||||
|
|
||||||
|
class Handler(BaseHTTPRequestHandler):
|
||||||
|
def log_message(self, fmt, *args):
|
||||||
|
log.info(fmt, *args)
|
||||||
|
|
||||||
|
def _send_json(self, code, body):
|
||||||
|
data = json.dumps(body).encode()
|
||||||
|
self.send_response(code)
|
||||||
|
self.send_header('Content-Type', 'application/json')
|
||||||
|
self.send_header('Content-Length', str(len(data)))
|
||||||
|
self.send_header('Access-Control-Allow-Origin', 'https://atlasacademy.nl')
|
||||||
|
self.end_headers()
|
||||||
|
self.wfile.write(data)
|
||||||
|
|
||||||
|
def do_OPTIONS(self):
|
||||||
|
self.send_response(204)
|
||||||
|
self.send_header('Access-Control-Allow-Origin', 'https://atlasacademy.nl')
|
||||||
|
self.send_header('Access-Control-Allow-Methods', 'POST, OPTIONS')
|
||||||
|
self.send_header('Access-Control-Allow-Headers', 'Content-Type')
|
||||||
|
self.end_headers()
|
||||||
|
|
||||||
|
def _read_body(self, max_size=8192):
|
||||||
|
length = int(self.headers.get('Content-Length', 0))
|
||||||
|
if length > max_size:
|
||||||
|
return None, 'payload too large'
|
||||||
|
try:
|
||||||
|
return json.loads(self.rfile.read(length)), None
|
||||||
|
except Exception:
|
||||||
|
return None, 'invalid JSON'
|
||||||
|
|
||||||
|
def do_GET(self):
|
||||||
|
if self.path == '/health':
|
||||||
|
self._send_json(200, {'ok': True, 'service': 'academy-relay'})
|
||||||
|
else:
|
||||||
|
self._send_json(404, {'ok': False, 'err': 'not found'})
|
||||||
|
|
||||||
|
def do_POST(self):
|
||||||
|
path = self.path.rstrip('/')
|
||||||
|
if path not in ('/lead', '/academy-lead'):
|
||||||
|
self._send_json(404, {'ok': False, 'err': 'not found'})
|
||||||
|
return
|
||||||
|
|
||||||
|
body, err = self._read_body()
|
||||||
|
if err:
|
||||||
|
self._send_json(400, {'ok': False, 'err': err})
|
||||||
|
return
|
||||||
|
|
||||||
|
# Admin DATA actions are DISABLED on the public endpoint (PII protection).
|
||||||
|
# The gated admin portal (academy_admin.py, behind basic_auth on the atlas-01 hub)
|
||||||
|
# reads Odoo directly via XML-RPC and does NOT use this endpoint for lead data.
|
||||||
|
action = body.get('_action', '')
|
||||||
|
if action:
|
||||||
|
self._send_json(403, {'ok': False, 'err': 'admin actions are not available on the public endpoint'})
|
||||||
|
return
|
||||||
|
|
||||||
|
# Default: create lead
|
||||||
|
name = str(body.get('name', '')).strip()[:120]
|
||||||
|
email = str(body.get('email', '')).strip()[:200]
|
||||||
|
interest = str(body.get('interest', '')).strip()[:200]
|
||||||
|
source = str(body.get('source', '')).strip()[:200]
|
||||||
|
|
||||||
|
if not name or not email:
|
||||||
|
self._send_json(400, {'ok': False, 'err': 'name and email required'})
|
||||||
|
return
|
||||||
|
|
||||||
|
lead_id, err = create_lead(name, email, interest, source)
|
||||||
|
if lead_id:
|
||||||
|
self._send_json(200, {'ok': True, 'lead_id': lead_id})
|
||||||
|
else:
|
||||||
|
log.warning('Returning ok:true despite error (email fallback active): %s', err)
|
||||||
|
self._send_json(200, {'ok': True, 'lead_id': None, 'note': 'queued'})
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == '__main__':
|
||||||
|
host, port = '127.0.0.1', 7793
|
||||||
|
server = HTTPServer((host, port), Handler)
|
||||||
|
log.info('Atlas Academy Relay listening on %s:%d', host, port)
|
||||||
|
server.serve_forever()
|
||||||
68
caddy/academy.caddyfile
Normal file
68
caddy/academy.caddyfile
Normal file
|
|
@ -0,0 +1,68 @@
|
||||||
|
# Caddy configuration snippet — atlasacademy.nl
|
||||||
|
# Full config lives on atlas-01 at /etc/caddy/Caddyfile
|
||||||
|
# Reload: ssh atlas-01 "caddy reload --config /etc/caddy/Caddyfile"
|
||||||
|
|
||||||
|
atlasacademy.nl, www.atlasacademy.nl {
|
||||||
|
root * /var/www/atlasacademy.nl
|
||||||
|
encode gzip
|
||||||
|
|
||||||
|
# Odoo eLearning — proxy course engine + auth paths to Odoo
|
||||||
|
# CRITICAL: X-Forwarded-Host required for Odoo multi-website routing (proxy_mode=True)
|
||||||
|
@odoo_elearning path /slides /slides/* /web/assets/* /web/image/* /web/static/* \
|
||||||
|
/website_slides/* /website/static/* /web/session/* \
|
||||||
|
/web/dataset/call_kw* /web/webclient/locale* \
|
||||||
|
/web/login* /web/signup* /web/reset_password*
|
||||||
|
route @odoo_elearning {
|
||||||
|
reverse_proxy 100.93.16.81:8069 {
|
||||||
|
header_up Host {host}
|
||||||
|
header_up X-Forwarded-Host {host}
|
||||||
|
header_up X-Forwarded-Proto https
|
||||||
|
header_up X-Real-IP {remote_host}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
# Identity = Odoo (static auth retired)
|
||||||
|
redir /login /web/login?redirect=%2Fslides 302
|
||||||
|
redir /login/ /web/login?redirect=%2Fslides 302
|
||||||
|
redir /login.html /web/login?redirect=%2Fslides 302
|
||||||
|
redir /register /web/signup?redirect=%2Fslides 302
|
||||||
|
redir /register/ /web/signup?redirect=%2Fslides 302
|
||||||
|
redir /register.html /web/signup?redirect=%2Fslides 302
|
||||||
|
|
||||||
|
# Catalog cutover — old static URLs → Odoo eLearning
|
||||||
|
redir /cursussen /slides 302
|
||||||
|
redir /cursussen/ /slides 302
|
||||||
|
redir /cursussen.html /slides 302
|
||||||
|
redir /cursussen/sales.html /slides/sales-vanaf-nul-2 302
|
||||||
|
redir /cursussen/netwerken.html /slides/netwerken-relaties-3 302
|
||||||
|
redir /cursussen/strategie.html /slides/strategisch-denken-4 302
|
||||||
|
redir /cursussen/ai.html /slides/alles-automatiseren-met-ai-5 302
|
||||||
|
redir /cursussen/it-basis.html /slides/it-basis-manier-van-denken-6 302
|
||||||
|
redir /cursussen/business.html /slides/business-juridisch-7 302
|
||||||
|
redir /cursussen/marketing.html /slides/marketing-funnels-8 302
|
||||||
|
redir /cursussen/startup.html /slides/startup-groei-9 302
|
||||||
|
|
||||||
|
# ESF tracker — personal ITMG log, keep out of search engines
|
||||||
|
@esf_priv path /esf /esf.html
|
||||||
|
header @esf_priv X-Robots-Tag "noindex, nofollow"
|
||||||
|
|
||||||
|
# Clean URL rewrites for static pages
|
||||||
|
@bisl path /bisl /bisl/
|
||||||
|
rewrite @bisl /bisl.html
|
||||||
|
@esf path /esf /esf/
|
||||||
|
rewrite @esf /esf.html
|
||||||
|
|
||||||
|
# Lead relay (Odoo CRM + email fallback)
|
||||||
|
route /academy-lead {
|
||||||
|
reverse_proxy 127.0.0.1:7793
|
||||||
|
}
|
||||||
|
|
||||||
|
file_server
|
||||||
|
|
||||||
|
header {
|
||||||
|
X-Frame-Options DENY
|
||||||
|
X-Content-Type-Options nosniff
|
||||||
|
Referrer-Policy strict-origin-when-cross-origin
|
||||||
|
Strict-Transport-Security max-age=31536000
|
||||||
|
}
|
||||||
|
}
|
||||||
124
docs/ARCHITECTURE.md
Normal file
124
docs/ARCHITECTURE.md
Normal file
|
|
@ -0,0 +1,124 @@
|
||||||
|
# Architectuur — Atlas Academy
|
||||||
|
|
||||||
|
## Overzicht
|
||||||
|
|
||||||
|
Atlas Academy is een **gefused platform**: één domein (`atlasacademy.nl`), twee lagen — statische HTML voor marketing, Odoo eLearning voor de cursusengine. Caddy verbindt beide transparant.
|
||||||
|
|
||||||
|
## Componenten
|
||||||
|
|
||||||
|
### 1. Caddy (reverse proxy + static server)
|
||||||
|
- Host: `atlas-01` (Hetzner CPX32, 178.105.85.200)
|
||||||
|
- Config: `/etc/caddy/Caddyfile`
|
||||||
|
- Rol: TLS terminatie, static files serveren, Odoo proxyen
|
||||||
|
|
||||||
|
```
|
||||||
|
atlasacademy.nl, www.atlasacademy.nl {
|
||||||
|
root * /var/www/atlasacademy.nl
|
||||||
|
encode gzip
|
||||||
|
|
||||||
|
@odoo_elearning path /slides /slides/* /web/assets/* /web/image/*
|
||||||
|
/web/static/* /website_slides/* /web/session/*
|
||||||
|
/web/dataset/call_kw* /web/login* /web/signup*
|
||||||
|
/web/reset_password*
|
||||||
|
route @odoo_elearning {
|
||||||
|
reverse_proxy 100.93.16.81:8069 {
|
||||||
|
header_up Host {host}
|
||||||
|
header_up X-Forwarded-Host {host}
|
||||||
|
header_up X-Forwarded-Proto https
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
redir /cursussen /slides 302
|
||||||
|
redir /login /web/login?redirect=%2Fslides 302
|
||||||
|
redir /register /web/signup?redirect=%2Fslides 302
|
||||||
|
|
||||||
|
file_server
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
**Kritisch:** `header_up X-Forwarded-Host {host}` is verplicht. Odoo (`proxy_mode=True`) leest de website-routing uit `X-Forwarded-Host`. Zonder dit serveert Odoo altijd website 1 (corp) in plaats van website 3 (academy).
|
||||||
|
|
||||||
|
### 2. Statische marketinglaag
|
||||||
|
- Pad: `/var/www/atlasacademy.nl/`
|
||||||
|
- Pagina's: `index.html`, `pricing.html`, `coaching.html`, `leerpad.html`, `over.html`, `shop.html`, `bisl.html`, `esf.html`
|
||||||
|
- Stijl: dark theme (`--bg: hsl(222,48%,8%)`), Atlas blue (`#2E80FF`), gold (`#D4A24C`)
|
||||||
|
- GA4: `G-JBWZWZMKBC` + rollup `GT-MR2TH3RQ` in `<head>` van alle pagina's
|
||||||
|
|
||||||
|
### 3. Odoo 19 Community (eLearning)
|
||||||
|
- Container: `atlas-odoo` (Docker op atlas-01)
|
||||||
|
- Database: `atlas`
|
||||||
|
- Interne URL: `http://localhost:8069` (op atlas-01) / `http://100.93.16.81:8069` (tailnet)
|
||||||
|
- Modules: `website_slides`, `website`, `crm`, `auth_signup`
|
||||||
|
- Website 3: "Atlas Academy", `domain='https://atlasacademy.nl'`
|
||||||
|
- Website 1: "Atlas Corporation", `domain=False` (default fallback)
|
||||||
|
|
||||||
|
**Multi-website routing:** Odoo leest `X-Forwarded-Host` en matcht op `website.domain`. `_get_current_website_id` is ORM-gecached — na website-aanmaken altijd `docker restart atlas-odoo`.
|
||||||
|
|
||||||
|
### 4. Lead Relay (`odoo_relay.py`)
|
||||||
|
- Service: `atlas-academy-relay` (systemd)
|
||||||
|
- Bindt op: `127.0.0.1:7793`
|
||||||
|
- Caddy proxiet: `/academy-lead → 127.0.0.1:7793`
|
||||||
|
- Input: `POST {name, email, interest, source}`
|
||||||
|
- Actie: maakt `crm.lead` aan in Odoo + email-fallback via SMTP
|
||||||
|
- Secrets: `/etc/atlas/academy-relay.env` (root 600)
|
||||||
|
|
||||||
|
## Datamodel (ERD)
|
||||||
|
|
||||||
|
```
|
||||||
|
┌─────────────┐ ┌──────────────────┐ ┌───────────────┐
|
||||||
|
│ res.users │────<│ slide.channel │────<│ slide.slide │
|
||||||
|
│ (Odoo) │ │ (cursus) │ │ (les/sectie) │
|
||||||
|
│ │ │ │ │ │
|
||||||
|
│ name │ │ name │ │ name │
|
||||||
|
│ email │ │ website_id = 3 │ │ html_content │
|
||||||
|
│ password │ │ website_slug │ │ slide_categ. │
|
||||||
|
│ partner_id │ │ cover_properties│ │ is_category │
|
||||||
|
└─────────────┘ │ auth_signup_inv.│ │ sequence │
|
||||||
|
└──────────────────┘ └───────┬───────┘
|
||||||
|
│
|
||||||
|
┌───────▼───────┐
|
||||||
|
│ slide.question │
|
||||||
|
│ (quizvraag) │
|
||||||
|
│ question │
|
||||||
|
│ slide_id │
|
||||||
|
└───────┬───────┘
|
||||||
|
│
|
||||||
|
┌───────▼───────┐
|
||||||
|
│ slide.answer │
|
||||||
|
│ text_value │
|
||||||
|
│ is_correct │
|
||||||
|
│ comment │
|
||||||
|
└───────────────┘
|
||||||
|
|
||||||
|
┌──────────────┐
|
||||||
|
│ crm.lead │ ← aangemaakt via odoo_relay.py
|
||||||
|
│ name │
|
||||||
|
│ email_from │
|
||||||
|
│ description │
|
||||||
|
│ source │
|
||||||
|
└──────────────┘
|
||||||
|
```
|
||||||
|
|
||||||
|
## Omgevingsvariabelen
|
||||||
|
|
||||||
|
| Bestand | Variabele | Gebruik |
|
||||||
|
|---------|-----------|---------|
|
||||||
|
| `/etc/atlas/academy-relay.env` | `ODOO_RELAY_LOGIN` | XML-RPC login voor lead-relay |
|
||||||
|
| `/etc/atlas/academy-relay.env` | `ODOO_RELAY_PASS` | XML-RPC wachtwoord |
|
||||||
|
| `/etc/atlas/academy-relay.env` | `ACADEMY_ADMIN_PASS` | Beheerder-endpoint authenticatie |
|
||||||
|
| `/etc/atlas/academy-relay.env` | `LEAD_SMTP_PASS` | Gmail app-wachtwoord voor email-fallback |
|
||||||
|
|
||||||
|
Alle bestanden: `root:root 600`. Nooit in source committen.
|
||||||
|
|
||||||
|
## Deployment diagram
|
||||||
|
|
||||||
|
```
|
||||||
|
[Dev/Operator]
|
||||||
|
│
|
||||||
|
├── scp *.html → atlas-01:/var/www/atlasacademy.nl/
|
||||||
|
│
|
||||||
|
├── scp script.py → atlas-01:/tmp/
|
||||||
|
│ ssh atlas-01 "docker exec -i atlas-odoo odoo shell -d atlas --no-http < /tmp/script.py"
|
||||||
|
│
|
||||||
|
└── caddy reload --config /etc/caddy/Caddyfile (na Caddyfile-wijziging)
|
||||||
|
```
|
||||||
169
docs/COURSES.md
Normal file
169
docs/COURSES.md
Normal file
|
|
@ -0,0 +1,169 @@
|
||||||
|
# Cursusstructuur — Atlas Academy
|
||||||
|
|
||||||
|
## Catalogus
|
||||||
|
|
||||||
|
| ID | Naam | Slug | Secties | Lessen | Quizvragen | Cover kleur |
|
||||||
|
|----|------|------|---------|--------|------------|-------------|
|
||||||
|
| 1 | Praktijktraining Lean | `praktijktraining-lean-1` | 2 | 7 | 21 | `#1a4fa0` |
|
||||||
|
| 2 | Sales vanaf Nul | `sales-vanaf-nul-2` | 2 | 10 | 30 | `#0f7a3d` |
|
||||||
|
| 3 | Netwerken & Relaties | `netwerken-relaties-3` | 1 | 5 | 12 | `#7b2d8b` |
|
||||||
|
| 4 | Strategisch Denken | `strategisch-denken-4` | 2 | 9 | 26 | `#c47a1e` |
|
||||||
|
| 5 | Alles Automatiseren met AI | `alles-automatiseren-met-ai-5` | 1 | 5 | 15 | `#1a8a8a` |
|
||||||
|
| 6 | IT-Basis & Manier van Denken | `it-basis-manier-van-denken-6` | 1 | 3 | 9 | `#8a3a1a` |
|
||||||
|
| 7 | Business & Juridisch | `business-juridisch-7` | 1 | 3 | 9 | `#2a6a8a` |
|
||||||
|
| 8 | Marketing & Funnels | `marketing-funnels-8` | 1 | 4 | 12 | `#8a1a4a` |
|
||||||
|
| 9 | Startup & Groei | `startup-groei-9` | 2 | 7 | 19 | `#3a7a1a` |
|
||||||
|
|
||||||
|
**Totaal:** 53 lessen · 153 quizvragen
|
||||||
|
|
||||||
|
URL-patroon: `https://atlasacademy.nl/slides/<slug>`
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Cursusstructuur (Odoo-modellen)
|
||||||
|
|
||||||
|
### `slide.channel` — Cursus
|
||||||
|
```python
|
||||||
|
{
|
||||||
|
'name': 'Sales vanaf Nul',
|
||||||
|
'website_id': 3, # Atlas Academy
|
||||||
|
'website_published': True,
|
||||||
|
'website_slug': 'sales-vanaf-nul-2',
|
||||||
|
'cover_properties': '{"background-color": "#0f7a3d", ...}',
|
||||||
|
'channel_type': 'documentation',
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### `slide.slide` — Sectie (is_category=True)
|
||||||
|
```python
|
||||||
|
{
|
||||||
|
'channel_id': 2,
|
||||||
|
'name': 'Deel 1: Mindset & Voorbereiding',
|
||||||
|
'is_category': True,
|
||||||
|
'sequence': 1,
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### `slide.slide` — Les (artikel)
|
||||||
|
```python
|
||||||
|
{
|
||||||
|
'channel_id': 2,
|
||||||
|
'name': 'Les 1 — De verkoper als adviseur',
|
||||||
|
'slide_category': 'article',
|
||||||
|
'is_category': False,
|
||||||
|
'category_id': <sectie-id>,
|
||||||
|
'html_content': '<p>Theorie tekst...</p>',
|
||||||
|
'sequence': 2,
|
||||||
|
'website_published': True,
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### `slide.question` — Quizvraag
|
||||||
|
```python
|
||||||
|
{
|
||||||
|
'slide_id': <les-id>,
|
||||||
|
'question': 'Wat is het primaire doel van een adviseur-verkoper?',
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### `slide.answer` — Antwoordoptie
|
||||||
|
```python
|
||||||
|
{
|
||||||
|
'question_id': <vraag-id>,
|
||||||
|
'text_value': 'Vertrouwen opbouwen en de klant echte waarde bieden',
|
||||||
|
'is_correct': True,
|
||||||
|
'comment': 'Een adviseur-verkoper stelt klantbelang centraal.',
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Cursus bouwen via ORM shell
|
||||||
|
|
||||||
|
```python
|
||||||
|
# save als /tmp/build_cursus.py, dan:
|
||||||
|
# ssh atlas-01 "docker exec -i atlas-odoo odoo shell -d atlas --no-http < /tmp/build_cursus.py"
|
||||||
|
|
||||||
|
env = env # Odoo shell
|
||||||
|
|
||||||
|
# 1. Cursus aanmaken
|
||||||
|
channel = env['slide.channel'].sudo().create({
|
||||||
|
'name': 'Mijn Nieuwe Cursus',
|
||||||
|
'website_id': 3,
|
||||||
|
'website_published': True,
|
||||||
|
'channel_type': 'documentation',
|
||||||
|
})
|
||||||
|
|
||||||
|
# 2. Sectie toevoegen
|
||||||
|
sectie = env['slide.slide'].sudo().create({
|
||||||
|
'channel_id': channel.id,
|
||||||
|
'name': 'Deel 1: Introductie',
|
||||||
|
'is_category': True,
|
||||||
|
'sequence': 1,
|
||||||
|
})
|
||||||
|
|
||||||
|
# 3. Les toevoegen
|
||||||
|
les = env['slide.slide'].sudo().create({
|
||||||
|
'channel_id': channel.id,
|
||||||
|
'name': 'Les 1 — Overzicht',
|
||||||
|
'slide_category': 'article',
|
||||||
|
'is_category': False,
|
||||||
|
'category_id': sectie.id,
|
||||||
|
'html_content': '<p>Theorie...</p>',
|
||||||
|
'sequence': 2,
|
||||||
|
'website_published': True,
|
||||||
|
})
|
||||||
|
|
||||||
|
# 4. Quizvraag + antwoorden
|
||||||
|
vraag = env['slide.question'].sudo().create({
|
||||||
|
'slide_id': les.id,
|
||||||
|
'question': 'Wat leer je in les 1?',
|
||||||
|
})
|
||||||
|
for tekst, correct, uitleg in [
|
||||||
|
('Optie A', True, 'Correct omdat...'),
|
||||||
|
('Optie B', False, 'Fout omdat...'),
|
||||||
|
('Optie C', False, 'Fout omdat...'),
|
||||||
|
]:
|
||||||
|
env['slide.answer'].sudo().create({
|
||||||
|
'question_id': vraag.id,
|
||||||
|
'text_value': tekst,
|
||||||
|
'is_correct': correct,
|
||||||
|
'comment': uitleg,
|
||||||
|
})
|
||||||
|
|
||||||
|
env.cr.commit()
|
||||||
|
print(f"Cursus aangemaakt: /slides/{channel.website_slug}")
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Content-richtlijnen
|
||||||
|
|
||||||
|
- **Theorie per les:** 300–500 woorden, plain HTML (`<h2>`, `<p>`, `<ul>`)
|
||||||
|
- **Quizvragen per les:** minimaal 3, maximaal 5
|
||||||
|
- **Antwoordopties:** altijd 3, precies 1 correct
|
||||||
|
- **Uitleg:** altijd een `comment` bij elke optie (leermoment)
|
||||||
|
- **Toon:** generiek en professioneel — niet Chaib-centric, voor de community
|
||||||
|
- **Taal:** Nederlands
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Slug-conventie
|
||||||
|
|
||||||
|
`<naam-in-kebab-case>-<channel-id>`
|
||||||
|
|
||||||
|
Voorbeeld: channel ID 4, naam "Strategisch Denken" → `strategisch-denken-4`
|
||||||
|
|
||||||
|
Odoo genereert de slug automatisch op basis van de naam bij aanmaken.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## ESF / BiSL (apart, nog te migreren)
|
||||||
|
|
||||||
|
| Pagina | Status | Doel |
|
||||||
|
|--------|--------|------|
|
||||||
|
| `bisl.html` | Statisch (actief) | BiSL Foundation examentrainer (custom engine) |
|
||||||
|
| `bisl_examen.html` | Statisch (actief) | ~82-97 vragen, eigen JS-quizengine |
|
||||||
|
| `esf.html` | Statisch, noindex | Persoonlijk ITMG ESF-studieoverzicht |
|
||||||
|
|
||||||
|
Migratie naar Odoo eLearning is gepland maar niet launch-blocking.
|
||||||
181
docs/DEPLOYMENT.md
Normal file
181
docs/DEPLOYMENT.md
Normal file
|
|
@ -0,0 +1,181 @@
|
||||||
|
# Deployment Runbook — Atlas Academy
|
||||||
|
|
||||||
|
## Infrastructuur
|
||||||
|
|
||||||
|
| Service | Host | Pad |
|
||||||
|
|---------|------|-----|
|
||||||
|
| Caddy (TLS + proxy) | atlas-01 (`178.105.85.200`) | `/etc/caddy/Caddyfile` |
|
||||||
|
| Static marketing | atlas-01 | `/var/www/atlasacademy.nl/` |
|
||||||
|
| Odoo eLearning | atlas-01 Docker | container `atlas-odoo`, DB `atlas` |
|
||||||
|
| Lead relay | atlas-01 systemd | `atlas-academy-relay`, port `7793` |
|
||||||
|
| Tailnet IP | atlas-01 tailscale | `100.93.16.81` |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 1. Statische pagina deployen
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Één pagina pushen
|
||||||
|
scp pricing.html atlas-01:/var/www/atlasacademy.nl/pricing.html
|
||||||
|
curl -so /dev/null -w '%{http_code}' https://atlasacademy.nl/pricing.html
|
||||||
|
# verwacht: 200
|
||||||
|
|
||||||
|
# Meerdere pagina's tegelijk
|
||||||
|
scp *.html atlas-01:/var/www/atlasacademy.nl/
|
||||||
|
```
|
||||||
|
|
||||||
|
Geen Caddy reload nodig — Caddy serveert files direct.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 2. Cursus toevoegen aan Odoo
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# 1. Script schrijven op lokale machine (zie docs/COURSES.md voor formaat)
|
||||||
|
# 2. Uploaden naar atlas-01
|
||||||
|
scp build_cursus.py atlas-01:/tmp/
|
||||||
|
|
||||||
|
# 3. Uitvoeren in Odoo ORM shell
|
||||||
|
ssh atlas-01 "docker exec -i atlas-odoo odoo shell -d atlas --no-http < /tmp/build_cursus.py"
|
||||||
|
|
||||||
|
# Verwachte output:
|
||||||
|
# Cursus aangemaakt: /slides/mijn-cursus-10
|
||||||
|
```
|
||||||
|
|
||||||
|
**Let op:** altijd `env.cr.commit()` aan het einde van het script, anders worden geen wijzigingen opgeslagen.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 3. Caddy configuratie wijzigen
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# 1. Huidige config backuppen
|
||||||
|
ssh atlas-01 "cp /etc/caddy/Caddyfile /etc/caddy/Caddyfile.bak.$(date +%s)"
|
||||||
|
|
||||||
|
# 2. Bewerken
|
||||||
|
ssh atlas-01 "nano /etc/caddy/Caddyfile"
|
||||||
|
|
||||||
|
# 3. Valideren vóór reload
|
||||||
|
ssh atlas-01 "caddy validate --config /etc/caddy/Caddyfile"
|
||||||
|
|
||||||
|
# 4. Herladen (zero-downtime)
|
||||||
|
ssh atlas-01 "caddy reload --config /etc/caddy/Caddyfile"
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 4. Lead relay
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Status
|
||||||
|
ssh atlas-01 "systemctl status atlas-academy-relay"
|
||||||
|
|
||||||
|
# Logs
|
||||||
|
ssh atlas-01 "journalctl -u atlas-academy-relay -n 50 --no-pager"
|
||||||
|
|
||||||
|
# Herstarten (na config-wijziging)
|
||||||
|
ssh atlas-01 "systemctl restart atlas-academy-relay"
|
||||||
|
|
||||||
|
# Secrets bijwerken
|
||||||
|
ssh atlas-01 "nano /etc/atlas/academy-relay.env"
|
||||||
|
ssh atlas-01 "systemctl restart atlas-academy-relay"
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 5. Odoo herstarten
|
||||||
|
|
||||||
|
Na wijzigingen die ORM-cache moeten legen (website aanmaken, config params):
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ssh atlas-01 "docker restart atlas-odoo"
|
||||||
|
# wacht ~30s
|
||||||
|
curl -so /dev/null -w '%{http_code}' https://atlasacademy.nl/slides
|
||||||
|
# verwacht: 200
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 6. Odoo ORM shell — veelgebruikte één-regels
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Lijst alle cursussen
|
||||||
|
ssh atlas-01 "docker exec -i atlas-odoo odoo shell -d atlas --no-http" <<'EOF'
|
||||||
|
for c in env['slide.channel'].sudo().search([]): print(c.id, c.name, c.website_id.id)
|
||||||
|
EOF
|
||||||
|
|
||||||
|
# Controleer website 3
|
||||||
|
ssh atlas-01 "docker exec -i atlas-odoo odoo shell -d atlas --no-http" <<'EOF'
|
||||||
|
w = env['website'].sudo().browse(3)
|
||||||
|
print(w.name, w.domain, w.auth_signup_uninvited)
|
||||||
|
EOF
|
||||||
|
|
||||||
|
# Signup status per website
|
||||||
|
ssh atlas-01 "docker exec -i atlas-odoo odoo shell -d atlas --no-http" <<'EOF'
|
||||||
|
for w in env['website'].sudo().search([]): print(w.id, w.name, w.auth_signup_uninvited)
|
||||||
|
EOF
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 7. Assets / cache legen
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Browser-cache bypass: open in incognito
|
||||||
|
# Odoo assets regenereren (na theme-wijziging)
|
||||||
|
ssh atlas-01 "docker exec -i atlas-odoo odoo shell -d atlas --no-http" <<'EOF'
|
||||||
|
env['ir.attachment'].sudo().search([
|
||||||
|
('url', 'like', '/web/assets/'),
|
||||||
|
('store_fname', '!=', False)
|
||||||
|
]).unlink()
|
||||||
|
env.cr.commit()
|
||||||
|
print('Assets cleared')
|
||||||
|
EOF
|
||||||
|
ssh atlas-01 "docker restart atlas-odoo"
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 8. IndexNow pingen na content-wijziging
|
||||||
|
|
||||||
|
```bash
|
||||||
|
KEY="atlascorporation-indexnow-2025"
|
||||||
|
curl -X POST "https://api.indexnow.org/indexnow" \
|
||||||
|
-H "Content-Type: application/json" \
|
||||||
|
-d "{\"host\":\"atlasacademy.nl\",\"key\":\"$KEY\",\"urlList\":[\"https://atlasacademy.nl/\",\"https://atlasacademy.nl/slides\"]}"
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 9. Rollback procedure
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Static pagina rollback (bak-bestanden aanwezig)
|
||||||
|
ssh atlas-01 "ls /var/www/atlasacademy.nl/*.bak* | tail -5"
|
||||||
|
ssh atlas-01 "cp /var/www/atlasacademy.nl/pricing.html.bak.nav /var/www/atlasacademy.nl/pricing.html"
|
||||||
|
|
||||||
|
# Caddy rollback
|
||||||
|
ssh atlas-01 "cp /etc/caddy/Caddyfile.bak.<timestamp> /etc/caddy/Caddyfile && caddy reload --config /etc/caddy/Caddyfile"
|
||||||
|
|
||||||
|
# Odoo cursus verwijderen
|
||||||
|
# Verwijder via Odoo backend UI (tailnet: http://100.93.16.81:8069/web)
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 10. Monitoring
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# HTTPS check
|
||||||
|
curl -so /dev/null -w '%{http_code}' https://atlasacademy.nl/
|
||||||
|
curl -so /dev/null -w '%{http_code}' https://atlasacademy.nl/slides
|
||||||
|
|
||||||
|
# Relay check
|
||||||
|
curl -s -X POST https://atlasacademy.nl/academy-lead \
|
||||||
|
-H "Content-Type: application/json" \
|
||||||
|
-d '{"name":"Test","email":"test@test.nl","interest":"test","source":"deploy-check"}'
|
||||||
|
# verwacht: {"ok": true, ...}
|
||||||
|
|
||||||
|
# Odoo health
|
||||||
|
curl -so /dev/null -w '%{http_code}' http://100.93.16.81:8069/web/health
|
||||||
|
```
|
||||||
160
docs/ODOO.md
Normal file
160
docs/ODOO.md
Normal file
|
|
@ -0,0 +1,160 @@
|
||||||
|
# Odoo eLearning Setup — Atlas Academy
|
||||||
|
|
||||||
|
## Installatie
|
||||||
|
|
||||||
|
`website_slides` is geïnstalleerd als onderdeel van Odoo 19 Community op atlas-01.
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Verificatie
|
||||||
|
ssh atlas-01 "docker exec atlas-odoo odoo --list-db 2>/dev/null"
|
||||||
|
# DB: atlas
|
||||||
|
|
||||||
|
# Module status
|
||||||
|
ssh atlas-01 "docker exec -i atlas-odoo odoo shell -d atlas --no-http" <<'EOF'
|
||||||
|
m = env['ir.module.module'].sudo().search([('name','=','website_slides')])
|
||||||
|
print(m.name, m.state) # verwacht: website_slides installed
|
||||||
|
EOF
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Multi-website configuratie
|
||||||
|
|
||||||
|
Atlas Academy draait op **website 3** (apart van de Atlas Corporation-website op website 1).
|
||||||
|
|
||||||
|
| | Website 1 | Website 3 |
|
||||||
|
|--|-----------|-----------|
|
||||||
|
| Naam | Atlas Corporation | Atlas Academy |
|
||||||
|
| Domein | *(default)* | `https://atlasacademy.nl` |
|
||||||
|
| Signup | `b2b` (gesloten) | `b2c` (open) |
|
||||||
|
| Taal | NL | NL |
|
||||||
|
| Logo | Atlas Corp | Atlas Academy icon |
|
||||||
|
|
||||||
|
### Kritische gotcha's
|
||||||
|
|
||||||
|
**1. Caching van website-routing**
|
||||||
|
`_get_current_website_id` is ORM-gecached. Na aanmaken/wijzigen van een website:
|
||||||
|
```bash
|
||||||
|
ssh atlas-01 "docker restart atlas-odoo"
|
||||||
|
```
|
||||||
|
|
||||||
|
**2. X-Forwarded-Host verplicht**
|
||||||
|
Caddy moet `X-Forwarded-Host {host}` doorgeven, anders serveert Odoo altijd website 1:
|
||||||
|
```caddyfile
|
||||||
|
reverse_proxy 100.93.16.81:8069 {
|
||||||
|
header_up Host {host}
|
||||||
|
header_up X-Forwarded-Host {host}
|
||||||
|
header_up X-Forwarded-Proto https
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
**3. `proxy_mode = True`**
|
||||||
|
Controleer `/opt/atlas-odoo/config/odoo.conf`:
|
||||||
|
```ini
|
||||||
|
proxy_mode = True
|
||||||
|
```
|
||||||
|
|
||||||
|
**4. Signup is per-website, niet globaal**
|
||||||
|
De globale `auth_signup.allow_uninvited` parameter wordt **genegeerd** als `website` module actief is. Gebruik altijd:
|
||||||
|
```python
|
||||||
|
env['website'].sudo().browse(3).write({'auth_signup_uninvited': 'b2c'})
|
||||||
|
env.cr.commit()
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Website 3 aanmaken (referentie)
|
||||||
|
|
||||||
|
```python
|
||||||
|
env = env # Odoo shell
|
||||||
|
|
||||||
|
w3 = env['website'].sudo().create({
|
||||||
|
'name': 'Atlas Academy',
|
||||||
|
'domain': 'https://atlasacademy.nl',
|
||||||
|
'company_id': env.company.id,
|
||||||
|
'language_ids': [(4, env.ref('base.lang_nl').id)],
|
||||||
|
'default_lang_id': env.ref('base.lang_nl').id,
|
||||||
|
'auth_signup_uninvited': 'b2c',
|
||||||
|
})
|
||||||
|
# Stel logo in
|
||||||
|
import base64, requests
|
||||||
|
logo_data = requests.get('https://atlasacademy.nl/atlas-icon.png').content
|
||||||
|
w3.write({'logo': base64.b64encode(logo_data).decode()})
|
||||||
|
env.cr.commit()
|
||||||
|
print(f"Website aangemaakt: ID={w3.id}")
|
||||||
|
# Vervolgens: docker restart atlas-odoo
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Cursus website-toewijzing
|
||||||
|
|
||||||
|
Alle cursussen (`slide.channel`) moeten `website_id=3` hebben:
|
||||||
|
|
||||||
|
```python
|
||||||
|
channels = env['slide.channel'].sudo().search([])
|
||||||
|
for c in channels:
|
||||||
|
if not c.website_id or c.website_id.id != 3:
|
||||||
|
c.sudo().write({'website_id': 3})
|
||||||
|
env.cr.commit()
|
||||||
|
print(f"{len(channels)} cursussen toegewezen aan website 3")
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Email base-URL
|
||||||
|
|
||||||
|
Odoo gebruikt `website.get_base_url()` voor links in e-mails (wachtwoord reset etc.).
|
||||||
|
Dankzij multi-website:
|
||||||
|
- Website 3 → `get_base_url()` = `https://atlasacademy.nl` ✅
|
||||||
|
- Website 1 → `get_base_url()` = corp-domein ✅
|
||||||
|
|
||||||
|
De globale `web.base.url` parameter wordt **niet** gewijzigd (zou corp-emails breken).
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Odoo backend bereikbaarheid
|
||||||
|
|
||||||
|
| Route | Bereikbaar? | Via |
|
||||||
|
|-------|-------------|-----|
|
||||||
|
| `atlasacademy.nl/slides` | ✅ Publiek | Caddy proxy |
|
||||||
|
| `atlasacademy.nl/web/login` | ✅ Publiek | Caddy proxy |
|
||||||
|
| `atlasacademy.nl/web` (backend) | ❌ Niet geproxied | — |
|
||||||
|
| `http://100.93.16.81:8069` | ✅ Tailnet only | Direct |
|
||||||
|
| `odoo.atlascorporation.nl` | ✅ SSO only | Authentik + Caddy |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Veelgebruikte ORM-commando's
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Shell openen
|
||||||
|
ssh atlas-01 "docker exec -i atlas-odoo odoo shell -d atlas --no-http"
|
||||||
|
|
||||||
|
# Alle cursussen tonen
|
||||||
|
for c in env['slide.channel'].sudo().search([]): print(c.id, c.name, c.website_slug)
|
||||||
|
|
||||||
|
# Cursuspagina URL genereren
|
||||||
|
c = env['slide.channel'].sudo().browse(2)
|
||||||
|
print(f"https://atlasacademy.nl/slides/{c.website_slug}")
|
||||||
|
|
||||||
|
# Lessen van een cursus tonen
|
||||||
|
slides = env['slide.slide'].sudo().search([('channel_id','=',2),('is_category','=',False)])
|
||||||
|
for s in slides: print(s.sequence, s.name, len(s.question_ids), 'vragen')
|
||||||
|
|
||||||
|
# Website-instellingen inspecteren
|
||||||
|
w = env['website'].sudo().browse(3)
|
||||||
|
print(w.name, w.domain, w.auth_signup_uninvited, w.get_base_url())
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Bekende issues & oplossingen
|
||||||
|
|
||||||
|
| Issue | Oorzaak | Oplossing |
|
||||||
|
|-------|---------|-----------|
|
||||||
|
| `/web/signup` → 404 | `auth_signup_uninvited` niet op `b2c` | ORM shell: `w.write({'auth_signup_uninvited':'b2c'})` |
|
||||||
|
| Courses tonen op corp-website | `website_id=None` op channels | Script: set alle channels op `website_id=3` |
|
||||||
|
| Wachtwoord-reset e-mail heeft wrong URL | `web.base.url` verkeerd OF website 3 geen domein | Controleer `w3.domain` en `w3.get_base_url()` |
|
||||||
|
| Odoo toont corp-logo op academy-domein | Website-cache niet geleegd | `docker restart atlas-odoo` |
|
||||||
|
| `/slides` geeft 502 | Odoo container down | `docker start atlas-odoo && docker logs atlas-odoo` |
|
||||||
108
docs/SECURITY.md
Normal file
108
docs/SECURITY.md
Normal file
|
|
@ -0,0 +1,108 @@
|
||||||
|
# Security Model — Atlas Academy
|
||||||
|
|
||||||
|
## Dreigingsmodel
|
||||||
|
|
||||||
|
| Dreiging | Maatregel | Status |
|
||||||
|
|----------|-----------|--------|
|
||||||
|
| Hardcoded secrets in source | Env-bestanden (`/etc/atlas/*.env`, root 600) | ✅ Opgelost |
|
||||||
|
| Zwakke wachtwoord-hashing | bcrypt via `academy_auth_v2.py` (nu retired; Odoo native auth) | ✅ Opgelost |
|
||||||
|
| PII in publieke admin-panel | `academy_admin.py` verwijderd uit docroot | ✅ Opgelost |
|
||||||
|
| Odoo backend publiek bereikbaar | `/web` niet geproxied via academy-domein | ✅ Opgelost |
|
||||||
|
| Open signup op corp-website | `website 1.auth_signup_uninvited = 'b2b'` | ✅ Opgelost |
|
||||||
|
| Clickjacking | `X-Frame-Options: DENY` via Caddy | ✅ Actief |
|
||||||
|
| MIME-sniffing | `X-Content-Type-Options: nosniff` | ✅ Actief |
|
||||||
|
| HTTPS downgrade | `Strict-Transport-Security: max-age=31536000` | ✅ Actief |
|
||||||
|
| ESF-tracker indexeerbaar | `X-Robots-Tag: noindex, nofollow` + `robots.txt` | ✅ Actief |
|
||||||
|
| Stale SMTP app-wachtwoord | Handmatige rotatie vereist (Google Account UI) | ⚠️ Openstaand |
|
||||||
|
| XML-RPC relay-wachtwoord | In env, maar waarde mogelijk stale | ⚠️ Controleren |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Secrets locaties
|
||||||
|
|
||||||
|
Alle secrets zijn **buiten source** gehouden. Alleen locaties zijn gedocumenteerd.
|
||||||
|
|
||||||
|
| Bestand | Inhoud | Rechten |
|
||||||
|
|---------|--------|---------|
|
||||||
|
| `/etc/atlas/academy-relay.env` | `ODOO_RELAY_LOGIN`, `ODOO_RELAY_PASS`, `ACADEMY_ADMIN_PASS`, `LEAD_SMTP_PASS` | `root:root 600` |
|
||||||
|
| `/etc/atlas/academy-auth.env` | `AA_SECRET` (retired Flask JWT secret) | `root:root 600` |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Toegangsarchitectuur
|
||||||
|
|
||||||
|
```
|
||||||
|
Internet
|
||||||
|
│
|
||||||
|
▼
|
||||||
|
atlasacademy.nl (Caddy)
|
||||||
|
│
|
||||||
|
├── /slides, /web/login, /web/signup → Odoo (public eLearning)
|
||||||
|
│
|
||||||
|
├── /academy-lead → odoo_relay.py (localhost only)
|
||||||
|
│
|
||||||
|
├── /var/www/atlasacademy.nl/* → Static files
|
||||||
|
│
|
||||||
|
└── /web (NIET geproxied) → ❌ Geblokkeerd voor publiek
|
||||||
|
(Odoo backend enkel via tailnet)
|
||||||
|
|
||||||
|
odoo.atlascorporation.nl (Caddy)
|
||||||
|
│
|
||||||
|
└── Authentik forward_auth → Alleen via SSO bereikbaar
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Odoo signup-beveiliging
|
||||||
|
|
||||||
|
```
|
||||||
|
Website 1 (Atlas Corporation) → auth_signup_uninvited = 'b2b' → GESLOTEN
|
||||||
|
Website 3 (Atlas Academy) → auth_signup_uninvited = 'b2c' → OPEN (gewenst)
|
||||||
|
```
|
||||||
|
|
||||||
|
Verificatie:
|
||||||
|
```bash
|
||||||
|
ssh atlas-01 "docker exec -i atlas-odoo odoo shell -d atlas --no-http" <<'EOF'
|
||||||
|
for w in env['website'].sudo().search([]):
|
||||||
|
print(f"Website {w.id} ({w.name}): signup={w.auth_signup_uninvited}")
|
||||||
|
EOF
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Headers (Caddy)
|
||||||
|
|
||||||
|
```caddyfile
|
||||||
|
header {
|
||||||
|
X-Frame-Options DENY
|
||||||
|
X-Content-Type-Options nosniff
|
||||||
|
Referrer-Policy strict-origin-when-cross-origin
|
||||||
|
Strict-Transport-Security max-age=31536000
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Secrets roteren
|
||||||
|
|
||||||
|
### SMTP app-wachtwoord (`LEAD_SMTP_PASS`)
|
||||||
|
1. Ga naar [myaccount.google.com/apppasswords](https://myaccount.google.com/apppasswords)
|
||||||
|
2. Verwijder het oude wachtwoord, maak een nieuw aan
|
||||||
|
3. Update op atlas-01: `sudo nano /etc/atlas/academy-relay.env`
|
||||||
|
4. Herstart: `sudo systemctl restart atlas-academy-relay`
|
||||||
|
|
||||||
|
### Odoo relay-wachtwoord (`ODOO_RELAY_PASS`)
|
||||||
|
1. Log in op Odoo backend (tailnet)
|
||||||
|
2. Wijzig wachtwoord van de relay-gebruiker
|
||||||
|
3. Update `/etc/atlas/academy-relay.env`
|
||||||
|
4. `sudo systemctl restart atlas-academy-relay`
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Wat NIET te doen
|
||||||
|
|
||||||
|
- ❌ Nooit secrets committen in git
|
||||||
|
- ❌ Nooit `/web` proxien via het publieke academy-domein
|
||||||
|
- ❌ Nooit wachtwoorden automatisch roteren (operator handelt dit af)
|
||||||
|
- ❌ Nooit `--send` gebruiken in `atlas_client_email.py` zonder goedkeuring
|
||||||
|
- ❌ Nooit studentgegevens publiceren (geen nep-reviews, nep-studentaantallen)
|
||||||
197
docs/USERFLOW.md
Normal file
197
docs/USERFLOW.md
Normal file
|
|
@ -0,0 +1,197 @@
|
||||||
|
# User Flows & Use Cases — Atlas Academy
|
||||||
|
|
||||||
|
## Use Cases
|
||||||
|
|
||||||
|
### UC-1: Nieuwe bezoeker ontdekt het platform
|
||||||
|
**Actor:** Ondernemer (potentiële student)
|
||||||
|
**Doel:** Cursusaanbod verkennen zonder account
|
||||||
|
|
||||||
|
```
|
||||||
|
Bezoeker
|
||||||
|
│
|
||||||
|
├── [Vorige actie: Google → atlasacademy.nl]
|
||||||
|
│
|
||||||
|
▼
|
||||||
|
atlasacademy.nl (index.html)
|
||||||
|
│ "Nu live · 9 cursussen"
|
||||||
|
│
|
||||||
|
├── klikt "Bekijk de cursussen →"
|
||||||
|
│ ↓
|
||||||
|
│ /slides (Odoo cursuscatalogus)
|
||||||
|
│ │
|
||||||
|
│ ├── ziet 9 cursuskaarten met kleur-covers
|
||||||
|
│ ├── klikt cursus → /slides/sales-vanaf-nul-2
|
||||||
|
│ │ │
|
||||||
|
│ │ ├── leest eerste lessen (preview)
|
||||||
|
│ │ └── beantwoordt quizvragen
|
||||||
|
│ │
|
||||||
|
│ └── klikt pricing.html voor kosten
|
||||||
|
│
|
||||||
|
└── verlaat → lead? [nee] → geen actie
|
||||||
|
```
|
||||||
|
|
||||||
|
**Succes:** bezoeker heeft minimaal 1 les gelezen + 1 quizvraag beantwoord.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
### UC-2: Registratie & account aanmaken
|
||||||
|
**Actor:** Geïnteresseerde bezoeker
|
||||||
|
**Doel:** Gratis account aanmaken voor voortgangsopslag
|
||||||
|
|
||||||
|
```
|
||||||
|
Bezoeker
|
||||||
|
│
|
||||||
|
├── klikt "Gratis account aanmaken" op homepage
|
||||||
|
│ ↓
|
||||||
|
│ /register → 302 → /web/signup?redirect=/slides
|
||||||
|
│ │
|
||||||
|
│ ├── Odoo signup-formulier (website 3)
|
||||||
|
│ │ Naam · E-mail · Wachtwoord
|
||||||
|
│ │
|
||||||
|
│ ├── submit → Odoo maakt res.users aan
|
||||||
|
│ │
|
||||||
|
│ ├── bevestigingsmail via atlasacademy.nl
|
||||||
|
│ │ (base_url = website 3 domein)
|
||||||
|
│ │
|
||||||
|
│ └── redirect → /slides (ingelogd)
|
||||||
|
│
|
||||||
|
└── succes: voortgang wordt opgeslagen per cursus
|
||||||
|
```
|
||||||
|
|
||||||
|
**Foutpaden:**
|
||||||
|
- E-mail al in gebruik → Odoo: "account bestaat al"
|
||||||
|
- Wachtwoord te kort → Odoo validatie
|
||||||
|
- Website 1 (corp) = b2b → signup geblokkeerd (correct)
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
### UC-3: Inloggen (terugkerende student)
|
||||||
|
**Actor:** Bestaande gebruiker
|
||||||
|
**Doel:** Doorgaan met cursus
|
||||||
|
|
||||||
|
```
|
||||||
|
Terugkerende student
|
||||||
|
│
|
||||||
|
├── klikt "Inloggen" in nav van marketing-pagina
|
||||||
|
│ ↓
|
||||||
|
│ /login → 302 → /web/login?redirect=/slides
|
||||||
|
│ │
|
||||||
|
│ ├── Odoo login-formulier
|
||||||
|
│ │
|
||||||
|
│ ├── submit → sessie cookie gezet
|
||||||
|
│ │
|
||||||
|
│ └── redirect → /slides
|
||||||
|
│ └── cursus hervatten
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
### UC-4: Cursus volgen (hoofdflow)
|
||||||
|
**Actor:** Ingelogde student
|
||||||
|
**Doel:** Les lezen + kennischeck doen
|
||||||
|
|
||||||
|
```
|
||||||
|
[/slides] Cursuscatalogus
|
||||||
|
│
|
||||||
|
└── klikt cursus → /slides/<slug>
|
||||||
|
│
|
||||||
|
├── Cursuspagina: inhoudsopgave
|
||||||
|
│
|
||||||
|
└── klikt les → /slides/<slug>/<les-slug>
|
||||||
|
│
|
||||||
|
├── Theorie (HTML, ~300-500 woorden)
|
||||||
|
│
|
||||||
|
└── Kennischeck (3 MC-vragen per les)
|
||||||
|
│
|
||||||
|
├── kiest antwoord → feedback (uitleg)
|
||||||
|
├── alle correct → "Les voltooid" ✓
|
||||||
|
└── voortgang opgeslagen in Odoo
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
### UC-5: Lead insturen (interesse formulier)
|
||||||
|
**Actor:** Bezoeker op marketingpagina
|
||||||
|
**Doel:** Interesse kenbaar maken (coaching / waitlist)
|
||||||
|
|
||||||
|
```
|
||||||
|
Bezoeker
|
||||||
|
│
|
||||||
|
└── vult formulier in op coaching.html of index.html
|
||||||
|
│
|
||||||
|
POST /academy-lead (JSON: {name, email, interest, source})
|
||||||
|
│
|
||||||
|
└── odoo_relay.py (atlas-01:7793)
|
||||||
|
│
|
||||||
|
├── maakt crm.lead aan in Odoo
|
||||||
|
│
|
||||||
|
├── stuurt notificatie e-mail (SMTP fallback)
|
||||||
|
│
|
||||||
|
└── HTTP 200 → "Bedankt" bericht op pagina
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Swimlane diagram — Volledige gebruikerscyclus
|
||||||
|
|
||||||
|
```
|
||||||
|
STUDENT CADDY (atlasacademy.nl) ODOO (eLearning) CRM (Odoo)
|
||||||
|
│ │ │ │
|
||||||
|
│── GET / ───────────────>│ │ │
|
||||||
|
│<── 200 index.html ───────│ │ │
|
||||||
|
│ │ │ │
|
||||||
|
│── GET /slides ──────────>│── proxy ──────────────>│ │
|
||||||
|
│<── 200 cursuscatalogus ──│<──────────────────────│ │
|
||||||
|
│ │ │ │
|
||||||
|
│── GET /slides/<slug> ───>│── proxy ──────────────>│ │
|
||||||
|
│<── 200 cursuspagina ─────│<──────────────────────│ │
|
||||||
|
│ │ │ │
|
||||||
|
│── GET /register ────────>│── 302 /web/signup ────>│ │
|
||||||
|
│── POST signup ──────────>│── proxy ──────────────>│── nieuwe user ─────│
|
||||||
|
│<── 302 /slides ──────────│<──────────────────────│ │
|
||||||
|
│ │ │ │
|
||||||
|
│── POST /academy-lead ───>│── proxy ──────────────>│ >│─ crm.lead
|
||||||
|
│<── 200 {ok:true} ────────│ │ │
|
||||||
|
│ │ │ │
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Flowchart — Auth beslissingsboom
|
||||||
|
|
||||||
|
```
|
||||||
|
Bezoeker wil cursus volgen
|
||||||
|
│
|
||||||
|
▼
|
||||||
|
Heeft de user een sessie?
|
||||||
|
┌─────────┴─────────┐
|
||||||
|
Ja Nee
|
||||||
|
│ │
|
||||||
|
▼ ▼
|
||||||
|
/slides (direct) /web/login
|
||||||
|
│
|
||||||
|
┌────────┴────────┐
|
||||||
|
│ │
|
||||||
|
Heeft account? Geen account
|
||||||
|
│ │
|
||||||
|
▼ ▼
|
||||||
|
Inloggen /web/signup
|
||||||
|
│ │
|
||||||
|
└────────┬────────┘
|
||||||
|
│
|
||||||
|
▼
|
||||||
|
/slides (ingelogd)
|
||||||
|
│
|
||||||
|
Voortgang opgeslagen ✓
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Actoren & rechten
|
||||||
|
|
||||||
|
| Actor | Toegang | Auth |
|
||||||
|
|-------|---------|------|
|
||||||
|
| Anonieme bezoeker | Marketingpagina's, preview cursussen | Geen |
|
||||||
|
| Geregistreerde student | Volledige cursussen, voortgang | Odoo session |
|
||||||
|
| Operator (Chaib) | Odoo backend, alle content, CRM | Tailnet + Authentik SSO |
|
||||||
|
| Lead relay service | CRM leads aanmaken | XML-RPC app-user |
|
||||||
1191
static/bisl.html
Normal file
1191
static/bisl.html
Normal file
File diff suppressed because it is too large
Load diff
997
static/coaching.html
Normal file
997
static/coaching.html
Normal file
|
|
@ -0,0 +1,997 @@
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html lang="nl">
|
||||||
|
<head>
|
||||||
|
<meta charset="UTF-8">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
|
<meta name="description" content="Coaching met Chaib Aarab — Founder Atlas Corporation. Leer van iemand die het nu bouwt: AtlasPOS, automatisering, klanten, servers, sales.">
|
||||||
|
<meta name="robots" content="index, follow">
|
||||||
|
<title>Coaching — Atlas Academy</title>
|
||||||
|
<style>
|
||||||
|
:root {
|
||||||
|
--bg: #080C18;
|
||||||
|
--card: #0B1220;
|
||||||
|
--card2: #0d1f3c;
|
||||||
|
--border: rgba(55,65,81,.5);
|
||||||
|
--arc: #3B82F6;
|
||||||
|
--purple: #8B5CF6;
|
||||||
|
--cyan: #06B6D4;
|
||||||
|
--ok: #22C55E;
|
||||||
|
--warn: #F59E0B;
|
||||||
|
--pink: #EC4899;
|
||||||
|
--txt: #E2E8F0;
|
||||||
|
--muted: #6B7280;
|
||||||
|
--font: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
|
||||||
|
--radius: 10px;
|
||||||
|
--radius-lg: 16px;
|
||||||
|
--radius-xl: 24px;
|
||||||
|
}
|
||||||
|
|
||||||
|
*, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; }
|
||||||
|
html { scroll-behavior: smooth; }
|
||||||
|
body {
|
||||||
|
background: var(--bg);
|
||||||
|
color: var(--txt);
|
||||||
|
font-family: var(--font);
|
||||||
|
font-size: 16px;
|
||||||
|
line-height: 1.6;
|
||||||
|
-webkit-font-smoothing: antialiased;
|
||||||
|
overflow-x: hidden;
|
||||||
|
}
|
||||||
|
a { color: var(--arc); text-decoration: none; }
|
||||||
|
a:hover { color: #93C5FD; }
|
||||||
|
img { max-width: 100%; display: block; }
|
||||||
|
|
||||||
|
.container {
|
||||||
|
width: 100%;
|
||||||
|
max-width: 1140px;
|
||||||
|
margin: 0 auto;
|
||||||
|
padding: 0 24px;
|
||||||
|
}
|
||||||
|
.gradient-text {
|
||||||
|
background: linear-gradient(135deg, #fff 0%, #93c5fd 50%, #c4b5fd 100%);
|
||||||
|
-webkit-background-clip: text;
|
||||||
|
-webkit-text-fill-color: transparent;
|
||||||
|
background-clip: text;
|
||||||
|
}
|
||||||
|
.badge {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 6px;
|
||||||
|
padding: 4px 14px;
|
||||||
|
border-radius: 999px;
|
||||||
|
font-size: 12px;
|
||||||
|
font-weight: 700;
|
||||||
|
letter-spacing: .06em;
|
||||||
|
text-transform: uppercase;
|
||||||
|
}
|
||||||
|
.badge--blue { background: rgba(59,130,246,.15); color: var(--arc); border: 1px solid rgba(59,130,246,.3); }
|
||||||
|
.badge--amber { background: rgba(245,158,11,.12); color: var(--warn); border: 1px solid rgba(245,158,11,.25); }
|
||||||
|
.badge--green { background: rgba(34,197,94,.12); color: var(--ok); border: 1px solid rgba(34,197,94,.25); }
|
||||||
|
|
||||||
|
.btn {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 8px;
|
||||||
|
padding: 13px 28px;
|
||||||
|
border-radius: var(--radius);
|
||||||
|
font-size: 15px;
|
||||||
|
font-weight: 700;
|
||||||
|
cursor: pointer;
|
||||||
|
transition: all .2s;
|
||||||
|
border: none;
|
||||||
|
text-decoration: none;
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
.btn-primary {
|
||||||
|
background: linear-gradient(135deg, var(--arc), var(--purple));
|
||||||
|
color: #fff;
|
||||||
|
box-shadow: 0 0 30px rgba(59,130,246,.35);
|
||||||
|
}
|
||||||
|
.btn-primary:hover { box-shadow: 0 0 50px rgba(59,130,246,.6); transform: translateY(-2px); color: #fff; }
|
||||||
|
.btn-glass {
|
||||||
|
background: rgba(255,255,255,.07);
|
||||||
|
color: var(--txt);
|
||||||
|
border: 1px solid rgba(255,255,255,.12);
|
||||||
|
backdrop-filter: blur(12px);
|
||||||
|
}
|
||||||
|
.btn-glass:hover { background: rgba(255,255,255,.12); transform: translateY(-2px); color: var(--txt); }
|
||||||
|
.btn-outline {
|
||||||
|
background: transparent;
|
||||||
|
color: var(--arc);
|
||||||
|
border: 1.5px solid rgba(59,130,246,.4);
|
||||||
|
}
|
||||||
|
.btn-outline:hover { border-color: var(--arc); box-shadow: 0 0 20px rgba(59,130,246,.2); transform: translateY(-2px); }
|
||||||
|
.btn-sm { padding: 9px 18px; font-size: 14px; }
|
||||||
|
|
||||||
|
section { padding: 88px 0; }
|
||||||
|
.section-label {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 6px;
|
||||||
|
font-size: 11px;
|
||||||
|
font-weight: 700;
|
||||||
|
letter-spacing: .12em;
|
||||||
|
text-transform: uppercase;
|
||||||
|
color: var(--arc);
|
||||||
|
margin-bottom: 12px;
|
||||||
|
}
|
||||||
|
.section-label::before { content: ''; display: block; width: 16px; height: 1px; background: var(--arc); }
|
||||||
|
.section-title {
|
||||||
|
font-size: clamp(26px, 4vw, 40px);
|
||||||
|
font-weight: 800;
|
||||||
|
line-height: 1.15;
|
||||||
|
margin-bottom: 14px;
|
||||||
|
letter-spacing: -.02em;
|
||||||
|
}
|
||||||
|
.section-sub { color: var(--muted); font-size: 17px; max-width: 560px; line-height: 1.7; }
|
||||||
|
|
||||||
|
/* ---- REVEAL ---- */
|
||||||
|
.reveal { opacity: 0; transform: translateY(28px); transition: opacity .6s ease, transform .6s ease; }
|
||||||
|
.reveal.visible { opacity: 1; transform: translateY(0); }
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
NAV
|
||||||
|
============================ */
|
||||||
|
nav {
|
||||||
|
position: sticky;
|
||||||
|
top: 0;
|
||||||
|
z-index: 200;
|
||||||
|
background: rgba(8,12,24,.88);
|
||||||
|
backdrop-filter: blur(20px);
|
||||||
|
-webkit-backdrop-filter: blur(20px);
|
||||||
|
border-bottom: 1px solid rgba(59,130,246,.08);
|
||||||
|
}
|
||||||
|
.nav-inner {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: space-between;
|
||||||
|
height: 64px;
|
||||||
|
gap: 16px;
|
||||||
|
}
|
||||||
|
.nav-logo {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 10px;
|
||||||
|
font-size: 16px;
|
||||||
|
font-weight: 800;
|
||||||
|
color: var(--txt);
|
||||||
|
white-space: nowrap;
|
||||||
|
flex-shrink: 0;
|
||||||
|
letter-spacing: -.01em;
|
||||||
|
text-decoration: none;
|
||||||
|
}
|
||||||
|
.nav-logo:hover { color: #93C5FD; }
|
||||||
|
.nav-logo img { height: 28px; width: auto; filter: brightness(0) invert(1); }
|
||||||
|
.nav-links {
|
||||||
|
display: flex;
|
||||||
|
list-style: none;
|
||||||
|
gap: 4px;
|
||||||
|
margin: 0;
|
||||||
|
padding: 0;
|
||||||
|
}
|
||||||
|
.nav-links a {
|
||||||
|
padding: 6px 14px;
|
||||||
|
border-radius: 8px;
|
||||||
|
font-size: 14px;
|
||||||
|
font-weight: 500;
|
||||||
|
color: #CBD5E1;
|
||||||
|
transition: all .15s;
|
||||||
|
text-decoration: none;
|
||||||
|
}
|
||||||
|
.nav-links a:hover, .nav-links a.active { color: var(--txt); background: rgba(255,255,255,.07); }
|
||||||
|
.nav-cta-area { display: flex; align-items: center; gap: 10px; }
|
||||||
|
.nav-hamburger { display: none; background: none; border: none; color: var(--txt); font-size: 22px; cursor: pointer; padding: 4px 8px; }
|
||||||
|
|
||||||
|
#mobile-menu {
|
||||||
|
display: none;
|
||||||
|
position: fixed;
|
||||||
|
inset: 0;
|
||||||
|
background: rgba(8,12,24,.97);
|
||||||
|
z-index: 999;
|
||||||
|
padding: 80px 24px 40px;
|
||||||
|
flex-direction: column;
|
||||||
|
gap: 0;
|
||||||
|
}
|
||||||
|
#mobile-menu.open { display: flex; }
|
||||||
|
#mobile-menu a {
|
||||||
|
display: block;
|
||||||
|
padding: 18px 0;
|
||||||
|
font-size: 22px;
|
||||||
|
font-weight: 700;
|
||||||
|
color: #fff;
|
||||||
|
border-bottom: 1px solid rgba(255,255,255,.08);
|
||||||
|
text-decoration: none;
|
||||||
|
}
|
||||||
|
#mobile-menu .mob-close {
|
||||||
|
position: absolute;
|
||||||
|
top: 20px;
|
||||||
|
right: 20px;
|
||||||
|
background: none;
|
||||||
|
border: none;
|
||||||
|
color: #fff;
|
||||||
|
font-size: 28px;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (max-width: 768px) {
|
||||||
|
.nav-links { display: none; }
|
||||||
|
.nav-cta-area .btn { display: none; }
|
||||||
|
.nav-hamburger { display: block; }
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
HERO — SPLIT
|
||||||
|
============================ */
|
||||||
|
#hero {
|
||||||
|
padding: 0;
|
||||||
|
min-height: 92vh;
|
||||||
|
display: flex;
|
||||||
|
align-items: stretch;
|
||||||
|
}
|
||||||
|
.hero-split {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1fr 1fr;
|
||||||
|
min-height: 92vh;
|
||||||
|
}
|
||||||
|
.hero-photo-side {
|
||||||
|
position: relative;
|
||||||
|
overflow: hidden;
|
||||||
|
border-right: 3px solid var(--arc);
|
||||||
|
}
|
||||||
|
.hero-photo-side img {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
object-fit: cover;
|
||||||
|
object-position: right center;
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
.hero-photo-overlay {
|
||||||
|
position: absolute;
|
||||||
|
inset: 0;
|
||||||
|
background: linear-gradient(to right, transparent 60%, rgba(8,12,24,.3));
|
||||||
|
pointer-events: none;
|
||||||
|
}
|
||||||
|
.hero-text-side {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
justify-content: center;
|
||||||
|
padding: 64px 56px;
|
||||||
|
gap: 0;
|
||||||
|
}
|
||||||
|
.hero-badge-wrap { margin-bottom: 20px; }
|
||||||
|
.hero-h1 {
|
||||||
|
font-size: clamp(32px, 4.5vw, 56px);
|
||||||
|
font-weight: 900;
|
||||||
|
line-height: 1.08;
|
||||||
|
letter-spacing: -.03em;
|
||||||
|
margin-bottom: 20px;
|
||||||
|
}
|
||||||
|
.hero-sub {
|
||||||
|
font-size: 18px;
|
||||||
|
color: #94A3B8;
|
||||||
|
line-height: 1.7;
|
||||||
|
max-width: 460px;
|
||||||
|
margin-bottom: 36px;
|
||||||
|
}
|
||||||
|
.hero-cta-row {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
gap: 14px;
|
||||||
|
margin-bottom: 28px;
|
||||||
|
}
|
||||||
|
.hero-contact-line {
|
||||||
|
font-size: 13px;
|
||||||
|
color: var(--muted);
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
gap: 6px 14px;
|
||||||
|
}
|
||||||
|
.hero-contact-line a { color: var(--muted); transition: color .15s; }
|
||||||
|
.hero-contact-line a:hover { color: var(--arc); }
|
||||||
|
.hero-dot { color: rgba(255,255,255,.25); }
|
||||||
|
|
||||||
|
@media (max-width: 900px) {
|
||||||
|
.hero-split { grid-template-columns: 1fr; }
|
||||||
|
.hero-photo-side { height: 55vw; min-height: 300px; border-right: none; border-bottom: 3px solid var(--arc); }
|
||||||
|
.hero-text-side { padding: 40px 24px; }
|
||||||
|
#hero { min-height: auto; }
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
CHAIB PROFIEL CARD
|
||||||
|
============================ */
|
||||||
|
#profiel { padding: 80px 0; }
|
||||||
|
.profiel-card {
|
||||||
|
position: relative;
|
||||||
|
border-radius: var(--radius-xl);
|
||||||
|
overflow: hidden;
|
||||||
|
border: 1px solid var(--border);
|
||||||
|
}
|
||||||
|
.profiel-bg {
|
||||||
|
position: absolute;
|
||||||
|
inset: 0;
|
||||||
|
background: url('assets/chaib-banner.png') center/cover no-repeat;
|
||||||
|
filter: brightness(.18) saturate(.7);
|
||||||
|
}
|
||||||
|
.profiel-bg-overlay {
|
||||||
|
position: absolute;
|
||||||
|
inset: 0;
|
||||||
|
background: linear-gradient(135deg, rgba(8,12,24,.85) 50%, rgba(59,130,246,.08) 100%);
|
||||||
|
}
|
||||||
|
.profiel-inner {
|
||||||
|
position: relative;
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1fr 1fr;
|
||||||
|
gap: 48px;
|
||||||
|
padding: 56px;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
.profiel-left {}
|
||||||
|
.profiel-avatar-row {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 20px;
|
||||||
|
margin-bottom: 24px;
|
||||||
|
}
|
||||||
|
.profiel-avatar {
|
||||||
|
width: 80px;
|
||||||
|
height: 80px;
|
||||||
|
border-radius: 50%;
|
||||||
|
object-fit: cover;
|
||||||
|
object-position: right top;
|
||||||
|
border: 3px solid var(--arc);
|
||||||
|
flex-shrink: 0;
|
||||||
|
}
|
||||||
|
.profiel-name { font-size: 24px; font-weight: 800; color: var(--txt); }
|
||||||
|
.profiel-title { font-size: 14px; color: var(--muted); margin-top: 2px; }
|
||||||
|
.profiel-tags {
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
gap: 8px;
|
||||||
|
margin-bottom: 22px;
|
||||||
|
}
|
||||||
|
.profiel-tag {
|
||||||
|
background: rgba(59,130,246,.1);
|
||||||
|
border: 1px solid rgba(59,130,246,.2);
|
||||||
|
color: #93C5FD;
|
||||||
|
font-size: 12px;
|
||||||
|
font-weight: 600;
|
||||||
|
padding: 4px 10px;
|
||||||
|
border-radius: 6px;
|
||||||
|
}
|
||||||
|
.profiel-bio { color: #CBD5E1; font-size: 15px; line-height: 1.75; margin-bottom: 24px; }
|
||||||
|
.profiel-right {}
|
||||||
|
.profiel-stats-grid {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1fr 1fr;
|
||||||
|
gap: 16px;
|
||||||
|
margin-bottom: 28px;
|
||||||
|
}
|
||||||
|
.profiel-stat-card {
|
||||||
|
background: rgba(11,18,32,.7);
|
||||||
|
backdrop-filter: blur(20px);
|
||||||
|
border: 1px solid var(--border);
|
||||||
|
border-radius: var(--radius);
|
||||||
|
padding: 18px 20px;
|
||||||
|
}
|
||||||
|
.profiel-stat-num { font-size: 22px; font-weight: 800; color: var(--arc); }
|
||||||
|
.profiel-stat-lbl { font-size: 12px; color: var(--muted); margin-top: 2px; }
|
||||||
|
.profiel-quote {
|
||||||
|
background: rgba(11,18,32,.7);
|
||||||
|
backdrop-filter: blur(20px);
|
||||||
|
border-left: 3px solid var(--arc);
|
||||||
|
border-radius: 0 var(--radius) var(--radius) 0;
|
||||||
|
padding: 20px 22px;
|
||||||
|
color: #CBD5E1;
|
||||||
|
font-size: 15px;
|
||||||
|
font-style: italic;
|
||||||
|
line-height: 1.7;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (max-width: 900px) {
|
||||||
|
.profiel-inner { grid-template-columns: 1fr; padding: 32px 24px; gap: 28px; }
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
WAT IK AANBIED
|
||||||
|
============================ */
|
||||||
|
#aanbod { padding: 80px 0; background: linear-gradient(180deg, rgba(59,130,246,.04) 0%, transparent 100%); }
|
||||||
|
.aanbod-header { text-align: center; margin-bottom: 56px; }
|
||||||
|
.aanbod-header .section-label { justify-content: center; }
|
||||||
|
.aanbod-header .section-label::before { display: none; }
|
||||||
|
.aanbod-grid {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: repeat(3, 1fr);
|
||||||
|
gap: 24px;
|
||||||
|
}
|
||||||
|
.aanbod-card {
|
||||||
|
background: rgba(11,18,32,.7);
|
||||||
|
backdrop-filter: blur(20px);
|
||||||
|
border: 1px solid var(--border);
|
||||||
|
border-radius: var(--radius-lg);
|
||||||
|
padding: 36px 30px;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
gap: 0;
|
||||||
|
position: relative;
|
||||||
|
overflow: hidden;
|
||||||
|
transition: transform .2s, box-shadow .2s;
|
||||||
|
}
|
||||||
|
.aanbod-card:hover { transform: translateY(-4px); box-shadow: 0 20px 60px rgba(0,0,0,.4); }
|
||||||
|
.aanbod-card::before {
|
||||||
|
content: '';
|
||||||
|
position: absolute;
|
||||||
|
top: 0; left: 0; right: 0;
|
||||||
|
height: 2px;
|
||||||
|
}
|
||||||
|
.aanbod-card--starter::before { background: linear-gradient(90deg, var(--arc), var(--cyan)); }
|
||||||
|
.aanbod-card--pro::before { background: linear-gradient(90deg, var(--warn), #f97316); }
|
||||||
|
.aanbod-card--custom::before { background: linear-gradient(90deg, var(--purple), var(--pink)); }
|
||||||
|
.aanbod-icon { font-size: 36px; margin-bottom: 16px; }
|
||||||
|
.aanbod-tier { font-size: 11px; font-weight: 700; letter-spacing: .1em; text-transform: uppercase; color: var(--muted); margin-bottom: 4px; }
|
||||||
|
.aanbod-name { font-size: 20px; font-weight: 800; color: var(--txt); margin-bottom: 4px; }
|
||||||
|
.aanbod-meta { font-size: 13px; color: var(--muted); margin-bottom: 20px; }
|
||||||
|
.aanbod-price { font-size: 32px; font-weight: 900; color: var(--txt); margin-bottom: 4px; }
|
||||||
|
.aanbod-price span { font-size: 14px; font-weight: 500; color: var(--muted); }
|
||||||
|
.aanbod-divider { border: none; border-top: 1px solid var(--border); margin: 20px 0; }
|
||||||
|
.aanbod-features { list-style: none; display: flex; flex-direction: column; gap: 10px; margin-bottom: 28px; flex: 1; }
|
||||||
|
.aanbod-features li { display: flex; gap: 10px; font-size: 14px; color: #CBD5E1; }
|
||||||
|
.aanbod-check--blue { color: var(--arc); font-weight: 700; flex-shrink: 0; }
|
||||||
|
.aanbod-check--amber { color: var(--warn); font-weight: 700; flex-shrink: 0; }
|
||||||
|
.aanbod-check--purple { color: var(--purple); font-weight: 700; flex-shrink: 0; }
|
||||||
|
|
||||||
|
@media (max-width: 900px) {
|
||||||
|
.aanbod-grid { grid-template-columns: 1fr; }
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
VOOR WIE
|
||||||
|
============================ */
|
||||||
|
#voor-wie { padding: 80px 0; }
|
||||||
|
.voor-wie-header { margin-bottom: 48px; }
|
||||||
|
.persona-grid {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: repeat(3, 1fr);
|
||||||
|
gap: 20px;
|
||||||
|
}
|
||||||
|
.persona-card {
|
||||||
|
background: rgba(11,18,32,.7);
|
||||||
|
backdrop-filter: blur(20px);
|
||||||
|
border: 1px solid var(--border);
|
||||||
|
border-radius: var(--radius-lg);
|
||||||
|
padding: 32px 28px;
|
||||||
|
transition: transform .2s, border-color .2s;
|
||||||
|
}
|
||||||
|
.persona-card:hover { transform: translateY(-3px); border-color: rgba(59,130,246,.3); }
|
||||||
|
.persona-icon { font-size: 40px; margin-bottom: 16px; }
|
||||||
|
.persona-title { font-size: 17px; font-weight: 700; color: var(--txt); margin-bottom: 10px; line-height: 1.3; }
|
||||||
|
.persona-desc { font-size: 14px; color: var(--muted); line-height: 1.65; margin-bottom: 16px; }
|
||||||
|
.persona-tag {
|
||||||
|
display: inline-block;
|
||||||
|
background: rgba(59,130,246,.1);
|
||||||
|
border: 1px solid rgba(59,130,246,.2);
|
||||||
|
color: #93C5FD;
|
||||||
|
font-size: 11px;
|
||||||
|
font-weight: 600;
|
||||||
|
padding: 3px 9px;
|
||||||
|
border-radius: 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (max-width: 900px) {
|
||||||
|
.persona-grid { grid-template-columns: 1fr; }
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
AANMELDEN FORM
|
||||||
|
============================ */
|
||||||
|
#aanmelden { padding: 80px 0; background: linear-gradient(180deg, transparent, rgba(59,130,246,.04)); }
|
||||||
|
.form-card {
|
||||||
|
background: rgba(11,18,32,.7);
|
||||||
|
backdrop-filter: blur(20px);
|
||||||
|
border: 1px solid var(--border);
|
||||||
|
border-radius: var(--radius-xl);
|
||||||
|
padding: 56px;
|
||||||
|
max-width: 700px;
|
||||||
|
margin: 0 auto;
|
||||||
|
}
|
||||||
|
.form-header { text-align: center; margin-bottom: 40px; }
|
||||||
|
.form-group { margin-bottom: 20px; }
|
||||||
|
.form-label {
|
||||||
|
display: block;
|
||||||
|
font-size: 13px;
|
||||||
|
font-weight: 600;
|
||||||
|
color: #94A3B8;
|
||||||
|
margin-bottom: 6px;
|
||||||
|
letter-spacing: .02em;
|
||||||
|
}
|
||||||
|
.form-input {
|
||||||
|
width: 100%;
|
||||||
|
background: rgba(255,255,255,.05);
|
||||||
|
border: 1px solid rgba(255,255,255,.12);
|
||||||
|
border-radius: var(--radius);
|
||||||
|
padding: 12px 16px;
|
||||||
|
color: var(--txt);
|
||||||
|
font-size: 15px;
|
||||||
|
font-family: var(--font);
|
||||||
|
transition: border-color .15s, box-shadow .15s;
|
||||||
|
outline: none;
|
||||||
|
}
|
||||||
|
.form-input:focus { border-color: var(--arc); box-shadow: 0 0 0 3px rgba(59,130,246,.15); }
|
||||||
|
.form-input::placeholder { color: var(--muted); }
|
||||||
|
select.form-input option { background: #0B1220; }
|
||||||
|
textarea.form-input { resize: vertical; min-height: 110px; }
|
||||||
|
.form-row { display: grid; grid-template-columns: 1fr 1fr; gap: 16px; }
|
||||||
|
.form-submit { width: 100%; padding: 14px; font-size: 16px; margin-top: 8px; justify-content: center; }
|
||||||
|
.form-note { text-align: center; font-size: 13px; color: var(--muted); margin-top: 14px; }
|
||||||
|
.form-success {
|
||||||
|
display: none;
|
||||||
|
text-align: center;
|
||||||
|
padding: 24px;
|
||||||
|
background: rgba(34,197,94,.08);
|
||||||
|
border: 1px solid rgba(34,197,94,.2);
|
||||||
|
border-radius: var(--radius);
|
||||||
|
color: var(--ok);
|
||||||
|
font-weight: 600;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media (max-width: 600px) {
|
||||||
|
.form-card { padding: 32px 20px; }
|
||||||
|
.form-row { grid-template-columns: 1fr; }
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
FOOTER
|
||||||
|
============================ */
|
||||||
|
footer {
|
||||||
|
background: rgba(4,8,16,.9);
|
||||||
|
border-top: 1px solid rgba(255,255,255,.05);
|
||||||
|
padding: 60px 0 32px;
|
||||||
|
}
|
||||||
|
.footer-inner {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 2fr 1fr 1fr 1fr;
|
||||||
|
gap: 40px;
|
||||||
|
margin-bottom: 40px;
|
||||||
|
}
|
||||||
|
.footer-brand p { color: var(--muted); font-size: 14px; line-height: 1.7; margin-top: 10px; max-width: 260px; }
|
||||||
|
.footer-logo { font-size: 16px; font-weight: 800; color: var(--txt); }
|
||||||
|
.footer-col-title { font-size: 12px; font-weight: 700; letter-spacing: .08em; text-transform: uppercase; color: #64748B; margin-bottom: 12px; }
|
||||||
|
.footer-links { list-style: none; display: flex; flex-direction: column; gap: 8px; }
|
||||||
|
.footer-links a { font-size: 14px; color: var(--muted); transition: color .15s; }
|
||||||
|
.footer-links a:hover { color: var(--arc); }
|
||||||
|
.footer-bottom { border-top: 1px solid rgba(255,255,255,.05); padding-top: 24px; display: flex; justify-content: space-between; align-items: center; flex-wrap: wrap; gap: 8px; }
|
||||||
|
.footer-copy { font-size: 13px; color: #475569; }
|
||||||
|
.footer-copy a { color: #64748B; }
|
||||||
|
.footer-copy a:hover { color: var(--arc); }
|
||||||
|
|
||||||
|
@media (max-width: 900px) {
|
||||||
|
.footer-inner { grid-template-columns: 1fr 1fr; }
|
||||||
|
}
|
||||||
|
@media (max-width: 600px) {
|
||||||
|
.footer-inner { grid-template-columns: 1fr; }
|
||||||
|
.footer-bottom { flex-direction: column; text-align: center; }
|
||||||
|
}
|
||||||
|
.lang-toggle{background:transparent;border:1px solid rgba(59,130,246,.5);color:#9CA3AF;padding:5px 12px;border-radius:20px;cursor:pointer;font-size:12px;font-weight:600;transition:all .2s;margin-right:8px;}</style>
|
||||||
|
|
||||||
|
<!-- GA4 -->
|
||||||
|
<script async src="https://www.googletagmanager.com/gtag/js?id=G-JBWZWZMKBC"></script>
|
||||||
|
<script>window.dataLayer=window.dataLayer||[];function gtag(){dataLayer.push(arguments);}gtag('js',new Date());gtag('config','G-JBWZWZMKBC');</script>
|
||||||
|
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
|
||||||
|
<!-- ============================
|
||||||
|
NAV
|
||||||
|
============================ -->
|
||||||
|
<nav id="nav" role="navigation" aria-label="Hoofdnavigatie">
|
||||||
|
<div class="container">
|
||||||
|
<div class="nav-inner">
|
||||||
|
<a href="index.html" class="nav-logo">
|
||||||
|
<img src="assets/logo.png" alt="Atlas Academy logo" width="28" height="28">
|
||||||
|
<span>Atlas Academy</span>
|
||||||
|
</a>
|
||||||
|
<ul class="nav-links">
|
||||||
|
<li><a href="cursussen.html">Cursussen</a></li>
|
||||||
|
<li><a href="leerpad.html">Leerpad</a></li>
|
||||||
|
<li><a href="coaching.html" class="active">Coaching</a></li>
|
||||||
|
<li><a href="pricing.html">Prijzen</a></li>
|
||||||
|
<li><a href="shop.html">Shop</a></li>
|
||||||
|
<li><a href="over.html">Over</a></li>
|
||||||
|
<li><a href="/web/login?redirect=%2Fslides">Inloggen</a></li>
|
||||||
|
</ul>
|
||||||
|
<div class="nav-cta-area">
|
||||||
|
<a href="mailto:info@atlascorporation.nl?subject=Atlas+Academy" class="btn btn-primary btn-sm">Start gratis →</a>
|
||||||
|
<button class="nav-hamburger" onclick="toggleMobileMenu()" aria-label="Menu">☰</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</nav>
|
||||||
|
|
||||||
|
<div id="mobile-menu">
|
||||||
|
<button class="mob-close" onclick="toggleMobileMenu()">×</button>
|
||||||
|
<a href="cursussen.html" onclick="toggleMobileMenu()">Cursussen</a>
|
||||||
|
<a href="leerpad.html" onclick="toggleMobileMenu()">Leerpad</a>
|
||||||
|
<a href="coaching.html" onclick="toggleMobileMenu()">Coaching</a>
|
||||||
|
<a href="pricing.html" onclick="toggleMobileMenu()">Prijzen</a>
|
||||||
|
<a href="shop.html" onclick="toggleMobileMenu()">Shop</a>
|
||||||
|
<a href="over.html" onclick="toggleMobileMenu()">Over</a>
|
||||||
|
<a href="/web/login?redirect=%2Fslides" onclick="toggleMobileMenu()">Inloggen</a>
|
||||||
|
<a href="mailto:info@atlascorporation.nl?subject=Atlas+Academy" class="btn btn-primary" style="margin-top:32px;justify-content:center;">Start gratis →</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- ============================
|
||||||
|
HERO — SPLIT LAYOUT
|
||||||
|
============================ -->
|
||||||
|
<section id="hero" aria-label="Coaching hero">
|
||||||
|
<div class="hero-split">
|
||||||
|
|
||||||
|
<!-- LEFT: Photo -->
|
||||||
|
<div class="hero-photo-side">
|
||||||
|
<img src="assets/chaib.png" alt="Chaib Aarab — Founder Atlas Corporation, ERP POS CRM">
|
||||||
|
<div class="hero-photo-overlay"></div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- RIGHT: Text -->
|
||||||
|
<div class="hero-text-side">
|
||||||
|
<div class="hero-badge-wrap">
|
||||||
|
<span class="badge badge--blue">Coaching</span>
|
||||||
|
</div>
|
||||||
|
<h1 class="hero-h1">
|
||||||
|
<span class="gradient-text">Leer van iemand<br>die het nu doet</span>
|
||||||
|
</h1>
|
||||||
|
<p class="hero-sub">
|
||||||
|
Geen consultant met een theorie. Een ondernemer die dagelijks bouwt — AtlasPOS, automatisering, klanten, servers, sales. Coaching die aansluit op jouw realiteit.
|
||||||
|
</p>
|
||||||
|
<div class="hero-cta-row">
|
||||||
|
<a href="mailto:info@atlascorporation.nl?subject=Coaching aanvraag" class="btn btn-primary">Vraag een sessie aan →</a>
|
||||||
|
<a href="#aanbod" class="btn btn-glass">Zie de formats</a>
|
||||||
|
</div>
|
||||||
|
<div class="hero-contact-line">
|
||||||
|
<span>Tilburg</span>
|
||||||
|
<span class="hero-dot">·</span>
|
||||||
|
<span>Chaib Aarab</span>
|
||||||
|
<span class="hero-dot">·</span>
|
||||||
|
<a href="mailto:chaib@atlascorporation.nl">chaib@atlascorporation.nl</a>
|
||||||
|
<span class="hero-dot">·</span>
|
||||||
|
<a href="tel:+31639259220">06 39 25 92 20</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<!-- ============================
|
||||||
|
CHAIB PROFIEL CARD
|
||||||
|
============================ -->
|
||||||
|
<section id="profiel">
|
||||||
|
<div class="container">
|
||||||
|
<div class="profiel-card reveal">
|
||||||
|
<div class="profiel-bg"></div>
|
||||||
|
<div class="profiel-bg-overlay"></div>
|
||||||
|
<div class="profiel-inner">
|
||||||
|
|
||||||
|
<div class="profiel-left">
|
||||||
|
<span class="section-label">De coach</span>
|
||||||
|
<div class="profiel-avatar-row">
|
||||||
|
<img src="assets/chaib.png" alt="Chaib Aarab" class="profiel-avatar">
|
||||||
|
<div>
|
||||||
|
<div class="profiel-name">Bouchaib (Chaib) Aarab</div>
|
||||||
|
<div class="profiel-title">Founder & IT Consultant — Atlas Corporation · Tilburg</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="profiel-tags">
|
||||||
|
<span class="profiel-tag">8+ jaar ervaring</span>
|
||||||
|
<span class="profiel-tag">Efficy CRM consultant</span>
|
||||||
|
<span class="profiel-tag">AtlasPOS founder</span>
|
||||||
|
<span class="profiel-tag">Avans Hogeschool</span>
|
||||||
|
<span class="profiel-tag">Scalda ICT</span>
|
||||||
|
<span class="profiel-tag">Tilburg</span>
|
||||||
|
<span class="profiel-tag">AI & automatisering</span>
|
||||||
|
<span class="profiel-tag">Odoo / ERP</span>
|
||||||
|
</div>
|
||||||
|
<p class="profiel-bio">
|
||||||
|
Ik begon als applicatieontwikkelaar, deed CRM-implementaties bij Efficy in ’s-Hertogenbosch, en bouw nu vanuit Tilburg <strong>AtlasPOS</strong> — een live SaaS-product. Naast het product draai ik de volledige IT-stack zelf: servers, automatisering, klantgesprekken, sales. Wat ik je leer, pas ik deze week nog toe.
|
||||||
|
</p>
|
||||||
|
<a href="https://www.linkedin.com/in/baarab/" target="_blank" rel="noopener" class="btn btn-outline">
|
||||||
|
Volg op LinkedIn →
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="profiel-right">
|
||||||
|
<div class="profiel-stats-grid">
|
||||||
|
<div class="profiel-stat-card">
|
||||||
|
<div class="profiel-stat-num">2023</div>
|
||||||
|
<div class="profiel-stat-lbl">Atlas Corporation opgericht</div>
|
||||||
|
</div>
|
||||||
|
<div class="profiel-stat-card">
|
||||||
|
<div class="profiel-stat-num">SaaS</div>
|
||||||
|
<div class="profiel-stat-lbl">AtlasPOS live in productie</div>
|
||||||
|
</div>
|
||||||
|
<div class="profiel-stat-card">
|
||||||
|
<div class="profiel-stat-num">CRM</div>
|
||||||
|
<div class="profiel-stat-lbl">Efficy implementaties</div>
|
||||||
|
</div>
|
||||||
|
<div class="profiel-stat-card">
|
||||||
|
<div class="profiel-stat-num">8+</div>
|
||||||
|
<div class="profiel-stat-lbl">Jaar IT-ervaring</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="profiel-quote">
|
||||||
|
“De meeste ondernemers leren van mensen die het beschrijven. Ik leer je van iemand die het bouwt — live, met echte klanten, echte servers en echte fouten.”
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<!-- ============================
|
||||||
|
WAT IK AANBIED
|
||||||
|
============================ -->
|
||||||
|
<section id="aanbod">
|
||||||
|
<div class="container">
|
||||||
|
<div class="aanbod-header reveal">
|
||||||
|
<span class="section-label">Formats</span>
|
||||||
|
<h2 class="section-title">Wat ik aanbied</h2>
|
||||||
|
<p class="section-sub">Drie formats, één coach. Kies wat past bij jouw fase.</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="aanbod-grid">
|
||||||
|
|
||||||
|
<!-- Groepscoaching -->
|
||||||
|
<div class="aanbod-card aanbod-card--starter reveal">
|
||||||
|
<div class="aanbod-icon">👥</div>
|
||||||
|
<div class="aanbod-tier">Starter</div>
|
||||||
|
<div class="aanbod-name">Groepscoaching</div>
|
||||||
|
<div class="aanbod-meta">1× per maand · Zoom · 45 minuten</div>
|
||||||
|
<div class="aanbod-price">€20 <span>/ maand</span></div>
|
||||||
|
<hr class="aanbod-divider">
|
||||||
|
<ul class="aanbod-features">
|
||||||
|
<li><span class="aanbod-check--blue">✓</span> Vaste agenda: 10 min theorie → 25 min cases → 10 min Q&A</li>
|
||||||
|
<li><span class="aanbod-check--blue">✓</span> Opname beschikbaar na de sessie</li>
|
||||||
|
<li><span class="aanbod-check--blue">✓</span> Toegang tot Academy community</li>
|
||||||
|
<li><span class="aanbod-check--blue">✓</span> Leer van ondernemers in vergelijkbare fase</li>
|
||||||
|
</ul>
|
||||||
|
<a href="mailto:info@atlascorporation.nl?subject=Groepscoaching aanmelding" class="btn btn-primary">Word Starter-lid →</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- 1-op-1 -->
|
||||||
|
<div class="aanbod-card aanbod-card--pro reveal">
|
||||||
|
<div class="aanbod-icon">🎯</div>
|
||||||
|
<div class="aanbod-tier">Pro</div>
|
||||||
|
<div class="aanbod-name">1-op-1 Sessie</div>
|
||||||
|
<div class="aanbod-meta">30 min · maandelijks · jouw situatie centraal</div>
|
||||||
|
<div class="aanbod-price">€49 <span>/ maand</span></div>
|
||||||
|
<hr class="aanbod-divider">
|
||||||
|
<ul class="aanbod-features">
|
||||||
|
<li><span class="aanbod-check--amber">✓</span> Intake formulier vooraf — coach volledig voorbereid</li>
|
||||||
|
<li><span class="aanbod-check--amber">✓</span> Persoonlijk leerplan op basis van jouw fase</li>
|
||||||
|
<li><span class="aanbod-check--amber">✓</span> Directe feedback op jouw project of probleem</li>
|
||||||
|
<li><span class="aanbod-check--amber">✓</span> Toegang tot Chaibs netwerk waar relevant</li>
|
||||||
|
</ul>
|
||||||
|
<a href="mailto:info@atlascorporation.nl?subject=1-op-1 Coaching aanmelding" class="btn btn-primary" style="background:linear-gradient(135deg,var(--warn),#f97316);box-shadow:0 0 30px rgba(245,158,11,.35);">Word Pro-lid →</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- Persoonlijk traject -->
|
||||||
|
<div class="aanbod-card aanbod-card--custom reveal">
|
||||||
|
<div class="aanbod-icon">🌟</div>
|
||||||
|
<div class="aanbod-tier">Pro — Custom</div>
|
||||||
|
<div class="aanbod-name">Persoonlijk traject</div>
|
||||||
|
<div class="aanbod-meta">Op maat · duur en intensiteit in overleg</div>
|
||||||
|
<div class="aanbod-price"><span style="font-size:15px;color:var(--txt);font-weight:700;">Op aanvraag</span></div>
|
||||||
|
<hr class="aanbod-divider">
|
||||||
|
<ul class="aanbod-features">
|
||||||
|
<li><span class="aanbod-check--purple">✓</span> Diepgaand intake gesprek om jouw situatie te begrijpen</li>
|
||||||
|
<li><span class="aanbod-check--purple">✓</span> Maatwerk sessies: wekelijks, bi-weekly of ad hoc</li>
|
||||||
|
<li><span class="aanbod-check--purple">✓</span> Inclusief praktijkopdrachten en review</li>
|
||||||
|
<li><span class="aanbod-check--purple">✓</span> Directe bereikbaarheid via WhatsApp/mail</li>
|
||||||
|
</ul>
|
||||||
|
<a href="mailto:info@atlascorporation.nl?subject=Persoonlijk traject aanvraag" class="btn btn-primary" style="background:linear-gradient(135deg,var(--purple),var(--pink));box-shadow:0 0 30px rgba(139,92,246,.35);">Vraag traject aan →</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<!-- ============================
|
||||||
|
VOOR WIE
|
||||||
|
============================ -->
|
||||||
|
<section id="voor-wie">
|
||||||
|
<div class="container">
|
||||||
|
<div class="voor-wie-header reveal">
|
||||||
|
<span class="section-label">Doelgroep</span>
|
||||||
|
<h2 class="section-title">Voor wie is dit?</h2>
|
||||||
|
<p class="section-sub">Coaching is niet voor iedereen. Dit zijn de drie profielen waar ik het meeste impact heb.</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="persona-grid">
|
||||||
|
|
||||||
|
<div class="persona-card reveal">
|
||||||
|
<div class="persona-icon">🚀</div>
|
||||||
|
<div class="persona-title">Startende ondernemer die wil leren hoe je een product lanceert</div>
|
||||||
|
<p class="persona-desc">
|
||||||
|
Je hebt een idee of early-stage product maar weet niet hoe je van nul naar betalende klanten gaat. Ik leer je de weg die ik zelf ben gegaan met AtlasPOS: validatie, pricing, eerste sales, technische opzet.
|
||||||
|
</p>
|
||||||
|
<span class="persona-tag">Product launchen</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="persona-card reveal">
|
||||||
|
<div class="persona-icon">⚙️</div>
|
||||||
|
<div class="persona-title">ZZP-er die IT-processen wil automatiseren</div>
|
||||||
|
<p class="persona-desc">
|
||||||
|
Je werkt solo maar verliest tijd aan repetitieve taken. Ik help je n8n, Odoo of andere tools inzetten zodat je meer kunt doen met minder manueel werk — zonder interne IT-afdeling.
|
||||||
|
</p>
|
||||||
|
<span class="persona-tag">AI & automatisering</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="persona-card reveal">
|
||||||
|
<div class="persona-icon">📈</div>
|
||||||
|
<div class="persona-title">MKB die CRM/ERP wil implementeren zonder dure consultants</div>
|
||||||
|
<p class="persona-desc">
|
||||||
|
Je bedrijf groeit maar de processen houden het tempo niet bij. Ik begeleid je bij het kiezen en inrichten van CRM of ERP — vanuit praktijkervaring bij Efficy en eigen Odoo-implementaties.
|
||||||
|
</p>
|
||||||
|
<span class="persona-tag">CRM / ERP</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<!-- ============================
|
||||||
|
AANMELDEN FORM
|
||||||
|
============================ -->
|
||||||
|
<section id="aanmelden">
|
||||||
|
<div class="container">
|
||||||
|
<div class="form-card reveal">
|
||||||
|
<div class="form-header">
|
||||||
|
<span class="section-label" style="justify-content:center;margin-bottom:12px;">
|
||||||
|
<span style="display:block;width:16px;height:1px;background:var(--arc);"></span>
|
||||||
|
Aanmelden
|
||||||
|
</span>
|
||||||
|
<h2 class="section-title">Vraag een sessie aan</h2>
|
||||||
|
<p class="section-sub" style="margin:0 auto;text-align:center;">
|
||||||
|
Vul je gegevens in en Chaib neemt binnen 24 uur contact op.
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div id="formSuccess" class="form-success">
|
||||||
|
✓ Aanmelding ontvangen. Je hoort binnen 24 uur van Chaib.
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<form id="coachingForm" onsubmit="submitLead(event)">
|
||||||
|
<div class="form-row">
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="form-label" for="fname">Naam *</label>
|
||||||
|
<input type="text" id="fname" name="naam" class="form-input" placeholder="Jouw naam" required>
|
||||||
|
</div>
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="form-label" for="femail">E-mail *</label>
|
||||||
|
<input type="email" id="femail" name="email" class="form-input" placeholder="jij@bedrijf.nl" required>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="form-row">
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="form-label" for="fphone">Telefoon</label>
|
||||||
|
<input type="tel" id="fphone" name="telefoon" class="form-input" placeholder="06 xx xx xx xx">
|
||||||
|
</div>
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="form-label" for="fformat">Format *</label>
|
||||||
|
<select id="fformat" name="format" class="form-input" required>
|
||||||
|
<option value="">Kies een format...</option>
|
||||||
|
<option value="groep">Groepscoaching — €20/mo (Starter)</option>
|
||||||
|
<option value="1op1">1-op-1 Sessie — €49/mo (Pro)</option>
|
||||||
|
<option value="traject">Persoonlijk traject (op aanvraag)</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="form-label" for="fvraag">Waar wil je mee geholpen worden? *</label>
|
||||||
|
<textarea id="fvraag" name="vraag" class="form-input" placeholder="Beschrijf kort je situatie, je bedrijf en waar je nu tegenaan loopt." required></textarea>
|
||||||
|
</div>
|
||||||
|
<button type="submit" class="btn btn-primary form-submit">Verstuur aanmelding →</button>
|
||||||
|
<p class="form-note">Geen spam. Enkel een persoonlijke reactie van Chaib binnen 24 uur.</p>
|
||||||
|
</form>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<!-- ============================
|
||||||
|
FOOTER
|
||||||
|
============================ -->
|
||||||
|
<footer>
|
||||||
|
<div class="container">
|
||||||
|
<div class="footer-inner">
|
||||||
|
<div class="footer-brand">
|
||||||
|
<span class="footer-logo">🎓 Atlas Academy</span>
|
||||||
|
<p>Praktische kennis voor ondernemers die bouwen. Onderdeel van Atlas Corporation.</p>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<div class="footer-col-title">Cursussen</div>
|
||||||
|
<ul class="footer-links">
|
||||||
|
<li><a href="cursussen.html">Alle cursussen</a></li>
|
||||||
|
<li><a href="bisl.html">BiSL Foundation</a></li>
|
||||||
|
<li><a href="leerpad.html">Leerpad</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<div class="footer-col-title">Platform</div>
|
||||||
|
<ul class="footer-links">
|
||||||
|
<li><a href="coaching.html">Coaching</a></li>
|
||||||
|
<li><a href="pricing.html">Prijzen</a></li>
|
||||||
|
<li><a href="shop.html">Shop</a></li>
|
||||||
|
<li><a href="over.html">Over</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<div class="footer-col-title">Contact</div>
|
||||||
|
<ul class="footer-links">
|
||||||
|
<li><a href="mailto:chaib@atlascorporation.nl">chaib@atlascorporation.nl</a></li>
|
||||||
|
<li><a href="tel:+31639259220">06 39 25 92 20</a></li>
|
||||||
|
<li><a href="https://www.linkedin.com/in/baarab/" target="_blank" rel="noopener">LinkedIn</a></li>
|
||||||
|
<li><a href="https://atlascorporation.nl" target="_blank" rel="noopener">atlascorporation.nl</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer-bottom">
|
||||||
|
<p class="footer-copy">© 2026 Atlas Academy · onderdeel van <a href="https://atlascorporation.nl" target="_blank" rel="noopener">Atlas Corporation</a></p>
|
||||||
|
<p class="footer-copy">KvK · BTW · <a href="mailto:info@atlascorporation.nl">info@atlascorporation.nl</a></p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</footer>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
function toggleMobileMenu() {
|
||||||
|
var m = document.getElementById('mobile-menu');
|
||||||
|
m.classList.toggle('open');
|
||||||
|
}
|
||||||
|
|
||||||
|
function submitLead(e) {
|
||||||
|
e.preventDefault();
|
||||||
|
var form = document.getElementById('coachingForm');
|
||||||
|
var data = new FormData(form);
|
||||||
|
var body = [];
|
||||||
|
data.forEach(function(v, k) { body.push(encodeURIComponent(k) + '=' + encodeURIComponent(v)); });
|
||||||
|
|
||||||
|
fetch('academy-lead', {
|
||||||
|
method: 'POST',
|
||||||
|
headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
|
||||||
|
body: body.join('&') + '&source=coaching'
|
||||||
|
}).then(function(r) {
|
||||||
|
form.style.display = 'none';
|
||||||
|
document.getElementById('formSuccess').style.display = 'block';
|
||||||
|
}).catch(function() {
|
||||||
|
// fallback: open mailto
|
||||||
|
var naam = data.get('naam') || '';
|
||||||
|
var email = data.get('email') || '';
|
||||||
|
var fmt = data.get('format') || '';
|
||||||
|
var vraag = data.get('vraag') || '';
|
||||||
|
window.location.href = 'mailto:info@atlascorporation.nl?subject=Coaching aanvraag - ' + encodeURIComponent(naam)
|
||||||
|
+ '&body=' + encodeURIComponent('Naam: ' + naam + '\nE-mail: ' + email + '\nFormat: ' + fmt + '\n\n' + vraag);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// Scroll reveal
|
||||||
|
(function() {
|
||||||
|
var els = document.querySelectorAll('.reveal');
|
||||||
|
var obs = new IntersectionObserver(function(entries) {
|
||||||
|
entries.forEach(function(e) {
|
||||||
|
if (e.isIntersecting) { e.target.classList.add('visible'); obs.unobserve(e.target); }
|
||||||
|
});
|
||||||
|
}, { threshold: 0.08 });
|
||||||
|
els.forEach(function(el, i) {
|
||||||
|
el.style.transitionDelay = (i * 0.04) + 's';
|
||||||
|
obs.observe(el);
|
||||||
|
});
|
||||||
|
})();
|
||||||
|
|
||||||
|
// Nav active scroll
|
||||||
|
window.addEventListener('scroll', function() {
|
||||||
|
var nav = document.getElementById('nav');
|
||||||
|
if (window.scrollY > 20) { nav.style.background = 'rgba(8,12,24,.95)'; }
|
||||||
|
else { nav.style.background = 'rgba(8,12,24,.88)'; }
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
<script>function toggleLang(){var isNL=document.documentElement.lang!=="en";var lang=isNL?"en":"nl";document.documentElement.lang=lang;document.getElementById("langBtn").textContent=isNL?"NL":"EN";document.querySelectorAll("[data-nl]").forEach(function(el){var v=el.getAttribute("data-"+lang);if(v)el.innerHTML=v;});localStorage.setItem("aa_lang",lang);}(function(){if(localStorage.getItem("aa_lang")==="en")toggleLang();})();</script></body>
|
||||||
|
</html>
|
||||||
201
static/esf.html
Normal file
201
static/esf.html
Normal file
File diff suppressed because one or more lines are too long
245
static/index.html
Normal file
245
static/index.html
Normal file
|
|
@ -0,0 +1,245 @@
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html lang="nl">
|
||||||
|
<head>
|
||||||
|
<meta charset="UTF-8">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
|
<meta name="theme-color" content="#080c18">
|
||||||
|
<meta name="description" content="Atlas Academy — binnenkort online. Praktijkkennis voor MKB-ondernemers. Laat je e-mail achter voor vroege toegang.">
|
||||||
|
<meta name="robots" content="index, follow">
|
||||||
|
<meta property="og:title" content="Atlas Academy — Online leerplatform">
|
||||||
|
<meta property="og:description" content="Praktijkkennis voor MKB-ondernemers. Schrijf je in voor de wachtlijst.">
|
||||||
|
<meta property="og:image" content="https://atlasacademy.nl/og-card.png">
|
||||||
|
<meta property="og:url" content="https://atlasacademy.nl">
|
||||||
|
<meta property="og:type" content="website">
|
||||||
|
<meta name="twitter:card" content="summary_large_image">
|
||||||
|
<title>Atlas Academy — Online leerplatform</title>
|
||||||
|
<link rel="icon" type="image/png" href="/atlas-icon.png">
|
||||||
|
<!-- GA4 -->
|
||||||
|
<!-- Google Tag (GT-MR2TH3RQ rollup G-2S7SWHG9TH) -->
|
||||||
|
<script async src="https://www.googletagmanager.com/gtag/js?id=GT-MR2TH3RQ"></script>
|
||||||
|
<script>window.dataLayer=window.dataLayer||[];function gtag(){dataLayer.push(arguments);}gtag("js",new Date());gtag("config","GT-MR2TH3RQ",{linker:{domains:["atlascorporation.nl","atlasagency.nl","atlaspos.nl","atlasworks.nl","www.atlasworks.nl"],accept_incoming:true}});gtag("config","G-JBWZWZMKBC");</script>
|
||||||
|
<style>
|
||||||
|
:root {
|
||||||
|
--bg: hsl(222,48%,8%);
|
||||||
|
--surface: hsl(223,42%,12%);
|
||||||
|
--border: rgba(78,160,255,.12);
|
||||||
|
--brand: #2E80FF;
|
||||||
|
--brand-glow: rgba(46,128,255,.35);
|
||||||
|
--gold: #D4A24C;
|
||||||
|
--gold-glow: rgba(212,162,76,.25);
|
||||||
|
--text: #eef2ff;
|
||||||
|
--text-2: #7a8aab;
|
||||||
|
--text-3: #4a5a7b;
|
||||||
|
--font: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
|
||||||
|
--radius: 12px;
|
||||||
|
--radius-lg: 20px;
|
||||||
|
}
|
||||||
|
*,*::before,*::after{box-sizing:border-box;margin:0;padding:0}
|
||||||
|
html{scroll-behavior:smooth}
|
||||||
|
body{
|
||||||
|
background:var(--bg);
|
||||||
|
color:var(--text);
|
||||||
|
font-family:var(--font);
|
||||||
|
font-size:16px;
|
||||||
|
line-height:1.6;
|
||||||
|
-webkit-font-smoothing:antialiased;
|
||||||
|
overflow-x:hidden;
|
||||||
|
min-height:100vh;
|
||||||
|
display:flex;
|
||||||
|
flex-direction:column;
|
||||||
|
align-items:center;
|
||||||
|
justify-content:center;
|
||||||
|
padding:40px 24px;
|
||||||
|
}
|
||||||
|
a{color:var(--brand);text-decoration:none;transition:color .2s}
|
||||||
|
a:hover{color:#6fb4ff}
|
||||||
|
|
||||||
|
/* Starfield canvas */
|
||||||
|
#stars{position:fixed;inset:0;z-index:0;pointer-events:none}
|
||||||
|
|
||||||
|
/* Main card */
|
||||||
|
.main{position:relative;z-index:1;max-width:480px;width:100%}
|
||||||
|
|
||||||
|
/* Icon ring */
|
||||||
|
.icon-wrap{display:flex;justify-content:center;margin-bottom:32px}
|
||||||
|
.icon-ring{position:relative;width:88px;height:88px}
|
||||||
|
.icon-ring svg{position:absolute;inset:0;animation:spin-slow 20s linear infinite}
|
||||||
|
.icon-ring svg:nth-child(2){animation-direction:reverse;animation-duration:14s}
|
||||||
|
.icon-ring img{position:absolute;inset:50%;transform:translate(-50%,-50%);width:48px;height:48px;z-index:1}
|
||||||
|
@keyframes spin-slow{to{transform:rotate(360deg)}}
|
||||||
|
|
||||||
|
/* Badge */
|
||||||
|
.badge{display:inline-flex;align-items:center;gap:6px;padding:5px 14px;background:rgba(46,128,255,.08);border:1px solid rgba(46,128,255,.2);border-radius:999px;font-size:11px;font-weight:700;color:var(--brand);letter-spacing:.07em;text-transform:uppercase;margin:0 auto 20px;width:fit-content}
|
||||||
|
.badge::before{content:'';width:5px;height:5px;background:var(--brand);border-radius:50%;animation:pulse 2s infinite}
|
||||||
|
@keyframes pulse{0%,100%{opacity:1;box-shadow:0 0 6px var(--brand)}50%{opacity:.3;box-shadow:0 0 2px var(--brand)}}
|
||||||
|
|
||||||
|
h1{font-size:clamp(36px,6vw,56px);font-weight:900;letter-spacing:-.03em;line-height:1.1;margin-bottom:8px;text-align:center}
|
||||||
|
.gradient{background:linear-gradient(135deg,#fff 0%,#93c5fd 40%,#D4A24C 100%);-webkit-background-clip:text;-webkit-text-fill-color:transparent;background-clip:text}
|
||||||
|
.sub{font-size:17px;color:var(--text-2);text-align:center;margin-bottom:44px;line-height:1.55}
|
||||||
|
|
||||||
|
/* Card */
|
||||||
|
.card{background:var(--surface);border:1px solid var(--border);border-radius:var(--radius-lg);padding:32px;backdrop-filter:blur(20px);-webkit-backdrop-filter:blur(20px)}
|
||||||
|
.card h2{font-size:18px;font-weight:700;margin-bottom:6px}
|
||||||
|
.card p{font-size:14px;color:var(--text-2);margin-bottom:24px}
|
||||||
|
.form-group{display:flex;flex-direction:column;gap:12px}
|
||||||
|
.form-group input{
|
||||||
|
background:rgba(255,255,255,.04);
|
||||||
|
border:1px solid rgba(78,160,255,.15);
|
||||||
|
border-radius:var(--radius);
|
||||||
|
padding:14px 16px;
|
||||||
|
color:var(--text);
|
||||||
|
font-size:15px;
|
||||||
|
outline:none;
|
||||||
|
transition:border-color .25s,box-shadow .25s;
|
||||||
|
font-family:var(--font);
|
||||||
|
width:100%
|
||||||
|
}
|
||||||
|
.form-group input:focus{border-color:var(--brand);box-shadow:0 0 0 3px var(--brand-glow)}
|
||||||
|
.form-group input::placeholder{color:var(--text-3)}
|
||||||
|
.btn{
|
||||||
|
display:inline-flex;align-items:center;justify-content:center;gap:8px;
|
||||||
|
padding:15px 28px;border-radius:var(--radius);font-size:15px;font-weight:700;
|
||||||
|
cursor:pointer;transition:all .25s;border:none;text-decoration:none;
|
||||||
|
width:100%;font-family:var(--font);letter-spacing:.01em
|
||||||
|
}
|
||||||
|
.btn-primary{
|
||||||
|
background:linear-gradient(135deg,var(--brand),#1a5dc7);
|
||||||
|
color:#fff;
|
||||||
|
box-shadow:0 0 28px var(--brand-glow);
|
||||||
|
}
|
||||||
|
.btn-primary:hover{transform:translateY(-2px);box-shadow:0 0 44px rgba(46,128,255,.5);color:#fff}
|
||||||
|
.btn-primary:disabled{opacity:.55;cursor:not-allowed;transform:none;box-shadow:none}
|
||||||
|
|
||||||
|
.success{display:none;color:#4ade80;font-size:14px;margin-top:16px;font-weight:600;text-align:center}
|
||||||
|
.success.visible{display:block}
|
||||||
|
|
||||||
|
/* Footer */
|
||||||
|
.footer{position:relative;z-index:1;display:flex;gap:20px;justify-content:center;flex-wrap:wrap;margin-top:28px}
|
||||||
|
.footer a{font-size:13px;color:var(--text-3);transition:color .2s}
|
||||||
|
.footer a:hover{color:var(--text)}
|
||||||
|
.footer .sep{color:var(--text-3);opacity:.4}
|
||||||
|
.footer-copy{margin-top:12px;font-size:11px;color:var(--text-3);text-align:center}
|
||||||
|
|
||||||
|
@media(max-width:480px){
|
||||||
|
.card{padding:24px}
|
||||||
|
body{padding:32px 16px}
|
||||||
|
}
|
||||||
|
</style>
|
||||||
|
<style>#planet-bg::after{content:"";position:absolute;inset:0;background:radial-gradient(ellipse at center,transparent 40%,hsl(222,48%,8%) 100%)}</style>
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
|
||||||
|
<div id="planet-bg" aria-hidden="true" style="position:fixed;inset:0;z-index:0;background:url(assets/euatlas.png) center/cover no-repeat;opacity:.35;pointer-events:none"></div>
|
||||||
|
<canvas id="stars" aria-hidden="true"></canvas>
|
||||||
|
|
||||||
|
<div class="main">
|
||||||
|
<div class="icon-wrap">
|
||||||
|
<div class="icon-ring">
|
||||||
|
<svg width="88" height="88" viewBox="0 0 88 88" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<circle cx="44" cy="44" r="40" stroke="#D4A24C" stroke-width="1" stroke-dasharray="4 6" opacity="0.5"/>
|
||||||
|
<circle cx="44" cy="4" r="2" fill="#D4A24C" opacity="0.7"/>
|
||||||
|
<circle cx="84" cy="44" r="2" fill="#D4A24C" opacity="0.7"/>
|
||||||
|
<circle cx="44" cy="84" r="2" fill="#D4A24C" opacity="0.7"/>
|
||||||
|
<circle cx="4" cy="44" r="2" fill="#D4A24C" opacity="0.7"/>
|
||||||
|
</svg>
|
||||||
|
<svg width="88" height="88" viewBox="0 0 88 88" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<circle cx="44" cy="44" r="34" stroke="#2E80FF" stroke-width="1" stroke-dasharray="3 5" opacity="0.4"/>
|
||||||
|
</svg>
|
||||||
|
<img src="/atlas-icon.png" alt="Atlas Academy" width="48" height="48" onerror="this.style.display='none'">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div style="text-align:center">
|
||||||
|
<div class="badge">Nu live</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<h1 class="gradient">Atlas Academy</h1>
|
||||||
|
<p class="sub">Praktijkcursussen voor ondernemers die bouwen.<br>Theorie én kennischecks — direct toegang tot 9 cursussen.</p>
|
||||||
|
|
||||||
|
<div class="card">
|
||||||
|
<h2>Begin vandaag</h2>
|
||||||
|
<p>Maak gratis een account aan en start meteen, of bekijk eerst het cursusaanbod.</p>
|
||||||
|
<div class="form-group">
|
||||||
|
<a href="/slides" class="btn btn-primary" style="text-decoration:none">Bekijk de cursussen →</a>
|
||||||
|
<a href="/register" class="btn" style="text-decoration:none;background:rgba(255,255,255,.06);color:var(--text);border:1px solid rgba(78,160,255,.25)">Gratis account aanmaken</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div style="position:relative;z-index:1;text-align:center;margin-top:20px;font-size:13px;color:#7a8aab">
|
||||||
|
Al een account? <a href="/login.html" style="color:#2E80FF;font-weight:700">Inloggen →</a>
|
||||||
|
|
|
||||||
|
<a href="/register.html" style="color:#2E80FF;font-weight:600">Nieuw account</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
/* ── Starfield ── */
|
||||||
|
(function(){
|
||||||
|
var c=document.getElementById('stars'),x=c.getContext('2d'),s=[],N=0,w=0,h=0,dpr=1,raf=0;
|
||||||
|
function size(){
|
||||||
|
dpr=Math.min(window.devicePixelRatio||1,2);
|
||||||
|
w=c.width=Math.floor(innerWidth*dpr);h=c.height=Math.floor(innerHeight*dpr);
|
||||||
|
c.style.width=innerWidth+'px';c.style.height=innerHeight+'px';
|
||||||
|
N=Math.max(50,Math.min(180,Math.round(innerWidth*innerHeight/10000)));
|
||||||
|
}
|
||||||
|
function init(){
|
||||||
|
s=[];
|
||||||
|
for(var i=0;i<N;i++) s.push({
|
||||||
|
x:Math.random()*w,y:Math.random()*h,
|
||||||
|
r:(Math.random()*1.4+0.2)*dpr,
|
||||||
|
a:Math.random()*0.55+0.15,
|
||||||
|
va:Math.random()*0.008+0.002,
|
||||||
|
vx:(Math.random()*0.12+0.01)*dpr,
|
||||||
|
vy:(Math.random()*0.05+0.006)*dpr,
|
||||||
|
p:Math.random()*6.283,
|
||||||
|
col:i%11===0?'#E8C46A':(i%5===0?'#8ab4f8':'#ffffff')
|
||||||
|
});
|
||||||
|
}
|
||||||
|
function draw(){
|
||||||
|
x.clearRect(0,0,w,h);
|
||||||
|
for(var i=0;i<N;i++){
|
||||||
|
var t=s[i];t.x-=t.vx;t.y+=t.vy;t.p+=t.va;
|
||||||
|
if(t.x<-2)t.x=w+2;if(t.y>h+2)t.y=-2;
|
||||||
|
var al=t.a+Math.sin(t.p)*0.25;
|
||||||
|
al=al<0?0:al>1?1:al;
|
||||||
|
x.globalAlpha=al;x.fillStyle=t.col;
|
||||||
|
x.beginPath();x.arc(t.x,t.y,t.r,0,6.283);x.fill();
|
||||||
|
}
|
||||||
|
raf=requestAnimationFrame(draw);
|
||||||
|
}
|
||||||
|
function start(){size();init();draw()}
|
||||||
|
start();
|
||||||
|
var rt;addEventListener('resize',function(){
|
||||||
|
clearTimeout(rt);rt=setTimeout(function(){
|
||||||
|
if(raf)cancelAnimationFrame(raf);start();
|
||||||
|
},200);
|
||||||
|
});
|
||||||
|
})();
|
||||||
|
|
||||||
|
/* ── Form ── */
|
||||||
|
async function handleSubmit(e){
|
||||||
|
e.preventDefault();
|
||||||
|
var btn=document.getElementById('btn');
|
||||||
|
var name=document.getElementById('name').value.trim();
|
||||||
|
var email=document.getElementById('email').value.trim();
|
||||||
|
if(!name||!email)return;
|
||||||
|
btn.textContent='Even wachten...';btn.disabled=true;
|
||||||
|
try{
|
||||||
|
var resp=await fetch('/academy-lead',{
|
||||||
|
method:'POST',
|
||||||
|
headers:{'Content-Type':'application/json'},
|
||||||
|
body:JSON.stringify({name:name,email:email,interest:'waitlist',source:'coming-soon'})
|
||||||
|
});
|
||||||
|
if(resp.ok){
|
||||||
|
document.getElementById('success').classList.add('visible');
|
||||||
|
document.getElementById('form').querySelector('.form-group').style.display='none';
|
||||||
|
btn.style.display='none';
|
||||||
|
}else{btn.textContent='Probeer opnieuw';btn.disabled=false}
|
||||||
|
}catch(err){btn.textContent='Probeer opnieuw';btn.disabled=false}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
1371
static/leerpad.html
Normal file
1371
static/leerpad.html
Normal file
File diff suppressed because it is too large
Load diff
487
static/over.html
Normal file
487
static/over.html
Normal file
|
|
@ -0,0 +1,487 @@
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html lang="nl">
|
||||||
|
<head>
|
||||||
|
<meta charset="UTF-8">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
|
<meta name="description" content="Business IT-consultant en implementatiespecialist. Ik help organisaties bij het selecteren, implementeren en optimaliseren van bedrijfssoftware en IT-processen op het snijvlak van operatie en software.">
|
||||||
|
<meta name="robots" content="index, follow">
|
||||||
|
<meta property="og:title" content="Chaib Aarab — Over mij | Atlas Academy">
|
||||||
|
<meta property="og:description" content="Business IT-consultant en implementatiespecialist. Ik help organisaties bij het selecteren, implementeren en optimaliseren van bedrijfssoftware en IT-processen op het snijvlak van operatie en software.">
|
||||||
|
<meta property="og:image" content="assets/chaib-banner.png">
|
||||||
|
<meta property="og:url" content="https://atlasacademy.nl/over.html">
|
||||||
|
<meta property="og:type" content="profile">
|
||||||
|
<title>Chaib Aarab — Over mij | Atlas Academy</title>
|
||||||
|
<script async src="https://www.googletagmanager.com/gtag/js?id=G-JBWZWZMKBC"></script>
|
||||||
|
<script>window.dataLayer=window.dataLayer||[];function gtag(){dataLayer.push(arguments);}gtag('js',new Date());gtag('config','G-JBWZWZMKBC');</script>
|
||||||
|
<script type="application/ld+json">
|
||||||
|
{"@context":"https://schema.org","@type":"Person","name":"Bouchaib Aarab","alternateName":"Chaib Aarab","jobTitle":"Founder & Business IT Consultant","description":"Business IT-consultant en implementatiespecialist gespecialiseerd in Odoo/ERP, CRM implementatie, AI automatisering en SaaS development.","url":"https://atlasacademy.nl/over.html","image":"https://atlasacademy.nl/assets/chaib-banner.png","email":"chaib@atlascorporation.nl","telephone":"+31639259220","address":{"@type":"PostalAddress","addressLocality":"Tilburg","addressCountry":"NL"},"sameAs":["https://www.linkedin.com/in/baarab/","https://atlascorporation.nl","https://atlaspos.nl","https://atlasworks.nl","https://atlasacademy.nl"],"worksFor":{"@type":"Organization","name":"Atlas Corporation","url":"https://atlascorporation.nl"},"knowsLanguage":["nl","en","fr"],"alumniOf":[{"@type":"EducationalOrganization","name":"Avans Hogeschool","addressLocality":"'s-Hertogenbosch"},{"@type":"EducationalOrganization","name":"Scalda","addressLocality":"Terneuzen"}]}
|
||||||
|
</script><style>
|
||||||
|
:root{--bg:#080C18;--card:#0B1220;--card2:#0d1a30;--border:rgba(55,65,81,.5);--accent:#3B82F6;--purple:#8B5CF6;--green:#22C55E;--txt:#E2E8F0;--muted:#6B7280;--font:-apple-system,BlinkMacSystemFont,'Segoe UI',Roboto,sans-serif;--radius:10px;--radius-lg:16px}
|
||||||
|
*,*::before,*::after{box-sizing:border-box;margin:0;padding:0}
|
||||||
|
html{scroll-behavior:smooth}
|
||||||
|
body{background:var(--bg);color:var(--txt);font-family:var(--font);font-size:16px;line-height:1.7;-webkit-font-smoothing:antialiased;overflow-x:hidden}
|
||||||
|
a{color:var(--accent);text-decoration:none;transition:color .2s}
|
||||||
|
a:hover{color:#93C5FD}
|
||||||
|
img{max-width:100%;display:block}
|
||||||
|
.container{width:100%;max-width:1140px;margin:0 auto;padding:0 24px}
|
||||||
|
.btn{display:inline-flex;align-items:center;gap:8px;padding:14px 28px;border-radius:var(--radius);font-size:15px;font-weight:700;cursor:pointer;transition:all .25s;border:none;text-decoration:none;white-space:nowrap;letter-spacing:.01em}
|
||||||
|
.btn-primary{background:linear-gradient(135deg,var(--accent),var(--purple));color:#fff;box-shadow:0 0 32px rgba(59,130,246,.4)}
|
||||||
|
.btn-primary:hover{transform:translateY(-2px);box-shadow:0 0 48px rgba(59,130,246,.6);color:#fff}
|
||||||
|
.btn-outline{background:transparent;color:#fff;border:2px solid rgba(255,255,255,.35)}
|
||||||
|
.btn-outline:hover{border-color:#fff;color:#fff;background:rgba(255,255,255,.07)}
|
||||||
|
.btn-sm{padding:9px 18px;font-size:13px}
|
||||||
|
.btn-ghost{background:rgba(59,130,246,.1);color:var(--accent);border:1px solid rgba(59,130,246,.3)}
|
||||||
|
.btn-ghost:hover{background:rgba(59,130,246,.2);color:var(--accent)}
|
||||||
|
.reveal{opacity:0;transform:translateY(30px);transition:opacity .65s ease,transform .65s ease}
|
||||||
|
.reveal.visible{opacity:1;transform:translateY(0)}
|
||||||
|
.gradient-text{background:linear-gradient(135deg,#fff 0%,#93C5FD 40%,var(--purple) 100%);-webkit-background-clip:text;-webkit-text-fill-color:transparent;background-clip:text}
|
||||||
|
section{padding:96px 0}
|
||||||
|
.section-label{font-size:12px;font-weight:700;letter-spacing:.12em;text-transform:uppercase;color:var(--accent);margin-bottom:12px}
|
||||||
|
.section-title{font-size:clamp(28px,4vw,44px);font-weight:800;line-height:1.2;margin-bottom:16px}
|
||||||
|
.section-sub{font-size:18px;color:var(--muted);max-width:600px}
|
||||||
|
#nav{position:fixed;top:0;left:0;right:0;z-index:1000;background:rgba(8,12,24,.8);backdrop-filter:blur(20px);-webkit-backdrop-filter:blur(20px);border-bottom:1px solid var(--border);height:64px;display:flex;align-items:center}
|
||||||
|
.nav-inner{display:flex;align-items:center;justify-content:space-between;width:100%;max-width:1140px;margin:0 auto;padding:0 24px}
|
||||||
|
.nav-logo{display:flex;align-items:center;gap:10px;text-decoration:none;color:#fff;font-weight:700;font-size:17px}
|
||||||
|
.nav-logo img{width:32px;height:32px;object-fit:contain;filter:brightness(0) invert(1)}
|
||||||
|
.nav-links{display:flex;align-items:center;gap:32px;list-style:none}
|
||||||
|
.nav-links a{color:rgba(255,255,255,.7);font-size:14px;font-weight:500;transition:color .2s}
|
||||||
|
.nav-links a:hover,.nav-links a.active{color:#fff}
|
||||||
|
.nav-cta{display:flex;align-items:center;gap:12px}
|
||||||
|
.nav-hamburger{display:none;background:none;border:none;color:#fff;cursor:pointer;padding:8px}
|
||||||
|
#mobile-menu{display:none;position:fixed;inset:64px 0 0 0;background:rgba(8,12,24,.98);backdrop-filter:blur(20px);z-index:999;flex-direction:column;align-items:center;justify-content:center;gap:32px}
|
||||||
|
#mobile-menu a{color:#fff;font-size:22px;font-weight:700;text-decoration:none}
|
||||||
|
#hero{min-height:100vh;display:flex;align-items:stretch;padding:0;margin-top:64px}
|
||||||
|
.hero-split{display:flex;width:100%;min-height:calc(100vh - 64px)}
|
||||||
|
.hero-photo{width:45%;flex-shrink:0;position:relative;overflow:hidden}
|
||||||
|
.hero-photo img{width:100%;height:100%;object-fit:cover;object-position:top center;display:block}
|
||||||
|
.hero-photo::after{content:'';position:absolute;top:0;right:0;width:120px;height:100%;background:linear-gradient(to right,transparent,var(--bg))}
|
||||||
|
.hero-content{flex:1;display:flex;align-items:center;padding:80px 64px;background:var(--bg);position:relative}
|
||||||
|
.hero-content::before{content:'';position:absolute;top:-200px;right:-200px;width:600px;height:600px;background:radial-gradient(circle,rgba(59,130,246,.08) 0%,transparent 70%);pointer-events:none}
|
||||||
|
.hero-inner{max-width:540px}
|
||||||
|
.hero-badge{display:inline-flex;align-items:center;gap:8px;background:rgba(59,130,246,.1);border:1px solid rgba(59,130,246,.25);color:var(--accent);font-size:12px;font-weight:700;letter-spacing:.1em;text-transform:uppercase;padding:6px 14px;border-radius:999px;margin-bottom:24px}
|
||||||
|
.hero-badge::before{content:'';width:6px;height:6px;background:var(--accent);border-radius:50%}
|
||||||
|
.hero-name{font-size:clamp(36px,5vw,64px);font-weight:900;line-height:1.1;color:#fff;margin-bottom:8px}
|
||||||
|
.hero-name .alias{font-size:clamp(20px,2.5vw,28px);font-weight:400;color:var(--muted);display:block;margin-top:4px}
|
||||||
|
.hero-subtitle{font-size:16px;font-weight:600;color:var(--accent);margin-bottom:20px;letter-spacing:.02em}
|
||||||
|
.hero-intro{font-size:16px;color:var(--muted);line-height:1.75;margin-bottom:32px}
|
||||||
|
.hero-contact{display:flex;flex-wrap:wrap;gap:12px;align-items:center;margin-bottom:28px}
|
||||||
|
.contact-item{display:flex;align-items:center;gap:7px;font-size:14px;color:rgba(255,255,255,.7);text-decoration:none;transition:color .2s}
|
||||||
|
.contact-item:hover{color:#fff}
|
||||||
|
.contact-item svg{color:var(--accent);flex-shrink:0}
|
||||||
|
.contact-sep{color:var(--border);font-size:18px}
|
||||||
|
.hero-langs{display:flex;flex-wrap:wrap;gap:8px}
|
||||||
|
.lang-badge{display:inline-flex;align-items:center;gap:6px;padding:5px 12px;border-radius:999px;font-size:12px;font-weight:600;background:rgba(255,255,255,.06);border:1px solid var(--border);color:rgba(255,255,255,.8)}
|
||||||
|
#verhaal{background:linear-gradient(180deg,var(--bg) 0%,#050810 50%,var(--bg) 100%)}
|
||||||
|
.verhaal-grid{display:grid;grid-template-columns:1fr 1fr;gap:80px;align-items:start}
|
||||||
|
.verhaal-sticky{position:sticky;top:96px}
|
||||||
|
.verhaal-photo{border-radius:var(--radius-lg);overflow:hidden;border:1px solid var(--border);box-shadow:0 40px 80px rgba(0,0,0,.5)}
|
||||||
|
.verhaal-photo img{width:100%;height:420px;object-fit:cover;object-position:top;display:block}
|
||||||
|
.verhaal-caption{padding:20px 24px;background:var(--card);display:flex;align-items:center;gap:12px}
|
||||||
|
.verhaal-caption-dot{width:8px;height:8px;border-radius:50%;background:var(--green);flex-shrink:0;animation:pulse 1.5s infinite}
|
||||||
|
@keyframes pulse{0%,100%{opacity:1;box-shadow:0 0 0 0 rgba(34,197,94,.4)}50%{opacity:.7;box-shadow:0 0 0 6px rgba(34,197,94,0)}}
|
||||||
|
.verhaal-caption-text{font-size:13px;color:var(--muted)}
|
||||||
|
.verhaal-caption-text strong{color:#fff}
|
||||||
|
.verhaal-text{padding-top:8px}
|
||||||
|
.verhaal-text h2{font-size:clamp(28px,3.5vw,40px);font-weight:800;line-height:1.2;margin-bottom:40px}
|
||||||
|
.story-p{font-size:17px;color:rgba(226,232,240,.85);line-height:1.8;margin-bottom:28px;padding-left:20px;border-left:3px solid transparent;transition:border-color .3s}
|
||||||
|
.story-p:hover{border-left-color:var(--accent)}
|
||||||
|
#mijlpalen{background:var(--bg)}
|
||||||
|
.mijlpalen-header{text-align:center;margin-bottom:72px}
|
||||||
|
.timeline-grid{display:grid;grid-template-columns:repeat(2,1fr);gap:0;max-width:900px;margin:0 auto;position:relative}
|
||||||
|
.timeline-grid::before{content:'';position:absolute;left:50%;top:0;bottom:0;width:2px;background:linear-gradient(180deg,var(--accent) 0%,var(--purple) 60%,rgba(139,92,246,.1) 100%);transform:translateX(-50%)}
|
||||||
|
.tl-item{padding:0 48px 56px;position:relative}
|
||||||
|
.tl-item:nth-child(odd){text-align:right;padding-right:56px;padding-left:0}
|
||||||
|
.tl-item:nth-child(even){padding-left:56px;padding-right:0}
|
||||||
|
.tl-item::before{content:'';position:absolute;top:6px;width:14px;height:14px;border-radius:50%;background:var(--accent);border:3px solid var(--bg);box-shadow:0 0 0 2px var(--accent);z-index:1}
|
||||||
|
.tl-item:nth-child(odd)::before{right:-7px}
|
||||||
|
.tl-item:nth-child(even)::before{left:-7px}
|
||||||
|
.tl-year{font-size:13px;font-weight:800;letter-spacing:.1em;color:var(--accent);margin-bottom:6px;text-transform:uppercase}
|
||||||
|
.tl-title{font-size:17px;font-weight:700;color:#fff;line-height:1.3;margin-bottom:4px}
|
||||||
|
.tl-sub{font-size:13px;color:var(--muted);line-height:1.5}
|
||||||
|
.tl-item.highlight .tl-title{color:#93C5FD}
|
||||||
|
.tl-item.highlight::before{background:var(--purple);box-shadow:0 0 0 2px var(--purple),0 0 12px rgba(139,92,246,.5)}
|
||||||
|
#portfolio{background:linear-gradient(180deg,var(--bg) 0%,#050810 100%)}
|
||||||
|
.portfolio-header{text-align:center;margin-bottom:56px}
|
||||||
|
.companies-grid{display:grid;grid-template-columns:repeat(2,1fr);gap:24px}
|
||||||
|
.company-card{position:relative;background:var(--card);border:1px solid var(--border);border-radius:var(--radius-lg);padding:36px;overflow:hidden;transition:all .3s;text-decoration:none;display:flex;flex-direction:column;gap:0;color:var(--txt)}
|
||||||
|
.company-card::before{content:'';position:absolute;inset:0;background:linear-gradient(135deg,rgba(59,130,246,.07) 0%,rgba(139,92,246,.07) 100%);opacity:0;transition:opacity .3s}
|
||||||
|
.company-card:hover{transform:translateY(-6px);border-color:rgba(59,130,246,.4);box-shadow:0 20px 60px rgba(0,0,0,.5),0 0 40px rgba(59,130,246,.12);color:var(--txt)}
|
||||||
|
.company-card:hover::before{opacity:1}
|
||||||
|
.company-card-top{display:flex;align-items:flex-start;justify-content:space-between;margin-bottom:20px}
|
||||||
|
.company-icon{width:52px;height:52px;background:linear-gradient(135deg,var(--accent),var(--purple));border-radius:12px;display:flex;align-items:center;justify-content:center;font-size:24px;flex-shrink:0}
|
||||||
|
.status-badge{display:inline-flex;align-items:center;gap:5px;padding:4px 10px;border-radius:999px;font-size:11px;font-weight:700;letter-spacing:.04em}
|
||||||
|
.status-live{background:rgba(34,197,94,.12);color:var(--green);border:1px solid rgba(34,197,94,.25)}
|
||||||
|
.status-live::before{content:'';width:6px;height:6px;background:var(--green);border-radius:50%;animation:blink 1.5s infinite}
|
||||||
|
@keyframes blink{0%,100%{opacity:1}50%{opacity:.4}}
|
||||||
|
.status-this{background:rgba(59,130,246,.12);color:var(--accent);border:1px solid rgba(59,130,246,.25)}
|
||||||
|
.company-name{font-size:22px;font-weight:800;color:#fff;margin-bottom:6px}
|
||||||
|
.company-tagline{font-size:13px;font-weight:600;color:var(--accent);margin-bottom:12px}
|
||||||
|
.company-desc{font-size:14px;color:var(--muted);line-height:1.6;flex:1;margin-bottom:20px}
|
||||||
|
.company-arrow{display:flex;align-items:center;gap:6px;font-size:13px;font-weight:700;color:var(--accent);transition:gap .2s}
|
||||||
|
.company-card:hover .company-arrow{gap:10px}
|
||||||
|
#vaardigheden{background:var(--bg)}
|
||||||
|
.vaardigheden-header{text-align:center;margin-bottom:56px}
|
||||||
|
.vaard-grid{display:grid;grid-template-columns:repeat(3,1fr);gap:24px}
|
||||||
|
.vaard-col{background:var(--card);border:1px solid var(--border);border-radius:var(--radius-lg);padding:32px;transition:all .3s}
|
||||||
|
.vaard-col:hover{border-color:rgba(59,130,246,.3);transform:translateY(-4px)}
|
||||||
|
.vaard-col-icon{width:44px;height:44px;border-radius:10px;display:flex;align-items:center;justify-content:center;font-size:20px;margin-bottom:16px}
|
||||||
|
.vaard-col-icon.tech{background:rgba(59,130,246,.15)}
|
||||||
|
.vaard-col-icon.biz{background:rgba(139,92,246,.15)}
|
||||||
|
.vaard-col-icon.pers{background:rgba(34,197,94,.15)}
|
||||||
|
.vaard-col-title{font-size:16px;font-weight:800;color:#fff;margin-bottom:20px}
|
||||||
|
.vaard-list{list-style:none;display:flex;flex-direction:column;gap:10px}
|
||||||
|
.vaard-list li{display:flex;align-items:center;gap:10px;font-size:14px;color:rgba(226,232,240,.8)}
|
||||||
|
.vaard-list li::before{content:'';width:6px;height:6px;border-radius:50%;flex-shrink:0}
|
||||||
|
.tech .vaard-list li::before{background:var(--accent)}
|
||||||
|
.biz .vaard-list li::before{background:var(--purple)}
|
||||||
|
.pers .vaard-list li::before{background:var(--green)}
|
||||||
|
#linkedin-section{background:linear-gradient(180deg,var(--bg) 0%,#050810 100%)}
|
||||||
|
.linkedin-inner{text-align:center}
|
||||||
|
.linkedin-header{margin-bottom:40px}
|
||||||
|
.linkedin-container{display:flex;justify-content:center;margin-bottom:24px}
|
||||||
|
.li-badge-wrap{background:rgba(11,18,32,.7);backdrop-filter:blur(20px);border:1px solid var(--border);border-radius:var(--radius-lg);padding:28px 36px;display:inline-block}
|
||||||
|
.li-fallback{align-items:center;gap:16px;background:rgba(11,18,32,.7);border:1px solid var(--border);border-radius:var(--radius-lg);padding:20px 28px}
|
||||||
|
.li-fallback-icon{width:40px;height:40px;background:#0A66C2;border-radius:8px;display:flex;align-items:center;justify-content:center;color:#fff;font-weight:900;font-size:18px;flex-shrink:0}
|
||||||
|
.li-fallback-name{font-weight:700;color:#fff;font-size:16px}
|
||||||
|
.li-fallback-sub{font-size:13px;color:var(--muted)}
|
||||||
|
#opleiding{background:var(--bg)}
|
||||||
|
.opleiding-header{text-align:center;margin-bottom:48px}
|
||||||
|
.opleiding-grid{display:grid;grid-template-columns:repeat(2,1fr);gap:24px;max-width:860px;margin:0 auto}
|
||||||
|
.edu-card{background:var(--card);border:1px solid var(--border);border-radius:var(--radius-lg);padding:32px 36px;display:flex;gap:24px;align-items:flex-start;transition:all .3s}
|
||||||
|
.edu-card:hover{border-color:rgba(59,130,246,.3);transform:translateY(-4px)}
|
||||||
|
.edu-icon{width:52px;height:52px;background:linear-gradient(135deg,rgba(59,130,246,.2),rgba(139,92,246,.2));border-radius:12px;display:flex;align-items:center;justify-content:center;font-size:22px;flex-shrink:0}
|
||||||
|
.edu-period{font-size:12px;font-weight:700;letter-spacing:.1em;color:var(--accent);text-transform:uppercase;margin-bottom:6px}
|
||||||
|
.edu-institution{font-size:18px;font-weight:800;color:#fff;margin-bottom:4px}
|
||||||
|
.edu-study{font-size:14px;color:var(--muted);line-height:1.5}
|
||||||
|
.edu-location{font-size:12px;color:rgba(107,114,128,.7);margin-top:4px}
|
||||||
|
#contact{background:linear-gradient(135deg,rgba(59,130,246,.06) 0%,rgba(139,92,246,.06) 100%);border-top:1px solid var(--border);border-bottom:1px solid var(--border)}
|
||||||
|
.contact-inner{text-align:center;max-width:600px;margin:0 auto}
|
||||||
|
.contact-inner h2{font-size:clamp(28px,4vw,44px);font-weight:800;color:#fff;margin-bottom:16px}
|
||||||
|
.contact-inner p{font-size:17px;color:var(--muted);margin-bottom:40px}
|
||||||
|
.contact-buttons{display:flex;flex-wrap:wrap;gap:16px;justify-content:center}
|
||||||
|
footer{background:#030609;border-top:1px solid var(--border);padding:64px 0 40px}
|
||||||
|
.footer-grid{display:grid;grid-template-columns:2fr 1fr 1fr 1fr;gap:40px;margin-bottom:48px}
|
||||||
|
.footer-brand{display:flex;flex-direction:column;gap:12px}
|
||||||
|
.footer-brand img{width:36px;height:36px;object-fit:contain;filter:brightness(0) invert(1)}
|
||||||
|
.footer-brand-name{font-size:18px;font-weight:800;color:#fff}
|
||||||
|
.footer-brand-tag{font-size:13px;color:var(--muted);line-height:1.6}
|
||||||
|
.footer-socials{display:flex;gap:12px;margin-top:4px}
|
||||||
|
.footer-social{width:34px;height:34px;border-radius:8px;background:rgba(255,255,255,.06);border:1px solid var(--border);display:flex;align-items:center;justify-content:center;color:var(--muted);transition:all .2s;text-decoration:none}
|
||||||
|
.footer-social:hover{background:var(--accent);border-color:var(--accent);color:#fff}
|
||||||
|
.footer-col h4{font-size:13px;font-weight:700;color:#fff;margin-bottom:16px;letter-spacing:.04em;text-transform:uppercase}
|
||||||
|
.footer-col ul{list-style:none;display:flex;flex-direction:column;gap:10px}
|
||||||
|
.footer-col ul li a{font-size:13px;color:var(--muted);transition:color .2s}
|
||||||
|
.footer-col ul li a:hover{color:#fff}
|
||||||
|
.footer-bottom{border-top:1px solid var(--border);padding-top:28px;display:flex;flex-direction:column;gap:4px}
|
||||||
|
.footer-copy{font-size:12px;color:rgba(107,114,128,.7)}
|
||||||
|
@media(max-width:1024px){.hero-split{flex-direction:column}.hero-photo{width:100%;height:380px}.hero-photo::after{display:none}.hero-content{padding:52px 40px}.verhaal-grid{grid-template-columns:1fr;gap:48px}.verhaal-sticky{position:static}.vaard-grid{grid-template-columns:1fr}.footer-grid{grid-template-columns:1fr 1fr}}
|
||||||
|
@media(max-width:768px){section{padding:64px 0}.nav-links,.nav-cta{display:none}.nav-hamburger{display:flex}.hero-content{padding:40px 24px}.hero-contact{flex-direction:column;align-items:flex-start}.contact-sep{display:none}.companies-grid{grid-template-columns:1fr}.timeline-grid{grid-template-columns:1fr}.timeline-grid::before{left:18px}.tl-item{padding-left:48px!important;padding-right:0!important;text-align:left!important}.tl-item::before{left:11px!important;right:auto!important}.opleiding-grid{grid-template-columns:1fr}.footer-grid{grid-template-columns:1fr;gap:32px}.contact-buttons{flex-direction:column;align-items:center}}
|
||||||
|
@media(max-width:480px){.hero-name{font-size:32px}.hero-content{padding:32px 20px}}
|
||||||
|
.lang-toggle{background:transparent;border:1px solid rgba(59,130,246,.5);color:#9CA3AF;padding:5px 12px;border-radius:20px;cursor:pointer;font-size:12px;font-weight:600;transition:all .2s;margin-right:8px;}</style></head>
|
||||||
|
<body>
|
||||||
|
<nav id="nav">
|
||||||
|
<div class="nav-inner">
|
||||||
|
<a href="index.html" class="nav-logo"><img src="assets/logo.png" alt="Atlas Academy">Atlas Academy</a>
|
||||||
|
<ul class="nav-links">
|
||||||
|
<li><a href="over.html" class="active">Over</a></li>
|
||||||
|
<li><a href="cursussen.html">Cursussen</a></li>
|
||||||
|
<li><a href="coaching.html">Coaching</a></li>
|
||||||
|
<li><a href="shop.html">Shop</a></li>
|
||||||
|
<li><a href="pricing.html">Prijzen</a></li>
|
||||||
|
<li><a href="/web/login?redirect=%2Fslides">Inloggen</a></li>
|
||||||
|
</ul>
|
||||||
|
<div class="nav-cta"><a href="cursussen.html" class="btn btn-primary btn-sm">Start gratis →</a></div>
|
||||||
|
<button class="nav-hamburger" onclick="toggleMobileMenu()" aria-label="Menu">
|
||||||
|
<svg width="24" height="24" fill="none" stroke="currentColor" stroke-width="2" viewBox="0 0 24 24"><line x1="3" y1="6" x2="21" y2="6"/><line x1="3" y1="12" x2="21" y2="12"/><line x1="3" y1="18" x2="21" y2="18"/></svg>
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</nav>
|
||||||
|
<div id="mobile-menu">
|
||||||
|
<a href="over.html" onclick="toggleMobileMenu()">Over</a>
|
||||||
|
<a href="cursussen.html" onclick="toggleMobileMenu()">Cursussen</a>
|
||||||
|
<a href="coaching.html" onclick="toggleMobileMenu()">Coaching</a>
|
||||||
|
<a href="shop.html" onclick="toggleMobileMenu()">Shop</a>
|
||||||
|
<a href="pricing.html" onclick="toggleMobileMenu()">Prijzen</a>
|
||||||
|
<a href="cursussen.html" class="btn btn-primary">Start gratis →</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<section id="hero">
|
||||||
|
<div class="hero-split">
|
||||||
|
<div class="hero-photo">
|
||||||
|
<img src="assets/chaib-banner.png" alt="Bouchaib Aarab — Business IT Consultant & Founder" loading="eager" fetchpriority="high">
|
||||||
|
</div>
|
||||||
|
<div class="hero-content">
|
||||||
|
<div class="hero-inner">
|
||||||
|
<div class="hero-badge">Over mij</div>
|
||||||
|
<h1 class="hero-name">Bouchaib Aarab<span class="alias">(Chaib)</span></h1>
|
||||||
|
<p class="hero-subtitle">Business IT Consultant · Founder · Tilburg</p>
|
||||||
|
<p class="hero-intro">Business IT-consultant en implementatiespecialist. Ik help organisaties bij het selecteren, implementeren en optimaliseren van bedrijfssoftware en IT-processen op het snijvlak van operatie en software.</p>
|
||||||
|
<div class="hero-contact">
|
||||||
|
<a href="mailto:chaib@atlascorporation.nl" class="contact-item">
|
||||||
|
<svg width="15" height="15" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M4 4h16c1.1 0 2 .9 2 2v12c0 1.1-.9 2-2 2H4c-1.1 0-2-.9-2-2V6c0-1.1.9-2 2-2z"/><polyline points="22,6 12,13 2,6"/></svg>
|
||||||
|
chaib@atlascorporation.nl
|
||||||
|
</a>
|
||||||
|
<span class="contact-sep">·</span>
|
||||||
|
<a href="tel:+31639259220" class="contact-item">
|
||||||
|
<svg width="15" height="15" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M22 16.92v3a2 2 0 0 1-2.18 2 19.79 19.79 0 0 1-8.63-3.07A19.5 19.5 0 0 1 4.69 12 19.79 19.79 0 0 1 1.61 3.18 2 2 0 0 1 3.59 1h3a2 2 0 0 1 2 1.72 12.84 12.84 0 0 0 .7 2.81 2 2 0 0 1-.45 2.11L7.91 8.5a16 16 0 0 0 6.07 6.07l.95-.95a2 2 0 0 1 2.11-.45 12.84 12.84 0 0 0 2.81.7A2 2 0 0 1 22 16.92z"/></svg>
|
||||||
|
06 39 25 92 20
|
||||||
|
</a>
|
||||||
|
<span class="contact-sep">·</span>
|
||||||
|
<a href="https://www.linkedin.com/in/baarab/" target="_blank" rel="noopener" class="btn btn-ghost btn-sm">
|
||||||
|
<svg width="14" height="14" viewBox="0 0 24 24" fill="currentColor"><path d="M19 0h-14c-2.761 0-5 2.239-5 5v14c0 2.761 2.239 5 5 5h14c2.762 0 5-2.239 5-5v-14c0-2.761-2.238-5-5-5zm-11 19h-3v-11h3v11zm-1.5-12.268c-.966 0-1.75-.79-1.75-1.764s.784-1.764 1.75-1.764 1.75.79 1.75 1.764-.783 1.764-1.75 1.764zm13.5 12.268h-3v-5.604c0-3.368-4-3.113-4 0v5.604h-3v-11h3v1.765c1.396-2.586 7-2.777 7 2.476v6.759z"/></svg>
|
||||||
|
LinkedIn
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
<div class="hero-langs">
|
||||||
|
<span class="lang-badge">🇳🇱 Nederlands</span>
|
||||||
|
<span class="lang-badge">🇬🇧 English</span>
|
||||||
|
<span class="lang-badge">🇫🇷 Français</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section id="verhaal">
|
||||||
|
<div class="container">
|
||||||
|
<div class="verhaal-grid">
|
||||||
|
<div class="verhaal-sticky reveal">
|
||||||
|
<div class="verhaal-photo">
|
||||||
|
<img src="assets/chaib.png" alt="Chaib Aarab — ERP POS CRM Founder" loading="lazy">
|
||||||
|
<div class="verhaal-caption">
|
||||||
|
<div class="verhaal-caption-dot"></div>
|
||||||
|
<div class="verhaal-caption-text"><strong>Bouchaib Aarab</strong> — actief als founder & consultant, Tilburg 2026</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="verhaal-text">
|
||||||
|
<p class="section-label">Mijn verhaal</p>
|
||||||
|
<h2 class="gradient-text">Van ICT-student tot SaaS-founder</h2>
|
||||||
|
<p class="story-p reveal">Ik ben opgegroeid met een fascinatie voor hoe dingen werken. Niet alleen technisch — maar hoe processen, mensen en systemen samen een organisatie vormen. Dat heeft me geleid van een ICT-opleiding aan Scalda in Terneuzen, via projectmanagement in de websitebouw, naar CRM-implementaties voor grote bedrijven, en uiteindelijk naar mijn eigen onderneming.</p>
|
||||||
|
<p class="story-p reveal">Tijdens mijn tijd als voorzitter van Innovision Solutions stuurde ik een studentenbedrijf van 200+ studenten aan. We haalden projecten uit het bedrijfsleven binnen, we presenteerden op beurzen en uiteindelijk zelfs voor het landelijke onderwijsorganisatie in Nederland. Het was de eerste keer dat ik begreep hoe krachtig het is als mensen en technologie goed zijn georganiseerd.</p>
|
||||||
|
<p class="story-p reveal">Bij Efficy deed ik CRM-implementaties van A tot Z. Van intake en requirements tot configuratie, training en oplevering. Ik leerde hoe je een klantproces vertaalt naar een werkend systeem — en hoe je change management doet zonder dat mensen afhaken. Die kennis gebruik ik elke dag nog.</p>
|
||||||
|
<p class="story-p reveal">In 2023 richtte ik Atlas Corporation op. Niet als consultant die zijn uren verkoopt, maar als ondernemer die producten bouwt. AtlasPOS is mijn eerste SaaS: een kassasysteem voor Tilburgse horecazaken voor €79 per maand. Atlas Academy is de bundeling van alles wat ik heb geleerd — voor ondernemers die zelf willen bouwen.</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section id="mijlpalen">
|
||||||
|
<div class="container">
|
||||||
|
<div class="mijlpalen-header reveal">
|
||||||
|
<p class="section-label">Carrière</p>
|
||||||
|
<h2 class="section-title gradient-text">Mijlpalen</h2>
|
||||||
|
<p class="section-sub" style="margin:0 auto;">Een decennium bouwen, leren en opstarten.</p>
|
||||||
|
</div>
|
||||||
|
<div class="timeline-grid">
|
||||||
|
<div class="tl-item reveal"><div class="tl-year">2014</div><div class="tl-title">ICT studie gestart</div><div class="tl-sub">Scalda, Terneuzen — Applicatie- en mediaontwikkelaar</div></div>
|
||||||
|
<div class="tl-item reveal"><div class="tl-year">2016</div><div class="tl-title">Project Manager</div><div class="tl-sub">Innovision Solutions — eerste ervaring met SCRUM en klantaansturing</div></div>
|
||||||
|
<div class="tl-item highlight reveal"><div class="tl-year">2017</div><div class="tl-title">Chairman Innovision Solutions</div><div class="tl-sub">200+ studenten aangestuurd · Presentatie landelijke onderwijsorganisatie, Nederland · open dagen & beurzen</div></div>
|
||||||
|
<div class="tl-item reveal"><div class="tl-year">2017</div><div class="tl-title">Support Engineer → Project Manager</div><div class="tl-sub">Dutchwebdesign / Hybridd, Breda — front/back-end development, gepromoveerd tijdens contract</div></div>
|
||||||
|
<div class="tl-item reveal"><div class="tl-year">2018</div><div class="tl-title">Business Administration</div><div class="tl-sub">Avans Hogeschool, 's-Hertogenbosch — studie niet afgerond — gekozen voor eigen bedrijf</div></div>
|
||||||
|
<div class="tl-item highlight reveal"><div class="tl-year">2022</div><div class="tl-title">CRM Implementation Consultant</div><div class="tl-sub">Efficy, 's-Hertogenbosch — full-cycle: intake → requirements → config → training → delivery</div></div>
|
||||||
|
<div class="tl-item reveal"><div class="tl-year">2023</div><div class="tl-title">Atlas Works opgericht</div><div class="tl-sub">IT consultancy voor MKB, Tilburg — eerste zelfstandige klanten, Odoo & procesoptimalisatie</div></div>
|
||||||
|
<div class="tl-item highlight reveal"><div class="tl-year">2024</div><div class="tl-title">AtlasPOS gelanceerd</div><div class="tl-sub">SaaS kassasysteem €79/maand — eerste betalende klanten in Tilburgse horeca</div></div>
|
||||||
|
<div class="tl-item reveal"><div class="tl-year">2025</div><div class="tl-title">Atlas Corporation officieel</div><div class="tl-sub">Holding voor alle Atlas-producten — fleet management, AI-stack, n8n automatisering live</div></div>
|
||||||
|
<div class="tl-item highlight reveal"><div class="tl-year">2026</div><div class="tl-title">Atlas Academy live</div><div class="tl-sub">Leerplatform voor ondernemers — kennis van de praktijk, niet de theorie</div></div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section id="portfolio">
|
||||||
|
<div class="container">
|
||||||
|
<div class="portfolio-header reveal">
|
||||||
|
<p class="section-label">Portfolio</p>
|
||||||
|
<h2 class="section-title gradient-text">Mijn bedrijven</h2>
|
||||||
|
<p class="section-sub" style="margin:0 auto;">Vier ondernemingen, één missie: MKB versnellen met technologie.</p>
|
||||||
|
</div>
|
||||||
|
<div class="companies-grid">
|
||||||
|
<a href="https://atlascorporation.nl" target="_blank" rel="noopener" class="company-card reveal">
|
||||||
|
<div class="company-card-top"><div class="company-icon">🏚</div><span class="status-badge status-live">LIVE</span></div>
|
||||||
|
<div class="company-name">Atlas Corporation</div><div class="company-tagline">Holding · IT Consultancy</div>
|
||||||
|
<p class="company-desc">De holding achter alle Atlas-producten. Business IT consultancy voor MKB-bedrijven tot ~10 medewerkers zonder interne IT-capaciteit. Odoo, AI-automatisering, infrastructuur.</p>
|
||||||
|
<div class="company-arrow">atlascorporation.nl <span>→</span></div>
|
||||||
|
</a>
|
||||||
|
<a href="https://atlaspos.nl" target="_blank" rel="noopener" class="company-card reveal">
|
||||||
|
<div class="company-card-top"><div class="company-icon">🖥</div><span class="status-badge status-live">LIVE · €79/mo</span></div>
|
||||||
|
<div class="company-name">AtlasPOS</div><div class="company-tagline">SaaS · Kassasysteem · Horeca</div>
|
||||||
|
<p class="company-desc">Mijn eerste SaaS-product. Een compleet kassasysteem inclusief pin-terminal voor Tilburgse horecazaken. €79 per maand, all-in. Gebouwd, live, betalende klanten.</p>
|
||||||
|
<div class="company-arrow">atlaspos.nl <span>→</span></div>
|
||||||
|
</a>
|
||||||
|
<a href="https://atlasworks.nl" target="_blank" rel="noopener" class="company-card reveal">
|
||||||
|
<div class="company-card-top"><div class="company-icon">🔧</div><span class="status-badge status-live">LIVE</span></div>
|
||||||
|
<div class="company-name">Atlas Works</div><div class="company-tagline">Refurbished IT · MKB Hardware</div>
|
||||||
|
<p class="company-desc">Gecertificeerde refurbished laptops en desktops voor het MKB. Duurzaam, betrouwbaar, betaalbaar. Gecombineerd met IT-support en consultancy voor kleine bedrijven.</p>
|
||||||
|
<div class="company-arrow">atlasworks.nl <span>→</span></div>
|
||||||
|
</a>
|
||||||
|
<a href="index.html" class="company-card reveal">
|
||||||
|
<div class="company-card-top"><div class="company-icon">🎓</div><span class="status-badge status-this">DIT PLATFORM</span></div>
|
||||||
|
<div class="company-name">Atlas Academy</div><div class="company-tagline">Leerplatform · Ondernemers</div>
|
||||||
|
<p class="company-desc">Alles wat ik heb geleerd over bouwen, implementeren en ondernemen — gebundeld voor ondernemers die zelf willen groeien. Cursussen, coaching en praktijkkennis.</p>
|
||||||
|
<div class="company-arrow">atlasacademy.nl <span>→</span></div>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section id="vaardigheden">
|
||||||
|
<div class="container">
|
||||||
|
<div class="vaardigheden-header reveal">
|
||||||
|
<p class="section-label">Expertise</p>
|
||||||
|
<h2 class="section-title gradient-text">Vaardigheden</h2>
|
||||||
|
<p class="section-sub" style="margin:0 auto;">Opgebouwd over 9 jaar op het snijvlak van business en technologie.</p>
|
||||||
|
</div>
|
||||||
|
<div class="vaard-grid">
|
||||||
|
<div class="vaard-col tech reveal">
|
||||||
|
<div class="vaard-col-icon tech">⚙</div>
|
||||||
|
<div class="vaard-col-title">Technisch</div>
|
||||||
|
<ul class="vaard-list"><li>Odoo / ERP implementatie</li><li>n8n automatisering</li><li>AI (Ollama / RAG / LLM)</li><li>Web development</li><li>Linux / VPS beheer</li><li>MeshCentral fleet management</li><li>Security (OWASP)</li></ul>
|
||||||
|
</div>
|
||||||
|
<div class="vaard-col biz reveal">
|
||||||
|
<div class="vaard-col-icon biz">📊</div>
|
||||||
|
<div class="vaard-col-title">Business</div>
|
||||||
|
<ul class="vaard-list"><li>CRM implementatie</li><li>Procesoptimalisatie</li><li>Requirements analyse</li><li>Stakeholdermanagement</li><li>Projectmanagement (SCRUM)</li><li>Change management</li><li>SaaS product development</li></ul>
|
||||||
|
</div>
|
||||||
|
<div class="vaard-col pers reveal">
|
||||||
|
<div class="vaard-col-icon pers">🧠</div>
|
||||||
|
<div class="vaard-col-title">Persoonlijk</div>
|
||||||
|
<ul class="vaard-list"><li>Analytisch denken</li><li>Probleemoplossend</li><li>Klantgericht</li><li>Communicatief sterk</li><li>Zelfstandig en gedisciplineerd</li><li>Snel leren</li><li>Ondernemende mindset</li></ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section id="linkedin-section">
|
||||||
|
<div class="container">
|
||||||
|
<div class="linkedin-inner">
|
||||||
|
<div class="linkedin-header reveal">
|
||||||
|
<p class="section-label">LinkedIn</p>
|
||||||
|
<h2 class="section-title gradient-text">Volg mijn werk</h2>
|
||||||
|
<p class="section-sub" style="margin:0 auto;">Ik deel inzichten over ondernemen, AI en MKB-technologie.</p>
|
||||||
|
</div>
|
||||||
|
<div class="linkedin-container reveal">
|
||||||
|
<div class="li-badge-wrap">
|
||||||
|
<div class="badge-base LI-profile-badge" data-locale="nl_NL" data-size="large" data-theme="dark" data-type="HORIZONTAL" data-vanity="baarab" data-version="v1">
|
||||||
|
<a class="badge-base__link LI-simple-link" href="https://nl.linkedin.com/in/baarab" target="_blank" rel="noopener">Bouchaib Aarab</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="li-fallback" id="li-fallback" style="display:none;">
|
||||||
|
<div class="li-fallback-icon">in</div>
|
||||||
|
<div><div class="li-fallback-name">Bouchaib Aarab</div><div class="li-fallback-sub">Founder @ Atlas Corporation</div></div>
|
||||||
|
<a href="https://nl.linkedin.com/in/baarab" target="_blank" rel="noopener" class="btn btn-primary btn-sm" style="margin-left:auto;">Verbinden</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div style="margin-top:28px;" class="reveal">
|
||||||
|
<a href="https://www.linkedin.com/in/baarab/" target="_blank" rel="noopener" class="btn btn-outline">Bekijk LinkedIn profiel →</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
<script src="https://platform.linkedin.com/badges/js/profile.js" async defer type="text/javascript"></script>
|
||||||
|
|
||||||
|
<section id="opleiding">
|
||||||
|
<div class="container">
|
||||||
|
<div class="opleiding-header reveal">
|
||||||
|
<p class="section-label">Achtergrond</p>
|
||||||
|
<h2 class="section-title gradient-text">Opleiding</h2>
|
||||||
|
</div>
|
||||||
|
<div class="opleiding-grid">
|
||||||
|
<div class="edu-card reveal">
|
||||||
|
<div class="edu-icon">🏛</div>
|
||||||
|
<div>
|
||||||
|
<div class="edu-period">2018 – 2021</div>
|
||||||
|
<div class="edu-institution">Avans Hogeschool</div>
|
||||||
|
<div class="edu-study">Business Administration — studie niet afgerond — gekozen voor eigen bedrijf</div>
|
||||||
|
<div class="edu-location">'s-Hertogenbosch, Nederland</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="edu-card reveal">
|
||||||
|
<div class="edu-icon">💻</div>
|
||||||
|
<div>
|
||||||
|
<div class="edu-period">2014 – 2018</div>
|
||||||
|
<div class="edu-institution">Scalda</div>
|
||||||
|
<div class="edu-study">ICT: Applicatie- en mediaontwikkelaar — MBO niveau 4, afgerond</div>
|
||||||
|
<div class="edu-location">Terneuzen, Nederland</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section id="contact">
|
||||||
|
<div class="container">
|
||||||
|
<div class="contact-inner reveal">
|
||||||
|
<p class="section-label" style="text-align:center;">Samenwerken</p>
|
||||||
|
<h2>Wil je samenwerken of heb je een vraag?</h2>
|
||||||
|
<p>Neem direct contact op — ik reageer persoonlijk.</p>
|
||||||
|
<div class="contact-buttons">
|
||||||
|
<a href="mailto:chaib@atlascorporation.nl" class="btn btn-primary">
|
||||||
|
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M4 4h16c1.1 0 2 .9 2 2v12c0 1.1-.9 2-2 2H4c-1.1 0-2-.9-2-2V6c0-1.1.9-2 2-2z"/><polyline points="22,6 12,13 2,6"/></svg>
|
||||||
|
chaib@atlascorporation.nl
|
||||||
|
</a>
|
||||||
|
<a href="tel:+31639259220" class="btn btn-outline">
|
||||||
|
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M22 16.92v3a2 2 0 0 1-2.18 2 19.79 19.79 0 0 1-8.63-3.07A19.5 19.5 0 0 1 4.69 12 19.79 19.79 0 0 1 1.61 3.18 2 2 0 0 1 3.59 1h3a2 2 0 0 1 2 1.72 12.84 12.84 0 0 0 .7 2.81 2 2 0 0 1-.45 2.11L7.91 8.5a16 16 0 0 0 6.07 6.07l.95-.95a2 2 0 0 1 2.11-.45 12.84 12.84 0 0 0 2.81.7A2 2 0 0 1 22 16.92z"/></svg>
|
||||||
|
06 39 25 92 20
|
||||||
|
</a>
|
||||||
|
<a href="https://www.linkedin.com/in/baarab/" target="_blank" rel="noopener" class="btn btn-ghost">
|
||||||
|
<svg width="16" height="16" viewBox="0 0 24 24" fill="currentColor"><path d="M19 0h-14c-2.761 0-5 2.239-5 5v14c0 2.761 2.239 5 5 5h14c2.762 0 5-2.239 5-5v-14c0-2.761-2.238-5-5-5zm-11 19h-3v-11h3v11zm-1.5-12.268c-.966 0-1.75-.79-1.75-1.764s.784-1.764 1.75-1.764 1.75.79 1.75 1.764-.783 1.764-1.75 1.764zm13.5 12.268h-3v-5.604c0-3.368-4-3.113-4 0v5.604h-3v-11h3v1.765c1.396-2.586 7-2.777 7 2.476v6.759z"/></svg>
|
||||||
|
LinkedIn
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<footer>
|
||||||
|
<div class="container">
|
||||||
|
<div class="footer-grid">
|
||||||
|
<div class="footer-brand">
|
||||||
|
<img src="assets/logo.png" alt="Atlas Academy" width="36" height="36">
|
||||||
|
<div class="footer-brand-name">Atlas Academy</div>
|
||||||
|
<p class="footer-brand-tag">Leer wat werkt. Bouw wat telt. Kennis van een ondernemer die het nu doet.</p>
|
||||||
|
<div class="footer-socials">
|
||||||
|
<a href="https://www.linkedin.com/in/baarab/" target="_blank" rel="noopener" class="footer-social" aria-label="LinkedIn">
|
||||||
|
<svg width="16" height="16" viewBox="0 0 24 24" fill="currentColor"><path d="M19 0h-14c-2.761 0-5 2.239-5 5v14c0 2.761 2.239 5 5 5h14c2.762 0 5-2.239 5-5v-14c0-2.761-2.238-5-5-5zm-11 19h-3v-11h3v11zm-1.5-12.268c-.966 0-1.75-.79-1.75-1.764s.784-1.764 1.75-1.764 1.75.79 1.75 1.764-.783 1.764-1.75 1.764zm13.5 12.268h-3v-5.604c0-3.368-4-3.113-4 0v5.604h-3v-11h3v1.765c1.396-2.586 7-2.777 7 2.476v6.759z"/></svg>
|
||||||
|
</a>
|
||||||
|
<a href="mailto:chaib@atlascorporation.nl" class="footer-social" aria-label="Email">
|
||||||
|
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M4 4h16c1.1 0 2 .9 2 2v12c0 1.1-.9 2-2 2H4c-1.1 0-2-.9-2-2V6c0-1.1.9-2 2-2z"/><polyline points="22,6 12,13 2,6"/></svg>
|
||||||
|
</a>
|
||||||
|
<a href="tel:+31639259220" class="footer-social" aria-label="Bel Chaib">
|
||||||
|
<svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M22 16.92v3a2 2 0 0 1-2.18 2 19.79 19.79 0 0 1-8.63-3.07A19.5 19.5 0 0 1 4.69 12 19.79 19.79 0 0 1 1.61 3.18 2 2 0 0 1 3.59 1h3a2 2 0 0 1 2 1.72 12.84 12.84 0 0 0 .7 2.81 2 2 0 0 1-.45 2.11L7.91 8.5a16 16 0 0 0 6.07 6.07l.95-.95a2 2 0 0 1 2.11-.45 12.84 12.84 0 0 0 2.81.7A2 2 0 0 1 22 16.92z"/></svg>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer-col"><h4>Cursussen</h4><ul><li><a href="cursussen.html">Alle cursussen</a></li><li><a href="cursussen.html">Odoo MKB</a></li><li><a href="cursussen.html">AI Automatisering</a></li><li><a href="cursussen.html">SaaS bouwen</a></li><li><a href="leerpad.html">Leerpaden</a></li></ul></div>
|
||||||
|
<div class="footer-col"><h4>Over</h4><ul><li><a href="over.html">Mijn verhaal</a></li><li><a href="coaching.html">Coaching</a></li><li><a href="pricing.html">Prijzen</a></li><li><a href="shop.html">Shop</a></li><li><a href="https://www.linkedin.com/in/baarab/" target="_blank" rel="noopener">LinkedIn</a></li></ul></div>
|
||||||
|
<div class="footer-col"><h4>Bedrijven</h4><ul><li><a href="https://atlascorporation.nl" target="_blank" rel="noopener">Atlas Corporation</a></li><li><a href="https://atlaspos.nl" target="_blank" rel="noopener">AtlasPOS</a></li><li><a href="https://atlasworks.nl" target="_blank" rel="noopener">Atlas Works</a></li><li><a href="mailto:chaib@atlascorporation.nl">Contact</a></li></ul></div>
|
||||||
|
</div>
|
||||||
|
<div class="footer-bottom">
|
||||||
|
<p class="footer-copy">© 2024–2026 Atlas Academy — onderdeel van Atlas Corporation. KvK: zie atlascorporation.nl</p>
|
||||||
|
<p class="footer-copy">chaib@atlascorporation.nl · 06 39 25 92 20 · Tilburg, Nederland</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</footer>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
const revealObserver = new IntersectionObserver((entries) => {
|
||||||
|
entries.forEach(e => { if (e.isIntersecting) e.target.classList.add('visible'); });
|
||||||
|
}, { threshold: 0.1, rootMargin: '0px 0px -40px 0px' });
|
||||||
|
document.querySelectorAll('.reveal').forEach(el => revealObserver.observe(el));
|
||||||
|
function toggleMobileMenu() {
|
||||||
|
const m = document.getElementById('mobile-menu');
|
||||||
|
if (m.style.display === 'none' || !m.style.display) { m.style.display = 'flex'; document.body.style.overflow = 'hidden'; }
|
||||||
|
else { m.style.display = 'none'; document.body.style.overflow = ''; }
|
||||||
|
}
|
||||||
|
const nav = document.getElementById('nav');
|
||||||
|
window.addEventListener('scroll', () => {
|
||||||
|
nav.style.background = window.scrollY > 80 ? 'rgba(8,12,24,.95)' : 'rgba(8,12,24,.8)';
|
||||||
|
}, { passive: true });
|
||||||
|
window.addEventListener('load', () => {
|
||||||
|
setTimeout(() => {
|
||||||
|
const b = document.querySelector('.LI-profile-badge');
|
||||||
|
if (b && !b.querySelector('iframe') && !b.querySelector('.profile-badge')) document.getElementById('li-fallback').style.display = 'flex';
|
||||||
|
}, 3000);
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
<script>function toggleLang(){var isNL=document.documentElement.lang!=="en";var lang=isNL?"en":"nl";document.documentElement.lang=lang;document.getElementById("langBtn").textContent=isNL?"NL":"EN";document.querySelectorAll("[data-nl]").forEach(function(el){var v=el.getAttribute("data-"+lang);if(v)el.innerHTML=v;});localStorage.setItem("aa_lang",lang);}(function(){if(localStorage.getItem("aa_lang")==="en")toggleLang();})();</script></body>
|
||||||
|
</html>
|
||||||
964
static/pricing.html
Normal file
964
static/pricing.html
Normal file
|
|
@ -0,0 +1,964 @@
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html lang="nl">
|
||||||
|
<head>
|
||||||
|
<meta charset="UTF-8">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
|
<meta name="description" content="Atlas Academy prijzen — Starter €20/maand, Pro €49/maand. Geen verborgen kosten, maandelijks opzegbaar.">
|
||||||
|
<meta name="robots" content="index, follow">
|
||||||
|
<title>Prijzen — Atlas Academy</title>
|
||||||
|
<style>
|
||||||
|
/* ============================
|
||||||
|
CSS CUSTOM PROPERTIES (exact from index.html)
|
||||||
|
============================ */
|
||||||
|
:root {
|
||||||
|
--bg: #040810;
|
||||||
|
--card: #0a1628;
|
||||||
|
--card2: #0d1f3c;
|
||||||
|
--border: rgba(59,130,246,.15);
|
||||||
|
--arc: #3B82F6;
|
||||||
|
--purple: #8B5CF6;
|
||||||
|
--cyan: #06B6D4;
|
||||||
|
--ok: #22C55E;
|
||||||
|
--warn: #F59E0B;
|
||||||
|
--pink: #EC4899;
|
||||||
|
--amber: #F59E0B;
|
||||||
|
--txt: #F1F5F9;
|
||||||
|
--muted: #94A3B8;
|
||||||
|
--font: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
|
||||||
|
--radius: 10px;
|
||||||
|
--radius-lg: 16px;
|
||||||
|
--radius-xl: 24px;
|
||||||
|
}
|
||||||
|
|
||||||
|
*, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; }
|
||||||
|
html { scroll-behavior: smooth; }
|
||||||
|
body {
|
||||||
|
background: var(--bg);
|
||||||
|
color: var(--txt);
|
||||||
|
font-family: var(--font);
|
||||||
|
font-size: 16px;
|
||||||
|
line-height: 1.6;
|
||||||
|
-webkit-font-smoothing: antialiased;
|
||||||
|
overflow-x: hidden;
|
||||||
|
}
|
||||||
|
a { color: var(--arc); text-decoration: none; }
|
||||||
|
a:hover { color: #93C5FD; }
|
||||||
|
img { max-width: 100%; }
|
||||||
|
|
||||||
|
.container {
|
||||||
|
width: 100%;
|
||||||
|
max-width: 1140px;
|
||||||
|
margin: 0 auto;
|
||||||
|
padding: 0 24px;
|
||||||
|
}
|
||||||
|
.gradient-text {
|
||||||
|
background: linear-gradient(135deg, #fff 0%, #93c5fd 50%, #c4b5fd 100%);
|
||||||
|
-webkit-background-clip: text;
|
||||||
|
-webkit-text-fill-color: transparent;
|
||||||
|
background-clip: text;
|
||||||
|
}
|
||||||
|
.btn {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 8px;
|
||||||
|
padding: 12px 26px;
|
||||||
|
border-radius: var(--radius);
|
||||||
|
font-size: 15px;
|
||||||
|
font-weight: 600;
|
||||||
|
cursor: pointer;
|
||||||
|
transition: all .2s;
|
||||||
|
border: none;
|
||||||
|
text-decoration: none;
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
.btn-primary {
|
||||||
|
background: linear-gradient(135deg, var(--arc), var(--purple));
|
||||||
|
color: #fff;
|
||||||
|
box-shadow: 0 0 30px rgba(59,130,246,.35);
|
||||||
|
}
|
||||||
|
.btn-primary:hover { box-shadow: 0 0 50px rgba(59,130,246,.6); transform: translateY(-2px); color: #fff; }
|
||||||
|
.btn-glass {
|
||||||
|
background: rgba(255,255,255,.06);
|
||||||
|
color: var(--txt);
|
||||||
|
border: 1px solid rgba(255,255,255,.12);
|
||||||
|
backdrop-filter: blur(12px);
|
||||||
|
}
|
||||||
|
.btn-glass:hover { background: rgba(255,255,255,.1); border-color: rgba(255,255,255,.2); transform: translateY(-2px); color: var(--txt); }
|
||||||
|
.btn-outline {
|
||||||
|
background: transparent;
|
||||||
|
color: var(--arc);
|
||||||
|
border: 1.5px solid rgba(59,130,246,.4);
|
||||||
|
}
|
||||||
|
.btn-outline:hover { border-color: var(--arc); box-shadow: 0 0 20px rgba(59,130,246,.2); transform: translateY(-2px); color: var(--arc); }
|
||||||
|
.btn-ghost {
|
||||||
|
background: transparent;
|
||||||
|
color: var(--muted);
|
||||||
|
border: 1px solid rgba(255,255,255,.08);
|
||||||
|
}
|
||||||
|
.btn-ghost:hover { background: rgba(255,255,255,.05); color: var(--txt); border-color: rgba(255,255,255,.15); }
|
||||||
|
|
||||||
|
section { padding: 88px 0; }
|
||||||
|
.section-label {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 6px;
|
||||||
|
font-size: 11px;
|
||||||
|
font-weight: 700;
|
||||||
|
letter-spacing: .12em;
|
||||||
|
text-transform: uppercase;
|
||||||
|
color: var(--arc);
|
||||||
|
margin-bottom: 12px;
|
||||||
|
}
|
||||||
|
.section-label::before { content: ''; display: block; width: 16px; height: 1px; background: var(--arc); }
|
||||||
|
.section-title { font-size: clamp(26px, 4vw, 40px); font-weight: 800; line-height: 1.15; margin-bottom: 14px; letter-spacing: -.02em; }
|
||||||
|
.section-sub { color: var(--muted); font-size: 17px; max-width: 540px; line-height: 1.7; }
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
BACKGROUND ANIMATIONS
|
||||||
|
============================ */
|
||||||
|
@keyframes mesh { 0%, 100% { background-position: 0% 50%; } 50% { background-position: 100% 50%; } }
|
||||||
|
@keyframes float1 { 0%, 100% { transform: translate(0,0) scale(1); } 33% { transform: translate(30px,-20px) scale(1.05); } 66% { transform: translate(-20px,15px) scale(.97); } }
|
||||||
|
@keyframes float2 { 0%, 100% { transform: translate(0,0) scale(1); } 33% { transform: translate(-25px,20px) scale(1.03); } 66% { transform: translate(20px,-15px) scale(.98); } }
|
||||||
|
@keyframes float3 { 0%, 100% { transform: translate(0,0) scale(1); } 50% { transform: translate(15px,25px) scale(1.04); } }
|
||||||
|
@keyframes fadeSlideUp { from { opacity: 0; transform: translateY(28px); } to { opacity: 1; transform: translateY(0); } }
|
||||||
|
@keyframes shimmer { from { background-position: -200% center; } to { background-position: 200% center; } }
|
||||||
|
@keyframes borderGlow {
|
||||||
|
0%, 100% { box-shadow: 0 0 0 0 rgba(59,130,246,.4), 0 0 40px rgba(59,130,246,.15); }
|
||||||
|
50% { box-shadow: 0 0 0 4px rgba(59,130,246,.1), 0 0 80px rgba(59,130,246,.25); }
|
||||||
|
}
|
||||||
|
@keyframes gradientBorder {
|
||||||
|
0% { background-position: 0% 50%; }
|
||||||
|
50% { background-position: 100% 50%; }
|
||||||
|
100% { background-position: 0% 50%; }
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
NAV (exact glassmorphism from index.html)
|
||||||
|
============================ */
|
||||||
|
nav {
|
||||||
|
position: sticky;
|
||||||
|
top: 0;
|
||||||
|
z-index: 200;
|
||||||
|
background: rgba(4,8,16,.85);
|
||||||
|
backdrop-filter: blur(20px);
|
||||||
|
-webkit-backdrop-filter: blur(20px);
|
||||||
|
border-bottom: 1px solid rgba(59,130,246,.08);
|
||||||
|
}
|
||||||
|
.nav-inner { display: flex; align-items: center; justify-content: space-between; height: 64px; gap: 16px; }
|
||||||
|
.nav-logo {
|
||||||
|
font-size: 16px;
|
||||||
|
font-weight: 800;
|
||||||
|
color: var(--txt);
|
||||||
|
white-space: nowrap;
|
||||||
|
flex-shrink: 0;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 8px;
|
||||||
|
letter-spacing: -.01em;
|
||||||
|
}
|
||||||
|
.nav-logo:hover { color: #93C5FD; }
|
||||||
|
.nav-logo-icon {
|
||||||
|
width: 28px; height: 28px;
|
||||||
|
background: linear-gradient(135deg, var(--arc), var(--purple));
|
||||||
|
border-radius: 8px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
font-size: 14px;
|
||||||
|
flex-shrink: 0;
|
||||||
|
}
|
||||||
|
.nav-links { display: flex; align-items: center; gap: 28px; list-style: none; }
|
||||||
|
.nav-links a { color: var(--muted); font-size: 14px; font-weight: 500; transition: color .15s; }
|
||||||
|
.nav-links a:hover { color: var(--txt); }
|
||||||
|
.nav-links a.active { color: var(--arc); font-weight: 700; }
|
||||||
|
.nav-cta { padding: 9px 20px; font-size: 14px; }
|
||||||
|
.nav-mobile-toggle {
|
||||||
|
display: none;
|
||||||
|
background: rgba(255,255,255,.05);
|
||||||
|
border: 1px solid rgba(255,255,255,.1);
|
||||||
|
color: var(--txt);
|
||||||
|
padding: 6px 10px;
|
||||||
|
border-radius: 8px;
|
||||||
|
font-size: 18px;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
.nav-mobile-menu {
|
||||||
|
display: none;
|
||||||
|
flex-direction: column;
|
||||||
|
background: rgba(10,22,40,.98);
|
||||||
|
border-bottom: 1px solid rgba(59,130,246,.1);
|
||||||
|
padding: 8px 0;
|
||||||
|
}
|
||||||
|
.nav-mobile-menu a {
|
||||||
|
display: block;
|
||||||
|
padding: 13px 24px;
|
||||||
|
color: var(--txt);
|
||||||
|
font-size: 15px;
|
||||||
|
border-bottom: 1px solid rgba(255,255,255,.04);
|
||||||
|
transition: background .15s;
|
||||||
|
}
|
||||||
|
.nav-mobile-menu a:hover { background: rgba(59,130,246,.06); }
|
||||||
|
.nav-mobile-menu a:last-child { border-bottom: none; }
|
||||||
|
@media (max-width: 700px) {
|
||||||
|
.nav-links, .nav-cta { display: none; }
|
||||||
|
.nav-mobile-toggle { display: block; }
|
||||||
|
.nav-mobile-menu.open { display: flex; }
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
HERO
|
||||||
|
============================ */
|
||||||
|
#hero {
|
||||||
|
min-height: 50vh;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
position: relative;
|
||||||
|
overflow: hidden;
|
||||||
|
background: linear-gradient(-45deg, #040810, #071428, #1e1b4b, #060f2a, #0c1a3a);
|
||||||
|
background-size: 400% 400%;
|
||||||
|
animation: mesh 18s ease infinite;
|
||||||
|
padding: 80px 0 72px;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
.hero-orb {
|
||||||
|
position: absolute;
|
||||||
|
border-radius: 50%;
|
||||||
|
pointer-events: none;
|
||||||
|
filter: blur(80px);
|
||||||
|
opacity: .45;
|
||||||
|
}
|
||||||
|
.hero-orb-1 {
|
||||||
|
width: 700px; height: 700px;
|
||||||
|
background: radial-gradient(circle, rgba(59,130,246,.4) 0%, transparent 70%);
|
||||||
|
top: -200px; left: -150px;
|
||||||
|
animation: float1 20s ease-in-out infinite;
|
||||||
|
}
|
||||||
|
.hero-orb-2 {
|
||||||
|
width: 600px; height: 600px;
|
||||||
|
background: radial-gradient(circle, rgba(139,92,246,.35) 0%, transparent 70%);
|
||||||
|
bottom: -180px; right: -100px;
|
||||||
|
animation: float2 24s ease-in-out infinite;
|
||||||
|
}
|
||||||
|
.hero-orb-3 {
|
||||||
|
width: 400px; height: 400px;
|
||||||
|
background: radial-gradient(circle, rgba(6,182,212,.25) 0%, transparent 70%);
|
||||||
|
top: 40%; left: 55%;
|
||||||
|
animation: float3 16s ease-in-out infinite;
|
||||||
|
}
|
||||||
|
#hero::after {
|
||||||
|
content: '';
|
||||||
|
position: absolute;
|
||||||
|
inset: 0;
|
||||||
|
background-image:
|
||||||
|
linear-gradient(rgba(59,130,246,.04) 1px, transparent 1px),
|
||||||
|
linear-gradient(90deg, rgba(59,130,246,.04) 1px, transparent 1px);
|
||||||
|
background-size: 60px 60px;
|
||||||
|
pointer-events: none;
|
||||||
|
}
|
||||||
|
.hero-inner {
|
||||||
|
position: relative;
|
||||||
|
z-index: 2;
|
||||||
|
animation: fadeSlideUp .7s ease both;
|
||||||
|
}
|
||||||
|
.hero-badge {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 8px;
|
||||||
|
background: rgba(59,130,246,.08);
|
||||||
|
border: 1px solid rgba(59,130,246,.2);
|
||||||
|
color: #93C5FD;
|
||||||
|
padding: 7px 18px;
|
||||||
|
border-radius: 999px;
|
||||||
|
font-size: 13px;
|
||||||
|
font-weight: 600;
|
||||||
|
letter-spacing: .02em;
|
||||||
|
margin-bottom: 28px;
|
||||||
|
backdrop-filter: blur(8px);
|
||||||
|
}
|
||||||
|
#hero h1 {
|
||||||
|
font-size: clamp(32px, 5vw, 56px);
|
||||||
|
font-weight: 900;
|
||||||
|
line-height: 1.08;
|
||||||
|
letter-spacing: -.03em;
|
||||||
|
margin-bottom: 18px;
|
||||||
|
color: #fff;
|
||||||
|
}
|
||||||
|
.hero-sub {
|
||||||
|
font-size: clamp(15px, 2vw, 18px);
|
||||||
|
color: #94A3B8;
|
||||||
|
max-width: 480px;
|
||||||
|
margin: 0 auto;
|
||||||
|
line-height: 1.7;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
PRICING GRID
|
||||||
|
============================ */
|
||||||
|
#pricing {
|
||||||
|
background: var(--bg);
|
||||||
|
padding: 40px 0 96px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.pricing-grid {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 280px 1fr 280px;
|
||||||
|
gap: 24px;
|
||||||
|
align-items: start;
|
||||||
|
margin-bottom: 48px;
|
||||||
|
}
|
||||||
|
@media (max-width: 900px) {
|
||||||
|
.pricing-grid {
|
||||||
|
grid-template-columns: 1fr;
|
||||||
|
max-width: 520px;
|
||||||
|
margin-left: auto;
|
||||||
|
margin-right: auto;
|
||||||
|
}
|
||||||
|
/* Reorder: Starter first on mobile */
|
||||||
|
.pricing-card--featured { order: -1; }
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Base card (Free + Pro — slightly muted) */
|
||||||
|
.pricing-card {
|
||||||
|
background: rgba(10,22,40,.7);
|
||||||
|
border: 1px solid rgba(255,255,255,.07);
|
||||||
|
border-radius: var(--radius-xl);
|
||||||
|
padding: 32px 26px 28px;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
gap: 0;
|
||||||
|
transition: border-color .2s, transform .2s;
|
||||||
|
backdrop-filter: blur(12px);
|
||||||
|
position: relative;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
.pricing-card:hover {
|
||||||
|
border-color: rgba(255,255,255,.14);
|
||||||
|
transform: translateY(-2px);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* FREE card — slightly smaller, muted accent */
|
||||||
|
.pricing-card--free {
|
||||||
|
opacity: .88;
|
||||||
|
}
|
||||||
|
.pricing-card--free::before {
|
||||||
|
content: '';
|
||||||
|
position: absolute;
|
||||||
|
top: 0; left: 0; right: 0;
|
||||||
|
height: 2px;
|
||||||
|
background: linear-gradient(90deg, rgba(34,197,94,.5), rgba(16,185,129,.3));
|
||||||
|
}
|
||||||
|
|
||||||
|
/* STARTER card — PROMINENT: gradient border animation, larger */
|
||||||
|
.pricing-card--featured {
|
||||||
|
border: none;
|
||||||
|
background: linear-gradient(var(--card2), var(--card2)) padding-box,
|
||||||
|
linear-gradient(135deg, var(--arc), var(--purple), var(--cyan), var(--arc)) border-box;
|
||||||
|
background-size: 100% 100%, 300% 300%;
|
||||||
|
animation: gradientBorder 4s ease infinite;
|
||||||
|
border-radius: var(--radius-xl);
|
||||||
|
border: 2px solid transparent;
|
||||||
|
position: relative;
|
||||||
|
padding: 40px 30px 36px;
|
||||||
|
box-shadow: 0 0 60px rgba(59,130,246,.18), 0 32px 64px rgba(0,0,0,.5);
|
||||||
|
animation: borderGlow 3s ease-in-out infinite;
|
||||||
|
}
|
||||||
|
/* Re-apply gradient border via pseudo */
|
||||||
|
.pricing-card--featured::after {
|
||||||
|
content: '';
|
||||||
|
position: absolute;
|
||||||
|
inset: 0;
|
||||||
|
border-radius: var(--radius-xl);
|
||||||
|
padding: 2px;
|
||||||
|
background: linear-gradient(135deg, var(--arc), var(--purple), var(--cyan), var(--arc));
|
||||||
|
background-size: 300% 300%;
|
||||||
|
animation: gradientBorder 4s ease infinite;
|
||||||
|
-webkit-mask: linear-gradient(#fff 0 0) content-box, linear-gradient(#fff 0 0);
|
||||||
|
-webkit-mask-composite: destination-out;
|
||||||
|
mask-composite: exclude;
|
||||||
|
pointer-events: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* PRO card — gold/amber accent */
|
||||||
|
.pricing-card--pro {
|
||||||
|
border-color: rgba(245,158,11,.15);
|
||||||
|
}
|
||||||
|
.pricing-card--pro:hover { border-color: rgba(245,158,11,.3); }
|
||||||
|
.pricing-card--pro::before {
|
||||||
|
content: '';
|
||||||
|
position: absolute;
|
||||||
|
top: 0; left: 0; right: 0;
|
||||||
|
height: 2px;
|
||||||
|
background: linear-gradient(90deg, var(--warn), #f97316, var(--warn));
|
||||||
|
background-size: 200%;
|
||||||
|
animation: shimmer 3s linear infinite;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* "Meest gekozen" badge */
|
||||||
|
.most-chosen {
|
||||||
|
position: absolute;
|
||||||
|
top: -16px;
|
||||||
|
left: 50%;
|
||||||
|
transform: translateX(-50%);
|
||||||
|
background: linear-gradient(135deg, var(--arc), var(--purple));
|
||||||
|
color: #fff;
|
||||||
|
font-size: 11px;
|
||||||
|
font-weight: 800;
|
||||||
|
letter-spacing: .08em;
|
||||||
|
text-transform: uppercase;
|
||||||
|
padding: 5px 20px;
|
||||||
|
border-radius: 999px;
|
||||||
|
white-space: nowrap;
|
||||||
|
box-shadow: 0 4px 20px rgba(59,130,246,.4);
|
||||||
|
z-index: 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
.pricing-tier {
|
||||||
|
font-size: 11px;
|
||||||
|
font-weight: 700;
|
||||||
|
letter-spacing: .12em;
|
||||||
|
text-transform: uppercase;
|
||||||
|
color: var(--muted);
|
||||||
|
margin-bottom: 14px;
|
||||||
|
}
|
||||||
|
.pricing-card--featured .pricing-tier { color: var(--arc); }
|
||||||
|
.pricing-card--pro .pricing-tier { color: var(--warn); }
|
||||||
|
|
||||||
|
.pricing-price {
|
||||||
|
display: flex;
|
||||||
|
align-items: baseline;
|
||||||
|
gap: 6px;
|
||||||
|
margin-bottom: 6px;
|
||||||
|
}
|
||||||
|
.pricing-amount {
|
||||||
|
font-size: 44px;
|
||||||
|
font-weight: 900;
|
||||||
|
color: var(--txt);
|
||||||
|
line-height: 1;
|
||||||
|
}
|
||||||
|
.pricing-card--featured .pricing-amount {
|
||||||
|
background: linear-gradient(135deg, #fff 0%, #93c5fd 50%, #c4b5fd 100%);
|
||||||
|
-webkit-background-clip: text;
|
||||||
|
-webkit-text-fill-color: transparent;
|
||||||
|
background-clip: text;
|
||||||
|
font-size: 52px;
|
||||||
|
}
|
||||||
|
.pricing-card--pro .pricing-amount {
|
||||||
|
background: linear-gradient(135deg, var(--warn), #f97316);
|
||||||
|
-webkit-background-clip: text;
|
||||||
|
-webkit-text-fill-color: transparent;
|
||||||
|
background-clip: text;
|
||||||
|
}
|
||||||
|
.pricing-per { font-size: 15px; color: var(--muted); }
|
||||||
|
|
||||||
|
.pricing-tagline {
|
||||||
|
font-size: 13px;
|
||||||
|
color: var(--muted);
|
||||||
|
margin-bottom: 22px;
|
||||||
|
line-height: 1.55;
|
||||||
|
}
|
||||||
|
.pricing-card--featured .pricing-tagline { font-size: 14px; color: #94A3B8; }
|
||||||
|
|
||||||
|
/* Plan bullets (short feature summary) */
|
||||||
|
.plan-bullets {
|
||||||
|
list-style: none;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
gap: 8px;
|
||||||
|
margin-bottom: 22px;
|
||||||
|
padding-bottom: 22px;
|
||||||
|
border-bottom: 1px solid rgba(255,255,255,.06);
|
||||||
|
}
|
||||||
|
.plan-bullets li {
|
||||||
|
font-size: 14px;
|
||||||
|
color: var(--txt);
|
||||||
|
display: flex;
|
||||||
|
align-items: flex-start;
|
||||||
|
gap: 9px;
|
||||||
|
line-height: 1.5;
|
||||||
|
}
|
||||||
|
.plan-bullets li::before {
|
||||||
|
content: '→';
|
||||||
|
color: var(--arc);
|
||||||
|
font-weight: 700;
|
||||||
|
flex-shrink: 0;
|
||||||
|
margin-top: 1px;
|
||||||
|
}
|
||||||
|
.pricing-card--pro .plan-bullets li::before { color: var(--warn); }
|
||||||
|
.pricing-card--free .plan-bullets li::before { color: var(--ok); }
|
||||||
|
|
||||||
|
/* Feature checklist */
|
||||||
|
.feature-list {
|
||||||
|
list-style: none;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
gap: 10px;
|
||||||
|
margin-bottom: 28px;
|
||||||
|
flex: 1;
|
||||||
|
}
|
||||||
|
.feature-list li {
|
||||||
|
font-size: 13px;
|
||||||
|
color: var(--muted);
|
||||||
|
display: flex;
|
||||||
|
align-items: flex-start;
|
||||||
|
gap: 10px;
|
||||||
|
line-height: 1.45;
|
||||||
|
}
|
||||||
|
.ico {
|
||||||
|
flex-shrink: 0;
|
||||||
|
font-size: 13px;
|
||||||
|
font-weight: 900;
|
||||||
|
margin-top: 1px;
|
||||||
|
width: 16px;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
.ico--yes { color: var(--ok); }
|
||||||
|
.ico--no { color: rgba(148,163,184,.3); }
|
||||||
|
|
||||||
|
/* Highlighted features on starter */
|
||||||
|
.pricing-card--featured .feature-list li {
|
||||||
|
font-size: 14px;
|
||||||
|
color: #94A3B8;
|
||||||
|
}
|
||||||
|
.pricing-card--featured .ico--yes { color: var(--ok); }
|
||||||
|
|
||||||
|
/* CTA buttons */
|
||||||
|
.pricing-cta {
|
||||||
|
display: block;
|
||||||
|
text-align: center;
|
||||||
|
margin-top: auto;
|
||||||
|
padding: 13px 24px;
|
||||||
|
border-radius: var(--radius);
|
||||||
|
font-size: 15px;
|
||||||
|
font-weight: 700;
|
||||||
|
transition: all .2s;
|
||||||
|
text-decoration: none;
|
||||||
|
}
|
||||||
|
.pricing-cta--ghost {
|
||||||
|
background: transparent;
|
||||||
|
color: var(--muted);
|
||||||
|
border: 1px solid rgba(255,255,255,.08);
|
||||||
|
}
|
||||||
|
.pricing-cta--ghost:hover { background: rgba(255,255,255,.05); color: var(--txt); border-color: rgba(255,255,255,.15); }
|
||||||
|
.pricing-cta--primary {
|
||||||
|
background: linear-gradient(135deg, var(--arc), var(--purple));
|
||||||
|
color: #fff;
|
||||||
|
box-shadow: 0 0 30px rgba(59,130,246,.4);
|
||||||
|
padding: 15px 28px;
|
||||||
|
font-size: 16px;
|
||||||
|
}
|
||||||
|
.pricing-cta--primary:hover { box-shadow: 0 0 56px rgba(59,130,246,.6); transform: translateY(-2px); color: #fff; }
|
||||||
|
.pricing-cta--amber {
|
||||||
|
background: transparent;
|
||||||
|
color: var(--warn);
|
||||||
|
border: 1.5px solid rgba(245,158,11,.4);
|
||||||
|
}
|
||||||
|
.pricing-cta--amber:hover { background: rgba(245,158,11,.08); border-color: var(--warn); box-shadow: 0 0 20px rgba(245,158,11,.2); transform: translateY(-2px); color: var(--warn); }
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
PAYMENT NOTE
|
||||||
|
============================ */
|
||||||
|
.payment-note {
|
||||||
|
text-align: center;
|
||||||
|
font-size: 14px;
|
||||||
|
color: var(--muted);
|
||||||
|
padding: 20px 0 0;
|
||||||
|
line-height: 1.7;
|
||||||
|
border-top: 1px solid rgba(255,255,255,.05);
|
||||||
|
margin-top: 4px;
|
||||||
|
}
|
||||||
|
.payment-note strong { color: var(--txt); }
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
FAQ
|
||||||
|
============================ */
|
||||||
|
#faq {
|
||||||
|
background: rgba(10,22,40,.5);
|
||||||
|
padding: 88px 0;
|
||||||
|
}
|
||||||
|
.faq-header { margin-bottom: 40px; }
|
||||||
|
.faq-list {
|
||||||
|
max-width: 800px;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
border: 1px solid rgba(59,130,246,.1);
|
||||||
|
border-radius: var(--radius-xl);
|
||||||
|
overflow: hidden;
|
||||||
|
background: rgba(10,22,40,.6);
|
||||||
|
backdrop-filter: blur(16px);
|
||||||
|
}
|
||||||
|
.faq-item { border-bottom: 1px solid rgba(255,255,255,.05); }
|
||||||
|
.faq-item:last-child { border-bottom: none; }
|
||||||
|
.faq-q {
|
||||||
|
width: 100%;
|
||||||
|
background: none;
|
||||||
|
border: none;
|
||||||
|
color: var(--txt);
|
||||||
|
font-family: var(--font);
|
||||||
|
font-size: 15px;
|
||||||
|
font-weight: 600;
|
||||||
|
padding: 22px 28px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: space-between;
|
||||||
|
gap: 16px;
|
||||||
|
cursor: pointer;
|
||||||
|
text-align: left;
|
||||||
|
transition: background .15s, color .15s;
|
||||||
|
}
|
||||||
|
.faq-q:hover { background: rgba(59,130,246,.04); }
|
||||||
|
.faq-icon { font-size: 20px; color: var(--arc); flex-shrink: 0; transition: transform .2s; font-weight: 300; line-height: 1; }
|
||||||
|
.faq-a {
|
||||||
|
display: none;
|
||||||
|
padding: 0 28px 22px;
|
||||||
|
font-size: 14px;
|
||||||
|
color: var(--muted);
|
||||||
|
line-height: 1.75;
|
||||||
|
}
|
||||||
|
.faq-item.open .faq-a { display: block; }
|
||||||
|
.faq-item.open .faq-icon { transform: rotate(45deg); }
|
||||||
|
.faq-item.open .faq-q { color: var(--arc); }
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
SCROLL REVEAL
|
||||||
|
============================ */
|
||||||
|
.reveal { opacity: 0; transform: translateY(24px); transition: opacity .6s ease, transform .6s ease; }
|
||||||
|
.reveal.visible { opacity: 1; transform: translateY(0); }
|
||||||
|
|
||||||
|
/* ============================
|
||||||
|
FOOTER
|
||||||
|
============================ */
|
||||||
|
footer {
|
||||||
|
background: var(--card);
|
||||||
|
border-top: 1px solid rgba(59,130,246,.08);
|
||||||
|
padding: 56px 0 32px;
|
||||||
|
}
|
||||||
|
.footer-inner {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1.5fr 1fr 1fr 1fr;
|
||||||
|
gap: 40px;
|
||||||
|
margin-bottom: 40px;
|
||||||
|
}
|
||||||
|
.footer-logo {
|
||||||
|
font-size: 16px;
|
||||||
|
font-weight: 800;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 8px;
|
||||||
|
color: var(--txt);
|
||||||
|
margin-bottom: 12px;
|
||||||
|
}
|
||||||
|
.footer-brand p { color: var(--muted); font-size: 13px; max-width: 240px; line-height: 1.6; }
|
||||||
|
.footer-col-title { font-size: 12px; font-weight: 700; text-transform: uppercase; letter-spacing: .08em; color: var(--muted); margin-bottom: 16px; }
|
||||||
|
.footer-links { list-style: none; display: flex; flex-direction: column; gap: 10px; }
|
||||||
|
.footer-links a { color: var(--muted); font-size: 14px; transition: color .15s; }
|
||||||
|
.footer-links a:hover { color: var(--txt); }
|
||||||
|
.footer-bottom {
|
||||||
|
border-top: 1px solid rgba(255,255,255,.05);
|
||||||
|
padding-top: 24px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: space-between;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
gap: 12px;
|
||||||
|
}
|
||||||
|
.footer-copy { color: var(--muted); font-size: 13px; }
|
||||||
|
.footer-copy a { color: var(--muted); }
|
||||||
|
.footer-copy a:hover { color: var(--arc); }
|
||||||
|
@media (max-width: 720px) { .footer-inner { grid-template-columns: 1fr 1fr; } }
|
||||||
|
@media (max-width: 480px) { .footer-inner { grid-template-columns: 1fr; gap: 28px; } }
|
||||||
|
.lang-toggle{background:transparent;border:1px solid rgba(59,130,246,.5);color:#9CA3AF;padding:5px 12px;border-radius:20px;cursor:pointer;font-size:12px;font-weight:600;transition:all .2s;margin-right:8px;}</style>
|
||||||
|
|
||||||
|
<!-- GA4 -->
|
||||||
|
<script async src="https://www.googletagmanager.com/gtag/js?id=G-JBWZWZMKBC"></script>
|
||||||
|
<script>window.dataLayer=window.dataLayer||[];function gtag(){dataLayer.push(arguments);}gtag('js',new Date());gtag('config','G-JBWZWZMKBC');</script>
|
||||||
|
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
|
||||||
|
<!-- NAV -->
|
||||||
|
<nav>
|
||||||
|
<div class="container nav-inner">
|
||||||
|
<a href="index.html" class="nav-logo">
|
||||||
|
<span class="nav-logo-icon">🎓</span>
|
||||||
|
Atlas Academy
|
||||||
|
</a>
|
||||||
|
<ul class="nav-links">
|
||||||
|
<li><a href="cursussen.html">Cursussen</a></li>
|
||||||
|
<li><a href="leerpad.html">Leerpad</a></li>
|
||||||
|
<li><a href="coaching.html">Coaching</a></li>
|
||||||
|
<li><a href="pricing.html" class="active">Prijzen</a></li>
|
||||||
|
<li><a href="shop.html">Shop</a></li>
|
||||||
|
<li><a href="over.html">Over</a></li>
|
||||||
|
<li><a href="/web/login?redirect=%2Fslides">Inloggen</a></li>
|
||||||
|
</ul>
|
||||||
|
<button class="lang-toggle" onclick="toggleLang()" id="langBtn">EN</button><a class="btn btn-primary nav-cta" href="mailto:info@atlascorporation.nl?subject=Atlas+Academy">Start gratis →</a>
|
||||||
|
<button class="nav-mobile-toggle" onclick="toggleMenu()" aria-label="Menu openen">☰</button>
|
||||||
|
</div>
|
||||||
|
<div class="nav-mobile-menu" id="mobileMenu">
|
||||||
|
<a href="cursussen.html">Cursussen</a>
|
||||||
|
<a href="leerpad.html">Leerpad</a>
|
||||||
|
<a href="coaching.html">Coaching</a>
|
||||||
|
<a href="pricing.html">Prijzen</a>
|
||||||
|
<a href="shop.html">Shop</a>
|
||||||
|
<a href="over.html">Over</a>
|
||||||
|
<a href="/web/login?redirect=%2Fslides">Inloggen</a>
|
||||||
|
<a href="mailto:info@atlascorporation.nl?subject=Atlas+Academy">Start gratis</a>
|
||||||
|
</div>
|
||||||
|
</nav>
|
||||||
|
|
||||||
|
<!-- HERO -->
|
||||||
|
<section id="hero">
|
||||||
|
<div class="hero-orb hero-orb-1"></div>
|
||||||
|
<div class="hero-orb hero-orb-2"></div>
|
||||||
|
<div class="hero-orb hero-orb-3"></div>
|
||||||
|
<div class="container">
|
||||||
|
<div class="hero-inner">
|
||||||
|
<div class="hero-badge">Prijzen</div>
|
||||||
|
<h1 class="gradient-text">Transparante prijzen.<br>Geen verborgen kosten.</h1>
|
||||||
|
<p class="hero-sub">Kies het plan dat past bij jouw fase. Maandelijks opzegbaar — geen jaarcontract vereist.</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<!-- PRICING TABLE -->
|
||||||
|
<section id="pricing">
|
||||||
|
<div class="container">
|
||||||
|
|
||||||
|
<div class="pricing-grid reveal">
|
||||||
|
|
||||||
|
<!-- ===== FREE ===== -->
|
||||||
|
<div class="pricing-card pricing-card--free">
|
||||||
|
<div class="pricing-tier">Free</div>
|
||||||
|
<div class="pricing-price">
|
||||||
|
<span class="pricing-amount" style="font-size:40px;">Gratis</span>
|
||||||
|
</div>
|
||||||
|
<p class="pricing-tagline">Begin zonder risico. Kijk of de aanpak bij je past.</p>
|
||||||
|
|
||||||
|
<ul class="plan-bullets">
|
||||||
|
<li>3 modules gratis</li>
|
||||||
|
<li>BiSL Foundation preview (lessen 1–3)</li>
|
||||||
|
<li>Geen credit card nodig</li>
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
<ul class="feature-list">
|
||||||
|
<li><span class="ico ico--yes">✓</span> BiSL les 1–3</li>
|
||||||
|
<li><span class="ico ico--yes">✓</span> Cursuscatalogus</li>
|
||||||
|
<li><span class="ico ico--yes">✓</span> Leerpad inzien</li>
|
||||||
|
<li><span class="ico ico--no">✕</span> Groepscoaching</li>
|
||||||
|
<li><span class="ico ico--no">✕</span> Alle modules</li>
|
||||||
|
<li><span class="ico ico--no">✕</span> 1-op-1 sessie</li>
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
<a href="mailto:info@atlascorporation.nl?subject=Atlas+Academy+Free" class="pricing-cta pricing-cta--ghost">
|
||||||
|
Start gratis
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- ===== STARTER (FEATURED — center, prominent) ===== -->
|
||||||
|
<div class="pricing-card pricing-card--featured">
|
||||||
|
<span class="most-chosen">⭐ Meest gekozen</span>
|
||||||
|
<div class="pricing-tier">Starter</div>
|
||||||
|
<div class="pricing-price">
|
||||||
|
<span class="pricing-amount">€20</span>
|
||||||
|
<span class="pricing-per">/ maand</span>
|
||||||
|
</div>
|
||||||
|
<p class="pricing-tagline">Alles wat je nodig hebt om serieus te bouwen en te groeien.</p>
|
||||||
|
|
||||||
|
<ul class="plan-bullets">
|
||||||
|
<li>Alle 25 modules</li>
|
||||||
|
<li>8 complete cursussen</li>
|
||||||
|
<li>BiSL examentrainer (97 vragen)</li>
|
||||||
|
<li>Groepscoaching 1×/maand — Zoom 45 min, opname</li>
|
||||||
|
<li>12-weken leerpad</li>
|
||||||
|
<li>Community toegang</li>
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
<ul class="feature-list">
|
||||||
|
<li><span class="ico ico--yes">✓</span> Alles uit Free</li>
|
||||||
|
<li><span class="ico ico--yes">✓</span> Alle modules</li>
|
||||||
|
<li><span class="ico ico--yes">✓</span> BiSL examentrainer</li>
|
||||||
|
<li><span class="ico ico--yes">✓</span> Groepscoaching</li>
|
||||||
|
<li><span class="ico ico--yes">✓</span> 12-weken leerpad</li>
|
||||||
|
<li><span class="ico ico--no">✕</span> 1-op-1 sessie</li>
|
||||||
|
<li><span class="ico ico--no">✕</span> Persoonlijk traject</li>
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
<a href="mailto:info@atlascorporation.nl?subject=Atlas+Academy+Starter" class="pricing-cta pricing-cta--primary">
|
||||||
|
Word Starter →
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- ===== PRO (amber/gold accent) ===== -->
|
||||||
|
<div class="pricing-card pricing-card--pro">
|
||||||
|
<div class="pricing-tier">Pro</div>
|
||||||
|
<div class="pricing-price">
|
||||||
|
<span class="pricing-amount">€49</span>
|
||||||
|
<span class="pricing-per">/ maand</span>
|
||||||
|
</div>
|
||||||
|
<p class="pricing-tagline">Voor ondernemers die sneller willen groeien met persoonlijke begeleiding.</p>
|
||||||
|
|
||||||
|
<ul class="plan-bullets">
|
||||||
|
<li>Alles uit Starter</li>
|
||||||
|
<li>1-op-1 sessie 30 min/maand (met Chaib)</li>
|
||||||
|
<li>Persoonlijk leertraject</li>
|
||||||
|
<li>Prioriteit e-mail support</li>
|
||||||
|
<li>Early access nieuwe cursussen</li>
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
<ul class="feature-list">
|
||||||
|
<li><span class="ico ico--yes">✓</span> Alles uit Starter</li>
|
||||||
|
<li><span class="ico ico--yes">✓</span> 1-op-1 sessie</li>
|
||||||
|
<li><span class="ico ico--yes">✓</span> Persoonlijk traject</li>
|
||||||
|
<li><span class="ico ico--yes">✓</span> Prioriteit support</li>
|
||||||
|
<li><span class="ico ico--yes">✓</span> Early access nieuwe cursussen</li>
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
<a href="mailto:info@atlascorporation.nl?subject=Atlas+Academy+Pro" class="pricing-cta pricing-cta--amber">
|
||||||
|
Word Pro →
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div><!-- /pricing-grid -->
|
||||||
|
|
||||||
|
<!-- PAYMENT NOTE -->
|
||||||
|
<div class="payment-note reveal">
|
||||||
|
<strong>Alle betalingen via factuur of automatische incasso.</strong>
|
||||||
|
Maandelijks opzegbaar — geen verborgen kosten, geen jaarcontract vereist.
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<!-- FAQ -->
|
||||||
|
<section id="faq">
|
||||||
|
<div class="container">
|
||||||
|
<div class="faq-header reveal">
|
||||||
|
<span class="section-label">Veelgestelde vragen</span>
|
||||||
|
<h2 class="section-title">Alles over onze prijzen</h2>
|
||||||
|
</div>
|
||||||
|
<div class="faq-list reveal">
|
||||||
|
|
||||||
|
<div class="faq-item">
|
||||||
|
<button class="faq-q" onclick="toggleFaq(this)">
|
||||||
|
<span>Krijg ik korting als ik jaarlijks betaal?</span>
|
||||||
|
<span class="faq-icon">+</span>
|
||||||
|
</button>
|
||||||
|
<div class="faq-a">
|
||||||
|
Ja. Bij jaarlijkse betaling ontvang je twee maanden gratis — effectief betaal je voor 10 maanden in plaats van 12. Vraag het jaarplan aan via <a href="mailto:info@atlascorporation.nl?subject=Atlas+Academy+Jaarplan">info@atlascorporation.nl</a> en wij sturen je een offerte.
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="faq-item">
|
||||||
|
<button class="faq-q" onclick="toggleFaq(this)">
|
||||||
|
<span>Kan ik mijn geld terug krijgen als het niets voor mij is?</span>
|
||||||
|
<span class="faq-icon">+</span>
|
||||||
|
</button>
|
||||||
|
<div class="faq-a">
|
||||||
|
We hanteren geen automatische restitutie, maar denken altijd mee. Als je binnen de eerste 14 dagen aangeeft dat de inhoud niet aansluit bij je verwachting, nemen we het op. Stuur een mail naar <a href="mailto:info@atlascorporation.nl?subject=Atlas+Academy+Terugbetaling">info@atlascorporation.nl</a> met een korte toelichting.
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="faq-item">
|
||||||
|
<button class="faq-q" onclick="toggleFaq(this)">
|
||||||
|
<span>Is er een groepskorting voor teams of organisaties?</span>
|
||||||
|
<span class="faq-icon">+</span>
|
||||||
|
</button>
|
||||||
|
<div class="faq-a">
|
||||||
|
Ja. Vanaf 3 medewerkers bieden we een maatwerkprijs. Denk aan een gezamenlijk leerpad, groepscoaching op maat en één centrale facturering. Neem contact op via <a href="mailto:info@atlascorporation.nl?subject=Atlas+Academy+Groepskorting">info@atlascorporation.nl</a> voor een offerte op maat.
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="faq-item">
|
||||||
|
<button class="faq-q" onclick="toggleFaq(this)">
|
||||||
|
<span>Geldt er een studentenkorting?</span>
|
||||||
|
<span class="faq-icon">+</span>
|
||||||
|
</button>
|
||||||
|
<div class="faq-a">
|
||||||
|
Studenten en BBZ-deelnemers komen in aanmerking voor een gereduceerd tarief. Stuur een bewijs van inschrijving of een BBZ-toekenning mee in je mail en we regelen een aangepast abonnement. We geloven dat prijs geen drempel mag zijn voor praktische kennis.
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="faq-item">
|
||||||
|
<button class="faq-q" onclick="toggleFaq(this)">
|
||||||
|
<span>Hoe zeg ik mijn abonnement op?</span>
|
||||||
|
<span class="faq-icon">+</span>
|
||||||
|
</button>
|
||||||
|
<div class="faq-a">
|
||||||
|
Stuur een e-mail naar <a href="mailto:info@atlascorporation.nl?subject=Atlas+Academy+Opzeggen">info@atlascorporation.nl</a> vóór de volgende factuurdatum. Geen formulieren, geen gedoe. Je behoudt toegang tot het einde van de lopende betaalperiode.
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<!-- FOOTER -->
|
||||||
|
<footer>
|
||||||
|
<div class="container">
|
||||||
|
<div class="footer-inner">
|
||||||
|
<div class="footer-brand">
|
||||||
|
<span class="footer-logo">🎓 Atlas Academy</span>
|
||||||
|
<p>Praktische kennis voor ondernemers die bouwen. Onderdeel van Atlas Corporation.</p>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<div class="footer-col-title">Cursussen</div>
|
||||||
|
<ul class="footer-links">
|
||||||
|
<li><a href="/cursussen/bisl.html">BiSL Foundation</a></li>
|
||||||
|
<li><a href="/leerplatform.html">IT Basis</a></li>
|
||||||
|
<li><a href="/cursussen/startup.html">Startup & Groei</a></li>
|
||||||
|
<li><a href="/leerplatform.html">Sales & Marketing</a></li>
|
||||||
|
<li><a href="cursussen.html">Alle cursussen →</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<div class="footer-col-title">Platform</div>
|
||||||
|
<ul class="footer-links">
|
||||||
|
<li><a href="cursussen.html">Cursussen</a></li>
|
||||||
|
<li><a href="leerpad.html">Leerpad</a></li>
|
||||||
|
<li><a href="coaching.html">Coaching</a></li>
|
||||||
|
<li><a href="pricing.html">Prijzen</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<div class="footer-col-title">Contact</div>
|
||||||
|
<ul class="footer-links">
|
||||||
|
<li><a href="mailto:info@atlascorporation.nl">info@atlascorporation.nl</a></li>
|
||||||
|
<li><a href="https://atlascorporation.nl" target="_blank" rel="noopener">atlascorporation.nl</a></li>
|
||||||
|
<li><a href="mailto:info@atlascorporation.nl?subject=Atlas+Academy">Aanmelden</a></li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="footer-bottom">
|
||||||
|
<p class="footer-copy">© 2026 Atlas Academy · onderdeel van <a href="https://atlascorporation.nl" target="_blank" rel="noopener">Atlas Corporation</a></p>
|
||||||
|
<p class="footer-copy" style="font-size:12px;">KvK · BTW · info@atlascorporation.nl</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</footer>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
function toggleMenu() {
|
||||||
|
document.getElementById('mobileMenu').classList.toggle('open');
|
||||||
|
}
|
||||||
|
function toggleFaq(btn) {
|
||||||
|
var item = btn.closest('.faq-item');
|
||||||
|
var isOpen = item.classList.contains('open');
|
||||||
|
document.querySelectorAll('.faq-item.open').forEach(function(el) { el.classList.remove('open'); });
|
||||||
|
if (!isOpen) item.classList.add('open');
|
||||||
|
}
|
||||||
|
|
||||||
|
// Scroll reveal
|
||||||
|
(function() {
|
||||||
|
var els = document.querySelectorAll('.reveal');
|
||||||
|
var obs = new IntersectionObserver(function(entries) {
|
||||||
|
entries.forEach(function(e) {
|
||||||
|
if (e.isIntersecting) { e.target.classList.add('visible'); obs.unobserve(e.target); }
|
||||||
|
});
|
||||||
|
}, { threshold: 0.1 });
|
||||||
|
els.forEach(function(el, i) {
|
||||||
|
el.style.transitionDelay = (i * 0.08) + 's';
|
||||||
|
obs.observe(el);
|
||||||
|
});
|
||||||
|
})();
|
||||||
|
</script>
|
||||||
|
<script>function toggleLang(){var isNL=document.documentElement.lang!=="en";var lang=isNL?"en":"nl";document.documentElement.lang=lang;document.getElementById("langBtn").textContent=isNL?"NL":"EN";document.querySelectorAll("[data-nl]").forEach(function(el){var v=el.getAttribute("data-"+lang);if(v)el.innerHTML=v;});localStorage.setItem("aa_lang",lang);}(function(){if(localStorage.getItem("aa_lang")==="en")toggleLang();})();</script></body>
|
||||||
|
</html>
|
||||||
204
static/shop.html
Normal file
204
static/shop.html
Normal file
|
|
@ -0,0 +1,204 @@
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html lang="nl">
|
||||||
|
<head>
|
||||||
|
<meta charset="UTF-8">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
|
<meta name="description" content="Atlas Academy Shop — refurbished zakelijke laptops, desktops, monitoren en kassasystemen. Getest, 24 maanden garantie, afhalen in Tilburg. Direct bestellen op atlasworks.nl.">
|
||||||
|
<meta name="robots" content="index, follow">
|
||||||
|
<meta property="og:title" content="Atlas Academy Shop — Hardware voor operators">
|
||||||
|
<meta property="og:description" content="Refurbished zakelijke laptops, desktops en kassasystemen. Getest, 24 maanden garantie, afhalen in Tilburg.">
|
||||||
|
<meta property="og:image" content="https://atlasacademy.nl/assets/logo.png">
|
||||||
|
<meta property="og:url" content="https://atlasacademy.nl/shop.html">
|
||||||
|
<title>Shop — Atlas Academy</title>
|
||||||
|
<script async src="https://www.googletagmanager.com/gtag/js?id=G-JBWZWZMKBC"></script>
|
||||||
|
<script>window.dataLayer=window.dataLayer||[];function gtag(){dataLayer.push(arguments);}gtag('js',new Date());gtag('config','G-JBWZWZMKBC');</script>
|
||||||
|
<style>
|
||||||
|
:root{--bg:#080C18;--card:#0B1220;--border:rgba(55,65,81,.5);--accent:#3B82F6;--purple:#8B5CF6;--green:#22C55E;--txt:#E2E8F0;--muted:#6B7280;--font:-apple-system,BlinkMacSystemFont,'Segoe UI',Roboto,sans-serif;--radius:10px;--radius-lg:16px}
|
||||||
|
*,*::before,*::after{box-sizing:border-box;margin:0;padding:0}
|
||||||
|
html{scroll-behavior:smooth}
|
||||||
|
body{background:var(--bg);color:var(--txt);font-family:var(--font);font-size:16px;line-height:1.7;-webkit-font-smoothing:antialiased}
|
||||||
|
a{color:var(--accent);text-decoration:none}
|
||||||
|
a:hover{color:#93C5FD}
|
||||||
|
img{max-width:100%;display:block}
|
||||||
|
.container{width:100%;max-width:1140px;margin:0 auto;padding:0 24px}
|
||||||
|
nav{position:sticky;top:0;z-index:100;background:rgba(8,12,24,.85);backdrop-filter:blur(20px);-webkit-backdrop-filter:blur(20px);border-bottom:1px solid var(--border);height:64px;display:flex;align-items:center}
|
||||||
|
.nav-inner{display:flex;align-items:center;justify-content:space-between;width:100%;max-width:1140px;margin:0 auto;padding:0 24px}
|
||||||
|
.nav-logo{display:flex;align-items:center;gap:10px;color:#fff;font-weight:700;font-size:17px;text-decoration:none}
|
||||||
|
.nav-logo img{width:32px;height:32px;object-fit:contain;filter:brightness(0) invert(1)}
|
||||||
|
.nav-links{display:flex;align-items:center;gap:32px;list-style:none}
|
||||||
|
.nav-links a{color:rgba(255,255,255,.7);font-size:14px;font-weight:500}
|
||||||
|
.nav-links a:hover{color:#fff}
|
||||||
|
.nav-cta .btn{padding:9px 18px;font-size:13px}
|
||||||
|
.btn{display:inline-flex;align-items:center;gap:8px;padding:14px 28px;border-radius:var(--radius);font-size:15px;font-weight:700;cursor:pointer;transition:all .25s;border:none;text-decoration:none;white-space:nowrap}
|
||||||
|
.btn-primary{background:linear-gradient(135deg,var(--accent),var(--purple));color:#fff;box-shadow:0 0 32px rgba(59,130,246,.4)}
|
||||||
|
.btn-primary:hover{transform:translateY(-2px);box-shadow:0 0 48px rgba(59,130,246,.6);color:#fff}
|
||||||
|
.btn-lg{padding:18px 36px;font-size:17px}
|
||||||
|
.btn-block{width:100%;justify-content:center}
|
||||||
|
.gradient-text{background:linear-gradient(135deg,#fff 0,#93C5FD 50%,#C4B5FD 100%);-webkit-background-clip:text;-webkit-text-fill-color:transparent;background-clip:text}
|
||||||
|
.hero{padding:72px 0 32px;text-align:center}
|
||||||
|
.hero-label{font-size:12px;font-weight:700;letter-spacing:.12em;text-transform:uppercase;color:var(--accent);margin-bottom:12px}
|
||||||
|
.hero h1{font-size:clamp(28px,4vw,48px);font-weight:900;margin-bottom:16px}
|
||||||
|
.hero p{color:var(--muted);font-size:18px;max-width:640px;margin:0 auto}
|
||||||
|
.trust-bar{display:flex;justify-content:center;gap:40px;flex-wrap:wrap;padding:24px 0;border-bottom:1px solid var(--border);margin-bottom:40px}
|
||||||
|
.trust-item{display:flex;align-items:center;gap:8px;color:var(--muted);font-size:14px;font-weight:500}
|
||||||
|
.trust-item span{font-size:20px}
|
||||||
|
.filters{display:flex;flex-wrap:wrap;gap:10px;justify-content:center;margin-bottom:32px}
|
||||||
|
.filter-btn{padding:9px 18px;border-radius:999px;border:1px solid var(--border);background:var(--card);color:var(--muted);font-size:13px;font-weight:700;cursor:pointer;transition:all .2s}
|
||||||
|
.filter-btn:hover{color:#fff;border-color:rgba(255,255,255,.3)}
|
||||||
|
.filter-btn.active{background:linear-gradient(135deg,var(--accent),var(--purple));color:#fff;border-color:transparent}
|
||||||
|
.shop-section{padding:0 0 80px}
|
||||||
|
.product-grid{display:grid;grid-template-columns:repeat(3,1fr);gap:24px}
|
||||||
|
.card{display:flex;flex-direction:column;background:var(--card);border:1px solid var(--border);border-radius:var(--radius-lg);overflow:hidden;transition:transform .2s,border-color .2s}
|
||||||
|
.card:hover{transform:translateY(-4px);border-color:rgba(59,130,246,.45)}
|
||||||
|
.card-img{aspect-ratio:4/3;background:#0a0f1c;display:flex;align-items:center;justify-content:center;overflow:hidden;border-bottom:1px solid var(--border)}
|
||||||
|
.card-img img{width:100%;height:100%;object-fit:contain;padding:16px}
|
||||||
|
.card-body{display:flex;flex-direction:column;flex:1;padding:18px 18px 20px}
|
||||||
|
.card-badge{align-self:flex-start;font-size:10px;font-weight:800;letter-spacing:.06em;text-transform:uppercase;padding:4px 10px;border-radius:999px;margin-bottom:10px;background:rgba(59,130,246,.12);color:#93C5FD;border:1px solid rgba(59,130,246,.25)}
|
||||||
|
.card-badge.pos{background:rgba(139,92,246,.12);color:#C4B5FD;border-color:rgba(139,92,246,.25)}
|
||||||
|
.card-badge.bundle{background:rgba(34,197,94,.12);color:#86EFAC;border-color:rgba(34,197,94,.25)}
|
||||||
|
.card-title{font-size:15px;font-weight:700;color:#fff;line-height:1.4;margin-bottom:14px;display:-webkit-box;-webkit-line-clamp:3;-webkit-box-orient:vertical;overflow:hidden;min-height:62px}
|
||||||
|
.card-price-row{display:flex;align-items:baseline;gap:8px;margin-top:auto;margin-bottom:14px}
|
||||||
|
.card-price{font-size:26px;font-weight:900;background:linear-gradient(135deg,var(--green),#4ADE80);-webkit-background-clip:text;-webkit-text-fill-color:transparent;background-clip:text}
|
||||||
|
.card-price-vat{font-size:12px;color:var(--muted)}
|
||||||
|
.card .btn{font-size:13px;padding:12px 18px}
|
||||||
|
.state{text-align:center;padding:60px 0;color:var(--muted)}
|
||||||
|
.spinner{width:36px;height:36px;border:3px solid var(--border);border-top-color:var(--accent);border-radius:50%;animation:spin .8s linear infinite;margin:0 auto 16px}
|
||||||
|
@keyframes spin{to{transform:rotate(360deg)}}
|
||||||
|
.count-line{text-align:center;color:var(--muted);font-size:13px;margin-bottom:28px}
|
||||||
|
.what-section{padding:72px 0;background:#050810;border-top:1px solid var(--border);border-bottom:1px solid var(--border)}
|
||||||
|
.section-label{font-size:12px;font-weight:700;letter-spacing:.12em;text-transform:uppercase;color:var(--accent);margin-bottom:12px;text-align:center}
|
||||||
|
.section-title{font-size:clamp(24px,3vw,36px);font-weight:800;text-align:center;margin-bottom:48px}
|
||||||
|
.features-grid{display:grid;grid-template-columns:repeat(3,1fr);gap:24px}
|
||||||
|
.feature-card{background:var(--card);border:1px solid var(--border);border-radius:var(--radius-lg);padding:28px;text-align:center}
|
||||||
|
.feature-icon{font-size:36px;margin-bottom:16px}
|
||||||
|
.feature-title{font-size:16px;font-weight:800;color:#fff;margin-bottom:8px}
|
||||||
|
.feature-desc{font-size:13px;color:var(--muted);line-height:1.6}
|
||||||
|
.cta-section{padding:72px 0;text-align:center}
|
||||||
|
.cta-section h2{font-size:clamp(22px,3vw,32px);font-weight:800;margin-bottom:12px}
|
||||||
|
.cta-section p{color:var(--muted);font-size:16px;max-width:520px;margin:0 auto 32px}
|
||||||
|
footer{background:#03060f;border-top:1px solid var(--border);padding:40px 0 24px}
|
||||||
|
.footer-inner{display:flex;align-items:center;justify-content:space-between;flex-wrap:wrap;gap:16px}
|
||||||
|
.footer-copy{font-size:12px;color:var(--muted)}
|
||||||
|
@media(max-width:900px){.product-grid{grid-template-columns:repeat(2,1fr)}.features-grid{grid-template-columns:1fr}}
|
||||||
|
@media(max-width:768px){.nav-links{display:none}}
|
||||||
|
@media(max-width:560px){.product-grid{grid-template-columns:1fr}.trust-bar{gap:20px}}
|
||||||
|
</style>
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<nav>
|
||||||
|
<div class="nav-inner">
|
||||||
|
<a href="index.html" class="nav-logo"><img src="assets/logo.png" alt="Atlas Academy" width="32" height="32"> Atlas Academy</a>
|
||||||
|
<ul class="nav-links">
|
||||||
|
<li><a href="cursussen.html">Cursussen</a></li>
|
||||||
|
<li><a href="leerpad.html">Leerpad</a></li>
|
||||||
|
<li><a href="coaching.html">Coaching</a></li>
|
||||||
|
<li><a href="pricing.html">Prijzen</a></li>
|
||||||
|
<li><a href="shop.html" style="color:#fff;font-weight:700">Shop</a></li>
|
||||||
|
<li><a href="over.html">Over</a></li>
|
||||||
|
<li><a href="/web/login?redirect=%2Fslides">Inloggen</a></li>
|
||||||
|
</ul>
|
||||||
|
<div class="nav-cta"><a href="mailto:info@atlascorporation.nl" class="btn btn-primary">Start gratis →</a></div>
|
||||||
|
</div>
|
||||||
|
</nav>
|
||||||
|
<section class="hero"><div class="container">
|
||||||
|
<p class="hero-label">Atlas Hardware</p>
|
||||||
|
<h1 class="gradient-text">De machines waar wij zelf op draaien</h1>
|
||||||
|
<p>Refurbished zakelijke laptops, desktops, monitoren en kassasystemen. Getest, met 24 maanden garantie. Bestellen en betalen gaat veilig via atlasworks.nl.</p>
|
||||||
|
</div></section>
|
||||||
|
<div class="container"><div class="trust-bar">
|
||||||
|
<div class="trust-item"><span>✅</span> Uitgebreid getest</div>
|
||||||
|
<div class="trust-item"><span>🔒</span> 24 maanden garantie</div>
|
||||||
|
<div class="trust-item"><span>📍</span> Afhalen in Tilburg</div>
|
||||||
|
<div class="trust-item"><span>💳</span> Veilig betalen via iDEAL</div>
|
||||||
|
</div></div>
|
||||||
|
<section class="shop-section"><div class="container">
|
||||||
|
<div class="filters" id="filters">
|
||||||
|
<button class="filter-btn active" data-type="all">Alles</button>
|
||||||
|
<button class="filter-btn" data-type="laptop">Laptops</button>
|
||||||
|
<button class="filter-btn" data-type="desktop">Desktops</button>
|
||||||
|
<button class="filter-btn" data-type="monitor">Monitoren</button>
|
||||||
|
<button class="filter-btn" data-type="bundle">Werkplekken</button>
|
||||||
|
<button class="filter-btn" data-type="pos">Kassa & POS</button>
|
||||||
|
<button class="filter-btn" data-type="accessory">Accessoires</button>
|
||||||
|
</div>
|
||||||
|
<p class="count-line" id="countLine"></p>
|
||||||
|
<div id="shopState" class="state"><div class="spinner"></div>Producten laden…</div>
|
||||||
|
<div class="product-grid" id="grid" style="display:none"></div>
|
||||||
|
</div></section>
|
||||||
|
<section class="what-section"><div class="container">
|
||||||
|
<p class="section-label">Waarom hier kopen</p>
|
||||||
|
<h2 class="section-title gradient-text">Geen verrassingen — wel werkende hardware</h2>
|
||||||
|
<div class="features-grid">
|
||||||
|
<div class="feature-card"><div class="feature-icon">🔍</div><div class="feature-title">Volledig getest</div><div class="feature-desc">Elke machine doorloopt een meerpunts-checklist: scherm, toetsenbord, batterij, SSD, WiFi, poorten — alles werkt of we leveren hem niet.</div></div>
|
||||||
|
<div class="feature-card"><div class="feature-icon">🛠️</div><div class="feature-title">24 maanden garantie</div><div class="feature-desc">Gaat er iets stuk? Breng hem langs in Tilburg en we fixen het of ruilen om. Geen gezeur met retourlabels of callcenters.</div></div>
|
||||||
|
<div class="feature-card"><div class="feature-icon">💳</div><div class="feature-title">Zakelijke factuur</div><div class="feature-desc">Netjes op naam van je bedrijf, BTW verrekenbaar. Veilig afrekenen via iDEAL op atlasworks.nl — geen marktplaats-gedoe.</div></div>
|
||||||
|
</div>
|
||||||
|
</div></section>
|
||||||
|
<section class="cta-section"><div class="container">
|
||||||
|
<h2 class="gradient-text">Vraag of advies nodig?</h2>
|
||||||
|
<p>Twijfel je welke machine bij je past? Stuur een mail en we denken met je mee — afhalen in Tilburg of verzenden kan ook.</p>
|
||||||
|
<a href="mailto:info@atlascorporation.nl?subject=Hardware advies" class="btn btn-primary btn-lg">Stel je vraag →</a>
|
||||||
|
</div></section>
|
||||||
|
<footer><div class="container"><div class="footer-inner">
|
||||||
|
<p class="footer-copy">© 2026 Atlas Corporation — Tilburg, Nederland</p>
|
||||||
|
<p class="footer-copy"><a href="mailto:info@atlascorporation.nl">info@atlascorporation.nl</a></p>
|
||||||
|
</div></div></footer>
|
||||||
|
<script>
|
||||||
|
(function(){
|
||||||
|
var FEED='https://www.atlasworks.nl/academy-feed.php';
|
||||||
|
var TYPE_LABEL={laptop:'Laptop',desktop:'Desktop',monitor:'Monitor',accessory:'Accessoire',bundle:'Werkplek',pos:'Kassa / POS',other:'Hardware'};
|
||||||
|
var grid=document.getElementById('grid');
|
||||||
|
var stateEl=document.getElementById('shopState');
|
||||||
|
var countLine=document.getElementById('countLine');
|
||||||
|
var all=[];var current='all';
|
||||||
|
function euro(n){try{return '€'+Number(n).toLocaleString('nl-NL',{minimumFractionDigits:0,maximumFractionDigits:0});}catch(e){return '€'+n;}}
|
||||||
|
function esc(s){return String(s).replace(/[&<>"']/g,function(c){return {'&':'&','<':'<','>':'>','"':'"',"'":'''}[c];});}
|
||||||
|
function track(p){if(window.gtag){gtag('event','select_item',{item_id:String(p.id),item_name:p.title});}}
|
||||||
|
function card(p){
|
||||||
|
var badgeClass=(p.type==='pos')?'pos':(p.type==='bundle'?'bundle':'');
|
||||||
|
var label=TYPE_LABEL[p.type]||'Hardware';
|
||||||
|
var img=p.img?'<img src="'+esc(p.img)+'" alt="'+esc(p.title)+'" loading="lazy">':'';
|
||||||
|
var a=document.createElement('article');
|
||||||
|
a.className='card';a.setAttribute('data-type',p.type);
|
||||||
|
a.innerHTML='<a class="card-img" href="'+esc(p.url)+'" target="_blank" rel="noopener" aria-label="'+esc(p.title)+'">'+img+'</a>'
|
||||||
|
+'<div class="card-body">'
|
||||||
|
+'<span class="card-badge '+badgeClass+'">'+esc(label)+'</span>'
|
||||||
|
+'<h3 class="card-title">'+esc(p.title)+'</h3>'
|
||||||
|
+'<div class="card-price-row"><span class="card-price">'+euro(p.price)+'</span><span class="card-price-vat">excl. BTW</span></div>'
|
||||||
|
+'<a class="btn btn-primary btn-block" href="'+esc(p.url)+'" target="_blank" rel="noopener">Bekijk & koop op atlasworks.nl →</a>'
|
||||||
|
+'</div>';
|
||||||
|
var links=a.querySelectorAll('a[href]');
|
||||||
|
for(var i=0;i<links.length;i++){links[i].addEventListener('click',function(){track(p);});}
|
||||||
|
return a;
|
||||||
|
}
|
||||||
|
function render(){
|
||||||
|
var list=(current==='all')?all:all.filter(function(p){return p.type===current;});
|
||||||
|
grid.innerHTML='';
|
||||||
|
if(!list.length){grid.style.display='none';stateEl.style.display='block';stateEl.innerHTML='Geen producten in deze categorie.';countLine.textContent='';return;}
|
||||||
|
stateEl.style.display='none';grid.style.display='grid';
|
||||||
|
list.forEach(function(p){grid.appendChild(card(p));});
|
||||||
|
countLine.textContent=list.length+' product'+(list.length===1?'':'en')+' beschikbaar';
|
||||||
|
}
|
||||||
|
document.getElementById('filters').addEventListener('click',function(e){
|
||||||
|
var b=e.target.closest('.filter-btn');if(!b)return;
|
||||||
|
current=b.getAttribute('data-type');
|
||||||
|
var btns=this.querySelectorAll('.filter-btn');
|
||||||
|
for(var i=0;i<btns.length;i++){btns[i].classList.toggle('active',btns[i]===b);}
|
||||||
|
render();
|
||||||
|
});
|
||||||
|
fetch(FEED,{mode:'cors'}).then(function(r){if(!r.ok)throw new Error('HTTP '+r.status);return r.json();}).then(function(d){
|
||||||
|
all=(d.products||[]).filter(function(p){return p.url&&p.price;});
|
||||||
|
var fb=document.querySelectorAll('.filter-btn');
|
||||||
|
for(var i=0;i<fb.length;i++){
|
||||||
|
var t=fb[i].getAttribute('data-type');if(t==='all')continue;
|
||||||
|
var has=all.some(function(p){return p.type===t;});
|
||||||
|
if(!has)fb[i].style.display='none';
|
||||||
|
}
|
||||||
|
render();
|
||||||
|
}).catch(function(err){
|
||||||
|
stateEl.innerHTML='Het assortiment kon niet geladen worden. Bekijk alle hardware direct op <a href="https://atlasworks.nl/assortiment/" target="_blank" rel="noopener">atlasworks.nl</a>.';
|
||||||
|
});
|
||||||
|
})();
|
||||||
|
</script>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
Loading…
Reference in a new issue