@@ -73,32 +73,79 @@ protected override DependencyObject GetContainerForItemOverride()
73
73
74
74
protected override void PrepareContainerForItemOverride ( DependencyObject element , object item )
75
75
{
76
- base . PrepareContainerForItemOverride ( element , item ) ;
76
+ if ( IsUsingOwnContainerAsTemplateRoot && element is ContentPresenter cp )
77
+ {
78
+ // ItemsControl::PrepareContainerForItemOverride will apply the ItemContainerStyle to the element which is not something we want here,
79
+ // since it can throw: The DP [WrongDP] is owned by [Control] and cannot be used on [ContentPresenter].
80
+ // While this doesnt break the control or the visual, it can cause a scaling performance degradation.
81
+
82
+ cp . ContentTemplate = ItemTemplate ;
83
+ cp . ContentTemplateSelector = ItemTemplateSelector ;
84
+
85
+ cp . DataContext = item ;
86
+ SetContent ( cp , item ) ;
87
+
88
+ #if ! HAS_UNO
89
+ // force template materialization
90
+ cp . Measure ( Size . Empty ) ;
91
+ #endif
77
92
78
- void SetupTabBarItem ( TabBarItem item )
93
+ if ( cp . GetFirstChild ( ) is TabBarItem tbi )
94
+ {
95
+ ApplyContainerStyle ( tbi ) ;
96
+ SetupTabBarItem ( tbi ) ;
97
+ }
98
+ }
99
+ else
79
100
{
80
- item . IsSelected = IsSelected ( IndexFromContainer ( element ) ) ;
81
- item . Click += OnTabBarItemClick ;
82
- item . IsSelectedChanged += OnTabBarIsSelectedChanged ;
101
+ base . PrepareContainerForItemOverride ( element , item ) ;
102
+ if ( element is TabBarItem tbi )
103
+ {
104
+ SetupTabBarItem ( tbi ) ;
105
+ }
83
106
}
84
107
85
- if ( element is TabBarItem container )
108
+ void SetContent ( ContentPresenter cp , object item )
86
109
{
87
- SetupTabBarItem ( container ) ;
110
+ if ( string . IsNullOrEmpty ( DisplayMemberPath ) )
111
+ {
112
+ cp . Content = item ;
113
+ }
114
+ else
115
+ {
116
+ cp . SetBinding ( ContentPresenter . ContentProperty , new Binding
117
+ {
118
+ Source = item ,
119
+ Path = new ( DisplayMemberPath ) ,
120
+ } ) ;
121
+ }
88
122
}
89
- else if ( IsUsingOwnContainerAsTemplateRoot &&
90
- element is ContentPresenter outerContainer )
123
+ void ApplyContainerStyle ( TabBarItem tbi )
91
124
{
92
- var templateRoot = outerContainer . ContentTemplate . LoadContent ( ) ;
93
- if ( templateRoot is TabBarItem tabBarItem )
125
+ var localStyleValue = tbi . ReadLocalValue ( FrameworkElement . StyleProperty ) ;
126
+ var isStyleSetFromTabBar = tbi . IsStyleSetFromTabBar ;
127
+
128
+ if ( localStyleValue == DependencyProperty . UnsetValue || isStyleSetFromTabBar )
94
129
{
95
- outerContainer . ContentTemplate = null ;
96
- SetupTabBarItem ( tabBarItem ) ;
97
- tabBarItem . DataContext = item ;
98
- tabBarItem . Style ??= ItemContainerStyle ;
99
- outerContainer . Content = tabBarItem ;
130
+ var style = ItemContainerStyle ?? ItemContainerStyleSelector ? . SelectStyle ( item , tbi ) ;
131
+ if ( style is { } )
132
+ {
133
+ tbi . Style = style ;
134
+ tbi . IsStyleSetFromTabBar = true ;
135
+ }
136
+ else
137
+ {
138
+ tbi . ClearValue ( FrameworkElement . StyleProperty ) ;
139
+ tbi . IsStyleSetFromTabBar = false ;
140
+ }
100
141
}
101
142
}
143
+ void SetupTabBarItem ( TabBarItem tbi )
144
+ {
145
+ tbi . IsSelected = IsSelected ( IndexFromContainer ( element ) ) ;
146
+ tbi . Click += OnTabBarItemClick ;
147
+ tbi . IsSelectedChanged += OnTabBarIsSelectedChanged ;
148
+ }
102
149
}
103
150
104
151
internal virtual bool IsSelected ( int index )
@@ -108,30 +155,26 @@ internal virtual bool IsSelected(int index)
108
155
109
156
protected override void ClearContainerForItemOverride ( DependencyObject element , object item )
110
157
{
111
- base . ClearContainerForItemOverride ( element , item ) ;
112
-
113
- void TearDownTabBarItem ( TabBarItem item )
158
+ if ( IsUsingOwnContainerAsTemplateRoot && element is ContentPresenter cp )
114
159
{
115
- item . Click -= OnTabBarItemClick ;
116
- item . IsSelectedChanged -= OnTabBarIsSelectedChanged ;
117
- if ( ! IsUsingOwnContainerAsTemplateRoot )
160
+ if ( cp . GetFirstChild ( ) is TabBarItem tbi )
118
161
{
119
- item . Style = null ;
162
+ TearDownTabBarItem ( tbi ) ;
120
163
}
121
164
}
122
- if ( element is TabBarItem container )
165
+ else
123
166
{
124
- TearDownTabBarItem ( container ) ;
125
- }
126
- else if ( IsUsingOwnContainerAsTemplateRoot &&
127
- element is ContentPresenter outerContainer )
128
- {
129
- if ( outerContainer . Content is TabBarItem innerContainer )
167
+ base . ClearContainerForItemOverride ( element , item ) ;
168
+ if ( element is TabBarItem tbi )
130
169
{
131
- TearDownTabBarItem ( innerContainer ) ;
132
- innerContainer . DataContext = null ;
170
+ TearDownTabBarItem ( tbi ) ;
133
171
}
134
- outerContainer . Content = null ;
172
+ }
173
+
174
+ void TearDownTabBarItem ( TabBarItem item )
175
+ {
176
+ item . Click -= OnTabBarItemClick ;
177
+ item . IsSelectedChanged -= OnTabBarIsSelectedChanged ;
135
178
}
136
179
}
137
180
0 commit comments