Initial nucleus array UI
This commit is contained in:
parent
4f2f230335
commit
394df2167d
@ -2,6 +2,7 @@ using System;
|
||||
using System.Collections.Generic;
|
||||
using UnityEngine;
|
||||
using Unity.Mathematics;
|
||||
using static Unity.Mathematics.math;
|
||||
|
||||
public class Receptor : IReceptor {
|
||||
[SerializeField]
|
||||
@ -11,10 +12,23 @@ public class Receptor : IReceptor {
|
||||
set => _name = value;
|
||||
}
|
||||
|
||||
class Receiver {
|
||||
public INucleus nucleus;
|
||||
public int thingId;
|
||||
public string thingName;
|
||||
public Receiver(INucleus nucleus, int thingId, string thingName) {
|
||||
this.nucleus = nucleus;
|
||||
this.thingId = thingId;
|
||||
this.thingName = thingName;
|
||||
}
|
||||
}
|
||||
|
||||
[SerializeReference]
|
||||
private List<INucleus> _receivers = new();
|
||||
public List<INucleus> receivers => _receivers;
|
||||
|
||||
protected int[] thingIds; // every receiver can handle a thing with this id
|
||||
|
||||
public virtual void AddReceiver(INucleus receivingNucleus) {
|
||||
this.receivers.Add(receivingNucleus);
|
||||
receivingNucleus.AddSynapse(this);
|
||||
@ -25,7 +39,6 @@ public class Receptor : IReceptor {
|
||||
receiverNucleus.synapses.RemoveAll(synapse => synapse.nucleus == this);
|
||||
}
|
||||
|
||||
//public bool isSleeping => false;
|
||||
private int stale = 1000;
|
||||
|
||||
private bool _isSleeping = false;
|
||||
@ -42,7 +55,6 @@ public class Receptor : IReceptor {
|
||||
public float distanceResolution = 0.1f;
|
||||
public float directionResolution = 5;
|
||||
|
||||
//public float3 outputValue => this.localPosition;
|
||||
private float3 _outputValue;
|
||||
public float3 outputValue {
|
||||
get { return this._outputValue; }
|
||||
@ -53,6 +65,11 @@ public class Receptor : IReceptor {
|
||||
}
|
||||
}
|
||||
|
||||
public Receptor(Cluster cluster) {
|
||||
if (cluster != null)
|
||||
cluster.nuclei.Add(this);
|
||||
}
|
||||
|
||||
public Receptor(Cluster cluster, INucleus nucleus) {
|
||||
if (cluster != null)
|
||||
cluster.nuclei.Add(this);
|
||||
@ -63,65 +80,67 @@ public class Receptor : IReceptor {
|
||||
if (cluster == null)
|
||||
return null;
|
||||
|
||||
Receptor receptor = new(cluster);
|
||||
foreach (INucleus nucleus in cluster.inputs) {
|
||||
if (nucleus != null && nucleus.name == nucleusName) {
|
||||
Receptor receptor = new(cluster, nucleus);
|
||||
return receptor;
|
||||
// Receptor receptor = new(cluster, nucleus);
|
||||
// return receptor;
|
||||
receptor.AddReceiver(nucleus);
|
||||
}
|
||||
}
|
||||
return null;
|
||||
if (receptor.receivers.Count == 0)
|
||||
return null;
|
||||
else
|
||||
return receptor;
|
||||
}
|
||||
|
||||
public virtual void ProcessStimulus(int thingId, Vector3 newLocalPositionVector, string thingName = null) {
|
||||
this.localPosition = newLocalPositionVector;
|
||||
|
||||
thingIds ??= new int[this.receivers.Count];
|
||||
|
||||
int receiverIx = 0;
|
||||
INucleus selectedReceiver = null;
|
||||
int selectedReceiverIx = 0;
|
||||
foreach (INucleus receiver in this.receivers) {
|
||||
selectedReceiver = receiver;
|
||||
// selectedReceiver = receiver;
|
||||
// receiverIx++;
|
||||
|
||||
if (thingIds[receiverIx] == thingId) {
|
||||
// We found an existing receiver for this thing
|
||||
selectedReceiver = receiver;
|
||||
selectedReceiverIx = receiverIx;
|
||||
// Do not look any further
|
||||
break;
|
||||
}
|
||||
else if (receiver.isSleeping) {
|
||||
// A sleeping receiver is not active and can therefore always be used
|
||||
selectedReceiver = receiver;
|
||||
selectedReceiverIx = receiverIx;
|
||||
// Look further because we may find an existing receiver for this thing
|
||||
}
|
||||
else if (selectedReceiver == null) {
|
||||
// If we haven't found a receiver yet, just start by taking the first
|
||||
selectedReceiver = receiver;
|
||||
selectedReceiverIx = receiverIx;
|
||||
}
|
||||
else if (selectedReceiver.isSleeping == false) {
|
||||
// If no existing or sleeping receiver is found, we look for
|
||||
// the receiver with the furthest/least interesting stimulus
|
||||
if (length(receiver.outputValue) < length(selectedReceiver.outputValue)) {
|
||||
// Debug.Log($"{selectedReceiver.name}[{selectedReceiverIx}] {length(selectedReceiver.outputValue)}" +
|
||||
// $" {receiver.name}[{receiverIx}] {length(receiver.outputValue)} ");
|
||||
selectedReceiver = receiver;
|
||||
selectedReceiverIx = receiverIx;
|
||||
}
|
||||
}
|
||||
receiverIx++;
|
||||
}
|
||||
// selectedReceiver.thingId = thingId;
|
||||
// Debug.Log($"Receiver {selectedReceiver.name}[{selectedReceiverIx}] for thing {thingId}");
|
||||
thingIds[selectedReceiverIx] = thingId;
|
||||
// if (thingName != null)
|
||||
// selectedReceiver.nucleus.name = selectedReceiver.nucleus.baseName + " " + thingName;
|
||||
selectedReceiver.UpdateState();
|
||||
|
||||
// Perceptoid selectedPerceptoid = null;
|
||||
// foreach (Perceptoid perceptoid in this.perceptei) {
|
||||
// if (perceptoid.thingId == thingId) {
|
||||
// // We found an existing perceptoid for this thing
|
||||
// selectedPerceptoid = perceptoid;
|
||||
// // Do not look any further
|
||||
|
||||
// break;
|
||||
// }
|
||||
// else if (perceptoid.isSleeping) {
|
||||
// // A sleeping perceptoid is not active and can therefore always be reused
|
||||
// selectedPerceptoid = perceptoid;
|
||||
// // Look further because we could find a existing perceptoid for this thing
|
||||
// }
|
||||
|
||||
// else if (selectedPerceptoid == null) {
|
||||
// // If we haven't found a perceptoid yet, just start by taking the first
|
||||
// selectedPerceptoid = perceptoid;
|
||||
// }
|
||||
|
||||
// else if (selectedPerceptoid.isSleeping == false) {
|
||||
// // If no existing or sleeping perceptoid is found, we look for the perceptoid
|
||||
// // we the furthest (least interesting) stimulus
|
||||
// if (perceptoid.receptor.localPosition.magnitude < selectedPerceptoid.receptor.localPosition.magnitude) {
|
||||
// Debug.Log($"{selectedPerceptoid.name} {selectedPerceptoid.receptor.localPosition.magnitude} {perceptoid.receptor.localPosition.magnitude} ");
|
||||
// selectedPerceptoid = perceptoid;
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// if (selectedPerceptoid == null) {
|
||||
// Debug.Log("No perceptoid selected, stimulus is ignored");
|
||||
// return;
|
||||
// }
|
||||
// // Debug.Log($"Stimulus {thingType} {thingId} {selectedPerceptoid.name}");
|
||||
// selectedPerceptoid.thingId = thingId;
|
||||
// if (thingName != null)
|
||||
// selectedPerceptoid.name = selectedPerceptoid.baseName + " " + thingName;
|
||||
// selectedPerceptoid.UpdateState();
|
||||
}
|
||||
|
||||
public void UpdateNuclei() {
|
||||
|
||||
@ -78,11 +78,12 @@ public class ClusterInspector : Editor {
|
||||
GameObject gameObject;
|
||||
private List<NeuroidLayer> layers = new();
|
||||
private readonly Dictionary<IReceptor, Vector2Int> neuroidPositions = new();
|
||||
private bool expandArray = false;
|
||||
|
||||
Vector2 pan = Vector2.zero;
|
||||
//Vector2 pan = Vector2.zero;
|
||||
//float zoom = 1f;
|
||||
bool draggingCanvas = false;
|
||||
Vector2 lastMouse;
|
||||
//bool draggingCanvas = false;
|
||||
//Vector2 lastMouse;
|
||||
ClusterWrapper currentWrapper;
|
||||
|
||||
public GraphView() {
|
||||
@ -98,9 +99,9 @@ public class ClusterInspector : Editor {
|
||||
Add(imguiContainer);
|
||||
|
||||
//RegisterCallback<WheelEvent>(OnWheel);
|
||||
RegisterCallback<MouseDownEvent>(OnMouseDown);
|
||||
RegisterCallback<MouseMoveEvent>(OnMouseMove);
|
||||
RegisterCallback<MouseUpEvent>(OnMouseUp);
|
||||
// RegisterCallback<MouseDownEvent>(OnMouseDown);
|
||||
// RegisterCallback<MouseMoveEvent>(OnMouseMove);
|
||||
// RegisterCallback<MouseUpEvent>(OnMouseUp);
|
||||
}
|
||||
|
||||
public void SetGraph(GameObject gameObject, Cluster brain, INucleus nucleus, VisualElement inspectorContainer) {
|
||||
@ -181,19 +182,19 @@ public class ClusterInspector : Editor {
|
||||
|
||||
}
|
||||
|
||||
void OnMouseDown(MouseDownEvent e) {
|
||||
if (e.button == 2) { draggingCanvas = true; lastMouse = e.mousePosition; e.StopPropagation(); }
|
||||
}
|
||||
void OnMouseMove(MouseMoveEvent e) {
|
||||
if (draggingCanvas) {
|
||||
var delta = e.mousePosition - lastMouse;
|
||||
pan += delta;
|
||||
//content.style.left = pan.x;
|
||||
//content.style.top = pan.y;
|
||||
lastMouse = e.mousePosition;
|
||||
}
|
||||
}
|
||||
void OnMouseUp(MouseUpEvent e) { if (e.button == 2) draggingCanvas = false; }
|
||||
// void OnMouseDown(MouseDownEvent e) {
|
||||
// if (e.button == 2) { draggingCanvas = true; lastMouse = e.mousePosition; e.StopPropagation(); }
|
||||
// }
|
||||
// void OnMouseMove(MouseMoveEvent e) {
|
||||
// if (draggingCanvas) {
|
||||
// var delta = e.mousePosition - lastMouse;
|
||||
// pan += delta;
|
||||
// //content.style.left = pan.x;
|
||||
// //content.style.top = pan.y;
|
||||
// lastMouse = e.mousePosition;
|
||||
// }
|
||||
// }
|
||||
// void OnMouseUp(MouseUpEvent e) { if (e.button == 2) draggingCanvas = false; }
|
||||
|
||||
void OnIMGUI() {
|
||||
if (currentNucleus == null)
|
||||
@ -217,8 +218,23 @@ public class ClusterInspector : Editor {
|
||||
|
||||
// Draw selected Nucleus
|
||||
Handles.color = Color.white;
|
||||
Handles.DrawSolidDisc(position, Vector3.forward, size + 2);
|
||||
DrawNucleus(this.currentNucleus, position, length(this.currentNucleus.outputValue), 20);
|
||||
if (expandArray) {
|
||||
float spacing = 400f / this.currentNucleus.array.nuclei.Length;
|
||||
float margin = 10 + spacing / 2;
|
||||
int row = 0;
|
||||
foreach (INucleus nucleus in this.currentNucleus.array.nuclei) {
|
||||
Vector3 pos = new(150, margin + row * spacing, 0.0f);
|
||||
Handles.color = Color.white;
|
||||
//Handles.DrawLine(parentPos, pos);
|
||||
|
||||
DrawNucleus(nucleus, pos, 0, size);
|
||||
row++;
|
||||
}
|
||||
}
|
||||
else {
|
||||
Handles.DrawSolidDisc(position, Vector3.forward, size + 2);
|
||||
DrawNucleus(this.currentNucleus, position, length(this.currentNucleus.outputValue), 20);
|
||||
}
|
||||
}
|
||||
|
||||
private void DrawReceivers(INucleus nucleus, Vector3 parentPos, float size) {
|
||||
@ -318,18 +334,36 @@ public class ClusterInspector : Editor {
|
||||
normal = { textColor = Color.white },
|
||||
fontStyle = FontStyle.Bold,
|
||||
};
|
||||
if (nucleus is Neuron neuron) {
|
||||
if (nucleus is INucleus neuron) {
|
||||
if (neuron.array == null || neuron.array.nuclei == null || neuron.array.nuclei.Length == 0)
|
||||
neuron.array = new NucleusArray(neuron);
|
||||
|
||||
if (neuron.array.nuclei.Length > 1) {
|
||||
if ((!expandArray || neuron.array.nuclei[0] != this.currentNucleus) && neuron.array.nuclei.Length > 1) {
|
||||
Handles.Label(labelPosition, neuron.array.nuclei.Length.ToString(), style);
|
||||
}
|
||||
style.alignment = TextAnchor.UpperCenter;
|
||||
Vector3 labelPos = position - Vector3.down * (size + 0.2f); // below disc along up axis
|
||||
// if ((!expandArray || neuron.array.nuclei[0] != this.currentNucleus) && neuron.array.nuclei.Length > 1) {
|
||||
// Handles.Label(labelPos, nucleus.name, style);
|
||||
// }
|
||||
// else {
|
||||
if (expandArray && neuron.array.nuclei[0] == this.currentNucleus) {
|
||||
int arrayIx = 0;
|
||||
foreach (INucleus n in neuron.array.nuclei) {
|
||||
if (n == neuron)
|
||||
break;
|
||||
arrayIx++;
|
||||
}
|
||||
Handles.Label(labelPos, $"{nucleus.name}[{arrayIx}]", style);
|
||||
}
|
||||
else
|
||||
Handles.Label(labelPos, nucleus.name, style);
|
||||
}
|
||||
else {
|
||||
style.alignment = TextAnchor.UpperCenter;
|
||||
Vector3 labelPos = position - Vector3.down * (size + 0.2f); // below disc along up axis
|
||||
Handles.Label(labelPos, nucleus.name, style);
|
||||
}
|
||||
|
||||
style.alignment = TextAnchor.UpperCenter;
|
||||
Vector3 labelPos = position - Vector3.down * (size + 0.2f); // below disc along up axis
|
||||
Handles.Label(labelPos, nucleus.name, style);
|
||||
|
||||
Rect neuronRect = new(position.x - size, position.y - size, size * 2, size * 2);
|
||||
int id = GUIUtility.GetControlID(FocusType.Passive);
|
||||
@ -371,7 +405,13 @@ public class ClusterInspector : Editor {
|
||||
}
|
||||
|
||||
private void HandleClicked(IReceptor nucleus) {
|
||||
if (nucleus is INucleus n) {
|
||||
if (nucleus == this.currentNucleus) {
|
||||
if (nucleus is INucleus n) {
|
||||
expandArray = !expandArray;
|
||||
return;
|
||||
}
|
||||
}
|
||||
else if (nucleus is INucleus n) {
|
||||
this.currentNucleus = n;
|
||||
BuildLayers();
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user