internal static void DeserializeBeatmapData(IReadonlyBeatmapData beatmapData) { NoodleObjectDatas = new Dictionary <BeatmapObjectData, NoodleObjectData>(); foreach (BeatmapObjectData beatmapObjectData in beatmapData.beatmapObjectsData) { NoodleObjectData noodleObjectData; dynamic customData; switch (beatmapObjectData) { case CustomNoteData customNoteData: customData = customNoteData.customData; noodleObjectData = ProcessCustomNote(customData); break; case CustomObstacleData customObstacleData: customData = customObstacleData.customData; noodleObjectData = ProcessCustomObstacle(customData); break; case CustomWaypointData customWaypointData: customData = customWaypointData.customData; noodleObjectData = new NoodleObjectData(); break; default: continue; } FinalizeCustomObject(customData, noodleObjectData, beatmapData); NoodleObjectDatas.Add(beatmapObjectData, noodleObjectData); } }
private static void FinalizeCustomObject(dynamic dynData, NoodleObjectData noodleObjectData, IReadonlyBeatmapData beatmapData) { dynamic rotation = Trees.at(dynData, ROTATION); if (rotation != null) { if (rotation is List <object> list) { IEnumerable <float> rot = list?.Select(n => Convert.ToSingle(n)); noodleObjectData.WorldRotationQuaternion = Quaternion.Euler(rot.ElementAt(0), rot.ElementAt(1), rot.ElementAt(2)); } else { noodleObjectData.WorldRotationQuaternion = Quaternion.Euler(0, (float)rotation, 0); } } IEnumerable <float> localrot = ((List <object>)Trees.at(dynData, LOCALROTATION))?.Select(n => Convert.ToSingle(n)); if (localrot != null) { noodleObjectData.LocalRotationQuaternion = Quaternion.Euler(localrot.ElementAt(0), localrot.ElementAt(1), localrot.ElementAt(2)); } noodleObjectData.Track = AnimationHelper.GetTrackPreload(dynData, beatmapData); dynamic animationObjectDyn = Trees.at(dynData, "_animation"); Dictionary <string, PointDefinition> pointDefinitions = Trees.at(((CustomBeatmapData)beatmapData).customData, "pointDefinitions"); AnimationHelper.GetAllPointData( animationObjectDyn, pointDefinitions, out PointDefinition localPosition, out PointDefinition localRotation, out PointDefinition localScale, out PointDefinition localLocalRotation, out PointDefinition localDissolve, out PointDefinition localDissolveArrow, out PointDefinition localCuttable, out PointDefinition localDefinitePosition); NoodleObjectData.AnimationObjectData animationObjectData = new NoodleObjectData.AnimationObjectData { LocalPosition = localPosition, LocalRotation = localRotation, LocalScale = localScale, LocalLocalRotation = localLocalRotation, LocalDissolve = localDissolve, LocalDissolveArrow = localDissolveArrow, LocalCuttable = localCuttable, LocalDefinitePosition = localDefinitePosition, }; noodleObjectData.AnimationObject = animationObjectData; noodleObjectData.Cuttable = Trees.at(dynData, CUTTABLE); noodleObjectData.Fake = Trees.at(dynData, FAKENOTE); IEnumerable <float?> position = ((List <object>)Trees.at(dynData, POSITION))?.Select(n => n.ToNullableFloat()); noodleObjectData.StartX = position?.ElementAtOrDefault(0); noodleObjectData.StartY = position?.ElementAtOrDefault(1); noodleObjectData.NJS = (float?)Trees.at(dynData, NOTEJUMPSPEED); noodleObjectData.SpawnOffset = (float?)Trees.at(dynData, NOTESPAWNOFFSET); noodleObjectData.AheadTimeInternal = (float?)Trees.at(dynData, "aheadTime"); }
internal static void OnDeserializeBeatmapData(CustomDataDeserializer.DeserializeBeatmapEventArgs eventArgs) { if (eventArgs.IsMultiplayer) { return; } CustomBeatmapData beatmapData = eventArgs.BeatmapData; _noodleObjectDatas = new Dictionary <BeatmapObjectData, IBeatmapObjectDataCustomData>(); Dictionary <string, PointDefinition> pointDefinitions = beatmapData.GetBeatmapPointDefinitions(); Dictionary <string, Track> beatmapTracks = beatmapData.GetBeatmapTracks(); foreach (BeatmapObjectData beatmapObjectData in eventArgs.BeatmapObjectDatas) { try { NoodleObjectData noodleObjectData; Dictionary <string, object?> customData; switch (beatmapObjectData) { case CustomObstacleData customObstacleData: customData = customObstacleData.customData; noodleObjectData = ProcessCustomObstacle(customData); break; case CustomNoteData customNoteData: customData = customNoteData.customData; noodleObjectData = ProcessCustomNote(customData); break; case CustomWaypointData customWaypointData: customData = customWaypointData.customData; noodleObjectData = new NoodleObjectData(); break; default: continue; } FinalizeCustomObject(customData, noodleObjectData, pointDefinitions, beatmapTracks); _noodleObjectDatas.Add(beatmapObjectData, noodleObjectData); } catch (Exception e) { CustomDataDeserializer.LogFailure(Plugin.Logger, e, beatmapObjectData); } } _noodleEventDatas = new Dictionary <CustomEventData, ICustomEventCustomData>(); foreach (CustomEventData customEventData in eventArgs.CustomEventDatas) { try { ICustomEventCustomData noodleEventData; Dictionary <string, object?> data = customEventData.data; switch (customEventData.type) { case ASSIGNPLAYERTOTRACK: noodleEventData = new NoodlePlayerTrackEventData(GetTrack(customEventData.data, beatmapTracks) ?? throw new InvalidOperationException("Track was not defined.")); break; case ASSIGNTRACKPARENT: noodleEventData = ProcessParentTrackEvent(data, beatmapTracks); break; default: continue; } _noodleEventDatas.Add(customEventData, noodleEventData); } catch (Exception e) { CustomDataDeserializer.LogFailure(Plugin.Logger, e, customEventData); } } }
private static void FinalizeCustomObject(Dictionary <string, object?> dynData, NoodleObjectData noodleObjectData, Dictionary <string, PointDefinition> pointDefinitions, Dictionary <string, Track> beatmapTracks) { object?rotation = dynData.Get <object>(ROTATION); if (rotation != null) { if (rotation is List <object> list) { IEnumerable <float> rot = list.Select(n => Convert.ToSingle(n)); noodleObjectData.WorldRotationQuaternion = Quaternion.Euler(rot.ElementAt(0), rot.ElementAt(1), rot.ElementAt(2)); } else { noodleObjectData.WorldRotationQuaternion = Quaternion.Euler(0, Convert.ToSingle(rotation), 0); } } IEnumerable <float>?localrot = dynData.Get <List <object> >(LOCALROTATION)?.Select(n => Convert.ToSingle(n)); if (localrot != null) { noodleObjectData.LocalRotationQuaternion = Quaternion.Euler(localrot.ElementAt(0), localrot.ElementAt(1), localrot.ElementAt(2)); } noodleObjectData.Track = GetTrackArray(dynData, beatmapTracks); Dictionary <string, object?>?animationObjectDyn = dynData.Get <Dictionary <string, object?> >(ANIMATION); if (animationObjectDyn != null) { NoodleObjectData.AnimationObjectData animationObjectData = new NoodleObjectData.AnimationObjectData { LocalPosition = TryGetPointData(animationObjectDyn, POSITION, pointDefinitions), LocalRotation = TryGetPointData(animationObjectDyn, ROTATION, pointDefinitions), LocalScale = TryGetPointData(animationObjectDyn, SCALE, pointDefinitions), LocalLocalRotation = TryGetPointData(animationObjectDyn, LOCALROTATION, pointDefinitions), LocalDissolve = TryGetPointData(animationObjectDyn, DISSOLVE, pointDefinitions), LocalDissolveArrow = TryGetPointData(animationObjectDyn, DISSOLVEARROW, pointDefinitions), LocalCuttable = TryGetPointData(animationObjectDyn, CUTTABLE, pointDefinitions), LocalDefinitePosition = TryGetPointData(animationObjectDyn, DEFINITEPOSITION, pointDefinitions), }; noodleObjectData.AnimationObject = animationObjectData; } noodleObjectData.Cuttable = dynData.Get <bool?>(CUTTABLE); noodleObjectData.Fake = dynData.Get <bool?>(FAKENOTE); IEnumerable <float?>?position = dynData.GetNullableFloats(POSITION); noodleObjectData.StartX = position?.ElementAtOrDefault(0); noodleObjectData.StartY = position?.ElementAtOrDefault(1); noodleObjectData.NJS = dynData.Get <float?>(NOTEJUMPSPEED); noodleObjectData.SpawnOffset = dynData.Get <float?>(NOTESPAWNOFFSET); noodleObjectData.AheadTimeInternal = dynData.Get <float?>("aheadTime"); }