From 3df3d923fb0d458a06b10c85d790c505e2bb53d9 Mon Sep 17 00:00:00 2001 From: Savya Bikram Shah Date: Mon, 6 Jul 2026 13:20:27 +0545 Subject: [PATCH] Difficulty based sorting and analytics fixes --- .DS_Store | Bin 16388 -> 18436 bytes Assets/.DS_Store | Bin 16388 -> 16388 bytes Assets/AddressableAssetsData/.DS_Store | Bin 0 -> 6148 bytes Assets/AppsFlyer/.DS_Store | Bin 0 -> 6148 bytes Assets/Confetti FX/.DS_Store | Bin 0 -> 6148 bytes Assets/Darkmatter/.DS_Store | Bin 8196 -> 10244 bytes .../DrawingCatalog/IDrawingTemplate.cs | 1 + .../Services/Analytics/AnalyticsEvents.cs | 3 +- .../Capture/GallerySaveCompletedSignal.cs | 6 +- .../DrawingCatalog/ColorbookShownSignal.cs | 10 + .../ColorbookShownSignal.cs.meta | 2 + .../DrawingTemplate/DrawingTemplateSO.cs | 7 + .../Code/Features/AppBoot/Flow/AppBootFlow.cs | 6 + .../Features/ArtBook/UI/ArtbookPresenter.cs | 16 +- .../Features/Capture/Systems/CaptureSystem.cs | 6 +- .../System/ColorbookFlowController.cs | 8 +- .../Systems/DrawingCatalogController.cs | 2 +- .../UI/DrawingCatalogPresenter.cs | 8 +- .../Editor/DrawingTemplateEditorWindow.cs | 13 +- .../AddressableDrawingTemplateCatalog.cs | 15 +- .../Systems/GameplayFlowController.cs | 36 +- .../Analytics/Systems/AnalyticsTracker.cs | 24 +- .../Capture/Systems/CaptureService.cs | 38 +- Assets/Darkmatter/Content/.DS_Store | Bin 8196 -> 8196 bytes .../Darkmatter/Content/Colorbook UI/.DS_Store | Bin 10244 -> 10244 bytes .../Colorbook UI/DrawingItems/.DS_Store | Bin 6148 -> 6148 bytes .../Aeroplane/Areroplane Reference.png.meta | 2 +- .../Apple/apple reference.png.meta | 2 +- .../DrawingItems/Bus1/bus reference.png.meta | 2 +- .../Car1/Car1_Reference(1).png.meta | 2 +- .../Elephant/Elephant Reference.png.meta | 2 +- .../DrawingItems/dog/dog reference.png.meta | 2 +- ...niversalRenderPipelineGlobalSettings.asset | 15 +- Assets/FacebookSDK/.DS_Store | Bin 0 -> 6148 bytes Assets/Firebase/.DS_Store | Bin 0 -> 6148 bytes Assets/Packages/.DS_Store | Bin 0 -> 6148 bytes Assets/Plugins/.DS_Store | Bin 0 -> 6148 bytes Assets/Spine/.DS_Store | Bin 0 -> 6148 bytes Assets/TextMesh Pro/.DS_Store | Bin 0 -> 6148 bytes .../TMP_SDF-URP Unlit.shadergraph.meta | 10 + Assets/_Recovery.meta | 8 + Assets/_Recovery/0.unity | 4042 +++++++++++++++++ Assets/_Recovery/0.unity.meta | 7 + 43 files changed, 4231 insertions(+), 64 deletions(-) create mode 100644 Assets/AddressableAssetsData/.DS_Store create mode 100644 Assets/AppsFlyer/.DS_Store create mode 100644 Assets/Confetti FX/.DS_Store create mode 100644 Assets/Darkmatter/Code/Core/Data/Signals/Features/DrawingCatalog/ColorbookShownSignal.cs create mode 100644 Assets/Darkmatter/Code/Core/Data/Signals/Features/DrawingCatalog/ColorbookShownSignal.cs.meta create mode 100644 Assets/FacebookSDK/.DS_Store create mode 100644 Assets/Firebase/.DS_Store create mode 100644 Assets/Packages/.DS_Store create mode 100644 Assets/Plugins/.DS_Store create mode 100644 Assets/Spine/.DS_Store create mode 100644 Assets/TextMesh Pro/.DS_Store create mode 100644 Assets/_Recovery.meta create mode 100644 Assets/_Recovery/0.unity create mode 100644 Assets/_Recovery/0.unity.meta diff --git a/.DS_Store b/.DS_Store index 8e312411e1be07082d2ca3c366ca58a7aee0d572..1f34ff2736dee66149396c1ae9c44022c6d6168f 100644 GIT binary patch delta 1039 zcmZo^U~HMdsKUU&!01$(V#vVY0Az9iF^Cr60SW^-3P9R`XQGO>XeUsV1t`J5kjPNN zP|8rmkjhXzS&(V*WCI%(Rwj__WPWY&$zA$3jI5L2m?=&6G3R3vn>pFepm1@T1lwkI z4i*kZmB}&YdTgS8eci#|Cr>apKrmG%zXGaXz%V(7(QGr1fFnyi3quIdj$DR)~ggicERLw^Icq$a`KaaVjMyy&WnA19(P2QPr)l+kbyAUX6*u?Rt8Rp z*_%T|*qQ5*?FLB#0aTu$fFTDQ7Qk>oc7;q;iBZ)zuq&{tM7RgPO0dhgq231BJK0sd znVFIM^W^#BGL!4fc{n=uD0Di0Kkf(;5XsF)7>q0d3|3wy#s!-NnNG4Y+DztAaA5KN zzkBNB00jxQO)=WB0Y4|_DM-PXeF{>{zNrP1S1VLAB{@&lP+ZRJaawQkCB=9~pUDYI zBAeZmTv=Ikcbs`VxnEs|ZM}}#=AiGBH>%62LzrN1voSa_6a!%@FrgG92e95*hRxs9 z8`vj{F->JupDe%_J(=HNK|MQz4?`wH5->?60&yjBkTbTt&INiMO$BmrM}-K&A{|2& zB1CYjD#+kPqyWa53pTGdc+bSb{7@@>@;qY+wmW~ezi|9Md5^IajCsdcikU@KVDe96 zJLV%PdXue8f|;it zv23C&8z^ppxsDr1xT5DgV6?qvp3HCKD+A17pv>t3Qp?D|5CEkUK=kASo7TyqCQ9VH H=L#bL>9`o= delta 714 zcmZpfz}V8jsKUU&!01$(V#vT?0c3IjF^Cr60SW^-3P9R`d!mZAXf05b1t`J5P{feR zki?M4P|T1zS&(V*WCIr#Rwj__WFCWPM%Kxz1k5-Y`Tm0e!{o_^QJaOBzOqhi;N8s5 z!NS2PvH5|3Bg^E|qQaZki2i1p>@Jzh%#`+Ua<`<+WIX{Mj#}Tp1>0U7cLWKDmx)pv=uu zWalf+%~WxHJ=sCP0KrrNhBBYd1SCHL9mod6Kw!ZQBwW!G j3NSuiGf(Ds@#SHJq$RN0$>}`3qN%7}rqES9$gTnau#(c& diff --git a/Assets/.DS_Store b/Assets/.DS_Store index dcbd58be7f48ec6a8bd0efb937411931e8c9dc59..e385eb0d3fb1d63ff9c646be0e75272c7dd7124c 100644 GIT binary patch delta 537 zcmZo^U~Fk%oUnn%w%m4^>d)hj3=9mclQ)=)OuWFycwysxYXPR&b(3WT<=C?CfD}x2 z5L7@gMJ87X@-Z&h+$qS(#9?O=?1wE16d>5Cboctu9(>Yw+A>M#Wq+pjQ$S@2}&d)6X>R@1CaR8B0lLZvC zCbuZoFtu_{)=`p}ETxnHbWF9I5b)P!ZeArz*_KB6ca-XmX&I z)MR_DBo^_m2Mj=t#OA$Pb}UStL6iULsd4<93UWR$NdD@{2qD~pBrGL>;+B^a7$!~- znLJ(JmN|!^eBuPL$#3P$aI8na-K>Hn*m6jz~lugVw?F?g;`ky z?pCBt4%CvGY_FBXA{d{*0OUw)-m7KD!c^!t`LCWDMieUwuQy1C#X)UbCegRP(#?YO;c%8G@;` wxy?|6jY)3;F!mHUdPUN|bUX&yyun;-@;h@bHi*FHf94z5ajD^fX#)8Z0II;m2><{9 diff --git a/Assets/AddressableAssetsData/.DS_Store b/Assets/AddressableAssetsData/.DS_Store new file mode 100644 index 0000000000000000000000000000000000000000..852a700506a1190299a10aaffd68b325a3696fcf GIT binary patch literal 6148 zcmeHKu}%U(5S^7vK%gLKVMVU9R1!;zgPbw3G2yHY;1MwakBBr@S6li4eu4>KVd)3h z8EZRZ>zmz0_Bc>%3^6-o_ub9T+|0b&+hvJJ)JI{Js6<3LG)5XtFR1M23Cy${&ureqe}|uij42KKTxTbpVAin$oJd5sEv`_&ii=W z_;{?%vkI568gzNJm_*yn;B zW#V3<$>${5nd~duysV-fLa7CK?Od#R{bh kI=vms3*L&i(4=6@keIn*NQEU&S!Oe+XyxRgR5pxDLaAPR{WG{MsQ0_|<|3&bB#OMgPK z%Xc`lGbXpU20M{313PbTcV=hy9k+7}0H!%j8UQr_2(S@W)=~W+G*8Wwl8lhEv1_Do zF&s2H{d6?;taU&cPzL@R1N7~#K?@Q%g9&)w@9uSRew4;>ZX$0j^m-&MS>Y4yMvL-hmpueZYah^$Mr*N4klt$tqdpwE(2wL ztWo`MEx-S}PWq$_C<80SfT_ftxQSbm+UjkNYHf(Ei;aZrGDhoyO3JbAP$}NRW(DU$ X>L5mf86%FM=#PM||F$Z9V5hNrQ&cMtB11DhM z2E739+iq(&4Pruo{+H~R+V9&hud*Ezk!p;)b)p&(g(!@{2C5~&{agxBu`Qge^cW*L zr8W)dY|t;Tr9m7J2Y#Caymr@VAFKA9dgQF%dg~}lhemGuVL2sPq*87@%1P zp81o4b0Uke#oQoz5Xz(iO{%h23}w>M9$8*&F*j(^N$Hs}j-6TA8;a7iqdn4eQn5j) z#Q|}^cffwF)%g71E5HByN%Bh^5C{I111d;bNdvEB&(^}r@mU+89HMYAFE^-DP}$>H gKk!k!iJ}925kCN9i@8CxAml?p+aQ%V@S_fV0zP7vJpcdz literal 0 HcmV?d00001 diff --git a/Assets/Darkmatter/.DS_Store b/Assets/Darkmatter/.DS_Store index 121c3f48bff1eaedc3d1dc787119750195ae3723..d283d0a8710e0323fe3c91a2f14ab9f212253c24 100644 GIT binary patch delta 625 zcmZp1XbF&DU|?W$DortDU{C-uIe-{M3-C-V6q~50$SAilU^hRb+-4quS4{Oe>4w3{ z`MCu^1q=*aA9nyr76xaAe1;T;)ZBa*m!zEhB%l~a(G0GRs&B^~QRP$c$`@oHnQc4) zs1;#$S#VKaPJZ6zzd|m|EMgT0zE5@)%VHL15SW}OEIj$BSpH-lan5WM*V%8{3O2!o zA(5ekAraYi?Mmx(5}!j|2bV{<4x2oR>)aPiHV{v$XJZIvNM=Z7$OGbH6wCQeO93rM zkw|)r0g`59U@!pDlM7^eHwOqRF-~4BIt^!#`lI-Y@*o8OB$t>) delta 147 zcmZn(XmOBWU|?W$DortDU;r^WfEYvza8E20o2aMAD6}zPH$S7$W*&i8Oq=tBy_s1A zTIcWb^$y(w~lT{?*CUZ%a3Ni!r0f7WJkZ=VVv9a(w^JIRNKn_NT!3>k* Pd8TeI6?I|6Wk?YKY{etw diff --git a/Assets/Darkmatter/Code/Core/Contracts/Features/DrawingCatalog/IDrawingTemplate.cs b/Assets/Darkmatter/Code/Core/Contracts/Features/DrawingCatalog/IDrawingTemplate.cs index ed010fc..c7c536a 100644 --- a/Assets/Darkmatter/Code/Core/Contracts/Features/DrawingCatalog/IDrawingTemplate.cs +++ b/Assets/Darkmatter/Code/Core/Contracts/Features/DrawingCatalog/IDrawingTemplate.cs @@ -9,6 +9,7 @@ namespace Darkmatter.Core.Contracts.Features.DrawingCatalog { string Id { get; } string DisplayName { get; } + int Difficulty { get; } Sprite DefaultThumbnail { get; } GameObject DrawingPrefab { get; } GameObject ColoringPrefab { get; } diff --git a/Assets/Darkmatter/Code/Core/Contracts/Services/Analytics/AnalyticsEvents.cs b/Assets/Darkmatter/Code/Core/Contracts/Services/Analytics/AnalyticsEvents.cs index 876063b..d3ddfbf 100644 --- a/Assets/Darkmatter/Code/Core/Contracts/Services/Analytics/AnalyticsEvents.cs +++ b/Assets/Darkmatter/Code/Core/Contracts/Services/Analytics/AnalyticsEvents.cs @@ -32,7 +32,8 @@ namespace Darkmatter.Core.Contracts.Services.Analytics public const string ShapeAssembled = "shape_assembled"; public const string ColorApplied = "color_applied"; - // Progression & content (GA4 recommended level_start / level_complete) + // Progression & content. level_start is a GA4-recommended games event; level_complete is our + // custom completion marker (GA4's own pair would be level_end + success). public const string LevelStart = "level_start"; public const string LevelComplete = "level_complete"; public const string AllContentCompleted = "all_content_completed"; diff --git a/Assets/Darkmatter/Code/Core/Data/Signals/Features/Capture/GallerySaveCompletedSignal.cs b/Assets/Darkmatter/Code/Core/Data/Signals/Features/Capture/GallerySaveCompletedSignal.cs index bb66386..2925e31 100644 --- a/Assets/Darkmatter/Code/Core/Data/Signals/Features/Capture/GallerySaveCompletedSignal.cs +++ b/Assets/Darkmatter/Code/Core/Data/Signals/Features/Capture/GallerySaveCompletedSignal.cs @@ -1,4 +1,8 @@ namespace Darkmatter.Core.Data.Signals.Features.Capture { - public record struct GallerySaveCompletedSignal(bool Success); + /// + /// TemplateId identifies which drawing was saved; publishers outside gameplay (art book) must set it + /// because there is no active drawing for analytics to fall back on there. + /// + public record struct GallerySaveCompletedSignal(bool Success, string TemplateId = null); } diff --git a/Assets/Darkmatter/Code/Core/Data/Signals/Features/DrawingCatalog/ColorbookShownSignal.cs b/Assets/Darkmatter/Code/Core/Data/Signals/Features/DrawingCatalog/ColorbookShownSignal.cs new file mode 100644 index 0000000..d047c67 --- /dev/null +++ b/Assets/Darkmatter/Code/Core/Data/Signals/Features/DrawingCatalog/ColorbookShownSignal.cs @@ -0,0 +1,10 @@ +namespace Darkmatter.Core +{ + /// + /// The drawing-catalog (colorbook) screen became visible: scene entry (play / back / next) or + /// returning from the art book. Distinct from , which is the + /// command to show the view and only fires on one navigation path. Analytics keys colorbook_opened + /// and abandoned-drawing detection off this. + /// + public record struct ColorbookShownSignal; +} diff --git a/Assets/Darkmatter/Code/Core/Data/Signals/Features/DrawingCatalog/ColorbookShownSignal.cs.meta b/Assets/Darkmatter/Code/Core/Data/Signals/Features/DrawingCatalog/ColorbookShownSignal.cs.meta new file mode 100644 index 0000000..a54c212 --- /dev/null +++ b/Assets/Darkmatter/Code/Core/Data/Signals/Features/DrawingCatalog/ColorbookShownSignal.cs.meta @@ -0,0 +1,2 @@ +fileFormatVersion: 2 +guid: fa0fb32346ff54da3a9bbfec9f763cf2 \ No newline at end of file diff --git a/Assets/Darkmatter/Code/Core/Data/Static/Features/DrawingTemplate/DrawingTemplateSO.cs b/Assets/Darkmatter/Code/Core/Data/Static/Features/DrawingTemplate/DrawingTemplateSO.cs index ad215b0..3929c02 100644 --- a/Assets/Darkmatter/Code/Core/Data/Static/Features/DrawingTemplate/DrawingTemplateSO.cs +++ b/Assets/Darkmatter/Code/Core/Data/Static/Features/DrawingTemplate/DrawingTemplateSO.cs @@ -12,6 +12,8 @@ namespace Darkmatter.Core.Data.Static.Features.DrawingTemplate { [SerializeField] private string id; [SerializeField] private string displayName; + [SerializeField, Min(0), Tooltip("0 = auto (pieces + regions). Any positive value overrides the computed difficulty.")] + private int difficultyOverride; [SerializeField] private Sprite defaultThumbnail; [SerializeField] private GameObject drawingPrefab; [SerializeField] private GameObject coloringPrefab; @@ -22,6 +24,11 @@ namespace Darkmatter.Core.Data.Static.Features.DrawingTemplate public string Id => id; public string DisplayName => displayName; + // Workload-based: every shape to place and region to color adds one point. + // A positive difficultyOverride replaces the computed value. + public int AutoDifficulty => pieces.Count + regions.Count; + public int Difficulty => difficultyOverride > 0 ? difficultyOverride : AutoDifficulty; + public bool HasDifficultyOverride => difficultyOverride > 0; public Sprite DefaultThumbnail => defaultThumbnail; public GameObject DrawingPrefab => drawingPrefab; public GameObject ColoringPrefab => coloringPrefab; diff --git a/Assets/Darkmatter/Code/Features/AppBoot/Flow/AppBootFlow.cs b/Assets/Darkmatter/Code/Features/AppBoot/Flow/AppBootFlow.cs index 90365bc..0dec868 100644 --- a/Assets/Darkmatter/Code/Features/AppBoot/Flow/AppBootFlow.cs +++ b/Assets/Darkmatter/Code/Features/AppBoot/Flow/AppBootFlow.cs @@ -30,6 +30,12 @@ namespace Darkmatter.Features.AppBoot.Flow public async UniTask StartAsync(CancellationToken cancellation = default) { + // Entry points run in serviceModules registration order and this module is near the front. + // Everything below LoadAsync completes synchronously, so without a real yield the + // IntroStartedSignal publish would happen before later-registered subscribers + // (e.g. AnalyticsTracker) have run Start() — the event bus has no replay, so they'd miss it. + await UniTask.Yield(); + #if UNITY_ANDROID || UNITY_IOS Application.targetFrameRate = 60; #endif diff --git a/Assets/Darkmatter/Code/Features/ArtBook/UI/ArtbookPresenter.cs b/Assets/Darkmatter/Code/Features/ArtBook/UI/ArtbookPresenter.cs index 9e7264d..7672cf9 100644 --- a/Assets/Darkmatter/Code/Features/ArtBook/UI/ArtbookPresenter.cs +++ b/Assets/Darkmatter/Code/Features/ArtBook/UI/ArtbookPresenter.cs @@ -7,6 +7,7 @@ using Darkmatter.Core.Contracts.Features.DrawingCatalog; using Darkmatter.Core.Contracts.Features.Progression; using Darkmatter.Core.Contracts.Features.SaveGate; using Darkmatter.Core.Contracts.Services.Gallery; +using Darkmatter.Core.Data.Signals.Features.Capture; using Darkmatter.Core.Data.Signals.Features.Drawing; using Darkmatter.Libs.Observer; using UnityEngine; @@ -209,7 +210,20 @@ namespace Darkmatter.Features.Artbook texture = await _progression.GetCachedThumbnailAsync(entry.Value.Id); if (texture == null) return; - await _gallery.SaveImageAsync(texture, entry.Value.Name, ct); + // Mirror CaptureSystem's pairing: Started before the write, Completed(success) in + // finally — art-book saves land in the same gallery_save_* analytics funnel as + // gameplay saves. + _eventBus.Publish(new GallerySaveStartedSignal()); + var success = false; + try + { + await _gallery.SaveImageAsync(texture, entry.Value.Name, ct); + success = true; + } + finally + { + _eventBus.Publish(new GallerySaveCompletedSignal(success, entry.Value.Id)); + } // The art book has no success popup of its own, so use the shared toast. await _saveGate.ShowSavedAsync(ct); } diff --git a/Assets/Darkmatter/Code/Features/Capture/Systems/CaptureSystem.cs b/Assets/Darkmatter/Code/Features/Capture/Systems/CaptureSystem.cs index a9215d9..6978494 100644 --- a/Assets/Darkmatter/Code/Features/Capture/Systems/CaptureSystem.cs +++ b/Assets/Darkmatter/Code/Features/Capture/Systems/CaptureSystem.cs @@ -60,12 +60,14 @@ namespace Darkmatter.Features.Capture var tex = new Texture2D(2, 2, TextureFormat.RGBA32, mipChain: false); var success = false; + // Started must pair 1:1 with the Completed publish in finally — a failed LoadImage or a + // throw in BuildFileNameAsync would otherwise emit Completed(false) with no Started. + _bus.Publish(new GallerySaveStartedSignal()); try { if (tex.LoadImage(png)) { var fileName = await BuildFileNameAsync(); - _bus.Publish(new GallerySaveStartedSignal()); await _galleryService.SaveImageAsync(tex, fileName, ct); success = true; } @@ -73,7 +75,7 @@ namespace Darkmatter.Features.Capture finally { UnityEngine.Object.Destroy(tex); - _bus.Publish(new GallerySaveCompletedSignal(success)); + _bus.Publish(new GallerySaveCompletedSignal(success, _progression.LastOpenedTemplateId)); } return png; } diff --git a/Assets/Darkmatter/Code/Features/ColorbookFlow/System/ColorbookFlowController.cs b/Assets/Darkmatter/Code/Features/ColorbookFlow/System/ColorbookFlowController.cs index 013f1ca..c5f02da 100644 --- a/Assets/Darkmatter/Code/Features/ColorbookFlow/System/ColorbookFlowController.cs +++ b/Assets/Darkmatter/Code/Features/ColorbookFlow/System/ColorbookFlowController.cs @@ -68,7 +68,13 @@ public class ColorbookFlowController : IAsyncStartable, IDisposable // one VContainer cancels on teardown, and the linked _scopeCts may lag the callback order. if (cancellation.IsCancellationRequested || ct.IsCancellationRequested) return; - if (!_navigatingToGameplay) _loadingScreen.Hide(); + if (!_navigatingToGameplay) + { + _loadingScreen.Hide(); + // Catalog genuinely on screen — not a transit hop toward gameplay (edit/next relays land + // in this scene with _navigatingToGameplay already latched and never reveal the catalog). + _bus.Publish(new ColorbookShownSignal()); + } PrewarmInterstitialAdAsync().Forget(); } diff --git a/Assets/Darkmatter/Code/Features/DrawingCatalog/Systems/DrawingCatalogController.cs b/Assets/Darkmatter/Code/Features/DrawingCatalog/Systems/DrawingCatalogController.cs index 9190ee2..ece263b 100644 --- a/Assets/Darkmatter/Code/Features/DrawingCatalog/Systems/DrawingCatalogController.cs +++ b/Assets/Darkmatter/Code/Features/DrawingCatalog/Systems/DrawingCatalogController.cs @@ -57,8 +57,8 @@ public sealed class DrawingCatalogController : IDrawingCatalogController private void Refresh() { _visible.Clear(); + // Catalog already orders ids by difficulty (easiest first), then id. _visible.AddRange(_catalog.AllTemplateIds); - _visible.Sort(StringComparer.OrdinalIgnoreCase); ListChanged?.Invoke(); } } \ No newline at end of file diff --git a/Assets/Darkmatter/Code/Features/DrawingCatalog/UI/DrawingCatalogPresenter.cs b/Assets/Darkmatter/Code/Features/DrawingCatalog/UI/DrawingCatalogPresenter.cs index 56f3559..569b4bf 100644 --- a/Assets/Darkmatter/Code/Features/DrawingCatalog/UI/DrawingCatalogPresenter.cs +++ b/Assets/Darkmatter/Code/Features/DrawingCatalog/UI/DrawingCatalogPresenter.cs @@ -48,8 +48,14 @@ namespace Darkmatter.Features.DrawingCatalog } private void HandleOpenColorBookSignal(OpenColorBookSignal signal) + { + ShowCatalog(); + } + + private void ShowCatalog() { _view.Show(); + _eventBus.Publish(new ColorbookShownSignal()); } private void OnRightPageBtnClicked() @@ -84,7 +90,7 @@ namespace Darkmatter.Features.DrawingCatalog private void OnArtBookBtnClicked() { - _eventBus.Publish(new OpenArtBookSignal(()=> _view.Show())); + _eventBus.Publish(new OpenArtBookSignal(ShowCatalog)); _view.Hide(); } diff --git a/Assets/Darkmatter/Code/Features/DrawingTemplate/Editor/DrawingTemplateEditorWindow.cs b/Assets/Darkmatter/Code/Features/DrawingTemplate/Editor/DrawingTemplateEditorWindow.cs index 8818609..183ba9c 100644 --- a/Assets/Darkmatter/Code/Features/DrawingTemplate/Editor/DrawingTemplateEditorWindow.cs +++ b/Assets/Darkmatter/Code/Features/DrawingTemplate/Editor/DrawingTemplateEditorWindow.cs @@ -68,7 +68,9 @@ namespace Darkmatter.Features.DrawingTemplates.Editor _templates.Clear(); _shapes.Clear(); _palettes.Clear(); - _templates.AddRange(FindAllOfType()); + _templates.AddRange(FindAllOfType() + .OrderBy(t => t.Difficulty) + .ThenBy(t => t.Id, StringComparer.OrdinalIgnoreCase)); _shapes.AddRange(FindAllOfType()); _palettes.AddRange(FindAllOfType()); } @@ -169,7 +171,7 @@ namespace Darkmatter.Features.DrawingTemplates.Editor using (new EditorGUILayout.VerticalScope()) { GUILayout.Label(string.IsNullOrEmpty(t.DisplayName) ? t.name : t.DisplayName, EditorStyles.boldLabel); - GUILayout.Label("id: " + (string.IsNullOrEmpty(t.Id) ? "" : t.Id), EditorStyles.miniLabel); + GUILayout.Label($"id: {(string.IsNullOrEmpty(t.Id) ? "" : t.Id)} • diff: {t.Difficulty}{(t.HasDifficultyOverride ? "*" : $" ({t.Pieces.Count}p+{t.AuthoredRegions.Count}r)")}", EditorStyles.miniLabel); } if (GUILayout.Button("Select", GUILayout.Width(54))) Select(t); @@ -206,6 +208,13 @@ namespace Darkmatter.Features.DrawingTemplates.Editor EditorGUILayout.LabelField("Basics", EditorStyles.boldLabel); EditorGUILayout.PropertyField(so.FindProperty("id"), new GUIContent("Id (Addressable Key)")); EditorGUILayout.PropertyField(so.FindProperty("displayName")); + EditorGUILayout.PropertyField(so.FindProperty("difficultyOverride"), + new GUIContent("Difficulty Override", "0 = auto (pieces + regions). Any positive value overrides.")); + EditorGUILayout.LabelField( + new GUIContent("Difficulty (effective)", "Sorts the catalog, lowest first."), + new GUIContent(t.HasDifficultyOverride + ? $"{t.Difficulty} (override; auto would be {t.AutoDifficulty})" + : $"{t.Difficulty} (auto: {t.Pieces.Count} pieces + {t.AuthoredRegions.Count} regions)")); EditorGUILayout.PropertyField(so.FindProperty("defaultThumbnail")); EditorGUILayout.Space(6); diff --git a/Assets/Darkmatter/Code/Features/DrawingTemplate/Systems/AddressableDrawingTemplateCatalog.cs b/Assets/Darkmatter/Code/Features/DrawingTemplate/Systems/AddressableDrawingTemplateCatalog.cs index 93d00d0..dfb95ea 100644 --- a/Assets/Darkmatter/Code/Features/DrawingTemplate/Systems/AddressableDrawingTemplateCatalog.cs +++ b/Assets/Darkmatter/Code/Features/DrawingTemplate/Systems/AddressableDrawingTemplateCatalog.cs @@ -1,3 +1,4 @@ +using System; using System.Collections.Generic; using System.Threading; using Cysharp.Threading.Tasks; @@ -48,7 +49,7 @@ namespace Darkmatter.Features.DrawingTemplates.Systems _byId[t.Id] = t; } - _allIds.Sort(); + SortIds(); _initialized = true; } @@ -84,12 +85,22 @@ namespace Darkmatter.Features.DrawingTemplates.Systems if (!_allIds.Contains(id)) { _allIds.Add(id); - _allIds.Sort(); + SortIds(); } return t; } + // Easiest drawings first; ties broken by id so the order is stable. + private void SortIds() + { + _allIds.Sort((a, b) => + { + var byDifficulty = _byId[a].Difficulty.CompareTo(_byId[b].Difficulty); + return byDifficulty != 0 ? byDifficulty : string.Compare(a, b, StringComparison.OrdinalIgnoreCase); + }); + } + public void ReleaseAll() { if (!_initialized) return; diff --git a/Assets/Darkmatter/Code/Features/GameplayFlow/Systems/GameplayFlowController.cs b/Assets/Darkmatter/Code/Features/GameplayFlow/Systems/GameplayFlowController.cs index 8936986..34593e6 100644 --- a/Assets/Darkmatter/Code/Features/GameplayFlow/Systems/GameplayFlowController.cs +++ b/Assets/Darkmatter/Code/Features/GameplayFlow/Systems/GameplayFlowController.cs @@ -2,6 +2,7 @@ using System; using System.Collections.Generic; using System.Threading; using Cysharp.Threading.Tasks; +using Darkmatter.Core; using Darkmatter.Core.Contracts.Features.Capture; using Darkmatter.Core.Contracts.Features.Coloring; using Darkmatter.Core.Contracts.Features.DrawingCatalog; @@ -28,6 +29,7 @@ namespace Darkmatter.Features.GameplayFlow.Systems public sealed class GameplayFlowController : IAsyncStartable, IGameplayFlowController, IDisposable { private const int AutosaveDebounceMs = 500; + private const float ThumbnailMinIntervalSec = 30f; private readonly IProgressionSystem _progression; private readonly IDrawingTemplateCatalog _catalog; @@ -44,10 +46,12 @@ namespace Darkmatter.Features.GameplayFlow.Systems private string _templateId; private DrawingPhase _phase = DrawingPhase.ShapeBuilding; private bool _allContentReported; + private float _lastThumbnailTime = float.NegativeInfinity; private IDisposable _assembledSub; private IDisposable _colorAppliedSub; private IDisposable _drawingSelectedSub; + private IDisposable _openColorbookSub; private CancellationTokenSource _autosaveCts; private CancellationTokenSource _scopeCts; @@ -104,6 +108,10 @@ namespace Darkmatter.Features.GameplayFlow.Systems _assembledSub = _bus.Subscribe(OnShapeAssembled); _colorAppliedSub = _bus.Subscribe(OnColorApplied); _drawingSelectedSub = _bus.Subscribe(OnDrawingSelected); + // The art book's "colorbook" button publishes OpenColorBookSignal. In the Colorbook + // scene DrawingCatalogPresenter shows the catalog; during gameplay that presenter is + // dead, so treat the signal as "leave gameplay for the colorbook" (same as back). + _openColorbookSub = _bus.Subscribe(OnOpenColorBook); _loadingScreen.SetProgress(1f); if (_phase == DrawingPhase.Coloring) @@ -131,8 +139,10 @@ namespace Darkmatter.Features.GameplayFlow.Systems public async UniTask SaveAsync(CancellationToken ct) { - await SaveCurrentAsync(ct); - await _capture.CapturePngAsync(saveToGallery: true, ct); + // One capture serves both the gallery write and the progress thumbnail — this used to + // run the full capture pipeline twice back to back. + var png = await _capture.CapturePngAsync(saveToGallery: true, ct); + await SaveCurrentAsync(ct, captureThumbnail: false, precapturedThumbnail: png); } public async UniTask NextAsync(CancellationToken ct) @@ -209,6 +219,11 @@ namespace Darkmatter.Features.GameplayFlow.Systems DebouncedAutosaveAsync(_autosaveCts.Token).Forget(); } + private void OnOpenColorBook(OpenColorBookSignal _) + { + BackAsync(CancellationToken.None).Forget(); + } + private void OnDrawingSelected(DrawingSelectedSignal signal) { if (string.IsNullOrEmpty(signal.TemplateId)) return; @@ -232,7 +247,13 @@ namespace Darkmatter.Features.GameplayFlow.Systems try { await UniTask.Delay(AutosaveDebounceMs, cancellationToken: ct); - await SaveCurrentAsync(ct); + // Autosaves fire after every paint pause; capturing a thumbnail each time renders the + // scene to an RT and PNG-encodes it, which OOM-kills long sessions on low-RAM devices. + // Colors always persist; the thumbnail refreshes at most every ThumbnailMinIntervalSec + // here and unconditionally on the exit paths (back / next / select-away). + bool refreshThumbnail = + Time.realtimeSinceStartup - _lastThumbnailTime >= ThumbnailMinIntervalSec; + await SaveCurrentAsync(ct, captureThumbnail: refreshThumbnail); } catch (OperationCanceledException) { @@ -240,7 +261,8 @@ namespace Darkmatter.Features.GameplayFlow.Systems } } - private async UniTask SaveCurrentAsync(CancellationToken ct) + private async UniTask SaveCurrentAsync(CancellationToken ct, bool captureThumbnail = true, + byte[] precapturedThumbnail = null) { if (string.IsNullOrEmpty(_templateId)) return; @@ -263,7 +285,10 @@ namespace Darkmatter.Features.GameplayFlow.Systems FirstCompletedUtc = existing?.FirstCompletedUtc, }; - var thumbnailPng = await _capture.CapturePngAsync(saveToGallery: false, ct); + byte[] thumbnailPng = precapturedThumbnail; + if (thumbnailPng == null && captureThumbnail) + thumbnailPng = await _capture.CapturePngAsync(saveToGallery: false, ct); + if (thumbnailPng != null) _lastThumbnailTime = Time.realtimeSinceStartup; await _progression.SaveProgressAsync(progress, thumbnailPng); } @@ -284,6 +309,7 @@ namespace Darkmatter.Features.GameplayFlow.Systems _assembledSub?.Dispose(); _colorAppliedSub?.Dispose(); _drawingSelectedSub?.Dispose(); + _openColorbookSub?.Dispose(); _autosaveCts?.Cancel(); _autosaveCts?.Dispose(); _scopeCts?.Cancel(); diff --git a/Assets/Darkmatter/Code/Services/Analytics/Systems/AnalyticsTracker.cs b/Assets/Darkmatter/Code/Services/Analytics/Systems/AnalyticsTracker.cs index 69ba573..3fd5ea4 100644 --- a/Assets/Darkmatter/Code/Services/Analytics/Systems/AnalyticsTracker.cs +++ b/Assets/Darkmatter/Code/Services/Analytics/Systems/AnalyticsTracker.cs @@ -56,8 +56,9 @@ namespace Darkmatter.Services.Analytics _subs.Add(_bus.Subscribe(_ => _analytics.LogEvent(AnalyticsEvents.IntroCompleted))); _subs.Add(_bus.Subscribe(_ => _analytics.LogEvent(AnalyticsEvents.PlayClicked))); - // Navigation - _subs.Add(_bus.Subscribe(_ => _analytics.LogEvent(AnalyticsEvents.ColorbookOpened))); + // Navigation. ColorbookShownSignal (not OpenColorBookSignal, which is the show-view command + // and misses scene-entry paths) fires on every way the catalog becomes visible. + _subs.Add(_bus.Subscribe(_ => OnColorbookShown())); _subs.Add(_bus.Subscribe(_ => _analytics.LogEvent(AnalyticsEvents.ArtbookOpened))); _subs.Add(_bus.Subscribe(_ => OnReturnToMainMenu())); @@ -90,6 +91,10 @@ namespace Darkmatter.Services.Analytics private void OnDrawingSelected(string drawingId) { + // GameplayFlowController relays the selection a second time after the scene swap + // (artbook edit path) — same id while already active is that relay, not a new selection. + if (drawingId == _activeDrawingId) return; + // A new selection while a drawing is still open (uncompleted) = the previous one was abandoned. EndActiveDrawingIfAbandoned(); @@ -156,7 +161,7 @@ namespace Darkmatter.Services.Analytics if (dur >= 0f) p[AnalyticsParams.DurationSeconds] = dur; _analytics.LogEvent(AnalyticsEvents.DrawingCompleted, p); - // GA4 recommended games event (lights up built-in level funnels). + // Companion to GA4's level_start (custom name — GA4's own pair would be level_end). _analytics.LogEvent(AnalyticsEvents.LevelComplete, new Dictionary { [AnalyticsParams.LevelName] = s.TemplateId, @@ -178,9 +183,11 @@ namespace Darkmatter.Services.Analytics private void OnGallerySaveCompleted(GallerySaveCompletedSignal s) { _analytics.LogEvent(AnalyticsEvents.GallerySaveCompleted, AnalyticsParams.Success, s.Success ? "true" : "false"); + // Prefer the id carried by the signal: art-book saves happen with no active drawing. + string drawingId = string.IsNullOrEmpty(s.TemplateId) ? _activeDrawingId ?? string.Empty : s.TemplateId; _analytics.LogEvent(AnalyticsEvents.DrawingSaved, new Dictionary { - [AnalyticsParams.DrawingId] = _activeDrawingId ?? string.Empty, + [AnalyticsParams.DrawingId] = drawingId, [AnalyticsParams.Success] = s.Success ? 1 : 0, }); } @@ -191,6 +198,15 @@ namespace Darkmatter.Services.Analytics _analytics.LogEvent(AnalyticsEvents.MainMenuReturned); } + private void OnColorbookShown() + { + // Reaching the catalog with a drawing still open means the player backed out of gameplay + // mid-drawing — the abandon moment. (Completion clears the active drawing before the + // catalog reloads, so the finish path never lands here with one open.) + EndActiveDrawingIfAbandoned(); + _analytics.LogEvent(AnalyticsEvents.ColorbookOpened); + } + // Emits drawing_abandoned for an open, uncompleted drawing. Completion clears _activeDrawingId, so // reaching here with a non-null id means the drawing was left without finishing — the leak signal. private void EndActiveDrawingIfAbandoned() diff --git a/Assets/Darkmatter/Code/Services/Capture/Systems/CaptureService.cs b/Assets/Darkmatter/Code/Services/Capture/Systems/CaptureService.cs index 0bcf3f2..d0729ab 100644 --- a/Assets/Darkmatter/Code/Services/Capture/Systems/CaptureService.cs +++ b/Assets/Darkmatter/Code/Services/Capture/Systems/CaptureService.cs @@ -68,44 +68,36 @@ namespace Darkmatter.Services.Capture var prevActive = RenderTexture.active; RenderTexture.active = rt; - var fullScreen = new Texture2D(sw, sh, TextureFormat.RGBA32, mipChain: false); - fullScreen.ReadPixels(new Rect(0, 0, sw, sh), 0, 0); - fullScreen.Apply(); + // Read only the crop region straight off the RT. A full-screen ReadPixels followed by + // GetPixels/SetPixels cropping allocated a managed Color[] at 16 bytes/pixel (tens of MB) + // on every capture — autosave runs this after each paint, OOM-killing low-RAM devices. + var cropped = new Texture2D(cropW, cropH, TextureFormat.RGBA32, mipChain: false); + cropped.ReadPixels(new Rect(crop.x, crop.y, cropW, cropH), 0, 0); + cropped.Apply(); RenderTexture.active = prevActive; captureViewScope?.Dispose(); captureViewScope = null; try { - var cropped = new Texture2D(cropW, cropH, TextureFormat.RGBA32, mipChain: false); + int targetW = Mathf.Max(1, Mathf.RoundToInt(cropW * scale)); + int targetH = Mathf.Max(1, Mathf.RoundToInt(cropH * scale)); + Texture2D output = cropped; + if (output.width != targetW || output.height != targetH) + output = Resize(cropped, targetW, targetH); + try { - cropped.SetPixels(fullScreen.GetPixels((int)crop.x, (int)crop.y, cropW, cropH)); - cropped.Apply(); - - int targetW = Mathf.Max(1, Mathf.RoundToInt(cropW * scale)); - int targetH = Mathf.Max(1, Mathf.RoundToInt(cropH * scale)); - Texture2D output = cropped; - if (output.width != targetW || output.height != targetH) - output = Resize(cropped, targetW, targetH); - - try - { - return output.EncodeToPNG(); - } - finally - { - if (output != cropped) Object.Destroy(output); - } + return output.EncodeToPNG(); } finally { - Object.Destroy(cropped); + if (output != cropped) Object.Destroy(output); } } finally { - Object.Destroy(fullScreen); + Object.Destroy(cropped); } } finally diff --git a/Assets/Darkmatter/Content/.DS_Store b/Assets/Darkmatter/Content/.DS_Store index 0b3cbc137cb13087516181d05e1bcabc2cfe4799..4ae6d237329881df9f5fb175cdb9992f8ff1c4e1 100644 GIT binary patch delta 218 zcmZp1XmOa}&&aniU^hP_-)0_xW2^!>>4w3{`MCuQK)}gxVaDWx!ZISc`7SO=Ir&LI sF^)xz-TJA|k2^voQm{%06l5S7<9dMsq=LJGZA%p+0Q0d%(f|Me delta 40 qcmZp1XmOa}&&ahgU^hP_*Jd7pW2~FI#A+EQHtg8UE^!*h*$Mz0at^it diff --git a/Assets/Darkmatter/Content/Colorbook UI/.DS_Store b/Assets/Darkmatter/Content/Colorbook UI/.DS_Store index f2ef5dbbf51a3537b97ad47b2540cad322217e5e..61d439cd5a0f1c5c3d29bfd73b7102b151208eb1 100644 GIT binary patch delta 187 zcmZn(XbG6$&nUMsU^hRb+++slGlyGr3Q96lJp&7 F0sw5NI1T^+ delta 47 zcmZn(XbG6$&nUGqU^hRb)MN(%iOnhkSuBi#llw&^Hph#u;F{R5V>7$LZJxGd+!H_|Z!4D{mB%PCP z7@VA+TL6@2U@{8cj7wc^zKcszPJR+lp5wivRh-TDvd`$dJd7npD17kYhPBBlF}wRRz-kP5CubOz>qFZ1)J`4Tc6BI5CCHX<4lQ3@4I23U58_(eOCm_?i%&$yul-InuF zaaDJs-S8V3kY~3?6Dny%bJ}`-)iVCvx5J}uL{;bcw5+G_q?6)_ow9D#KD*d>w(H-&CMS4$oC;Y1vA4&F@8F*#1R14hdB!NGD}EKFw6`aMR*{rsX$F-8!=eZ zVGkCU88(WVPHe*mTV=Khg=2M`A7VIhrs%6P;0&}G=;`H9`v2+I^M58Y z{k+J>xFzeYotu+h8=#j^5s7OQ*D2V_H3j(FT|^Td9N`4h-)~sHpPuhWK@j$$ko?7+jnk{^=ev3~ zrZY1pK6KWJ_6?Ol37f=XfCGfs$B?j&7;$<<*jc_?WtWVzgR2`RDew53neEG>dL62nj*3854Uh7fY rqsGQ@i9wx0o!yT0fVbimYT9Vd;{l;>F)>IUGWikEGDs&1{HOwNpeChC literal 0 HcmV?d00001 diff --git a/Assets/Packages/.DS_Store b/Assets/Packages/.DS_Store new file mode 100644 index 0000000000000000000000000000000000000000..dd1778239b56e0f0d6217948842e3e3af03ba931 GIT binary patch literal 6148 zcmeHKy-or_5dId?U}&ho@}7W5{HafJHpbWx8*L1tXaXDtjqR0|`V`hag^$1kSljsk zezQA4E=UZT7-MFVneT3PX7A=(a>D>{&6`dGr~oKY1q-V*pNOoB&PYK$vgrICDFzrJ z#W}8LqRsIa8IZH9;s9s3<(W;NUmbh?EC;BgfeqSq>SnLoXq~40p)aO7epocWpC(DW zm$sQ#8Xb>c?_QpF7T=@u<2{BKQ+3qtrJOR3u#ZdrhOd0hb!-v0a}_TiKF*JvuI;JT zebd_J?AuR2s`xrO_r5Fgx+cbeF<=aQn*sK0ky1IJS!2K$Fa{z8W z@go4SNVgYW%Pb)|kz%Zv1>_3Fg;Zilbvk0WkWPQ3aj{|+Fr>rj@Zt2yPA3%SpU(Xw z9}X7>G;0hP19=9P!fi$R|L*+xKc8fG#(**KuNZK}q?I&TlJ?e_;-uF`)DxzGY`--{oa5yGulFe3=f2`b5-&Gj>+dv>3)!tt=m!G@$(agy5IG#-N2_n6l>+P-Q*N0JCR{D*s z`5CVkWpfdxp)OX@0VT4IG%|deRgpUX(azi5M2jsmrgdfA% oIIj>aOVIIKF>-k;-hg|TFM~Cvz>g~M3FXIV2><{9 literal 0 HcmV?d00001 diff --git a/Assets/Spine/.DS_Store b/Assets/Spine/.DS_Store new file mode 100644 index 0000000000000000000000000000000000000000..5903de0dd72526677912476b1c3a338b176f472d GIT binary patch literal 6148 zcmeHKu};H44E2=?g1S`d!h&=XD@*?%ROy6RsKks)5L9YNh3Fo!u`%;6u<{>>4`5^E z`E1%IN5zIvWlO$y@!1#WT@=SeCIo8dn)z-PBjL&|AFcho$;&gWBey(qJ6JT1qtCohM`&-?GMN3l=-tIzCu=VM|F7z4(@rZRw< z&60EkZ8Qdq0b^jn0Dm7mlrdGT1jDBTLudhjZJ2{#&b8H=52tr_+M&2`ckJ(jJGoTQMq|Jjs57u7mtC&^!}a}tJ;<(%0b^jJ z7;x=ulnwAmT3e%s<67&X=TH{*s{|Jzn1oUcUoORa&>*mTo&ZzDN)Q%^{RjjaY%m7? Glz}hfkWpX& literal 0 HcmV?d00001 diff --git a/Assets/TextMesh Pro/.DS_Store b/Assets/TextMesh Pro/.DS_Store new file mode 100644 index 0000000000000000000000000000000000000000..00ec14e7caaf199acd2d5c9183566a4e575160df GIT binary patch literal 6148 zcmeHKy-ve05dI9QD6kY&NGwPZNQ_8*gHWY?fR=>~`XegQkkTIsF=c1r5#SAY0AOW> zm5G6wXW-6uOVXsMVyFk__BackingField: {fileID: 2122267604} + k__BackingField: {fileID: 2133561494} +--- !u!1001 &1976259500 +PrefabInstance: + m_ObjectHideFlags: 0 + serializedVersion: 2 + m_Modification: + serializedVersion: 3 + m_TransformParent: {fileID: 0} + m_Modifications: + - target: {fileID: 100100, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_Name + value: TutorialOverlayCanvas + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_Pivot.x + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_Pivot.y + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchorMax.x + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchorMax.y + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchorMin.x + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchorMin.y + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_SizeDelta.x + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_SizeDelta.y + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalPosition.x + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalPosition.y + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalPosition.z + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalRotation.w + value: 1 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalRotation.x + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalRotation.y + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalRotation.z + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchoredPosition.x + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchoredPosition.y + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalEulerAnglesHint.x + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalEulerAnglesHint.y + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100101, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalEulerAnglesHint.z + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100105, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_Alpha + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100701, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalScale.x + value: 1.2599487 + objectReference: {fileID: 0} + - target: {fileID: 100701, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalScale.y + value: 1.2599487 + objectReference: {fileID: 0} + - target: {fileID: 100701, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalScale.z + value: 1.2599487 + objectReference: {fileID: 0} + - target: {fileID: 100800, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_IsActive + value: 1 + objectReference: {fileID: 0} + - target: {fileID: 100901, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchorMax.x + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100901, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchorMax.y + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100901, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_SizeDelta.x + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 100901, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_SizeDelta.y + value: 710 + objectReference: {fileID: 0} + - target: {fileID: 100901, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalScale.x + value: 0.22292544 + objectReference: {fileID: 0} + - target: {fileID: 100901, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalScale.y + value: 0.22292544 + objectReference: {fileID: 0} + - target: {fileID: 100901, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalScale.z + value: 0.22292544 + objectReference: {fileID: 0} + - target: {fileID: 100901, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchoredPosition.x + value: -52 + objectReference: {fileID: 0} + - target: {fileID: 100901, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchoredPosition.y + value: 87 + objectReference: {fileID: 0} + - target: {fileID: 100903, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_Type + value: 1 + objectReference: {fileID: 0} + - target: {fileID: 100903, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_PreserveAspect + value: 1 + objectReference: {fileID: 0} + - target: {fileID: 101001, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchorMax.y + value: 1 + objectReference: {fileID: 0} + - target: {fileID: 101001, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchorMin.y + value: 1 + objectReference: {fileID: 0} + - target: {fileID: 101001, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_SizeDelta.x + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 101001, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_SizeDelta.y + value: 0 + objectReference: {fileID: 0} + - target: {fileID: 101001, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalScale.x + value: 5.2138014 + objectReference: {fileID: 0} + - target: {fileID: 101001, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalScale.y + value: 5.2138014 + objectReference: {fileID: 0} + - target: {fileID: 101001, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_LocalScale.z + value: 5.2138014 + objectReference: {fileID: 0} + - target: {fileID: 101001, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchoredPosition.x + value: 1913.019 + objectReference: {fileID: 0} + - target: {fileID: 101001, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_AnchoredPosition.y + value: -337.5 + objectReference: {fileID: 0} + - target: {fileID: 101003, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_text + value: Tutorial is not my name + objectReference: {fileID: 0} + - target: {fileID: 101003, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_fontSize + value: 60 + objectReference: {fileID: 0} + - target: {fileID: 101003, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_fontColor.b + value: 1 + objectReference: {fileID: 0} + - target: {fileID: 101003, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_fontColor.g + value: 1 + objectReference: {fileID: 0} + - target: {fileID: 101003, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_fontColor.r + value: 1 + objectReference: {fileID: 0} + - target: {fileID: 101003, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_fontColor32.rgba + value: 4294967295 + objectReference: {fileID: 0} + - target: {fileID: 3730188213376167672, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_Padding.m_Top + value: -35 + objectReference: {fileID: 0} + - target: {fileID: 3730188213376167672, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_Padding.m_Left + value: 261 + objectReference: {fileID: 0} + - target: {fileID: 3730188213376167672, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + propertyPath: m_Padding.m_Right + value: 303 + objectReference: {fileID: 0} + m_RemovedComponents: [] + m_RemovedGameObjects: [] + m_AddedGameObjects: [] + m_AddedComponents: [] + m_SourcePrefab: {fileID: 100100000, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} +--- !u!114 &1976259501 stripped +MonoBehaviour: + m_CorrespondingSourceObject: {fileID: 100106, guid: 7d10b17c0a1e4e7d9b2f8c6a5d4e3f22, type: 3} + m_PrefabInstance: {fileID: 1976259500} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 0} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: 4ecf127118699405ebcd0e0712d7373d, type: 3} + m_Name: + m_EditorClassIdentifier: +--- !u!1 &2122267603 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 2122267605} + - component: {fileID: 2122267604} + m_Layer: 0 + m_Name: IntroVideoPlayer + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!328 &2122267604 +VideoPlayer: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2122267603} + m_Enabled: 1 + m_VideoClip: {fileID: 32900000, guid: 94bb9480e86df4128b09488bd123a53e, type: 3} + m_TargetCameraAlpha: 1 + m_TargetCamera3DLayout: 0 + m_TargetCamera: {fileID: 82022334} + m_TargetTexture: {fileID: 8400000, guid: 5da879599920c456aa9dfc836a706075, type: 2} + m_TimeReference: 0 + m_TargetMaterialRenderer: {fileID: 0} + m_TargetMaterialProperty: + m_RenderMode: 2 + m_AspectRatio: 2 + m_DataSource: 0 + m_TimeUpdateMode: 1 + m_PlaybackSpeed: 1 + m_AudioOutputMode: 2 + m_TargetAudioSources: + - {fileID: 0} + m_DirectAudioVolumes: + - 1 + m_Url: + m_EnabledAudioTracks: 01 + m_DirectAudioMutes: 00 + m_ControlledAudioTrackCount: 1 + m_PlayOnAwake: 0 + m_SkipOnDrop: 0 + m_Looping: 0 + m_WaitForFirstFrame: 0 + m_FrameReadyEventEnabled: 0 + m_VideoShaders: [] +--- !u!4 &2122267605 +Transform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2122267603} + serializedVersion: 2 + m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} + m_LocalPosition: {x: 0, y: 0, z: 0} + m_LocalScale: {x: 1, y: 1, z: 1} + m_ConstrainProportionsScale: 0 + m_Children: [] + m_Father: {fileID: 0} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} +--- !u!1 &2133561494 +GameObject: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + serializedVersion: 6 + m_Component: + - component: {fileID: 2133561498} + - component: {fileID: 2133561497} + - component: {fileID: 2133561496} + - component: {fileID: 2133561495} + m_Layer: 5 + m_Name: IntroCanvas + m_TagString: Untagged + m_Icon: {fileID: 0} + m_NavMeshLayer: 0 + m_StaticEditorFlags: 0 + m_IsActive: 1 +--- !u!114 &2133561495 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2133561494} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: dc42784cf147c0c48a680349fa168899, type: 3} + m_Name: + m_EditorClassIdentifier: UnityEngine.UI::UnityEngine.UI.GraphicRaycaster + m_IgnoreReversedGraphics: 1 + m_BlockingObjects: 0 + m_BlockingMask: + serializedVersion: 2 + m_Bits: 4294967295 +--- !u!114 &2133561496 +MonoBehaviour: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2133561494} + m_Enabled: 1 + m_EditorHideFlags: 0 + m_Script: {fileID: 11500000, guid: 0cd44c1031e13a943bb63640046fad76, type: 3} + m_Name: + m_EditorClassIdentifier: UnityEngine.UI::UnityEngine.UI.CanvasScaler + m_UiScaleMode: 1 + m_ReferencePixelsPerUnit: 100 + m_ScaleFactor: 1 + m_ReferenceResolution: {x: 1920, y: 1080} + m_ScreenMatchMode: 0 + m_MatchWidthOrHeight: 0.5 + m_PhysicalUnit: 3 + m_FallbackScreenDPI: 96 + m_DefaultSpriteDPI: 96 + m_DynamicPixelsPerUnit: 1 + m_PresetInfoIsWorld: 0 +--- !u!223 &2133561497 +Canvas: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2133561494} + m_Enabled: 1 + serializedVersion: 3 + m_RenderMode: 0 + m_Camera: {fileID: 0} + m_PlaneDistance: 100 + m_PixelPerfect: 0 + m_ReceivesEvents: 1 + m_OverrideSorting: 0 + m_OverridePixelPerfect: 0 + m_SortingBucketNormalizedSize: 0 + m_VertexColorAlwaysGammaSpace: 1 + m_UseReflectionProbes: 0 + m_AdditionalShaderChannelsFlag: 0 + m_UpdateRectTransformForStandalone: 0 + m_SortingLayerID: 0 + m_SortingOrder: 1000 + m_TargetDisplay: 0 +--- !u!224 &2133561498 +RectTransform: + m_ObjectHideFlags: 0 + m_CorrespondingSourceObject: {fileID: 0} + m_PrefabInstance: {fileID: 0} + m_PrefabAsset: {fileID: 0} + m_GameObject: {fileID: 2133561494} + m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} + m_LocalPosition: {x: 0, y: 0, z: 0} + m_LocalScale: {x: 0, y: 0, z: 0} + m_ConstrainProportionsScale: 0 + m_Children: + - {fileID: 202998925} + m_Father: {fileID: 0} + m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} + m_AnchorMin: {x: 0, y: 0} + m_AnchorMax: {x: 0, y: 0} + m_AnchoredPosition: {x: 0, y: 0} + m_SizeDelta: {x: 0, y: 0} + m_Pivot: {x: 0, y: 0} +--- !u!1660057539 &9223372036854775807 +SceneRoots: + m_ObjectHideFlags: 0 + m_Roots: + - {fileID: 519420032} + - {fileID: 94039067} + - {fileID: 82022335} + - {fileID: 1798580248} + - {fileID: 2122267605} + - {fileID: 1890425865} + - {fileID: 2133561498} + - {fileID: 109717503} + - {fileID: 1424266587} + - {fileID: 196669903} + - {fileID: 673724413} + - {fileID: 1156238481} + - {fileID: 680382929} + - {fileID: 1976259500} + - {fileID: 1546866195} diff --git a/Assets/_Recovery/0.unity.meta b/Assets/_Recovery/0.unity.meta new file mode 100644 index 0000000..3bddccc --- /dev/null +++ b/Assets/_Recovery/0.unity.meta @@ -0,0 +1,7 @@ +fileFormatVersion: 2 +guid: 90078c122328b4902a1e67255b30525a +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: