< Summary

Class:DCL.Builder.BIWCreatorController
Assembly:BuilderInWorld
File(s):/tmp/workspace/unity-renderer/unity-renderer/Assets/DCLPlugins/BuilderInWorld/Scripts/Controllers/BIWCreatorController.cs
Covered lines:121
Uncovered lines:64
Coverable lines:185
Total lines:386
Line coverage:65.4% (121 of 185)
Covered branches:0
Total branches:0

Metrics

MethodBranch coverage Crap Score Cyclomatic complexity NPath complexity Sequence coverage
BIWCreatorController()0%110100%
Initialize(...)0%220100%
Dispose()0%220100%
Update()0%6200%
SendAnalytics()0%6200%
CleanUp()0%330100%
IsAnyErrorOnEntities()0%2100%
IsInsideTheLimits(...)0%19.568043.48%
CreateErrorOnEntity(...)0%22090%
DeleteErrorOnEntity(...)0%2.022083.33%
CreateCatalogItem(...)0%110100%
CreateCatalogItem(...)0%9.089090%
ExistsLoadingGameObjectForEntity(...)0%110100%
CreateLoadingObject(...)0%220100%
OnShapeLoadFinish(...)0%2100%
RemoveLoadingObject(...)0%2.022083.33%
RemoveLoadingObjectInmediate(...)0%220100%
AddSmartItemComponent(...)0%2100%
AddEntityNameComponent(...)0%110100%
AddLockedComponent(...)0%110100%
AddShape(...)0%2.52050%
AddSceneMappings(...)0%42600%
CreateLastCatalogItem()0%4.074083.33%
OnCatalogItemSelected(...)0%3.13077.78%
OnCatalogItemDropped(...)0%2100%

File(s)

/tmp/workspace/unity-renderer/unity-renderer/Assets/DCLPlugins/BuilderInWorld/Scripts/Controllers/BIWCreatorController.cs

#LineLine coverage
 1using DCL.Components;
 2using DCL.Models;
 3using System;
 4using System.Collections.Generic;
 5using System.Linq;
 6using DCL.Builder;
 7using DCL.Controllers;
 8using UnityEngine;
 9
 10namespace DCL.Builder
 11{
 12    public class BIWCreatorController : BIWController, IBIWCreatorController
 13    {
 14        private const float SECONDS_TO_SEND_ANALYTICS = 5f;
 15        public event Action OnInputDone;
 16        public event Action OnCatalogItemPlaced;
 17
 18        private IBIWModeController modeController;
 19
 20        private IBIWFloorHandler floorHandler;
 21        private IBIWEntityHandler entityHandler;
 22
 23        private GameObject loadingObjectPrefab;
 24        private GameObject errorPrefab;
 25
 26        private CatalogItem lastCatalogItemCreated;
 27
 1428        private readonly Dictionary<string, BIWLoadingPlaceHolder> loadingGameObjects = new Dictionary<string, BIWLoadin
 1429        private readonly Dictionary<BIWEntity, GameObject> errorGameObjects = new Dictionary<BIWEntity, GameObject>();
 30
 1431        private readonly List<KeyValuePair<CatalogItem, string>> itemsToSendAnalytics = new List<KeyValuePair<CatalogIte
 32
 33        private float lastAnalyticsSentTimestamp = 0;
 34
 35        public override void Initialize(IContext context)
 36        {
 1437            base.Initialize(context);
 38
 1439            modeController = context.editorContext.modeController;
 1440            floorHandler = context.editorContext.floorHandler;
 1441            entityHandler = context.editorContext.entityHandler;
 1442            loadingObjectPrefab = context.projectReferencesAsset.loadingPrefab;
 1443            errorPrefab = context.projectReferencesAsset.errorPrefab;
 44
 1445            if ( context.editorContext.editorHUD != null)
 46            {
 1447                context.editorContext.editorHUD.OnCatalogItemSelected += OnCatalogItemSelected;
 1448                context.editorContext.editorHUD.OnCatalogItemDropped += OnCatalogItemDropped;
 49            }
 1450        }
 51
 52        public override void Dispose()
 53        {
 1454            base.Dispose();
 1455            if ( context.editorContext.editorHUD != null)
 56            {
 1457                context.editorContext.editorHUD.OnCatalogItemSelected -= OnCatalogItemSelected;
 1458                context.editorContext.editorHUD.OnCatalogItemDropped -= OnCatalogItemDropped;
 59            }
 60
 1461            CleanUp();
 1462        }
 63
 64        public override void Update()
 65        {
 066            base.Update();
 067            if (Time.realtimeSinceStartup >= lastAnalyticsSentTimestamp)
 68            {
 069                SendAnalytics();
 070                lastAnalyticsSentTimestamp = Time.realtimeSinceStartup + SECONDS_TO_SEND_ANALYTICS;
 71            }
 072        }
 73
 74        private void SendAnalytics()
 75        {
 076            if (itemsToSendAnalytics.Count == 0)
 077                return;
 78
 079            BIWAnalytics.NewObjectPlacedChunk(itemsToSendAnalytics);
 080            itemsToSendAnalytics.Clear();
 081        }
 82
 83        public void CleanUp()
 84        {
 4285            foreach (BIWLoadingPlaceHolder placeHolder in loadingGameObjects.Values)
 86            {
 787                placeHolder.Dispose();
 88            }
 89
 3890            foreach (BIWEntity entity in errorGameObjects.Keys.ToArray())
 91            {
 592                DeleteErrorOnEntity(entity);
 93            }
 94
 1495            loadingGameObjects.Clear();
 1496            errorGameObjects.Clear();
 1497        }
 98
 099        public bool IsAnyErrorOnEntities() { return errorGameObjects.Count > 0; }
 100
 101        private bool IsInsideTheLimits(CatalogItem sceneObject)
 102        {
 15103            if ( context.editorContext.editorHUD == null)
 0104                return false;
 105
 15106            SceneMetricsModel limits = sceneToEdit.metricsCounter.maxCount;
 15107            SceneMetricsModel usage = sceneToEdit.metricsCounter.currentCount;
 108
 15109            if (limits.bodies < usage.bodies + sceneObject.metrics.bodies)
 110            {
 0111                context.editorContext.editorHUD.ShowSceneLimitsPassed();
 0112                return false;
 113            }
 114
 15115            if (limits.entities < usage.entities + sceneObject.metrics.entities)
 116            {
 0117                context.editorContext.editorHUD.ShowSceneLimitsPassed();
 0118                return false;
 119            }
 120
 15121            if (limits.materials < usage.materials + sceneObject.metrics.materials)
 122            {
 0123                context.editorContext.editorHUD.ShowSceneLimitsPassed();
 0124                return false;
 125            }
 126
 15127            if (limits.meshes < usage.meshes + sceneObject.metrics.meshes)
 128            {
 0129                context.editorContext.editorHUD.ShowSceneLimitsPassed();
 0130                return false;
 131            }
 132
 15133            if (limits.textures < usage.textures + sceneObject.metrics.textures)
 134            {
 0135                context.editorContext.editorHUD.ShowSceneLimitsPassed();
 0136                return false;
 137            }
 138
 15139            if (limits.triangles < usage.triangles + sceneObject.metrics.triangles)
 140            {
 0141                context.editorContext.editorHUD.ShowSceneLimitsPassed();
 0142                return false;
 143            }
 144
 15145            return true;
 146        }
 147
 148        public void CreateErrorOnEntity(BIWEntity entity)
 149        {
 7150            if (errorGameObjects.ContainsKey(entity))
 0151                return;
 152
 7153            GameObject instantiatedError = UnityEngine.Object.Instantiate(errorPrefab, Vector3.zero, errorPrefab.transfo
 7154            instantiatedError.transform.SetParent(entity.rootEntity.gameObject.transform, true);
 7155            instantiatedError.transform.localPosition = Vector3.zero;
 156
 7157            var missingAsset = instantiatedError.GetComponent<MissingAsset>();
 7158            missingAsset.Configure(entity);
 159
 7160            errorGameObjects.Add(entity, instantiatedError);
 7161            entity.OnDelete += DeleteErrorOnEntity;
 7162        }
 163
 164        public void DeleteErrorOnEntity(BIWEntity entity)
 165        {
 7166            if (!errorGameObjects.ContainsKey(entity))
 0167                return;
 168
 7169            entity.OnDelete -= DeleteErrorOnEntity;
 7170            GameObject.Destroy(errorGameObjects[entity]);
 7171            errorGameObjects.Remove(entity);
 7172        }
 173
 16174        public void CreateCatalogItem(CatalogItem catalogItem, bool autoSelect = true, bool isFloor = false) { CreateCat
 175
 176        public BIWEntity CreateCatalogItem(CatalogItem catalogItem, Vector3 startPosition, bool autoSelect = true, bool 
 177        {
 15178            if (catalogItem.IsNFT() && BIWNFTController.i.IsNFTInUse(catalogItem.id))
 0179                return null;
 180
 15181            IsInsideTheLimits(catalogItem);
 182
 15183            BIWUtils.AddSceneMappings(catalogItem.contents, BIWUrlUtils.GetUrlSceneObjectContent(), sceneToEdit.sceneDat
 15184            DCL.Environment.i.world.sceneController.UpdateParcelScenesExecute(sceneToEdit.sceneData);
 185
 15186            Vector3 editionPosition = modeController.GetCurrentEditionPosition();
 187
 15188            BIWEntity entity = entityHandler.CreateEmptyEntity(sceneToEdit, startPosition, editionPosition, false);
 15189            entity.isFloor = isFloor;
 15190            entity.SetRotation(Vector3.zero);
 191
 15192            if (!isFloor)
 8193                CreateLoadingObject(entity);
 194
 20195            entity.rootEntity.OnShapeUpdated += (entity) => onFloorLoadedAction?.Invoke(entity);
 196
 15197            AddShape(catalogItem, entity);
 15198            AddEntityNameComponent(catalogItem, entity);
 15199            AddLockedComponent(entity);
 200
 15201            if (catalogItem.IsSmartItem())
 202            {
 0203                AddSmartItemComponent(entity);
 204            }
 205
 15206            if (catalogItem.IsVoxel())
 0207                entity.isVoxel = true;
 208
 15209            if (autoSelect)
 210            {
 8211                entityHandler.DeselectEntities();
 8212                entityHandler.Select(entity.rootEntity);
 213            }
 214
 15215            entity.rootEntity.gameObject.transform.eulerAngles = Vector3.zero;
 216
 15217            modeController.CreatedEntity(entity);
 218
 15219            lastCatalogItemCreated = catalogItem;
 220
 15221            entityHandler.EntityListChanged();
 15222            entityHandler.NotifyEntityIsCreated(entity.rootEntity);
 15223            OnInputDone?.Invoke();
 15224            OnCatalogItemPlaced?.Invoke();
 15225            return entity;
 226        }
 227
 228        #region LoadingObjects
 229
 2230        public bool ExistsLoadingGameObjectForEntity(string entityId) { return loadingGameObjects.ContainsKey(entityId);
 231
 232        public void CreateLoadingObject(BIWEntity entity)
 233        {
 10234            if (loadingGameObjects.ContainsKey(entity.rootEntity.entityId))
 1235                return;
 236
 9237            BIWLoadingPlaceHolder loadingPlaceHolder = UnityEngine.Object.Instantiate(loadingObjectPrefab, entity.rootEn
 9238            loadingGameObjects.Add(entity.rootEntity.entityId, loadingPlaceHolder);
 9239            entity.OnShapeFinishLoading += OnShapeLoadFinish;
 9240        }
 241
 242        private void OnShapeLoadFinish(BIWEntity entity)
 243        {
 0244            entity.OnShapeFinishLoading -= OnShapeLoadFinish;
 0245            RemoveLoadingObject(entity.rootEntity.entityId);
 0246        }
 247
 248        public void RemoveLoadingObject(string entityId)
 249        {
 1250            if (!loadingGameObjects.ContainsKey(entityId))
 0251                return;
 1252            BIWLoadingPlaceHolder loadingPlaceHolder = loadingGameObjects[entityId];
 1253            loadingGameObjects.Remove(entityId);
 1254            loadingPlaceHolder.DestroyAfterAnimation();
 1255        }
 256
 257        public void RemoveLoadingObjectInmediate(string entityId)
 258        {
 6259            if (!loadingGameObjects.ContainsKey(entityId))
 5260                return;
 1261            BIWLoadingPlaceHolder loadingPlaceHolder = loadingGameObjects[entityId];
 1262            loadingGameObjects.Remove(entityId);
 1263            loadingPlaceHolder.Dispose();
 1264        }
 265
 266        #endregion
 267
 268        #region Add Components
 269
 270        private void AddSmartItemComponent(BIWEntity entity)
 271        {
 272            //Note (Adrian): This will disable the smart item component until it is implemented in kernel
 273            //TODO: After the implementation in kernel of smart items, we should eliminate this return
 0274            return;
 275            SmartItemComponent.Model model = new SmartItemComponent.Model();
 276            model.values = new Dictionary<object, object>();
 277
 278            sceneToEdit.EntityComponentCreateOrUpdateWithModel(entity.rootEntity.entityId, CLASS_ID_COMPONENT.SMART_ITEM
 279
 280            //Note (Adrian): We can't wait to set the component 1 frame, so we set it
 281            if (entity.rootEntity.TryGetBaseComponent(CLASS_ID_COMPONENT.SMART_ITEM, out IEntityComponent component))
 282                ((SmartItemComponent) component).UpdateFromModel(model);
 283        }
 284
 285        private void AddEntityNameComponent(CatalogItem catalogItem, BIWEntity entity)
 286        {
 15287            entityHandler.SetEntityName(entity, catalogItem.name, false);
 15288        }
 289
 290        private void AddLockedComponent(BIWEntity entity)
 291        {
 15292            DCLLockedOnEdit.Model model = new DCLLockedOnEdit.Model();
 15293            model.isLocked = entity.isFloor;
 294
 15295            EntityComponentsUtils.AddLockedOnEditComponent(sceneToEdit, entity.rootEntity, model, Guid.NewGuid().ToStrin
 15296        }
 297
 298        private void AddShape(CatalogItem catalogItem, BIWEntity entity)
 299        {
 15300            if (catalogItem.IsNFT())
 301            {
 0302                NFTShape.Model model = new NFTShape.Model();
 0303                model.color = new Color(0.6404918f, 0.611472f, 0.8584906f);
 0304                model.src = catalogItem.model;
 0305                model.assetId = catalogItem.id;
 306
 0307                NFTShape nftShape = EntityComponentsUtils.AddNFTShapeComponent(sceneToEdit, entity.rootEntity, model, ca
 0308                nftShape.CallWhenReady(entity.ShapeLoadFinish);
 0309            }
 310            else
 311            {
 15312                LoadableShape.Model model = new LoadableShape.Model();
 15313                model.src = catalogItem.model;
 15314                model.assetId = catalogItem.id;
 315
 15316                GLTFShape gltfComponent = EntityComponentsUtils.AddGLTFComponent(sceneToEdit, entity.rootEntity, model, 
 15317                gltfComponent.CallWhenReady(entity.ShapeLoadFinish);
 318            }
 15319        }
 320
 321        #endregion
 322
 323        private void AddSceneMappings(CatalogItem catalogItem)
 324        {
 0325            LoadParcelScenesMessage.UnityParcelScene data = sceneToEdit.sceneData;
 0326            data.baseUrl = BIWUrlUtils.GetUrlSceneObjectContent();
 0327            if (data.contents == null)
 0328                data.contents = new List<ContentServerUtils.MappingPair>();
 0329            foreach (KeyValuePair<string, string> content in catalogItem.contents)
 330            {
 0331                ContentServerUtils.MappingPair mappingPair = new ContentServerUtils.MappingPair();
 0332                mappingPair.file = content.Key;
 0333                mappingPair.hash = content.Value;
 0334                bool found = false;
 0335                foreach (ContentServerUtils.MappingPair mappingPairToCheck in data.contents)
 336                {
 0337                    if (mappingPairToCheck.file == mappingPair.file)
 338                    {
 0339                        found = true;
 0340                        break;
 341                    }
 342                }
 343
 0344                if (!found)
 0345                    data.contents.Add(mappingPair);
 346            }
 347
 0348            DCL.Environment.i.world.sceneController.UpdateParcelScenesExecute(data);
 0349        }
 350
 351        public void CreateLastCatalogItem()
 352        {
 1353            if (lastCatalogItemCreated != null)
 354            {
 1355                if (entityHandler.IsAnyEntitySelected())
 1356                    entityHandler.DeselectEntities();
 1357                OnCatalogItemSelected(lastCatalogItemCreated);
 1358                OnInputDone?.Invoke();
 359            }
 0360        }
 361
 362        private void OnCatalogItemSelected(CatalogItem catalogItem)
 363        {
 1364            if (floorHandler.IsCatalogItemFloor(catalogItem))
 365            {
 0366                floorHandler.ChangeFloor(catalogItem);
 0367            }
 368            else
 369            {
 1370                CreateCatalogItem(catalogItem);
 371            }
 372
 1373            string catalogSection = "";
 1374            if ( context.editorContext.editorHUD != null)
 1375                catalogSection =    context.editorContext.editorHUD.GetCatalogSectionSelected().ToString();
 376
 1377            itemsToSendAnalytics.Add(new KeyValuePair<CatalogItem, string>(catalogItem, catalogSection));
 1378        }
 379
 380        private void OnCatalogItemDropped(CatalogItem catalogItem)
 381        {
 0382            OnCatalogItemSelected(catalogItem);
 0383            entityHandler.DeselectEntities();
 0384        }
 385    }
 386}