I want to setup a background image for a page. Right now I am using
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="M.LaunchPage"
Title ="M" BackgroundImage="Mars.jpg">
<ContentPage.Content>
<StackLayout Padding="10,0,10,10" >
<Button VerticalOptions="CenterAndExpand" Text="Sign Up" TextColor="White" Clicked="OnSignUp" BackgroundColor="Maroon" />
<StackLayout Padding="10,0,10,10" Orientation="Horizontal" VerticalOptions="EndAndExpand" />
</StackLayout>
</ContentPage.Content>
</ContentPage>
This works well but the image is being filled multiple times to fit the screen. Cn anyone suggest better code so that I can fit the image on the page perfectly?
Thanks.
This is platform dependent, for example on iOS the following is used in the Form's iOS's PageRender:
View.BackgroundColor = UIColor.FromPatternImage(UIImage.FromBundle(bgImage));
The View.BackgroundColor will end up tiling your image when it is smaller the UIController's View dimensions as FromPatternImage is designed to be used with a small repeating pattern (for memory and draw performance reasons) and not full screen/page images.
In order for this auto-tiling not to happen, you would be to assign the background image in code based upon the device's screen resolution and page size at runtime and not statically assign it in XAML.
Note: You could bind the BackgroundImage property in a ViewModel where the calculations of which image to use could be done.
You should use each platform specifications, for example in iOS you need to have Mars#2x.jpg and Mars#3x.jpg,in our platform project in Forms you can specify from "Mars" it will pick the correct one.
On Android set the image in the correct dpi folder.
Related
I would like to create backdrop for pop up window.
By backdrop I mean semi transparent background which is behind popup and stretches on a whole application screen. This makes the popout window more dominant and blocks the possibility to click on anything else in the background.
It would be best if popup window xaml code is deep inside the structure of the view if possible. Not at the top of hierarchy or bottom.
My issue with this is that the backdrop size wont stretch over its parents size.
So if my view is
1000x1000
My content in view is
500x500
and my pop up window is in this 500x500 it wont stretch over this size.
I tried with Position absolute, relative, translatin x/y, adjusting margins to high values to get bigger size.
I just cant get it done.
Example
You can use the Plugin PopupPage .And set the layout of popup as you want
<?xml version="1.0" encoding="utf-8" ?>
<pages:PopupPage
xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:pages="clr-namespace:Rg.Plugins.Popup.Pages;assembly=Rg.Plugins.Popup"
xmlns:animations="clr-namespace:Rg.Plugins.Popup.Animations;assembly=Rg.Plugins.Popup"
x:Class="MyProject.MyPopupPage">
<!--You can set an animation in the xaml file or in the csharp code behind-->
<pages:PopupPage.Animation>
<animations:ScaleAnimation
PositionIn="Center"
PositionOut="Center"
ScaleIn="1.2"
ScaleOut="0.8"
DurationIn="400"
DurationOut="300"
EasingIn="SinOut"
EasingOut="SinIn"
HasBackgroundAnimation="True"/>
</pages:PopupPage.Animation>
<!--You can use any elements here which are extended from Xamarin.Forms.View-->
<StackLayout
VerticalOptions="Center"
HorizontalOptions="Center"
Padding="20, 20, 20, 20">
//...
</StackLayout>
</pages:PopupPage>
And for more details you can check https://github.com/rotorgames/Rg.Plugins.Popup/wiki/Getting-started
I am currently building my mobile application using Xamarin.Forms and i encountered a problem (on both platform of ios and android) when i tried to use Xamarin.Forms gestures more particularly a tap gesture on a xaml Label. Because i want to use this label as a link.
The problem is that this tab gesture that i used does not work sometime ( approximately 5 times test = 1 time bug).
During DEBUG when the problem occured i see that the tabbing is still recognized but it did not respond in the action i set up.
It occurs on both iOS and Android devices.
Here is my XAML code:
<RelativeLayout>
<Image Source="icon_question" WidthRequest="15" HeightRequest="15"></Image>
<Label Margin="15, -3, 0, 0" HorizontalOptions="CenterAndExpand" HorizontalTextAlignment="Center"
Text="Some text" TextColor="Blue" FontSize="15" TextDecorations="Underline">
<Label.GestureRecognizers>
<TapGestureRecognizer Tapped="_tabLinkForgetPassword"></TapGestureRecognizer>
</Label.GestureRecognizers>
</Label>
</RelativeLayout>
and here is my code behind:
private void _tabLinkForgetPassword(object s, EventArgs e)
{
App.Current.MainPage = new ResetPasswordPage(false);
}
I expect that the tab respond everytime, not just sometime like this. I appreciate all your help.
As stated by AndroDevil, you have to handle the tap gesture on a parent (a Grid, StackLayout, ContentView, whatever you want). in your case, why don't you use the Relative layout ? Thus, you can tap either the Label or the Image.
When you think it doesn't work, it is just that when you tap on the empty space : between characters (or even inside the void of a char like O (but admit it, kind of hard to tap on those few pixels)) of your text.
Last, you don't need to set NumberOfTapsRequired because as far as I remember, it is the default value.
I have an image in my app with a frame around it to make the image a circle. I want a custom shape for the Frame, but can't figure out how to get this exact shape.
(Please ignore the house inside the drawing, it is simply there to represent an Image in Xamarin, I only need the outline to be the shape).
I also don't require the Frame to have a colored border, only the shape.
Any help will be appreciated!
Here is my code right now for the Frame + Image:
<Frame x:Name="PictureFrame" Padding="0" Margin="0" HorizontalOptions="Center" BorderColor="Transparent" WidthRequest="80" HeightRequest="80" HasShadow="False">
<Image x:Name="Picture" Source="picture" Margin="0,0,0,0" Aspect="AspectFill"/>
</Frame>
You probably have to create a custom renderer to achieve what you're looking for. For example, on Android the Frame mask is actually implemented with a bezier path that you could control to your liking if you dive a bit deeper into the code.
Take a look at the FreshEssentials AdvancedFrame view which almost has what you need. The modification they've made is that you can have a sharp 90 degree angle on either both corners on the left or on the right. You'd simply have to modify this code a little bit to have a rounded corner on all except the top left corner.
What you need to modify are the following:
AdvancedFrame (In case you want the corner radiuses to be configurable separately or something else. This is the base that inherits from the original Frame control in Xamarin.Forms)
AdvancedFrameRendererDroid
AdvancedFrameRendereriOS
AdvancedFrameRendererUWP (Only if you require UWP support)
Tips:
On Android, the background mask for the frame is defined with the Path class.
On iOS, UIBezierPath class from the UIKit framework is used.
Now with Xamarin.Forms you can use Shapes. The Path Data is your circle with point.
<AbsoluteLayout
BackgroundColor="AliceBlue"
>
<Path
AbsoluteLayout.LayoutBounds="0,0,1,1"
AbsoluteLayout.LayoutFlags="All"
Margin="8"
Data="M142.798828,0 C221.365114,0.164668482 285,63.9009723 285,142.5 C285,221.200577 221.200577,285 142.5,285 C63.7994232,285 0,221.200577 0,142.5 C0,139.784357 0.0759637392,137.086456 0.225882227,134.408306 L0,133.828125 L0,0 L142.798828,0 Z"
Stroke="LightBlue"
StrokeThickness="2"
HorizontalOptions="Center"
VerticalOptions="Center"
/>
<Image
AbsoluteLayout.LayoutBounds="0,0,1,1"
AbsoluteLayout.LayoutFlags="All"
Aspect="AspectFit"
Source="brigadeiro"
HorizontalOptions="Center"
VerticalOptions="Center"
WidthRequest="94"
HeightRequest="94"
/>
</AbsoluteLayout>
I am simply displaying an Image on my Xamarin Forms page. The image is transparent and this is how it displaying on page:
How can I remove those white and grey background?
This is my source code:
<ContentPage.Content>
<StackLayout>
<Image x:Name="myimage" Aspect="Fill">
</Image>
</StackLayout>
</ContentPage.Content>
Code-behind
myimage.Source = ImageSource.FromResource("RailwayApp.bull.jpg");
My try:
I tried setting IsOpaque property to True/False neither worked. Also declared BackgroundColor="Transparent" on XAML page but not worked.
In this case you can't, the background is actually not transparent - it would have to be a transparent PNG or GIF to support this. This is a JPG, so the background is actually grey and white.
To make this work you will first have to actually make the image transparent by converting in one of the two transparent formats (and actually remove the background) and then it should display as transparent as expected.
From my previous experience and some research on the web, I don't know if it's possible to have the following behavior:
<ContentPage.Content>
<AbsoluteLayout BackgroundColor="#2F767B">
<AbsoluteLayout x:Name="ScreenLayoutAdapter" BackgroundColor="#235A5E"
AbsoluteLayout.LayoutFlags="All">
<AbsoluteLayout.LayoutBounds>
<OnPlatform x:TypeArguments="Rectangle" Android="0, 0, 1, 1" iOS="1, 1, 1, 0.975" WinPhone="0, 1, 1, 1"/>
</AbsoluteLayout.LayoutBounds>
<ListView x:Name="ListViewCourses" BackgroundColor="Transparent" RowHeight="90"
AbsoluteLayout.LayoutBounds="0.5,1,0.9,0.9"
AbsoluteLayout.LayoutFlags="All">
<ListView.ItemTemplate>
<DataTemplate>
<ViewCell>
<AbsoluteLayout Margin="2">
<!-- Your design for the cell template -->
</AbsoluteLayout>
</ViewCell>
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
</AbsoluteLayout>
</AbsoluteLayout>
</ContentPage.Content>
In the c# side, I then have a ObservableCollection<Item> that I bind with the ListViewCourses.
But now my question is:
When I touch an item, how can I change of DataTemplate cell?
I mean, it's a list of items but when I touch one, I want that the cell grows up and displays more information, about the item selected.
If I have to bring more information to make you understand, tell me
Thank in advance ! :)
What you could do, instead of changing the DataTemplate of a single item, is have all of the controls containing the extra information that you want to show, be set to IsVisible = false and then when it is clicked, set IsVisible = true on all the controls and also call ListView.ForceLayout() to force the ViewCell to get redrawn.
Finally, make sure ListView.HasUnevenRows = true or else the ViewCell will not change size.
Alternatively, you may be able to add the controls containing extra information to the ViewCell when it is selected, it may or may not be slower/faster depending on the number of items in the ListView, the amount of extra controls you are adding, and whether you need to query the DB or a service for that extra information.
Let me know if you have any questions/issues.
Edit: Actually, you will want to call ViewCell.ForceUpdateSize(), info here, in order to change the size of the ViewCell once selected. You also may need to store that ViewCell instance in a class level variable so that you can shrink it back down when the user clicks a different ViewCell in the list.
Edit #2: One last thing I have run into, is that on iOS, if you have enabled ListViewCachingStrategy.RecycleElement on your ListView, you will most likely not see any change in the ViewCell after making controls visible and calling ForceUpdateSize(). This might have something to do with the last paragraph here, but I am not sure how to properly fix/get around it at this time.
Edit #3: For example you might do something like this:
<ViewCell>
<!-- Use ListView.ItemTapped instead of the TapGestureRecognizer below -->
<!-- <ViewCell.GestureRecognizers>
<TapGestureRecognizer Tapped="OnViewCellTapped"/>
</ViewCell.GestureRecognizers> -->
<StackLayout>
<!-- Main info displayed by default -->
<StackLayout StyleId="DefaultStackLayout">
<Label Text="{Binding ItemName}"/>
<Label Text="{Binding ItemDates}"/>
<Label Text="{Binding ItemCredits}"/>
</StackLayout>
<!-- Extra info displayed upon selection -->
<StackLayout StyleId="ExtraStackLayout"
IsVisible="False">
<Label Text="{Binding ItemBuilding}"/>
<Label Text="{Binding ItemTeacher}"/>
<Label Text="{Binding ItemHours}"/>
</StackLayout>
</StackLayout>
</ViewCell>
Then when the user selects the cell, you would need to do something like this:
using System.Linq;
...
private void OnViewCellTapped(object sender, EventArgs args) {}
tapCount++;
ViewCell viewCellSender = (ViewCell)sender;
StackLayout rootStack = (StackLayout)viewCellSender.View;
StackLayout extraInfoStack = rootStack.Children.Where(stack => stack.StyleId == "ExtraStackLayout");
extraInfoStack.IsVisible = true;
viewCellSender.ForceUpdateSize();
}
I have not tested any of this or even attempted it before, so if the above does not work, I am confident that inserting the extraInfoStack element content once the ViewCell is clicked, will work. But give the above a try first. Obviously you will need to change the layouts if you want to use AbsoluteLayout and you will also need to change the OnViewCellTapped() casting code.
Edit #4: I usually try to steer clear of constant numbers for height and width values if possible but sometimes it is unavoidable. So for this all to work you are going to have to set ListView.HasUnevenRows = true and that means you will need to get rid of your ListView.RowHeight value completely since the rows need to be allowed to have variable height.
If at all possible, I would try to not set a constants height value, but if you absolutely cannot live without setting the height to a constants value, then you can probably give your ViewCell's inner AbsoluteLayout a HeightRequest of 120, but then you would need to change that value when the item is selected, after making your extra controls visible and before calling ViewCell.ForceUpdateSize(). Setting IsVisible to false is supposed to make it so that the control does not take up any space, so those extra controls should not mess with the sizing while they are hidden but I have never tried it myself.
If you run into issues, please let me know.