Files
sanspie 5eb1832907
ci-platforms / darwin amd64 smoke (push) Skipped
ci / build (amd64, linux, ubuntu-24.04) (push) Failing after 15m28s
ci / release (push) Skipped
ci-platforms / windows amd64 smoke (push) Skipped
ci-platforms / darwin arm64 smoke (push) Skipped
ci / checks (push) Successful in 7m47s
Complete Stage 12 for v0.12.0
2026-11-05 11:46:53 +03:00

77 lines
2.4 KiB
Go

package agentbridge
import (
"bytes"
"crypto/sha256"
"encoding/json"
"errors"
"fmt"
"aego/app/agent"
"aego/app/agent/mcp"
)
type captureSetup struct {
Scene, Camera, View, Input string
Seed uint64
Tick, Width, Height, Scale int
}
type visualReceipt struct {
ID string
Generation uint64
Setup captureSetup
PNG []byte
}
func (b *Bridge) rememberShots(rep *agent.RunReport, gen uint64, scene string, req agent.RunRequest) {
for i := range rep.Shots {
s := &rep.Shots[i]
if len(s.PNG) == 0 || len(s.PNG) > 5<<20 {
continue
}
seed := req.Seed
if seed == 0 {
seed = 1
}
setup := captureSetup{scene, req.Camera, s.ViewSignature, req.Input, seed, s.Frame, s.Width, s.Height, req.ShotWidth}
salt, _ := json.Marshal(setup)
h := sha256.New()
h.Write(salt)
h.Write(s.PNG)
s.CaptureID = fmt.Sprintf("%x", h.Sum(nil))
if len(b.captures) >= 8 {
copy(b.captures, b.captures[1:])
b.captures = b.captures[:7]
}
b.captures = append(b.captures, visualReceipt{s.CaptureID, gen, setup, bytes.Clone(s.PNG)})
}
}
func (b *Bridge) compareTool() mcp.Tool {
str := map[string]any{"type": "string"}
return mcp.Tool{Name: "scene_compare_frames", Description: "See two PNGs from scene_run shots side by side in call order. Both captureIDs must come from this conversation, with the same scene, camera, tick, seed, input and sizing.", ReadOnly: true, Schema: visualSchema([]string{"before", "after"}, map[string]any{"before": str, "after": str}), Output: func(a map[string]any) (*agent.Output, error) {
var got [2]visualReceipt
gen := b.panelGeneration.Load()
if err := b.main(func() {
for i, key := range []string{"before", "after"} {
id, _ := a[key].(string)
for _, r := range b.captures {
if r.Generation == gen && r.ID == id {
got[i] = r
break
}
}
}
}); err != nil {
return nil, err
}
x, y := got[0], got[1]
if x.ID == "" || y.ID == "" {
return nil, errors.New("capture missing or expired; repeat scene_run with shot")
}
if x.Setup != y.Setup {
return nil, errors.New("capture settings differ; replay with matching scene, camera, tick, seed, input and scale")
}
return &agent.Output{OK: true, Value: map[string]any{"before": x.ID, "after": y.ID, "setup": x.Setup}, Images: []agent.Image{{Mime: "image/png", Data: x.PNG}, {Mime: "image/png", Data: y.PNG}}}, nil
}}
}