COMPO · 24.03 · COUNTER-DIAGONAL / TENSION PROFILES

Crossing is geometry.
Tension is a vector.

24.03 назначает main и counter только явной декларацией, вычисляет точную геометрию пары осей и собирает owner-qualified tension profile как набор независимых descriptors. Здесь нет скрытого «лучшего угла», автоматического выбора оси или итогового score.

ModuleCompo 24.03
Rolesexplicit only
Crossingexact geometry
Tensionvector only
Metricsnone
NextSTOP

Role declaration first, interpretation later

24.00 supplies valid diagonal candidates. 24.03 only binds two of them to MAIN/COUNTER roles and describes the resulting pair.

00 / contract
24.00 axis candidates + explicit MAIN / COUNTER assignment → exact pair geometry → CounterDiagonalRelationDescriptor optional owner-qualified tension channels → DiagonalTensionProfile (VECTOR) NO auto main-axis selection NO auto counter-axis selection NO scalar tension score NO target fit NO candidate generator

One owner per semantic layer

Пара осей принадлежит 24.03, но сами оси, object orientation и mass distribution остаются у своих владельцев.

01 / ownership
24.00

Axis identity

Точки, направления, exact line identity.

24.03

Main / counter relation

Role assignment, crossing relation, angle, intersection, tension vector.

24.04

Target fit

Only downstream may decide whether a profile fits an explicit target.

Main and counter are declared roles

Ни угол, ни масса, ни hierarchy не выбирают роли автоматически.

02 / explicit roles
DiagonalAxisRoleAssignment {
  assignmentRef,
  scopeRef,
  snapshotRef,
  mainAxisRef,
  counterAxisRef,
  assignmentOwnerRef,
  sourceRef,
  provenance,
  status,
  mutationAllowed: false
}
MAINComposition role only.
COUNTERComposition role only.
NO AUTO PICKAngle / mass / rank cannot assign either role here.

Exact pair geometry

Мы вычисляем только то, что действительно следует из двух бесконечных прямых.

03 / relation math
u = d_main / ||d_main|| v = d_counter / ||d_counter|| cross(d_main, d_counter) = 0 → PARALLEL_DISTINCT → intersectionPoint = null → acuteCrossingAngle = 0 otherwise → INTERSECTING → exact intersectionPoint → acuteCrossingAngle = acos(|dot(u,v)|) → normalizedAngularSeparation = angle / (π/2)

How the geometry reads

Пояснительные схемы показывают различия, которые нельзя смешивать в один «диагональный score».

04 / visual explanation

Main × counter: exact crossing

Intersection point is a derived coordinate, not a focal-point claim.

acute angleintersection
MAINCOUNTERintersection

Counter ≠ perpendicular by definition

35°, 57° or 90° can all be valid. Desirability belongs to 24.04 target fit.

oblique counter90° is only one case
counterAxisRef is a role reference, not “the perpendicular line”.

Parallel distinct is still valid geometry

No crossing point exists; angular separation is exactly 0, which is valid data rather than N_A.

angle = 0°intersection = null
0 ≠ missing. A zero angle is a legitimate descriptor for distinct parallel lines.

Acute angle normalization

Normalization makes the descriptor dimensionless; it does not turn it into a quality score.

0° → 0.0045° → 0.5090° → 1.00
normalizedAngularSeparation ∈ [0,1] · descriptor ≠ vote

Tension profile stays a vector

Геометрия пары может соседствовать с дополнительными explicit channels, но 24.03 не сворачивает их в один scalar.

05 / vector semantics
DiagonalTensionChannelEvidence {
  roleAssignmentRef,
  channelRef,
  value: 0..1,
  channelOwnerRef,
  sourceRef,
  sourceOwnerRef,
  dependsOnRefs[],
  provenance,
  status
}

DiagonalTensionProfile {
  mainAxisRef,
  counterAxisRef,
  relationRef,
  acuteCrossingAngleRadians,
  normalizedAngularSeparation,
  intersectionPoint,
  channelResolutions[],
  scalarTension: null,
  qualityScore: null,
  targetFit: null
}
VISUAL MODEL

Independent channels

angle
0.62
channel:A
0.35
channel:B
0.81
No averaging here. No hidden equal weights. 24.04 may compare this vector with an explicit target.

Bounded explicit profile set

No Cartesian generation across all candidate pairs or all channels.

06 / bounded selection
24.00Explicit axis candidates.
ROLE REQUESTExplicit mainAxisRef + counterAxisRef.
PAIR GEOMETRYIntersection + acute angle.
CHANNEL VECTOROnly explicitly requested tension channels.
24.04Target fit, score and candidate generation stay downstream.
DiagonalTensionProfileSetPolicy {
  selectionMode: "EXPLICIT_ROLE_ASSIGNMENTS_ONLY",
  channelSelectionMode: "EXPLICIT_REQUESTED_CHANNELS_ONLY",
  maxProfiles: 128,
  maxChannelsPerProfile: 64,
  overflowMode: "N_A_WITHOUT_TRUNCATION",
  duplicateRolePairMode: "N_A_NO_WINNER",
  autoRoleSelection: false,
  autoTensionInference: false,
  autoScoring: false,
  autoCandidateGeneration: false
}

Immutable downstream attachment

24.00 seed remains unchanged.

07 / attachment
TensionProfileAttachment {
  diagonalCompositionSeedRef,
  tensionProfileSetRef,
  status,
  mutationAllowed: false
}
correction request ≠ mutation attachment ≠ overwrite foreign geometry remains foreign

Critical firewalls

Тension здесь описывается, но не оценивается.

08 / guardrails
Never infer

Main from size, hierarchy, mass, angle or dominant direction. Counter from perpendicularity. Tension from mass spread or alignment.

Preserve exact zeros

0° angle and channel value 0 are valid observations. They are not N_A.

Defer desirability

“Controlled”, “too weak”, “too strong”, “dynamic enough” require an explicit 24.04 target profile.

acute angle != quality normalized angular separation != MetricResult channel value != independent vote vector profile != scalar tension score counter diagonal != Topic25 diagonal flow template

CANON → LAB → DATA → IDEAS

Research hooks remain explicit and non-canonical until validated.

09 / hooks
IDEAS_REFS[]Perceived dynamism vs crossing angle; scene-type effects.
DATA_CAPTURE[]Role pair, angle, intersection, channels and lineage.
DEFERRED_SEMANTIC_INPUTS[]Desired tension band and style intent belong to 24.04.
HUMAN_FEEDBACK_HOOKS[]Main/counter role corrections and channel disputes.
CONFLICT_PRIORITY_ASSUMPTIONS[]Confidence never chooses a winner under conflict.
LAB_HOOKS[]Angle/tension psychophysics and explicit target calibration.

24.03 regression suite

Tests cover exact role lineage, intersection math, parallel-zero preservation, acute-angle normalization, channel conflicts, bounded selection, immutability and the 24.04 ownership firewall.

10 / deterministic tests
Tests not run yet.

DATA FOR LAYOUT ENGINE

Machine-readable contract for the Topic24 counter-diagonal layer.

11 / machine contract
{
  "module": "Compo 24.03",
  "name": "counter_diagonal_and_tension_profiles",
  "version": "1.0-canonical",
  "canonical_main_title": "Counter-diagonal and tension profiles",
  "topic": "24_ДИАГОНАЛЬНАЯ_КОМПОЗИЦИЯ",
  "scope": "EXPLICIT_MAIN_COUNTER_AXIS_ROLE_ASSIGNMENT_EXACT_PAIR_GEOMETRY_INTERSECTION_ACUTE_CROSSING_ANGLE_AND_OWNER_QUALIFIED_VECTOR_TENSION_PROFILE_DESCRIPTORS_ONLY_WITHOUT_TARGET_FIT_SCORING_OR_CANDIDATE_GENERATION",
  "main_topic_contract": {
    "topic_title": "Диагональная композиция",
    "topic_goal": "Описывает диагональную структуру всей сцены: main diagonal, counter-diagonal, проекции масс на ось и controlled diagonal tension.",
    "expected_output": "DiagonalCompositionDescriptor, main/counter axes, projection distribution",
    "planned_files": [
      "24.00 Diagonal axis candidates",
      "24.01 Object orientation vs diagonal",
      "24.02 Mass distribution along diagonal",
      "24.03 Counter-diagonal and tension profiles",
      "24.04 Scoring, candidates and tests"
    ]
  },
  "ownership": {
    "owner": "Compo24.03",
    "owns": [
      "DiagonalAxisRoleAssignment",
      "CounterDiagonalRelationClass taxonomy",
      "CounterDiagonalRelationDescriptor",
      "DiagonalTensionChannelEvidence adapter",
      "DiagonalTensionChannelResolution",
      "DiagonalTensionProfileRequest",
      "DiagonalTensionProfile",
      "DiagonalTensionProfileSetPolicy",
      "DiagonalTensionProfileSet",
      "TensionProfileAttachment",
      "explicit main/counter role declaration over exact 24.00 axis candidates",
      "exact main/counter line-pair intersection and acute crossing-angle descriptors",
      "owner-qualified normalized tension-channel vector resolution without scalar aggregation",
      "identity/status/provenance rules for Topic24 counter-diagonal/tension layer",
      "non-mutating correction request for role assignment / tension-channel evidence errors"
    ],
    "does_not_own": [
      "24.00 axis candidate identity or discovery — Compo24.00",
      "24.01 object-orientation relation — Compo24.01",
      "24.02 mass projection/distribution — Compo24.02",
      "automatic main/counter selection from angle, mass, hierarchy or appearance — prohibited here",
      "automatic tension inference from orientation or mass — prohibited here",
      "target tension desirability, MetricResult, final scoring or candidate generation — Compo24.04",
      "flow-template diagonal path matching — Topic25",
      "hierarchy / dominance / beautyScore / final-layout ranking",
      "foreign geometry/style/semantic mutation"
    ]
  },
  "consumes": [
    "exact 24.00 DiagonalAxisCandidateSet and DiagonalCompositionSeed lineage",
    "explicit mainAxisRef + counterAxisRef role assignment",
    "optional owner-qualified normalized tension-channel evidence",
    "optional foreign refs from 24.01/24.02 only as declared evidence lineage, never auto-interpreted"
  ],
  "provides": [
    "DiagonalAxisRoleAssignment",
    "CounterDiagonalRelationDescriptor",
    "DiagonalTensionChannelResolution[]",
    "DiagonalTensionProfile[]",
    "DiagonalTensionProfileSet",
    "TensionProfileAttachment"
  ],
  "owns_metrics": [],
  "independent_numeric_votes": 0,
  "geometry_math": {
    "unitDirection": "u=d/||d||",
    "lineRelation": "cross(d_main,d_counter)==0 ? PARALLEL_DISTINCT : INTERSECTING",
    "intersection": "p_main + t*d_main where t=cross(p_counter-p_main,d_counter)/cross(d_main,d_counter)",
    "acuteCrossingAngle": "acos(abs(dot(u_main,u_counter))) in [0,pi/2]",
    "normalizedAngularSeparation": "acuteCrossingAngle/(pi/2)",
    "zeroAngle": "valid for distinct parallel lines",
    "ninetyDegrees": "valid geometry, not automatically optimal"
  },
  "tension_profile_semantics": {
    "profile": "VECTOR_ONLY",
    "builtInGeometricChannels": [
      "acuteCrossingAngleRadians",
      "normalizedAngularSeparation"
    ],
    "ownerQualifiedChannels": "explicit values in [0,1] with exact channelRef and owner/source lineage",
    "scalarTension": null,
    "qualityScore": null,
    "targetFit": null,
    "implicitWeighting": false,
    "implicitEqualWeighting": false
  },
  "status_semantics": {
    "OK": "valid exact root lineage, explicit role assignment and resolved requested channels",
    "N_A": "missing axis, equivalent role conflict, missing/conflicting requested channel evidence or bounded-policy overflow; never numeric zero",
    "INVALID": "malformed/impossible record; never numeric zero"
  },
  "firewalls": [
    "main axis != more important object",
    "counter axis != weaker axis",
    "counter diagonal need not be perpendicular",
    "parallel distinct lines are valid geometry and have zero acute angle",
    "crossing angle != aesthetic quality",
    "normalizedAngularSeparation != score",
    "explicit channel value 0 is valid data",
    "tension profile != scalar tension score",
    "orientation alignment != tension unless an owner explicitly supplies a tension channel",
    "mass spread != tension unless an owner explicitly supplies a tension channel",
    "controlled tension is a downstream target-fit concept owned by 24.04",
    "N_A != 0",
    "INVALID != 0",
    "local != global"
  ],
  "visual_explanation": {
    "diagrams": [
      "main vs counter diagonal with exact crossing point",
      "counter diagonal need not be perpendicular",
      "parallel-distinct counter axis with no intersection",
      "acute crossing angle normalized from 0 to 1",
      "vector tension channels with no scalar aggregation",
      "24.00→24.03→24.04 ownership pipeline"
    ]
  },
  "topic24ProgressAfterThisModule": "4/5 local",
  "next_module": "Compo 24.04 — Scoring, candidates and tests",
  "hard_stop": "No 24.04 scoring/candidate generator implementation in this file"
}
VISITS / ...