Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
dotNET Platform
wpf
提交
48258a02
W
wpf
项目概览
dotNET Platform
/
wpf
11 个月 前同步成功
通知
1
Star
1
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
W
wpf
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
48258a02
编写于
2月 26, 2020
作者:
R
Rob LaDuca
浏览文件
操作
浏览文件
下载
差异文件
Merging release/3.1 to master
上级
6ef558b7
5759ba9d
变更
7
显示空白变更内容
内联
并排
Showing
7 changed file
with
188 addition
and
88 deletion
+188
-88
src/Microsoft.DotNet.Wpf/src/PresentationBuildTasks/Microsoft.WinFx.props
...tNet.Wpf/src/PresentationBuildTasks/Microsoft.WinFx.props
+1
-1
src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Controls/DefinitionBase.cs
...tationFramework/System/Windows/Controls/DefinitionBase.cs
+77
-35
src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Controls/Grid.cs
...src/PresentationFramework/System/Windows/Controls/Grid.cs
+2
-2
src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Controls/ItemsControl.cs
...entationFramework/System/Windows/Controls/ItemsControl.cs
+42
-2
src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Controls/VirtualizingStackPanel.cs
...amework/System/Windows/Controls/VirtualizingStackPanel.cs
+9
-9
src/Microsoft.DotNet.Wpf/src/System.Windows.Controls.Ribbon/Microsoft/Windows/Controls/Ribbon/RibbonHelper.cs
....Ribbon/Microsoft/Windows/Controls/Ribbon/RibbonHelper.cs
+15
-6
src/Microsoft.DotNet.Wpf/src/System.Windows.Controls.Ribbon/Microsoft/Windows/Controls/Ribbon/RibbonMenuButton.cs
...bon/Microsoft/Windows/Controls/Ribbon/RibbonMenuButton.cs
+42
-33
未找到文件。
src/Microsoft.DotNet.Wpf/src/PresentationBuildTasks/Microsoft.WinFx.props
浏览文件 @
48258a02
...
...
@@ -2,7 +2,7 @@
<PropertyGroup>
<_PresentationBuildTasksTfm Condition="'$(MSBuildRuntimeType)' == 'Core'">netcoreapp2.1</_PresentationBuildTasksTfm>
<_PresentationBuildTasksTfm Condition="'$(MSBuildRuntimeType)' != 'Core'">net472</_PresentationBuildTasksTfm>
<_PresentationBuildTasksAssembly Condition="'$(_PresentationBuildTasksAssembly)'==''">$([
System.IO.Path]::GetFullPath('$(MSBuildThisFileDirectory)..\tools\$(_PresentationBuildTasksTfm)\PresentationBuildTasks.dll'
))</_PresentationBuildTasksAssembly>
<_PresentationBuildTasksAssembly Condition="'$(_PresentationBuildTasksAssembly)'==''">$([
MSBuild]::Unescape($([System.IO.Path]::GetFullPath('$(MSBuildThisFileDirectory)..\tools\$(_PresentationBuildTasksTfm)\PresentationBuildTasks.dll'))
))</_PresentationBuildTasksAssembly>
</PropertyGroup>
<UsingTask TaskName="Microsoft.Build.Tasks.Windows.MarkupCompilePass1" AssemblyFile="$(_PresentationBuildTasksAssembly)" />
...
...
src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Controls/DefinitionBase.cs
浏览文件 @
48258a02
...
...
@@ -411,6 +411,14 @@ internal double MinSizeForArrange
}
}
/// <summary>
/// Returns min size, never taking into account shared state.
/// </summary>
internal
double
RawMinSize
{
get
{
return
_minSize
;
}
}
/// <summary>
/// Offset.
/// </summary>
...
...
@@ -872,7 +880,7 @@ private void OnLayoutUpdated(object sender, EventArgs e)
// accumulate min size of all participating definitions
for
(
int
i
=
0
,
count
=
_registry
.
Count
;
i
<
count
;
++
i
)
{
sharedMinSize
=
Math
.
Max
(
sharedMinSize
,
_registry
[
i
].
M
inSize
);
sharedMinSize
=
Math
.
Max
(
sharedMinSize
,
_registry
[
i
].
_m
inSize
);
}
bool
sharedMinSizeChanged
=
!
DoubleUtil
.
AreClose
(
_minSize
,
sharedMinSize
);
...
...
@@ -882,32 +890,66 @@ private void OnLayoutUpdated(object sender, EventArgs e)
{
DefinitionBase
definitionBase
=
_registry
[
i
];
if
(
sharedMinSizeChanged
||
definitionBase
.
LayoutWasUpdated
)
// we'll set d.UseSharedMinimum to maintain the invariant:
// d.UseSharedMinimum iff d._minSize < this.MinSize
// i.e. iff d is not a "long-pole" definition.
//
// Measure/Arrange of d's Grid uses d._minSize for long-pole
// definitions, and max(d._minSize, shared size) for
// short-pole definitions. This distinction allows us to react
// to changes in "long-pole-ness" more efficiently and correctly,
// by avoiding remeasures when a long-pole definition changes.
bool
useSharedMinimum
=
!
DoubleUtil
.
AreClose
(
definitionBase
.
_minSize
,
sharedMinSize
);
// before doing that, determine whether d's Grid needs to be remeasured.
// It's important _not_ to remeasure if the last measure is still
// valid, otherwise infinite loops are possible
bool
measureIsValid
;
if
(!
definitionBase
.
UseSharedMinimum
)
{
// if definition's min size is different, then need to re-measure
if
(!
DoubleUtil
.
AreClose
(
sharedMinSize
,
definitionBase
.
MinSize
))
// d was a long-pole. measure is valid iff it's still a long-pole,
// since previous measure didn't use shared size.
measureIsValid
=
!
useSharedMinimum
;
}
else
if
(
useSharedMinimum
)
{
Grid
parentGrid
=
(
Grid
)
definitionBase
.
Parent
;
parentGrid
.
InvalidateMeasure
();
definitionBase
.
UseSharedMinimum
=
true
;
// d was a short-pole, and still is. measure is valid
// iff the shared size didn't change
measureIsValid
=
!
sharedMinSizeChanged
;
}
else
{
definitionBase
.
UseSharedMinimum
=
false
;
// d was a short-pole, but is now a long-pole. This can
// happen in several ways:
// a. d's minSize increased to or past the old shared size
// b. other long-pole definitions decreased, leaving
// d as the new winner
// In the former case, the measure is valid - it used
// d's new larger minSize. In the latter case, the
// measure is invalid - it used the old shared size,
// which is larger than d's (possibly changed) minSize
measureIsValid
=
(
definitionBase
.
LayoutWasUpdated
&&
DoubleUtil
.
GreaterThanOrClose
(
definitionBase
.
_minSize
,
this
.
MinSize
));
}
if
(!
measureIsValid
)
{
Grid
parentGrid
=
(
Grid
)
definitionBase
.
Parent
;
parentGrid
.
InvalidateMeasure
();
}
else
if
(!
DoubleUtil
.
AreClose
(
sharedMinSize
,
definitionBase
.
SizeCache
))
{
// if measure is valid then also need to check arrange.
// Note: definitionBase.SizeCache is volatile but at this point
// it contains up-to-date final size
if
(!
DoubleUtil
.
AreClose
(
sharedMinSize
,
definitionBase
.
SizeCache
))
{
Grid
parentGrid
=
(
Grid
)
definitionBase
.
Parent
;
parentGrid
.
InvalidateArrange
();
}
}
// now we can restore the invariant, and clear the layout flag
definitionBase
.
UseSharedMinimum
=
useSharedMinimum
;
definitionBase
.
LayoutWasUpdated
=
false
;
}
}
_minSize
=
sharedMinSize
;
...
...
src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Controls/Grid.cs
浏览文件 @
48258a02
...
...
@@ -1178,11 +1178,11 @@ private double[] CacheMinSizes(int cellsHead, bool isRows)
{
if
(
isRows
)
{
minSizes
[
PrivateCells
[
i
].
RowIndex
]
=
DefinitionsV
[
PrivateCells
[
i
].
RowIndex
].
MinSize
;
minSizes
[
PrivateCells
[
i
].
RowIndex
]
=
DefinitionsV
[
PrivateCells
[
i
].
RowIndex
].
Raw
MinSize
;
}
else
{
minSizes
[
PrivateCells
[
i
].
ColumnIndex
]
=
DefinitionsU
[
PrivateCells
[
i
].
ColumnIndex
].
MinSize
;
minSizes
[
PrivateCells
[
i
].
ColumnIndex
]
=
DefinitionsU
[
PrivateCells
[
i
].
ColumnIndex
].
Raw
MinSize
;
}
i
=
PrivateCells
[
i
].
Next
;
...
...
src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Controls/ItemsControl.cs
浏览文件 @
48258a02
...
...
@@ -3011,7 +3011,7 @@ private bool IsOnCurrentPage(FrameworkElement viewPort, FrameworkElement element
Rect
viewPortBounds
=
new
Rect
(
new
Point
(),
viewPort
.
RenderSize
);
Rect
elementBounds
=
new
Rect
(
new
Point
(),
element
.
RenderSize
);
elementBounds
=
element
.
TransformToAncestor
(
viewPort
).
TransformBounds
(
elementBounds
);
elementBounds
=
CorrectCatastrophicCancellation
(
element
.
TransformToAncestor
(
viewPort
)
).
TransformBounds
(
elementBounds
);
bool
northSouth
=
(
axis
==
FocusNavigationDirection
.
Up
||
axis
==
FocusNavigationDirection
.
Down
);
bool
eastWest
=
(
axis
==
FocusNavigationDirection
.
Left
||
axis
==
FocusNavigationDirection
.
Right
);
...
...
@@ -3078,6 +3078,46 @@ private bool IsOnCurrentPage(FrameworkElement viewPort, FrameworkElement element
return
ElementViewportPosition
.
None
;
}
// in large virtualized hierarchical lists (TreeView or grouping), the transform
// returned by element.TransformToAncestor(viewport) is vulnerable to catastrophic
// cancellation. If element is at the top of the viewport, but embedded in
// layers of the hierarchy, the contributions of the intermediate elements add
// up to a large positive number which should exactly cancel out the large
// negative offset of the viewport's direct child to produce net offset of 0.0.
// But floating-point drift while accumulating the intermediate offsets and
// catastrophic cancellation in the last step may produce a very small
// non-zero number instead (e.g. -0.0000000000006548). This can lead to
// infinite loops and incorrect decisions in layout.
// To mitigate this problem, replace near-zero offsets with zero.
private
static
GeneralTransform
CorrectCatastrophicCancellation
(
GeneralTransform
transform
)
{
MatrixTransform
matrixTransform
=
transform
as
MatrixTransform
;
if
(
matrixTransform
!=
null
)
{
bool
needNewTransform
=
false
;
Matrix
matrix
=
matrixTransform
.
Matrix
;
if
(
matrix
.
OffsetX
!=
0.0
&&
LayoutDoubleUtil
.
AreClose
(
matrix
.
OffsetX
,
0.0
))
{
matrix
.
OffsetX
=
0.0
;
needNewTransform
=
true
;
}
if
(
matrix
.
OffsetY
!=
0.0
&&
LayoutDoubleUtil
.
AreClose
(
matrix
.
OffsetY
,
0.0
))
{
matrix
.
OffsetY
=
0.0
;
needNewTransform
=
true
;
}
if
(
needNewTransform
)
{
transform
=
new
MatrixTransform
(
matrix
);
}
}
return
transform
;
}
private
static
bool
ElementIntersectsViewport
(
Rect
viewportRect
,
Rect
elementRect
)
{
if
(
viewportRect
.
IsEmpty
||
elementRect
.
IsEmpty
)
...
...
src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Controls/VirtualizingStackPanel.cs
浏览文件 @
48258a02
...
...
@@ -5550,7 +5550,7 @@ private void CoerceScrollingViewportOffset(ref Rect viewport, Size extent, bool
bool areContainersUniformlySized,
double uniformOrAverageContainerSize)
{
if (firstContainer == null)
if (firstContainer == null
|| IsViewportEmpty(isHorizontal, viewport)
)
{
return -1.0; // undefined if no children in view
}
...
...
src/Microsoft.DotNet.Wpf/src/System.Windows.Controls.Ribbon/Microsoft/Windows/Controls/Ribbon/RibbonHelper.cs
浏览文件 @
48258a02
...
...
@@ -1059,7 +1059,11 @@ public static bool IsOurWindow(IntPtr hwnd, DependencyObject element)
// popups when both active source and current captured is
// null due to clicking some where else should be handled by
// click through event handler.
ReacquireCapture
(
targetCapture
,
targetFocus
);
if
(!
ReacquireCapture
(
targetCapture
,
targetFocus
))
{
// call the setter if we couldn't reacquire capture
setter
(
false
);
}
e
.
Handled
=
true
;
}
else
...
...
@@ -1078,7 +1082,11 @@ public static bool IsOurWindow(IntPtr hwnd, DependencyObject element)
{
// If a descendant of targetCapture is losing capture
// then take capture on targetCapture
ReacquireCapture
(
targetCapture
,
targetFocus
);
if
(!
ReacquireCapture
(
targetCapture
,
targetFocus
))
{
// call the setter if we couldn't reacquire capture
setter
(
false
);
}
e
.
Handled
=
true
;
}
else
if
(!
IsCaptureInSubtree
(
targetCapture
))
...
...
@@ -1092,13 +1100,14 @@ public static bool IsOurWindow(IntPtr hwnd, DependencyObject element)
}
}
private
static
void
ReacquireCapture
(
UIElement
targetCapture
,
UIElement
targetFocus
)
private
static
bool
ReacquireCapture
(
UIElement
targetCapture
,
UIElement
targetFocus
)
{
Mouse
.
Capture
(
targetCapture
,
CaptureMode
.
SubTree
);
if
(
targetFocus
!=
null
&&
!
targetFocus
.
IsKeyboardFocusWithin
)
bool
success
=
Mouse
.
Capture
(
targetCapture
,
CaptureMode
.
SubTree
);
if
(
success
&&
targetFocus
!=
null
&&
!
targetFocus
.
IsKeyboardFocusWithin
)
{
targetFocus
.
Focus
();
}
return
success
;
}
public
static
bool
IsMousePhysicallyOver
(
UIElement
element
)
...
...
src/Microsoft.DotNet.Wpf/src/System.Windows.Controls.Ribbon/Microsoft/Windows/Controls/Ribbon/RibbonMenuButton.cs
浏览文件 @
48258a02
...
...
@@ -1513,7 +1513,10 @@ private void OnGotKeyboardFocusThunk(KeyboardFocusChangedEventArgs e)
{
// Call base.OnIsKeyboardFocusWithinChanged only if the new focus
// is not a direct descendant of menu button.
// It's possible to get here when disabled, which can lead to a
// focus war resulting in StackOverflow. Don't start the war.
if
(
e
.
OriginalSource
!=
this
&&
this
.
IsEnabled
&&
!
TreeHelper
.
IsVisualAncestorOf
(
this
,
e
.
OriginalSource
as
DependencyObject
))
{
BaseOnIsKeyboardFocusWithin
();
...
...
@@ -1528,13 +1531,19 @@ protected override void OnGotKeyboardFocus(KeyboardFocusChangedEventArgs e)
if
(
ribbonCurrentSelection
!=
null
&&
IsDropDownOpen
)
{
// If the drop down is open and the ribbonCurrentSelection is valid
// but still popup doesnt have focus within,
// then focus the current selection.
// It's possible to get here when disabled, or when an app explicitly
// moves focus in a GotKeyboardFocus handler called earlier in the
// bubbling route. Either of these can lead to a
// focus war resulting in StackOverflow. Don't start the war
UIElement
popupChild
=
_popup
.
TryGetChild
();
if
(
popupChild
!=
null
&&
this
.
IsEnabled
&&
this
.
IsKeyboardFocusWithin
&&
!
popupChild
.
IsKeyboardFocusWithin
)
{
// If the drop down is open and the ribbonCurrentSelection is valid
// but still popup doesnt have focus within,
// then focus the current selection.
ribbonCurrentSelection
.
Focus
();
}
}
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录