using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using Microsoft.Phone.Controls;

using UnityApp = UnityPlayer.UnityApp;
using UnityBridge = WinRTBridge.WinRTBridge;

namespace WindowsPhoneUnityConnection
{
	public partial class MainPage : PhoneApplicationPage
	{
		private bool _unityStartedLoading;
		private bool _unityLoaded;
		private int _eventCount = 0;
		private UnityEngine.GameObject _cube;

		// Constructor
		public MainPage()
		{
			UnityApp.SetBridge(new UnityBridge());
			InitializeComponent();
		}

		private void DrawingSurfaceBackground_Loaded(object sender, RoutedEventArgs e)
		{
			if (!_unityStartedLoading)
			{
				_unityStartedLoading = true;

				UnityApp.SetLoadedCallback(Unity_Loaded);

				var content = Application.Current.Host.Content;
				var width = (int)Math.Floor(content.ActualWidth * content.ScaleFactor / 100.0 + 0.5);
				var height = (int)Math.Floor(content.ActualHeight * content.ScaleFactor / 100.0 + 0.5);

				UnityApp.SetNativeResolution(width, height);
				UnityApp.SetRenderResolution(width, height);
				UnityPlayer.UnityApp.SetOrientation((int)Orientation);

				DrawingSurfaceBackground.SetBackgroundContentProvider(UnityApp.GetBackgroundContentProvider());
				DrawingSurfaceBackground.SetBackgroundManipulationHandler(UnityApp.GetManipulationHandler());
			}
		}

		private void Unity_Loaded()
		{
			// It's now safe to access Unity objects.
			// Get MainScript (which is attached to Main Camera) and subscribe to button click event.

			var mainScript = (MainScript)UnityEngine.GameObject.FindObjectOfType(typeof(MainScript));
			mainScript.buttonClicked += mainScript_buttonClicked;

			// Get Cube object from the MainScene.

			_cube = UnityEngine.GameObject.Find("Cube");

			// Unity is loaded and we are done with initialization.

			_unityLoaded = true;

			// Display XAML controls which were hidden while loading Unity.
			// XAML controls can only be accessed from UI thread.

			Dispatcher.BeginInvoke(() =>
			{
				EventTextBlock.Visibility = Visibility.Visible;
				CubeTextBlock.Visibility = Visibility.Visible;
				CubeSlider.Visibility = Visibility.Visible;
			});
		}

		private void mainScript_buttonClicked()
		{
			// Unity button has been clicked.
			// Update TextBlock control from UI thread.

			Dispatcher.BeginInvoke(() =>
			{
				EventTextBlock.Text = string.Format("Event count: {0}", ++_eventCount);
			});
		}

		private void PhoneApplicationPage_OrientationChanged(object sender, OrientationChangedEventArgs e)
		{
			UnityApp.SetOrientation((int)e.Orientation);
		}

		private void CubeSlider_ValueChanged(object sender, RoutedPropertyChangedEventArgs<double> e)
		{
			if (_unityLoaded)
			{
				var value = (float)-e.NewValue;

				// It is only safe to access Unity objects from Unity thread.

				UnityApp.BeginInvoke(() =>
				{
					_cube.transform.rotation = UnityEngine.Quaternion.Euler(0, value, 0);
				});
			}
		}
	}
}