mirror of
https://github.com/bitwarden/mobile
synced 2025-12-16 00:03:22 +00:00
Added nofooter and noheader options to extendedtable view.
This commit is contained in:
@@ -38,6 +38,8 @@ namespace Bit.App.Controls
|
|||||||
}
|
}
|
||||||
|
|
||||||
public int EstimatedRowHeight { get; set; }
|
public int EstimatedRowHeight { get; set; }
|
||||||
|
public bool NoHeader { get; set; }
|
||||||
|
public bool NoFooter { get; set; }
|
||||||
|
|
||||||
protected override SizeRequest OnSizeRequest(double widthConstraint, double heightConstraint)
|
protected override SizeRequest OnSizeRequest(double widthConstraint, double heightConstraint)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -71,7 +71,7 @@ namespace Bit.App.Pages
|
|||||||
};
|
};
|
||||||
|
|
||||||
Title = "bitwarden";
|
Title = "bitwarden";
|
||||||
Content = buttonStackLayout;
|
Content = new ScrollView { Content = buttonStackLayout };
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task LoginAsync()
|
public async Task LoginAsync()
|
||||||
|
|||||||
@@ -61,18 +61,16 @@ namespace Bit.App.Pages
|
|||||||
|
|
||||||
var passwordLabel = new Label
|
var passwordLabel = new Label
|
||||||
{
|
{
|
||||||
|
Text = "The master password is the password you use to access your vault. It is very important that you do not forget your master password. There is no way to recover the password in the event that you forget it.",
|
||||||
LineBreakMode = LineBreakMode.WordWrap,
|
LineBreakMode = LineBreakMode.WordWrap,
|
||||||
FontSize = Device.GetNamedSize(NamedSize.Small, typeof(Label)),
|
FontSize = Device.GetNamedSize(NamedSize.Small, typeof(Label)),
|
||||||
Style = (Style)Application.Current.Resources["text-muted"]
|
Style = (Style)Application.Current.Resources["text-muted"],
|
||||||
|
Margin = new Thickness(15, (this.IsLandscape() ? 5 : 0), 15, 25)
|
||||||
};
|
};
|
||||||
var fs = new FormattedString();
|
|
||||||
fs.Spans.Add(new Span { Text = "The master password is the password you use to access your vault. It is very important that you do not forget your master password. There is" });
|
|
||||||
fs.Spans.Add(new Span { Text = " no way", FontAttributes = FontAttributes.Bold });
|
|
||||||
fs.Spans.Add(new Span { Text = " to recover the password in the event that you forget it." });
|
|
||||||
passwordLabel.FormattedText = fs;
|
|
||||||
|
|
||||||
var table2 = new FormTableView
|
var table2 = new FormTableView
|
||||||
{
|
{
|
||||||
|
NoHeader = true,
|
||||||
Root = new TableRoot
|
Root = new TableRoot
|
||||||
{
|
{
|
||||||
new TableSection
|
new TableSection
|
||||||
@@ -88,40 +86,21 @@ namespace Bit.App.Pages
|
|||||||
Text = "A master password hint can help you remember your password if you forget it.",
|
Text = "A master password hint can help you remember your password if you forget it.",
|
||||||
LineBreakMode = LineBreakMode.WordWrap,
|
LineBreakMode = LineBreakMode.WordWrap,
|
||||||
FontSize = Device.GetNamedSize(NamedSize.Small, typeof(Label)),
|
FontSize = Device.GetNamedSize(NamedSize.Small, typeof(Label)),
|
||||||
Style = (Style)Application.Current.Resources["text-muted"]
|
Style = (Style)Application.Current.Resources["text-muted"],
|
||||||
|
Margin = new Thickness(15, (this.IsLandscape() ? 5 : 0), 15, 25)
|
||||||
};
|
};
|
||||||
|
|
||||||
var layout = new RelativeLayout
|
var layout = new StackLayout
|
||||||
{
|
{
|
||||||
Padding = new Thickness(0, 0, 0, 35)
|
Children = { table, passwordLabel, table2, hintLabel },
|
||||||
|
Spacing = 0
|
||||||
};
|
};
|
||||||
layout.Children.Add(
|
|
||||||
table,
|
|
||||||
Constraint.Constant(0),
|
|
||||||
Constraint.Constant(0),
|
|
||||||
Constraint.RelativeToParent((parent) => { return parent.Width; })
|
|
||||||
);
|
|
||||||
layout.Children.Add(
|
|
||||||
passwordLabel,
|
|
||||||
Constraint.Constant(15),
|
|
||||||
Constraint.RelativeToView(table, (parent, sibling) => { return sibling.Y + sibling.Height - (this.IsPortrait() ? 45 : 25); }),
|
|
||||||
Constraint.RelativeToParent((parent) => { return parent.Width - 30; })
|
|
||||||
);
|
|
||||||
layout.Children.Add(
|
|
||||||
table2,
|
|
||||||
Constraint.Constant(0),
|
|
||||||
Constraint.RelativeToView(passwordLabel, (parent, sibling) => { return sibling.Y + sibling.Height - (this.IsPortrait() ? 15 : 10); }),
|
|
||||||
Constraint.RelativeToParent((parent) => { return parent.Width; })
|
|
||||||
);
|
|
||||||
layout.Children.Add(
|
|
||||||
hintLabel,
|
|
||||||
Constraint.Constant(15),
|
|
||||||
Constraint.RelativeToView(table2, (parent, sibling) => { return sibling.Y + sibling.Height - (this.IsPortrait() ? 45 : 25); }),
|
|
||||||
Constraint.RelativeToParent((parent) => { return parent.Width - 30; })
|
|
||||||
);
|
|
||||||
|
|
||||||
layout.LowerChild(table2);
|
layout.LayoutChanged += (sender, args) =>
|
||||||
layout.LowerChild(table);
|
{
|
||||||
|
passwordLabel.WidthRequest = layout.Bounds.Width - passwordLabel.Bounds.Left * 2;
|
||||||
|
hintLabel.WidthRequest = layout.Bounds.Width - hintLabel.Bounds.Left * 2;
|
||||||
|
};
|
||||||
|
|
||||||
var scrollView = new ScrollView
|
var scrollView = new ScrollView
|
||||||
{
|
{
|
||||||
@@ -207,6 +186,7 @@ namespace Bit.App.Pages
|
|||||||
HasUnevenRows = true;
|
HasUnevenRows = true;
|
||||||
EnableSelection = false;
|
EnableSelection = false;
|
||||||
VerticalOptions = LayoutOptions.Start;
|
VerticalOptions = LayoutOptions.Start;
|
||||||
|
NoFooter = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -37,6 +37,7 @@ namespace Bit.App.Pages
|
|||||||
|
|
||||||
var nameCell = new FormEntryCell(AppResources.Name);
|
var nameCell = new FormEntryCell(AppResources.Name);
|
||||||
nameCell.Entry.Text = folder.Name.Decrypt();
|
nameCell.Entry.Text = folder.Name.Decrypt();
|
||||||
|
nameCell.Tapped += NameCell_Tapped;
|
||||||
|
|
||||||
var deleteCell = new ExtendedTextCell { Text = AppResources.Delete, TextColor = Color.Red };
|
var deleteCell = new ExtendedTextCell { Text = AppResources.Delete, TextColor = Color.Red };
|
||||||
deleteCell.Tapped += DeleteCell_Tapped;
|
deleteCell.Tapped += DeleteCell_Tapped;
|
||||||
@@ -45,16 +46,18 @@ namespace Bit.App.Pages
|
|||||||
{
|
{
|
||||||
Intent = TableIntent.Settings,
|
Intent = TableIntent.Settings,
|
||||||
EnableScrolling = false,
|
EnableScrolling = false,
|
||||||
EnableSelection = false,
|
EnableSelection = true,
|
||||||
HasUnevenRows = true,
|
HasUnevenRows = true,
|
||||||
VerticalOptions = LayoutOptions.Start,
|
VerticalOptions = LayoutOptions.Start,
|
||||||
BackgroundColor = Color.Gray,
|
|
||||||
Margin = new Thickness(0, -1),
|
|
||||||
Root = new TableRoot
|
Root = new TableRoot
|
||||||
{
|
{
|
||||||
new TableSection()
|
new TableSection
|
||||||
{
|
{
|
||||||
nameCell
|
nameCell
|
||||||
|
},
|
||||||
|
new TableSection
|
||||||
|
{
|
||||||
|
deleteCell
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
@@ -65,23 +68,6 @@ namespace Bit.App.Pages
|
|||||||
mainTable.EstimatedRowHeight = 70;
|
mainTable.EstimatedRowHeight = 70;
|
||||||
}
|
}
|
||||||
|
|
||||||
var deleteTable = new ExtendedTableView
|
|
||||||
{
|
|
||||||
Intent = TableIntent.Settings,
|
|
||||||
EnableScrolling = false,
|
|
||||||
EnableSelection = true,
|
|
||||||
VerticalOptions = LayoutOptions.End,
|
|
||||||
BackgroundColor = Color.Yellow,
|
|
||||||
Margin = new Thickness(0, -1),
|
|
||||||
Root = new TableRoot
|
|
||||||
{
|
|
||||||
new TableSection()
|
|
||||||
{
|
|
||||||
deleteCell
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
var saveToolBarItem = new ToolbarItem(AppResources.Save, null, async () =>
|
var saveToolBarItem = new ToolbarItem(AppResources.Save, null, async () =>
|
||||||
{
|
{
|
||||||
if(!_connectivity.IsConnected)
|
if(!_connectivity.IsConnected)
|
||||||
@@ -108,7 +94,7 @@ namespace Bit.App.Pages
|
|||||||
}, ToolbarItemOrder.Default, 0);
|
}, ToolbarItemOrder.Default, 0);
|
||||||
|
|
||||||
Title = "Edit Folder";
|
Title = "Edit Folder";
|
||||||
Content = new ScrollView { Content = new StackLayout { Children = { mainTable, deleteTable } } };
|
Content = mainTable;
|
||||||
ToolbarItems.Add(saveToolBarItem);
|
ToolbarItems.Add(saveToolBarItem);
|
||||||
if(Device.OS == TargetPlatform.iOS)
|
if(Device.OS == TargetPlatform.iOS)
|
||||||
{
|
{
|
||||||
@@ -121,6 +107,15 @@ namespace Bit.App.Pages
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void NameCell_Tapped(object sender, EventArgs e)
|
||||||
|
{
|
||||||
|
var cell = sender as FormEntryCell;
|
||||||
|
if(cell != null)
|
||||||
|
{
|
||||||
|
cell.Entry.Focus();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private async void DeleteCell_Tapped(object sender, EventArgs e)
|
private async void DeleteCell_Tapped(object sender, EventArgs e)
|
||||||
{
|
{
|
||||||
// TODO: Validate the delete operation. ex. Cannot delete a folder that has sites in it?
|
// TODO: Validate the delete operation. ex. Cannot delete a folder that has sites in it?
|
||||||
|
|||||||
@@ -63,9 +63,9 @@ namespace Bit.App.Pages
|
|||||||
var table = new ExtendedTableView
|
var table = new ExtendedTableView
|
||||||
{
|
{
|
||||||
EnableScrolling = false,
|
EnableScrolling = false,
|
||||||
Intent = TableIntent.Menu,
|
Intent = TableIntent.Settings,
|
||||||
HasUnevenRows = true,
|
HasUnevenRows = true,
|
||||||
VerticalOptions = LayoutOptions.End,
|
NoFooter = true,
|
||||||
Root = new TableRoot
|
Root = new TableRoot
|
||||||
{
|
{
|
||||||
new TableSection
|
new TableSection
|
||||||
@@ -95,13 +95,16 @@ namespace Bit.App.Pages
|
|||||||
var stackLayout = new StackLayout
|
var stackLayout = new StackLayout
|
||||||
{
|
{
|
||||||
Orientation = StackOrientation.Vertical,
|
Orientation = StackOrientation.Vertical,
|
||||||
Children = { Password, table }
|
Children = { Password, table },
|
||||||
|
VerticalOptions = LayoutOptions.FillAndExpand,
|
||||||
|
Spacing = 0
|
||||||
};
|
};
|
||||||
|
|
||||||
var scrollView = new ScrollView
|
var scrollView = new ScrollView
|
||||||
{
|
{
|
||||||
Content = stackLayout,
|
Content = stackLayout,
|
||||||
Orientation = ScrollOrientation.Vertical
|
Orientation = ScrollOrientation.Vertical,
|
||||||
|
VerticalOptions = LayoutOptions.FillAndExpand
|
||||||
};
|
};
|
||||||
|
|
||||||
Title = "Generate Password";
|
Title = "Generate Password";
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ using System.ComponentModel;
|
|||||||
using Bit.App.Controls;
|
using Bit.App.Controls;
|
||||||
using Bit.iOS.Controls;
|
using Bit.iOS.Controls;
|
||||||
using CoreGraphics;
|
using CoreGraphics;
|
||||||
|
using Foundation;
|
||||||
using UIKit;
|
using UIKit;
|
||||||
using Xamarin.Forms;
|
using Xamarin.Forms;
|
||||||
using Xamarin.Forms.Platform.iOS;
|
using Xamarin.Forms.Platform.iOS;
|
||||||
@@ -24,8 +25,20 @@ namespace Bit.iOS.Controls
|
|||||||
UpdateRowHeight(view);
|
UpdateRowHeight(view);
|
||||||
UpdateEstimatedRowHeight(view);
|
UpdateEstimatedRowHeight(view);
|
||||||
UpdateSeparatorColor(view);
|
UpdateSeparatorColor(view);
|
||||||
|
|
||||||
|
if(view.NoFooter)
|
||||||
|
{
|
||||||
|
Control.SectionFooterHeight = 0.00001f;
|
||||||
|
}
|
||||||
|
if(view.NoHeader)
|
||||||
|
{
|
||||||
|
Control.SectionHeaderHeight = 0.00001f;
|
||||||
|
}
|
||||||
|
|
||||||
|
SetSource();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
|
protected override void OnElementPropertyChanged(object sender, PropertyChangedEventArgs e)
|
||||||
{
|
{
|
||||||
base.OnElementPropertyChanged(sender, e);
|
base.OnElementPropertyChanged(sender, e);
|
||||||
@@ -44,6 +57,15 @@ namespace Bit.iOS.Controls
|
|||||||
{
|
{
|
||||||
SetSelection(view);
|
SetSelection(view);
|
||||||
}
|
}
|
||||||
|
else if(e.PropertyName == TableView.HasUnevenRowsProperty.PropertyName)
|
||||||
|
{
|
||||||
|
SetSource();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void SetSource()
|
||||||
|
{
|
||||||
|
Control.Source = new CustomTableViewModelRenderer((ExtendedTableView)Element);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void SetScrolling(ExtendedTableView view)
|
private void SetScrolling(ExtendedTableView view)
|
||||||
@@ -85,5 +107,70 @@ namespace Bit.iOS.Controls
|
|||||||
{
|
{
|
||||||
Control.SeparatorColor = view.SeparatorColor.ToUIColor(UIColor.Gray);
|
Control.SeparatorColor = view.SeparatorColor.ToUIColor(UIColor.Gray);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public class CustomTableViewModelRenderer : UnEvenTableViewModelRenderer
|
||||||
|
{
|
||||||
|
private readonly ExtendedTableView _view;
|
||||||
|
|
||||||
|
public CustomTableViewModelRenderer(ExtendedTableView model)
|
||||||
|
: base(model)
|
||||||
|
{
|
||||||
|
_view = model;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override nfloat GetHeightForRow(UITableView tableView, NSIndexPath indexPath)
|
||||||
|
{
|
||||||
|
if(_view.HasUnevenRows)
|
||||||
|
{
|
||||||
|
return UITableView.AutomaticDimension;
|
||||||
|
}
|
||||||
|
|
||||||
|
return base.GetHeightForRow(tableView, indexPath);
|
||||||
|
}
|
||||||
|
|
||||||
|
public override nfloat GetHeightForHeader(UITableView tableView, nint section)
|
||||||
|
{
|
||||||
|
if(_view.NoHeader)
|
||||||
|
{
|
||||||
|
return 0.00001f;
|
||||||
|
}
|
||||||
|
|
||||||
|
return base.GetHeightForHeader(tableView, section);
|
||||||
|
}
|
||||||
|
|
||||||
|
public override UIView GetViewForHeader(UITableView tableView, nint section)
|
||||||
|
{
|
||||||
|
if(_view.NoHeader)
|
||||||
|
{
|
||||||
|
return new UIView(CGRect.Empty);
|
||||||
|
}
|
||||||
|
|
||||||
|
return base.GetViewForHeader(tableView, section);
|
||||||
|
}
|
||||||
|
|
||||||
|
public override nfloat GetHeightForFooter(UITableView tableView, nint section)
|
||||||
|
{
|
||||||
|
if(_view.NoFooter)
|
||||||
|
{
|
||||||
|
return 0.00001f;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 1f;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override UIView GetViewForFooter(UITableView tableView, nint section)
|
||||||
|
{
|
||||||
|
if(_view.NoFooter)
|
||||||
|
{
|
||||||
|
var view = new UIView(CGRect.Empty)
|
||||||
|
{
|
||||||
|
Hidden = true
|
||||||
|
};
|
||||||
|
return view;
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user