Skip to content

SVG structure and metadata

A SimpleDiagrams SVG is an ordinary static SVG with additional attributes that describe which paints follow the diagram's fill and line controls. It should look correct in a browser before those controls are applied. The geometry and metadata together let the same source serve desktop and web shape libraries.

This page is for people drawing, generating, or maintaining SVGs for SimpleDiagrams 5 for macOS. Start with Preparing SVGs for the visual explanation of strokes and fills.

What desktop import does

Dragging an SVG onto the canvas offers two representations:

  • Convert to Editable Shape compiles the drawing into SimpleDiagrams' native vector format and links its paints to the diagram's fill and line controls.
  • Keep as SVG Artwork preserves the supported authored appearance. Internal paints do not follow the diagram's colour controls.

Keep the original SVG for future artwork revisions. Editable conversion does not retain the SVG's named layers, XML, or individually editable illustration nodes. Its result is a native diagram shape you can place, resize, rotate, recolour, label, and connect.

One file, one meaning

Convert to Editable Shape reads the data-sd-fill and data-sd-stroke metadata described below. An SVG that carries any of it is converted the same way a published library shape is: marked parts follow the diagram's fill and line controls, and parts marked keep, or not marked at all, stay the colour you drew. An SVG with no metadata is converted by looking at its actual fills and strokes instead (see "Construct the paint").

For example, green leaves and a terracotta pot marked keep retain those colours after conversion while the pot's outline follows the line control. They are fixed, not a third colour control: adding more metadata does not create additional controls.

If a marking is misspelt (Fill-chip) or placed on an element that cannot carry one (the root svg, a title), that one marking is left out and the import sheet says "unrecognized color markings". The part then follows the marking of the group it sits in, or keeps its drawn colour if there is none. The other markings still apply. If that was the file's only marking, nothing is left to follow the controls and every colour stays as drawn. Library publishing is stricter and refuses such a file, so fix the typo at the source.

Construct the paint before adding metadata

Each SVG drawable can have two independent paints: a fill for its interior and a stroke for its outline. For predictable ordinary desktop conversion:

Part of the drawing Authored SVG paint Editable result
Pot, leaf, box face, or other surface White fill and black stroke on the same closed drawable Interior follows fill; outline follows line
Stem, leaf vein, vent, or other open line fill="none" and black stroke Follows line
Solid ink dot or small ink detail Black fill and stroke="none" Follows line in otherwise conventional black-and-white artwork

These rules apply to an SVG with no data-sd-* metadata. Every actual stroke becomes line paint. A fill on a drawable that also has a stroke becomes fill paint. Fill-only geometry requires a fallback: the importer compares tones across the drawing (a stroked part contributes its stroke colour, a fill-only part its fill colour), assigns darker fill-only parts to line paint and lighter ones to fill paint. If every sampled tone is essentially the same, all fill-only parts become line paint, with one exception: a drawing with no strokes at all whose fills are exactly one colour is a silhouette. All of it becomes fill paint, and the shape starts with a black fill (#000000) instead of the ordinary white editable default, so it still appears as drawn. As with any converted shape, a fill colour you have chosen in the toolbar is applied over that starting colour.

That silhouette rule explains a surprise: a drawing made only of white filled shapes, with no strokes anywhere, comes out entirely in the fill colour and starts black. Give surfaces a real stroke, on the same face as their fill. Likewise, an expanded outline is a filled silhouette, not a line. Keep outlines as real strokes.

Write absent paint as none. A transparent colour, zero opacity, or zero stroke width does not remove the stroke structurally; conversion can still classify its fill as a surface, and replacing the source colour or width can reveal a previously invisible stroke.

Canonical paint metadata

These attributes describe paint roles. Desktop reads them during Convert to Editable Shape and when compiling a published library; the website reads them when rendering a reviewed shape. Use the exact lower-case names and values:

Attribute Value Behaviour
data-sd-fill fill-chip Fill follows the diagram fill colour and texture
data-sd-fill stroke-chip Fill follows the diagram line colour and texture; useful for ink dots
data-sd-fill keep Fill keeps its authored paint
data-sd-stroke stroke-chip Stroke follows the line colour and texture and the shape's line width
data-sd-stroke fill-chip Stroke follows the fill colour and texture, keeping its authored width
data-sd-stroke keep Stroke keeps its authored paint and width

Dashes, caps, and joins stay as drawn in every case; choosing an Outline Pattern replaces the dash of strokes that follow the line colour. A paint that follows a control ignores the SVG's fill-opacity and stroke-opacity, because its transparency comes from the colour you choose. opacity on an element or group is kept.

Put the attributes on a drawable such as path or circle, or on a g group. Do not put them on the root svg, title, desc, or definition containers. Unknown values and misplaced attributes fail library publishing; ordinary desktop conversion drops them, reports them, and honours the rest.

The attributes identify which parts can change, not the colour a library shape starts with. A first-party library master may set an initial editable fill in its separate shape.json metadata as default_fill_hex (uppercase #RRGGBB); without that field, the library default is white. Fixed details marked keep still use their authored SVG colours. Dragging an ordinary SVG onto the desktop canvas reads the SVG's own markings but not library metadata. The colours drawn on parts that follow a control are a preview only: a converted shape starts white with a black 1-point line, with your current toolbar colours applied over that. Each library also has an Initial colors setting that decides whether its shapes arrive in their own colours or yours; see Using libraries.

Published library packages carry this default per shape. The website's upload check compares each package fill with its reviewed master metadata, so a package cannot silently substitute white for a domain colour. Package thumbnails must depict the same default that a newly placed shape receives.

The two roles inherit independently through groups. A descendant can override one role without changing the other. With no marking on an element or its ancestors, that channel defaults to keep: leaving a part unmarked is the normal way to say it must never change with the diagram's colours. Writing keep explicitly does the same thing and lets another author see the intent.

none still means no paint: a role chooses how to colour an existing paint channel; it does not turn fill="none" into a filled surface.

Declare both paints at each new chip marking

There is one inheritance rule that needs special care. An element with its own fill-chip or stroke-chip marking starts a paint root. At that element, a missing fill starts again at SVG's default black, and a missing stroke starts again at none. Either channel's chip marking resets both missing paints, even when a parent supplied them. Width, dash, opacity, and transforms still inherit. Inherited markings and an element's own keep markings do not start a new paint root.

The practical rule is simple: whenever you add a chip marking to a group or drawable, also write both its fill and stroke. Unmarked children can inherit those explicit paints safely.

For example, this element snippet is a correctly marked detail line:

<path d="M8 16 C12 15.8 17 16.2 22 16"
      fill="none" stroke="#000000" stroke-width="1"
      data-sd-fill="keep" data-sd-stroke="stroke-chip"/>

Without those explicit paints, a browser could inherit a parent's line paint and look correct while desktop conversion and the published-master consumer produce a black filled curve with no stroke. Metadata does not change how an ordinary browser renders SVG, which is why a browser preview alone cannot verify the file.

Complete working example

Save this entire example as example-cabinet.svg. It contains a surface, two detail lines, and an ink dot, with a transparent background. Its geometry is deliberately simple; hand-drawn styling is discussed below.

<svg xmlns="http://www.w3.org/2000/svg"
     width="80" height="80" viewBox="0 0 80 80">
  <title>Example cabinet</title>
  <g fill="#ffffff" stroke="#000000" stroke-width="1"
     stroke-linecap="round" stroke-linejoin="round"
     data-sd-fill="fill-chip" data-sd-stroke="stroke-chip">
    <path d="M14 12 L66 12 L66 68 L14 68 Z"/>
  </g>
  <g fill="none" stroke="#000000" stroke-width="1"
     stroke-linecap="round" stroke-linejoin="round"
     data-sd-fill="keep" data-sd-stroke="stroke-chip">
    <path d="M24 48 L56 48 M24 55 L56 55"/>
  </g>
  <g fill="#000000" stroke="none"
     data-sd-fill="stroke-chip" data-sd-stroke="keep">
    <circle cx="25" cy="27" r="2"/>
  </g>
</svg>

Every surface owns its fill and stroke together. The groups establish explicit paint and metadata; their unmarked children inherit them. No special namespace, JSON metadata block, legacy layer name, or application-specific file extension is needed.

A portable SVG vocabulary

For newly generated basic shapes, use this conservative subset even if your drawing tool can export more:

  • One root svg with xmlns="http://www.w3.org/2000/svg", positive numeric width and height, and a viewBox containing four finite numbers with positive width and height. Unitless dimensions are simplest.
  • Direct path, rect, circle, ellipse, polygon, polyline, and line geometry, grouped with g. Optional title and desc describe the artwork.
  • Direct presentation attributes for fill, stroke, width, cap, join, and fill rule. Prefer explicit solid hex colours and round line caps and joins.
  • A small margin around the visible geometry, including the full stroke. Keep the background transparent; do not add a canvas-sized white rectangle.
  • UTF-8 source. Prefer a descriptive filename such as potted-plant.svg.

Avoid text, embedded images, gradients, patterns, filters, masks, CSS, animation, external references, nested SVG viewports, and editor-specific effects. For this subset, draw repeated geometry directly instead of using definitions and references, and resolve transforms into coordinates when practical. Desktop supports some broader SVG features, but a smaller vocabulary makes portable generated files easier to inspect and convert without losses. Unsupported effects are left out and named on the import sheet. A few constructs make Convert to Editable Shape unavailable altogether: a nested svg, a colour written as hsl() or as most colour names, a CDATA section, and CSS rules other than simple class selectors.

If lettering is essential to the illustration, convert it to path geometry; it will no longer be editable text. For an editable caption, add a label in SimpleDiagrams after import.

Do not add vector-effect="non-scaling-stroke" to the source; desktop leaves it out and says so. SimpleDiagrams manages stroke scaling: native desktop geometry is resized before strokes are drawn, and the shared web renderer supplies its own non-scaling behaviour. A stroke that follows the line colour is drawn at the shape's line width, 1 point until you change it, at any size, and an SVG is placed at its width and height in points. Draw your strokes at stroke-width="1" and the SVG looks the way it will import; any other source width is only a preview.

Keep reusable shared artwork at or below 500,000 bytes. This is the shared web asset ceiling and a useful authoring budget, not the desktop import limit; desktop's editable XML boundary accepts up to 8 MiB, with additional structural limits. Simple symbols should be much smaller than either ceiling. Lower-case filenames are a portable convention; desktop also accepts spaces and uppercase names.

Avoid IDs containing _fill, _stroke, _ignore, or their escaped _x5F_ forms. In an SVG with no data-sd-* metadata they still act as paint instructions. Use descriptive neutral IDs such as pot-body, or omit IDs.

Drawing a clean hand-drawn line

The hand-drawn appearance belongs in the path geometry. Start with the correct shape and add small, smooth, irregular deviations along it. Several restrained imperfections read more like a drawn line than one large bend. Vary their spacing and amplitude so the contour does not look like a regular wave.

Apply the treatment to curved contours as well as straight edges: a plant's leaves, stems, veins, pot sides, and rim should feel drawn by the same hand. Retain the silhouette and important corners. At normal diagram size, check that the imperfection is visible without making the object look swollen or distorted. A high-zoom view alone is misleading. With a width-1 line in a drawing 64 to 100 units across, deviations of about 0.25 units are a good starting point.

For isometric objects, construct the geometry first using axes approximately 30 degrees above and below horizontal, with vertical edges vertical. Hold endpoints and shared corners fixed, then perturb the lines gently around those baselines. Reuse the same shared edge in reverse on adjoining faces; independent waviness creates doubled seams. When reversing a cubic curve, reverse its control points as well as its endpoints.

Draw overlapping objects back-to-front. Test with a transparent fill or a native texture whose gaps reveal the background: solid white fills can conceal unwanted backing plates or internal lines. Do not expand strokes or use a filter to simulate pencil texture. The app's native textures can be applied after conversion.

Check the result in SimpleDiagrams

  1. Open the SVG in a browser to catch broken geometry, clipping, and poor readability. Check both a normal placed size and a larger view.
  2. Drag it onto the desktop canvas and choose Convert to Editable Shape. Read any loss warnings, but do not treat their absence as proof of correct paint mapping.
  3. Choose a conspicuous fill colour and a different line colour. Check that bodies follow fill, and outlines, details, and ink dots follow line.
  4. Resize larger and smaller, and try a different line width. Check seams, clipping, recognisability, and line quality.
  5. Try transparent fill and a native texture. Look for unexpected background plates and overlapping geometry.
  6. Save and reopen the diagram, then check an export if that is how the artwork will be shared.

A source linter can catch missing paints, invalid role values, and unsupported constructs. It cannot prove that a line looks hand-drawn or that the native import has the intended result. Published-master validation is also separate from ordinary editable import; use the appropriate library build process to verify fixed paints and metadata mappings before distributing a library.

Keep provenance and licensing with the source artwork. A valid SVG is an asset, not a complete shape-library package: library identity, names, keywords, and other catalogue settings belong in the library's metadata. Do not invent SVG attributes for them. See Your own libraries for the desktop workflow.