שדות Payload CMS הסטנדרטיים מכסים 80% מהמשימות. אבל כאשר לקוח צריך בורר צבעים מפלטת מותג — לא טקסט, אלא ויזואלית — צריך לכתוב קומפוננטה מותאמת אישית. התיעוד הרשמי של Payload CMS לשדות מותאמים אישית (Custom Fields) מאפשר להוסיף כל ממשק משתמש בפאנל הניהול תוך שמירה על ולידציה קפדנית בצד השרת. אנו נתקלים לעתים קרובות בבקשות כאלה: בורר צבעים, עורך JSON מותאם אישית, שדה עם השלמה אוטומטית מ-API חיצוני. הטיפוסים המובנים אינם גמישים, ולכן אנו מפתחים פתרונות מותאמים אישית תוך 2-3 ימים. הניסיון שלנו: יותר מ-10 שנים ב-React, TypeScript, Payload CMS. השלמנו למעלה מ-50 פרויקטים עם שדות מותאמים אישית. זמן החיסכון הממוצע לעורכים לאחר היישום הוא 70%. צרו קשר כדי לדון במקרה שלכם.
מדוע שדות Payload CMS הסטנדרטיים אינם מספיקים?
הטיפוסים המובנים (טקסט, מספר, select) טובים למשימות טיפוסיות. אבל ברגע שנדרש ממשק משתמש לא סטנדרטי — בחירת צבע ויזואלית, עורך מותאם אישית עם תצוגה מקדימה, טעינת נתונים דינמית — צריך להרחיב את הפונקציונליות. חלופה היא לכתוב פלאגין, אבל לעתים קרובות קל יותר ליצור שדה מותאם אישית. זה נותן שליטה מלאה על התצוגה והוולידציה, והקוד נשאר בתוך קולקציה אחת. השוואה: הגדרת select עם נראות מותנית אורכת 15 דקות, בעוד קומפוננטה מותאמת אישית עם השלמה אוטומטית מ-API אורכת כ-4 שעות. אבל התוצאה הרבה יותר נוחה לעורך. לדוגמה, בפרויקט אחד החלפנו 10 שדות סטנדרטיים בבלוק מותאם אישית אחד — מהירות המילוי גדלה פי 3.
כיצד ליצור שדה מותאם אישית עם ולידציה?
נבחן שדה להזנת מספר טלפון עם מסכת +7. ולידציה פשוטה עם ביטוי רגולרי — אבל נוסיף קומפוננטה מותאמת אישית להצגת המסכה. הוולידציה מתבצעת גם בצד הלקוח (בפאנל הניהול) וגם בשרת בעת השמירה. זו משימה טיפוסית שאנו פותרים באופן קבוע.
{
name: 'phone',
type: 'text',
validate: (value) => {
if (!value) return true
const phoneRegex = /^\+7\d{10}$/
if (!phoneRegex.test(value)) {
return 'Формат: +7XXXXXXXXXX'
}
return true
},
}לתרחישים מורכבים יותר, כמו נראות מותנית של שדות, אנו משתמשים ב-{ name: 'phone', type: 'text', validate: (value) => { if (!value) return true const phoneRegex = /^\+7\d{10}$/ if (!phoneRegex.test(value)) { return 'Формат: +7XXXXXXXXXX' } return true }, } . זה מפחית את העומס על המשתמש: אם תיבת הסימון לא פעילה, השדה מוסתר.
כיצד לחבר קומפוננטת UI מותאמת אישית? — Payload Custom Fields
לתצוגה לא סטנדרטית בפאנל הניהול, אנו יוצרים קומפוננטת React. הנתונים נשמרים כרגיל, אבל ממשק המשתמש משתנה. דוגמה — ColorPicker:
'use client'
import { useField } from 'payload/components/forms'
const ColorPickerField = ({ path }: { path: string }) => {
const { value, setValue } = useField<string>({ path })
const colors = ['#FF5733', '#33FF57', '#3357FF', '#FF33A8', '#33A8FF']
return (
<div className="field-type">
<label className="field-label">Цвет</label>
<div style={{ display: 'flex', gap: 8 }}>
{colors.map(color => (
<div
key={color}
onClick={() => setValue(color)}
style={{
width: 32,
height: 32,
borderRadius: '50%',
background: color,
cursor: 'pointer',
border: value === color ? '3px solid #000' : '2px solid transparent'
}}
/>
))}
</div>
<input
type="text"
value={value || ''}
onChange={e => setValue(e.target.value)}
placeholder="#000000"
style={{ marginTop: 8 }}
/>
</div>
)
}
export default ColorPickerField
חיבור בקולקציה:
{ name: 'brandColor', type: 'text', admin: { components: { Field: '/fields/ColorPicker/index#ColorPickerField', }, }, } באופן דומה, ניתן לחבר עורכים מותאמים אישית, אינטגרציות Figma, או מחוללי קוד QR. המהנדסים שלנו לוקחים על עצמם פיתוח קומפוננטה מלא — מאב-טיפוס ועד בדיקות. קבלו ייעוץ לפרויקט שלכם — כתבו לנו.
מדוע Blocks הם הבחירה הטובה ביותר לדפים גמישים?
Blocks הם בונה דפים שבו העורך בוחר סוג בלוק (טקסט, תמונה, CTA). בניגוד ל-Arrays או Groups, Blocks תומכים בקבוצות שדות שונות בכל בלוק. נשווה:
| מאפיין | Blocks | Array | Group |
|---|---|---|---|
| שדות שונים לכל שורה | כן | לא | לא |
| גרירה ושחרור של בלוקים | כן | כן | לא |
| מורכבות הגדרה | בינונית | נמוכה | נמוכה |
| גמישות דף | גבוהה | בינונית | נמוכה |
דוגמה להגדרת Blocks:
const TextBlock: Block = {
slug: 'textBlock',
fields: [
{
name: 'content',
type: 'richText',
},
{
name: 'columns',
type: 'select',
options: [
{
label: '1 колонка',
value: '1',
},
{
label: '2 колонки',
value: '2',
},
],
defaultValue: '1',
},
],
}
const ImageBlock: Block = {
slug: 'imageBlock',
fields: [
{
name: 'image',
type: 'upload',
relationTo: 'media',
required: true,
},
{
name: 'caption',
type: 'text',
},
{
name: 'fullWidth',
type: 'checkbox',
defaultValue: false,
},
],
}שימוש ב-Blocks מקצר את זמן פיתוח הדף פי 2-3 בהשוואה ל-Array. העורך בונה את הפריסה בעצמו, ואנו מבטיחים עיבוד נכון בכל המכשירים. צרו קשר כדי לדון במשימות שלכם.
מהם Virtual Fields ולמה הם נחוצים?
לפעמים צריך לחשב ערך תוך כדי תנועה מבלי לשמור אותו. אנו משתמשים ב-admin.condition hooks. שדות כאלה שימושיים להצגת נתונים מורכבים, כמו שם מלא משם פרטי ושם משפחה. הם לא משפיעים על הביצועים כי הם מחושבים רק בקריאה. דוגמה — שדה 'use client' import { useField } from 'payload/components/forms' const ColorPickerField = ({ path }: { path: string }) => { const { value, setValue } = useField<string>({ path }) const colors = ['#FF5733', '#33FF57', '#3357FF', '#FF33A8', '#33A8FF'] return ( <div className="field-type"> <label className="field-label">Цвет</label> <div style={{ display: 'flex', gap: 8 }}> {colors.map(color => ( <div key={color} onClick={() => setValue(color)} style={{ width: 32, height: 32, borderRadius: '50%', background: color, cursor: 'pointer', border: value === color ? '3px solid #000' : '2px solid transparent' }} /> ))} </div> <input type="text" value={value || ''} onChange={e => setValue(e.target.value)} placeholder="#000000" style={{ marginTop: 8 }} /> </div> ) } export default ColorPickerField וירטואלי:
{ name: 'fullName', type: 'text', hooks: { afterRead: [({ data }) => `${data.firstName} ${data.lastName}`], }, } שדות כאלה חוסכים מקום במסד הנתונים ומפשטים את ה-API.
מה כלול בפיתוח שדות מותאמים אישית?
אנו מספקים מחזור מלא: מניתוח דרישות ועד פריסה ותיעוד. הטבלה מציגה את השלבים המרכזיים.
| שלב | משך | תוצאה |
|---|---|---|
| ניתוח דרישות | 1-2 שעות | מפרט שדה, אב-טיפוס UI |
| פיתוח 3-5 שדות | 2-3 ימים | קונפיגורציות, קומפוננטות React, בדיקות |
| אינטגרציה לפרויקט | יום אחד | התקנה, הגדרה, בדיקת תאימות |
| הדרכת עורכים | 1-2 שעות | הדרכת וידאו או מדריך טקסט |
| תמיכה לאחר פריסה | חודש אחד | תיקוני באגים, ייעוץ |
לוחות הזמנים הם משוערים. שדות מורכבים (אינטגרציה עם API חיצוני) עשויים לקחת יותר זמן. אנו נעריך את הפרויקט שלכם — צרו קשר.
אנו מבטיחים יישום איכותי: כל השדות עוברים בדיקת קוד ובדיקות יחידה. קבלו ייעוץ לפרויקט שלכם — כתבו לנו.







