I want to have a background image like the following for the header section of my navigation panel
I currently have an image to display the profile picture in a StackLayout. Instead of setting the BackgroundColor property to the StackLayout tag how can I add a background image?
<StackLayout>
<Image Source="profile.png" WidthRequest="75" HeightRequest="75" HorizontalOptions="FillAndExpand" VerticalOptions="FillAndExpand"/>
</Stacklayout>
You'll need to switch from Stacklayout to a something that allows it's views to overlap, like a Grid or Absolute layout.
To use a grid, simply put your image and your content in the same row:
<Grid>
<Image Grid.Row="0"
Aspect="AspectFill"
Source="airplane" />
<Label Grid.Row="0"
FontAttributes="Bold"
FontSize="Large"
HorizontalOptions="Center"
Text="Welcome to Xamarin.Forms!"
VerticalOptions="CenterAndExpand" />
</Grid>
Result:
:
Related
I'm working on a cross platform app on both iOS and Android.
Now I want to display some searched result in a big grid, every cell can be clicked. There should be 3 results in every row, and every cell in a same row should has a same height with a shadow frame. Every result may have a different height.
Here is a image demonstrated what I want (just like Excel):
Firstly, I tried to use a BindableLayout Grid, which has an indexed item list. Every item has a Row and a Col property to fill into a cell. But the Grid's height is different.
Here is the xaml.
<ContentPage.BindingContext>
<mvvm:GridViewModel />
</ContentPage.BindingContext>
<ContentPage.Content>
<StackLayout Margin="5,50,5,0" >
<Label Text="Result:" />
<ScrollView x:Name="scrollViewResult" VerticalOptions="StartAndExpand">
<Grid BindableLayout.ItemsSource="{Binding GridResult}" ColumnDefinitions="*,*,*" RowDefinitions="Auto" VerticalOptions="StartAndExpand">
<BindableLayout.ItemTemplate>
<DataTemplate>
<!-- Every cell is a nested Grid. Using grid is for the purpose of button.-->
<Grid x:Name="NestedGrid" Grid.Row="{Binding Row}" Grid.Column="{Binding Col}" RowDefinitions="Auto" ColumnDefinitions="*" >
<!-- Frame for the corner radius and shadow.-->
<Frame Grid.Row="0" Grid.Column="0" CornerRadius="5" Margin="1">
<!-- Label text is real display text.-->
<Label Text="{Binding Value}" Margin="-15" FontSize="Small" LineBreakMode="WordWrap" HorizontalOptions="Center" VerticalOptions="StartAndExpand" HorizontalTextAlignment="Center"/>
</Frame>
<!-- Here placing a hole-cell button for a better click gesture. -->
<Button Grid.Row="0" Grid.Column="0" BackgroundColor="Transparent" Clicked="Button_Clicked" Margin="5"/>
</Grid>
</DataTemplate>
</BindableLayout.ItemTemplate>
</Grid>
</ScrollView>
</StackLayout>
</ContentPage.Content>
It likes below. emmmmm, not good (a BindableLayout Grid):
Then, I tried to use nested BindableLayout Grid(only one row) in a BindableLayout StackLayout. Every item in StackLayout is a list, every item in the list has a Col property to fill into a cell. Act a little better but not enough, for some short text will still hold large blank, and some has different height in a row.
<ContentPage.BindingContext>
<mvvm:GridInGridViewModel />
</ContentPage.BindingContext>
<ContentPage.Content>
<StackLayout Margin="5,50,5,0" >
<Label Text="Result:" />
<ScrollView x:Name="scrollViewResult" VerticalOptions="FillAndExpand">
<StackLayout BindableLayout.ItemsSource="{Binding GridResult}">
<BindableLayout.ItemTemplate>
<DataTemplate>
<!-- Every Grid has one row and 3 columns.-->
<Grid x:Name="ARowGrid" Margin="5,5,5,0" ColumnSpacing="5" RowSpacing="15" RowDefinitions="Auto" ColumnDefinitions="30*,30*,30*" BindableLayout.ItemsSource="{Binding Items}">
<BindableLayout.ItemTemplate>
<DataTemplate>
<!-- Every cell in ARowGrid is a nested Grid. Using grid is for the purpose of button.-->
<Grid x:Name="NestedGrid" Grid.Row="0" Grid.Column="{Binding Col}" RowDefinitions="Auto" ColumnDefinitions="*" >
<!-- Frame for the corner radius and shadow.-->
<Frame Grid.Row="0" Grid.Column="0" CornerRadius="5" Margin="0">
<!-- Label text is real display text.-->
<Label Text="{Binding Value}" Margin="-15" FontSize="Small" LineBreakMode="WordWrap" HorizontalOptions="Center" VerticalOptions="Start" HorizontalTextAlignment="Center"/>
</Frame>
<!-- Here placing a hole-cell button for a better click gesture. -->
<Button Grid.Row="0" Grid.Column="0" BackgroundColor="Transparent" Clicked="Button_Clicked" Margin="5"/>
</Grid>
</DataTemplate>
</BindableLayout.ItemTemplate>
</Grid>
</DataTemplate>
</BindableLayout.ItemTemplate>
</StackLayout>
</ScrollView>
</StackLayout>
</ContentPage.Content>
It acts like this (a BindableLayout Grid in BindableLayout StackLayout):
So is there any way to adjust height of ever row of a grid to fit the content's height, with every cell in a row has the same height, the height is the max height of content(may be add some margin).
Added 1.======================
I tried the collection view. It not works well too.
The Xamarin as follows.
<ContentPage.BindingContext>
<mvvm:GridViewModel />
</ContentPage.BindingContext>
<ContentPage.Content>
<StackLayout Margin="5,50,5,0" >
<Label Text="Result:" />
<ScrollView x:Name="scrollViewResult" VerticalOptions="StartAndExpand">
<CollectionView ItemsSource="{Binding GridResult}" VerticalOptions="StartAndExpand">
<CollectionView.ItemsLayout>
<GridItemsLayout Orientation="Vertical"
Span="3"
VerticalItemSpacing="5"
HorizontalItemSpacing="5" />
</CollectionView.ItemsLayout>
<CollectionView.ItemTemplate>
<DataTemplate>
<!-- Every cell is a nested Grid. Using grid is for the purpose of button.-->
<Grid x:Name="NestedGrid" RowDefinitions="Auto" ColumnDefinitions="*" VerticalOptions="Start">
<!-- Frame for the corner radius and shadow.-->
<Frame Grid.Row="0" Grid.Column="0" CornerRadius="5" Margin="1">
<!-- Label text is real display text.-->
<Label Text="{Binding Value}" Margin="-15" FontSize="Small" LineBreakMode="WordWrap" HorizontalOptions="Center" VerticalOptions="StartAndExpand" HorizontalTextAlignment="Center"/>
</Frame>
<!-- Here placing a hole-cell button for a better click gesture. -->
<Button Grid.Row="0" Grid.Column="0" BackgroundColor="Transparent" Clicked="Button_Clicked" Margin="5"/>
</Grid>
</DataTemplate>
</CollectionView.ItemTemplate>
</CollectionView>
</ScrollView>
</StackLayout>
</ContentPage.Content>
Here is the result. Emm, not well.
CollectionView result
I did a test on myside and I found out that the RowDefinitions of inside grid is auto, if you set it as "*", the cells will have the same heigt.As microsoft document says about grid length:
The GridLength struct specifies a row height or a column width in terms of the GridUnitType enumeration, which has three members:
Auto – the row height or column width is autosized based on the cell
contents (Auto in XAML).
Star – leftover row height or column width is
allocated proportionally (a number followed by * in XAML).
Absolute – the row height or column width is a value in device-independent units (a number in XAML).
As what i mentioned above, adding a hidden label in a hidden frame can solve this problem. Also I set the Button's HeightRequest to a small value(just 1 row) and set Margin to a fixed value(just 5).
Here is the code.
<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:mvvm="clr-namespace:RecForYou.Mvvm"
x:Class="RecForYou.GridInGridPage">
<ContentPage.BindingContext>
<mvvm:GridInGridViewModel />
</ContentPage.BindingContext>
<ContentPage.Content>
<StackLayout Margin="5,50,5,0" >
<Label Text="Result:" />
<ScrollView x:Name="scrollViewResult" VerticalOptions="FillAndExpand">
<StackLayout BindableLayout.ItemsSource="{Binding GridResult}">
<BindableLayout.ItemTemplate>
<DataTemplate>
<!-- Every Grid has one row and 3 columns.-->
<Grid x:Name="ARowGrid" Margin="5,5,5,0" ColumnSpacing="5" RowSpacing="15" RowDefinitions="Auto" ColumnDefinitions="30*,30*,30*" BindableLayout.ItemsSource="{Binding Items}">
<BindableLayout.ItemTemplate>
<DataTemplate>
<!-- Every cell in ARowGrid is a nested Grid. Using grid is for the purpose of button.-->
<Grid x:Name="NestedGrid" Grid.Row="0" Grid.Column="{Binding Col}" RowDefinitions="Auto" ColumnDefinitions="*" >
<!-- Frame for the corner radius and shadow.-->
<Frame Grid.Row="0" Grid.Column="0" CornerRadius="5" Margin="0">
<!-- Label text is real display text.-->
<Label Text="{Binding Value}" Margin="-15" FontSize="Small" LineBreakMode="WordWrap" HorizontalOptions="Center" VerticalOptions="Start" HorizontalTextAlignment="Center"/>
</Frame>
<Frame Grid.Row="0" Grid.Column="0" CornerRadius="5" Margin="0" BackgroundColor="Transparent">
<!-- Label text is real display text.-->
<Label Text="{Binding HiddenValue}" Margin="-15" FontSize="Small" LineBreakMode="WordWrap" HorizontalOptions="Center" VerticalOptions="Start" HorizontalTextAlignment="Center" TextColor="Transparent"/>
</Frame>
<!-- Here placing a hole-cell button for a better click gesture. -->
<Button Grid.Row="0" Grid.Column="0" BackgroundColor="Transparent" Clicked="Button_Clicked" Margin="5" HeightRequest="10"/>
</Grid>
</DataTemplate>
</BindableLayout.ItemTemplate>
</Grid>
</DataTemplate>
</BindableLayout.ItemTemplate>
</StackLayout>
</ScrollView>
</StackLayout>
</ContentPage.Content>
</ContentPage>
And the hole project is in github
Here is the result.
result
I don't know if there is any performance issues for another frame and another label.
Is there any better solution?
When i have one StackLayout inside another one, there is a faint border shadow around it.
I don't like the way it looks, is there a way to get rid of it ?
Here is XAML of the bottom pannel:
<StackLayout Orientation="Horizontal"
HorizontalOptions="Fill"
VerticalOptions="EndAndExpand">
<Button Text="⌂"
HorizontalOptions="StartAndExpand"/>
<StackLayout>
<Button Text="Kontrola"
VerticalOptions="Start"
HorizontalOptions="CenterAndExpand"/>
<Label Text="Autorem zadání je Cermat.cz"
FontSize="Micro"
HorizontalOptions="FillAndExpand"
VerticalOptions="EndAndExpand"/>
</StackLayout>
<Button Text="˃"
HorizontalOptions="EndAndExpand"
FontSize="Title"
BackgroundColor="Gray"
BorderColor="Gray"
IsEnabled="False"/>
</StackLayout>
In your Stacklayout:
<StackLayout Orientation="Horizontal"
HorizontalOptions="Fill"
VerticalOptions="EndAndExpand">
you are not setting the Spacing to 0, in the Microsoft Documentation for Stacklayout it says:
By default, StackLayout will add a 6px margin between views.
And that's why you se those lines, it's the spacing between the 3 elements you have inside horizontally. But it's weird why you even see those lines, because you are not setting the background color to white in those elements. i don't know if you ommited that, since i don't see you setting the border color to green too.
As per the title, i have a label inside a frame, both set to fill and expand and its inside a Grid, wanted to know if its possible to expand automatically when the content of the label text goes to the next line
<Frame Grid.Row="1"
VerticalOptions="FillAndExpand"
HorizontalOptions="FillAndExpand"
Margin="15,25,15,10"
CornerRadius="25"
Padding="10"
HasShadow="False"
BorderColor="Transparent"
BackgroundColor="White">
<Label x:Name="QuestionLabel"
VerticalTextAlignment="Center"
HorizontalTextAlignment="Start"
VerticalOptions="FillAndExpand"
HorizontalOptions="FillAndExpand"
LineBreakMode="WordWrap"
Style="{x:StaticResource LabelTitleBold}"
Text="{Binding Question}"
TextColor="{x:StaticResource Primary}"/>
</Frame>
This is what i've done, any inputs would be deeply appreciated
Thanks
What you need to do is try setting the height of Row in RowDefinition of the Grid to Auto. This might help.
<RowDefinition Height="auto" />
Let me know
Hi i'm trying to place 2 image in xamarin forms using stackLayout.But it adds some space at the top of the form.I Used Blank Project.
my code is
<StackLayout>
<Image Source="review.jpg"
BackgroundColor="Transparent"
WidthRequest="300"
HeightRequest="100"
VerticalOptions="Start" HorizontalOptions="FillAndExpand"
FlexLayout.Grow="1">
<Image.GestureRecognizers>
<TapGestureRecognizer Tapped="Navigate_review"/>
</Image.GestureRecognizers>
</Image>
<Image Source="upload.jpg"
BackgroundColor="Transparent"
WidthRequest="320"
HeightRequest="100"
VerticalOptions="Start" HorizontalOptions="FillAndExpand"
FlexLayout.Grow="1">
<Image.GestureRecognizers>
<TapGestureRecognizer Tapped="Navigate_upload"/>
</Image.GestureRecognizers>
</Image>
</StackLayout>
i am getting this output:
Output Image 1
Output Image 2
It adds some extra space at the top of the page. how to set the layout to remove this space?
The code you post does not have any issue.
I reckon your app is created with Tabbed template. If that is the case, the empty space at the top is actually the tab. As shown in this image.
If you create a Blank project (not Tabbed nor MasterDetails), it will not have the empty spaces at the top. As shown in this image.
You can use the Margin attribute to remove the excess space on top, bottom, right or left. Let's assume, if we using a table view and it produces the 20 pixel excess space on top of the display. So we can reduce that excess space by using
<TableView Margin="0,-20,0,0" >
<TableVie/>
-20 using for reduce the excess 20pix😀
I think the problem is you are testing on emulators.Real devices will not show this issue I hope.
StackLayout and Grid have default spacing of 6. On StackLayout you can set Spacing. For more details, you can refer to this Document
Try this snippet:
<StackLayout
Spacing="0">
<Image
Source="hintsicon"
BackgroundColor="Transparent"
WidthRequest="300"
HeightRequest="100"
Aspect="Fill"
VerticalOptions="Start"
HorizontalOptions="FillAndExpand">
<Image.GestureRecognizers>
<TapGestureRecognizer
Tapped="Navigate_review" />
</Image.GestureRecognizers>
</Image>
<Image
Source="hintsicon"
BackgroundColor="Transparent"
WidthRequest="320"
HeightRequest="100"
Aspect="Fill"
VerticalOptions="Start"
HorizontalOptions="FillAndExpand">
<Image.GestureRecognizers>
<TapGestureRecognizer
Tapped="Navigate_upload" />
</Image.GestureRecognizers>
</Image>
</StackLayout>
I think you are using like below in your App.xaml.cs page:
MainPage = new NavigationPage(new MainPage());
I'm trying to create a ListView with a Image and Labels, but the problem is, I can't resize the image with the StackLayout together. That is my XAML Code :
<ListView x:Name="listView">
<ListView.ItemTemplate>
<DataTemplate>
<ViewCell>
<StackLayout BackgroundColor="#eee"
Orientation="Vertical">
<StackLayout Orientation="Vertical">
<Image Source="{Binding image}" />
<Label Text="{Binding title}"
TextColor="#f35e20" />
<Label Text="{Binding subtitle}"
HorizontalOptions="StartAndExpand"
TextColor="#503026" />
</StackLayout>
</StackLayout>
</ViewCell>
</DataTemplate>
</ListView.ItemTemplate>
I tryed to add a prop of Image HeightRequest and WidthRequest and the image did change but not the StackLayout
That is the Result :
And That's what i want :
From my comment, set ListView.HasUnevenRows = true so that the ListView does not restrict your cell's size and then you need to let the UI know that the cell's size changed by running ViewCell.ForceUpdateSize() on the instance of the ViewCell that got its Image resized.