/**********************************************************************************
* Blueprint Reality Inc. CONFIDENTIAL
* 2020 Blueprint Reality Inc.
* All Rights Reserved.
*
* NOTICE:  All information contained herein is, and remains, the property of
* Blueprint Reality Inc. and its suppliers, if any.  The intellectual and
* technical concepts contained herein are proprietary to Blueprint Reality Inc.
* and its suppliers and may be covered by Patents, pending patents, and are
* protected by trade secret or copyright law.
*
* Dissemination of this information or reproduction of this material is strictly
* forbidden unless prior written permission is obtained from Blueprint Reality Inc.
***********************************************************************************/

using BlueprintReality.MixCast.Thrift;
using BlueprintReality.Thrift.SharedTextures;
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

namespace BlueprintReality.SharedTextures
{
    [Serializable]
    public class SharedTextureWatcher : IDisposable
    {
        public static Func<string, SharedTextureWatcher> Create { get; protected set; }
        static SharedTextureWatcher()
        {
            Create = (string texId) =>
            {
                return new SharedTextureWatcher(texId);
            };
        }
        public static void OverrideCreateFunc(Func<string, SharedTextureWatcher> newFunc)
        {
            Create = newFunc;
        }

        public string TextureId { get; protected set; }

        protected SharedTex textureInfo = new SharedTex();
        public bool IsAvailable { get { return textureInfo.Handle != 0; } }

        protected SharedTextureWatcher(string texId)
        {
            TextureId = texId;
            SharedTextureSending.OnTextureSent += RefreshTextureFromEvent;
            RefreshTextureInfo();
        }
        public virtual void Dispose()
        {
            SharedTextureSending.OnTextureSent -= RefreshTextureFromEvent;
        }

        public virtual void RefreshTextureInfo()
        {
            Texture localTex = null;
            if( SharedTextureSending.TryGetLocalTexture(TextureId, ref localTex) )
            {
                textureInfo = new SharedTex((long)localTex.GetNativeTexturePtr(), localTex.width, localTex.height, -1);
                return;
            }

            SharedTex newTexInfo;

            SharedTextureCommunication.Client client = string.IsNullOrEmpty(SharedTexturePlugin.manualThriftAddress) ?
                UnityThriftMixCastClient.Get<SharedTextureCommunication.Client>() :
                UnityThriftMixCastClient.Get<SharedTextureCommunication.Client>(SharedTexturePlugin.manualThriftAddress);

            if (client.TrySharedTextureRequest(TextureId, out newTexInfo))
                textureInfo = newTexInfo;
            else
                textureInfo = new SharedTex();
        }
        protected virtual void HandleTextureInfoChanged()
        {

        }

        //Useful for streamlining event driven updates
        public void RefreshTextureFromEvent(string evTextureId, SharedTex evTextureInfo)
        {
            if (TextureId == evTextureId)
            {
                textureInfo = evTextureInfo;
                HandleTextureInfoChanged();
            }
        }
    }
}
