I need to implement layout like in Twitter app, where the app has TabView for primary information and SideDrawer for supplementary information.
If I try to init RadSideDrawer mainContent with TabView and Frame I got empty screen:
...
<nsDrawer:RadSideDrawer.mainContent>
<TabView androidTabsPosition="bottom">
<TabViewItem class="tab-view-item" title="catalog">
<Frame defaultPage="pages/catalog/catalog-page"></Frame>
</TabViewItem>
</TabView>
</nsDrawer:RadSideDrawer.mainContent>
...
But if I init RadSideDrawer mainContent with Frame I got correct page:
...
<nsDrawer:RadSideDrawer.mainContent>
<Frame defaultPage="pages/catalog/catalog-page"></Frame>
</nsDrawer:RadSideDrawer.mainContent>
...
What it the correct way to combine TabView Navigation and SideDrawer Navigation?
I suspect the Frame should be wrapped within TabViewItem.view and TabViewItem must be wrapped by <TabView.items>
<nsDrawer:RadSideDrawer.mainContent>
<TabView androidTabsPosition="bottom">
<TabView.items>
<TabViewItem class="tab-view-item" title="catalog">
<TabViewItem.view>
<Frame defaultPage="pages/catalog/catalog-page"></Frame>
</TabViewItem.view>
</TabViewItem>
</TabView.items>
</TabView>
</nsDrawer:RadSideDrawer.mainContent>
Related
I am having issues with GridLayout losing their column sizing inside a TabView whenever I go to another tab below the current index
An example is below where I am navigating from the 'Freaks' tab to the 'Legends' tab before it and the items inside the GridLayout lose their column position. All of them seem to revert back to column 0'. Both of the tabs uses the same component with only the data being passed as props being different.
Original GridLayout column position in 'Freaks' tab
GridLayout in 'Legends' tab losing column specifications
Gridlayout code would be
<GridLayout columns="40, *, auto" class="w-100 py-7 border-bottom-light" #longPress="optionsOpened">
<TImage :col="0" :src="image" class="w-40 h-40 round" />
<StackLayout :col="1" class="px-20" verticalAlignment="center">
<Label class="text-13" :text="`${data.attributes.first_name} ${data.attributes.last_name}`" textWrap="true" />
<Label v-if="role" class="text-11 text-grey text-capitalize" :text="data.attributes.jersey_number ? `#${data.attributes.jersey_number} ${role}` : role" />
</StackLayout>
<template v-if="!hide_action">
<StackLayout class="action-container" :col="2" orientation="horizontal">
<ActionTile class="at" :text="0xf00c" :is_icon="true" v-if="data.attributes.available == true" #tap.native="markAvailability(!data.attributes.available)" />
<ActionTile class="at" color="red" :text="0xf00d" :is_icon="true" v-if="data.attributes.available == false" #tap.native="markAvailability(!data.attributes.available)" />
</StackLayout>
</template>
</GridLayout>
Has anyone encountered a similar issue? If so, what was your fix? Any help would be much appreciated.
I am trying to test and example with MasterDetail. You can see the code in:
https://github.com/jrariasf/MD8/tree/master/MD8
The Master have 5 buttons to access to 4 detail pages (Home, MainPage, ViewA, ViewB and ViewC).
From ViewA, with 2 buttons I am able to load ViewB and ViewC
But I am not able to do that pushing a button in hambubrger menu then load the detail page adequated.
It only works if I put an absolute path in the CommandParameter in "PrismMasterDetailPage.xaml":
<?xml version="1.0" encoding="utf-8" ?>
<MasterDetailPage xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
xmlns:prism="http://prismlibrary.com"
prism:ViewModelLocator.AutowireViewModel="True"
x:Class="MD8.Views.PrismMasterDetailPage">
<MasterDetailPage.Master>
<ContentPage Title="Menu">
<StackLayout Padding="20">
<!-- TODO: // Update the Layout and add some real menu items -->
<Button Text="Home" Command="{Binding NavigateCommand}" CommandParameter="/PrismMasterDetailPage/NavigationPage/ViewA" />
<Button Text="MainPage" Command="{Binding NavigateCommand}" CommandParameter="/NavigationPage/MainPage" />
<Button Text="ViewA" Command="{Binding NavigateCommand}" CommandParameter="../ViewA" />
<Button Text="ViewB" Command="{Binding NavigateCommand}" CommandParameter="./ViewB" />
<Button Text="ViewC" Command="{Binding NavigateCommand}" CommandParameter="ViewC" />
</StackLayout>
</ContentPage>
</MasterDetailPage.Master>
</MasterDetailPage>
Then, in "PrismMasterDetailPageViewModel.cs"
void ExecuteCommandName(string page)
{
Console.WriteLine("PrismMasterDetailPageViewModel - ExecuteCommandName() Vamos a {0}", page);
_navigationService.NavigateAsync(page);
}
If I am in "/PrismMasterDetailPage/NavigationPage/ViewA", what I have to do to unload ViewA and load ViewB ?
For example, in App.xaml.cs the code is:
await NavigationService.NavigateAsync("PrismMasterDetailPage/NavigationPage/ViewA");
Then, execute the app on android emulator, push buttons of hamburger menu and the result it is not as I expected.
Pressing Home button, the _navigationService.GetNavigationUriPath() returns: /PrismMasterDetailPage/NavigationPage/ViewA/NavigationPage?useModalNavigation=true/ViewA
why?
If I press button ViewA or ViewB or ViewC, it don't show anything. But the OnNavigatedFrom() method is called on each View*ViewModel.cs
What is wrong?
Thanks!!
One fo the first things you need to do is understand where you are Navigating from. Navigation in Xamarin.Forms is very dependent on where you are Navigating from. Remember that without Prism you would do something like this:
var mdp = new MyMasterDetailPage
{
Detail = new NavigationPage(new ViewA)
};
In order to achieve a Hamburger Menu with Prism you typically would want a MasterDetailPage as the Application's Main Page. The next segment in the Navigation Uri must be a NavigationPage and the following page would generally be a ContentPage.
<Button Text="Home"
Command="{Binding NavigateCommand}"
CommandParameter="/PrismMasterDetailPage/NavigationPage/ViewA" />
Ok so looking at this first one, this is generally what you would use when navigating from the PrismApplication which is why it works.
<Button Text="MainPage"
Command="{Binding NavigateCommand}"
CommandParameter="/NavigationPage/MainPage" />
Looking at this one, this is really close to what you do want except you are doing an absolute navigation which means that you are resetting the Application.MainPage. What you actually need is a relative Uri because you are navigating from the MasterDetailPage.
<Button Text="ViewA"
Command="{Binding NavigateCommand}"
CommandParameter="../ViewA" />
This is completely wrong because ../{path} is only supported from within a NavigationPage and you are in a MasterDetailPage...
<Button Text="ViewB"
Command="{Binding NavigateCommand}"
CommandParameter="./ViewB" />
This is just not supported by Prism at all.
<Button Text="ViewC"
Command="{Binding NavigateCommand}"
CommandParameter="ViewC" />
This is setting the MasterDetailPage.Detail like:
mdp.Detail = new ViewC()
Of course as I mentioned above you need it to be
mdp.Detail = new NavigationPage(new ViewC());
Thanks a lot Dan Siegel ! (#Dan S.)
I have just seen your comment, a month ago, sorry.
I was a newbie in C# and Xamarin and Prism and I am still a newbie but less :-)
I have learnt and tested a lot in the last weeks and I understand better the concepts.
After reading you I know that ../{path} is only valid with a NavigationPage .
Futhermore, one problem I had was thar I was checking the value of "_navigationService.GetNavigationUriPath()" inside OnNavigatedTo method and as I read later, at that moment the UriPath is not the real final UriPath.
In my code I wrote:
public void OnNavigatedTo(INavigationParameters parameters)
{
Console.WriteLine("DEBUG - ViewAVM: We are in {0}",
_navigationService.GetNavigationUriPath());
}
I moved the GetNavigationUriPath() call to another method and the results were as I expected.
Thanks!!
Why does this following code produce this result: https://imgur.com/a/lQhLs8o ?
However, if I move the BottomNavigatorBar component to top position before CountryListComponent, it produces the desired result that looks like this: https://imgur.com/a/23z7bb2 ?
<template>
<Page actionBarHidden="true">
<DockLayout height="100%">
// first
<CountryListComponent dock="top">
// second
<BottomNavigationBar dock="bottom" activeColor="pink"
inactiveColor="yellow"
backgroundColor="black"
verticalAlignment="bottom"
#tabSelected="this.changeTab"
row="1">
<BottomNavigationTab title="Fiaarst" icon="icon-29.png" />
<BottomNavigationTab title="Second" icon="icon-29.png" />
<BottomNavigationTab title="Third" icon="icon-29.png" />
</BottomNavigationBar>
</DockLayout>
</Page>
</template>
CountryListComponent
<template>
<StackLayout backgroundColor="blue">
</StackLayout>
</template>
Refer the DockLayout documentation, by default stretchLastChild will be true which means BottomNavigationBar will take entire space if it's last child and vice versa.
I'm unable get showModal to pass context through a frame to the default page. Also, showingModally does not seem to fire when modal is loaded (I guess args from showingModally should pass context?).
I've tried the example provided on https://docs.nativescript.org/ui/modal-view under Custom Actionbar, because I need the modal to load within a frame. The modal opens and closes fine, but showingModally in the modal XML does not seem to run.
home/home-page.js
const modalView = "home/modal-root";
function openModal(args) {
console.log('Opens modal');
const mainpage = args.object.page;
const context = "some context";
mainpage.showModal(modalView, context, () => {
console.log('Modal closed');
}, true);
}
exports.openModal = openModal;
home/home-page.xml
<Page xmlns="http://www.nativescript.org/tns.xsd">
<Page.actionBar>
<ActionBar title="Modal view Navigation" />
</Page.actionBar>
<GridLayout rows="auto, *">
<Button text="Open modal" tap="openModal" textWrap="true" />
</GridLayout>
</Page>
home/modal-root.xml
<Frame defaultPage="home/modal-view-page" />
home/modal-view-page.js
function onShowingModally(args) {
console.log("onShowingModally");
}
exports.onShowingModally = onShowingModally;
function onCloseModal(args) {
args.object.closeModal();
}
exports.onCloseModal = onCloseModal;
home/modal-view-page.xml
<Page backgroundColor="green" showingModally="onShowingModally">
<Page.actionBar>
<ActionBar backgroundColor="red" title="Modal view" icon="">
</ActionBar>
</Page.actionBar>
<StackLayout backgroundColor="lightGreen">
<Label text="Modal view with ActionBar" style="text-align:center;" textWrap="true" />
<Button text="Close Modal" tap="onCloseModal" />
</StackLayout>
</Page>
I've added the example to https://play.nativescript.org/?template=play-js&id=lFxTi4&v=9
with console logging.
Console show "Opens modal" on open and "Modal closed" on close as expected (from home/home-page.js), but "onShowingModally" (home/modal-view-page.js) nevers shows in console.
I think the docs need to be fixed. When you have the Frame being shown modally, the event will be called on the Frame not on the page within. If you are showing a simple view instead of Frame, then the event should be called on the view, basically whatever is the root view for your modal and in your example it's the Frame.
Updated Playground
With my Xamarin cross-platform app, I have a drop-down menu which is created with the following XAML code:
<ContentPage>
<ContentPage.ToolbarItems>
<ToolbarItem Text="Add another child to my account" Order="Secondary" Priority="1" Clicked="AddAnotherChildClick" />
<ToolbarItem Text="Delete child from my account" Order="Secondary" Priority="2" Clicked="DeleteChildClick" />
<ToolbarItem Text="Log Out" Order="Secondary" Priority="3" Clicked="LogOutClick" />
</ContentPage.ToolbarItems>
</ContentPage>
I need to be able to control the background color and text color of the menu. It is currently grey with white text (see screenshot). I would like it black with orange text.
How can I change this - ideally using a global style?
If you are using Navigation page then you can do the follow:
var navPage = new NavigationPage(new YourPage());
this.MainPage = navPage;
navPage.BarBackgroundColor = Color.Orange;
navPage.BarTextColor = Color.Black;
It will work on iOS but on Android 5.0 and above the text color will not change. To change it see this link
How to change navigation bar text color in xamarin forms android