/// <summary>
        /// export selected gameobjects, temporarily spawn them in the scene if they are prefabs
        /// </summary>
        /// <returns>true if exported at least 1 mesh</returns>
        public static bool ExportSelectedObjectsPrefab()
        {
            List <Transform> entireSelection = new List <Transform>();

            entireSelection.AddRange(Selection.GetTransforms(SelectionMode.Editable));

            if (entireSelection.Count == 0)
            {
                Debug.Log("No Dynamic Objects selected"); return(false);
            }

            Debug.Log("Starting export of " + entireSelection.Count + " Dynamic Objects");

            List <Transform> sceneObjects = new List <Transform>();

            sceneObjects.AddRange(Selection.GetTransforms(SelectionMode.Editable | SelectionMode.ExcludePrefab));

            List <Transform> prefabsToSpawn = new List <Transform>();

            //add prefab objects to a list
            foreach (var v in entireSelection)
            {
                if (!sceneObjects.Contains(v))
                {
                    prefabsToSpawn.Add(v);
                }
            }

            //spawn prefabs
            var temporarySpawnedPrefabs = new List <GameObject>();

            foreach (var v in prefabsToSpawn)
            {
                var newPrefab = GameObject.Instantiate(v.gameObject);
                temporarySpawnedPrefabs.Add(newPrefab);
                sceneObjects.Add(newPrefab.transform);
            }

            //export all the objects
            int           successfullyExportedCount = 0;
            List <string> exportedMeshNames         = new List <string>();
            List <string> totalExportedMeshNames    = new List <string>();

            foreach (var v in sceneObjects)
            {
                var dynamic = v.GetComponent <DynamicObject>();
                if (dynamic == null)
                {
                    continue;
                }

                if (!dynamic.UseCustomMesh)
                {
                    //skip exporting a mesh with no name
                    continue;
                }
                if (string.IsNullOrEmpty(dynamic.MeshName))
                {
                    if (!totalExportedMeshNames.Contains(""))
                    {
                        totalExportedMeshNames.Add("");
                    }
                    Debug.LogWarning("GameObject " + dynamic.gameObject + " has empty mesh name");
                    continue;
                }

                if (exportedMeshNames.Contains(dynamic.MeshName))
                {
                    successfullyExportedCount++; continue;
                }                                                                                            //skip exporting same mesh

                if (v.GetComponent <Canvas>() != null)
                {
                    //TODO merge this deeper in the export process. do this recurively ignoring child dynamics
                    //take a snapshot
                    var width  = v.GetComponent <RectTransform>().sizeDelta.x *v.localScale.x;
                    var height = v.GetComponent <RectTransform>().sizeDelta.y *v.localScale.y;

                    var screenshot = CognitiveVR_SceneExplorerExporter.Snapshot(v);

                    var mesh = CognitiveVR_SceneExplorerExporter.ExportQuad(dynamic.MeshName, width, height, v, UnityEditor.SceneManagement.EditorSceneManager.GetActiveScene().name, screenshot);
                    CognitiveVR_SceneExplorerExporter.ExportDynamicObject(mesh, dynamic.MeshName, screenshot, dynamic.MeshName);
                    EditorCore.SaveDynamicThumbnailAutomatic(dynamic.gameObject);
                    successfullyExportedCount++;
                }
                else if (CognitiveVR_SceneExplorerExporter.ExportDynamicObject(v))
                {
                    EditorCore.SaveDynamicThumbnailAutomatic(dynamic.gameObject);
                    successfullyExportedCount++;
                }

                foreach (var common in System.Enum.GetNames(typeof(DynamicObject.CommonDynamicMesh)))
                {
                    if (common.ToLower() == dynamic.MeshName.ToLower())
                    {
                        //don't export common meshes!
                        continue;
                    }
                }
                if (!totalExportedMeshNames.Contains(dynamic.MeshName))
                {
                    totalExportedMeshNames.Add(dynamic.MeshName);
                }
                if (!exportedMeshNames.Contains(dynamic.MeshName))
                {
                    exportedMeshNames.Add(dynamic.MeshName);
                }
            }

            //destroy the temporary prefabs
            foreach (var v in temporarySpawnedPrefabs)
            {
                GameObject.DestroyImmediate(v);
            }

            if (entireSelection.Count == 0)
            {
                EditorUtility.DisplayDialog("Dynamic Object Export", "No Dynamic Objects selected", "Ok");
                return(false);
            }

            if (successfullyExportedCount == 0)
            {
                EditorUtility.DisplayDialog("Dynamic Object Export", "No Dynamic Objects successfully exported.\n\nDo you have Mesh Renderers, Skinned Mesh Renderers or Canvas components attached or as children?", "Ok");
                return(false);
            }

            if (successfullyExportedCount == 1 && entireSelection.Count == 1)
            {
                EditorUtility.DisplayDialog("Dynamic Object Export", "Successfully exported 1 Dynamic Object mesh", "Ok");
            }
            else
            {
                EditorUtility.DisplayDialog("Dynamic Object Export", "From selected Dynamic Objects , found " + totalExportedMeshNames.Count + " unique mesh names and successfully exported " + successfullyExportedCount, "Ok");
            }
            return(true);
        }
        /// <summary>
        /// export all dynamic objects in scene. skip prefabs
        /// </summary>
        /// <returns>true if any dynamics are exported</returns>
        public static bool ExportAllDynamicsInScene()
        {
            //List<Transform> entireSelection = new List<Transform>();
            //entireSelection.AddRange(Selection.GetTransforms(SelectionMode.Editable));

            var dynamics = FindObjectsOfType <DynamicObject>();

            Debug.Log("Starting export of " + dynamics.Length + " Dynamic Objects");


            //export all the objects
            int           successfullyExportedCount = 0;
            List <string> exportedMeshNames         = new List <string>();
            List <string> totalExportedMeshNames    = new List <string>();

            foreach (var dynamic in dynamics)
            {
                if (!dynamic.UseCustomMesh)
                {
                    //skip exporting a mesh with no name
                    continue;
                }
                if (string.IsNullOrEmpty(dynamic.MeshName))
                {
                    if (!totalExportedMeshNames.Contains(""))
                    {
                        totalExportedMeshNames.Add("");
                    }
                    Debug.LogWarning("GameObject " + dynamic.gameObject + " has empty mesh name");
                    continue;
                }

                if (exportedMeshNames.Contains(dynamic.MeshName))
                {
                    successfullyExportedCount++; continue;
                }                                                                                            //skip exporting same mesh

                if (dynamic.GetComponent <Canvas>() != null)
                {
                    //TODO merge this deeper in the export process. do this recurively ignoring child dynamics
                    //take a snapshot
                    var width  = dynamic.GetComponent <RectTransform>().sizeDelta.x *dynamic.transform.localScale.x;
                    var height = dynamic.GetComponent <RectTransform>().sizeDelta.y *dynamic.transform.localScale.y;

                    var screenshot = CognitiveVR_SceneExplorerExporter.Snapshot(dynamic.transform);

                    var mesh = CognitiveVR_SceneExplorerExporter.ExportQuad(dynamic.MeshName, width, height, dynamic.transform, UnityEditor.SceneManagement.EditorSceneManager.GetActiveScene().name, screenshot);
                    CognitiveVR_SceneExplorerExporter.ExportDynamicObject(mesh, dynamic.MeshName, screenshot, dynamic.MeshName);
                    EditorCore.SaveDynamicThumbnailAutomatic(dynamic.gameObject);
                    successfullyExportedCount++;
                }
                else if (CognitiveVR_SceneExplorerExporter.ExportDynamicObject(dynamic.transform))
                {
                    EditorCore.SaveDynamicThumbnailAutomatic(dynamic.gameObject);
                    successfullyExportedCount++;
                }

                foreach (var common in System.Enum.GetNames(typeof(DynamicObject.CommonDynamicMesh)))
                {
                    if (common.ToLower() == dynamic.MeshName.ToLower())
                    {
                        //don't export common meshes!
                        continue;
                    }
                }
                if (!totalExportedMeshNames.Contains(dynamic.MeshName))
                {
                    totalExportedMeshNames.Add(dynamic.MeshName);
                }

                if (!exportedMeshNames.Contains(dynamic.MeshName))
                {
                    exportedMeshNames.Add(dynamic.MeshName);
                }
            }

            if (successfullyExportedCount == 0)
            {
                EditorUtility.DisplayDialog("Dynamic Object Export", "No Dynamic Objects successfully exported.\n\nDo you have Mesh Renderers, Skinned Mesh Renderers or Canvas components attached or as children?", "Ok");
                return(false);
            }

            EditorUtility.DisplayDialog("Dynamic Object Export", "From all Dynamic Objects in scene, found " + totalExportedMeshNames.Count + " unique mesh names and successfully exported " + successfullyExportedCount, "Ok");
            return(true);
        }