ScrollDetails.cs 12.08 KiB
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using TMPro;
using UnityEngine.Networking;
using Newtonsoft.Json;
using static CommunicationEvents;
using System.Linq;
using static SOMDocManager;
public class ScrollDetails : MonoBehaviour
{
public WorldCursor cursor;
public GameObject parameterDisplayPrefab;
public Scroll ActiveScroll;
public GameObject mmtAnswerPopUp;
public static List<GameObject> ParameterDisplays;
private static List<Scroll.ScrollAssignment> LatestCompletions;
private static List<Fact> LatestRenderedHints;
public string currentMmtAnswer;
public bool dynamicScrollDescriptionsActive = true;
public bool automaticHintGenerationActive = true;
// Start is called before the first frame update
void Start()
{
cursor ??= GameObject.FindObjectOfType<WorldCursor>();
mmtAnswerPopUp.GetComponent<PopupBehavior>().hidePopUp();
}
private void OnEnable()
{
ScrollFactHintEvent.AddListener(animateHint);
NewAssignmentEvent.AddListener(newAssignmentTrigger);
RemoveFactEvent.AddListener(removeFactFromAssignment);
}
private void OnDisable()
{
ScrollFactHintEvent.RemoveListener(animateHint);
NewAssignmentEvent.RemoveListener(newAssignmentTrigger);
RemoveFactEvent.RemoveListener(removeFactFromAssignment);
}
public void setScroll(Scroll s)
{
Transform originalScroll = gameObject.transform.GetChild(1).transform;
Transform originalScrollView = originalScroll.GetChild(1);
Transform originalViewport = originalScrollView.GetChild(0);
this.ActiveScroll = s;
originalScroll.GetChild(0).GetComponent<TextMeshProUGUI>().text = s.description;
//Clear all current ScrollFacts
originalViewport.GetChild(0).gameObject.DestroyAllChildren();
ParameterDisplays = new List<GameObject>();
for (int i = 0; i < s.requiredFacts.Count; i++)
{
var originalObj = Instantiate(parameterDisplayPrefab, Vector3.zero, Quaternion.identity, transform);
var originalScrollFact = originalObj.transform.GetChild(0).GetComponent<RenderedScrollFact>();
originalScrollFact.ID = i;
originalScrollFact.Label = s.requiredFacts[i].label;
originalScrollFact.factUri = s.requiredFacts[i].@ref.uri;
originalObj.transform.SetParent(originalViewport.GetChild(0));
ParameterDisplays.Add(originalObj);
}
//set active scroll for ErrorMessagePopup
PopupBehavior popup = mmtAnswerPopUp.GetComponent<PopupBehavior>();
popup.setScroll(this.ActiveScroll);
popup.setParameterDisplays(ParameterDisplays);
}
public void magicButtonTrigger()
{
StartCoroutine(magicButton());
IEnumerator magicButton()
{
//Non blocking wait till sendView() is finished
yield return sendView("/scroll/apply");
if (currentMmtAnswer == null)
{
Debug.Log("DAS HAT NICHT GEKLAPPT");
PushoutFactFailEvent.Invoke(null, null);
}
else
{
Debug.Log(currentMmtAnswer);
Scroll.ScrollApplicationInfo pushout = JsonConvert.DeserializeObject<Scroll.ScrollApplicationInfo>(currentMmtAnswer);
if (pushout.acquiredFacts.Count == 0)
PushoutFactFailEvent.Invoke(null, pushout);
readPushout(pushout.acquiredFacts);
}
}
}
public void newAssignmentTrigger()
{
if (this.automaticHintGenerationActive || this.dynamicScrollDescriptionsActive)
StartCoroutine(newAssignment());
IEnumerator newAssignment()
{
//Non blocking wait till sendView() is finished
yield return sendView("/scroll/dynamic");
if (currentMmtAnswer == null)
{
Debug.Log("DAS HAT NICHT GEKLAPPT");
}
else
{
// Todo delte maybe
Debug.Log("Current mmt answer: " + currentMmtAnswer);
Scroll.ScrollDynamicInfo scrollDynamicInfo = JsonConvert.DeserializeObject<Scroll.ScrollDynamicInfo>(currentMmtAnswer);
processScrollDynamicInfo(scrollDynamicInfo);
}
}
}
IEnumerator sendView(string endpoint)
{
string body = prepareScrollAssignments();
System.DateTime startTime = System.DateTime.UtcNow;
using UnityWebRequest www = UnityWebRequest.Put(ServerAdress + endpoint, body);
www.method = UnityWebRequest.kHttpVerbPOST;
www.SetRequestHeader("Content-Type", "application/json");
yield return www.SendWebRequest();
System.DateTime twoTime = System.DateTime.UtcNow;
if (www.result == UnityWebRequest.Result.ConnectionError
|| www.result == UnityWebRequest.Result.ProtocolError)
{
Debug.Log(www.error);
currentMmtAnswer = null;
}
else
{
string answer = www.downloadHandler.text;
currentMmtAnswer = answer;
}
System.DateTime endTime = System.DateTime.UtcNow;
string diffInSeconds = (endTime - startTime).TotalMilliseconds.ToString();
string diff = (twoTime - startTime).TotalMilliseconds.ToString();
}
private string prepareScrollAssignments()
{
List<Scroll.ScrollAssignment> assignmentList = new();
for (int i = 0; i < ParameterDisplays.Count; i++)
{
Fact tempFact = ParameterDisplays[i].GetComponentInChildren<DropHandling>().currentFact;
if (tempFact != null)
assignmentList.Add(new Scroll.ScrollAssignment(ActiveScroll.requiredFacts[i].@ref.uri, tempFact.Id));
}
return JsonConvert.SerializeObject(new Scroll.FilledScroll(ActiveScroll.@ref, assignmentList));
}
private void readPushout(List<MMTDeclaration> pushoutFacts)
{
mmtAnswerPopUp.GetComponent<PopupBehavior>().hidePopUp(); //close error Window
bool samestep = false;
for (int i = 0; i < pushoutFacts.Count; i++, samestep = true)
{
Fact newFact = ParsingDictionary.parseFactDictionary[pushoutFacts[i].getType()].Invoke(pushoutFacts[i]);
if (newFact != null)
PushoutFactEvent.Invoke(FactManager.AddFactIfNotFound(newFact, out _, samestep, null, ActiveScroll.label), FactObject.FactMaterials.Solution);
else
Debug.Log("Parsing on pushout-fact returned null -> One of the dependent facts does not exist");
}
}
public void processScrollDynamicInfo(Scroll.ScrollDynamicInfo scrollDynamicInfo)
{
LatestCompletions = scrollDynamicInfo.completions.Count > 0
? scrollDynamicInfo.completions[0]
: new List<Scroll.ScrollAssignment>();
List<string> hintUris = LatestCompletions.Select(completion => completion.fact.uri).ToList();
//Update Scroll, process data for later hints and update Uri-List for which hints are available
hintUris = processRenderedScroll(scrollDynamicInfo.rendered, hintUris);
if (automaticHintGenerationActive)
//Show that Hint is available for ScrollParameter
HintAvailableEvent.Invoke(hintUris);
}
public List<string> processRenderedScroll(Scroll rendered, List<string> hintUris)
{
Transform scroll = gameObject.transform.GetChild(1).transform;
if (this.dynamicScrollDescriptionsActive)
//Update scroll-description
scroll.GetChild(0).GetComponent<TextMeshProUGUI>().text = rendered.description;
LatestRenderedHints = new List<Fact>();
for (int i = 0; i < rendered.requiredFacts.Count; i++)
{
GameObject obj = ParameterDisplays.Find(x => x.transform.GetChild(0).GetComponent<RenderedScrollFact>().factUri.Equals(rendered.requiredFacts[i].@ref.uri));
if (this.dynamicScrollDescriptionsActive)
{
//Update ScrollParameter label
obj.transform.GetChild(0).GetComponent<RenderedScrollFact>().Label = rendered.requiredFacts[i].label;
}
//Check Hint Informations
//If ScrollFact is assigned -> No Hint
if (obj.transform.GetChild(0).GetComponent<DropHandling>().currentFact == null)
{
// Debug.Log(" print out " + rendered.requiredFacts[i].getType());
Fact currentFact = ParsingDictionary.parseFactDictionary[rendered.requiredFacts[i].getType()].Invoke(rendered.requiredFacts[i]);
//If currentFact could be parsed: this fact maybe not yet exists in the global fact-list but there must be a fact
// of the same type and the same dependent facts in the fact-list, otherwise currentFact could not have been parsed
//If the fact could not be parsed -> Therefore not all dependent Facts exist -> No Hint
//AND if fact has no dependent facts -> No Hint
if (currentFact != null && currentFact.HasDependentFacts)
{
//Hint available for abstract-problem uri
hintUris.Add(currentFact.Id);
LatestRenderedHints.Add(currentFact);
}
}
}
return hintUris;
}
public void animateHint(GameObject scrollParameter, string scrollParameterUri)
{
Scroll.ScrollAssignment suitableCompletion = LatestCompletions.Find(x => x.fact.uri.Equals(scrollParameterUri));
Fact fact;
if (suitableCompletion != null)
{
if (FactOrganizer.AllFacts.ContainsKey(suitableCompletion.assignment.uri))
{
fact = FactOrganizer.AllFacts[suitableCompletion.assignment.uri];
//Animate ScrollParameter
scrollParameter.GetComponentInChildren<ImageHintAnimation>().AnimationTrigger();
//Animate Fact in FactPanel
AnimateExistingFactEvent.Invoke(fact, FactObject.FactMaterials.Hint);
}
}
else if (LatestRenderedHints.Exists(x => x.Id.Equals(scrollParameterUri)))
{
fact = LatestRenderedHints.Find(x => x.Id.Equals(scrollParameterUri));
var factId = fact.Id;
//If there is an equal existing fact -> Animate that fact AND ScrollParameter
if (FactOrganizer.AllFacts.ContainsKey(factId))
{
Fact existingFact = FactOrganizer.AllFacts[factId];
//Animate ScrollParameter
scrollParameter.GetComponentInChildren<ImageHintAnimation>().AnimationTrigger();
//Animate Fact in FactPanel
AnimateExistingFactEvent.Invoke(existingFact, FactObject.FactMaterials.Hint);
}
//If not -> Generate a Fact-Representation with such dependent facts
else
{
//Animate ScrollParameter
scrollParameter.GetComponentInChildren<ImageHintAnimation>().AnimationTrigger();
//Generate new FactRepresentation and animate it
AnimateNonExistingFactEvent.Invoke(fact);
}
}
}
//this is called whenever a Fact is Deleted in the world, to make sure it is removed from the scroll
public void removeFactFromAssignment(Fact fact)
{
Transform originalScroll = gameObject.transform.GetChild(1).transform;
Transform originalScrollView = originalScroll.GetChild(1);
Transform originalViewport = originalScrollView.GetChild(0);
for (int i = 0; i < originalViewport.GetChild(0).childCount; i++)
{
RenderedScrollFact scrollFact = originalViewport.GetChild(0).transform.GetChild(i).GetChild(0).gameObject.GetComponent<RenderedScrollFact>();
if (scrollFact.Label == fact.Label)
{
DropHandling dropHandling = originalViewport.GetChild(0).transform.GetChild(i).GetChild(0).gameObject.GetComponent<DropHandling>();
dropHandling.OnPointerClick(null);
}
}
}
}