ユーザーインターフェイス / コンポーネント / RadListView / データ操作:グループ化、フィルタリング、並べ替え

RadListViewデータ操作

この記事では、RadListViewへの組み込み機能として利用可能な1つまたはすべてのデータ操作を有効にするプロセスについて説明します。 このコンポーネントは、基本的なデータ操作のすべてに使いやすいAPIを提供します。 これにより、グループ化、フィルタリング、および並べ替えの条件を強力に構成して、RadListViewに表示されるアイテムの任意の構成を実現できます。

"RadListView" のコンテキストでの「データ操作」とは、 "items" プロパティに設定された「生の」ソースコレクションに対して操作を行うことを意味します。 これらの操作には、グループ化、並べ替え、およびフィルタリングがあります。 それぞれを個別に使用することも、他のものと組み合わせて使用することもできます。 これにより、"items" に提供した「生の」ビジネスオブジェクトコレクションを変更せずに、 アイテムをフィルタリングしてグループ化できます。

グループ化

グループ化を有効にするには、グループ化機能の基準として使用されるオブジェクトを返す関数に "groupingFunction" プロパティ を設定するだけです。 このような関数の簡単な例を次に示します。

get myGroupingFunc(): (item: any) => any {
	return (item: DataItem) => {
		return item.category;
	};
}

グループ化テンプレート

カスタムグループテンプレートを設定しています。

<GridLayout rows="auto, *">
	<StackLayout orientation="horizontal">
		<Button text="{{isEnabled ? 'Disable grouping' : 'Enable grouping'}}" tap="toggleGrouping"/>
	</StackLayout>
	<lv:RadListView items="{{ dataItems }}"
					row="1"
					id="myListView"
					groupingFunction="{{ myGroupingFunc }}">
		<lv:RadListView.itemTemplate>
			<StackLayout orientation="vertical">
				<Label fontSize="20" text="{{ itemName }}"/>
				<Label fontSize="14" text="{{ itemDescription }}"/>
			</StackLayout>
		</lv:RadListView.itemTemplate>
		<lv:RadListView.groupTemplate>
			<GridLayout ios:height="50">
				<Label text="{{ category }}" class="groupLabel"/>
			</GridLayout>
		</lv:RadListView.groupTemplate>
	</lv:RadListView>
</GridLayout>

並べ換え

並べ替えは、"sortingFunction" プロパティに 2つのパラメーターと3種類の返り値を持つ関数を割り当てることで有効になります。 この関数はの返り値は、0(2つのパラメーターが等しい)、1(最初のパラメーターが大きい)、-1(2番目のパラメーターが大きい)となります。 このような関数の簡単な例を次に示します。

get mySortingFunc(): (item: any, otherItem: any) => number {
	return (item: DataItem, otherItem: DataItem) => {
		const res = item.id < otherItem.id ? -1 : item.id > otherItem.id ? 1 : 0;
		return res;
	};
}

フィルタリング

"RadListView" でフィルタリングを有効にするには、 "filteringFunction" プロパティを 1つのパラメーターを受け取る関数に設定し、 パラメーターとして渡されたアイテムを含める必要がある場合はtrueを返し、 そうでない場合はfalseを返します。 このような関数の簡単な例を次に示します。

get myFilteringFunc(): (item: any) => boolean {
	return (item: DataItem) => {
		return item.itemName.includes("Special Item");
	};
}

例1:グループ化、フィルタリング、並べ替えの実装

この例では、次の基準を使用して、同じ"RadListView" ですべてのデータ操作を有効にします。

<GridLayout rows="*, 7*">
	<StackLayout orientation="horizontal">
		<Button width="33%" text="{{isFilteringEnabled ? 'Disable filtering' : 'Enable filtering'}}" tap="toggleFilter"/>
		<Button width="33%" text="{{isSortingEnabled ? 'Disable sorting' : 'Enable sorting'}}" tap="toggleSorting"/>
		<Button width="33%" text="{{isGroupingEnabled ? 'Disable grouping' : 'Enable grouping'}}" tap="toggleGrouping"/>
	</StackLayout>
	<lv:RadListView itemSelected="onItemSelected" selectionBehavior="Press" id="myListView" row="1" items="{{ dataItems }}"
					sortingFunction="{{ mySortingFunc }}"
					filteringFunction="{{ myFilteringFunc }}"
					groupingFunction="{{ myGroupingFunc }}">
		<lv:RadListView.itemTemplate>
			<StackLayout orientation="vertical">
				<Label fontSize="20" text="{{ itemName }}"/>
				<Label fontSize="14" text="{{ itemDescription }}"/>
			</StackLayout>
		</lv:RadListView.itemTemplate>
	</lv:RadListView>
</GridLayout>
import { ViewModel } from "./multiple-model";
import { Page } from "tns-core-modules/ui/page";
import { RadListView } from "nativescript-ui-listview";

let page: Page;
let bindingContext: ViewModel;

export function onPageLoaded(args) {
    page = args.object;
    bindingContext = new ViewModel();
    page.bindingContext = bindingContext;
}

export function toggleFilter() {
    const listView = page.getViewById("myListView") as RadListView;
    if (!listView.filteringFunction) {
        listView.filteringFunction = bindingContext.myFilteringFunc;
        bindingContext.isFilteringEnabled = true;
    } else {
        listView.filteringFunction = undefined;
        bindingContext.isFilteringEnabled = false;
    }
}

export function toggleSorting() {
    const listView = page.getViewById("myListView") as RadListView;
    if (!listView.sortingFunction) {
        listView.sortingFunction = bindingContext.mySortingFunc;
        bindingContext.isSortingEnabled = true;
    } else {
        listView.sortingFunction = undefined;
        bindingContext.isSortingEnabled = false;
    }
}

export function toggleGrouping() {
    const listView = page.getViewById("myListView") as RadListView;
    if (!listView.groupingFunction) {
        listView.groupingFunction = bindingContext.myGroupingFunc;
        bindingContext.isGroupingEnabled = true;
    } else {
        listView.groupingFunction = undefined;
        bindingContext.isGroupingEnabled = false;
    }
}
import { ObservableArray } from "tns-core-modules/data/observable-array";
import { Observable } from"tns-core-modules/data/observable";

export class ViewModel extends Observable {

    private _items: ObservableArray<DataItem>;
    private _words = ["One", "Two", "Three", "Four", "Five", "Six", "Seven", "Eight", "Nine", "Ten"];

    constructor() {
        super();
        this.set("_items", new ObservableArray<DataItem>(items));
        this.isGroupingEnabled = true;
        this.isFilteringEnabled = true;
        this.isSortingEnabled = true;
    }

    get isGroupingEnabled() {
        return this.get("_isGroupingEnabled");
    }

    set isGroupingEnabled(value: boolean) {
        this.set("_isGroupingEnabled", value);
    }

    get isFilteringEnabled() {
        return this.get("_isFilteringEnabled");
    }

    set isFilteringEnabled(value: boolean) {
        this.set("_isFilteringEnabled", value);
    }

    get isSortingEnabled() {
        return this.get("_isSortingEnabled");
    }

    set isSortingEnabled(value: boolean) {
        this.set("_isSortingEnabled", value);
    }

    get dataItems() {
        return this.get("_items");
    }

    get myGroupingFunc(): (item: any) => any {
        return (item: DataItem) => {
            return item.category;
        };
    }

    get myFilteringFunc(): (item: any) => any {
        return (item: DataItem) => {
            return item.itemName.includes("Special Item");
        };
    }

    get mySortingFunc(): (item: any, otherItem: any) => number {
        return (item: DataItem, otherItem: DataItem) => {
            const res = item.id < otherItem.id ? -1 : item.id > otherItem.id ? 1 : 0;
            return res;
        };
    }

    private getRandomLengthString() {
        const sentenceLength = Math.round((Math.random() * 15));
        let result = this._words[0];
        for (let i = 0; i < sentenceLength; i++) {
            result += (this._words[i % this._words.length] + " ");
        }
        return result;
    }
}

export class DataItem {
    public id: number;
    public itemName: string;
    public itemDescription: string;
    public category: string;

    constructor(id: number, name: string, description: string, category: string) {
        this.id = id;
        this.itemName = name;
        this.itemDescription = description;
        this.category = category;
    }
}

const items: DataItem[] = [
    new DataItem(89, "Special Item 89", "This is item category is: Category 1", "Category 1"),
    new DataItem(23, "Item 23", "This is item category is: Category 2", "Category 2"),
    new DataItem(1, "Item 1", "This is item category is: Category 1", "Category 1"),
    new DataItem(34, "Item 34", "This is item category is: Category 3", "Category 3"),
    new DataItem(55, "Special Item 55", "This is item category is: Category 3", "Category 3"),
    new DataItem(78, "Item 78", "This is item category is: Category 1", "Category 1"),
    new DataItem(5, "Item 5", "This is item category is: Category 1", "Category 1"),
    new DataItem(111, "Special Item 111", "This is item category is: Category 2", "Category 2"),
    new DataItem(665, "Special Item 665", "This is item category is: Category 2", "Category 2"),
    new DataItem(1134, "Item 1134", "This is item category is: Category 1", "Category 1"),
    new DataItem(22, "Special Item 22", "This is item category is: Category 3", "Category 3"),
    new DataItem(345, "Item 345", "This is item category is: Category 1", "Category 1"),
    new DataItem(80, "Item 80", "This is item category is: Category 1", "Category 1"),
    new DataItem(54, "Item 54", "This is item category is: Category 3", "Category 3"),
];

これにより、フィルター処理、並べ替え、およびグループ化されたオブジェクトを含む次のUIが生成されます。

図1:RadListViewで有効化されたグループ化、フィルタリング、並べ替え:

iOSでのRadListViewデータ操作 AndroidでのRadListViewデータ操作

参考文献

このシナリオを実際に見てみたいですか? GitHubのSDKサンプルリポジトリを確認してください。これとNativeScript UIを使用した他の多くの実用的な例があります。

役立つと思われる関連記事:

入門

コアコンセプト

ユーザーインターフェース

ツール

ハードウェアアクセス

プラグインの開発

リリース

アプリテンプレート

パフォーマンスの最適化

フレームワークモジュール

ガイド

サポートを受ける

トラブルシューティング

Siedkick