浏览代码

[1.5.4] Upgrade widgets.

/main
Yuncong Zhang 5 年前
当前提交
6daeb787
共有 10 个文件被更改,包括 200 次插入86 次删除
  1. 12
      Runtime/rendering/editable.cs
  2. 23
      Runtime/ui/painting/txt/font_manager.cs
  3. 6
      Runtime/ui/renderer/cmdbufferCanvas/rendering/canvas_shader.cs
  4. 7
      Runtime/widgets/page_view.cs
  5. 4
      Runtime/widgets/routes.cs
  6. 26
      Runtime/widgets/scroll_view.cs
  7. 39
      Runtime/widgets/scrollable.cs
  8. 2
      Runtime/widgets/single_child_scroll_view.cs
  9. 4
      Runtime/widgets/text.cs
  10. 163
      Runtime/widgets/text_selection.cs

12
Runtime/rendering/editable.cs


public TextSelectionDelegate textSelectionDelegate;
public ValueListenable<bool> selectionStartInViewport {
get { return this._selectionStartInViewport; }
}
readonly ValueNotifier<bool> _selectionStartInViewport = new ValueNotifier<bool>(true);
public ValueListenable<bool> selectionEndInViewport {
get { return this._selectionEndInViewport; }
}
readonly ValueNotifier<bool> _selectionEndInViewport = new ValueNotifier<bool>(true);
int _extentOffset = -1;
int _baseOffset = -1;

23
Runtime/ui/painting/txt/font_manager.cs


public class FontManager {
readonly Dictionary<string, FontInfo>[] _fonts =
new Dictionary<string, FontInfo>[9 * 2]; // max weight size x max style size
static readonly int defaultFontSize = 14;
public static readonly FontManager instance = new FontManager();

}
public void addFont(Font font, string familyName,
public void addFont(Font font, string familyName,
FontWeight fontWeight = null, FontStyle fontStyle = FontStyle.normal) {
fontWeight = fontWeight ?? FontWeight.normal;

var fonts = this._getFonts(fontWeight.index, fontStyle);
fonts.TryGetValue(familyName, out var current);
D.assert(current == null || current.font == font,
D.assert(current == null || current.font == font,
() => $"font with key {familyName} {fontWeight} {fontStyle} already exists");
var fontInfo = new FontInfo(font);
fonts[familyName] = fontInfo;

return fontInfo;
}
}
var osFont = Font.CreateDynamicFontFromOSFont(familyName, defaultFontSize);
osFont.hideFlags = HideFlags.DontSave;
osFont.material.hideFlags = HideFlags.DontSave;

}
}
public static class FontExtension
{
public static class FontExtension {
internal static bool getGlyphInfo(this Font font, char ch, out CharacterInfo info, int fontSize,
UnityEngine.FontStyle fontStyle) {
if (fontSize <= 0) {

bool success = font.GetCharacterInfo(ch, out info, fontSize, fontStyle);
if (!success) {
if (!char.IsControl(ch)) {
Debug.LogWarning(
$"character info not found from the given font: character '{ch}' (code{(int) ch}) font: ${font.name}");
D.assert(() => {
Debug.LogWarning(
$"character info not found from the given font: character '{ch}' (code{(int) ch}) font: ${font.name}");
return true;
});
}
info = default;

return true;
}
internal static void RequestCharactersInTextureSafe(this Font font, string text, int fontSize,
UnityEngine.FontStyle fontStyle = UnityEngine.FontStyle.Normal) {
internal static void RequestCharactersInTextureSafe(this Font font, string text, int fontSize,
UnityEngine.FontStyle fontStyle = UnityEngine.FontStyle.Normal) {
font.RequestCharactersInTexture(text, fontSize, fontStyle);
}
}

6
Runtime/ui/renderer/cmdbufferCanvas/rendering/canvas_shader.cs


using System;
using Unity.UIWidgets.foundation;
using UnityEngine;
using UnityEngine.Rendering;

mat.SetInt(_dstBlend, (int) UnityEngine.Rendering.BlendMode.Zero);
}
else {
Debug.LogWarning("Not supported BlendMode: " + op + ". Defaults to srcOver");
D.assert(() => {
Debug.LogWarning("Not supported BlendMode: " + op + ". Defaults to srcOver");
return true;
});
mat.SetInt(_srcBlend, (int) UnityEngine.Rendering.BlendMode.One);
mat.SetInt(_dstBlend, (int) UnityEngine.Rendering.BlendMode.OneMinusSrcAlpha);
}

7
Runtime/widgets/page_view.cs


bool pageSnapping = true,
ValueChanged<int> onPageChanged = null,
List<Widget> children = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down,
DragStartBehavior dragStartBehavior = DragStartBehavior.start,
IndexedWidgetBuilder itemBuilder = null,
SliverChildDelegate childDelegate = null,
int itemCount = 0

this.childrenDelegate = new SliverChildListDelegate(children ?? new List<Widget>());
}
}
// TODO: PageView.builder
// TODO: PageView.custom
public readonly Axis scrollDirection;

4
Runtime/widgets/routes.cs


break;
case AnimationStatus.dismissed:
// We might still be the current route if a subclass is controlling the
// We might still be an active route if a subclass is controlling the
if (!this.isCurrent) {
if (!this.isActive) {
this.navigator.finalizeRoute(this);
D.assert(this.overlayEntries.isEmpty());
}

26
Runtime/widgets/scroll_view.cs


Key center = null,
float anchor = 0.0f,
float? cacheExtent = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(key: key) {
D.assert(!(controller != null && primary == true),
() => "Primary ScrollViews obtain their ScrollController via inheritance from a PrimaryScrollController widget. " +

float anchor = 0.0f,
float? cacheExtent = null,
List<Widget> slivers = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(
key: key,
scrollDirection: scrollDirection,

bool shrinkWrap = false,
EdgeInsets padding = null,
float? cacheExtent = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(
key: key,
scrollDirection: scrollDirection,

bool addRepaintBoundaries = true,
float? cacheExtent = null,
List<Widget> children = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(
key: key,
scrollDirection: scrollDirection,

bool addAutomaticKeepAlives = true,
bool addRepaintBoundaries = true,
float? cacheExtent = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(key: key,
scrollDirection: scrollDirection,
reverse: reverse,

bool addAutomaticKeepAlives = true,
bool addRepaintBoundaries = true,
float? cacheExtent = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) {
return new ListView(
key: key,

bool addAutomaticKeepAlives = true,
bool addRepaintBoundaries = true,
float? cacheExtent = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(
key: key,
scrollDirection: scrollDirection,

SliverGridDelegate gridDelegate = null,
SliverChildDelegate childrenDelegate = null,
float? cacheExtent = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(
key: key,
scrollDirection: scrollDirection,

SliverGridDelegate gridDelegate = null,
SliverChildDelegate childrenDelegate = null,
float? cacheExtent = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) {
return new GridView(
key: key,

bool addRepaintBoundaries = true,
float? cacheExtent = null,
List<Widget> children = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(
key: key,
scrollDirection: scrollDirection,

bool addRepaintBoundaries = true,
float? cacheExtent = null,
List<Widget> children = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) {
return new GridView(
key: key,

bool addRepaintBoundaries = true,
bool addSemanticIndexes = true,
List<Widget> children = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(
key: key,
scrollDirection: scrollDirection,

bool addAutomaticKeepAlives = true,
bool addRepaintBoundaries = true,
List<Widget> children = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) {
return new GridView(
key: key,

39
Runtime/widgets/scrollable.cs


using Unity.UIWidgets.rendering;
using Unity.UIWidgets.scheduler;
using Unity.UIWidgets.ui;
using UnityEngine;
namespace Unity.UIWidgets.widgets {
public delegate Widget ViewportBuilder(BuildContext context, ViewportOffset position);

ScrollController controller = null,
ScrollPhysics physics = null,
ViewportBuilder viewportBuilder = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(key: key) {
D.assert(viewportBuilder != null);

D.assert(this._hold == null);
D.assert(this._drag == null);
}
float _targetScrollOffsetForPointerScroll(PointerScrollEvent e) {
float delta = this.widget.axis == Axis.horizontal ? e.delta.dx : e.delta.dy;
return Mathf.Min(Mathf.Max(this.position.pixels + delta, this.position.minScrollExtent),
this.position.maxScrollExtent);
}
// TODO: float _receivedPointerSignal(PointerSignalEvent event) {
// }
void _handlePointerrScroll(PointerEvent e) {
D.assert(e is PointerScrollEvent);
float targetScrollOffset = this._targetScrollOffsetForPointerScroll(e as PointerScrollEvent);
if (targetScrollOffset != this.position.pixels) {
this.position.jumpTo(targetScrollOffset);
}
}
void _disposeHold() {
this._hold = null;

Widget result = new _ScrollableScope(
scrollable: this,
position: this.position,
child: new RawGestureDetector(
key: this._gestureDetectorKey,
gestures: this._gestureRecognizers,
behavior: HitTestBehavior.opaque,
child: new IgnorePointer(
key: this._ignorePointerKey,
ignoring: this._shouldIgnorePointer,
child: this.widget.viewportBuilder(context, this.position)
child: new Listener(
// TODO: onPointerSignal: _receivePointerSignal,
child: new RawGestureDetector(
key: this._gestureDetectorKey,
gestures: this._gestureRecognizers,
behavior: HitTestBehavior.opaque,
child: new IgnorePointer(
key: this._ignorePointerKey,
ignoring: this._shouldIgnorePointer,
child: this.widget.viewportBuilder(context, this.position)
)
)
)
);

2
Runtime/widgets/single_child_scroll_view.cs


ScrollPhysics physics = null,
ScrollController controller = null,
Widget child = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(key: key) {
D.assert(!(controller != null && primary == true),
() => "Primary ScrollViews obtain their ScrollController via inheritance from a PrimaryScrollController widget. " +

4
Runtime/widgets/text.cs


TextOverflow? overflow = null,
float? textScaleFactor = null,
int? maxLines = null) : base(key) {
D.assert(data != null);
D.assert(data != null, () => "A non-null string must be provided to a Text widget.");
this.textSpan = null;
this.data = data;
this.style = style;

TextOverflow? overflow = null,
float? textScaleFactor = null,
int? maxLines = null) : base(key) {
D.assert(textSpan != null);
D.assert(textSpan != null, () => "A non-null TextSpan must be provided to a Text.rich widget.");
this.textSpan = textSpan;
this.data = null;
this.style = style;

163
Runtime/widgets/text_selection.cs


RenderEditable renderObject = null,
TextSelectionControls selectionControls = null,
TextSelectionDelegate selectionDelegate = null,
DragStartBehavior? dragStartBehavior = null) {
DragStartBehavior dragStartBehavior = DragStartBehavior.start) {
D.assert(value != null);
D.assert(context != null);
this.context = context;

this.selectionDelegate = selectionDelegate;
this._value = value;
OverlayState overlay = Overlay.of(context);
D.assert(overlay != null);
this._handleController = new AnimationController(duration: _fadeDuration, vsync: overlay);
this._toolbarController = new AnimationController(duration: _fadeDuration, vsync: overlay);
D.assert(overlay != null, () => $"No Overlay widget exists above {context}.\n" +
"Usually the Navigator created by WidgetsApp provides the overlay. Perhaps your " +
"app content was created above the Navigator with the WidgetsApp builder parameter.");
this._toolbarController = new AnimationController(duration: fadeDuration, vsync: overlay);
this.dragStartBehavior = dragStartBehavior;
}

public readonly RenderEditable renderObject;
public readonly TextSelectionControls selectionControls;
public readonly TextSelectionDelegate selectionDelegate;
public readonly DragStartBehavior? dragStartBehavior;
public readonly DragStartBehavior dragStartBehavior;
public static TimeSpan _fadeDuration = TimeSpan.FromMilliseconds(150);
AnimationController _handleController;
public static readonly TimeSpan fadeDuration = TimeSpan.FromMilliseconds(150);
Animation<float> _handleOpacity {
get { return this._handleController.view; }
}
Animation<float> _toolbarOpacity {
get { return this._toolbarController.view; }

this._buildHandle(context, _TextSelectionHandlePosition.end)),
};
Overlay.of(this.context, debugRequiredFor: this.debugRequiredFor).insertAll(this._handles);
this._handleController.forward(from: 0.0f);
}
public void showToolbar() {

this._toolbar?.remove();
this._toolbar = null;
this._handleController.stop();
this._handleController.dispose();
this._toolbarController.dispose();
}

return new Container(); // hide the second handle when collapsed
}
return new FadeTransition(
opacity: this._handleOpacity,
child: new _TextSelectionHandleOverlay(
onSelectionHandleChanged: (TextSelection newSelection) => {
this._handleSelectionHandleChanged(newSelection, position);
},
onSelectionHandleTapped: this._handleSelectionHandleTapped,
layerLink: this.layerLink,
renderObject: this.renderObject,
selection: this._selection,
selectionControls: this.selectionControls,
position: position,
dragStartBehavior: this.dragStartBehavior ?? DragStartBehavior.down
)
return new _TextSelectionHandleOverlay(
onSelectionHandleChanged: (TextSelection newSelection) => {
this._handleSelectionHandleChanged(newSelection, position);
},
onSelectionHandleTapped: this._handleSelectionHandleTapped,
layerLink: this.layerLink,
renderObject: this.renderObject,
selection: this._selection,
selectionControls: this.selectionControls,
position: position,
dragStartBehavior: this.dragStartBehavior
);
}

ValueChanged<TextSelection> onSelectionHandleChanged = null,
VoidCallback onSelectionHandleTapped = null,
TextSelectionControls selectionControls = null,
DragStartBehavior dragStartBehavior = DragStartBehavior.down
DragStartBehavior dragStartBehavior = DragStartBehavior.start
) : base(key: key) {
this.selection = selection;
this.position = position;

public override State createState() {
return new _TextSelectionHandleOverlayState();
}
internal ValueListenable<bool> _visibility {
get {
switch (this.position) {
case _TextSelectionHandlePosition.start:
return this.renderObject.selectionStartInViewport;
case _TextSelectionHandlePosition.end:
return this.renderObject.selectionEndInViewport;
}
return null;
}
}
class _TextSelectionHandleOverlayState : State<_TextSelectionHandleOverlay> {
class _TextSelectionHandleOverlayState : SingleTickerProviderStateMixin<_TextSelectionHandleOverlay> {
AnimationController _controller;
Animation<float> _opacity {
get { return this._controller.view; }
}
public override void initState() {
base.initState();
this._controller = new AnimationController(duration: TextSelectionOverlay.fadeDuration, vsync: this);
this._handleVisibilityChanged();
this.widget._visibility.addListener(this._handleVisibilityChanged);
}
void _handleVisibilityChanged() {
if (this.widget._visibility.value) {
this._controller.forward();
}
else {
this._controller.reverse();
}
}
public override void didUpdateWidget(StatefulWidget oldWidget) {
base.didUpdateWidget(oldWidget);
(oldWidget as _TextSelectionHandleOverlay)._visibility.removeListener(this._handleVisibilityChanged);
this._handleVisibilityChanged();
this.widget._visibility.addListener(this._handleVisibilityChanged);
}
public override void dispose() {
this.widget._visibility.removeListener(this._handleVisibilityChanged);
this._controller.dispose();
base.dispose();
}
void _handleDragStart(DragStartDetails details) {
this._dragPosition = details.globalPosition +
new Offset(0.0f, -this.widget.selectionControls.handleSize.height);

break;
}
Size viewport = this.widget.renderObject.size;
point = new Offset(
point.dx.clamp(0.0f, viewport.width),
point.dy.clamp(0.0f, viewport.height)
);
child: new GestureDetector(
dragStartBehavior: this.widget.dragStartBehavior,
onPanStart: this._handleDragStart,
onPanUpdate: this._handleDragUpdate,
onTap: this._handleTap,
child: new Stack(
overflow: Overflow.visible,
children: new List<Widget>() {
new Positioned(
left: point.dx,
top: point.dy,
child: this.widget.selectionControls.buildHandle(context, type,
this.widget.renderObject.preferredLineHeight)
)
}
child: new FadeTransition(
opacity: this._opacity,
child: new GestureDetector(
dragStartBehavior: this.widget.dragStartBehavior,
onPanStart: this._handleDragStart,
onPanUpdate: this._handleDragUpdate,
onTap: this._handleTap,
child: new Stack(
overflow: Overflow.visible,
children: new List<Widget>() {
new Positioned(
left: point.dx,
top: point.dy,
child: this.widget.selectionControls.buildHandle(context, type,
this.widget.renderObject.preferredLineHeight)
)
}
)
)
)
);

GestureTapUpCallback onSingleTapUp = null,
GestureTapCancelCallback onSingleTapCancel = null,
GestureLongPressCallback onSingleLongTapStart = null,
// TODO: GestureLongPressMoveUpdateCallback onSingleLongTapMoveUpdate = null,
// TODO: GestureLongPressEndCallback onSingleLongTapEnd = null,
GestureTapDownCallback onDoubleTapDown = null,
GestureDragStartCallback onDragSelectionStart = null,
DragSelectionUpdateCallback onDragSelectionUpdate = null,

public readonly GestureTapCancelCallback onSingleTapCancel;
public readonly GestureLongPressCallback onSingleLongTapStart;
// TODO: public readonly GestureLongPressMoveUpdateCallback onSingleLongTapMoveUpdate;
// TODO: public readonly GestureLongPressEndCallback onSingleLongTapEnd;
public readonly GestureTapDownCallback onDoubleTapDown;

}
}
// TODO: void _handleLongPressMoveUpdate(LongPressMoveUpdateDetails details) {
// }
// TODO: void _handleLongPressEnd(LongPressEndDetails details) {
// }
void _doubleTapTimeout() {
this._doubleTapTimer = null;
this._lastTapOffset = null;

)
);
if (this.widget.onSingleLongTapStart != null) {
if (this.widget.onSingleLongTapStart != null // ||
// TODO: this.widget.onSingleLongTapMoveUpdatee != null ||
// TODO: this.widget.onSingleLongTapEnd != null
) {
instance => { instance.onLongPress = this._handleLongPressStart; });
instance => {
instance.onLongPress = this._handleLongPressStart;
// TODO: instance.onLongPressMoveUpdate = _handleLongPressMoveUpdate
// TODO: instance.onLongPressEnd = _handleLongPressEnd
});
}
if (this.widget.onDragSelectionStart != null ||

)
);
}
// TODO: if (this.widget.onForcePressStart != null || this.widget.onForcePressEnd != null) {
// }
return new RawGestureDetector(
gestures: gestures,

正在加载...
取消
保存