YCS adalah singkatan dari Yayasan Cahaya Sunnah.
LIVE DEMO : https://ucapan.rodja.co.id
Web app generator kartu ucapan berbasis Vite dengan 3 tab:
- Simple
- User cukup isi nama.
- Semua template YCS langsung muncul sebagai preview.
- Setiap card bisa langsung Download atau Share.
- Studio
- User bisa pilih template, ubah font, warna, ukuran, dan offset teks.
- Teks dapat digeser langsung di canvas (drag).
- User bisa upload template pribadi (hanya lokal browser, tidak tersimpan ke sistem).
- Tersedia Preset Helper untuk menghasilkan JSON placeholder siap copy ke manifest.
- Gallery
- Tidak ada edit teks atau watermark.
- Card siap pakai untuk Download atau Share langsung.
- Riwayat update tersedia di
CHANGELOG.md.
- Vite
- HTML
- CSS
- JavaScript Canvas API
npm install
npm run devBuild production:
npm run build- Counter menggunakan GitHub Gist API (global counter, tidak perlu database).
- Token disimpan di environment variable
VITE_GIST_TOKENuntuk keamanan. - Gist ID dikonfigurasi di
public/templates/manifest.json.
-
Buat GitHub Personal Access Token (PAT) dengan scope
gist:- Buka https://github.com/settings/tokens
- Klik "Generate new token (classic)"
- Beri nama token, centang scope
gist - Copy token yang dihasilkan
-
Buat Gist publik:
- Buka https://gist.github.com
- Buat file baru dengan nama
counter.json - Isi dengan:
{"total":0,"download":0,"share":0,"items":{}} - Copy Gist ID dari URL (format:
667e65c647da97926980d9cc6e2137a9)
-
Setup environment variable:
- Untuk development: buat file
.envdenganVITE_GIST_TOKEN=ghp_xxxx - Untuk production: setup
VITE_GIST_TOKENdi hosting (Vercel/Netlify/dll)
- Untuk development: buat file
-
Konfigurasi Gist ID di
manifest.json:
{
"appConfig": {
"counterEnabled": true,
"counterType": "gist",
"counterGistId": "GIST_ID_ANDA"
}
}- Pastikan Gist dalam kondisi public agar bisa di-read tanpa auth.
- Untuk write/update, diperlukan PAT token dengan scope
gist. - Format data di Gist:
{
"total": 10,
"download": 5,
"share": 5,
"items": {
"item_used_simple:rodja-frame": 3
}
}Gunakan appConfig di public/templates/manifest.json untuk mengubah konfigurasi aplikasi tanpa edit file JavaScript.
Contoh:
{
"appConfig": {
"counterNamespace": "ucapan-rodja-co-id",
"counterEnabled": true,
"fileNamePrefix": "ycs",
"pageTitle": "YCS Eid Greeting Card",
"heroEyebrow": "YCS Eid Greeting Card",
"heroTitle": "Yayasan Cahaya Sunnah",
"heroDescription": "Platform kartu ucapan id resmi di bawah naungan Yayasan Cahaya Sunnah.",
"metaDescription": "Platform kartu ucapan id resmi Yayasan Cahaya Sunnah untuk membuat dan membagikan kartu ucapan dengan tampilan rapi, cepat, dan siap pakai.",
"canonicalUrl": "https://ucapan.rodja.co.id/",
"tabLabelSimple": "Simple",
"tabLabelStudio": "Studio",
"tabLabelGallery": "Gallery",
"simpleSectionTitle": "Simple",
"simpleSectionDescription": "Isi nama sekali, lalu seluruh template YCS langsung muncul dan siap dibagikan.",
"simpleSectionHelper": "Preview otomatis menyesuaikan setting placeholder tiap template.",
"studioSectionTitle": "Studio",
"studioSectionDescription": "Atur detail teks, geser posisi, dan upload template pribadi untuk kebutuhan personal.",
"gallerySectionTitle": "Gallery",
"gallerySectionDescription": "Kumpulan kartu ucapan siap pakai. Tidak perlu edit teks, langsung download atau share.",
"footerCreditPrefix": "Made with",
"footerCreditBy": "by",
"footerCreditLinkText": "IT Syathiby 2024",
"footerCreditLinkHref": "https://syathiby.github.io/",
"footerSourceLinkText": "Open Source",
"footerSourceLinkHref": "https://github.com/CreatorB/twibbon-rodja"
},
"ycsTemplates": [],
"freeFrames": []
}Keterangan field:
counterNamespace: identifier untuk membedakan data counter.counterEnabled:true/falseuntuk mengaktifkan/nonaktifkan fitur counter.counterNote: Catatan metode storage (localStorage).fileNamePrefix: prefix nama file saat download/share.pageTitle: judul halaman browser.heroEyebrow: teks kecil di atas judul hero.heroTitle: judul utama hero.heroDescription: deskripsi singkat di hero.metaDescription: deskripsi SEO dasar untuk halaman.canonicalUrl: canonical URL halaman production.tabLabelSimple,tabLabelStudio,tabLabelGallery: label tab desktop + mobile.simpleSectionTitle,simpleSectionDescription,simpleSectionHelper: teks panel Simple.studioSectionTitle,studioSectionDescription: teks panel Studio.gallerySectionTitle,gallerySectionDescription: teks panel Gallery.footerCreditPrefix,footerCreditBy: teks footer bagian kredit.footerCreditLinkText,footerCreditLinkHref: label + URL link kredit.footerSourceLinkText,footerSourceLinkHref: label + URL link open source.
Preset A - Production Rodja (saat ini):
{
"appConfig": {
"counterNamespace": "ucapan-rodja-co-id",
"counterEnabled": true,
"fileNamePrefix": "ycs",
"pageTitle": "YCS Eid Greeting Card",
"heroEyebrow": "YCS Eid Greeting Card",
"heroTitle": "Yayasan Cahaya Sunnah",
"heroDescription": "Platform kartu ucapan id resmi di bawah naungan Yayasan Cahaya Sunnah.",
"metaDescription": "Platform kartu ucapan id resmi Yayasan Cahaya Sunnah untuk membuat dan membagikan kartu ucapan dengan tampilan rapi, cepat, dan siap pakai.",
"canonicalUrl": "https://ucapan.rodja.co.id/",
"tabLabelSimple": "Simple",
"tabLabelStudio": "Studio",
"tabLabelGallery": "Gallery",
"simpleSectionTitle": "Simple",
"simpleSectionDescription": "Isi nama sekali, lalu seluruh template YCS langsung muncul dan siap dibagikan.",
"simpleSectionHelper": "Preview otomatis menyesuaikan setting placeholder tiap template.",
"studioSectionTitle": "Studio",
"studioSectionDescription": "Atur detail teks, geser posisi, dan upload template pribadi untuk kebutuhan personal.",
"gallerySectionTitle": "Gallery",
"gallerySectionDescription": "Kumpulan kartu ucapan siap pakai. Tidak perlu edit teks, langsung download atau share.",
"footerCreditPrefix": "Made with",
"footerCreditBy": "by",
"footerCreditLinkText": "IT Syathiby 2024",
"footerCreditLinkHref": "https://syathiby.github.io/",
"footerSourceLinkText": "Open Source",
"footerSourceLinkHref": "https://github.com/CreatorB/twibbon-rodja"
}
}Preset B - Generic Instansi Lain (template):
{
"appConfig": {
"counterNamespace": "ucapan-nama-instansi",
"counterEnabled": true,
"fileNamePrefix": "ucapan",
"pageTitle": "Ucapan Instansi",
"heroEyebrow": "Ucapan Resmi",
"heroTitle": "Twibbon Instansi",
"heroDescription": "Platform kartu ucapan id resmi instansi.",
"metaDescription": "Generator twibbon resmi untuk membuat dan membagikan kartu ucapan.",
"canonicalUrl": "https://contoh-domain.id/",
"tabLabelSimple": "Simple",
"tabLabelStudio": "Studio",
"tabLabelGallery": "Gallery",
"simpleSectionTitle": "Simple",
"simpleSectionDescription": "Isi nama sekali, semua template langsung siap.",
"simpleSectionHelper": "Preview menyesuaikan placeholder setiap template.",
"studioSectionTitle": "Studio",
"studioSectionDescription": "Atur detail teks dan posisi sesuai kebutuhan.",
"gallerySectionTitle": "Gallery",
"gallerySectionDescription": "Kartu siap pakai untuk download atau share.",
"footerCreditPrefix": "Made with",
"footerCreditBy": "by",
"footerCreditLinkText": "Tim IT",
"footerCreditLinkHref": "https://example.com/",
"footerSourceLinkText": "Open Source",
"footerSourceLinkHref": "https://github.com/your-org/your-repo"
}
}Langkah cepat migrasi domain lain:
- Ganti nilai
appConfigsesuai brand/domain target. - Pastikan
counterNamespaceunik untuk domain target. - Ganti
canonicalUrlke URL production yang benar. - Build lalu deploy seperti biasa.
ycs-eid-greeting-card/
index.html
public/
icon-32.png
icon-180.png
icon-192.png
icon-512.png
favicon.svg
og-image-1200x630.png
site.webmanifest
templates/
manifest.json
ycs-frame/
galleries/
src/
main.js
style.css
templates.js- Simpan frame resmi di folder public/templates/ycs-frame.
- Simpan kartu ucapan siap pakai di folder public/templates/galleries.
- Edit daftar template di public/templates/manifest.json.
- Tidak perlu edit logic rendering di src/main.js.
Struktur manifest yang dipakai:
{
"ycsTemplates": [],
"freeFrames": []
}Contoh entri frame pada ycsTemplates:
{
"id": "kajian-ramadhan-1",
"title": "Kajian Ramadhan 1",
"description": "Tema hijau emas",
"image": "kajian-ramadhan-1.png",
"textBox": {
"x": 0.5,
"y": 0.78,
"maxWidth": 0.7,
"maxLines": 3,
"minFont": 28,
"maxFont": 72,
"lineHeight": 1.16,
"align": "center"
},
"textStyle": {
"mainColor": "#ffffff",
"shadowColor": "rgba(0, 0, 0, 0.25)"
}
}Contoh entri kartu ucapan pada freeFrames:
{
"id": "idulfitri-ucapan-1",
"title": "Ucapan Idulfitri 1",
"description": "Kartu siap pakai",
"image": "idulfitri-ucapan-1.png"
}- Tambahkan file gambar ke public/templates/ycs-frame.
- Tambahkan objek template ke array ycsTemplates di public/templates/manifest.json.
- Jalankan aplikasi dan cek di tab Simple serta Studio.
- Buka tab Studio.
- Pilih template yang ingin dikalibrasi.
- Atur slider Preset Helper: Anchor X/Y, Max Width, Max Lines, Min/Max Font, dan Line Height.
- Klik Copy JSON lalu paste ke public/templates/manifest.json pada entri template terkait.
- Tambahkan file gambar ke public/templates/galleries.
- Tambahkan objek kartu ke array freeFrames di public/templates/manifest.json.
- Cek hasilnya di tab Gallery.
Contoh minimal preset (fallback di src/templates.js):
{
id: "template-baru",
title: "Template Baru",
description: "Deskripsi singkat",
imagePath: "/templates/template-baru.png",
textBox: {
x: 0.5,
y: 0.8,
maxWidth: 0.72,
maxLines: 3,
minFont: 30,
maxFont: 72,
lineHeight: 1.16,
align: "center"
}
}- Gunakan nilai relatif 0 sampai 1 untuk x, y, maxWidth agar konsisten di semua ukuran output.
- Output menggunakan ukuran tetap 1080x1350 (Portrait 4:5).
- Fokuskan textBox untuk area aman yang tidak menabrak ornamen template.
- Uji minimal 3 skenario:
- Nama pendek (1-2 kata)
- Nama sedang (3-4 kata)
- Nama panjang (5+ kata)
- Jika template punya area sempit, turunkan maxFont dan naikkan maxLines.
- Cek template di ukuran 1080x1350, 1080x1080, dan 1080x1920.
- Uji nama pendek, sedang, panjang, dan nama dengan 2 baris.
- Cek kontras teks terhadap background pada tab Simple dan Studio.
- Cek hasil download PNG dan pastikan resolusi sesuai pilihan ukuran.
- Cek fitur share di minimal 1 Android dan 1 iOS (jika tersedia).
- Pastikan tidak ada elemen teks menabrak logo, ornament, atau area wajah pada desain.
- Pastikan metadata dan aset share image sudah sesuai untuk production.
- Siapkan frame production ke public/templates/ycs-frame.
- Siapkan kartu ucapan siap pakai ke public/templates/galleries.
- Isi metadata placeholder di public/templates/manifest.json.
- Jalankan QA checklist di atas, lalu catat template yang perlu penyesuaian textBox.
- Finalisasi branch setelah semua template lolos di semua tab.
Pilih salah satu metode deploy berikut.
Jika targetnya langsung live dan server sering OOM saat build, gunakan urutan ini:
# lokal
cd D:/IT/HSN/syathiby/ycs/ycs-eid-greeting-card
git checkout dev
git pull origin dev
npm install
npm run build
# upload ke hosting
rsync -avz --delete -e "ssh -p 18765" dist/ u44-ymt6jwdhjg4c@ssh.rodja.co.id:~/www/ucapan.rodja.co.id/public_html/Lalu verifikasi:
ssh u44-ymt6jwdhjg4c@ssh.rodja.co.id -p 18765
cd ~/www/ucapan.rodja.co.id/public_html
lsPastikan minimal ada index.html, assets/, templates/, site.webmanifest, dan favicon.svg.
ssh u44-ymt6jwdhjg4c@ssh.rodja.co.id -p 18765
cd ~/www/ucapan.rodja.co.id
# clone pertama kali
git clone https://github.com/CreatorB/twibbon-rodja.git public_html
cd public_html
# pilih branch yang berisi update terbaru
git fetch origin
git checkout dev
git pull origin dev
# install dependency dan build
npm install
npm run build
# publish static build ke document root yang diserve
rsync -av --delete dist/ ./Catatan:
- Jika muncul error OOM saat
npm run build, gunakan Metode B (build di lokal). - Untuk update berikutnya cukup ulang dari
git fetch originsampairsync dist/ ./.
# di lokal
cd D:/IT/HSN/syathiby/ycs/ycs-eid-greeting-card
git checkout dev
git pull origin dev
npm install
npm run buildUpload hasil dist ke server (pakai salah satu):
# opsi 1 (rsync, lebih efisien)
rsync -avz --delete -e "ssh -p 18765" dist/ u44-ymt6jwdhjg4c@ssh.rodja.co.id:~/www/ucapan.rodja.co.id/public_html/# opsi 2 (scp)
scp -P 18765 -r dist/* u44-ymt6jwdhjg4c@ssh.rodja.co.id:~/www/ucapan.rodja.co.id/public_html/Verifikasi di server:
ssh u44-ymt6jwdhjg4c@ssh.rodja.co.id -p 18765
cd ~/www/ucapan.rodja.co.id/public_html
lsPastikan ada file/folder static berikut:
index.htmlassets/templates/favicon.svg,icon-*.png,site.webmanifest
Jika website masih menampilkan tema lama, kemungkinan document root bukan di public_html.
Uji cepat:
cd ~/www/ucapan.rodja.co.id/public_html
echo OK-DEPLOY > deploy-check.txtBuka https://ucapan.rodja.co.id/deploy-check.txt.
- Jika tampil
OK-DEPLOY, berarti document root benar. - Jika tidak tampil, sesuaikan deploy ke folder document root yang benar dari panel hosting.