Skip to content
C.W.K.
Stream
Lesson 03 of 04 · published

Art Carries Mood, Data Carries Facts

~13 min · generative-art, provenance, acceptance-criteria, real-pixels

Level 0Cold Workshop
0 XP0/35 lessons0/12 achievements
0/100 XP to next level100 XP to go0% complete

A Line Drawn Through the Middle of Every Frame

The workshop can put generated images on screen, and it routes every one of them through the family image engine rather than calling a provider itself — the same ownership rule as voice. But the interesting constraint is not where the images come from. It is what they are allowed to depict.

Every frame in a render falls into one of three categories, and the categories do not mix. Factual frames render from code and data — names, numbers, structures, anything a viewer could be misled by. Application visuals are real screenshots of live software, never mockups. Generated art carries mood and transitions only.

The hard gate sits on that third category: an art card that grows readable fake interface elements, invented application names, or numbers gets rejected outright. Not softened, not labeled — rejected and regenerated. The reasoning is that the claim "everything factual on this screen is real" is indivisible. One blurred boundary does not cost you that one frame; it costs the credibility of every other frame, because the viewer now has to wonder about each one.

Judging Generated Output Without Fooling Yourself

Generated images need acceptance criteria, because "does it look good" is not a decision procedure. The layered version that works looks like this:

Hard gates come first and are non-negotiable: text must be letter-perfect at full resolution, anatomy must survive inspection, and there must be no factual pollution. Any failure is a regeneration, with no discussion, because these are the failures a viewer notices instantly.

Measured checks come next, and the key move is to judge at delivery size. A card evaluated at full resolution on a large display is being judged under conditions no viewer will ever experience. Downscale it to the size and dwell time it actually gets. Things that looked fine at full size collapse; things that looked slightly rough turn out to be invisible.

Comparative selection comes last, and it is the one that changes results most. Absolute quality judgment is unreliable — asking "is this good?" gets you an answer shaped by what you were hoping for. Relative ranking is far more robust. So generate several candidates per slot, rank them against the criteria, ship the winner, and log every loser with its failure reason, which is what makes the taste auditable later.

Code

The three categories, and the gate between them·text
FACTUAL      rendered from code + data
             names, quantities, structures, relationships
             -> deterministic. same inputs, same pixels.

APPLICATION  real screenshots of software that actually runs
             -> never a mockup, never a redraw, never "close enough"

ART          generated; mood, texture, transitions
             -> HARD GATE: no readable interface elements,
                no invented product names, no numbers,
                no fake data of any kind

# The gate is absolute because the credibility claim is global:
# a viewer who catches ONE invented detail must now doubt all of them.
Acceptance as a pipeline, not an opinion·python
def accept(candidates: list[Card], slot: Slot) -> Card:
    """Layered acceptance. Hard gates first, ranking last."""
    survivors = []
    for c in candidates:
        if not text_letter_perfect(c, at="full"):
            log_rejection(c, "text malformed at full resolution")
            continue
        if has_factual_pollution(c):        # fake UI, invented names, digits
            log_rejection(c, "factual pollution: art may not assert facts")
            continue
        if not anatomy_ok(c):
            log_rejection(c, "anatomy")
            continue
        survivors.append(c)

    if not survivors:
        raise NoAcceptableCandidate(slot)   # regenerate; never "ship the least bad"

    # judged at DELIVERY size, not authoring size
    ranked = sorted(survivors, key=lambda c: score(c.downscaled(slot.display_size)))
    winner = ranked[-1]
    for loser in ranked[:-1]:
        log_rejection(loser, f"ranked below winner: {compare(loser, winner)}")
    return winner

External links

Exercise

Take any interface or document you produce that mixes real data with illustrative or placeholder content. Draw the line explicitly: list which elements are load-bearing facts and which are decoration. Then check whether a reader could tell them apart without being told. If they could not, you have the same problem this lesson describes, and the fix is a visible rule rather than a caption nobody reads.
Hint
Placeholder data in demos is the classic case — a screenshot with invented but plausible numbers gets reused in a document, and by the third reuse nobody remembers it was fake. If invented content can be mistaken for real, either mark it structurally or do not generate it in that shape at all.

Progress

Progress is local-only — sign in to sync across devices.
Spotted a bug or have feedback on this page?Report an Issue

Comments 0

🔔 Reply notifications (sign in)
Sign inPlease sign in to comment.

No comments yet — be the first.