chore(SNNBot): remove SNN graph overlay, keep aiming lines
Deleted neuron panel visualization (input layer, hidden layer neurons, weight lines, output channels) from drawOverlay. Retain aiming lines: enemy bearing (green), gun direction (red), SNN target (yellow). Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -249,104 +249,6 @@ proc drawOverlay(bot: SNNBot, myX, myY, gunDir, enemyBearing, targetAngle: float
|
|||||||
let (tx, ty) = toXY(targetAngle, LINE_LEN)
|
let (tx, ty) = toXY(targetAngle, LINE_LEN)
|
||||||
drawLine(myX, myY, tx, ty)
|
drawLine(myX, myY, tx, ty)
|
||||||
|
|
||||||
# ── Neuron panel — barcode style (top-left corner at 10,10) ──────────────
|
|
||||||
const
|
|
||||||
PX = 10.0 # panel x
|
|
||||||
PY = 10.0 # panel y
|
|
||||||
let
|
|
||||||
panelW = getArenaWidth().float / 2.0
|
|
||||||
panelH = getArenaHeight().float / 2.0
|
|
||||||
CH = (panelH - PY - 20.0) / 7.0 # row height
|
|
||||||
LAYER_V = CH * 2.0 # inter-layer gap
|
|
||||||
IN_W = panelW # input layer spans full panel width
|
|
||||||
IN_STEP = IN_W / float(N_IN) # spacing between input lines
|
|
||||||
HID_STEP = IN_W / float(N_HID) # spacing between hidden lines (scales with N_HID)
|
|
||||||
HID_OFF = 0.0
|
|
||||||
|
|
||||||
# Input layer: vertical line per neuron, visible when activation > 0
|
|
||||||
let inputs = encodeInput(normalizeRelativeAngle(enemyBearing - gunDir))
|
|
||||||
setStrokeWidth(1.0)
|
|
||||||
for i in 0 ..< N_IN:
|
|
||||||
let alpha = uint8(inputs[i] * 255.0)
|
|
||||||
if alpha > 0:
|
|
||||||
let lx = PX + (float(i) + 0.5) * IN_STEP
|
|
||||||
setStrokeColor(fromRgba(0, 200, 255, alpha))
|
|
||||||
drawLine(lx, PY, lx, PY + CH)
|
|
||||||
|
|
||||||
# Hidden layer: vertical line per neuron, visible when membrane > 0
|
|
||||||
let hidY = PY + CH + LAYER_V
|
|
||||||
setStrokeWidth(1.5)
|
|
||||||
for h in 0 ..< N_HID:
|
|
||||||
let v = bot.snn.vHid[h].clamp(0.0, THRESH) / THRESH
|
|
||||||
if v > 0.0:
|
|
||||||
let lx = PX + HID_OFF + (float(h) + 0.5) * HID_STEP
|
|
||||||
let alpha = uint8(v * 255.0)
|
|
||||||
setStrokeColor(fromRgba(255, 140, 0, alpha))
|
|
||||||
drawLine(lx, hidY, lx, hidY + CH)
|
|
||||||
|
|
||||||
# Weight lines: input → hidden
|
|
||||||
var maxAbsWih = 0.0
|
|
||||||
for w in bot.snn.wih: maxAbsWih = max(maxAbsWih, abs(w))
|
|
||||||
setStrokeColor(fromRgba(180, 220, 255, 180))
|
|
||||||
for i in 0 ..< N_IN:
|
|
||||||
let ix = PX + (float(i) + 0.5) * IN_STEP
|
|
||||||
let iy = PY + CH
|
|
||||||
for h in 0 ..< N_HID:
|
|
||||||
let hx = PX + HID_OFF + (float(h) + 0.5) * HID_STEP
|
|
||||||
let hy = hidY
|
|
||||||
let w = bot.snn.wih[i * N_HID + h]
|
|
||||||
let norm = if maxAbsWih > 0.0: abs(w) / maxAbsWih else: 0.0
|
|
||||||
setStrokeWidth(0.5 + norm * 2.5)
|
|
||||||
drawLine(ix, iy, hx, hy)
|
|
||||||
|
|
||||||
# Output: two small vertical lines for sin/cos channels side-by-side
|
|
||||||
let outY = hidY + CH + LAYER_V
|
|
||||||
var sinOut = 0.0; var cosOut = 0.0
|
|
||||||
for h in 0 ..< N_HID:
|
|
||||||
let rate = bot.lastSpikes[h] / float(N_INFER)
|
|
||||||
sinOut += rate * bot.snn.wSin[h]
|
|
||||||
cosOut += rate * bot.snn.wCos[h]
|
|
||||||
let sinV = (sinOut.clamp(-1.0, 1.0) + 1.0) / 2.0
|
|
||||||
let cosV = (cosOut.clamp(-1.0, 1.0) + 1.0) / 2.0
|
|
||||||
let cx = PX + IN_W / 2.0
|
|
||||||
setStrokeWidth(2.0)
|
|
||||||
if sinV > 0.0:
|
|
||||||
setStrokeColor(fromRgba(200, 0, 255, uint8(sinV * 255.0)))
|
|
||||||
drawLine(cx - 4.0, outY, cx - 4.0, outY + CH)
|
|
||||||
if cosV > 0.0:
|
|
||||||
setStrokeColor(fromRgba(0, 200, 100, uint8(cosV * 255.0)))
|
|
||||||
drawLine(cx + 4.0, outY, cx + 4.0, outY + CH)
|
|
||||||
|
|
||||||
# ── Aiming-line legend ────────────────────────────────────────────────────
|
|
||||||
const
|
|
||||||
LEG_X = 10.0
|
|
||||||
LEG_SQ = 8.0
|
|
||||||
LEG_GAP = 4.0
|
|
||||||
LEG_ROW = 14.0
|
|
||||||
LEG_PAD = 6.0
|
|
||||||
let LEG_Y = getArenaHeight().float - 60.0
|
|
||||||
|
|
||||||
setFillColor(fromRgba(0, 0, 0, 160))
|
|
||||||
fillRectangle(LEG_X - LEG_PAD,
|
|
||||||
LEG_Y - LEG_PAD,
|
|
||||||
LEG_SQ + LEG_GAP + 80.0 + LEG_PAD,
|
|
||||||
3.0 * LEG_ROW + LEG_PAD)
|
|
||||||
|
|
||||||
setFillColor(GREEN)
|
|
||||||
fillRectangle(LEG_X, LEG_Y, LEG_SQ, LEG_SQ)
|
|
||||||
setFillColor(WHITE)
|
|
||||||
drawText("Enemy bearing", LEG_X + LEG_SQ + LEG_GAP, LEG_Y + LEG_SQ)
|
|
||||||
|
|
||||||
setFillColor(RED)
|
|
||||||
fillRectangle(LEG_X, LEG_Y + LEG_ROW, LEG_SQ, LEG_SQ)
|
|
||||||
setFillColor(WHITE)
|
|
||||||
drawText("Gun direction", LEG_X + LEG_SQ + LEG_GAP, LEG_Y + LEG_ROW + LEG_SQ)
|
|
||||||
|
|
||||||
setFillColor(YELLOW)
|
|
||||||
fillRectangle(LEG_X, LEG_Y + 2.0 * LEG_ROW, LEG_SQ, LEG_SQ)
|
|
||||||
setFillColor(WHITE)
|
|
||||||
drawText("SNN target", LEG_X + LEG_SQ + LEG_GAP, LEG_Y + 2.0 * LEG_ROW + LEG_SQ)
|
|
||||||
|
|
||||||
# ── Event handlers ────────────────────────────────────────────────────────────
|
# ── Event handlers ────────────────────────────────────────────────────────────
|
||||||
|
|
||||||
method onScannedBot*(bot: SNNBot, e: ScannedBotEvent) =
|
method onScannedBot*(bot: SNNBot, e: ScannedBotEvent) =
|
||||||
|
|||||||
Reference in New Issue
Block a user