"""Owner-visible rear-bay electrical architecture, not a reconnection diagram."""
from pathlib import Path
import json
import cadquery as cq
OUT=Path(__file__).parent
S=json.loads((OUT.parent/'body-data.json').read_text())['published_reference_dimensions_mm']['wheelbase']/2.4
parts=[]
def V(p):return cq.Vector(*(v*S for v in p))
def box(w,h,d,p):return cq.Workplane('XY').box(w*S,h*S,d*S).translate(V(p).toTuple()).val()
def cyl(r,l,p,axis=(0,0,1)):return cq.Solid.makeCylinder(r*S,l*S,V(p),cq.Vector(*axis))
def ring(ro,ri,l,p):return cyl(ro,l,p).cut(cyl(ri,l+.002,[p[0],p[1],p[2]-.001]))
def tube(points,r):
 pts=[V(p) for p in points];path=cq.Wire.assembleEdges([cq.Edge.makeSpline(pts)])
 return cq.Workplane(cq.Plane(origin=pts[0],normal=pts[1]-pts[0])).circle(r*S).sweep(path,isFrenet=True).val()
def add(name,shape,color=(.15,.16,.14)):
 assert shape.isValid() and shape.Volume()>0,name
 parts.append((name,shape,color))
fx,fy,fz=-.53,.84,.15
base=box(.09,.13,.018,[fx,fy,fz]);clips=[];fuses=[];tails=[];rows=[]
for i in range(4):
 y=fy+(i-1.5)*.025;rows.append(y)
 for sign in [-1,1]:
  x=fx+sign*.025
  clips.extend([box(.009,.012,.006,[x,y,.17]),box(.018,.007,.002,[x+sign*.009,y,.163])])
  tails.append(tube([[x+sign*.018,y,.164],[x+sign*.033,y-.006,.18],[fx+sign*.065,y-.018,.19]],.0018))
 # Recognition envelopes only: no element, resistance or amperage is assigned.
 fuses.extend([cyl(.0037,.034,[fx-.017,y,.178],(1,0,0)),cyl(.0042,.005,[fx-.022,y,.178],(1,0,0)),cyl(.0042,.005,[fx+.017,y,.178],(1,0,0))])
for y in [fy-.056,fy+.056]:base=base.cut(cyl(.003,.022,[fx,y,fz-.011]))
add('bay_fusebox_base_and_contacts_reference',cq.Compound.makeCompound([base,*clips]))
add('bay_four_glass_fuse_envelopes_reference',cq.Compound.makeCompound(fuses),(.65,.67,.58))
add('bay_visible_fuse_wire_tails_reference',cq.Compound.makeCompound(tails),(.34,.28,.24))
upper=box(.07,.055,.04,[-.54,.98,.16]);flange=box(.09,.009,.006,[-.54,.954,.138])
add('bay_upper_unidentified_electrical_can_reference',cq.Compound.makeCompound([upper,flange]),(.55,.56,.51))
upper_tails=[]
for i in range(3):
 p=[-.56+i*.018,.952,.17]
 upper_tails.append(tube([p,[p[0]-.01,.925,.19],[p[0]+.015,.90,.21]],.0018))
add('bay_upper_can_local_wire_tails_reference',cq.Compound.makeCompound(upper_tails),(.38,.29,.24))
add('bay_lower_unidentified_electrical_can_reference',cq.Compound.makeCompound([cyl(.025,.035,[-.53,.735,.16]),ring(.028,.024,.004,[-.53,.735,.193])]),(.30,.31,.27))
trunk=[[-.595,.92,.175],[-.615,.86,.19],[-.61,.77,.21],[-.57,.72,.23],[-.50,.70,.30]]
add('bay_local_loom_loop_reference',tube(trunk,.008),(.13,.14,.12))
lug=[-.30,1.00,.145]
eye=ring(.012,.004,.003,lug);neck=box(.012,.024,.003,[-.30,.980,.1465]);bolt=cyl(.0035,.018,[-.30,1.00,.131]);head=cyl(.007,.005,[-.30,1.00,.149])
add('battery_observed_body_lug_and_bolt_reference',cq.Compound.makeCompound([eye,neck,bolt,head]),(.50,.44,.31))
grommet=[.28,.98,.13]
add('bay_observed_bulkhead_grommet_reference',ring(.015,.006,.006,[grommet[0],grommet[1],grommet[2]-.003]),(.10,.11,.10))
crossing=[[.28,.90,.22],[.28,.95,.18],[.28,.98,.16],[.28,.98,.13],[.28,.98,.09]]
add('bay_observed_bulkhead_line_segment_reference',tube(crossing,.0025),(.35,.23,.18))
assembly=cq.Assembly(name='owner_visible_bay_electrical_reference');meshes=[]
for name,shape,color in parts:
 assembly.add(shape,name=name,color=cq.Color(*color));vs,ts=shape.tessellate(.6,.2)
 meshes.append(dict(name=name,color=color,vertices=[round(v,4) for p in vs for v in p.toTuple()],triangles=[i for tri in ts for i in tri]))
assembly.export(str(OUT/'bay-electrical-reference.step'))
limits='All body coordinates, sizes, routes, mounting holes, wire diameters, tail counts, contact shapes and connector positions are estimates. Owner photo supports four visible fuse envelopes and local wiring appearance, not ratings, fuse duties, internal bus connections or a verified pinout. Upper/lower metal-can identities remain unknown. Battery body-bolt continuation is visually observed, but polarity, conductor specification and other cable destinations remain unverified. Loom and can/fuse tails stop openly; adjacent ends are not asserted joined. No continuity, ballast arrangement, live circuit, complete harness, compatible part selection, safe reconnection or verified removal path. The one body aperture and grommet are estimated registration only; the crossing line is not identified as an electrical conductor.'
meta=dict(units='mm',source_frame='Canonical body coordinates scaled by nominal wheelbase / 2.4.',factory_sources=['https://www.spridgets.de/downloads/Parts-1977.pdf#page=188','https://www.spridgets.de/downloads/Parts-1977.pdf#page=191','https://www.spridgets.de/downloads/Parts-1977.pdf#page=192'],owner_photos=['IMG_6901','IMG_6891','IMG_6856'],basis='IMG_6901 shows exposed four-fuse architecture, local wire bundles, metal-can surroundings, a yellow-covered battery lead continuing to a body bolt and an unidentified slender line/grommet crossing. Factory plates distinguish market/chassis harness variants, earth-cable and fusebox architecture; none identifies fitted wire duties or component numbers.',limits=limits,nodes_units=dict(body_lug=lug,bulkhead_grommet=grommet,wire_crossing=crossing,local_loom=trunk),parts=meshes)
(OUT/'bay-electrical-reference.json').write_text(json.dumps(meta,separators=(',',':'))+'\n')
restored=cq.importers.importStep(str(OUT/'bay-electrical-reference.step')).val();assert restored.isValid()
print(json.dumps(dict(groups=len(parts),step_valid=True,solids=len(restored.Solids()),visible_fuse_count=4,body_lug=lug,bulkhead_crossing=grommet)))
