#nullable enable using System; using UnityEngine; using UnityEngine.UIElements; namespace UVC.UIToolkit { /// /// 스크롤 뷰 컴포넌트. /// Unity ScrollView를 래핑하여 커스텀 스타일을 적용합니다. /// 내용이 컨테이너보다 클 때 스크롤하여 볼 수 있습니다. /// /// /// ScrollView(스크롤 뷰)란? /// /// ScrollView는 내용이 표시 영역보다 클 때 스크롤하여 나머지 내용을 볼 수 있게 하는 컨테이너입니다. /// 긴 목록, 대화 내용, 문서 등 많은 콘텐츠를 제한된 공간에 표시할 때 사용합니다. /// /// /// 스크롤 모드 (ScrollViewMode): /// /// Vertical - 세로 스크롤만 (기본값, 대부분의 목록) /// Horizontal - 가로 스크롤만 (가로 갤러리, 타임라인) /// VerticalAndHorizontal - 양방향 스크롤 (큰 이미지, 스프레드시트) /// /// /// 주요 속성: /// /// mode - 스크롤 방향 설정 /// scrollOffset - 현재 스크롤 위치 /// verticalScrollerVisibility - 세로 스크롤바 표시 설정 /// horizontalScrollerVisibility - 가로 스크롤바 표시 설정 /// /// /// 실제 활용 예시: /// /// 채팅 창 - 메시지 목록 스크롤 /// 설정 페이지 - 많은 옵션 스크롤 /// 갤러리 - 이미지 목록 스크롤 /// 코드 에디터 - 긴 코드 스크롤 /// /// /// /// C# 코드에서 사용: /// /// // 기본 스크롤 뷰 /// var scrollView = new UTKScrollView(); /// scrollView.Add(new Label("내용 1")); /// scrollView.Add(new Label("내용 2")); /// scrollView.Add(new Label("내용 3")); /// /// // 스크롤 모드 설정 /// var verticalScroll = new UTKScrollView(ScrollViewMode.Vertical); /// var horizontalScroll = new UTKScrollView(ScrollViewMode.Horizontal); /// /// UXML에서 사용: /// /// /// /// /// /// /// /// /// /// /// /// /// /// /// /// /// [UxmlElement] public partial class UTKScrollView : ScrollView, IDisposable { #region Constants private const string USS_PATH = "UIToolkit/Common/UTKScrollView"; #endregion #region Fields private bool _disposed; #endregion #region Constructor public UTKScrollView() : base() { UTKThemeManager.Instance.ApplyThemeToElement(this); var uss = Resources.Load(USS_PATH); if (uss != null) { styleSheets.Add(uss); } SetupStyles(); SubscribeToThemeChanges(); } public UTKScrollView(ScrollViewMode mode) : this() { this.mode = mode; } #endregion #region Setup private void SetupStyles() { AddToClassList("utk-scrollview"); } private void SubscribeToThemeChanges() { UTKThemeManager.Instance.OnThemeChanged += OnThemeChanged; RegisterCallback(OnAttachToPanelForTheme); RegisterCallback(OnDetachFromPanelForTheme); } private void OnAttachToPanelForTheme(AttachToPanelEvent evt) { UTKThemeManager.Instance.OnThemeChanged -= OnThemeChanged; UTKThemeManager.Instance.OnThemeChanged += OnThemeChanged; UTKThemeManager.Instance.ApplyThemeToElement(this); } private void OnDetachFromPanelForTheme(DetachFromPanelEvent evt) { UTKThemeManager.Instance.OnThemeChanged -= OnThemeChanged; } private void OnThemeChanged(UTKTheme theme) { UTKThemeManager.Instance.ApplyThemeToElement(this); } #endregion #region IDisposable public void Dispose() { if (_disposed) return; _disposed = true; UTKThemeManager.Instance.OnThemeChanged -= OnThemeChanged; UnregisterCallback(OnAttachToPanelForTheme); UnregisterCallback(OnDetachFromPanelForTheme); } #endregion } }