Module
LinkClassify boundaries between measured clusters, then plan the supplied paragraph items with an explicit cost model. Identical inputs and policies produce deterministic boundaries, costs, and errors. Inspect optimized and greedy plans with typed physical widths, source unit intervals, and the recorded search result.
Why
LinkTopaz gives physical lengths a type that application code and paragraph planning can share. This module connects measured text clusters, break policies, and paragraph plans through that common length model. Explicit policies let applications select line breaking and justification behavior while retaining typed geometry.
Availability
LinkImport std.typeset in language mode 5.21. The current compiler selects std/typeset.tpz for this language mode. Availability in other released editions and inclusion in each installed distribution are Pending.
Exported types
Linkenum Break
enum Typeset
enum Distance
enum Break
enum Kinsoku
enum Justification
enum Cost
enum Break
record Box { unit
record Glue { unit
record Penalty { unit
enum Item { Box
record Break
record Break
record Break
record Latin
record Justification
record Line
record Knuth
record Paragraph { grid:Distance
record Plan
record Paragraph
record Paragraph
Type members keep the compiler-owned type name shown in their declarations. Importing a module does not create a new type identity.
Public API
LinkTypesetError.NoBreakOpportunities
JustificationMode.LatinWordSpace
JustificationMode.CjkInterCharacter
BreakPolicy.generatedHyphenEnds
BreakPolicy.protectFittingLatin
BreakPolicy.preserveShortWords
BreakPolicy.narrowestWordTarget
LatinSpacing.minWordSpaceRatio
LatinSpacing.maxWordSpaceRatio
LatinSpacing.maxLetterSpacingEm
JustificationPolicy.minGapCount
JustificationPolicy.minLineWidthRatioM
JustificationPolicy.minFinalLineWidthRatioM
JustificationPolicy.maxAdjustment
JustificationPolicy.maxGapAdjustment
JustificationPolicy.maxGapRatioR
JustificationPolicy.latinSpacing
JustificationPolicy.cjkStretchRatio
KnuthPlassPolicy.fitnessDemerit
KnuthPlassPolicy.flaggedDemerit
KnuthPlassPolicy.finalFlaggedDemerit
PlanLine.displayTextScalarLength
PlanLine.postValidationWidthLimit
ParagraphPlan.boundedFillFeasible
Pending contracts
LinkConvert physical lengths with toScaledPoints
LinkConvert physical lengths with toScaledPoints
Physical Length values with the Pt, Mm, Cm, or In marker provide toScaledPoints returning int. One point is 65,536 scaled points. The result is the exact stored signed 64-bit count.
The scaledPoints member is absent from every Length type. Calling that removed member is rejected with TPZ5006. Length<Em> has no toScaledPoints member and must resolve to a physical length first.
fromScaledPoints accepts every int from -9223372036854775808 through 9223372036854775807 inclusive. It returns Length<Pt> with that exact scaled-point count. Zero and negative inputs are valid. Construction performs no rounding and has no value-dependent failure.
fromMilliPoints interprets its int argument as thousandths of a point. Its scaled-point result is roundEven of the exact rational input times 8192 divided by 125.
fromMilliPoints accepts -140737488355328000 through 140737488355327999 inclusive. An input outside that range stops with runtime diagnostic TPZ4004. It does not return Result, wrap, saturate, or clamp.
Length<Pt>.toMilliPoints returns roundEven of the exact stored count times 125 divided by 8192. Every representable point length has a representable int result.
roundEven selects the nearest integer and chooses the even integer at an exact tie. Positive and negative ties follow the same rule. Range checking applies to the final rounded value. Intermediate arithmetic must preserve the exact rational value.
A count of 4096 scaled points converts to 62 millipoints. A count of 12288 converts to 188. Their negatives convert to -62 and -188. One millipoint constructs 66 scaled points and negative one constructs -66.
Millipoint conversion can lose scaled-point precision. A conversion to millipoints and back need not recover the original length. The maximum point length converts to 140737488355328000 millipoints, which exceeds the fromMilliPoints input range.
The constructors require int arguments. A float or Length argument is rejected with TPZ5001. Physical conversions and scalar arithmetic do not provide an implicit integer constructor.
A constructor evaluates its argument once before checking the result range. A receiver conversion evaluates its receiver once. These operations perform no I/O or mutation and read no font or paragraph state.
A fromMilliPoints overflow is reported at the public constructor call. Earlier argument effects remain visible and later expressions do not execute.
Why
Integer conversions use the same to prefix as unit conversions and collection conversions. Scaled points and millipoints remain distinct because they represent different units and rounding boundaries.
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Convert every physical length unit to scaled points
Linkimport std.ioimport std.typeset as tslet pt = (1pt).toScaledPoints()let mm = (25.4mm).toScaledPoints()let cm = (2.54cm).toScaledPoints()let inch = (1in).toScaledPoints()io.writeLine("{pt}|{mm}|{cm}|{inch}|{ts.fromScaledPoints(pt) == 1pt}")
65536|4718592|4718592|4718592|true
Expected result
Expected result
Execution completes. Exit code 0.
65536|4718592|4718592|4718592|true
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Keep the millipoint conversion boundary
Linkimport std.ioimport std.typeset as tslet tie = ts.fromScaledPoints(4096).toMilliPoints()let rounded = ts.fromMilliPoints(1) == ts.fromScaledPoints(66)io.writeLine("{tie}|{rounded}")
62|true
Expected result
Expected result
Execution completes. Exit code 0.
62|true
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Reject scaledPoints on `Length<Pt>`
Linklet distance = 1ptdistance.scaledPoints()
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5006stdlib-removed-scaled-points atmain.tpz:2:10
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Reject scaledPoints on `Length<Mm>`
Linklet distance = 1mmdistance.scaledPoints()
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5006stdlib-removed-scaled-points atmain.tpz:2:10
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Reject scaledPoints on `Length<Cm>`
Linklet distance = 1cmdistance.scaledPoints()
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5006stdlib-removed-scaled-points atmain.tpz:2:10
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Reject scaledPoints on `Length<In>`
Linklet distance = 1indistance.scaledPoints()
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5006stdlib-removed-scaled-points atmain.tpz:2:10
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Resolve font-relative lengths before integer conversion
Linklet distance = 1emdistance.toScaledPoints()
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5006stdlib-unresolved-em-scaled-points atmain.tpz:2:10
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Read both endpoints of the exact integer representation
Linkimport std.typeset as tsimport std.iolet low = ts.fromScaledPoints(-9223372036854775808).toScaledPoints()let high = ts.fromScaledPoints(9223372036854775807).toScaledPoints()io.writeLine("{low}|{high}")
-9223372036854775808|9223372036854775807
Expected result
Expected result
Execution completes. Exit code 0.
-9223372036854775808|9223372036854775807
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Construct the millipoint endpoints and keep signed rounding
Linkimport std.typeset as tsimport std.iolet low = ts.fromMilliPoints(-140737488355328000)let high = ts.fromMilliPoints(140737488355327999)let negative = ts.fromMilliPoints(-1)let lowGrid = ts.fromScaledPoints(-9223372036854775808).toMilliPoints()let highGrid = ts.fromScaledPoints(9223372036854775807).toMilliPoints()io.writeLine("{low == -140737488355328pt}|{high == ts.fromScaledPoints(9223372036854775742)}|{negative == ts.fromScaledPoints(-66)}")io.writeLine("{lowGrid}|{highGrid}")
true|true|true -140737488355328000|140737488355328000
Expected result
Expected result
Execution completes. Exit code 0.
true|true|true-140737488355328000|140737488355328000
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Round both signs and both sides of a millipoint tie
Linkimport std.typeset as tsimport std.iolet below = ts.fromScaledPoints(4095).toMilliPoints()let tie = ts.fromScaledPoints(4096).toMilliPoints()let above = ts.fromScaledPoints(4097).toMilliPoints()let negativeBelow = ts.fromScaledPoints(-4095).toMilliPoints()let negativeTie = ts.fromScaledPoints(-4096).toMilliPoints()let negativeAbove = ts.fromScaledPoints(-4097).toMilliPoints()let upperTie = ts.fromScaledPoints(12288).toMilliPoints()let negativeUpperTie = ts.fromScaledPoints(-12288).toMilliPoints()io.writeLine("{below}|{tie}|{above}|{negativeBelow}|{negativeTie}|{negativeAbove}|{upperTie}|{negativeUpperTie}")
62|62|63|-62|-62|-63|188|-188
Expected result
Expected result
Execution completes. Exit code 0.
62|62|63|-62|-62|-63|188|-188
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Reject a millipoint input above the representable range
Linkimport std.typeset as tsts.fromMilliPoints(140737488355328000)
No stdout.
Expected result
Expected result
Rejection during run. Nonzero exit.
TPZ4004stdlib-length-unrepresentable atmain.tpz:2:1
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Reject a millipoint input below the representable range
Linkimport std.typeset as tsts.fromMilliPoints(-140737488355328001)
No stdout.
Expected result
Expected result
Rejection during run. Nonzero exit.
TPZ4004stdlib-length-unrepresentable atmain.tpz:2:1
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Require an int for fromScaledPoints
Linkimport std.typeset as tsts.fromScaledPoints(1.0)
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-length-int-required atmain.tpz:2:21
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Require an int for fromMilliPoints
Linkimport std.typeset as tsts.fromMilliPoints(1.0)
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-length-int-required atmain.tpz:2:20
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
271329b482bc· 1303 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 122 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_resolve/src/std/typeset/length.tpz at
271329b482bc· 2 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 63-95 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293-302 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 152-172 - compiler/crates/topaz_product_runtime/src/program/validate.rs at
b48527d0a174· 38-89 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 646-648 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1320-1330 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490-499 - compiler/crates/topaz_product_runtime/src/wire.rs at
b48527d0a174· 42-49 -
topaz.stdlib.contract.to-scaled-pointsatworking-tree - topaz.decision.to-scaled-points.1 at
topaz.decisi
Diagnostics
LinkGive public typesetting distances a point-length type
LinkGive public typesetting distances a point-length type
Public measurement fields use Length<Pt>. Widths, advances, tracking, stretch, shrink, physical targets, insets, font sizes, and optional width limits keep that type across input and output records. Explicit Length conversion functions remain the integer interchange boundary.
Box., Box., Glue., Glue., Glue., Glue., and Penalty. have type Length<Pt>.
Break, Break, Break, and Break have type Length<Pt>.
Latin, Justification, and Justification have type Length<Pt>.
Line, Line, and Line have type Length<Pt>.
Plan, Plan, Plan, Plan, and Plan have type Length<Pt>. Plan has type Option<Length<Pt>>.
An int, a float, or a Length with another unit marker is not an implicit point-length argument. Convert physical units explicitly with toPt() before constructing a typesetting record.
Indices, counts, penalties, costs, and dimensionless ratios retain their declared types. LatinSpacing.maxLetterSpacingEm is a relative Length<Em>. Resolve it to Length<Pt> with fontSizePt before selecting the computation grid.
Paragraph. selects quantization at the computation boundary. ScaledPoint uses the exact scaled-point integer. MilliPoint uses the existing nearest-even conversion to millipoints. The selected grid never changes the physical interpretation of a public Length<Pt> value.
Returned distances are converted from the computation grid into Length<Pt> at the output boundary. Paragraph reports the computation policy and is not needed to interpret its distances.
The public type change preserves the selected cost model. FixedPoint retains its MilliPoint computation requirement. Word-space and CJK ratio calculations keep their independent floor rules. The relative letter-spacing distance is resolved and quantized through the shared Length conversions before it contributes to capacity.
The public line-badness entry point also receives width, target, and hyphen advance as Length<Pt>. It converts those distances to millipoints at entry and preserves its existing integer cost calculation.
Why
A physical distance carries the same Length<Pt> type in application geometry and paragraph planning. The type prevents a grid selector or an unlabelled scalar from silently changing the distance.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Use point lengths in Box
Linkimport std.typeset as tslet value: ts.Box = ts.Box {unitIndex: 0,text: "A",width: 12pt,trackingAfter: 0pt}let distance: Length<Pt> = value.width
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Reject untyped physical distances in Box
Linkimport std.typeset as tslet value: ts.Box = ts.Box {unitIndex: 0,text: "A",width: 12,trackingAfter: 0}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:5:10
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Use point lengths in Glue
Linkimport std.typeset as tslet value: ts.Glue = ts.Glue {unitIndex: 1,text: " ",width: 3pt,trackingAfter: 0pt,stretch: 1pt,shrink: 1pt}let distance: Length<Pt> = value.width
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Reject untyped physical distances in Glue
Linkimport std.typeset as tslet value: ts.Glue = ts.Glue {unitIndex: 1,text: " ",width: 3,trackingAfter: 0,stretch: 1,shrink: 1}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:5:10
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Use point lengths in Penalty
Linkimport std.typeset as tslet value: ts.Penalty = ts.Penalty {unitEnd: 1,width: 0pt,rule: ts.BreakRule.Forced(),kind: ts.BreakKind.ForcedEnd(),flagged: false}let distance: Length<Pt> = value.width
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Reject untyped physical distances in Penalty
Linkimport std.typeset as tslet value: ts.Penalty = ts.Penalty {unitEnd: 1,width: 0,rule: ts.BreakRule.Forced(),kind: ts.BreakKind.ForcedEnd(),flagged: false}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:4:10
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Use point lengths in BreakPolicy
Linkimport std.typeset as tslet value: ts.BreakPolicy = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.Unicode16Ja(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true],generatedHyphenEnds: [],protectFittingLatin: true,preserveShortWords: true,narrowestWordTarget: 12pt,bodyWordTarget: 24pt}let distance: Length<Pt> = value.narrowestWordTarget
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Reject untyped physical distances in BreakPolicy
Linkimport std.typeset as tslet value: ts.BreakPolicy = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.Unicode16Ja(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true],generatedHyphenEnds: [],protectFittingLatin: true,preserveShortWords: true,narrowestWordTarget: 12,bodyWordTarget: 24}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:11:24
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Use point lengths in BreakCluster
Linkimport std.typeset as tslet value: ts.BreakCluster = ts.BreakCluster {text: "A",advance: 12pt,trackingAfter: 0pt}let distance: Length<Pt> = value.advance
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Reject untyped physical distances in BreakCluster
Linkimport std.typeset as tslet value: ts.BreakCluster = ts.BreakCluster {text: "A",advance: 12,trackingAfter: 0}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:4:12
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Use point lengths in LatinSpacing
Linkimport std.typeset as tslet value: ts.LatinSpacing = ts.LatinSpacing {minWordSpaceRatio: 0.8,maxWordSpaceRatio: 1.33,maxLetterSpacingEm: 0.01em,fontSizePt: 12pt}let distance: Length<Pt> = value.fontSizePt
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Reject untyped physical distances in LatinSpacing
Linkimport std.typeset as tslet value: ts.LatinSpacing = ts.LatinSpacing {minWordSpaceRatio: 0.8,maxWordSpaceRatio: 1.33,maxLetterSpacingEm: 0.01em,fontSizePt: 12.0}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:6:15
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Use point lengths in JustificationPolicy
Linkimport std.typeset as tslet value: ts.JustificationPolicy = ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(),minGapCount: 0,minLineWidthRatioM: 0,minFinalLineWidthRatioM: None(),maxAdjustment: 12pt,maxGapAdjustment: 3pt,maxGapRatioR: 0,latinSpacing: None(),cjkStretchRatio: 0.0}let distance: Length<Pt> = value.maxAdjustment
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Reject untyped physical distances in JustificationPolicy
Linkimport std.typeset as tslet value: ts.JustificationPolicy = ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(),minGapCount: 0,minLineWidthRatioM: 0,minFinalLineWidthRatioM: None(),maxAdjustment: 12,maxGapAdjustment: 3,maxGapRatioR: 0,latinSpacing: None(),cjkStretchRatio: 0.0}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:7:18
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Use point lengths in LineGeometry
Linkimport std.typeset as tslet value: ts.LineGeometry = ts.LineGeometry {bodyTarget: 24pt,firstTarget: 20pt,dropCapSpan: 0,dropCapInset: 0pt}let distance: Length<Pt> = value.bodyTarget
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Reject untyped physical distances in LineGeometry
Linkimport std.typeset as tslet value: ts.LineGeometry = ts.LineGeometry {bodyTarget: 24,firstTarget: 20,dropCapSpan: 0,dropCapInset: 0}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:3:15
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Use point lengths in PlanLine
Linkimport std.typeset as tslet value: ts.PlanLine = ts.PlanLine {start: 0,endExclusive: 1,trimmedEndExclusive: 1,displayTextScalarLength: 1,kind: ts.BreakKind.ForcedEnd(),target: 12pt,rawTextWidth: 10pt,trimmedTextWidth: 10pt,costTextWidth: 10pt,selectedPenaltyWidth: 0pt,postValidationWidthLimit: Some(13pt),cost: 0,adjustmentRatioR: 0}let distance: Length<Pt> = value.targetlet limit: Option<Length<Pt>> = value.postValidationWidthLimit
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Reject untyped physical distances in PlanLine
Linkimport std.typeset as tslet value: ts.PlanLine = ts.PlanLine {start: 0,endExclusive: 1,trimmedEndExclusive: 1,displayTextScalarLength: 1,kind: ts.BreakKind.ForcedEnd(),target: 12,rawTextWidth: 10,trimmedTextWidth: 10,costTextWidth: 10,selectedPenaltyWidth: 0,postValidationWidthLimit: Some(13),cost: 0,adjustmentRatioR: 0}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:8:11
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Pass typed distances to the line-cost function
Linkimport std.typeset as tslet value = ts.lineBadness(20pt, 20pt, 4, 1, ts.BreakKind.ForcedEnd(), false, 0, 0pt)
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Reject raw distances at the line-cost boundary
Linkimport std.typeset as tslet value = ts.lineBadness(20, 20, 4, 1, ts.BreakKind.ForcedEnd(), false, 0, 0)
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:2:28
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 16 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
271329b482bc· 90 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1846 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1976 - compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-length-ptatworking-tree - topaz.decision.typeset-length-pt.1 at
topaz.decisi
Name the CJK cluster break category
LinkName the CJK cluster break category
Break constructs the variant for the existing CJK and East Asian cluster classification. Break is absent and rejected.
Renaming this variant preserves the classification predicates and the effect of the selected Unicode, locale, custom punctuation, and shaping-boundary policies.
A CjkCluster category does not itself permit a break. classify returns the opportunities admitted by its supplied policy.
Why
A break category names the text it classifies. CjkCluster covers the existing Chinese, Japanese, and Korean classification path and matches the module's CjkInterCharacter vocabulary. Locale policy continues to determine where a break is allowed.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 2 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
271329b482bc· 43 - compiler/crates/topaz_resolve/src/std/typeset/atlas_breaks.tpz at
271329b482bc· 28 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1334 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_interp/tests/fixtures/typeset_leaf.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.cjk-clusteratworking-tree - topaz.decision.cjk-cluster.1 at
topaz.decisi
Use the CJK cluster variant
Linkimport std.typeset as tslet kind: ts.BreakKind = ts.BreakKind.CjkCluster()
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 2 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
271329b482bc· 43 - compiler/crates/topaz_resolve/src/std/typeset/atlas_breaks.tpz at
271329b482bc· 28 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1334 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_interp/tests/fixtures/typeset_leaf.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.cjk-clusteratworking-tree - topaz.decision.cjk-cluster.1 at
topaz.decisi
Reject the former KoreanCluster name
Linkimport std.typeset as tslet kind = ts.BreakKind.KoreanCluster()
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5006stdlib-removed-korean-cluster atmain.tpz:2:12
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 2 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
271329b482bc· 43 - compiler/crates/topaz_resolve/src/std/typeset/atlas_breaks.tpz at
271329b482bc· 28 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1334 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_interp/tests/fixtures/typeset_leaf.tpz at
271329b482bc· 1 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.cjk-clusteratworking-tree - topaz.decision.cjk-cluster.1 at
topaz.decisi
Compute fixed-point line badness from point lengths
LinkCompute fixed-point line badness from point lengths
line is the public entry point. lineBadnessMpt is absent and importing it is rejected with TPZ3009.
The three distances require Length<Pt>. A raw scalar or another unit marker is rejected with TPZ5001. Width and hyphen advance may be negative. justificationB accepts every int and can make the resulting cost negative.
Evaluate all eight argument expressions once in source order before entering the function. Convert width, target, and hyphenAdvance to millipoints in that order with the shared nearest-even rule.
The converted target must be positive. charCount and spaces must each be nonnegative and need not satisfy a relation to each other. Invalid inputs return Err containing TypesetError.InvalidInput before cost arithmetic. The explanatory message text is not fixed.
Let w, t, and h be the converted distances, c the character count, s the space count, and j the supplied justification cost. Let B be 1,000,000 and R be 100,000,000.
For a nonnegative n and positive d, H gives n divided by d rounded to the nearest integer with ties upward. H describes cost rounding. Physical Length conversion keeps its separate nearest-even rule.
The following sequence uses checked int operations in the stated order. A failing intermediate operation stops with runtime diagnostic TPZ4004. It does not return TypesetError or replace overflow with a bounded cost.
Set effective to w + h for LatinSoftHyphen and to w for every other kind. Set slack to t - effective and absolute to the absolute value of slack.
Set raw to 4 R when absolute is at least 4 t. Otherwise set raw to absolute * R / with integer division. This explicit ratio cap does not change a supplied length.
Set capacity to 100 + s * 45 when slack is nonnegative and to 100 + s * 25 otherwise. Set ratio = H(raw * 100, capacity), then q = H(ratio * ratio, R), then cost = H(q * (1000 * B), R).
If isLast is true, replace cost with H(cost * 2, 5). Add 500 B when isLast is true and `w 100 < t * 52`. The strict comparison uses the original converted width and also applies when charCount is zero.
If slack is negative, add 20000 * B + H(20000 * B * ratio, R). Add 65 B for LatinHyphen or LatinSoftHyphen. Add 50000 B for HardFallback. The other break kinds add no break penalty.
If c is at most two, add 275 B. Then add 10 B and j in that order and return the result in Ok. The hyphenAdvance input affects width for LatinSoftHyphen and is ignored for the other kinds.
An exact fit with more than two characters, no special break penalty, and zero justification cost returns 10000000. The documented 90 point line against a 100 point target with nine characters and two spaces returns 12770080.
The function performs no I/O, changes no input, and reads no font, paragraph, or global grid state. Effects from argument evaluation remain visible on InvalidInput or a later arithmetic fault.
An arithmetic fault identifies the public lineBadness call as its primary source location. Argument effects already performed remain visible and later expressions do not run.
Why
One typed entry point fixes the physical meaning before scoring a line. Explicit intermediate rounding makes costs reproducible. The same last-line width condition applies to every valid character count, including an empty line.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Compute a line cost from point lengths
Linkimport std.ioimport std.typeset as tslet cost = ts.lineBadness(20pt, 20pt, 4, 1, ts.BreakKind.ForcedEnd(), false, 0, 0pt)match (cost) {case Ok(value) => io.writeLine("{value}")case Err(_) => io.writeLine("unexpected input error")}
10000000
Expected result
Expected result
Execution completes. Exit code 0.
10000000
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Reject the former millipoint function name
Linkimport std.typeset { lineBadnessMpt }
No stdout.
Expected result
Expected result
Rejection during resolve. Nonzero exit.
TPZ3009selected-name-not-exported atmain.tpz:1:22
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Preserve the published fixed-point costs
Linkimport std.typeset as tsimport std.testimport std.iofunction show(value: Result<int, ts.TypesetError>) -> () {let cost = test.assertOk(value)io.writeLine("{cost}")}show(ts.lineBadness(100pt, 100pt, 10, 2, ts.BreakKind.LatinSpace(), false, 0, 0pt))show(ts.lineBadness(90pt, 100pt, 9, 2, ts.BreakKind.LatinSpace(), false, 0, 0pt))show(ts.lineBadness(100pt, 100pt, 10, 2, ts.BreakKind.LatinHyphen(), false, 0, 0pt))show(ts.lineBadness(40pt, 100pt, 4, 0, ts.BreakKind.ForcedEnd(), true, 0, 0pt))
10000000 12770080 75000000 654000000
Expected result
Expected result
Execution completes. Exit code 0.
100000001277008075000000654000000
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Apply break penalties and the small character count boundary
Linkimport std.typeset as tsimport std.testimport std.iofunction show(value: Result<int, ts.TypesetError>) -> () {let cost = test.assertOk(value)io.writeLine("{cost}")}show(ts.lineBadness(100pt, 100pt, 3, 0, ts.BreakKind.CjkCluster(), false, 0, 0pt))show(ts.lineBadness(100pt, 100pt, 3, 0, ts.BreakKind.ClosingPunctuation(), false, 0, 0pt))show(ts.lineBadness(100pt, 100pt, 3, 0, ts.BreakKind.HardFallback(), false, 0, 0pt))show(ts.lineBadness(100pt, 100pt, 2, 0, ts.BreakKind.ForcedEnd(), false, 0, 0pt))show(ts.lineBadness(99pt, 100pt, 9, 0, ts.BreakKind.LatinSoftHyphen(), false, 0, 1pt))show(ts.lineBadness(99pt, 100pt, 9, 0, ts.BreakKind.LatinHyphen(), false, 0, 1pt))
10000000 10000000 50010000000 285000000 75000000 75100000
Expected result
Expected result
Execution completes. Exit code 0.
1000000010000000500100000002850000007500000075100000
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Use a strict last-line width threshold
Linkimport std.typeset as tsimport std.testimport std.iofunction show(value: Result<int, ts.TypesetError>) -> () {let cost = test.assertOk(value)io.writeLine("{cost}")}show(ts.lineBadness(52pt, 100pt, 4, 0, ts.BreakKind.ForcedEnd(), true, 0, 0pt))show(ts.lineBadness(51pt, 100pt, 4, 0, ts.BreakKind.ForcedEnd(), true, 0, 0pt))
102160000 606040000
Expected result
Expected result
Execution completes. Exit code 0.
102160000606040000
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Apply the last-line width condition to zero characters
Linkimport std.typeset as tsimport std.testimport std.iofunction show(value: Result<int, ts.TypesetError>) -> () {let cost = test.assertOk(value)io.writeLine("{cost}")}show(ts.lineBadness(0pt, 100pt, 0, 0, ts.BreakKind.ForcedEnd(), true, 0, 0pt))
1185000000
Expected result
Expected result
Execution completes. Exit code 0.
1185000000
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Keep signed inputs and cap the scoring ratio explicitly
Linkimport std.typeset as tsimport std.testimport std.iofunction show(value: Result<int, ts.TypesetError>) -> () {let cost = test.assertOk(value)io.writeLine("{cost}")}show(ts.lineBadness(100pt, 100pt, 3, 0, ts.BreakKind.ForcedEnd(), false, -10000001, 0pt))show(ts.lineBadness(-1000pt, 100pt, 3, 0, ts.BreakKind.ForcedEnd(), false, 0, -1pt))show(ts.lineBadness(500pt, 100pt, 3, 0, ts.BreakKind.ForcedEnd(), false, 0, 0pt))show(ts.lineBadness(600pt, 100pt, 3, 0, ts.BreakKind.ForcedEnd(), false, 0, 0pt))
-1 16010000000 116010000000 116010000000
Expected result
Expected result
Execution completes. Exit code 0.
-116010000000116010000000116010000000
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Return InvalidInput for the target and count boundaries
Linkimport std.typeset as tsimport std.iofor result in ([ts.lineBadness(1pt, 0pt, 3, 0, ts.BreakKind.ForcedEnd(), false, 0, 0pt),ts.lineBadness(1pt, -1pt, 3, 0, ts.BreakKind.ForcedEnd(), false, 0, 0pt),ts.lineBadness(1pt, 1pt, -1, 0, ts.BreakKind.ForcedEnd(), false, 0, 0pt),ts.lineBadness(1pt, 1pt, 3, -1, ts.BreakKind.ForcedEnd(), false, 0, 0pt)]) {match (result) {case Err(InvalidInput(_)) => io.writeLine("invalid input")case _ => io.writeLine("unexpected result")}}
invalid input invalid input invalid input invalid input
Expected result
Expected result
Execution completes. Exit code 0.
invalid inputinvalid inputinvalid inputinvalid input
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Validate target positivity after millipoint conversion
Linkimport std.typeset as tsimport std.testimport std.iofunction show(value: Result<int, ts.TypesetError>) -> () {let cost = test.assertOk(value)io.writeLine("{cost}")}let rejected = ts.lineBadness(0pt, ts.fromScaledPoints(32), 3, 0, ts.BreakKind.ForcedEnd(), false, 0, 0pt)match (rejected) {case Err(InvalidInput(_)) => io.writeLine("rounded target is zero")case _ => io.writeLine("unexpected result")}show(ts.lineBadness(ts.fromScaledPoints(33), ts.fromScaledPoints(33), 3, 0, ts.BreakKind.ForcedEnd(), false, 0, 0pt))show(ts.lineBadness(ts.fromScaledPoints(4096), ts.fromMilliPoints(62), 3, 0, ts.BreakKind.ForcedEnd(), false, 0, 0pt))
rounded target is zero 10000000 10000000
Expected result
Expected result
Execution completes. Exit code 0.
rounded target is zero1000000010000000
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Evaluate every argument before input validation
Linkimport std.typeset as tsimport std.iofunction length(label: string, value: Length<Pt>) -> Length<Pt> {io.writeLine(label)value}function count(label: string, value: int) -> int {io.writeLine(label)value}function kind(value: ts.BreakKind) -> ts.BreakKind {io.writeLine("kind")value}function last(value: bool) -> bool {io.writeLine("last")value}let result = ts.lineBadness(length("width", 1pt), length("target", 0pt),count("chars", 3), count("spaces", 0),kind(ts.BreakKind.ForcedEnd()), last(false),count("justification", 0), length("hyphen", 0pt))match (result) {case Err(InvalidInput(_)) => io.writeLine("invalid input")case _ => io.writeLine("unexpected result")}
width target chars spaces kind last justification hyphen invalid input
Expected result
Expected result
Execution completes. Exit code 0.
widthtargetcharsspaceskindlastjustificationhypheninvalid input
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Stop on checked cost overflow
Linkimport std.typeset as tsts.lineBadness(1pt, 1pt, 3, 0, ts.BreakKind.ForcedEnd(), false, 9223372036854775807, 0pt)
No stdout.
Expected result
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/cost.tpz at
271329b482bc· 1 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 80 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_self_frontend/topaz/resolver/validation_init.tpz at
271329b482bc· 174 - compiler/crates/topaz_self_frontend/topaz/checker/expression_core.tpz at
271329b482bc· 1511 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
b48527d0a174· 29 - docs/content/en/docs/stdlib/typeset.mdx at
912a5e86e1f9· 379 - issues/31 at
topaz.decisi· 1 - pull/51 at
topaz.decisi· 1 - compiler/crates/topaz_product_runtime/src/runtime/machine.rs at
b48527d0a174· 490 -
topaz.stdlib.contract.line-badnessatworking-tree - topaz.decision.line-badness-name.1 at
topaz.decisi
Diagnostics
LinkResolve relative letter spacing through Length
LinkResolve relative letter spacing through Length
LatinSpacing stores minWordSpaceRatio and maxWordSpaceRatio as dimensionless float values, maxLetterSpacingEm as Length<Em>, and fontSizePt as Length<Pt>. There is no implicit scalar or cross-unit conversion.
Record construction and field reads store and return the supplied values. They do not validate a paragraph policy or resolve the relative length. Field expressions follow ordinary source-order evaluation once.
A paragraph validates every supplied LatinSpacing record before planning. This validation also applies in Unjustified mode and with the KnuthPlass cost model.
minWordSpaceRatio must be finite and between 0.8 and 1.0 inclusive. maxWordSpaceRatio must be finite and between 1.0 and 1.33 inclusive. Invalid ratios return Err containing TypesetError.InvalidPolicy.
maxLetterSpacingEm must be between 0em and 0.015em inclusive on the stored relative grid. The upper bound is 983 em ticks. A negative tick or 984 ticks returns Err containing TypesetError.InvalidPolicy.
fontSizePt must have a strictly positive scaled-point count. A one-scaled-point font is valid even when the paragraph uses millipoints. Zero and negative fonts return Err containing TypesetError.InvalidPolicy, including when letter spacing is zero.
InvalidPolicy carries explanatory text. Its exact message text and the order among independent invalid policy fields are not fixed by this contract.
Resolve the stored maximum with maxLetterSpacingEm.resolve(fontSizePt). The stored relative count is multiplied by the physical font count and divided by 65,536 with one nearest-even rounding to scaled points. No ambient font is read.
Convert the resolved result to the selected computation grid. ScaledPoint preserves its integer count. MilliPoint applies the shared nearest-even conversion. Every eligible gap receives this rounded bound before multiplication by the gap count.
An eligible Latin letter gap lies between adjacent retained text units. Each unit must contain an alphabetic scalar and every scalar must be in U+0041 through U+024F, U+0300 through U+036F, or U+1E00 through U+1EFF. Paragraph trimming determines the retained units.
The retained line uses this capacity path when it contains a CJK unit, or contains a Latin letter unit and no other alphabetic unit. A non-Latin unit containing an alphabetic scalar counts as another alphabetic unit. Paragraph classification determines CJK units.
Let S be the sum of the grid widths of retained units whose text is U+0020. Word shrink capacity is floor(float(S) * (1.. Word stretch capacity is floor(float(S) * (max. Each expression keeps that binary64 evaluation order and its independent floor.
The letter stretch contribution is the eligible gap count times the quantized relative limit. CJK capacity retains its separate floor rule. Combining these contributions does not repeat font resolution or round their total as one relative length.
Unjustified mode does not apply spacing capacity. KnuthPlass obtains stretch and shrink from glue after the shared policy validation. FixedPoint uses the validated Latin spacing in its justification capacity and requires MilliPoint.
Resolution, integer accumulation, and capacity arithmetic use their checked numeric contracts. Overflow stops with TPZ4004 and does not return InvalidPolicy. Validation and conversion perform no I/O and do not mutate the record.
For 0.01em at 12pt, 655 relative ticks resolve to 7,860 scaled points and then 120 millipoints. For 0.0078125em at 24pt, each gap receives 188 millipoints. Two such gaps provide 376 millipoints.
Why
One relative length model gives a letter-spacing limit an explicit font and unit. Validating the stored policy before planning separates field construction from recoverable policy errors. Per-gap quantization makes the permitted adjustment reproducible.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Store a relative spacing length and an explicit point font size
Linkimport std.typeset as tslet value = ts.LatinSpacing {minWordSpaceRatio: 0.8,maxWordSpaceRatio: 1.33,maxLetterSpacingEm: 0.01em,fontSizePt: 12pt}let relative: Length<Em> = value.maxLetterSpacingEmlet physical: Length<Pt> = relative.resolve(value.fontSizePt)
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Resolve the stored spacing before converting to the computation grid
Linkimport std.typeset as tsimport std.iolet spacing = ts.LatinSpacing {minWordSpaceRatio: 0.8,maxWordSpaceRatio: 1.33,maxLetterSpacingEm: 0.01em,fontSizePt: 12pt}let limit = spacing.maxLetterSpacingEm.resolve(spacing.fontSizePt)let exact = limit == ts.fromScaledPoints(7860)let millipoints = limit.toMilliPoints()io.writeLine("{exact}|{millipoints}")
true|120
Expected result
Expected result
Execution completes. Exit code 0.
true|120
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Apply nearest-even rounding at each typed value boundary
Linkimport std.typeset as tsimport std.iolet lowTie = (0.5em).resolve(ts.fromScaledPoints(3)) == ts.fromScaledPoints(2)let highTie = (0.5em).resolve(ts.fromScaledPoints(5)) == ts.fromScaledPoints(2)let literalGrid = (0.01em).resolve(12pt) == ts.fromScaledPoints(7860)let gridLow = (0.5em).resolve(0.125pt).toMilliPoints()let gridHigh = (0.5em).resolve(0.375pt).toMilliPoints()io.writeLine("{lowTie}|{highTie}|{literalGrid}|{gridLow}|{gridHigh}")
true|true|true|62|188
Expected result
Expected result
Execution completes. Exit code 0.
true|true|true|62|188
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Reject an untyped multiplier in the relative-length field
Linkimport std.typeset as tslet spacing = ts.LatinSpacing {minWordSpaceRatio: 0.8,maxWordSpaceRatio: 1.33,maxLetterSpacingEm: 0.01,fontSizePt: 12pt}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-relative-distance-requires-em atmain.tpz:5:23
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Reject a physical length where an em length is required
Linkimport std.typeset as tslet spacing = ts.LatinSpacing {minWordSpaceRatio: 0.8,maxWordSpaceRatio: 1.33,maxLetterSpacingEm: 0.12pt,fontSizePt: 12pt}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-relative-distance-requires-em atmain.tpz:5:23
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Reject treating the stored relative length as a float
Linkimport std.typeset as tsfunction multiplier(value: ts.LatinSpacing) -> float {value.maxLetterSpacingEm}
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-relative-distance-is-not-float atmain.tpz:3:3
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Admit the inclusive ratio and font bounds
Linkimport std.typeset as tsimport std.iofunction paragraph(grid: ts.DistanceGrid, spacing: Option<ts.LatinSpacing>) -> ts.Paragraph {ts.Paragraph {grid: grid,items: [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "abc", width: 10pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty {unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(),kind: ts.BreakKind.ForcedEnd(), flagged: false})],geometry: ts.LineGeometry {bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt},justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(),minGapCount: 0, minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: spacing, cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy {toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0,flaggedDemerit: 0, finalFlaggedDemerit: 0}}}for value in ([ts.LatinSpacing { minWordSpaceRatio: 0.8, maxWordSpaceRatio: 1.0, maxLetterSpacingEm: 0em, fontSizePt: ts.fromScaledPoints(1) },ts.LatinSpacing { minWordSpaceRatio: 1.0, maxWordSpaceRatio: 1.33, maxLetterSpacingEm: 0.015em, fontSizePt: 12pt }]) {match (ts.breakParagraph(paragraph(ts.DistanceGrid.MilliPoint(), Some(value)))) {case Ok(_) => io.writeLine("valid policy")case Err(_) => io.writeLine("unexpected error")}}
valid policy valid policy
Expected result
Expected result
Execution completes. Exit code 0.
valid policyvalid policy
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Reject ratios just outside every allowed endpoint
Linkimport std.typeset as tsimport std.iofunction paragraph(grid: ts.DistanceGrid, spacing: Option<ts.LatinSpacing>) -> ts.Paragraph {ts.Paragraph {grid: grid,items: [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "abc", width: 10pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty {unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(),kind: ts.BreakKind.ForcedEnd(), flagged: false})],geometry: ts.LineGeometry {bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt},justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(),minGapCount: 0, minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: spacing, cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy {toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0,flaggedDemerit: 0, finalFlaggedDemerit: 0}}}for value in ([ts.LatinSpacing { minWordSpaceRatio: 0.7999, maxWordSpaceRatio: 1.0, maxLetterSpacingEm: 0em, fontSizePt: 12pt },ts.LatinSpacing { minWordSpaceRatio: 1.0001, maxWordSpaceRatio: 1.0, maxLetterSpacingEm: 0em, fontSizePt: 12pt },ts.LatinSpacing { minWordSpaceRatio: 1.0, maxWordSpaceRatio: 0.9999, maxLetterSpacingEm: 0em, fontSizePt: 12pt },ts.LatinSpacing { minWordSpaceRatio: 1.0, maxWordSpaceRatio: 1.3301, maxLetterSpacingEm: 0em, fontSizePt: 12pt }]) {match (ts.breakParagraph(paragraph(ts.DistanceGrid.MilliPoint(), Some(value)))) {case Err(InvalidPolicy(_)) => io.writeLine("invalid ratio")case _ => io.writeLine("unexpected result")}}
invalid ratio invalid ratio invalid ratio invalid ratio
Expected result
Expected result
Execution completes. Exit code 0.
invalid ratioinvalid ratioinvalid ratioinvalid ratio
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Reject negative spacing and nonpositive fonts
Linkimport std.typeset as tsimport std.iofunction paragraph(grid: ts.DistanceGrid, spacing: Option<ts.LatinSpacing>) -> ts.Paragraph {ts.Paragraph {grid: grid,items: [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "abc", width: 10pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty {unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(),kind: ts.BreakKind.ForcedEnd(), flagged: false})],geometry: ts.LineGeometry {bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt},justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(),minGapCount: 0, minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: spacing, cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy {toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0,flaggedDemerit: 0, finalFlaggedDemerit: 0}}}for value in ([ts.LatinSpacing { minWordSpaceRatio: 1.0, maxWordSpaceRatio: 1.0, maxLetterSpacingEm: -0.0000152587890625em, fontSizePt: 12pt },ts.LatinSpacing { minWordSpaceRatio: 1.0, maxWordSpaceRatio: 1.0, maxLetterSpacingEm: 0.0150146484375em, fontSizePt: 12pt },ts.LatinSpacing { minWordSpaceRatio: 1.0, maxWordSpaceRatio: 1.0, maxLetterSpacingEm: 0em, fontSizePt: 0pt },ts.LatinSpacing { minWordSpaceRatio: 1.0, maxWordSpaceRatio: 1.0, maxLetterSpacingEm: 0em, fontSizePt: -12pt }]) {match (ts.breakParagraph(paragraph(ts.DistanceGrid.MilliPoint(), Some(value)))) {case Err(InvalidPolicy(_)) => io.writeLine("invalid length policy")case _ => io.writeLine("unexpected result")}}
invalid length policy invalid length policy invalid length policy invalid length policy
Expected result
Expected result
Execution completes. Exit code 0.
invalid length policyinvalid length policyinvalid length policyinvalid length policy
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Read a stored policy before paragraph validation
Linkimport std.typeset as tsimport std.iolet value = ts.LatinSpacing { minWordSpaceRatio: 0.0, maxWordSpaceRatio: 2.0, maxLetterSpacingEm: 1em, fontSizePt: 0pt }io.writeLine("{value.minWordSpaceRatio == 0.0}|{value.maxWordSpaceRatio == 2.0}|{value.maxLetterSpacingEm == 1em}|{value.fontSizePt == 0pt}")
true|true|true|true
Expected result
Expected result
Execution completes. Exit code 0.
true|true|true|true
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Fill a line using a rounded bound for every letter gap
Linkimport std.typeset as tsimport std.ioimport std.testfunction paragraph(grid: ts.DistanceGrid, spacing: Option<ts.LatinSpacing>) -> ts.Paragraph {ts.Paragraph {grid: grid,items: [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.BoxItem(ts.Box { unitIndex: 1, text: "b", width: 1pt, trackingAfter: 0pt }),ts.Item.BoxItem(ts.Box { unitIndex: 2, text: "c", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty {unitEnd: 3, width: 0pt, rule: ts.BreakRule.Forced(),kind: ts.BreakKind.LatinSpace(), flagged: false}),ts.Item.BoxItem(ts.Box { unitIndex: 3, text: "xyz", width: 3.376pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty {unitEnd: 4, width: 0pt, rule: ts.BreakRule.Forced(),kind: ts.BreakKind.ForcedEnd(), flagged: false})],geometry: ts.LineGeometry {bodyTarget: 3.376pt, firstTarget: 3.376pt, dropCapSpan: 0, dropCapInset: 0pt},justification: ts.JustificationPolicy {mode: ts.JustificationMode.LatinWordSpace(),minGapCount: 0, minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: spacing, cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy {toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0,flaggedDemerit: 0, finalFlaggedDemerit: 0}}}let value = ts.LatinSpacing { minWordSpaceRatio: 1.0, maxWordSpaceRatio: 1.0, maxLetterSpacingEm: 0.0078125em, fontSizePt: 24pt }let result = test.assertOk(ts.breakParagraph(paragraph(ts.DistanceGrid.MilliPoint(), Some(value))))let filled = match (result.optimized.boundedFillFeasible) {case Some(value) => valuecase None() => false}io.writeLine("{filled}|{result.optimized.lines.length}|{result.optimized.lines[0].target == 3.376pt}")
true|2|true
Expected result
Expected result
Execution completes. Exit code 0.
true|2|true
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
271329b482bc· 33 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
271329b482bc· 38 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 92 - compiler/crates/topaz_syntax/src/length.rs at
271329b482bc· 293 - compiler/crates/topaz_value/src/value/length.rs at
271329b482bc· 90 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 25 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
b48527d0a174· 90 -
topaz.stdlib.contract.latin-spacing-ematworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Select a computation grid for typed distances
LinkSelect a computation grid for typed distances
DistanceGrid has the two payload-free values ScaledPoint() and MilliPoint(). They are distinct selectors and have no numeric conversion or ambient state.
Public physical inputs and outputs remain Length<Pt> under either selector. A grid selects internal quantization and does not reinterpret an integer or change a public unit marker.
ScaledPoint uses the signed scaled-point integer stored in each physical length. MilliPoint converts each input through Length<Pt>.toMilliPoints with nearest-even rounding.
Quantize each input once at the computation boundary. Resolve a relative length against its explicit font size before this conversion. Accumulation uses the resulting integers.
Return a computed distance through fromScaledPoints for ScaledPoint or fromMilliPoints for MilliPoint. The shared constructor range and rounding rules apply at this output boundary.
Grid conversion accepts signed lengths. Each grid computation applies its sign requirements after quantization. A positive point target that becomes zero millipoints fails a positive-target requirement. Font validation occurs during resolve before grid conversion.
FixedPoint requires MilliPoint. A paragraph that selects FixedPoint with ScaledPoint returns Err containing TypesetError.InvalidPolicy. KnuthPlass accepts either grid.
Selecting a grid and converting lengths perform no I/O and do not mutate their inputs. Ordinary receiver and argument evaluation happens once before conversion. Input evaluation failures propagate before the operation begins.
A millipoint round trip can change the stored scaled-point value. For example, 4096 scaled points become 62 millipoints and then 4063 scaled points.
Why
Typed distances retain their meaning while a computation chooses precision. One conversion rule at each boundary makes grid selection reproducible and keeps font resolution explicit.
Source evidence
- compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 72 - compiler/crates/topaz_resolve/src/stdlib.rs at
b48527d0a174· 465 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
b48527d0a174· 10 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 10 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293 -
topaz.stdlib.contract.distance-gridatworking-tree
Construct both computation grid selectors
Linkimport std.typeset as tslet scaled: ts.DistanceGrid = ts.DistanceGrid.ScaledPoint()let milli: ts.DistanceGrid = ts.DistanceGrid.MilliPoint()
No stdout.
Expected result
Expected result
Checking accepts the program. Exit code 0.
Source evidence
- compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 72 - compiler/crates/topaz_resolve/src/stdlib.rs at
b48527d0a174· 465 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
b48527d0a174· 10 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 10 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293 -
topaz.stdlib.contract.distance-gridatworking-tree
Round signed millipoint ties and expose grid loss
Linkimport std.typeset as tsimport std.iofor ticks in ([-12288, -4096, 0, 4096, 12288]) {let value = ts.fromScaledPoints(ticks).toMilliPoints()io.writeLine("{value}")}let restored = ts.fromMilliPoints(62)io.writeLine("{restored == ts.fromScaledPoints(4063)}")io.writeLine("{restored == ts.fromScaledPoints(4096)}")
-188 -62 0 62 188 true false
Expected result
Expected result
Execution completes. Exit code 0.
-188-62062188truefalse
Source evidence
- compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 72 - compiler/crates/topaz_resolve/src/stdlib.rs at
b48527d0a174· 465 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
b48527d0a174· 10 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 10 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293 -
topaz.stdlib.contract.distance-gridatworking-tree
Reject a scaled-point grid for FixedPoint
Linkimport std.typeset as tsimport std.iofunction paragraph(grid: ts.DistanceGrid, spacing: Option<ts.LatinSpacing>) -> ts.Paragraph {ts.Paragraph {grid: grid,items: [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "abc", width: 10pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty {unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(),kind: ts.BreakKind.ForcedEnd(), flagged: false})],geometry: ts.LineGeometry {bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt},justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(),minGapCount: 0, minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: spacing, cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy {toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0,flaggedDemerit: 0, finalFlaggedDemerit: 0}}}match (ts.breakParagraph(paragraph(ts.DistanceGrid.ScaledPoint(), None()))) {case Err(InvalidPolicy(_)) => io.writeLine("invalid grid policy")case _ => io.writeLine("unexpected result")}
invalid grid policy
Expected result
Expected result
Execution completes. Exit code 0.
invalid grid policy
Source evidence
- compiler/crates/topaz_self_frontend/src/request.rs at
b48527d0a174· 72 - compiler/crates/topaz_resolve/src/stdlib.rs at
b48527d0a174· 465 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
b48527d0a174· 10 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
b48527d0a174· 10 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 293 -
topaz.stdlib.contract.distance-gridatworking-tree
Convert physical units without rounding again
LinkConvert physical units without rounding again
Every physical Length stores a signed 64-bit scaled-point count and a unit marker. The inclusive count range is -9223372036854775808 through 9223372036854775807. Zero and negative lengths are valid.
One point is 65,536 scaled points. One inch is 72 points and exactly 25.4 millimetres. One centimetre is 10 millimetres.
A physical literal converts its exact decimal value to scaled points and rounds once to the nearest integer. An exact tie selects the even integer. The same rule applies to either sign.
The methods toPt, toMm, toCm, and toIn accept no arguments on Length<Pt>, Length<Mm>, Length<Cm>, and Length<In>. They return the named physical unit with the original scaled-point count.
A unit conversion performs no further rounding and cannot overflow. Converting to the existing unit returns the same typed value. Every conversion sequence preserves the physical distance and stored count.
The unit marker remains part of the static type. Assignment and function arguments do not convert units implicitly. A required Length<Pt> rejects another unit with TPZ5001. Convert explicitly before the call or assignment.
Length<Em> has no physical conversion member. Resolve it with an explicit positive point font size before converting units.
Each method evaluates its receiver once before producing the result. Conversion performs no I/O or mutation and reads no font or paragraph state.
Use toScaledPoints on any physical unit for the exact stored integer. Convert to Length<Pt> before calling toMilliPoints. The integer conversion contract defines its separate rounding boundary.
Why
A unit marker states how a length may be used while one physical grid preserves its distance. Conversion changes the marker without accumulating rounding error. One conversion name per target unit works for every physical source unit.
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 39-58 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 290-292 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 119-137 -
topaz.stdlib.contract.physical-length-conversionatworking-tree
Convert each physical unit to every physical target
Linkimport std.iolet pt = 72ptlet mm = 25.4mmlet cm = 2.54cmlet inch = 1inio.writeLine("{pt.toPt() == 72pt}|{pt.toMm() == 25.4mm}|{pt.toCm() == 2.54cm}|{pt.toIn() == 1in}")io.writeLine("{mm.toPt() == 72pt}|{mm.toMm() == 25.4mm}|{mm.toCm() == 2.54cm}|{mm.toIn() == 1in}")io.writeLine("{cm.toPt() == 72pt}|{cm.toMm() == 25.4mm}|{cm.toCm() == 2.54cm}|{cm.toIn() == 1in}")io.writeLine("{inch.toPt() == 72pt}|{inch.toMm() == 25.4mm}|{inch.toCm() == 2.54cm}|{inch.toIn() == 1in}")
true|true|true|true true|true|true|true true|true|true|true true|true|true|true
Expected result
Expected result
Execution completes. Exit code 0.
true|true|true|truetrue|true|true|truetrue|true|true|truetrue|true|true|true
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 39-58 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 290-292 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 119-137 -
topaz.stdlib.contract.physical-length-conversionatworking-tree
Preserve signed and quantized values through conversion chains
Linkimport std.typeset as tsimport std.iolet negative = (-1pt).toMm().toCm().toIn().toPt()let zero = (0mm).toIn().toPt()let metric = (0.1mm).toPt()let unchanged = metric.toCm().toMm().toIn().toPt()io.writeLine("{negative == -1pt}|{zero == 0pt}|{metric == ts.fromScaledPoints(18577)}|{unchanged == ts.fromScaledPoints(18577)}")
true|true|true|true
Expected result
Expected result
Execution completes. Exit code 0.
true|true|true|true
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 39-58 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 290-292 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 119-137 -
topaz.stdlib.contract.physical-length-conversionatworking-tree
Keep the full range when changing units
Linkimport std.typeset as tsimport std.iolet low = ts.fromScaledPoints(-9223372036854775808).toMm().toCm().toIn().toPt()let high = ts.fromScaledPoints(9223372036854775807).toIn().toCm().toMm().toPt()io.writeLine("{low == -140737488355328pt}|{high == 140737488355327.9999847412109375pt}")
true|true
Expected result
Expected result
Execution completes. Exit code 0.
true|true
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 39-58 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 290-292 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 119-137 -
topaz.stdlib.contract.physical-length-conversionatworking-tree
Require the declared physical unit after conversion
Linklet distance: Length<Pt> = (1pt).toMm()
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:1:28
Source evidence
- compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 19-29 - compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 39-58 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 290-292 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 119-137 -
topaz.stdlib.contract.physical-length-conversionatworking-tree
Resolve an em length with an explicit positive font size
LinkResolve an em length with an explicit positive font size
Length<Em> stores a signed 64-bit relative count with 65,536 ticks per em. Its inclusive count range is -9223372036854775808 through 9223372036854775807. Zero and negative relative lengths are valid.
An em literal rounds its exact decimal magnitude to relative ticks with nearest-even rounding. Resolution uses those stored ticks and does not recover discarded literal precision.
resolve takes one Length<Pt> font size and returns Length<Pt>. The font size must have a strictly positive scaled-point count. A one-scaled-point font is valid.
If e is the stored em count and f is the stored font-size count, the physical result is roundEven of the exact rational e times f divided by 65,536. Multiply before rounding and round once to the physical grid.
The result must fit the common signed 64-bit physical range after rounding. Overflow stops with runtime diagnostic TPZ4004. Exact intermediates must not create a smaller accepted domain.
A zero or negative font size stops with runtime diagnostic TPZ4004, including when the relative length is zero. These failures are runtime faults and are not Result values.
A font size with a different unit marker, an int, or a float is rejected with TPZ5001. A physical Length has no resolve member. Relative lengths have no direct physical conversion or integer grid member.
The receiver evaluates once and then the font-size argument evaluates once. Resolution reads no ambient font state and performs no I/O or mutation. It preserves effects already caused by evaluating those inputs.
After resolution, use the physical conversion methods and integer interchange operations. LatinSpacing uses this same resolution before the selected paragraph grid quantizes the per-gap distance.
For 0.01em and 12pt, the relative count is 655 and the resolved count is 7,860 scaled points. Its nearest-even millipoint conversion is 120.
Why
An explicit positive font size gives a relative length one physical meaning. Shared integer rounding makes standalone lengths and letter-spacing budgets agree, including ties, negative offsets, and range boundaries.
Source evidence
- compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 303-312 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 99-118 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1013-1137 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1616-1657 -
topaz.stdlib.contract.length-resolveatworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Resolve zero and negative relative lengths with a positive font
Linkimport std.typeset as tsimport std.iolet negative = (-0.5em).resolve(12pt)let zero = (0em).resolve(ts.fromScaledPoints(1))let large = (140737488355327.9999847412109375em).resolve(ts.fromScaledPoints(1))io.writeLine("{negative == -6pt}|{zero == 0pt}|{large == ts.fromScaledPoints(140737488355328)}")
true|true|true
Expected result
Expected result
Execution completes. Exit code 0.
true|true|true
Source evidence
- compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 303-312 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 99-118 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1013-1137 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1616-1657 -
topaz.stdlib.contract.length-resolveatworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Evaluate the relative value and font size once in order
Linkimport std.iofunction relative() -> Length<Em> {io.writeLine("relative")0.5em}function font() -> Length<Pt> {io.writeLine("font")12pt}let result = relative().resolve(font())io.writeLine("{result == 6pt}")
relative font true
Expected result
Expected result
Execution completes. Exit code 0.
relativefonttrue
Source evidence
- compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 303-312 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 99-118 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1013-1137 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1616-1657 -
topaz.stdlib.contract.length-resolveatworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Reject a zero font size
Linklet relative = 0emlet font = 0ptrelative.resolve(font)
No stdout.
Expected result
Expected result
Rejection during run. Nonzero exit.
TPZ4004stdlib-length-font-positive atmain.tpz:3:1
Source evidence
- compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 303-312 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 99-118 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1013-1137 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1616-1657 -
topaz.stdlib.contract.length-resolveatworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Reject a negative font size
Linklet relative = 1emlet font = -12ptrelative.resolve(font)
No stdout.
Expected result
Expected result
Rejection during run. Nonzero exit.
TPZ4004stdlib-length-font-positive atmain.tpz:3:1
Source evidence
- compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 303-312 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 99-118 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1013-1137 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1616-1657 -
topaz.stdlib.contract.length-resolveatworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Reject an unrepresentable physical result
Linkimport std.typeset as tslet relative = 2emlet font = ts.fromScaledPoints(9223372036854775807)relative.resolve(font)
No stdout.
Expected result
Expected result
Rejection during run. Nonzero exit.
TPZ4004stdlib-length-unrepresentable atmain.tpz:4:1
Source evidence
- compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 303-312 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 99-118 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1013-1137 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1616-1657 -
topaz.stdlib.contract.length-resolveatworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Require a point font size
Linklet relative = 1emrelative.resolve(1mm)
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-physical-distance-requires-points atmain.tpz:2:18
Source evidence
- compiler/crates/topaz_self_frontend/topaz/length.tpz at
b48527d0a174· 94-99 - compiler/crates/topaz_syntax/src/length.rs at
b48527d0a174· 303-312 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 43-55 - compiler/crates/topaz_value/src/value/length.rs at
b48527d0a174· 99-118 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
b48527d0a174· 1303-1313 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1013-1137 - compiler/crates/topaz_product_runtime/src/runtime/call.rs at
b48527d0a174· 1616-1657 -
topaz.stdlib.contract.length-resolveatworking-tree - topaz.decision.letter-spacing-em.1 at
topaz.decisi
Repeat a paragraph plan deterministically
LinkRepeat a paragraph plan deterministically
For the same ordered input values, policies, calculation grid, and product release, classifyBreaks and breakParagraph produce the same result. This includes boundary order, selected breaks, line widths, costs, and the returned error variant.
Planning reads measured text and policy values without changing caller arrays. It does not shape text, load fonts, or write output. Ordinary argument evaluation finishes before the operation begins.
The selected cost model, admission rules, and search bounds define plan quality. The two reported plans expose their own costs for inspection.
Why
Repeatable paragraph layout lets applications cache plans and reproduce published pages. An explicit search contract separates reproducibility from the quality of a chosen plan.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 1-107 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 1-39 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 1-96 -
topaz.stdlib.contract.typeset-determinismatworking-tree
Retain a deterministic choice among equal cost candidates
Linkimport std.typeset as tsimport std.ioimport std.testlet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "word", width: 10pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Allowed(0), kind: ts.BreakKind.LatinSpace(), flagged: false }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Allowed(0), kind: ts.BreakKind.ClosingPunctuation(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}function category(kind: ts.BreakKind) -> string {match (kind) {case LatinSpace() => "space"case ClosingPunctuation() => "punctuation"case _ => "unexpected kind"}}for pass in ([0, 1]) {let result = test.assertOk(ts.breakParagraph(input))let optimized = result.optimized.lines[0]let greedy = result.greedy.lines[0]io.writeLine("{pass} {optimized.start} {optimized.endExclusive} {category(optimized.kind)} {category(greedy.kind)}")}
0 0 1 space punctuation 1 0 1 space punctuation
Expected result
Expected result
Execution completes. Exit code 0.
0 0 1 space punctuation1 0 1 space punctuation
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 1-107 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 1-39 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 1-96 -
topaz.stdlib.contract.typeset-determinismatworking-tree
Report the same first failing stage for repeated invalid input
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 2, text: "a", width: 1pt, trackingAfter: 0pt })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 0pt, firstTarget: 0pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}for pass in ([0, 1]) {match (ts.breakParagraph(input)) {case Err(InvalidPolicy(_)) => io.writeLine("{pass} InvalidPolicy")case _ => io.writeLine("unexpected result")}}
0 InvalidPolicy 1 InvalidPolicy
Expected result
Expected result
Execution completes. Exit code 0.
0 InvalidPolicy1 InvalidPolicy
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 1-107 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 1-39 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 1-96 -
topaz.stdlib.contract.typeset-determinismatworking-tree
Classify measured clusters into an ordered boundary sequence
LinkClassify measured clusters into an ordered boundary sequence
classifyBreaks reads measured clusters in array order and returns Result<Array<Break. It does not shape text, normalize strings, split a cluster, or change any supplied record or array.
Each BreakCluster.text is the scalar string for one indivisible measured unit. Empty text still occupies one cluster index. advance includes trackingAfter. A span width sums its advances and removes the trackingAfter of its final cluster.
advance and advance minus trackingAfter must be nonnegative point lengths. Zero advance and signed trackingAfter are accepted. Invalid extents return TypesetError.InvalidInput. Length arithmetic follows the common Length contract.
classifyBreaks sums stored point ticks and compares them with the stored point targets. It has no DistanceGrid argument and does not quantize to a paragraph grid. Exact equality with a target counts as fitting.
boundaryAllowed has exactly one entry for each cluster. Entry i governs the boundary after cluster i. The last entry must be true for nonempty input. A wrong mask length or a false last entry returns TypesetError.InvalidInput.
Validation checks mask length and terminal permission, word targets, forbidBefore, forbidAfter, generated hyphen indices, and measured extents in that order. Array checks visit entries in input order. Unicode mandatory crossings are checked before boundary conflicts are visited in increasing cluster order. An empty result follows successful structural and policy validation.
An empty cluster array with a valid empty boundary mask returns Ok with an empty opportunity array. It does not create a synthetic unit or terminal opportunity.
Successful nonempty results contain increasing, unique unitEnd values from one through the cluster count. unitEnd is an exclusive cluster index rather than a byte or scalar offset. The final opportunity has unitEnd equal to the cluster count and kind ForcedEnd.
Repeated calls with equal cluster values and equal policies produce the same ordered opportunities and categories. Validation and classification do not read host locale, perform I/O, invoke caller callbacks, or mutate input values. Argument expressions use the ordinary language evaluation order.
A BreakOpportunity carries a boundary and its category. It does not carry a penalty width or BreakRule. A caller preserving mandatory boundaries maps every ForcedEnd opportunity to a Forced penalty before calling breakParagraph.
Why
A measured cluster is the unit that shaping can safely keep together. Exclusive indices connect classification to paragraph items without converting through text offsets. A complete terminal boundary and deterministic order make the output suitable for reproducible layout.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 24-32 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 1-94 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 52-66 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-inputsatworking-tree
Classify atomic clusters in repeatable boundary order
Linkimport std.typeset as tsimport std.ioimport std.testlet clusters = [ts.BreakCluster { text: "한", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "글", advance: 1pt, trackingAfter: 0pt }]let selected = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true, true],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}for pass in ([0, 1]) {let breaks = test.assertOk(ts.classifyBreaks(clusters, selected))for boundary in (breaks) {let category = match (boundary.kind) {case CjkCluster() => "CJK"case ForcedEnd() => "end"case _ => "unexpected kind"}io.writeLine("{pass} {boundary.unitEnd} {category}")}}io.writeLine(clusters[0].text)
0 1 CJK 0 2 end 1 1 CJK 1 2 end 한
Expected result
Expected result
Execution completes. Exit code 0.
0 1 CJK0 2 end1 1 CJK1 2 end한
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 24-32 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 1-94 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 52-66 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-inputsatworking-tree
Classify an empty cluster sequence
Linkimport std.typeset as tsimport std.ioimport std.testlet clusters: Array<ts.BreakCluster> = []let selected = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}let breaks = test.assertOk(ts.classifyBreaks(clusters, selected))io.writeLine("{breaks.length}")
0
Expected result
Expected result
Execution completes. Exit code 0.
0
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 24-32 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 1-94 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 52-66 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-inputsatworking-tree
Reject a mask with the wrong number of entries
Linkimport std.typeset as tsimport std.ioimport std.testfunction outcome(value: Result<Array<ts.BreakOpportunity>, ts.TypesetError>) -> string {match (value) {case Ok(_) => "Ok"case Err(InvalidInput(_)) => "InvalidInput"case Err(InvalidPolicy(_)) => "InvalidPolicy"case Err(_) => "unexpected error"}}let clusters = [ts.BreakCluster { text: "a", advance: 1pt, trackingAfter: 0pt }]let selected = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}io.writeLine(outcome(ts.classifyBreaks(clusters, selected)))
InvalidInput
Expected result
Expected result
Execution completes. Exit code 0.
InvalidInput
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 24-32 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 1-94 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 52-66 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-inputsatworking-tree
Reject negative measured and untracked cluster extents
Linkimport std.typeset as tsimport std.ioimport std.testfunction outcome(value: Result<Array<ts.BreakOpportunity>, ts.TypesetError>) -> string {match (value) {case Ok(_) => "Ok"case Err(InvalidInput(_)) => "InvalidInput"case Err(InvalidPolicy(_)) => "InvalidPolicy"case Err(_) => "unexpected error"}}let selected = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}io.writeLine(outcome(ts.classifyBreaks([ts.BreakCluster { text: "a", advance: -1pt, trackingAfter: 0pt }], selected)))io.writeLine(outcome(ts.classifyBreaks([ts.BreakCluster { text: "b", advance: 1pt, trackingAfter: 2pt }], selected)))
InvalidInput InvalidInput
Expected result
Expected result
Execution completes. Exit code 0.
InvalidInputInvalidInput
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 24-32 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 1-94 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 52-66 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-inputsatworking-tree
Reject a masked paragraph end in every ruleset
Linkimport std.typeset as tsimport std.ioimport std.testfunction outcome(value: Result<Array<ts.BreakOpportunity>, ts.TypesetError>) -> string {match (value) {case Ok(_) => "Ok"case Err(InvalidInput(_)) => "InvalidInput"case Err(InvalidPolicy(_)) => "InvalidPolicy"case Err(_) => "unexpected error"}}let clusters = [ts.BreakCluster { text: "a", advance: 1pt, trackingAfter: 0pt }]let atlas = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [false],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}let unicode = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.Unicode16Ja(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [false],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}io.writeLine(outcome(ts.classifyBreaks(clusters, atlas)))io.writeLine(outcome(ts.classifyBreaks(clusters, unicode)))
InvalidInput InvalidInput
Expected result
Expected result
Execution completes. Exit code 0.
InvalidInputInvalidInput
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 24-32 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 1-94 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 52-66 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-inputsatworking-tree
Keep exact point measurements at the classifier boundary
Linkimport std.typeset as tsimport std.testimport std.iolet clusters = [ts.BreakCluster { text: "a", advance: 0.5002pt, trackingAfter: 0pt },ts.BreakCluster { text: "b", advance: 0.5002pt, trackingAfter: 0pt }]let policy = ts.BreakPolicy {mode: ts.BreakMode.Word(), rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [], forbidAfter: [], boundaryAllowed: [true, true],generatedHyphenEnds: [], protectFittingLatin: false, preserveShortWords: false,narrowestWordTarget: 0pt, bodyWordTarget: 1pt}let result = test.assertOk(ts.classifyBreaks(clusters, policy))for boundary in (result) {io.writeLine("{boundary.unitEnd}")}
1 2
Expected result
Expected result
Execution completes. Exit code 0.
12
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 24-32 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 1-94 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 52-66 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-inputsatworking-tree
Apply word policy without crossing protected cluster boundaries
LinkApply word policy without crossing protected cluster boundaries
BreakPolicy supplies every classification choice explicitly. rules selects the character boundary policy. mode selects word protection. The two choices are independent and neither consults the host locale.
forbidBefore and forbidAfter contain Unicode scalar values. Each integer must be between zero and 1114111 and outside 55296 through 57343. Invalid values return TypesetError.InvalidPolicy. Ordering and duplicate entries do not change membership.
At an ordinary interior boundary, forbidAfter checks the final scalar on the left and forbidBefore checks the first scalar on the right. These custom bans filter admitted candidates and do not create candidates. They do not replace non-tailorable Unicode decisions.
The shaping boundary mask can remove an ordinary candidate. A mask conflict with a mandatory or non-tailorable required Unicode opportunity returns TypesetError.InvalidInput. A generated hyphen or character mode never bypasses a false mask entry.
generatedHyphenEnds contains exclusive interior cluster indices. Both neighboring clusters must consist of Unicode Alphabetic scalars or the apostrophes U+0027 and U+2019. An out of range index or nonword neighbor returns TypesetError.InvalidInput. Duplicate indices have no additional effect.
A generated index changes a missing or HardFallback candidate to LatinSoftHyphen when Unicode permits tailoring there. It does not replace another category or a non-tailorable prohibition. The selected locale, custom bans, shaping mask, and short-word policy still apply. The function does not insert text or measure a hyphen glyph.
narrowestWordTarget and bodyWordTarget are independent nonnegative point lengths. A negative target returns TypesetError.InvalidPolicy. Zero is accepted and equality with a target counts as fitting.
For a HardFallback inside a contiguous run of Alphabetic or apostrophe clusters, protectFittingLatin suppresses the break when the measured run width is at most narrowestWordTarget. Word mode also suppresses that break when the run width is at most bodyWordTarget. Character mode removes this second word-fit test while retaining all other constraints.
Word mode can add emergency boundaries inside an oversized word whose width exceeds bodyWordTarget. Unicode modes retain non-tailorable prohibitions and locale bans. Unicode16Ko also preserves a fitting whitespace-delimited Hangul run at bodyWordTarget.
With preserveShortWords, an interior boundary between nonwhitespace clusters is suppressed when their whitespace-delimited run has at most three Alphabetic or Number scalars. It is also suppressed when that run fits bodyWordTarget. These tests include generated hyphens. Mandatory and non-tailorable required Unicode opportunities retain their priority.
Why
Word fitting and character breaking answer different layout needs. Explicit thresholds let callers retain fitting words while admitting emergency breaks in oversized text. Applying shaping and punctuation constraints after candidate generation prevents a convenience option from splitting protected text.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 4-16 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 57-86 - compiler/crates/topaz_resolve/src/std/typeset/locale.tpz at
f3807a34248e· 61-106 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-policyatworking-tree
Keep generated hyphens behind the shaping mask
Linkimport std.typeset as tsimport std.ioimport std.testlet clusters = [ts.BreakCluster { text: "a", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "b", advance: 1pt, trackingAfter: 0pt }]let selected = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [false, true],generatedHyphenEnds: [1, 1],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}let breaks = test.assertOk(ts.classifyBreaks(clusters, selected))for boundary in (breaks) {io.writeLine("{boundary.unitEnd}")}
2
Expected result
Expected result
Execution completes. Exit code 0.
2
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 4-16 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 57-86 - compiler/crates/topaz_resolve/src/std/typeset/locale.tpz at
f3807a34248e· 61-106 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-policyatworking-tree
Keep a word together at the fitting threshold
Linkimport std.typeset as tsimport std.ioimport std.testlet clusters = [ts.BreakCluster { text: "a", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "b", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "c", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "d", advance: 1pt, trackingAfter: 0pt }]let fitting = ts.BreakPolicy {mode: ts.BreakMode.Word(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true, true, true, true],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 4pt}let oversized = ts.BreakPolicy {mode: ts.BreakMode.Word(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true, true, true, true],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 3pt}let guarded = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true, true, true, true],generatedHyphenEnds: [],protectFittingLatin: true,preserveShortWords: false,narrowestWordTarget: 4pt,bodyWordTarget: 0pt}let a = test.assertOk(ts.classifyBreaks(clusters, fitting))let b = test.assertOk(ts.classifyBreaks(clusters, oversized))let c = test.assertOk(ts.classifyBreaks(clusters, guarded))io.writeLine("{a.length} {b.length} {c.length}")
1 4 1
Expected result
Expected result
Execution completes. Exit code 0.
1 4 1
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 4-16 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 57-86 - compiler/crates/topaz_resolve/src/std/typeset/locale.tpz at
f3807a34248e· 61-106 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-policyatworking-tree
Classify one generated hyphen boundary despite duplicate input indices
Linkimport std.typeset as tsimport std.ioimport std.testlet clusters = [ts.BreakCluster { text: "a", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "b", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "c", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "d", advance: 1pt, trackingAfter: 0pt }]let selected = ts.BreakPolicy {mode: ts.BreakMode.Word(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true, true, true, true],generatedHyphenEnds: [2, 2],protectFittingLatin: true,preserveShortWords: false,narrowestWordTarget: 4pt,bodyWordTarget: 4pt}let breaks = test.assertOk(ts.classifyBreaks(clusters, selected))for boundary in (breaks) {let category = match (boundary.kind) {case LatinSoftHyphen() => "hyphen"case ForcedEnd() => "end"case _ => "unexpected kind"}io.writeLine("{boundary.unitEnd} {category}")}
2 hyphen 4 end
Expected result
Expected result
Execution completes. Exit code 0.
2 hyphen4 end
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 4-16 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 57-86 - compiler/crates/topaz_resolve/src/std/typeset/locale.tpz at
f3807a34248e· 61-106 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-policyatworking-tree
Preserve a word of three counted scalars
Linkimport std.typeset as tsimport std.ioimport std.testlet clusters = [ts.BreakCluster { text: "a", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "b", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "c", advance: 1pt, trackingAfter: 0pt }]let selected = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true, true, true],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: true,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}let breaks = test.assertOk(ts.classifyBreaks(clusters, selected))io.writeLine("{breaks.length} {breaks[0].unitEnd}")
1 3
Expected result
Expected result
Execution completes. Exit code 0.
1 3
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 4-16 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 57-86 - compiler/crates/topaz_resolve/src/std/typeset/locale.tpz at
f3807a34248e· 61-106 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-policyatworking-tree
Distinguish invalid policy values from invalid generated boundaries
Linkimport std.typeset as tsimport std.ioimport std.testfunction outcome(value: Result<Array<ts.BreakOpportunity>, ts.TypesetError>) -> string {match (value) {case Ok(_) => "Ok"case Err(InvalidInput(_)) => "InvalidInput"case Err(InvalidPolicy(_)) => "InvalidPolicy"case Err(_) => "unexpected error"}}let clusters = [ts.BreakCluster { text: "a", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "b", advance: 1pt, trackingAfter: 0pt }]let target = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true, true],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: -1pt}let scalar = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [55296],forbidAfter: [],boundaryAllowed: [true, true],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}let boundary = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true, true],generatedHyphenEnds: [2],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}io.writeLine(outcome(ts.classifyBreaks(clusters, target)))io.writeLine(outcome(ts.classifyBreaks(clusters, scalar)))io.writeLine(outcome(ts.classifyBreaks(clusters, boundary)))
InvalidPolicy InvalidPolicy InvalidInput
Expected result
Expected result
Execution completes. Exit code 0.
InvalidPolicyInvalidPolicyInvalidInput
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 4-16 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 57-86 - compiler/crates/topaz_resolve/src/std/typeset/locale.tpz at
f3807a34248e· 61-106 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 24-25 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-policyatworking-tree
Keep boundary policy separate from break category
LinkKeep boundary policy separate from break category
KinsokuRules is an explicit choice of boundary policy. AtlasDefault retains its fixed Atlas punctuation sets and context checks. It does not acquire new Unicode rules when the host changes.
Unicode16Ko, Unicode16Zh, and Unicode16Ja use the ordered Unicode 16.0.0 UAX 14 revision 53 decisions. They retain non-tailorable prohibitions, mandatory breaks, and required opportunities before locale and custom typography rules.
The Korean policy applies KLReq punctuation and fitting Hangul word handling. The Japanese policy applies strict JLReq kinsoku including small kana and numeric prefix and suffix contexts. The Chinese policy applies CLReq basic punctuation handling. The exact versioned character predicates are the referenced policy definitions.
Unicode policies reject a cluster that crosses a mandatory line break with TypesetError.InvalidInput. A mandatory break after an intact cluster is a ForcedEnd opportunity even when more clusters follow. A cluster boundary inside a forbidden Unicode sequence is not an opportunity.
LatinSpace marks an admitted boundary after a cluster whose text is U+0020. LatinHyphen marks an admitted boundary after an existing hyphen cluster. LatinSoftHyphen marks an admitted generated hyphen candidate. Neither category inserts a character into the input.
ClosingPunctuation marks an admitted boundary after the selected closing-punctuation category. CjkCluster marks the admitted CJK or East Asian cluster category. HardFallback marks another admitted boundary or a permitted emergency word boundary. These categories do not authorize a break excluded by the selected policy.
ForcedEnd marks the paragraph end or a mandatory Unicode boundary. BreakRule.Forced is the distinct planning constraint that prevents a plan from crossing that position. A ForcedEnd category on a caller-created penalty does not replace its BreakRule.
For Unicode candidates, mandatory boundaries are classified first, followed by space, existing hyphen, closing punctuation, CJK or East Asian text, and HardFallback. Generated hyphens replace a missing or HardFallback category when admissible. Output ordering follows the cluster indices rather than category order.
Why
A locale policy decides whether a boundary can be used. A category tells the planner why that admitted boundary exists. Keeping those roles distinct lets the same paragraph model carry Unicode, locale, and caller-supplied constraints without treating a punctuation label as permission.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/atlas_breaks.tpz at
f3807a34248e· 1-64 - compiler/crates/topaz_resolve/src/std/typeset/uax14.tpz at
f3807a34248e· 1-157 - compiler/crates/topaz_resolve/src/std/typeset/locale.tpz at
f3807a34248e· 1-59 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 27-86 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-categoriesatworking-tree
Select Japanese small-kana protection explicitly
Linkimport std.typeset as tsimport std.ioimport std.testlet clusters = [ts.BreakCluster { text: "あ", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "ぁ", advance: 1pt, trackingAfter: 0pt }]let atlas = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.AtlasDefault(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true, true],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}let japanese = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.Unicode16Ja(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true, true],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}let a = test.assertOk(ts.classifyBreaks(clusters, atlas))let b = test.assertOk(ts.classifyBreaks(clusters, japanese))io.writeLine("{a.length} {b.length}")
2 1
Expected result
Expected result
Execution completes. Exit code 0.
2 1
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/atlas_breaks.tpz at
f3807a34248e· 1-64 - compiler/crates/topaz_resolve/src/std/typeset/uax14.tpz at
f3807a34248e· 1-157 - compiler/crates/topaz_resolve/src/std/typeset/locale.tpz at
f3807a34248e· 1-59 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 27-86 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-categoriesatworking-tree
Keep a nonbreaking space protected in character mode
Linkimport std.typeset as tsimport std.ioimport std.testlet clusters = [ts.BreakCluster { text: "A", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: " ", advance: 1pt, trackingAfter: 0pt }, ts.BreakCluster { text: "B", advance: 1pt, trackingAfter: 0pt }]let selected = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.Unicode16Ja(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true, true, true],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}let breaks = test.assertOk(ts.classifyBreaks(clusters, selected))io.writeLine("{breaks.length} {breaks[0].unitEnd}")
1 3
Expected result
Expected result
Execution completes. Exit code 0.
1 3
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/atlas_breaks.tpz at
f3807a34248e· 1-64 - compiler/crates/topaz_resolve/src/std/typeset/uax14.tpz at
f3807a34248e· 1-157 - compiler/crates/topaz_resolve/src/std/typeset/locale.tpz at
f3807a34248e· 1-59 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 27-86 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-categoriesatworking-tree
Reject a cluster that hides a mandatory Unicode break
Linkimport std.typeset as tsimport std.ioimport std.testfunction outcome(value: Result<Array<ts.BreakOpportunity>, ts.TypesetError>) -> string {match (value) {case Ok(_) => "Ok"case Err(InvalidInput(_)) => "InvalidInput"case Err(InvalidPolicy(_)) => "InvalidPolicy"case Err(_) => "unexpected error"}}let clusters = [ts.BreakCluster { text: "A\nB", advance: 1pt, trackingAfter: 0pt }]let selected = ts.BreakPolicy {mode: ts.BreakMode.Character(),rules: ts.KinsokuRules.Unicode16Ja(),forbidBefore: [],forbidAfter: [],boundaryAllowed: [true],generatedHyphenEnds: [],protectFittingLatin: false,preserveShortWords: false,narrowestWordTarget: 0pt,bodyWordTarget: 0pt}io.writeLine(outcome(ts.classifyBreaks(clusters, selected)))
InvalidInput
Expected result
Expected result
Execution completes. Exit code 0.
InvalidInput
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/atlas_breaks.tpz at
f3807a34248e· 1-64 - compiler/crates/topaz_resolve/src/std/typeset/uax14.tpz at
f3807a34248e· 1-157 - compiler/crates/topaz_resolve/src/std/typeset/locale.tpz at
f3807a34248e· 1-59 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
f3807a34248e· 27-86 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 1319-1340 -
topaz.stdlib.contract.typeset-break-categoriesatworking-tree
Express preference, mandatory breaks, and forbidden breaks explicitly
LinkExpress preference, mandatory breaks, and forbidden breaks explicitly
Allowed carries an int preference for a selectable penalty. Negative values favor a break and positive values discourage it under the selected cost model. Zero is neutral. Every representable int remains an Allowed value rather than becoming a hard rule at a numeric threshold.
Forced requires every successful paragraph plan to end a line at that boundary. A plan cannot cross it or omit it to improve cost. If the required line cannot be admitted, planning returns the applicable TypesetError instead of ignoring the constraint.
Forbidden makes that penalty unselectable. It is not represented by a large Allowed preference. Penalty validation and duplicate-boundary rules determine the treatment of caller-supplied penalties at the same position.
BreakKind records a category and BreakRule records a planning constraint. Selecting a kind does not turn an Allowed penalty into Forced or Forbidden. The selected cost model interprets the Allowed preference and preserves both hard rules.
Constructing a rule creates an enum value and has no I/O or mutation. Allowed requires an int payload. An argument of another type is rejected with TPZ5001.
Why
An explicit variant makes a hard constraint independent of scoring scale. Callers can change the cost model without changing the meaning of a mandatory or forbidden break. Signed preferences remain a separate choice about plan quality.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 15-23 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 68-80 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 733-755 - compiler/crates/topaz_self_frontend/topaz/checker/call_facts.tpz at
f3807a34248e· 1660-1682 -
topaz.stdlib.contract.typeset-break-rulesatworking-tree
Keep signed penalty preferences distinct from hard break rules
Linkimport std.typeset as tsimport std.ioimport std.testlet rules = [ts.BreakRule.Allowed(-10000), ts.BreakRule.Allowed(0), ts.BreakRule.Allowed(10000)]for rule in (rules) {match (rule) {case Allowed(value) => io.writeLine("{value}")case _ => io.writeLine("unexpected rule")}}
-10000 0 10000
Expected result
Expected result
Execution completes. Exit code 0.
-10000010000
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 15-23 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 68-80 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 733-755 - compiler/crates/topaz_self_frontend/topaz/checker/call_facts.tpz at
f3807a34248e· 1660-1682 -
topaz.stdlib.contract.typeset-break-rulesatworking-tree
Reject a noninteger break preference
Linkimport std.typeset as tslet rule = ts.BreakRule.Allowed("avoid")
No stdout.
Expected result
Expected result
Rejection during check. Nonzero exit.
TPZ5001stdlib-break-rule-requires-integer atmain.tpz:2:33
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 15-23 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 68-80 - compiler/crates/topaz_self_frontend/topaz/checker/members_capabilities.tpz at
f3807a34248e· 691-713 - compiler/crates/topaz_self_frontend/topaz/checker/call_complete.tpz at
f3807a34248e· 733-755 - compiler/crates/topaz_self_frontend/topaz/checker/call_facts.tpz at
f3807a34248e· 1660-1682 -
topaz.stdlib.contract.typeset-break-rulesatworking-tree
Choose deterministic paragraph plans
LinkChoose deterministic paragraph plans
breakParagraph evaluates its Paragraph argument through the ordinary call rules, then reads its item sequence and policies. Planning performs no input mutation, text shaping, external I/O, or random selection. The same ordered input and computation rules produce the same lines and scores.
Paragraph.items supplies measured BoxItem and GlueItem units with contiguous indices from zero. PenaltyItem entries refer to boundaries between those units. The planner uses these measurements and supplied penalties directly. It does not call classifyBreaks or insert a terminal penalty.
Paragraph.grid selects integer quantization at the computation boundary. Every public distance remains Length<Pt>. FixedPoint requires MilliPoint. KnuthPlass accepts either DistanceGrid. The ordinary checked length conversion applies before integer planning.
Policy validation precedes item validation. Geometry, the cost model and grid combination, justification values, and KnuthPlassPolicy are validated even when a chosen model does not use a policy field for scoring. Invalid configuration returns TypesetError.InvalidPolicy. Invalid unit indices, capacities, or penalty endpoints return TypesetError.InvalidInput.
A valid empty items array returns two empty plans with zero totalCost and zero breakOpportunityCount. This case still validates the policies. Each empty plan reports its selected grid and None() for boundedFillFeasible.
For nonempty input, the planner orders penalties by increasing unitEnd and preserves supplied order at equal boundaries. Allowed and Forced entries are candidates. Forbidden entries are excluded individually. Duplicate candidates remain distinct. A Forced entry requires the plan to visit its boundary, where another eligible entry may be selected.
No candidates returns TypesetError.NoBreakOpportunities. The planner constructs the greedy baseline before the optimized search. Failure to complete that baseline returns TypesetError.NoGreedyPlan. A completed baseline followed by an unsuccessful optimized search returns TypesetError.NoPlan. An Err result contains no partial ParagraphResult.
For FixedPoint, greedy chooses the farthest raw width that fits the next target before the first overwide candidate or Forced boundary. If the first candidate is already overwide, greedy chooses it to advance. For KnuthPlass, greedy chooses the last ratio-admissible candidate up to the next Forced boundary. Every chosen boundary advances past the previous one.
FixedPoint optimization starts with the preceding 80 candidates at each destination. It extends the search backward while the preceding span fits the larger base target plus available shrink and one grid unit. It retains the least score for each boundary and semantic state. It admits at most two consecutive LatinSoftHyphen breaks.
FixedPoint optimized admission uses trimmed text width plus the selected penalty width. The width limit is the target plus available shrink for a nonfinal line, with one grid unit of rounding allowance. A line containing one unit can exceed this limit so an indivisible unit can make progress. Greedy reports the same limit but selects candidates using its raw width rule.
With FixedPoint, a justified mode, and Some(latinSpacing), optimization first searches for a complete plan whose lines satisfy the bounded fill check. It prefers that plan when found. Otherwise it repeats the search without that check. This preference can select a plan with a higher totalCost than the greedy plan.
KnuthPlass optimization considers every preceding candidate and retains each distinct line geometry bucket, fitness class, and flagged state at a boundary. FixedPoint also retains its soft hyphen streak. State buckets distinguish drop cap lines and collapse after the inset ends.
Equal scores retain the first visited predecessor. Candidates are visited in boundary order, with supplied order at equal boundaries. States are visited by increasing line geometry bucket, soft hyphen streak, fitness class, and then unflagged before flagged. Final selection uses the same first-on-equal rule.
The optimized field reports the selected model search and admission policy. The greedy field reports its baseline from the same input. Each reported cost belongs to the plan selected by these candidate, state, and admission rules. Ordinary checked arithmetic faults remain faults and are not converted into a TypesetError value.
Why
Applications need reproducible line boundaries and a clear choice between a bounded fixed point search and a Knuth Plass state search. Reporting both selected plans preserves the baseline for inspection. Keeping policy failure, missing candidates, and unsuccessful searches distinct lets a caller decide which input to revise.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 1-106 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 27-87 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 11-27 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
f3807a34248e· 1-28 -
topaz.stdlib.contract.typeset-paragraph-planningatworking-tree
Plan a paragraph through its supplied boundaries
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.BoxItem(ts.Box { unitIndex: 1, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 2, width: 0pt, rule: ts.BreakRule.Allowed(0), kind: ts.BreakKind.LatinSpace(), flagged: false }),ts.Item.BoxItem(ts.Box { unitIndex: 2, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.BoxItem(ts.Box { unitIndex: 3, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 4, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 2pt, firstTarget: 2pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Ok(result) => {for line in (result.optimized.lines) {io.writeLine("{line.start} {line.endExclusive}")}io.writeLine("{result.greedy.lines.length} {result.breakOpportunityCount}")}case Err(_) => io.writeLine("unexpected error")}
0 2 2 4 2 2
Expected result
Expected result
Execution completes. Exit code 0.
0 22 42 2
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 1-106 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 27-87 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 11-27 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
f3807a34248e· 1-28 -
topaz.stdlib.contract.typeset-paragraph-planningatworking-tree
Plan a valid empty paragraph
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = []let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Ok(result) => {io.writeLine("{result.optimized.lines.length} {result.greedy.lines.length}")io.writeLine("{result.optimized.totalCost} {result.greedy.totalCost} {result.breakOpportunityCount}")}case Err(_) => io.writeLine("unexpected error")}
0 0 0 0 0
Expected result
Expected result
Execution completes. Exit code 0.
0 00 0 0
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 1-106 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 27-87 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 11-27 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
f3807a34248e· 1-28 -
topaz.stdlib.contract.typeset-paragraph-planningatworking-tree
Report absent break opportunities
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 0pt })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(NoBreakOpportunities()) => io.writeLine("NoBreakOpportunities")case _ => io.writeLine("unexpected result")}
NoBreakOpportunities
Expected result
Expected result
Execution completes. Exit code 0.
NoBreakOpportunities
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 1-106 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 27-87 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 11-27 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
f3807a34248e· 1-28 -
topaz.stdlib.contract.typeset-paragraph-planningatworking-tree
Report a missing greedy completion
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.BoxItem(ts.Box { unitIndex: 1, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Allowed(0), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(NoGreedyPlan()) => io.writeLine("NoGreedyPlan")case _ => io.writeLine("unexpected result")}
NoGreedyPlan
Expected result
Expected result
Execution completes. Exit code 0.
NoGreedyPlan
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 1-106 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 27-87 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 11-27 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
f3807a34248e· 1-28 -
topaz.stdlib.contract.typeset-paragraph-planningatworking-tree
Report three forced soft hyphens in a row
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.LatinSoftHyphen(), flagged: false }),ts.Item.BoxItem(ts.Box { unitIndex: 1, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 2, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.LatinSoftHyphen(), flagged: false }),ts.Item.BoxItem(ts.Box { unitIndex: 2, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 3, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.LatinSoftHyphen(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 1pt, firstTarget: 1pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(NoPlan()) => io.writeLine("NoPlan")case _ => io.writeLine("unexpected result")}
NoPlan
Expected result
Expected result
Execution completes. Exit code 0.
NoPlan
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 1-106 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-36 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 27-87 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 11-27 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
f3807a34248e· 1-28 -
topaz.stdlib.contract.typeset-paragraph-planningatworking-tree
Compute each line target from one geometry
LinkCompute each line target from one geometry
LineGeometry.bodyTarget and firstTarget are positive Length<Pt> distances that remain positive after conversion to the selected grid. The line beginning at unit zero uses firstTarget. Each later line uses bodyTarget.
dropCapSpan is an integer from zero through three. dropCapInset is a nonnegative Length<Pt>. When both are positive, subtract the inset from the first dropCapSpan line targets. A zero span or zero inset leaves the base targets unchanged.
An active inset must be smaller than both firstTarget and bodyTarget after quantization. A nonpositive base target, span outside zero through three, negative inset, or inset that consumes a target returns TypesetError.InvalidPolicy before item validation.
PlanLine.target reports the resulting physical target after the first line choice, quantization, and any inset. Geometry selects the available width and does not alter source unit indices or measured text widths.
Why
One geometry record describes first line indentation and the finite span of a drop cap. Checking effective targets before searching prevents different search paths from assigning different meanings to unusable widths.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-9 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 82-87 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 1-8 -
topaz.stdlib.contract.typeset-line-geometryatworking-tree
Apply the first target and drop cap inset in line order
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 3pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false }),ts.Item.BoxItem(ts.Box { unitIndex: 1, text: "a", width: 3pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 2, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 8pt, dropCapSpan: 1, dropCapInset: 2pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Ok(result) => {let first = result.optimized.lines[0]let second = result.optimized.lines[1]io.writeLine("{first.target == 6pt} {second.target == 10pt}")}case Err(_) => io.writeLine("unexpected error")}
true true
Expected result
Expected result
Execution completes. Exit code 0.
true true
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-9 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 82-87 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 1-8 -
topaz.stdlib.contract.typeset-line-geometryatworking-tree
Reject a zero line target before planning
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 0pt, firstTarget: 0pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidPolicy(_)) => io.writeLine("InvalidPolicy")case _ => io.writeLine("unexpected result")}
InvalidPolicy
Expected result
Expected result
Execution completes. Exit code 0.
InvalidPolicy
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-9 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 82-87 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 1-8 -
topaz.stdlib.contract.typeset-line-geometryatworking-tree
Reject a negative drop cap inset
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 1, dropCapInset: -1pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidPolicy(_)) => io.writeLine("InvalidPolicy")case _ => io.writeLine("unexpected result")}
InvalidPolicy
Expected result
Expected result
Execution completes. Exit code 0.
InvalidPolicy
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-9 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 82-87 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 1-8 -
topaz.stdlib.contract.typeset-line-geometryatworking-tree
Read plan boundaries, measurements, and scores separately
LinkRead plan boundaries, measurements, and scores separately
ParagraphPlan.lines contains line records in source order. Each nonempty line consumes the half-open unit interval from start through endExclusive. The first line starts at zero, adjacent lines share an endpoint, and the last line ends at the unit count. These are BoxItem and GlueItem indices rather than item array offsets, scalar offsets, or byte offsets.
trimmedEndExclusive removes trailing units whose complete text is an ASCII space or a no-break space. It stays between start and endExclusive. displayTextScalarLength counts Unicode scalars in the consumed text after trailing ASCII spaces and no-break spaces are removed. It excludes the selected penalty insertion and retains leading text.
A unit width includes its following tracking contribution. rawTextWidth is the sum of consumed unit widths minus the last consumed unit trackingAfter. trimmedTextWidth applies the same formula to the trimmed unit interval. An empty trimmed interval has zero width. Reading a plan does not reshape text or modify source measurements.
kind reports the selected penalty kind. selectedPenaltyWidth reports that selected penalty width after conversion to the computation grid for every kind and cost model. The insertion contributes at the selected boundary and leaves the stored text, source indices, and displayTextScalarLength unchanged.
FixedPoint costTextWidth is the raw width, capped at the target minus selectedPenaltyWidth on a nonfinal line with bounded spacing capacity. KnuthPlass costTextWidth excludes leading GlueItem units and excludes trailing GlueItem units for an ordinary break. A Forced KnuthPlass break retains its trailing glue and associated capacity.
FixedPoint postValidationWidthLimit is Some(limit) with the effective target, nonfinal shrink allowance, and one grid unit of rounding allowance. It reports the optimized admission threshold. Single-unit lines and greedy choices can exceed it. KnuthPlass reports None() because its admission is expressed by glue capacity and adjustment ratios.
cost is the selected line contribution under the paragraph cost model, including applicable penalty and transition demerits. adjustmentRatioR is zero for FixedPoint. For KnuthPlass it is the signed ratio to the selected stretch or shrink capacity, scaled by 100000000 and rounded to nearest with ties to even.
ParagraphPlan.totalCost is the sum of its line costs in line order. Scores can be negative when an Allowed penalty rewards a break. A score is interpreted with its CostModel and policies. ParagraphPlan.grid reports the computation grid, while all reported distances retain Length<Pt>.
For an applicable FixedPoint bounded fill search, optimized.boundedFillFeasible is Some(true) when that search succeeds and Some(false) when the second search supplies the plan. In other cases it is None(). The greedy plan always reports None(). This field records feasibility within the configured bounded search.
ParagraphResult.optimized and greedy contain the two plans from the same validated input. breakOpportunityCount counts all eligible penalty entries before planning, including equal-boundary duplicates and the supplied terminal candidate. It is independent of the number of output lines.
Why
A renderer needs source consumption, display trimming, width admission, and scoring as separate measurements. Explicit indices and optional feasibility results let the renderer inspect source consumption and width fit for every selected line.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 55-67 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 7-25 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 52-80 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 1-27 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-46 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 78-105 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 28-36 -
topaz.stdlib.contract.typeset-plan-reportingatworking-tree
Keep consumed units distinct from displayed trailing space
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 3pt, trackingAfter: 0pt }),ts.Item.GlueItem(ts.Glue { unitIndex: 1, text: " ", width: 1pt, trackingAfter: 0pt, stretch: 0pt, shrink: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 2, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 4pt, firstTarget: 4pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Ok(result) => {let plan = result.optimizedlet line = plan.lines[0]io.writeLine("{line.start} {line.endExclusive} {line.trimmedEndExclusive} {line.displayTextScalarLength}")io.writeLine("{line.rawTextWidth == 4pt} {line.trimmedTextWidth == 3pt} {line.costTextWidth == 4pt}")io.writeLine("{line.selectedPenaltyWidth == 0pt} {line.adjustmentRatioR}")match (line.postValidationWidthLimit) {case Some(limit) => io.writeLine("{limit == 4.001pt}")case None() => io.writeLine("missing limit")}match (plan.boundedFillFeasible) {case None() => io.writeLine("no fill search")case Some(_) => io.writeLine("unexpected fill search")}}case Err(_) => io.writeLine("unexpected error")}
0 2 1 1 true true true true 0 true no fill search
Expected result
Expected result
Execution completes. Exit code 0.
0 2 1 1true true truetrue 0trueno fill search
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 55-67 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 7-25 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 52-80 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 1-27 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-46 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 78-105 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 28-36 -
topaz.stdlib.contract.typeset-plan-reportingatworking-tree
Report an indivisible unit wider than its target
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 5pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 1pt, firstTarget: 1pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Ok(result) => {let line = result.optimized.lines[0]io.writeLine("{line.start} {line.endExclusive} {line.trimmedTextWidth == 5pt} {line.target == 1pt}")}case Err(_) => io.writeLine("unexpected error")}
0 1 true true
Expected result
Expected result
Execution completes. Exit code 0.
0 1 true true
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 55-67 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 7-25 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 52-80 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 1-27 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-46 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
f3807a34248e· 78-105 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
f3807a34248e· 28-36 -
topaz.stdlib.contract.typeset-plan-reportingatworking-tree
Set Knuth Plass tolerance and transition costs
LinkSet Knuth Plass tolerance and transition costs
Every KnuthPlassPolicy field is a nonnegative int. A negative toleranceR, linePenalty, fitnessDemerit, flaggedDemerit, or finalFlaggedDemerit returns TypesetError.InvalidPolicy. Validation applies even when the selected CostModel is FixedPoint.
KnuthPlass uses explicit GlueItem stretch and shrink. JustificationPolicy values are validated but do not replace these capacities or its ratio score. Leading glue is discarded for the natural width and capacities. An ordinary break discards trailing glue, while a Forced break consumes trailing glue so a caller can represent a ragged final line.
Let slack be the target minus natural text width and selected penalty width. Nonnegative slack uses total stretch and negative slack uses total shrink. Zero capacity admits an exact fit and rejects a nonzero slack. Shrink admits ratios down to negative one. Positive ratios must be no greater than toleranceR divided by 100000000.
The reported adjustment ratio is scaled by 100000000 and rounded to nearest with ties to even. Admission and fitness use the exact ratio before rounding. Badness is 100 times the absolute ratio cubed, rounded to nearest with ties to even and capped at 10000.
Add linePenalty and badness, then square their sum for the basic line score. An Allowed penalty adds its squared value when nonnegative and subtracts its squared value when negative. Forced penalties add no such term. The resulting score is a signed checked int.
The four fitness classes are ratios below negative one half, ratios from negative one half through one half, ratios above one half through one, and ratios above one. Add fitnessDemerit when consecutive lines differ by more than one class. The first line has no preceding fitness transition.
Add flaggedDemerit when both the preceding and selected penalties are flagged. Add finalFlaggedDemerit when the final line follows a flagged penalty, whether or not its own penalty is flagged. The first line has no preceding flag.
An exact fit with linePenalty equal to 10, zero penalty cost, and no transition demerit has line cost 100 and adjustmentRatioR equal to zero. A nonexact line with no usable stretch or shrink is inadmissible, including a final line whose caller supplied no terminal capacity.
Why
Tolerance controls acceptable adjustment and demerits control the relative cost of adjacent lines. Explicit glue capacities make final line behavior and flagged transitions reproducible without hidden default glue or a separate final line algorithm.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-51 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 32-35 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 46-48 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
f3807a34248e· 4-28 -
topaz.stdlib.contract.typeset-knuth-plass-policyatworking-tree
Score an exact Knuth Plass line
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 10pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.KnuthPlass(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Ok(result) => {let line = result.optimized.lines[0]io.writeLine("{line.cost} {line.adjustmentRatioR} {result.optimized.totalCost}")match (line.postValidationWidthLimit) {case None() => io.writeLine("ratio admission")case Some(_) => io.writeLine("unexpected width limit")}}case Err(_) => io.writeLine("unexpected error")}
100 0 100 ratio admission
Expected result
Expected result
Execution completes. Exit code 0.
100 0 100ratio admission
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-51 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 32-35 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 46-48 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
f3807a34248e· 4-28 -
topaz.stdlib.contract.typeset-knuth-plass-policyatworking-tree
Validate Knuth Plass policy before choosing a cost model
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: -1, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidPolicy(_)) => io.writeLine("InvalidPolicy")case _ => io.writeLine("unexpected result")}
InvalidPolicy
Expected result
Expected result
Execution completes. Exit code 0.
InvalidPolicy
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-51 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 32-35 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 46-48 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
f3807a34248e· 4-28 -
topaz.stdlib.contract.typeset-knuth-plass-policyatworking-tree
Report a line with no capacity to reach its target
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 9pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.KnuthPlass(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(NoGreedyPlan()) => io.writeLine("NoGreedyPlan")case _ => io.writeLine("unexpected result")}
NoGreedyPlan
Expected result
Expected result
Execution completes. Exit code 0.
NoGreedyPlan
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-51 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 32-35 - compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
f3807a34248e· 46-48 - compiler/crates/topaz_resolve/src/std/typeset/wide.tpz at
f3807a34248e· 4-28 -
topaz.stdlib.contract.typeset-knuth-plass-policyatworking-tree
Preserve measured units and validate their physical extents
LinkPreserve measured units and validate their physical extents
Item.BoxItem, Item.GlueItem, and Item.PenaltyItem preserve their record payloads. Constructing these records and variants does not plan a paragraph or validate its measurements.
BoxItem and GlueItem contribute one measured unit each in their encounter order. Their unitIndex fields must be exactly zero through the unit count minus one. PenaltyItem contributes a boundary without consuming a unit index.
Box.text and Glue.text retain the supplied string, including empty text and multiple Unicode scalars. A measured unit remains indivisible. Unit indices count these records rather than bytes, scalars, or grapheme clusters.
Box.width and Glue.width include trackingAfter. Width and width minus trackingAfter must both be nonnegative. Tracking may be positive, zero, or negative while those two conditions hold.
Each width, tracking amount, stretch, and shrink is a Length<Pt>. Paragraph planning quantizes it through the selected grid. A line span sums its unit widths and removes the final unit's trackingAfter.
Glue.stretch and Glue.shrink are nonnegative adjustment capacities. A box supplies zero capacity. The selected cost and justification policies determine how capacities participate in planning.
Positive capacity does not itself insert text or change the input records. Unjustified planning performs no distributed adjustment. Text trimming and model-specific glue treatment follow the PlanLine and paragraph contracts.
breakParagraph returns InvalidInput for a noncontiguous unitIndex, a negative width or capacity, or a negative width before tracking. Validation applies even when a later candidate would discard that unit.
The function uses the supplied measurements without shaping the text again. It does not reorder or mutate the caller's item array or its records.
Why
Measured text already has a source order and physical advances. Preserving those units keeps line breaking compatible with shaping. Explicit tracking and capacities give every planner the same measured input.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 16 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 24 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 52 -
topaz.stdlib.contract.typeset-measured-itemsatworking-tree
Keep measured units and signed tracking in source order
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.PenaltyItem(ts.Penalty { unitEnd: 3, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false }),ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "AB", width: 3pt, trackingAfter: 1pt }),ts.Item.GlueItem(ts.Glue { unitIndex: 1, text: " ", width: 2pt, trackingAfter: 0.5pt, stretch: 1pt, shrink: 1pt }),ts.Item.BoxItem(ts.Box { unitIndex: 2, text: "C", width: 4pt, trackingAfter: -1pt })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Ok(result) => {let line = result.optimized.lines[0]io.writeLine("{line.start}:{line.endExclusive}:{line.displayTextScalarLength}")io.writeLine("{line.rawTextWidth == 10pt}:{line.trimmedTextWidth == 10pt}")io.writeLine("{items.length}")match (items[0]) {case PenaltyItem(_) => io.writeLine("penalty first")case _ => io.writeLine("changed input")}}case Err(_) => io.writeLine("unexpected error")}
0:3:4 true:true 4 penalty first
Expected result
Expected result
Execution completes. Exit code 0.
0:3:4true:true4penalty first
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 16 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 24 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 52 -
topaz.stdlib.contract.typeset-measured-itemsatworking-tree
Keep a zero width unit with empty display text
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "", width: 0pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 1pt, firstTarget: 1pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Ok(result) => {let line = result.optimized.lines[0]io.writeLine("{line.endExclusive}:{line.displayTextScalarLength}:{line.rawTextWidth == 0pt}")}case Err(_) => io.writeLine("unexpected error")}
1:0:true
Expected result
Expected result
Execution completes. Exit code 0.
1:0:true
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 16 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 24 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 52 -
topaz.stdlib.contract.typeset-measured-itemsatworking-tree
Reject a gap in measured unit indices
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 1, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidInput(_)) => io.writeLine("InvalidInput")case _ => io.writeLine("unexpected result")}
InvalidInput
Expected result
Expected result
Execution completes. Exit code 0.
InvalidInput
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 16 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 24 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 52 -
topaz.stdlib.contract.typeset-measured-itemsatworking-tree
Reject negative glue stretch and shrink
Linkimport std.typeset as tsimport std.iofunction report(items: Array<ts.Item>) -> () {let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidInput(_)) => io.writeLine("InvalidInput")case _ => io.writeLine("unexpected result")}}report([ts.Item.GlueItem(ts.Glue { unitIndex: 0, text: " ", width: 1pt, trackingAfter: 0pt, stretch: -1pt, shrink: 0pt }), ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })])report([ts.Item.GlueItem(ts.Glue { unitIndex: 0, text: " ", width: 1pt, trackingAfter: 0pt, stretch: 0pt, shrink: -1pt }), ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })])
InvalidInput InvalidInput
Expected result
Expected result
Execution completes. Exit code 0.
InvalidInputInvalidInput
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 16 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 24 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 52 -
topaz.stdlib.contract.typeset-measured-itemsatworking-tree
Reject negative widths and negative extents before tracking
Linkimport std.typeset as tsimport std.iofunction report(items: Array<ts.Item>) -> () {let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidInput(_)) => io.writeLine("InvalidInput")case _ => io.writeLine("unexpected result")}}report([ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: -1pt, trackingAfter: 0pt }), ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })])report([ts.Item.GlueItem(ts.Glue { unitIndex: 0, text: " ", width: -1pt, trackingAfter: 0pt, stretch: 0pt, shrink: 0pt }), ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })])report([ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 2pt }), ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })])report([ts.Item.GlueItem(ts.Glue { unitIndex: 0, text: " ", width: 1pt, trackingAfter: 2pt, stretch: 0pt, shrink: 0pt }), ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })])
InvalidInput InvalidInput InvalidInput InvalidInput
Expected result
Expected result
Execution completes. Exit code 0.
InvalidInputInvalidInputInvalidInputInvalidInput
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 16 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 24 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 52 -
topaz.stdlib.contract.typeset-measured-itemsatworking-tree
Apply penalties at measured unit boundaries
LinkApply penalties at measured unit boundaries
Penalty.unitEnd is the exclusive end of a measured unit span. It must be greater than zero and no greater than the paragraph unit count. The penalty's position in the Item array does not set that boundary.
Planning collects penalties and visits them in increasing unitEnd order. Equal endpoints retain input order. Duplicate endpoints remain separate candidates and are counted separately in breakOpportunityCount.
Penalty.rule determines whether a candidate is selectable and how its additional cost is interpreted. Forbidden removes that candidate. A selectable duplicate at the same endpoint remains available. A Forced entry prevents any line from crossing that boundary.
Penalty.kind describes the selected boundary independently of its rule. For example a Forced rule can carry a LatinHyphen kind. The chosen line reports the selected candidate's kind.
Penalty.width is a nonnegative Length<Pt> that contributes when that candidate ends a line. Both cost models include this width for every kind. Unselected candidates contribute no width.
PlanLine.selectedPenaltyWidth reports that selected width separately from the measured text widths. Input penalty widths are validated even for Forbidden candidates.
Penalty.flagged marks a break for KnuthPlassPolicy.flaggedDemerit and finalFlaggedDemerit. FixedPoint does not use this flag. Its consecutive soft hyphen rule depends on kind.
An out-of-range unitEnd or negative penalty width returns InvalidInput from breakParagraph. Record and Item construction preserve the supplied data until that call validates it.
A complete plan needs a selectable terminal candidate at the unit count. Paragraph planning does not synthesize a terminal penalty or invoke break classification on the measured items.
Why
A boundary candidate separates admissibility, category, visible width, and cost history. The same selected width has one meaning in either cost model. Keeping duplicate candidates distinct permits explicit alternatives without changing source unit indices.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 20 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 69 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
v5.21.3· 1 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
v5.21.3· 12 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
v5.21.3· 1 -
topaz.stdlib.contract.typeset-penaltiesatworking-tree
Include a selected nonsoft penalty width with fixed costs
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 4pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 1pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.LatinHyphen(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 5pt, firstTarget: 5pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Ok(result) => {let line = result.optimized.lines[0]io.writeLine("{line.selectedPenaltyWidth == 1pt}:{line.costTextWidth == 4pt}:{line.cost}")}case Err(_) => io.writeLine("unexpected error")}
true:true:350000000
Expected result
Expected result
Execution completes. Exit code 0.
true:true:350000000
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 20 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 69 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
v5.21.3· 1 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
v5.21.3· 12 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
v5.21.3· 1 -
topaz.stdlib.contract.typeset-penaltiesatworking-tree
Include a selected nonsoft penalty width with knuth costs
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 4pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 1pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.LatinHyphen(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 5pt, firstTarget: 5pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.KnuthPlass(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Ok(result) => {let line = result.optimized.lines[0]io.writeLine("{line.selectedPenaltyWidth == 1pt}:{line.costTextWidth == 4pt}:{line.cost}")}case Err(_) => io.writeLine("unexpected error")}
true:true:100
Expected result
Expected result
Execution completes. Exit code 0.
true:true:100
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 20 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 69 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
v5.21.3· 1 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
v5.21.3· 12 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
v5.21.3· 1 -
topaz.stdlib.contract.typeset-penaltiesatworking-tree
Reject boundaries outside the measured units
Linkimport std.typeset as tsimport std.iofunction report(items: Array<ts.Item>) -> () {let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidInput(_)) => io.writeLine("InvalidInput")case _ => io.writeLine("unexpected result")}}report([ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 0pt }), ts.Item.PenaltyItem(ts.Penalty { unitEnd: 0, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })])report([ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 0pt }), ts.Item.PenaltyItem(ts.Penalty { unitEnd: 2, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })])
InvalidInput InvalidInput
Expected result
Expected result
Execution completes. Exit code 0.
InvalidInputInvalidInput
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 20 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 69 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
v5.21.3· 1 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
v5.21.3· 12 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
v5.21.3· 1 -
topaz.stdlib.contract.typeset-penaltiesatworking-tree
Reject a negative boundary width
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: -1pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidInput(_)) => io.writeLine("InvalidInput")case _ => io.writeLine("unexpected result")}
InvalidInput
Expected result
Expected result
Execution completes. Exit code 0.
InvalidInput
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 20 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 69 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
v5.21.3· 1 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
v5.21.3· 12 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
v5.21.3· 1 -
topaz.stdlib.contract.typeset-penaltiesatworking-tree
Distinguish invalid data from unavailable plans
LinkDistinguish invalid data from unavailable plans
TypesetError values are returned in Err by the typesetting operations that declare them. InvalidInput carries explanatory text for invalid measured data or boundary structure. InvalidPolicy carries explanatory text for an invalid algorithm configuration.
The string payload describes a cause. Programs distinguish failure categories by matching the variant rather than comparing library message text. Constructing an error value directly preserves its supplied string.
NoBreakOpportunities means a nonempty paragraph has no selectable penalty candidate after validation and filtering. It does not mean that the selected cost model searched unsuccessfully.
NoGreedyPlan means a validated paragraph has selectable candidates but its deterministic greedy baseline cannot reach the final unit. NoPlan means that baseline completed but the selected optimization search found no permitted complete plan.
A successful empty paragraph has two empty plans and zero candidates under the paragraph contract. It is not a missing-opportunity failure.
breakParagraph validates policy configuration before measured items. It then checks candidates, builds the greedy plan, and searches for an optimized plan in that order. The first failing stage determines the returned variant.
The policy stages check geometry, the cost model and grid combination, justification settings, and KnuthPlass settings. Item validation follows source encounter order and checks collected penalty endpoints after the measured units.
classifyBreaks applies its input and break-policy validation rules. The shared error variants do not impose paragraph validation order on break classification.
An Err contains no partial ParagraphResult and does not mutate the supplied input. Previously completed argument effects remain completed. A failure while evaluating an argument keeps its ordinary language diagnostic and prevents the typesetting call.
Why
Applications can repair malformed data, choose another policy, or report the absence of a plan when these outcomes stay distinct. Named variants provide that decision without relying on diagnostic wording or silently substituting a different algorithm.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 6 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
v5.21.3· 1 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
v5.21.3· 1 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
v5.21.3· 87 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
v5.21.3· 1 -
topaz.stdlib.contract.typeset-errorsatworking-tree
Preserve explanatory error payloads
Linkimport std.typeset as tsimport std.iolet failures: Array<ts.TypesetError> = [ts.TypesetError.InvalidInput("measured unit"),ts.TypesetError.InvalidPolicy("line target")]for failure in (failures) {match (failure) {case InvalidInput(message) => io.writeLine("input {message}")case InvalidPolicy(message) => io.writeLine("policy {message}")case _ => io.writeLine("unexpected variant")}}
input measured unit policy line target
Expected result
Expected result
Execution completes. Exit code 0.
input measured unitpolicy line target
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 6 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
v5.21.3· 1 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
v5.21.3· 1 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
v5.21.3· 87 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
v5.21.3· 1 -
topaz.stdlib.contract.typeset-errorsatworking-tree
Report an invalid paragraph policy before an invalid unit index
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 1, text: "a", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 0pt, firstTarget: 0pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidPolicy(_)) => io.writeLine("InvalidPolicy")case _ => io.writeLine("unexpected result")}
InvalidPolicy
Expected result
Expected result
Execution completes. Exit code 0.
InvalidPolicy
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/model.tpz at
v5.21.3· 6 - compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
v5.21.3· 1 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
v5.21.3· 27 - compiler/crates/topaz_resolve/src/std/typeset/greedy.tpz at
v5.21.3· 1 - compiler/crates/topaz_resolve/src/std/typeset/paragraph.tpz at
v5.21.3· 87 - compiler/crates/topaz_resolve/src/std/typeset/breaks.tpz at
v5.21.3· 1 -
topaz.stdlib.contract.typeset-errorsatworking-tree
Score justification with explicit policy precedence
LinkScore justification with explicit policy precedence
JustificationPolicy describes how FixedPoint scores a measured line. It does not change text, insert glyphs, or create break opportunities. Constructing the record does not run validation. breakParagraph validates it before measuring items.
minGapCount, minLineWidthRatioM, maxGapRatioR, and a present minFinalLineWidthRatioM must be nonnegative. maxAdjustment and maxGapAdjustment must be nonnegative point lengths. cjkStretchRatio must be finite and nonnegative. Violations return TypesetError.InvalidPolicy with an explanatory string.
The width ratio fields use 1000 for one whole target width. maxGapRatioR uses 100000000 for a ratio of one. These ratios have no additional upper bound. A threshold above the attainable width can increase cost without making the policy malformed.
A present LatinSpacing value follows its typed length contract. minWordSpaceRatio ranges from 0.8 through 1.0. maxWordSpaceRatio ranges from 1.0 through 1.33. maxLetterSpacingEm ranges from 0em through 0.015em and fontSizePt is positive. Both float ratios must be finite. Invalid values return TypesetError.InvalidPolicy even when the selected model does not use their capacities.
Unjustified contributes zero justification cost and supplies no inferred spacing capacity. LatinWordSpace scores eligible word spaces. CjkInterCharacter also recognizes eligible boundaries between single CJK units. All policy fields are validated in every mode.
KnuthPlass computes its adjustment ratio from the supplied Glue stretch and shrink values. JustificationPolicy does not alter that ratio or its demerits. The policy still undergoes validation. The KnuthPlass policy defines tolerance and line costs.
For FixedPoint, a present LatinSpacing value takes precedence when the trimmed line contains Latin letter units without other alphabetic scripts, or contains a recognized single CJK unit. The inferred capacity replaces the fallback minimum gap count, minimum nonfinal width, total adjustment, per gap adjustment, and gap ratio tests for that line.
Inferred shrink capacity is the floor of the total U+0020 unit width multiplied by one minus minWordSpaceRatio. Stretch capacity adds three separately evaluated contributions. They are the floor of that space width multiplied by maxWordSpaceRatio minus one, the eligible Latin letter gap count multiplied by the resolved typed letter maximum, and the floor of the eligible CJK width multiplied by cjkStretchRatio. The CJK contribution is zero in LatinWordSpace mode.
An inferred Latin letter unit contains an Alphabetic scalar and has every scalar in U+0041 through U+024F, U+0300 through U+036F, or U+1E00 through U+1EFF. A letter gap joins two adjacent such units. A CJK capacity contribution uses the left width of adjacent single CJK units. Resolve the typed letter maximum with the explicit font size before grid conversion. Preserve each independent floor for dimensionless word and CJK ratios.
Without an inferred capacity, word gaps are units whose complete text is U+0020. CJK gaps join adjacent recognized single CJK units and count both sides of an intervening U+0020 or U+00A0 unit. Recognized CJK scalars are U+1100 through U+11FF, U+3130 through U+318F, U+3400 through U+4DBF, U+4E00 through U+9FFF, U+AC00 through U+D7A3, and U+F900 through U+FAFF. Punctuation does not provide a CJK gap.
The fallback nonfinal calculation first scores a line below minLineWidthRatioM. It then checks the total positive adjustment against maxAdjustment. LatinWordSpace uses minGapCount and maxGapAdjustment on word gaps. CjkInterCharacter uses word gaps when present and otherwise uses CJK gaps, minGapCount, maxGapAdjustment, and maxGapRatioR. Falling short raises the justification cost rather than returning an input error.
FixedPoint calculations use the millipoint grid. A total positive adjustment of at most one millipoint has zero fallback cost. For a larger adjustment, maxAdjustment is the exact total bound. Per gap checks tolerate one millipoint per gap. The CJK ratio comparison tolerates 100000 units of maxGapRatioR. These allowances do not add spacing to the returned text.
For a final FixedPoint line in a justified mode, None() in minFinalLineWidthRatioM contributes zero justification cost. Some supplies a minimum final width ratio and applies to that final line. It never replaces the nonfinal checks. Compare the attainable width after the permitted positive adjustment with the target times the ratio divided by 1000, rounded halfway upward.
For that final threshold, attainable width adds inferred stretch when available. Otherwise it adds the smaller of maxAdjustment and the word gap count times maxGapAdjustment. Meeting the threshold contributes zero. A shortfall contributes 25000000000 plus the halfway upward rounded shortfall times 1000000 divided by the target, multiplied by 1000000.
The optimized FixedPoint planner can try a pass that requires bounded fill before its ordinary pass. The paragraph plan reports whether that pass succeeded. A returned plan does not distribute the requested adjustment into the original units. Consumers use the reported widths and the selected policy when rendering.
When the exact nonfinal minimum width comparison fails, the scoring shortfall is target minus natural width, with a minimum of zero. Scale that shortfall by 1000000, divide by target with halfway upward rounding, then multiply by 1000000 for LatinWordSpace or 100000 for CjkInterCharacter. Add 25000000000 to this nonnegative contribution. These operations use checked arithmetic.
For every FixedPoint justification comparison, natural width is the trimmed text width plus selectedPenaltyWidth. The target remains PlanLine.target. A selected insertion supplies no word gap, CJK gap, letter gap, stretch, or shrink capacity.
Why
A caller needs to know which spacing controls determine a line cost. Explicit capacity precedence keeps the two cost models predictable. A distinct final line threshold gives its name one meaning and preserves ordinary nonfinal checks.
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-37 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
f3807a34248e· 1-110 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 1-115 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 12-30 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-52 -
topaz.stdlib.contract.typeset-justificationatworking-tree
Choose a justification mode explicitly
Linkimport std.typeset as tsimport std.iofunction name(mode: ts.JustificationMode) -> string {match (mode) {case Unjustified() => "unjustified"case LatinWordSpace() => "latin"case CjkInterCharacter() => "cjk"}}io.writeLine(name(ts.JustificationMode.Unjustified()))io.writeLine(name(ts.JustificationMode.LatinWordSpace()))io.writeLine(name(ts.JustificationMode.CjkInterCharacter()))
unjustified latin cjk
Expected result
Expected result
Execution completes. Exit code 0.
unjustifiedlatincjk
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-37 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
f3807a34248e· 1-110 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 1-115 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 12-30 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-52 -
topaz.stdlib.contract.typeset-justificationatworking-tree
Reject a negative gap count even in Unjustified mode
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "word", width: 10pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: -1,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidPolicy(_)) => io.writeLine("InvalidPolicy")case _ => io.writeLine("unexpected result")}
InvalidPolicy
Expected result
Expected result
Execution completes. Exit code 0.
InvalidPolicy
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-37 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
f3807a34248e· 1-110 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 1-115 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 12-30 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-52 -
topaz.stdlib.contract.typeset-justificationatworking-tree
Reject a negative physical adjustment cap
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "word", width: 10pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: -1pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidPolicy(_)) => io.writeLine("InvalidPolicy")case _ => io.writeLine("unexpected result")}
InvalidPolicy
Expected result
Expected result
Execution completes. Exit code 0.
InvalidPolicy
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-37 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
f3807a34248e· 1-110 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 1-115 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 12-30 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-52 -
topaz.stdlib.contract.typeset-justificationatworking-tree
Reject a negative final line ratio
Linkimport std.typeset as tsimport std.iolet items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "word", width: 10pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: Some(-1),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}match (ts.breakParagraph(input)) {case Err(InvalidPolicy(_)) => io.writeLine("InvalidPolicy")case _ => io.writeLine("unexpected result")}
InvalidPolicy
Expected result
Expected result
Execution completes. Exit code 0.
InvalidPolicy
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-37 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
f3807a34248e· 1-110 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 1-115 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 12-30 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-52 -
topaz.stdlib.contract.typeset-justificationatworking-tree
Score an underfilled nonfinal line without changing measured text
Linkimport std.typeset as tsimport std.ioimport std.testfunction sample(justification: ts.JustificationPolicy) -> ts.ParagraphResult {let items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "word", width: 4pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false }),ts.Item.BoxItem(ts.Box { unitIndex: 1, text: "next", width: 4pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 2, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: justification,costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}test.assertOk(ts.breakParagraph(input))}let natural = sample(ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0})let justified = sample(ts.JustificationPolicy {mode: ts.JustificationMode.LatinWordSpace(), minGapCount: 1,minLineWidthRatioM: 900, minFinalLineWidthRatioM: None(),maxAdjustment: 2pt, maxGapAdjustment: 1pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0})io.writeLine("{justified.optimized.lines.length}")io.writeLine("{justified.optimized.lines[0].cost > natural.optimized.lines[0].cost}")io.writeLine("{justified.optimized.lines[1].cost == natural.optimized.lines[1].cost}")io.writeLine("{justified.optimized.lines[0].adjustmentRatioR}")
2 true true 0
Expected result
Expected result
Execution completes. Exit code 0.
2truetrue0
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-37 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
f3807a34248e· 1-110 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 1-115 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 12-30 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-52 -
topaz.stdlib.contract.typeset-justificationatworking-tree
Apply the final line threshold to the final line
Linkimport std.typeset as tsimport std.ioimport std.testfunction sample(justification: ts.JustificationPolicy) -> ts.ParagraphResult {let items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "word", width: 10pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 20pt, firstTarget: 20pt, dropCapSpan: 0, dropCapInset: 0pt },justification: justification,costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}test.assertOk(ts.breakParagraph(input))}let unconstrained = sample(ts.JustificationPolicy {mode: ts.JustificationMode.LatinWordSpace(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0})let constrained = sample(ts.JustificationPolicy {mode: ts.JustificationMode.LatinWordSpace(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: Some(1000),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0})io.writeLine("{constrained.optimized.lines[0].cost > unconstrained.optimized.lines[0].cost}")
true
Expected result
Expected result
Execution completes. Exit code 0.
true
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-37 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
f3807a34248e· 1-110 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 1-115 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 12-30 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-52 -
topaz.stdlib.contract.typeset-justificationatworking-tree
Keep the final line threshold out of nonfinal scoring
Linkimport std.typeset as tsimport std.ioimport std.testfunction sample(justification: ts.JustificationPolicy) -> ts.ParagraphResult {let items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "word", width: 4pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false }),ts.Item.BoxItem(ts.Box { unitIndex: 1, text: "next", width: 4pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 2, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: justification,costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}test.assertOk(ts.breakParagraph(input))}let ordinary = sample(ts.JustificationPolicy {mode: ts.JustificationMode.LatinWordSpace(), minGapCount: 1,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0})let finalZero = sample(ts.JustificationPolicy {mode: ts.JustificationMode.LatinWordSpace(), minGapCount: 1,minLineWidthRatioM: 0, minFinalLineWidthRatioM: Some(0),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0})io.writeLine("{ordinary.optimized.lines[0].cost == finalZero.optimized.lines[0].cost}")
true
Expected result
Expected result
Execution completes. Exit code 0.
true
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-37 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
f3807a34248e· 1-110 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 1-115 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 12-30 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-52 -
topaz.stdlib.contract.typeset-justificationatworking-tree
Use explicit glue capacities for the KnuthPlass model
Linkimport std.typeset as tsimport std.ioimport std.testfunction sample(justification: ts.JustificationPolicy) -> ts.ParagraphResult {let items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "word", width: 10pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 10pt, firstTarget: 10pt, dropCapSpan: 0, dropCapInset: 0pt },justification: justification,costModel: ts.CostModel.KnuthPlass(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}test.assertOk(ts.breakParagraph(input))}let natural = sample(ts.JustificationPolicy {mode: ts.JustificationMode.Unjustified(), minGapCount: 0,minLineWidthRatioM: 0, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0})let scored = sample(ts.JustificationPolicy {mode: ts.JustificationMode.CjkInterCharacter(), minGapCount: 2,minLineWidthRatioM: 900, minFinalLineWidthRatioM: Some(1000),maxAdjustment: 3pt, maxGapAdjustment: 1pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.2})io.writeLine("{natural.optimized.totalCost}")io.writeLine("{scored.optimized.totalCost}")io.writeLine("{scored.optimized.lines[0].adjustmentRatioR}")
100 100 0
Expected result
Expected result
Execution completes. Exit code 0.
1001000
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-37 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
f3807a34248e· 1-110 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 1-115 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 12-30 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-52 -
topaz.stdlib.contract.typeset-justificationatworking-tree
Raise the score when an overwide unit misses a larger minimum
Linkimport std.typeset as tsimport std.ioimport std.testfunction sample(ratio: int) -> ts.ParagraphResult {let items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "wide", width: 1.5pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false }),ts.Item.BoxItem(ts.Box { unitIndex: 1, text: "end", width: 1pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 2, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 1pt, firstTarget: 1pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.LatinWordSpace(), minGapCount: 0,minLineWidthRatioM: ratio, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}test.assertOk(ts.breakParagraph(input))}let ordinary = sample(0)let thresholded = sample(2000)io.writeLine("{thresholded.optimized.lines[0].cost > ordinary.optimized.lines[0].cost}")
true
Expected result
Expected result
Execution completes. Exit code 0.
true
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-37 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
f3807a34248e· 1-110 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 1-115 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 12-30 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-52 -
topaz.stdlib.contract.typeset-justificationatworking-tree
Include an inserted width in justification without adding gaps
Linkimport std.typeset as tsimport std.ioimport std.testfunction sample(textWidth: Length<Pt>, insertionWidth: Length<Pt>) -> ts.ParagraphResult {let items: Array<ts.Item> = [ts.Item.BoxItem(ts.Box { unitIndex: 0, text: "a", width: textWidth, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 1, width: insertionWidth, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.LatinHyphen(), flagged: false }),ts.Item.BoxItem(ts.Box { unitIndex: 1, text: "tail", width: 5pt, trackingAfter: 0pt }),ts.Item.PenaltyItem(ts.Penalty { unitEnd: 2, width: 0pt, rule: ts.BreakRule.Forced(), kind: ts.BreakKind.ForcedEnd(), flagged: false })]let input = ts.Paragraph {grid: ts.DistanceGrid.MilliPoint(),items: items,geometry: ts.LineGeometry { bodyTarget: 5pt, firstTarget: 5pt, dropCapSpan: 0, dropCapInset: 0pt },justification: ts.JustificationPolicy {mode: ts.JustificationMode.LatinWordSpace(), minGapCount: 0,minLineWidthRatioM: 1000, minFinalLineWidthRatioM: None(),maxAdjustment: 0pt, maxGapAdjustment: 0pt, maxGapRatioR: 0,latinSpacing: None(), cjkStretchRatio: 0.0},costModel: ts.CostModel.FixedPoint(),knuthPlass: ts.KnuthPlassPolicy { toleranceR: 100000000, linePenalty: 10, fitnessDemerit: 0, flaggedDemerit: 0, finalFlaggedDemerit: 0 }}test.assertOk(ts.breakParagraph(input))}let inserted = sample(4pt, 1pt)let measured = sample(5pt, 0pt)io.writeLine("{inserted.optimized.lines[0].cost == measured.optimized.lines[0].cost}")
true
Expected result
Expected result
Execution completes. Exit code 0.
true
Source evidence
- compiler/crates/topaz_resolve/src/std/typeset/admission.tpz at
f3807a34248e· 1-37 - compiler/crates/topaz_resolve/src/std/typeset/spacing.tpz at
f3807a34248e· 1-110 - compiler/crates/topaz_resolve/src/std/typeset/measure.tpz at
f3807a34248e· 1-115 - compiler/crates/topaz_resolve/src/std/typeset/line.tpz at
f3807a34248e· 12-30 - compiler/crates/topaz_resolve/src/std/typeset/knuth_plass.tpz at
f3807a34248e· 1-52 -
topaz.stdlib.contract.typeset-justificationatworking-tree