Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -149,6 +149,8 @@ public bool TryGetContentHashByKey(string key, out string? hash)
return true;
}
}
else if (string.IsNullOrEmpty(key))
ReportHub.LogWarning(ReportCategory.WEARABLE, $"Empty content key requested for wearable with ID: {DTO.Metadata.id}");
else
ReportHub.LogError(ReportCategory.WEARABLE, $"No content found in DTO for wearable with ID: {DTO.Metadata.id}");

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -42,8 +42,7 @@ public static Representation NewFakeRepresentation() =>
[Serializable]
public abstract class MetadataBase : TrimmedAvatarAttachmentDTO.TrimmedMetadataBase<DataBase>
{
public string name;

// `name` is inherited from TrimmedMetadataBase<TDataBase>.
public I18n[] i18n;
public string thumbnail;

Expand Down
7 changes: 5 additions & 2 deletions Explorer/Assets/DCL/CommunicationData/URLHelpers/URN.cs
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,12 @@ public readonly struct URN

public URN(string urn)
{
// A null/empty urn produces the same field state as default(URN), which IsNullOrEmpty and
// IsValid already treat as a first-class value; ToLower() on it crashed emote loading when
// a DTO carried no id.
originalUrn = urn;
lowercaseUrn = originalUrn.ToLower();
hash = originalUrn != null ? lowercaseUrn.GetHashCode() : 0;
lowercaseUrn = string.IsNullOrEmpty(urn) ? urn : urn.ToLower();
hash = string.IsNullOrEmpty(urn) ? 0 : lowercaseUrn.GetHashCode();
}

private URN(URN urn, int shortenIndex)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -284,7 +284,9 @@ public void Dispose()
PicturePromise?.LoadingIntention.CancellationTokenSource.Cancel();
PicturePromise = null;

// Nulling the reference keeps Dispose idempotent for any caller that reaches it twice.
ProfilePicture.TryDereference();
ProfilePicture = null;
}
}
}
Expand Down
3 changes: 2 additions & 1 deletion Explorer/Assets/DCL/Profiles/SharedAPI/Profile.cs
Original file line number Diff line number Diff line change
Expand Up @@ -83,7 +83,8 @@ public Profile(string userId, string name, Avatar avatar)

public void Dispose()
{
GetCompact().Dispose();
// POOL's actionOnRelease runs Clear(), which already disposes the compact info -
// disposing it here too made every pooled release a double-dispose.
POOL.Release(this);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ public partial class SmartWearableSystem : BaseUnityLoopSystem
/// </summary>
private readonly Dictionary<string, ScenePromise> pendingScenes = new ();

private readonly CancellationTokenSource systemCts = new ();
private CancellationTokenSource outfitEquipCts = new ();

private bool currentSceneDirty;
Expand Down Expand Up @@ -95,6 +96,21 @@ public override void Initialize()
web3IdentityCache.OnIdentityCleared += OnIdentityCleared;
}

protected override void OnDispose()
{
backpackEventBus.EquipWearableEvent -= OnEquipWearable;
backpackEventBus.UnEquipWearableEvent -= OnUnEquipWearable;
backpackEventBus.EquipOutfitEvent -= OnEquipOutfit;
portableExperiencesController.PortableExperienceUnloaded -= OnPortableExperienceUnloaded;
loadingStatus.CurrentStage.OnUpdate -= OnLoadingStatusChanged;
scenesCache.CurrentScene.OnUpdate -= OnCurrentSceneChanged;
web3IdentityCache.OnIdentityCleared -= OnIdentityCleared;

systemCts.Cancel();
systemCts.Dispose();
outfitEquipCts.SafeCancelAndDispose();
}

private void OnEquipWearable(IWearable wearable, bool isManuallyEquipped)
{
if (!isManuallyEquipped) return;
Expand All @@ -104,7 +120,7 @@ private void OnEquipWearable(IWearable wearable, bool isManuallyEquipped)

private async UniTask TryRunSmartWearableSceneAsync(IWearable wearable)
{
bool isSmart = await smartWearableCache.IsSmartAsync(wearable, CancellationToken.None);
bool isSmart = await smartWearableCache.IsSmartAsync(wearable, systemCts.Token);
if (!isSmart || !smartWearableCache.CurrentSceneAllowsSmartWearables) return;

string id = SmartWearableCache.GetCacheId(wearable);
Expand Down Expand Up @@ -322,7 +338,7 @@ private void HandleSceneChange()
if (smartWearablesAllowed)
// Notice scenes that are already running won't run again, so we can call this safely
// TODO consider cancelling a previous running task
RunScenesForEquippedWearablesAsync(AuthorizationAction.SkipAuthorization, CancellationToken.None).Forget();
RunScenesForEquippedWearablesAsync(AuthorizationAction.SkipAuthorization, systemCts.Token).Forget();
else
UnloadAllSmartWearableScenes();
}
Expand All @@ -348,7 +364,7 @@ private void OnLoadingStatusChanged(LoadingStatus.LoadingStage stage)
loadingStatus.CurrentStage.OnUpdate -= OnLoadingStatusChanged;
scenesCache.CurrentScene.OnUpdate += OnCurrentSceneChanged;

RunScenesForEquippedWearablesAsync(AuthorizationAction.RequestAuthorization, CancellationToken.None).Forget();
RunScenesForEquippedWearablesAsync(AuthorizationAction.RequestAuthorization, systemCts.Token).Forget();
}

private async UniTask RunScenesForEquippedWearablesAsync(AuthorizationAction authorization, CancellationToken ct)
Expand Down
Loading