Навигация в приложении NativeScript с Angular 2 Router

Разработка /
Разработка: Навигация в приложении NativeScript с Angular 2 Router

Когда вы вдоволь наигрались с приложениями из одной страницы, вам придётся разобраться с навигацией между несколькими страницами. Сегодня мы как раз поговорим об этом.

Если вы следили за разработкой 2, начиная с беты, то видели, что компоненты навигации кардинально менялись почти в каждом релизе. А те, кто наблюдал за NativeScript и , также знают, что компания Telerik использовала все имеющиеся возможности Angular 2 в их текущем состоянии. Именно поэтому навигация в приложениях NativeScript Angular 2 менялась так часто за прошедший год. Однако, Angular 2 теперь официально вышел и Angular 2 Router не будет больше так сильно меняться.

Мы рассмотрим несложную навигацию между двумя компонентами Angular 2 в мобильном приложении на NativeScript под и iOS, используя стабильный Angular 2 Router.

Как всегда, мы начнём с чистого проекта NativeScript. Выполните в консоли следующие команды:

tns create MyProject --ng
cd MyProject
tns platform add ios
tns platform add android

В этом проекте мы используем два разных роутера, ни один из которых не включен в базовый шаблон NativeScript. Выполните следующие команды в папке app вашего проекта:

mkdir -p components/page1
mkdir -p components/page2
touch components/page1/page1.ts
touch components/page1/page1.html
touch components/page2/page2.ts
touch components/page2/page2.html

Если вам не удалось выполнить команды mkdir и touch или вам просто лень это делать, то просто создайте эти папки и файлы вручную.

Посмотрим сначала на вторую страницу нашего приложения, или, другими словами, страницу, на которую мы планируем перейти.

Откроем файл app/components/page2/page2.ts и вставим следующий код:

import {Component} from "@angular/core";
 
@Component({
    selector: "page2",
    templateUrl: "./components/page2/page2.html",
})
export class Page2Component {
 
    public constructor() {}
 
}

В этом TypeScript коде нет ничего особенного, мы просто привязываем к нему соответствующий файл HTML. Не забудьте создать класс Page2Component.

После этого откроем файл app/components/page2/page2.html и добавим такую разметку:

<ActionBar title="Page 2">
    <NavigationButton text="Back"></NavigationButton>
</ActionBar>
<StackLayout>
</StackLayout>

Здесь мы создаём верхнюю панель с кнопкой «Назад» и пустой макет. Пока оставим название страницы в панели такой, этого более чем достаточно для понимания, на какой мы находимся странице.

Теперь перейдём к первой странице, она будет и основной при открытии приложения.

Откроем файл app/components/page1/page1.ts и добавим следующий TypeScript код:

import {Component} from "@angular/core";
import {Router} from "@angular/router";
 
@Component({
    selector: "page1",
    templateUrl: "./components/page1/page1.html",
})
export class Page1Component {
 
    public constructor(private router: Router) {
 
    }
 
    public onTap() {
        this.router.navigate(["page2"]);
    }
 
}

Вообще этот код сильно похож на тот, что мы прописали во второй странице. Однако, здесь мы добавили метод onTap и импортировали компонент Angular 2 Router. После добавления роутера в конструктор, мы можем использовать его для навигации к любому доступному роуту.

У нас пока нет роутов, но мы вполне можем предположить, что page2 соответствует нашей второй странице. Через минуту мы это исправим.

Откроем файл app/components/page1/page1.html и добавим в него следующую разметку HTML:

<ActionBar title="Page 1">
    <ActionItem text="Next" ios.position="right" (tap)="onTap()"></ActionItem>
</ActionBar>
<StackLayout>
</StackLayout>

Обратили внимание на навигационную кнопку, вызывающую метод onTap при нажатии? Так будет работать навигация.

Но мы ещё не закончили. Помните, я говорил, что у нас ещё нет роутов? Нам нужно их создать.

Создадим файл app/app.routing.ts в папке проекта. В этот файл добавим такой код:

import { Page1Component } from "./components/page1/page1";
import { Page2Component } from "./components/page2/page2";
 
export const appRoutes: any = [
    { path: "", component: Page1Component },
    { path: "page2", component: Page2Component }
];
 
export const appComponents: any = [
    Page1Component,
    Page2Component
];

Мы импортировали все имеющиеся страницы в первых строках файла. Зададим доступные роуты в массиве appRoutes, где path это значение, используемое в навигации TypeScript, а component это компонент, соответствующий заданному path.

Чтобы сэкономить немного времени в следующем шаге, мы создадим массив всех доступных компонентов.

На следующем шаге мы включим информацию о роутах во всемогущий блок @NgModule, находящийся в файле app/main.ts. Этот файл будет примерно такой:

// this import should be first in order to load some required settings (like globals and reflect-metadata)
import { platformNativeScriptDynamic, NativeScriptModule } from "nativescript-angular/platform";
import { NgModule } from "@angular/core";
import { AppComponent } from "./app.component";
import { NativeScriptRouterModule } from "nativescript-angular/router";
import { appComponents, appRoutes } from "./app.routing";
 
@NgModule({
    declarations: [AppComponent, ...appComponents],
    bootstrap: [AppComponent],
    imports: [
        NativeScriptModule,
        NativeScriptRouterModule,
        NativeScriptRouterModule.forRoot(appRoutes)
    ],
})
class AppComponentModule {}
 
platformNativeScriptDynamic().bootstrapModule(AppComponentModule);

Мы импортировали NativeScriptRouterModule и константы, заданные перед этим в файле app/app.routing.ts.

В блоке @NgModule мы определили все компоненты из массива appComponents в свойстве declarations. Импортировали NativeScriptRouterModule и доступные роуты в свойстве imports.

Всё почти готово!

Ещё хорошо бы сразу определить, откуда эти роуты будут видны. Отроем файл app/app.component.html и заменим всю HTML разметку следующей:

<page-router-outlet></page-router-outlet>

Теперь при запуске приложения навигация между страницами будет работать как надо.

Передача параметров между роутами


А что, если вам понадобится передать кое-какую информацию между роутами? Как вариант, можно передать идентификатор из списка, а затем запросить этот идентификатор из второй страницы.

Немного изменим наш код, чтобы можно было так и сделать.

Откроем файл app/app.routing.ts и изменим следующую строку:

{ path: "page2/:name", component: Page2Component }

Здесь мы добавили /:name в path. Теперь мы можем передать переменную, представляющую name.

Чтобы передать данные из первой страницы, откроем файл app/components/page1/page1.ts и изменим команду навигации вот так:

this.router.navigate(["page2", "Nic Raboy"]);

Здесь мы передаём строку с моим именем в навигационном запросе. На второй странице нам нужно ожидать эту переменную и получить её.

В файле app/components/page2/page2.ts заменим код на следующий:

import {Component} from "@angular/core";
import {ActivatedRoute} from "@angular/router";
 
@Component({
    selector: "page2",
    templateUrl: "./components/page2/page2.html",
})
export class Page2Component {
 
    public fullName: string;
 
    public constructor(private route: ActivatedRoute) {
        this.route.params.subscribe((params) => {
            this.fullName = params["name"];
        });
    }
 
}

Для получения данных с главной страницы, компонент ActivatedRoute должен быть импортирован. В методе constructor мы подписались на параметры навигации и присвоили их переменной fullName. После этого мы можем вывести значение этой переменной в UI.

В файле app/components/page2/page2.html изменим HTML разметку на такую:

<ActionBar title="Page 2">
    <NavigationButton text="Back"></NavigationButton>
</ActionBar>
<StackLayout>
    <Label text="Hello {{fullName}}"></Label>
</StackLayout>

На экран будет выведено “Hello Nic Raboy”, когда вы перейдёте на эту страницу.

Заключение


Вот так просто можно использовать стабильную версию Angular 2 Router для построения навигации между страницами в приложении NativeScript под Android и iOS. Мы построили не просто навигацию, но ещё и предусмотрели возможность передать параметр с данными между страницами.

Видеоверсия этой статью (на англ.):.

Nic Raboy Navigating A NativeScript App With The Angular 2 Router
0 комментариев
Только зарегистрированные и авторизованные пользователи могут оставлять комментарии.