xamarin.forms - 如何在 iOS 中的选项卡项上制作多行文本
问题描述
我有 5 个选项卡,TabbedPage
最后 2 个选项卡的标题名称很长,在 Android 上,当没有更多空间用于文本时,它显示 3dots 为 ...。
例如。
tab 1 title - Title 1 for Tab1 tab 2 title - Title 2 for Tab2 tab 3 title - Title 3 for Tab3 Android - Title 1 f... | Title 2 f... | Title 3 f...
但在 iOS 上它不显示 3dots,它显示完整的文本,甚至可以覆盖另一个选项卡的标题。文本重叠的种类。
基本上我希望我的 TabbedPage 标题在多行上,我使用不同的内容页面作为我的 TabbedPage 的选项卡。我可以创建 MultiLine ContentPage n 它自己可以正常工作。但是当我将 MultiLine 标题内容页面设置为我的 TabbedPage 的选项卡时,它只显示第一行标题。
iOS 上 MultiLine TabbedPage Title 的任何解决方案,如下所示
我当前的渲染器代码
[assembly: ExportRenderer( typeof( TabbedPage ), typeof(ExtendedTabbedPageRenderer ) )]
namespace testBlu.iOS.Renderers
{
public class ExtendedTabbedPageRenderer : TabbedRenderer
{
public override void ViewDidAppear( bool animated )
{
base.ViewDidAppear( animated );
if( TabBar.Items != null )
{
UITabBarItem[] tabs = TabBar.Items;
foreach( UITabBarItem tab in tabs )
{
UITextAttributes selectedColor = new UITextAttributes { TextColor = UIColor.Black };
UITextAttributes fontSize = new UITextAttributes { Font = UIFont.SystemFontOfSize( 12 )};
tab.SetTitleTextAttributes( selectedColor, UIControlState.Normal );
tab.SetTitleTextAttributes( fontSize, UIControlState.Normal );
}
}
}
}
}
解决方案
如果需要在 Android 上显示相同的三个点,这里有一个解决方案。稍后如果有多线解决方案将在此处更新。
您可以使用自定义 TabbedRenderer来实现它。
[assembly: ExportRenderer(typeof(MainPage), typeof(ExtendedTabbedPageRenderer))]
namespace AppTab3.iOS
{
public class ExtendedTabbedPageRenderer : TabbedRenderer
{
public override void ViewWillAppear(bool animated)
{
base.ViewWillAppear(animated);
var tabs = Element as TabbedPage;
if(tabs != null)
{
for( int i = 0;i < TabBar.Items.Length;i++)
{
if (TabBar.Items[i] == null) return;
if(TabBar.Items[i].Title.Length > 6)
{
string showText = TabBar.Items[i].Title;
TabBar.Items[i].Title = showText.Substring(0, 5) + "...";
}
}
}
}
}
}
这里MainPage
里面的代码是一个TabbedPage
:<code>public partial class MainPage : TabbedPage
而这里我将 TabBar Text 的限制长度设置为6
. Xaml如下:
<?xml version="1.0" encoding="utf-8" ?>
<TabbedPage xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:d="http://xamarin.com/schemas/2014/forms/design"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
xmlns:views="clr-namespace:AppTab3.Views"
x:Class="AppTab3.Views.MainPage">
<TabbedPage.Children>
<NavigationPage Title="Browse">
<NavigationPage.Icon>
<OnPlatform x:TypeArguments="FileImageSource">
<On Platform="iOS" Value="tab_feed.png"/>
</OnPlatform>
</NavigationPage.Icon>
<x:Arguments>
<views:ItemsPage />
</x:Arguments>
</NavigationPage>
...
<NavigationPage Title="Page Five Long Title Page Five Long Title">
<NavigationPage.TitleView>
<Label Text="About Five Long Title" MaxLines="4"/>
</NavigationPage.TitleView>
<NavigationPage.Icon>
<OnPlatform x:TypeArguments="FileImageSource">
<On Platform="iOS"
Value="tab_about.png" />
</OnPlatform>
</NavigationPage.Icon>
<x:Arguments>
<views:AboutPage />
</x:Arguments>
</NavigationPage>
</TabbedPage.Children>
</TabbedPage>
效果:
=================================更新================= =============
我找到了在标签栏项目中实现多行标题的方法,需要修改代码TabbedRenderer
如下:
public override void ViewWillAppear(bool animated)
{
base.ViewWillAppear(animated);
var tabs = Element as TabbedPage;
if (tabs != null)
{
for (int i = 0; i < TabBar.Items.Length; i++)
{
if (TabBar.Items[i] == null) continue;
if (TabBar.Items[i].Title.Length > 6)
{
string[] splitTitle = TabBar.Items[i].Title.Split(" ");
TabBar.Items[i].Title = splitTitle[0] + "\n" + splitTitle[1];
UITabBarItem item = TabBar.Items[i] as UITabBarItem;
UIView view = item.ValueForKey(new Foundation.NSString("view")) as UIView;
UILabel label = view.Subviews[1] as UILabel;
//label.Text = "Hello\nWorld!";
label.Lines = 2;
label.LineBreakMode = UILineBreakMode.WordWrap;
//var frame = label.Frame;
//label.Frame = CGRect.FromLTRB(frame.Location.X, frame.Location.Y, frame.Size.Width, frame.Size.Height + 20);
}
}
}
}
效果:
注意:虽然这种方式可以实现,但苹果不建议这样做。会影响界面美观,并使Tabbar项的边框变形。
=============================使用共享代码更新================= ======
public override void ViewWillAppear(bool animated)
{
base.ViewWillAppear(animated);
var tabs = Element as TabbedPage;
if (tabs != null)
{
for (int i = 0; i < TabBar.Items.Length; i++)
{
if (TabBar.Items[i] == null) continue;
if (TabBar.Items[i].Title.Length > 6)
{
string[] splitTitle = TabBar.Items[i].Title.Split(" ");
if (null != splitTitle[1])
{
if (splitTitle[1].Length > 4)
{
string showText = splitTitle[1];
splitTitle[1] = showText.Substring(0, 3) + "...";
}
}
TabBar.Items[i].Title = splitTitle[0] + "\n" + splitTitle[1];
UITabBarItem item = TabBar.Items[i] as UITabBarItem;
UITextAttributes selectedColor = new UITextAttributes { TextColor = UIColor.Black };
UITextAttributes fontSize = new UITextAttributes { Font = UIFont.SystemFontOfSize(12) };
item.SetTitleTextAttributes(selectedColor, UIControlState.Selected);
item.SetTitleTextAttributes(fontSize, UIControlState.Selected);
UIView view = item.ValueForKey(new Foundation.NSString("view")) as UIView;
UILabel label = view.Subviews[1] as UILabel;
//label.Text = "Hello\nWorld!";
label.Lines = 2;
label.LineBreakMode = UILineBreakMode.WordWrap;
//var frame = label.Frame;
//label.Frame = CGRect.FromLTRB(frame.Location.X, frame.Location.Y, frame.Size.Width, frame.Size.Height + 10);
}
}
}
}
推荐阅读
- c# - 使用相机意图时未调用 OnActivityResult()?
- python - Python:计算允许领带的列表中项目的最大出现次数
- flutter - Riverpod FutureProvider 不断触发一次又一次
- ios - 将 ipa 上传到 AppStore 时如何修复“'CFBundleIconName' is missing”错误?
- mysql - 为一系列日期添加递增日期到 mysql 表
- sql - 仅返回一列中的日期与另一列中的日期最接近的行?
- javascript - 将记录集减少为具有嵌套对象数组的相同键的数组
- angular - Rxjs 将多个 observable 组合成一个 boolean observable
- bash - 如何附加到来自 powershell 输出的 bash 变量?
- heroku - nextjs,未在重定向时设置 cookie 标头