Logiciel marketing · Nouvelle ressource

Système de design Emplifi Soul.

Découvrez le contrat de tableau de données de Soul, son espacement de six pixels, ses rôles de couleurs en couches et sa typographie Inter compacte. Comparez la sélection multiple, la représentation des données manquantes et les lignes de synthèse, puis examinez les points d’entrée vérifiés du paquet privé React.

Guide OpenDesign7 chapitres44 entrées de référenceGuide de l’application d’origine
01

Aperçu de l’interface du système de design Emplifi Soul

Essayez la sélection globale, la sélection partielle, le tri, la révision groupée et l’annulation.

Tableau de révision de contenu sélectionnableOuvrir l’exemple complet
Interprétation indépendante HTML/CSS des recommandations de conception de Soul et des jetons vérifiés du mode clair. Police système utilisée en remplacement ; aucun élément privé de React. · Référence de mise en œuvre
02

Référence de conception du système de design Emplifi Soul

Documentation publique de conception de Soul et Storybook officiel en ligne. Il s’agit de valeurs de fondation désignées pour le mode clair, et non d’une affirmation selon laquelle chaque page de documentation et chaque version de package auraient un état identique. L’aperçu utilise les polices système comme solution de remplacement locale.

Modèle de couches

Source
Nom / règleValeur / configurationUtilisation
--color-layer-level-0#f3f3f5 Niveau de surface en mode clair.
--color-layer-level-1#ffffff Niveau de surface en mode clair.
--color-layer-level-2#f3f3f5 Niveau de surface en mode clair.
--color-layer-level-3#e7e7e7 Niveau de surface en mode clair.
--color-on-layer-primary#24242b Texte principal.
--color-on-layer-secondary#505057 Texte d’accompagnement.
Dark level 0 / level 1#111114 / #24242bLes surfaces sombres s’éclaircissent avec la profondeur.

Couleurs des actions et des tableaux

Source
Nom / règleValeur / configurationUtilisation
--color-button-primary#0c4bff Arrière-plan du bouton principal.
--color-on-layer-interactive#003beb Texte interactif.
--color-border-focus-ring#003beb Anneau de mise au point.
--color-table-row-odd#ffffff Lignes impaires et en-tête/pied de tableau.
--color-table-row-even#f9f9fa Lignes paires.
--color-table-row-hover#d5efff Indication de balayage.
--color-layer-main-navigation#111114 Navigation principale uniquement.

Espacement et rayon

Source
Nom / règleValeur / configurationUtilisation
--space-13pxEspacement de Foundation.
--space-26pxEspacement de Foundation.
--space-39pxEspacement de Foundation.
--space-412pxEspacement de Foundation.
--space-518pxEspacement de Foundation.
--space-624pxEspacement de Foundation.
--space-730pxEspacement de Foundation.
--space-836pxEspacement de Foundation.
--space-948pxEspacement de Foundation.
Default control height36pxOption compacte de 30 px ; à ne pas confondre avec l’échelle d’espacement.

Hiérarchie des arrondis

Source
Nom / règleValeur / configurationUtilisation
--border-radius-small2pxAdoucissement subtil.
--border-radius-medium6pxÉléments par défaut.
--border-radius-large8pxConteneurs.
--border-radius-full50%Cercle.
--border-radius-pill999pxForme de pilule.

Recettes typographiques

Source
Nom / règleValeur / configurationUtilisation
headline-1500 · 30px / 42pxTitre principal de la page.
headline-2500 · 20px / 30pxTitre de section.
headline-3500 · 16px / 24pxTitre de sous-section.
paragraph-regular400 · 13px / 18pxCorps de texte moyen.
Button label600 · 13px / 18pxCasse de phrase.
Table numeralsTabular numbersAligner les valeurs numériques comparables.

Bouton React API

Source
Nom / règleValeur / configurationUtilisation
Package@sbks/ds-buttonPortée privée ; Button est un export nommé.
variantBUTTON_VARIANT.LIGHT defaultBasé sur une énumération ; utilisez les constantes d’énumération exportées, et non des chaînes brutes dans TypeScript.
sizeBUTTON_SIZE.MEDIUM defaultMedium est la valeur de base.
isLoadingfalseVisualisation du chargement.
isSelectedfalseAspect sélectionné.
isAppliedfalsePrise en charge visuelle actuellement réservée à la variante invisible.
onClickMouse event handlerConnecter l’état de l’application locale.
badgestring | numberInformations sur la sélection appliquée.
themeInherited; light fallbackNe partez pas du principe qu’une surface sombre modifie automatiquement tous ses éléments descendants.
03

Guide complet du système de design Emplifi Soul

Un guide pratique pour choisir, appliquer et évaluer ce système dans une interface réelle.

DESIGN-emplifi-soul.md

Des conseils complets, un point de départ pour la mise en œuvre et des liens vers les sources.

Télécharger le guide

Recommandations de conception et état de l’implémentation du système de design Emplifi Soul

Ne déduisez pas l’existence d’un package à partir du nom d’un composant

Soul est le système de design d’Emplifi. Ses références publiques de conception et son Storybook sont consultables, mais le guide de démarrage officiel nécessite l’accès à une portée npm privée. Le spécimen dans le navigateur est une réalisation indépendante HTML/CSS ; il n’intègre pas Soul React. Le comportement du tableau interprète les recommandations de conception, dont la page publique indique encore que React est prévu.

Extrait de ce guide OpenDesign

L’exemple React fourni utilise délibérément un tableau sémantique et de véritables commandes Soul Button. Il propose un état d’application fonctionnel sans prétendre qu’un export DataTable non documenté existe. La documentation consultable publiquement ne donne ni accès au package ni autorisation de redistribuer des ressources privées.

Consultez la spécification associée

Un contrat de tableau de données qui va au-delà de la sélection des lignes — système de design Emplifi Soul

En-têtes, récapitulatifs et valeurs manquantes

Les recommandations de Soul pour les tableaux distinguent les en-têtes, les lignes, les cellules et une barre récapitulative facultative. Les valeurs numériques sont alignées à droite ; le texte, à gauche. Un récapitulatif peut présenter des totaux ou des moyennes : son libellé doit donc préciser l’opération plutôt que d’afficher un nombre sans explication.

Utilisez N/A lorsqu’une mesure ne s’applique pas, par exemple pour la durée d’une vidéo associée à une image. Un tiret cadratin indique une donnée indisponible ou inconnue. Ces cas ne doivent pas être remplacés par zéro : cela modifierait l’interprétation du récapitulatif et de toute comparaison fondée sur celui-ci.

  • Le spécimen actuel permet le tri et la sélection des lignes, mais ne calcule pas de récapitulatif.
  • Les lignes développées et les explications concernant les données manquantes sont des possibilités d’extension documentées ; elles ne sont pas simulées dans l’aperçu.
  • La référence de conception indique que le tableau React est prévu ; le code fourni gère donc lui-même le balisage du tableau au lieu d’inventer un import Soul DataTable.

Consultez la spécification associée

Le mode groupé modifie les actions disponibles

Soul place la barre d’actions groupées sous la collection et masque les actions individuelles des lignes lorsque la sélection groupée est active. La case à cocher de l’en-tête présente trois états : cochée, décochée et indéterminée. Le tri se limite à une seule colonne à la fois.

Dans le spécimen, les trois enregistrements sont locaux et restent dans le périmètre de sélection. L’en-tête « portée » indique le sens du tri ; les identifiants sélectionnés sont conservés après le réordonnancement. Toute action future au niveau d’une ligne devra respecter la restriction documentée du mode groupé, plutôt que de faire concurrence à la barre d’outils de traitement par lot.

Consultez la spécification associée

Créer de la profondeur avec des couches neutres — système de design Emplifi Soul

Un espace de travail CX tout en retenue

Le mode clair de Soul alterne les surfaces grises et blanches, tandis que les couches sombres s’éclaircissent progressivement. Le spécimen utilise une page grise, une surface de tableau blanche et une barre de navigation sombre et compacte. La couleur indique une fonction plutôt que de décorer chaque ligne.

Le bleu interactif est réservé à l’action de validation et aux contrôles sélectionnés. Les petites illustrations originales des publications apportent une touche de couleur décorative. Elles aident à distinguer les sujets sans leur attribuer à tort une signification de succès ou de danger.

Consultez la spécification associée

Système de design Emplifi Soul — une typographie compacte sans perdre la hiérarchie

Inter est la famille principale

Soul utilise Inter dans toute l’interface, Noto Sans Arabic pour le texte arabe et Noto Sans Mono pour le code. L’aperçu utilise les polices système, car il ne contient pas ces fichiers de polices. Les mesures restent fondées sur les recommandations publiées.

Un titre principal de 30/42 ouvre un système de texte courant en 13/18. Les chiffres du tableau utilisent des formes tabulaires. Le tableau n’adopte pas le style d’affichage surdimensionné des pages marketing, et les titres des publications restent du texte lisible plutôt que des libellés intégrés à une image.

Consultez la spécification associée

Système de design Emplifi Soul — rythme de six pixels et rayon des conteneurs

Organisez les contrôles denses

L’unité de base de l’espacement est de 6 px. Des valeurs telles que 12, 18, 24 et 36 px définissent des espacements plus importants ; les valeurs de 3 et 9 px sont réservées aux éléments internes compacts des composants, plutôt qu’aux marges de page par défaut. Le retrait du contenu passe de 24 px à 1559 px et moins à 36 px à partir de 1560 px.

Soul distingue les valeurs numériques d’espacement des tailles de composants de type T-shirt. Un contrôle moyen ne correspond pas à --space-6. L’exemple utilise des contrôles de 36 px, un arrondi des éléments de 6 px et un rayon de conteneur de 8 px.

Consultez la spécification associée

Système de design Emplifi Soul — mettez l’accent sur l’action suivante

Une seule action principale de validation

La variante principale de Soul met en avant l’action prioritaire. Les variantes claire et fantôme conviennent aux actions secondaires ; les contrôles invisibles allègent les barres d’outils denses. Dans l’aperçu, seule l’action de validation groupée bénéficie du style principal plein.

L’annulation de la sélection désélectionne les lignes sans modifier leur statut de validation. La validation ne modifie que l’état local, et le message précise explicitement qu’aucune publication n’a été effectuée. Le texte des contrôles utilise la casse de phrase.

Consultez la spécification associée

Système de design Emplifi Soul — chargez la bibliothèque privée de manière réfléchie

Foundation CSS précède la composition des composants

Le point d’entrée officiel importe variables.css et default-styles.css depuis @sbks/ds-design-library. Son point d’entrée Sass fournit des mixins ; il est distinct du CSS global. Button provient de @sbks/ds-button.

L’API du composant Button API comprend isLoading, isSelected, isApplied et badge. Les props associées à un enum nécessitent les constantes d’enum exportées par la bibliothèque dans TypeScript. Cet exemple utilise la variante LIGHT par défaut, vérifiée, plutôt que de supposer un chemin d’import pour l’enum.

  1. Effectuez la configuration autorisée du périmètre privé et des chargeurs de compilation en suivant le guide de démarrage rapide officiel.
  2. Importez une seule fois le CSS de fondation dans le point d’entrée de l’application et configurez les ressources de polices choisies.
  3. Montez l’exemple de tableau contrôlé fourni, puis testez la sélection, l’annulation et la validation locale avant de connecter un flux de publication.

Consultez la spécification associée

Système de design Emplifi Soul — exemples de composants

Exemple interactif autonome complet

Enregistrez le document complet sous index.html et ouvrez-le dans un navigateur. Interprétation indépendante des recommandations de design Soul et des jetons vérifiés du mode clair, en HTML/CSS. Polices système de substitution ; aucune ressource React privée.

html
<!doctype html><html lang="en"><meta charset="utf-8"><meta name="viewport" content="width=device-width, initial-scale=1"><title>Content review</title><style>:root{--color-layer-level-0:#f3f3f5;--color-layer-level-1:#fff;--color-on-layer-primary:#24242b;--color-on-layer-secondary:#505057;--color-button-primary:#0c4bff;--space-2:6px;--space-4:12px;--space-6:24px;--border-radius-medium:6px;--border-radius-large:8px}*{box-sizing:border-box}body{margin:0;background:var(--color-layer-level-0);color:var(--color-on-layer-primary);font:13px/18px system-ui}nav{padding:15px 24px;background:#111114;color:#f9f9fa;font-size:13px;display:flex;justify-content:space-between;gap:24px}main{padding:24px}header{display:flex;align-items:flex-start;justify-content:space-between;gap:18px;margin-bottom:24px}h1{font-size:30px;font-weight:500;line-height:42px;margin:0}p{color:#505057;margin:6px 0}small{font-size:11px}.surface{background:white;border:1px solid #ddd;border-radius:8px;overflow:hidden}.bar{padding:18px 24px;border-bottom:1px solid #ddd;display:flex;justify-content:space-between;gap:12px}table{width:100%;border-collapse:collapse;table-layout:fixed}caption{text-align:left;padding:12px 24px;background:#f9f9fa;font-size:11px;color:#505057}th,td{padding:16px 12px;text-align:left;border-bottom:1px solid #e7e7e7;font-weight:400}thead th{font-size:11px;font-weight:600;padding-top:12px;padding-bottom:12px}th:first-child,td:first-child{width:44px;text-align:center}.title{width:46%}.reach{width:15%;text-align:right;font-variant-numeric:tabular-nums}tbody tr:nth-child(even){background:#f9f9fa}tbody tr:hover{background:#d5efff}input{accent-color:#003beb;width:16px;height:16px;cursor:pointer}input:focus-visible,button:focus-visible{outline:2px solid #003beb;outline-offset:3px}button{font:600 13px/18px system-ui;border:1px solid #ccc;background:white;padding:8px 12px;border-radius:6px;min-height:36px;cursor:pointer;color:inherit}button:hover{background:#f3f3f5}#sort{border:0;background:transparent;padding:0;min-height:28px;color:#003beb}#apply{background:#0c4bff;color:white;border-color:#0c4bff}#apply:hover{background:#003beb}.name{display:flex;align-items:center;gap:12px}.art{width:52px;height:52px;flex:0 0 52px;border-radius:6px;position:relative;overflow:hidden}.field{background:#d4e5d3}.field:before{content:'';position:absolute;width:65px;height:65px;border-radius:50%;background:#7ca77a;left:15px;top:20px}.field:after{content:'';position:absolute;width:16px;height:16px;border-radius:50%;background:#fff1c5;left:8px;top:8px}.studio{background:#e6daee}.studio:before{content:'';position:absolute;width:20px;height:36px;background:#a089b2;left:8px;top:16px;transform:rotate(-14deg)}.studio:after{content:'';position:absolute;width:20px;height:28px;background:#c3abc9;left:30px;top:24px;transform:rotate(12deg)}.guide{background:#f4e4c9}.guide:before{content:'';position:absolute;width:26px;height:38px;background:#fff;left:13px;top:9px;transform:rotate(8deg);border:1px solid #c9ad7c}.name strong{font-weight:600;display:block}.name small{color:#505057}.state{font-size:11px;color:#505057}#bulk{display:flex;align-items:center;justify-content:space-between;gap:12px;padding:12px 24px;background:#f3f3f5;border-top:1px solid #ccc}#bulk[hidden]{display:none}.actions{display:flex;gap:6px}#status{margin:18px 0;min-height:18px}footer{padding:0 24px 20px;color:#505057;font-size:11px}@media(min-width:1560px){main{padding:36px}}@media(max-width:600px){main{padding:18px}.bar{padding:12px}.channel{display:none}.title{width:57%}.reach{width:22%}.state{display:block;margin-top:4px}th,td{padding:12px 6px}.art{width:36px;height:42px;flex-basis:36px}.name{gap:6px}#bulk{padding:12px;flex-direction:column;align-items:stretch}.actions{flex-wrap:wrap}header{flex-direction:column;gap:8px}h1{font-size:27px}.bar small{max-width:140px;text-align:right}nav{padding:14px 18px}}</style><nav><strong>Soul / Content workspace</strong><span>Demo collection</span></nav><main><header><div><h1>Content review</h1><p>A final editorial check before your team publishes.</p></div><small>3 fictional drafts · No publishing connection</small></header><section class="surface" aria-label="Content drafts"><div class="bar"><strong>Draft collection</strong><small>Select items to review together</small></div><table><caption>Local sample data. Reach values are illustrative.</caption><thead><tr><th scope="col"><input id="all" type="checkbox" aria-label="Select all drafts"></th><th scope="col" class="title">Content</th><th scope="col" class="channel">Channel</th><th scope="col" class="reach" id="reach-head" aria-sort="none"><button id="sort">Reach ↕</button></th></tr></thead><tbody id="rows"></tbody></table><div id="bulk" hidden><span id="count"></span><div class="actions"><button id="apply">Mark as reviewed</button><button id="cancel">Cancel selection</button></div></div></section><p id="status" role="status">Select a draft to begin. All changes stay in this example.</p></main><footer>Independent Soul interpretation · verified light-mode tokens · system font fallback</footer><script>let items=[{id:'field',title:'A morning in the field',channel:'Instagram',reach:2480},{id:'studio',title:'Inside the studio',channel:'Facebook',reach:1860},{id:'guide',title:'Care guide: summer edition',channel:'Instagram',reach:3210}],selected=new Set(),reviewed=new Set(),direction=0;const rows=document.querySelector('#rows'),all=document.querySelector('#all'),bulk=document.querySelector('#bulk'),status=document.querySelector('#status');function render(){rows.innerHTML=items.map(i=>`<tr><td><input type="checkbox" data-id="${i.id}" aria-label="Select ${i.title}" ${selected.has(i.id)?'checked':''}></td><th scope="row"><div class="name"><div class="art ${i.id}" aria-hidden="true"></div><div><strong>${i.title}</strong><span class="state">${reviewed.has(i.id)?'Reviewed locally':'Not reviewed'}</span></div></div></th><td class="channel">${i.channel}</td><td class="reach">${i.reach.toLocaleString('en-US')}</td></tr>`).join('');rows.querySelectorAll('input').forEach(x=>x.onchange=()=>{x.checked?selected.add(x.dataset.id):selected.delete(x.dataset.id);sync()});sync()}function sync(){all.checked=selected.size===items.length;all.indeterminate=selected.size>0&&selected.size<items.length;bulk.hidden=!selected.size;document.querySelector('#count').textContent=selected.size+' selected'}all.onchange=()=>{selected=all.checked?new Set(items.map(i=>i.id)):new Set();render()};document.querySelector('#cancel').onclick=()=>{selected.clear();render();all.focus()};document.querySelector('#apply').onclick=()=>{let n=selected.size;selected.forEach(x=>reviewed.add(x));selected.clear();render();status.textContent=n+(n===1?' draft':' drafts')+' reviewed locally. Nothing published.';all.focus()};document.querySelector('#sort').onclick=()=>{direction=direction===1?-1:1;items.sort((a,b)=>(a.reach-b.reach)*direction);document.querySelector('#reach-head').setAttribute('aria-sort',direction===1?'ascending':'descending');document.querySelector('#sort').textContent='Reach '+(direction===1?'↑':'↓');render()};render();</script></html>

Référence du code

  • Le tableau gère directement la sélection et le tri en HTML. Il ne prétend pas utiliser un export privé Soul DataTable ; l’exemple React utilise l’export Button vérifié avec un tableau développé par l’application.

Tableau de validation sélectionnable avec de vrais boutons Soul

Tableau sémantique natif et cases à cocher contrôlées, composés avec l’export Button documenté. Le tableau relève du code de l’application ; il ne s’agit pas d’un composant Soul DataTable inventé.

tsx
// ContentReview.tsx — inside a configured, authorized Soul application
import React, { useState } from 'react';
import { Button } from '@sbks/ds-button';
import '@sbks/ds-design-library/dist/css/variables.css';
import '@sbks/ds-design-library/dist/css/default-styles.css';

const posts = [
  { id: 'field', title: 'A morning in the field', channel: 'Instagram' },
  { id: 'studio', title: 'Inside the studio', channel: 'Facebook' },
  { id: 'guide', title: 'Care guide: summer edition', channel: 'Instagram' }
];
export default function ContentReview() {
  const [selected, setSelected] = useState<string[]>([]);
  const [reviewed, setReviewed] = useState<string[]>([]);
  const [message, setMessage] = useState('');
  const toggle = (id: string) => setSelected(previous =>
    previous.includes(id) ? previous.filter(x => x !== id) : [...previous, id]);
  const review = () => {
    setReviewed(previous => [...new Set([...previous, ...selected])]);
    setMessage(`${selected.length} items reviewed locally. Nothing published.`);
    setSelected([]);
  };
  return <section aria-labelledby="review-title">
    <h1 id="review-title">Content review</h1>
    <table style={{ width: '100%', borderCollapse: 'collapse' }}>
      <caption>Fictional content drafts</caption>
      <thead><tr><th scope="col">Select</th><th scope="col">Content</th>
        <th scope="col">Channel</th><th scope="col">Review</th></tr></thead>
      <tbody>{posts.map(post => <tr key={post.id}>
        <td><input type="checkbox" aria-label={`Select ${post.title}`}
          checked={selected.includes(post.id)} onChange={() => toggle(post.id)} /></td>
        <th scope="row">{post.title}</th><td>{post.channel}</td>
        <td>{reviewed.includes(post.id) ? 'Reviewed locally' : 'Not reviewed'}</td>
      </tr>)}</tbody>
    </table>
    {selected.length > 0 && <div aria-label="Bulk actions"
      style={{ display: 'flex', gap: 'var(--space-2)', marginTop: 'var(--space-6)' }}>
      <Button onClick={review}>Mark {selected.length} as reviewed</Button>
      <Button onClick={() => setSelected([])}>Cancel selection</Button>
    </div>}
    <p role="status">{message}</p>
  </section>;
}

Référence du code

  • La variante par défaut de Button est LIGHT. Cet exemple ne suppose ni l’emplacement d’export d’un enum ni des props DataTable inventées.
  • Installez et configurez d’abord la bibliothèque de design et les packages de boutons privés. Les imports sont vérifiés dans le Storybook officiel.
  • La validation groupée ne met à jour que l’état local. Aucun contenu n’est publié.
04

Emplifi Soul Configuration de l’agent du système de design

Point de départ de l’implémentation

Le guide de démarrage rapide officiel nécessite un accès au registre npm privé, au dépôt Emplifi et au VPN. Il prend en charge React 18/19 et Webpack 4/5, avec une configuration de Sass et du chargeur SVG. Suivez la procédure d’intégration liée pour accéder au périmètre interne, plutôt que de chercher ces packages dans le registre public. L’aperçu autonome n’a besoin d’aucune de ces ressources privées.

bash / tsx
# For authorized Emplifi environments with the private @sbks scope configured:
npm i -D @sbks/ds-design-library @sbks/ds-button

// Application entry:
import "@sbks/ds-design-library/dist/css/variables.css";
import "@sbks/ds-design-library/dist/css/default-styles.css";

// Optional SCSS file:
@use "@sbks/ds-design-library/dist/sass/main.scss" as *;

Un prompt pour votre projet

Prompt pour l’agent IA
Créez une interface de validation de contenu Emplifi Soul avec des variables vérifiées pour les couches, les couleurs et les espacements, une typographie de texte courant en 13/18, un rayon de contrôle de 6 px et des conteneurs de 8 px. Utilisez un tableau sémantique sélectionnable avec des identifiants stables, une sélection globale à l’état indéterminé et une colonne triée. Pour les applications autorisées, utilisez le véritable export @sbks/ds-button et le CSS de fondation ; n’inventez jamais de package DataTable public.
05

Emplifi Soul Sources et périmètre du système de design

Soul est le système de design d’Emplifi. Ses références publiques de conception et son Storybook sont consultables, mais le guide de démarrage officiel nécessite l’accès à une portée npm privée. Le spécimen dans le navigateur est une réalisation indépendante HTML/CSS ; il n’intègre pas Soul React. Le comportement du tableau interprète les recommandations de conception, dont la page publique indique encore que React est prévu.