private void UpdateScrollBar(ScrollRect scrollView, Entity scrollBarEntity, float2 contentToViewportRatio, ref ScrollViewTransforms transforms, ScrollBarAxis axis) { var scrollBar = ScrollBarFromEntity[scrollBarEntity]; var areaTransform = RectTransformFromEntity[scrollBarEntity]; var handleTransform = RectTransformFromEntity[scrollBar.ScrollHandle]; var scrollBarSize = math.saturate(contentToViewportRatio); float2 moveRange = (transforms.ViewportRect.Size - transforms.ContentRect.Size); float2 contentSize = transforms.ContentRect.Size; if (axis == ScrollBarAxis.Vertical) { areaTransform.AnchorMin = new float2(areaTransform.AnchorMin.x, 0.0f); areaTransform.AnchorMax = new float2(areaTransform.AnchorMax.x, 1.0f); areaTransform.Pivot = new float2(1.0f, 1.0f); areaTransform.SizeDelta = new float2(areaTransform.SizeDelta.x, -(areaTransform.SizeDelta.x + scrollView.HorizontalBarSpacing)); var areaRect = RectTransformUtils.CalculateWorldSpaceRect(transforms.ScrollViewRect, ElementScaleFromEntity[scrollBarEntity].Value, areaTransform); handleTransform.AnchorMin = new float2(0.0f, scrollBar.Value * (1.0f - scrollBarSize.y)); handleTransform.AnchorMax = new float2(1.0f, handleTransform.AnchorMin.y + scrollBarSize.y); WorldSpaceRect handleRect = RectTransformUtils.CalculateWorldSpaceRect(areaRect, ElementScaleFromEntity[scrollBarEntity].Value, handleTransform); scrollBar.HandleDragSensitivity = 1.0f / (areaRect.Size.y - handleRect.Size.y); scrollBar.RectDragSensitivity = scrollBar.HandleDragSensitivity / ((transforms.ContentRect.Size.y - transforms.ViewportRect.Size.y) / (areaRect.Size.y - handleRect.Size.y)); transforms.ContentRect.Min.y = transforms.ViewportRect.Min.y + scrollBar.Value * moveRange.y; transforms.ContentRect.Max.y = transforms.ContentRect.Min.y + contentSize.y; } else { areaTransform.AnchorMin = new float2(0.0f, areaTransform.AnchorMin.y); areaTransform.AnchorMax = new float2(1.0f, areaTransform.AnchorMax.y); areaTransform.Pivot = new float2(0.0f, 0.0f); areaTransform.SizeDelta = new float2(-(areaTransform.SizeDelta.y + scrollView.VerticalBarSpacing), areaTransform.SizeDelta.y); var areaRect = RectTransformUtils.CalculateWorldSpaceRect(transforms.ScrollViewRect, ElementScaleFromEntity[scrollBarEntity].Value, areaTransform); handleTransform.AnchorMin = new float2(scrollBar.Value * (1.0f - scrollBarSize.x), 0.0f); handleTransform.AnchorMax = new float2(handleTransform.AnchorMin.x + scrollBarSize.x, 1.0f); WorldSpaceRect handleRect = RectTransformUtils.CalculateWorldSpaceRect(areaRect, ElementScaleFromEntity[scrollBarEntity].Value, handleTransform); scrollBar.HandleDragSensitivity = 1.0f / (areaRect.Size.x - handleRect.Size.x); scrollBar.RectDragSensitivity = scrollBar.HandleDragSensitivity / ((transforms.ContentRect.Size.x - transforms.ViewportRect.Size.x) / (areaRect.Size.x - handleRect.Size.x)); transforms.ContentRect.Min.x = transforms.ViewportRect.Min.x + scrollBar.Value * moveRange.x; transforms.ContentRect.Max.x = transforms.ContentRect.Min.x + contentSize.x; } ScrollBarFromEntity[scrollBarEntity] = scrollBar; RectTransformFromEntity[scrollBar.ScrollHandle] = handleTransform; RectTransformFromEntity[scrollBarEntity] = areaTransform; }
public void Execute(ArchetypeChunk chunk, int chunkIndex, int firstEntityIndex) { NativeArray <ScrollRect> scrollRect = chunk.GetNativeArray(ScrollRectType); NativeArray <Entity> scrollEntity = chunk.GetNativeArray(EntityType); var rebuildContext = new HierarchyRebuildContext() { ChildrenFromEntity = ChildrenFromEntity, WorldSpaceRectFromEntity = WorldSpaceRectFromEntity, RectTransformFromEntity = RectTransformFromEntity, RebuildFlagFromEntity = RebuildFlagFromEntity, ElementScaleFromEntity = ElementScaleFromEntity, WorldSpaceMaskFromEntity = WorldSpaceMaskFromEntity, RectMaskFromEntity = RectMaskFromEntity }; for (int i = 0; i < scrollRect.Length; i++) { ScrollRect scrollView = scrollRect[i]; ScrollViewTransforms transforms = GatherTransforms(scrollEntity[i], scrollView); var oldContentRect = transforms.ContentRect; transforms.ViewportTransform.AnchorMin = new float2(0.0f, 0.0f); transforms.ViewportTransform.AnchorMax = new float2(1.0f, 1.0f); transforms.ViewportTransform.SizeDelta = new float2(-transforms.VerticalAreaTransform.SizeDelta.x - scrollView.VerticalBarSpacing, -transforms.HorizontalAreaTransform.SizeDelta.y - scrollView.HorizontalBarSpacing); transforms.ViewportRect = RectTransformUtils.CalculateWorldSpaceRect(transforms.ScrollViewRect, ElementScaleFromEntity[scrollEntity[i]].Value, transforms.ViewportTransform); RectTransformFromEntity[scrollView.Viewport] = transforms.ViewportTransform; var contentToViewportRatio = transforms.ViewportRect.Size / transforms.ContentRect.Size; var verticalEntity = scrollView.VerticalBar; if (ScrollBarFromEntity.Exists(verticalEntity)) { UpdateScrollBar(scrollView, verticalEntity, contentToViewportRatio, ref transforms, ScrollBarAxis.Vertical); } var horizontalEntity = scrollView.HorizontalBar; if (ScrollBarFromEntity.Exists(horizontalEntity)) { UpdateScrollBar(scrollView, horizontalEntity, contentToViewportRatio, ref transforms, ScrollBarAxis.Horizontal); } if (NeedUpdate(oldContentRect, transforms.ContentRect)) { var newContentTransform = RectTransformUtils.CalculateInverseTransformWithAnchors(transforms.ContentRect, transforms.ViewportRect, transforms.ContentTransform, ElementScaleFromEntity[scrollView.Content].Value); RectTransformFromEntity[scrollView.Content] = newContentTransform; UpdateScrollRectTransform(scrollEntity[i], transforms.ScrollViewRect, rebuildContext); } } }
public void InverseRectTransform() { NativeArray <WorldSpaceRect> parentRects = new NativeArray <WorldSpaceRect>(4, Allocator.Temp); parentRects[0] = new WorldSpaceRect() { Min = new float2(0.0f, 0.0f), Max = new float2(100.0f, 100.0f) }; parentRects[1] = new WorldSpaceRect() { Min = new float2(10.0f, 10.0f), Max = new float2(100.0f, 100.0f) }; parentRects[2] = new WorldSpaceRect() { Min = new float2(-10.0f, -10.0f), Max = new float2(100.0f, 100.0f) }; parentRects[3] = new WorldSpaceRect() { Min = new float2(-100.0f, -100.0f), Max = new float2(-10.0f, -10.0f) }; NativeArray <RectTransform> rectTransforms = new NativeArray <RectTransform>(4, Allocator.Temp); rectTransforms[0] = new RectTransform() { AnchorMin = new float2(0.0f, 0.0f), AnchorMax = new float2(1.0f, 1.0f), Pivot = new float2(0.5f, 0.5f), Position = new float2(5.0f, 5.0f), SizeDelta = new float2(20.0f, 20.0f) }; rectTransforms[1] = new RectTransform() { AnchorMin = new float2(0.0f, 0.0f), AnchorMax = new float2(0.0f, 1.0f), Pivot = new float2(1.0f, 1.0f), Position = new float2(5.0f, 5.0f), SizeDelta = new float2(20.0f, 20.0f) }; rectTransforms[2] = new RectTransform() { AnchorMin = new float2(0.5f, 0.5f), AnchorMax = new float2(0.5f, 0.5f), Pivot = new float2(0.5f, 0.5f), Position = new float2(-5.0f, -5.0f), SizeDelta = new float2(20.0f, 20.0f) }; rectTransforms[3] = new RectTransform() { AnchorMin = new float2(1.0f, 1.0f), AnchorMax = new float2(1.0f, 1.0f), Pivot = new float2(0.0f, 0.0f), Position = new float2(-5.0f, -5.0f), SizeDelta = new float2(20.0f, 20.0f) }; for (int i = 0; i < parentRects.Length; i++) { for (int j = 0; j < rectTransforms.Length; j++) { var worldSpace = RectTransformUtils.CalculateWorldSpaceRect(parentRects[i], new float2(1.0f, 1.0f), rectTransforms[j]); var emptyTransform = new RectTransform() { AnchorMin = rectTransforms[j].AnchorMin, AnchorMax = rectTransforms[j].AnchorMax, Pivot = rectTransforms[j].Pivot }; var calculatedTransform = RectTransformUtils.CalculateInverseTransformWithAnchors(worldSpace, parentRects[i], emptyTransform, new float2(1.0f, 1.0f)); Assert.IsTrue(RectTransformEquals(rectTransforms[j], calculatedTransform)); } } }