using UnityEngine;
using System.Collections;
using System.Collections.Generic;
public class NeironScript : MonoBehaviour {
public GameObject prefabNeiron;
public GameObject prefabSinaps;
public int IndexNeiron = 0;
private int _TypeIndexNeiron = 0;
public int TypeIndexNeiron
{
get { return _TypeIndexNeiron; }
set {
if (value == 0)
{ _TypeIndexNeiron = value;
gameObject.GetComponent<SpriteRenderer>().color = new Color32(255, 255, 0, 255);
}
if (value == 1)
{ _TypeIndexNeiron = value;
gameObject.GetComponent<SpriteRenderer>().color = new Color32( 0, 255, 0, 255);
}
if (value == 2)
{ _TypeIndexNeiron = value;
gameObject.GetComponent<SpriteRenderer>().color = new Color32(0, 255, 255, 255);
}
if (value == 3)
{ _TypeIndexNeiron = value;
gameObject.GetComponent<SpriteRenderer>().color = new Color32(255, 255, 255, 255);
}
}
}
public float Adder = 0.0f;
public float MaxAdder = 30f;
public float DampferAdder = 1.0f;
public float thresholdTop = 1.0f;
public float AnswerTime = 0.1f;
public float TimeRepose = 0f;
public bool IgnoreInput = false;
public List<GameObject> hitSinaps = new List<GameObject>();
public GameObject Area;
private bool _ActionN;
public bool ActionN
{
get { return _ActionN; }
set
{
_ActionN = value;
if (Area != null)
{
gameObject.GetComponent<LineRenderer>().enabled = value;
bool existAction = Area.GetComponent<AreaScript>().NeironActionList.Contains(gameObject);
if (_ActionN && (!existAction)) Area.GetComponent<AreaScript>().NeironActionList.Add(gameObject);
else Area.GetComponent<AreaScript>().NeironActionList.Remove(gameObject);
}
}
}
public float thresholdDown = -5.0f;
public float timeIgnore = 5.0f;
public float bonusThreshold = 0f;
public float DempferBonusThreshold = 1.0f;
public float TimeEvaluation = 5.0f;
public int LimitRecurrence = 5;
public float thresholdTopUp = 1.0f;
public bool TimeEvaluationBool = false;
public int LimitEvaluationInt = 0;
public float AdaptationTime = 0;
public float thresholdAdapt = 1f;
public float MaxForceSinaps = 100f;
private Vector3 VectorPattern;
public Vector3 VectorTrend;
public float Charge = 0.0f;
public float TimeCharge = 0.01f;
private float changeAngle = 0f;
public float FocusNeiron = 90f;
public bool FocusDinamic = true;
public float StepFocus = 1f;
public float MaxFocus = 90f;
public float Plasticity = 1.0f;
public bool PlasticityDinamic = true;
public float StepPlasticity = 0.01f;
public float BasicPlasticity = 1.0f;
public bool NewNeironDinamic = true;
private float angleMin = 0f;
private bool CorunPlasticRun = false;
private Vector3 noveltyVector = Vector3.zero;
private float noveltyFactor = 0.1f;
IEnumerator StartSummator (){
IgnoreInput = true;
gameObject.GetComponent<SpriteRenderer>().color = new Color32(255, 0, 0, 255);
ActionN = true;
yield return new WaitForSeconds(AnswerTime);
ActionN = false;
ExcitationTransfer ();
yield return new WaitForSeconds(TimeRepose);
IgnoreInput = false;
TypeIndexNeiron = _TypeIndexNeiron;
}
IEnumerator repolarizationTime (){
IgnoreInput = true;
gameObject.GetComponent<SpriteRenderer>().color = new Color32(0, 0, 255, 255);
yield return new WaitForSeconds(timeIgnore);
IgnoreInput = false;
TypeIndexNeiron = _TypeIndexNeiron;
}
IEnumerator StartModule (){
IgnoreInput = true;
ActionN = true;
gameObject.GetComponent<SpriteRenderer>().color = new Color32(255, 0, 0, 255);
yield return new WaitForSeconds(AnswerTime);
ExcitationTransfer ();
ActionN = false;
yield return new WaitForSeconds(TimeRepose);
IgnoreInput = false;
TypeIndexNeiron = _TypeIndexNeiron;
StartCoroutine ("EvaluationTime");
if ((AdaptationTime > 0) && (thresholdTop > thresholdAdapt)) StartCoroutine ("AdaptationVoid");
}
IEnumerator EvaluationTime(){
TimeEvaluationBool = true;
yield return new WaitForSeconds(TimeEvaluation);
TimeEvaluationBool = false;
}
IEnumerator AdaptationVoid(){
yield return new WaitForSeconds(AdaptationTime);
if (thresholdTop > thresholdAdapt) thresholdTop--;
if ((AdaptationTime > 0) && (thresholdTop > thresholdAdapt)) StartCoroutine ("AdaptationVoid");
}
IEnumerator NegativeRepolarization(){
IgnoreInput = true;
ActionN = true;
for (int i = 0; i < 16; i++)
{
Charge = Area.GetComponent<AreaScript>().Spike2[i];
if (Charge > 0) gameObject.GetComponent<SpriteRenderer>().color = new Color32(255, 0, 0, 255);
else gameObject.GetComponent<SpriteRenderer>().color = new Color32(0, 0, 255, 255);
yield return new WaitForSeconds(TimeCharge);
}
Charge = 0f;
TypeIndexNeiron = _TypeIndexNeiron;
ActionN = false;
IgnoreInput = false;
}
IEnumerator StartAssociative(){
IgnoreInput = true;
ActionN = true;
StartCoroutine("PositiveRepolarization");
yield return new WaitForSeconds(AnswerTime);
Compass ();
}
IEnumerator StartWhite() {
IgnoreInput = true;
ActionN = true;
StartCoroutine("PositiveRepolarization");
yield return new WaitForSeconds(AnswerTime);
ExcitationTransfer ();
}
IEnumerator PositiveRepolarization(){
for (int i = 0; i < 16; i++) {
Charge = Area.GetComponent<AreaScript>().Spike1[i];
if (Charge > 0) gameObject.GetComponent<SpriteRenderer>().color = new Color32(255, 0, 0, 255);
else gameObject.GetComponent<SpriteRenderer>().color = new Color32(0, 0, 255, 255);
yield return new WaitForSeconds(TimeCharge);
}
Charge = 0f;
TypeIndexNeiron = _TypeIndexNeiron;
ActionN = false;
yield return new WaitForSeconds(TimeRepose);
IgnoreInput = false;
StartCoroutine ("EvaluationTime");
if ((AdaptationTime > 0) && (thresholdTop > thresholdAdapt)) StartCoroutine ("AdaptationVoid");
}
IEnumerator PlasticTimeCoruntine (Vector2 PT){
CorunPlasticRun = true;
float PlasticBuffer = Plasticity;
Plasticity = PT.x;
yield return new WaitForSeconds(PT.y);
Plasticity = PlasticBuffer;
CorunPlasticRun = false;
}
public void ActiveNeiron (){
if (!IgnoreInput)
{
if (TypeIndexNeiron == 0) StartCoroutine ("StartSummator");
if (TypeIndexNeiron == 1) StartCoroutine ("StartModule");
if (TypeIndexNeiron == 2) StartCoroutine ("StartAssociative");
if (TypeIndexNeiron == 3) StartCoroutine ("StartWhite");
}
}
private void Compass (){
if (Area != null){
VectorPattern = Vector3.zero;
for (int i = 0; i < Area.GetComponent<AreaScript>().NeironActionList.Count; i++) {
if (gameObject == Area.GetComponent<AreaScript> ().NeironActionList [i]) continue;
Vector3 R = Area.GetComponent<AreaScript> ().NeironActionList [i].transform.position - transform.position;
VectorPattern += (Area.GetComponent<AreaScript> ().NeironActionList [i].GetComponent<NeironScript> ().Charge * R.normalized);
}
if (VectorPattern.sqrMagnitude < 3f) VectorPattern = VectorTrend;
if (VectorPattern.sqrMagnitude == 0) VectorPattern = new Vector3(Random.Range(-1f, 1f), Random.Range(-1f, 1f), Random.Range(-1f, 1f));
VectorPattern.Normalize();
if (noveltyVector == Vector3.zero) noveltyVector = -VectorPattern;
changeAngle = Vector3.Angle(VectorPattern, noveltyVector);
if (Area != null) Area.SendMessage("MessageOriginality", changeAngle/180);
VectorTrend = VectorPattern;
noveltyVector = Vector3.Slerp(noveltyVector, VectorPattern, noveltyFactor);
gameObject.GetComponent<LineRenderer>().SetPosition(0, transform.position);
gameObject.GetComponent<LineRenderer>().SetPosition(1, transform.position + VectorTrend * 6);
if (PlasticityDinamic) {
if (changeAngle < 10) Plasticity -= StepPlasticity; else Plasticity += StepPlasticity;
if (Plasticity > 1) Plasticity = 1f;
if (Plasticity < 0) Plasticity = 0f;
}
if (FocusDinamic){
if (changeAngle < 10) FocusNeiron -= StepFocus; else FocusNeiron = MaxFocus;
if (FocusNeiron < 0) FocusNeiron = 0;
}
if (NewNeironDinamic){
if (!Physics.CheckSphere(transform.position + VectorTrend * 5, 3f))
{
if (Area.GetComponent<AreaScript>().Global) NewNeiron();
else
{
if (Area.GetComponent<Collider>().bounds.Contains(transform.position + VectorTrend * 5)) NewNeiron();
}
}
Collider[] hitColliders = Physics.OverlapSphere(transform.position + VectorTrend * 5, 3f);
foreach (Collider value in hitColliders)
{
if (value.tag == "Neiron")
{
bool EnableSinaps = false;
foreach (GameObject sinapsValue in hitSinaps)
{
if (sinapsValue.GetComponent<SinapsScript>().NeironTarget == value.gameObject) {
EnableSinaps = true;
break;
}
}
if (!EnableSinaps) {
GameObject cSinaps = Instantiate(prefabSinaps, transform.position, transform.rotation) as GameObject;
cSinaps.transform.parent = transform;
cSinaps.GetComponent<SinapsScript>().NeironTarget = value.gameObject;
cSinaps.GetComponent<SinapsScript>().Force = 0f;
hitSinaps.Add(cSinaps);
}
}
}
}
angleMin = 180f;
if (hitSinaps.Count != 0) angleMin = Vector3.Angle(hitSinaps[0].GetComponent<SinapsScript>().NeironTarget.transform.position - transform.position, VectorTrend);
foreach(GameObject ShershSinaps in hitSinaps)
{
float angleShersh = Vector3.Angle(ShershSinaps.GetComponent<SinapsScript>().NeironTarget.transform.position - transform.position, VectorTrend);
if (angleShersh < angleMin) angleMin = angleShersh;
}
if (FocusNeiron < angleMin) FocusNeiron = angleMin;
foreach(GameObject SinapsCoeff in hitSinaps){
if (SinapsCoeff.GetComponent<SinapsScript>().TypeSinaps == 0){
float angleSinaps = Vector3.Angle(SinapsCoeff.GetComponent<SinapsScript>().NeironTarget.transform.position - transform.position, VectorTrend);
if (angleSinaps <= FocusNeiron) SinapsCoeff.GetComponent<SinapsScript>().Force += MaxForceSinaps * Plasticity;
else SinapsCoeff.GetComponent<SinapsScript>().Force -= MaxForceSinaps * Plasticity;
SinapsCoeff.GetComponent<SinapsScript>().Force = Mathf.Clamp(SinapsCoeff.GetComponent<SinapsScript>().Force, 0, MaxForceSinaps);
}
}
}
ExcitationTransfer ();
}
private void NewNeiron (){
GameObject clone = Instantiate(prefabNeiron, transform.position + VectorTrend * 6, transform.rotation) as GameObject;
if (Area != null) Area.GetComponent<AreaScript>().amount++;
clone.GetComponent<NeironScript>().Plasticity = BasicPlasticity;
clone.GetComponent<NeironScript>().ActionN = false;
clone.GetComponent<NeironScript>().IgnoreInput = false;
clone.GetComponent<NeironScript>().Adder = 0f;
clone.GetComponent<NeironScript>().VectorTrend = Vector3.zero;
clone.GetComponent<NeironScript>().Area = Area;
clone.GetComponent<NeironScript>().TimeEvaluationBool = false;
clone.GetComponent<NeironScript>().LimitEvaluationInt = 0;
clone.GetComponent<NeironScript>().Charge = 0.0f;
clone.GetComponent<NeironScript>().FocusNeiron = MaxFocus;
clone.GetComponent<NeironScript>().Plasticity = BasicPlasticity;
clone.GetComponent<NeironScript>().TypeIndexNeiron = 2;
clone.GetComponent<NeironScript>().noveltyVector = Vector3.zero;
clone.GetComponent<NeironScript>().VectorTrend = Vector3.zero;
clone.GetComponent<LineRenderer>().SetPosition(0, clone.transform.position);
clone.GetComponent<LineRenderer>().SetPosition(1, clone.transform.position);
clone.SendMessage("StopNeiron");
GameObject ManagerObj = GameObject.Find("Manager");
ManagerObj.GetComponent<ManagerScript>().EndIndexNeiron++;
clone.GetComponent<NeironScript>().IndexNeiron = ManagerObj.GetComponent<ManagerScript>().EndIndexNeiron;
clone.name = "Neiron" + clone.GetComponent<NeironScript>().IndexNeiron;
foreach (GameObject sd in clone.GetComponent<NeironScript>().hitSinaps) Destroy(sd);
clone.GetComponent<NeironScript>().hitSinaps.Clear();
}
void FixedUpdate(){
if (!IgnoreInput)
{
if (TypeIndexNeiron == 0)
{
if (Adder > thresholdTop)
{
StartCoroutine ("StartSummator");
}
}
if (TypeIndexNeiron == 1)
{
if (Adder > thresholdTop + bonusThreshold)
{
if (TimeEvaluationBool)
{
LimitEvaluationInt++;
StopCoroutine("EvaluationTime");
TimeEvaluationBool = false;
}
else LimitEvaluationInt = 0;
if ((LimitEvaluationInt > LimitRecurrence) && (bonusThreshold == 0)) thresholdTop += thresholdTopUp;
StopCoroutine ("AdaptationVoid");
StartCoroutine ("StartModule");
}
if (Adder < thresholdDown)
{
if (Area != null) StartCoroutine ("repolarizationTime");
}
}
if (TypeIndexNeiron == 2)
{
if (Adder > thresholdTop + bonusThreshold)
{
if (TimeEvaluationBool)
{
LimitEvaluationInt++;
StopCoroutine("EvaluationTime");
TimeEvaluationBool = false;
}
else LimitEvaluationInt = 0;
if ((LimitEvaluationInt > LimitRecurrence) && (bonusThreshold == 0)) thresholdTop += thresholdTopUp;
StopCoroutine ("AdaptationVoid");
StartCoroutine ("StartAssociative");
}
if (Adder < thresholdDown)
{
StartCoroutine ("NegativeRepolarization");
}
}
if (TypeIndexNeiron == 3)
{
if (Adder > thresholdTop + bonusThreshold)
{
if (TimeEvaluationBool)
{
LimitEvaluationInt++;
StopCoroutine("EvaluationTime");
TimeEvaluationBool = false;
}
else LimitEvaluationInt = 0;
if ((LimitEvaluationInt > LimitRecurrence) && (bonusThreshold == 0)) thresholdTop += thresholdTopUp;
StopCoroutine ("AdaptationVoid");
StartCoroutine ("StartWhite");
}
if (Adder < thresholdDown)
{
StartCoroutine ("NegativeRepolarization");
}
}
}
if (Mathf.Abs(Adder) <= DampferAdder) Adder = 0f;
if (Adder > DampferAdder) Adder -= DampferAdder;
if (Adder < -DampferAdder) Adder += DampferAdder;
if (Mathf.Abs(bonusThreshold) <= DempferBonusThreshold) bonusThreshold = 0f;
if (bonusThreshold > DempferBonusThreshold) bonusThreshold -= DempferBonusThreshold;
if (bonusThreshold < -DempferBonusThreshold) bonusThreshold += DempferBonusThreshold;
}
private void ExcitationTransfer ()
{
foreach (GameObject value in hitSinaps)
{
int T = value.GetComponent<SinapsScript>().TypeSinaps;
float F = value.GetComponent<SinapsScript>().Force;
GameObject NT = value.GetComponent<SinapsScript>().NeironTarget;
if (T == 0) NT.SendMessage("AddSummator", F);
if (T == 1) NT.SendMessage("AddTActual", F);
if (T == 2) NT.SendMessage("ActiveNeiron");
if (T == 3) NT.SendMessage("AddSummator", F);
value.GetComponent<SinapsScript>().GoAction = true;
}
}
public void AddSummator (float Summ)
{
Adder += Summ;
if (Adder > MaxAdder) Adder = MaxAdder;
if (Adder < - MaxAdder) Adder = -MaxAdder;
}
public void AddTActual (float T)
{
bonusThreshold += T;
if (bonusThreshold + thresholdTop < 0f) bonusThreshold = - thresholdTop + 0.0001f;
}
public void StopNeiron(){
StopAllCoroutines();
}
public void plasticSetTime (Vector2 plasticTime){
if (!CorunPlasticRun) StartCoroutine("PlasticTimeCoruntine", plasticTime);
if (TypeIndexNeiron == 2) thresholdTop = thresholdAdapt;
}
}