feat: SongCreator 씬 완성 — Beat Sage URL 지원, info.dat 메타데이터 자동 추출
- BeatSageUploader: audio_url 지원(UploadFromUrl), PollAndDownload 공통화, ZIP 500 오류 3회 재시도 - BeatSageConverter: info.dat 파싱(SongMetadata), BPM 자동 감지 → 노트 타이밍 변환에 적용 - SongCreatorManager: title/BPM 필수 입력 제거, 난이도 4개 자동 선택, GenerateFlowFromUrl 버그 수정 - NasPublisher: audioPath null 허용(URL 흐름에서 로컬 파일 없는 경우 스킵) - .gitignore/.gitattributes 초기 설정 Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,110 @@
|
||||
using UnityEngine;
|
||||
using Platinio.UI;
|
||||
using VRBeats.Events;
|
||||
|
||||
namespace VRBeats
|
||||
{
|
||||
public class Carousel : MonoBehaviour
|
||||
{
|
||||
[SerializeField] private RectTransform viewRect = null;
|
||||
[SerializeField] private float moveTime = 1.0f;
|
||||
[SerializeField] private Ease ease = Ease.EaseOutExpo;
|
||||
[SerializeField] private OnIntValueChange onIndexValueChange = null;
|
||||
|
||||
|
||||
private RectTransform[] elements = null;
|
||||
|
||||
public OnIntValueChange OnIndexValueChange
|
||||
{
|
||||
get
|
||||
{
|
||||
return onIndexValueChange;
|
||||
}
|
||||
}
|
||||
|
||||
public int CurrentIndex
|
||||
{
|
||||
get
|
||||
{
|
||||
return currentIndex;
|
||||
}
|
||||
|
||||
private set
|
||||
{
|
||||
currentIndex = value;
|
||||
onIndexValueChange.Invoke(currentIndex);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
private int currentIndex = 0;
|
||||
private bool isBusy = false;
|
||||
|
||||
private void Start()
|
||||
{
|
||||
CurrentIndex = transform.childCount - 1;
|
||||
SetupCarouselElements();
|
||||
}
|
||||
|
||||
private void SetupCarouselElements()
|
||||
{
|
||||
elements = new RectTransform[transform.childCount];
|
||||
//this is the canvas center
|
||||
float x = 0.5f;
|
||||
|
||||
for (int n = 0; n < transform.childCount; n++)
|
||||
{
|
||||
|
||||
elements[n] = transform.GetChild(n).GetComponent<RectTransform>();
|
||||
elements[n].anchoredPosition = elements[n].FromAbsolutePositionToAnchoredPosition(new Vector2(x, 0.5f) , viewRect);
|
||||
x -= 1.0f;
|
||||
}
|
||||
}
|
||||
|
||||
public void MoveLeft()
|
||||
{
|
||||
if (currentIndex + 1 >= transform.childCount || isBusy)
|
||||
return;
|
||||
|
||||
CurrentIndex++;
|
||||
isBusy = true;
|
||||
|
||||
for (int n = 0; n < transform.childCount; n++)
|
||||
{
|
||||
Vector2 currentPos = elements[n].FromAnchoredPositionToAbsolutePosition(viewRect);
|
||||
elements[n].MoveUI(currentPos + new Vector2(-1.0f , 0.0f ) , viewRect , moveTime ).SetOnComplete(delegate { isBusy = false; }).SetEase(ease);
|
||||
}
|
||||
}
|
||||
|
||||
public void MoveRight()
|
||||
{
|
||||
|
||||
if (currentIndex - 1 < 0 || isBusy)
|
||||
return;
|
||||
|
||||
|
||||
CurrentIndex--;
|
||||
isBusy = true;
|
||||
for (int n = 0; n < transform.childCount; n++)
|
||||
{
|
||||
Vector2 currentPos = elements[n].FromAnchoredPositionToAbsolutePosition(viewRect);
|
||||
elements[n].MoveUI(currentPos + new Vector2(1.0f, 0.0f), viewRect, moveTime).SetOnComplete(delegate { isBusy = false; }).SetEase(ease);
|
||||
}
|
||||
}
|
||||
|
||||
public void Focus(int index)
|
||||
{
|
||||
int offset = currentIndex - index;
|
||||
CurrentIndex = index;
|
||||
isBusy = true;
|
||||
|
||||
for (int n = 0; n < transform.childCount; n++)
|
||||
{
|
||||
Vector2 currentPos = elements[n].FromAnchoredPositionToAbsolutePosition(viewRect);
|
||||
elements[n].MoveUI(currentPos + new Vector2(1.0f * offset, 0.0f), viewRect, moveTime).SetOnComplete(delegate { isBusy = false; }).SetEase(ease);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
fileFormatVersion: 2
|
||||
guid: bba6b1c374675f240a81bc38489d0e40
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
AssetOrigin:
|
||||
serializedVersion: 1
|
||||
productId: 168243
|
||||
packageName: VR Beats Kit
|
||||
packageVersion: 2.0
|
||||
assetPath: Assets/VRBeatsKit/Scripts/UI/Carousel.cs
|
||||
uploadId: 546658
|
||||
@@ -0,0 +1,61 @@
|
||||
using UnityEngine;
|
||||
using Platinio.TweenEngine;
|
||||
using TMPro;
|
||||
|
||||
namespace VRBeats
|
||||
{
|
||||
public class FinalScoreLabel : MonoBehaviour
|
||||
{
|
||||
[SerializeField] private TextMeshProUGUI scoreText = null;
|
||||
[SerializeField] private float scoreFadeTime = 10.0f;
|
||||
[SerializeField] private int length = 10;
|
||||
|
||||
private string initialValue = "";
|
||||
private ScoreManager scoreManager = null;
|
||||
|
||||
private void Awake()
|
||||
{
|
||||
for (int n = 0; n < length; n++)
|
||||
{
|
||||
initialValue += "0";
|
||||
}
|
||||
|
||||
scoreManager = FindObjectOfType<ScoreManager>();
|
||||
|
||||
}
|
||||
|
||||
public void ShowScore()
|
||||
{
|
||||
PlatinioTween.instance.ValueTween( 0.0f , scoreManager.CurrentScore , scoreFadeTime).SetOnUpdateFloat(delegate (float v)
|
||||
{
|
||||
SetScore( (int)v );
|
||||
});
|
||||
}
|
||||
|
||||
public void ResetValues()
|
||||
{
|
||||
gameObject.CancelAllTweens();
|
||||
scoreText.text = initialValue;
|
||||
}
|
||||
|
||||
|
||||
private void SetScore(int score)
|
||||
{
|
||||
if (this.scoreText == null)
|
||||
return;
|
||||
|
||||
string scoreText = score.ToString();
|
||||
int addLength = Mathf.Max( length - scoreText.Length , 0);
|
||||
string addZeros = "";
|
||||
for (int n = 0; n < addLength; n++)
|
||||
{
|
||||
addZeros += "0";
|
||||
}
|
||||
|
||||
this.scoreText.text = addZeros + scoreText;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 6ad0599dde409f84a8031cf155e229e4
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
AssetOrigin:
|
||||
serializedVersion: 1
|
||||
productId: 168243
|
||||
packageName: VR Beats Kit
|
||||
packageVersion: 2.0
|
||||
assetPath: Assets/VRBeatsKit/Scripts/UI/FinalScoreLabel.cs
|
||||
uploadId: 546658
|
||||
@@ -0,0 +1,24 @@
|
||||
using UnityEngine;
|
||||
using UnityEngine.SceneManagement;
|
||||
using UnityEngine.UI;
|
||||
|
||||
namespace VRBeats
|
||||
{
|
||||
public class LoadSceneButton : MonoBehaviour
|
||||
{
|
||||
[SerializeField] private Button button = null;
|
||||
[SerializeField] private string sceneName = "";
|
||||
|
||||
private void Start()
|
||||
{
|
||||
button.onClick.AddListener(OnClick);
|
||||
}
|
||||
|
||||
private void OnClick()
|
||||
{
|
||||
SceneManager.LoadScene(sceneName);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 504eaffe3c185bf469313a589c4026d0
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
AssetOrigin:
|
||||
serializedVersion: 1
|
||||
productId: 168243
|
||||
packageName: VR Beats Kit
|
||||
packageVersion: 2.0
|
||||
assetPath: Assets/VRBeatsKit/Scripts/UI/LoadSceneButton.cs
|
||||
uploadId: 546658
|
||||
@@ -0,0 +1,52 @@
|
||||
using Platinio.TweenEngine;
|
||||
using UnityEngine;
|
||||
using UnityEngine.Events;
|
||||
|
||||
namespace VRBeats
|
||||
{
|
||||
public class Popup : MonoBehaviour
|
||||
{
|
||||
[SerializeField] private CanvasGroup cg = null;
|
||||
[SerializeField] private float fadeTime = 1.0f;
|
||||
[SerializeField] private Ease fadeEase = Ease.Linear;
|
||||
[SerializeField] private UnityEvent onShow = null;
|
||||
[SerializeField] private UnityEvent onHide = null;
|
||||
|
||||
private void Awake()
|
||||
{
|
||||
cg.alpha = 0.0f;
|
||||
cg.interactable = false;
|
||||
cg.blocksRaycasts = false;
|
||||
}
|
||||
|
||||
public void Show()
|
||||
{
|
||||
SetCanvasGroupInteractable(cg, true);
|
||||
FadeTween(1.0f).SetOnComplete( onShow.Invoke );
|
||||
}
|
||||
|
||||
public void Hide()
|
||||
{
|
||||
SetCanvasGroupInteractable(cg, false);
|
||||
FadeTween(0.0f).SetOnComplete( onHide.Invoke );
|
||||
}
|
||||
|
||||
private void SetCanvasGroupInteractable(CanvasGroup cg , bool state)
|
||||
{
|
||||
cg.interactable = state;
|
||||
cg.blocksRaycasts = state;
|
||||
}
|
||||
|
||||
private BaseTween FadeTween(float alpha)
|
||||
{
|
||||
gameObject.CancelAllTweens();
|
||||
return cg.Fade(alpha, fadeTime).SetEase(fadeEase).SetOwner(gameObject).SetOnComplete(delegate
|
||||
{
|
||||
cg.interactable = true;
|
||||
cg.blocksRaycasts = true;
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
fileFormatVersion: 2
|
||||
guid: f88dcf25cb49c7648b23e17f69accd39
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
AssetOrigin:
|
||||
serializedVersion: 1
|
||||
productId: 168243
|
||||
packageName: VR Beats Kit
|
||||
packageVersion: 2.0
|
||||
assetPath: Assets/VRBeatsKit/Scripts/UI/Popup.cs
|
||||
uploadId: 546658
|
||||
@@ -0,0 +1,26 @@
|
||||
using UnityEngine;
|
||||
using System.Collections;
|
||||
|
||||
namespace VRBeats
|
||||
{
|
||||
public class SaberSelectionPanel : MonoBehaviour
|
||||
{
|
||||
[SerializeField] private Carousel saberCarousel = null;
|
||||
|
||||
private IEnumerator Start()
|
||||
{
|
||||
|
||||
yield return new WaitForEndOfFrame();
|
||||
|
||||
saberCarousel.Focus( VR_SaberContainer.SelectedSaberIndex );
|
||||
saberCarousel.OnIndexValueChange.AddListener(OnSaberSelectionIndexChange);
|
||||
}
|
||||
|
||||
private void OnSaberSelectionIndexChange(int index)
|
||||
{
|
||||
VR_SaberContainer.SetSelectedSaberIndex(index);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
fileFormatVersion: 2
|
||||
guid: fcdc4aebd7df33d4b905814a0a81460d
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
AssetOrigin:
|
||||
serializedVersion: 1
|
||||
productId: 168243
|
||||
packageName: VR Beats Kit
|
||||
packageVersion: 2.0
|
||||
assetPath: Assets/VRBeatsKit/Scripts/UI/SaberSelectionPanel.cs
|
||||
uploadId: 546658
|
||||
@@ -0,0 +1,185 @@
|
||||
using UnityEngine;
|
||||
using UnityEngine.UI;
|
||||
using Platinio.TweenEngine;
|
||||
using VRBeats.ScriptableEvents;
|
||||
|
||||
namespace VRBeats
|
||||
{
|
||||
public class ScoreManager : MonoBehaviour
|
||||
{
|
||||
[SerializeField] private Text multiplierLabel = null;
|
||||
[SerializeField] private Text scoreLabel = null;
|
||||
[SerializeField] private Image multiplierLoader = null;
|
||||
[SerializeField] private float scoreFollowTime = 1.0f;
|
||||
[SerializeField] private CanvasGroup canvasGroup = null;
|
||||
[SerializeField] private GameEvent onGameOver = null;
|
||||
|
||||
private int maxMultiplier = 0;
|
||||
private int scorePerHit = 0;
|
||||
private int currentScore = 0;
|
||||
private int currentMultiplier = 0;
|
||||
private int toNextMultiplierIncrease = 2;
|
||||
private int acumulateCorrectSlices = 0;
|
||||
private int acumulateErrors = 0;
|
||||
private int errorLimit = 0;
|
||||
private float visualScore = 0.0f;
|
||||
private int scoreTweenID = -1;
|
||||
private int loaderTweenID = -1;
|
||||
|
||||
private bool destroyed = false;
|
||||
|
||||
public int CurrentScore
|
||||
{
|
||||
get
|
||||
{
|
||||
return currentScore;
|
||||
}
|
||||
}
|
||||
|
||||
private void Awake()
|
||||
{
|
||||
maxMultiplier = VR_BeatManager.instance.GameSettings.MaxMultiplier;
|
||||
scorePerHit = VR_BeatManager.instance.GameSettings.ScorePerHit;
|
||||
errorLimit = VR_BeatManager.instance.GameSettings.ErrorLimit;
|
||||
multiplierLoader.fillAmount = 0.0f;
|
||||
}
|
||||
|
||||
public void OnGameOver()
|
||||
{
|
||||
gameObject.CancelAllTweens();
|
||||
canvasGroup.Fade(0.0f, 0.5f).SetEase(Ease.EaseOutExpo).SetOwner(gameObject);
|
||||
}
|
||||
|
||||
public void OnGameRestart()
|
||||
{
|
||||
ResetThisComponent();
|
||||
gameObject.CancelAllTweens();
|
||||
canvasGroup.Fade(1.0f, 0.5f).SetEase(Ease.EaseOutExpo).SetOwner(gameObject);
|
||||
}
|
||||
|
||||
public void ResetThisComponent()
|
||||
{
|
||||
currentMultiplier = 0;
|
||||
currentScore = 0;
|
||||
acumulateCorrectSlices = 0;
|
||||
visualScore = 0;
|
||||
acumulateErrors = 0;
|
||||
toNextMultiplierIncrease = 2;
|
||||
}
|
||||
|
||||
|
||||
|
||||
private void Update()
|
||||
{
|
||||
UpdateUI();
|
||||
}
|
||||
|
||||
public void OnCorrectSlice()
|
||||
{
|
||||
if (destroyed)
|
||||
return;
|
||||
|
||||
acumulateErrors = 0;
|
||||
acumulateCorrectSlices++;
|
||||
currentScore += scorePerHit + (scorePerHit * currentMultiplier);
|
||||
|
||||
CancelTweenById(scoreTweenID);
|
||||
scoreTweenID = PlatinioTween.instance.ValueTween(visualScore, currentScore, scoreFollowTime).SetEase(Ease.EaseOutExpo).SetOnUpdateFloat(delegate (float value)
|
||||
{
|
||||
visualScore = value;
|
||||
}).ID;
|
||||
|
||||
UpdateMultiplierLoaderValue();
|
||||
|
||||
if (acumulateCorrectSlices >= toNextMultiplierIncrease)
|
||||
{
|
||||
IncreaseMultiplier();
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
private void CancelTweenById(int id)
|
||||
{
|
||||
if(id != -1)
|
||||
PlatinioTween.instance.CancelTween(id);
|
||||
}
|
||||
|
||||
private void UpdateMultiplierLoaderValue()
|
||||
{
|
||||
if (destroyed)
|
||||
return;
|
||||
|
||||
float multiplierLoaderValue = (float)acumulateCorrectSlices / (float)toNextMultiplierIncrease;
|
||||
|
||||
|
||||
CancelTweenById(loaderTweenID);
|
||||
loaderTweenID = PlatinioTween.instance.ValueTween(multiplierLoader.fillAmount, multiplierLoaderValue, 1.0f).SetEase(Ease.EaseOutExpo).SetOnUpdateFloat(delegate (float value)
|
||||
{
|
||||
if(multiplierLoader != null)
|
||||
multiplierLoader.fillAmount = value;
|
||||
}).SetOwner(multiplierLoader.gameObject).ID;
|
||||
}
|
||||
|
||||
public void OnIncorrectSlice()
|
||||
{
|
||||
if (destroyed)
|
||||
return;
|
||||
|
||||
acumulateErrors++;
|
||||
acumulateCorrectSlices = 0;
|
||||
currentMultiplier = 0;
|
||||
toNextMultiplierIncrease = 2;
|
||||
|
||||
UpdateMultiplierLoaderValue();
|
||||
|
||||
if (acumulateErrors > errorLimit)
|
||||
{
|
||||
onGameOver.Invoke();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void UpdateUI()
|
||||
{
|
||||
if (destroyed)
|
||||
return;
|
||||
|
||||
multiplierLabel.text = currentMultiplier.ToString();
|
||||
scoreLabel.text = Mathf.CeilToInt( visualScore ).ToString();
|
||||
}
|
||||
|
||||
private void IncreaseMultiplier()
|
||||
{
|
||||
if (destroyed)
|
||||
return;
|
||||
|
||||
acumulateCorrectSlices = 0;
|
||||
currentMultiplier = Mathf.Min( currentMultiplier + 1 , maxMultiplier );
|
||||
toNextMultiplierIncrease = (currentMultiplier + 1) * 2;
|
||||
|
||||
PlatinioTween.instance.CancelTween(multiplierLoader.gameObject);
|
||||
|
||||
PlatinioTween.instance.ValueTween(multiplierLoader.fillAmount, 1.0f, 1.0f).SetEase(Ease.EaseOutExpo).SetOnUpdateFloat(delegate (float value)
|
||||
{
|
||||
if(multiplierLoader != null)
|
||||
multiplierLoader.fillAmount = value;
|
||||
}).SetOwner(multiplierLoader.gameObject).SetOnComplete( delegate
|
||||
{
|
||||
if (multiplierLabel != null)
|
||||
{
|
||||
PlatinioTween.instance.ValueTween(multiplierLoader.fillAmount, 0.0f, 0.5f).SetEase(Ease.EaseOutExpo).SetOnUpdateFloat(delegate (float value)
|
||||
{
|
||||
if (multiplierLoader != null)
|
||||
multiplierLoader.fillAmount = value;
|
||||
}).SetOwner(multiplierLoader.gameObject);
|
||||
}
|
||||
|
||||
} );
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
fileFormatVersion: 2
|
||||
guid: be5904815dd86264b9f5dbb4cb4853a9
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
AssetOrigin:
|
||||
serializedVersion: 1
|
||||
productId: 168243
|
||||
packageName: VR Beats Kit
|
||||
packageVersion: 2.0
|
||||
assetPath: Assets/VRBeatsKit/Scripts/UI/ScoreManager.cs
|
||||
uploadId: 546658
|
||||
@@ -0,0 +1,205 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections;
|
||||
using UnityEngine;
|
||||
using UnityEngine.UI;
|
||||
using UnityEngine.EventSystems;
|
||||
using Platinio.UI;
|
||||
|
||||
/// <summary>
|
||||
/// Code to handle generic scroll list, like leaderboards or achievements
|
||||
/// </summary>
|
||||
public class Scroller : MonoBehaviour , IPointerDownHandler , IPointerUpHandler , IPointerExitHandler
|
||||
{
|
||||
public enum ScrollMode
|
||||
{
|
||||
Horizontal,
|
||||
Vertical
|
||||
}
|
||||
|
||||
#region INSPECTOR
|
||||
[SerializeField] protected ScrollRect scroll = null;
|
||||
[SerializeField] protected GridLayoutGroup gridLayout = null;
|
||||
[SerializeField] protected RectTransform viewRect = null;
|
||||
[SerializeField] protected ScrollMode scrollMode = ScrollMode.Horizontal;
|
||||
[SerializeField] protected bool shouldAling = false;
|
||||
[SerializeField] protected float scrollVelocityThreshold = 0.2f;
|
||||
#endregion
|
||||
|
||||
#region PRIVATE
|
||||
private List<GameObject> elements = new List<GameObject>();
|
||||
private RectTransform contentRect = null;
|
||||
private Coroutine shouldAlingCoroutine = null;
|
||||
private float minSize = 0.0f;
|
||||
private bool userInteraction = false;
|
||||
#endregion
|
||||
|
||||
protected RectTransform scrollRect = null;
|
||||
protected Action onReachEndOfList = null;
|
||||
|
||||
public GridLayoutGroup GridLayout
|
||||
{
|
||||
get { return gridLayout; }
|
||||
}
|
||||
|
||||
protected virtual void Awake()
|
||||
{
|
||||
scrollRect = scroll.GetComponent<RectTransform>();
|
||||
contentRect = gridLayout.GetComponent<RectTransform>();
|
||||
minSize = contentRect.rect.size.y;
|
||||
|
||||
SetupScrollingComponets();
|
||||
|
||||
//set listener for end of list
|
||||
scroll.onValueChanged.AddListener( delegate (Vector2 v)
|
||||
{
|
||||
if (userInteraction && scroll.velocity.magnitude > scrollVelocityThreshold)
|
||||
{
|
||||
|
||||
if (shouldAlingCoroutine != null)
|
||||
StopCoroutine( shouldAlingCoroutine );
|
||||
shouldAlingCoroutine = StartCoroutine( ShouldAlingRoutine() );
|
||||
}
|
||||
|
||||
|
||||
if (GetNormalizedPosition() <= 0.0f && onReachEndOfList != null)
|
||||
{
|
||||
onReachEndOfList();
|
||||
}
|
||||
} );
|
||||
}
|
||||
|
||||
private void Start()
|
||||
{
|
||||
GetStartingElements();
|
||||
ResizeContentRect();
|
||||
}
|
||||
|
||||
private void GetStartingElements()
|
||||
{
|
||||
for (int n = 0; n < gridLayout.transform.childCount; n++)
|
||||
{
|
||||
AddElement( gridLayout.transform.GetChild(n).gameObject );
|
||||
}
|
||||
}
|
||||
|
||||
public float GetNormalizedPosition()
|
||||
{
|
||||
return scrollMode == ScrollMode.Horizontal ? scroll.horizontalNormalizedPosition : scroll.verticalNormalizedPosition;
|
||||
}
|
||||
|
||||
private void SetupScrollingComponets()
|
||||
{
|
||||
gridLayout.startAxis = scrollMode == ScrollMode.Horizontal ? GridLayoutGroup.Axis.Horizontal : GridLayoutGroup.Axis.Vertical;
|
||||
scroll.vertical = scrollMode == ScrollMode.Vertical;
|
||||
scroll.horizontal = scrollMode == ScrollMode.Horizontal;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// add element to scroll list
|
||||
/// </summary>
|
||||
public void AddElement(GameObject element)
|
||||
{
|
||||
element.transform.parent = gridLayout.transform;
|
||||
element.transform.localScale = Vector3.one;
|
||||
elements.Add( element );
|
||||
ResizeContentRect();
|
||||
}
|
||||
|
||||
private IEnumerator ShouldAlingRoutine()
|
||||
{
|
||||
while (scroll.velocity.magnitude > 0.00001f)
|
||||
{
|
||||
yield return new WaitForEndOfFrame();
|
||||
}
|
||||
|
||||
AlingToCloserElement();
|
||||
}
|
||||
|
||||
private void AlingToCloserElement()
|
||||
{
|
||||
userInteraction = false;
|
||||
|
||||
Vector2 pos = elements[0].GetComponent<RectTransform>().FromAnchoredPositionToAbsolutePosition(viewRect);
|
||||
Debug.Log(pos);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Resizes the content rect to fit new elements
|
||||
/// </summary>
|
||||
protected void ResizeContentRect()
|
||||
{
|
||||
|
||||
float size = 0.0f;
|
||||
|
||||
if (scrollMode == ScrollMode.Horizontal)
|
||||
{
|
||||
size = ((gridLayout.cellSize.x + gridLayout.spacing.x) * elements.Count) + gridLayout.padding.left;
|
||||
}
|
||||
else if (scrollMode == ScrollMode.Vertical)
|
||||
{
|
||||
size = (( gridLayout.cellSize.y + gridLayout.spacing.y ) * elements.Count) + gridLayout.padding.top;
|
||||
}
|
||||
|
||||
|
||||
//resize contentRect to fit new element
|
||||
if (size > minSize)
|
||||
{
|
||||
if (scrollMode == ScrollMode.Vertical)
|
||||
{
|
||||
contentRect.SetSizeWithCurrentAnchors( RectTransform.Axis.Vertical, size );
|
||||
}
|
||||
else if (scrollMode == ScrollMode.Horizontal)
|
||||
{
|
||||
contentRect.SetSizeWithCurrentAnchors( RectTransform.Axis.Horizontal, size );
|
||||
}
|
||||
|
||||
|
||||
//reposition
|
||||
Vector2 pos = contentRect.anchoredPosition;
|
||||
|
||||
if (scrollMode == ScrollMode.Vertical)
|
||||
{
|
||||
contentRect.anchoredPosition = new Vector2( pos.x, pos.y - ( ( gridLayout.cellSize.y + gridLayout.spacing.y ) / 2.0f ) );
|
||||
}
|
||||
else if (scrollMode == ScrollMode.Horizontal)
|
||||
{
|
||||
contentRect.anchoredPosition = new Vector2( pos.x + ( ( gridLayout.cellSize.x + gridLayout.spacing.x ) / 2.0f ), pos.y );
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Deletes all elements from list
|
||||
/// </summary>
|
||||
protected void ClearList()
|
||||
{
|
||||
for (int n = 0; n < elements.Count; n++)
|
||||
{
|
||||
Destroy( elements[n].gameObject );
|
||||
}
|
||||
|
||||
elements = new List<GameObject>();
|
||||
contentRect.SetSizeWithCurrentAnchors( RectTransform.Axis.Vertical, minSize );
|
||||
}
|
||||
|
||||
public void OnPointerDown(PointerEventData eventData)
|
||||
{
|
||||
userInteraction = true;
|
||||
}
|
||||
|
||||
public void OnPointerUp(PointerEventData eventData)
|
||||
{
|
||||
userInteraction = false;
|
||||
}
|
||||
|
||||
public void OnPointerExit(PointerEventData eventData)
|
||||
{
|
||||
userInteraction = false;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 56bb13315703e9545abccbfad2863d1f
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
AssetOrigin:
|
||||
serializedVersion: 1
|
||||
productId: 168243
|
||||
packageName: VR Beats Kit
|
||||
packageVersion: 2.0
|
||||
assetPath: Assets/VRBeatsKit/Scripts/UI/Scroller.cs
|
||||
uploadId: 546658
|
||||
@@ -0,0 +1,76 @@
|
||||
using UnityEngine;
|
||||
using UnityEngine.EventSystems;
|
||||
using UnityEngine.UI;
|
||||
using TMPro;
|
||||
using Platinio.TweenEngine;
|
||||
using System;
|
||||
|
||||
namespace VRBeats.UI
|
||||
{
|
||||
public class TrackSlot : MonoBehaviour, IPointerEnterHandler, IPointerExitHandler , IPointerClickHandler
|
||||
{
|
||||
[SerializeField] private TextMeshProUGUI songName = null;
|
||||
[SerializeField] private TextMeshProUGUI authorName = null;
|
||||
[SerializeField] private Image bg = null;
|
||||
[SerializeField] private Image potrait = null;
|
||||
[SerializeField] private Color textSelectedColor;
|
||||
[SerializeField] private Color textNormalColor;
|
||||
[SerializeField] private Color backgroundSelectedColor;
|
||||
[SerializeField] private Color backgroundNormalColor;
|
||||
[SerializeField] private float fadeTime = 1.0f;
|
||||
[SerializeField] private Ease ease = Ease.EaseOutExpo;
|
||||
|
||||
private Action<TrackInfo> onClick = null;
|
||||
private TrackInfo trackInfo = null;
|
||||
|
||||
private void Awake()
|
||||
{
|
||||
songName.color = textNormalColor;
|
||||
authorName.color = textNormalColor;
|
||||
bg.color = backgroundNormalColor;
|
||||
}
|
||||
|
||||
public void Construct(TrackInfo info , Action<TrackInfo> onClick)
|
||||
{
|
||||
potrait.sprite = info.potrait;
|
||||
string songTile = string.Format("{0} ({1})" , info.songName , info.Mode.ToString());
|
||||
songName.text = songTile;
|
||||
authorName.text = info.author;
|
||||
trackInfo = info;
|
||||
this.onClick = onClick;
|
||||
}
|
||||
|
||||
|
||||
public void OnPointerEnter(PointerEventData eventData)
|
||||
{
|
||||
gameObject.CancelAllTweens();
|
||||
PlatinioTween.instance.ColorTween(songName.color , textSelectedColor , fadeTime).SetOnUpdateColor( delegate (Color c)
|
||||
{
|
||||
songName.color = c;
|
||||
authorName.color = c;
|
||||
} ).SetOwner(gameObject).SetEase(ease);
|
||||
|
||||
bg.ColorTween( backgroundSelectedColor , fadeTime ).SetOwner(gameObject).SetEase(ease);
|
||||
|
||||
}
|
||||
|
||||
public void OnPointerExit(PointerEventData eventData)
|
||||
{
|
||||
gameObject.CancelAllTweens();
|
||||
PlatinioTween.instance.ColorTween(songName.color, textNormalColor, fadeTime).SetOnUpdateColor(delegate (Color c)
|
||||
{
|
||||
songName.color = c;
|
||||
authorName.color = c;
|
||||
}).SetOwner(gameObject).SetEase(ease);
|
||||
|
||||
bg.ColorTween(backgroundNormalColor, fadeTime).SetOwner(gameObject).SetEase(ease);
|
||||
}
|
||||
|
||||
public void OnPointerClick(PointerEventData eventData)
|
||||
{
|
||||
onClick.Invoke(trackInfo);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 3b90c8d1018f9cc4f99322c68f30107e
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
AssetOrigin:
|
||||
serializedVersion: 1
|
||||
productId: 168243
|
||||
packageName: VR Beats Kit
|
||||
packageVersion: 2.0
|
||||
assetPath: Assets/VRBeatsKit/Scripts/UI/TrackSlot.cs
|
||||
uploadId: 546658
|
||||
@@ -0,0 +1,62 @@
|
||||
using System;
|
||||
using UnityEngine;
|
||||
using UnityEngine.SceneManagement;
|
||||
|
||||
namespace VRBeats.UI
|
||||
{
|
||||
public class TracksUIList : MonoBehaviour
|
||||
{
|
||||
[SerializeField] private TracksDatabase database = null;
|
||||
[SerializeField] private Scroller scroller = null;
|
||||
[SerializeField] private TrackSlot trackSlotPrefab = null;
|
||||
[SerializeField] private Transform contentParent = null;
|
||||
|
||||
private bool sceneIsLoading = false;
|
||||
private const string boxingStyleSceneName = "BoxingStyle";
|
||||
private const string saberStyleScenName = "SaberStyle";
|
||||
|
||||
private float timer = 0.0f;
|
||||
private bool trigger = false;
|
||||
|
||||
private void Start()
|
||||
{
|
||||
PopulateList();
|
||||
}
|
||||
|
||||
private void PopulateList()
|
||||
{
|
||||
for (int n = 0; n < database.TrackList.Length; n++)
|
||||
{
|
||||
int index = n;
|
||||
TrackSlot slot = Instantiate(trackSlotPrefab , contentParent);
|
||||
slot.transform.localScale = Vector3.one;
|
||||
slot.Construct(database.TrackList[n] , delegate (TrackInfo info){ OnSlotClick(info ,index); });
|
||||
scroller.AddElement(slot.gameObject);
|
||||
}
|
||||
}
|
||||
|
||||
private void Update()
|
||||
{
|
||||
if (!trigger && timer >= 5.0f)
|
||||
{
|
||||
trigger = true;
|
||||
OnSlotClick(database.TrackList[0], 0);
|
||||
}
|
||||
}
|
||||
|
||||
private void OnSlotClick(TrackInfo trackInfo , int index)
|
||||
{
|
||||
if (sceneIsLoading)
|
||||
return;
|
||||
|
||||
sceneIsLoading = true;
|
||||
PlayableManager.SetSelectedTrackIndex(index);
|
||||
string sceneName = trackInfo.Mode == Mode.Boxing ? boxingStyleSceneName : saberStyleScenName;
|
||||
SceneManager.LoadScene( sceneName );
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
fileFormatVersion: 2
|
||||
guid: e55232ae4f777b44e83162060b58ef8f
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
AssetOrigin:
|
||||
serializedVersion: 1
|
||||
productId: 168243
|
||||
packageName: VR Beats Kit
|
||||
packageVersion: 2.0
|
||||
assetPath: Assets/VRBeatsKit/Scripts/UI/TracksUIList.cs
|
||||
uploadId: 546658
|
||||
@@ -0,0 +1,23 @@
|
||||
using UnityEngine;
|
||||
using UnityEngine.UI;
|
||||
using VRBeats.ScriptableEvents;
|
||||
|
||||
namespace VRBeats.UI
|
||||
{
|
||||
[RequireComponent(typeof(Button))]
|
||||
public class TriggerRestartLevelButton : MonoBehaviour
|
||||
{
|
||||
[SerializeField] private GameEvent onRestart = null;
|
||||
|
||||
private void Awake()
|
||||
{
|
||||
GetComponent<Button>().onClick.AddListener( TriggerRestartEvent ); ;
|
||||
}
|
||||
|
||||
private void TriggerRestartEvent()
|
||||
{
|
||||
onRestart.Invoke();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
fileFormatVersion: 2
|
||||
guid: f8d2822e351e1a444ba7a33af6314372
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
||||
AssetOrigin:
|
||||
serializedVersion: 1
|
||||
productId: 168243
|
||||
packageName: VR Beats Kit
|
||||
packageVersion: 2.0
|
||||
assetPath: Assets/VRBeatsKit/Scripts/UI/TriggerRestartLevelButton.cs
|
||||
uploadId: 546658
|
||||
Reference in New Issue
Block a user