Using Ionic2 + angular4 to implement a region selection component, ionic2angular4

Source: Internet
Author: User

Using Ionic2 + angular4 to implement a region selection component, ionic2angular4

Preface

This article describes how to use Ionic2 + angular4 to implement a region selection component. Why is this article? The main reason is that during the recent project reconstruction process, it was found that the regional selection commands previously written with mobiscroll are difficult to reuse in angular2 (typeScript is used after all ). So I came up with the idea of writing a component myself.

I want to write data based on mobiscroll as before, but I found that it was very time-consuming. So I searched for the relevant components one day, and someone else wrote it as expected. Https://www.npmjs.com/package..but this group does not match my requirements. I do not simply choose provinces, cities, or provinces. Therefore, a public component is written based on ionic2 picker. I will not talk about it much below. If you are interested, let's take a look at the detailed introduction:

The Code is as follows:

AreasSelect. ts

Import {PickerController} from "ionic-angular"; import {Component, EventEmitter, Output, Input} from "@ angular/core"; import {areasList} from ".. /.. /datasource/areas "; @ Component ({selector: 'areas-select', templateUrl: 'areasSelect.com.html ',}) export class AreasSelect {constructor (protected Picker: PickerController) {} private picker; private provinceCol = 0; // province column private cityCol = 0; // city column privat E regionCol = 0; // The partition column private pickerColumnCmps; // The picker column data instance private isOpen = false; // whether the private pickerCmp is created; // picker instance private value = ''; // The selected data @ Input () citiesData = areasList; // region data (areas by default. ts data) @ Input () cancelText = 'close'; // close the button text @ Input () doneText = 'complete'; // The completion button text @ Input () separator = ''; // data connection mode @ Input () level = 3; // when the level is set to a maximum of three levels, * no value is returned for the event triggered when it is disabled * @ type {EventEmi Tter} */@ Output () cancel: EventEmitter <any> = new EventEmitter (); // close the event/*** the event triggered upon completion * returns obj * obj = {data: object, value: string} data is the corresponding province, city, and code * @ type {EventEmitter} */@ Output () done: EventEmitter <any> = new EventEmitter (); // complete the event/*** open the region selector * basic idea * 1. create picker * 2. data is first processed into an array separated by province, city, and district * 3. data is given to picker * 4 as a column. set the data display style (picker) * 5. generate picker */private open () {let pickerOptions = {Tons: [{text: this. cancelText, role: 'cancel', handler :() => {this. cancel. emit (null) ;},{ text: this. doneText, handler: (data) => {this. onChange (data); this. done. emit ({data: data, value: this. value}) ;}}]}; this. picker = this. picker. create (pickerOptions); this. generate (); // load this. validate (this. picker); // render this. picker. ionChange. subscribe () => {this. validate (this. picker) ;}); // generate This. picker. present (pickerOptions ). then () => {this. pickerCmp = this. picker. instance; this. pickerColumnCmps = this. pickerCmp. _ cols. toArray (); this. pickerColumnCmps. forEach (function (col) {return col. lastIndex =-1 ;}); this. isOpen = true; this. picker. onDidDismiss (function () {this. isOpen = false;});}/** process the data and hand it over to picker **/private generate () {let values = this. value. toString (). spli T (this. separator); // Add province data to picker let provinceCol = {name: 'province ', options: this. citiesData. map (function (province) {return {text: province. name, value: province. code, disabled: false };}), selectedIndex: 0 }; let provinceIndex = this. citiesData. findIndex (function (option) {return option. name = values [0] ;}); provinceIndex = provinceIndex ===-1? 0: provinceIndex; provinceCol. selectedIndex = provinceIndex; this. picker. addColumn (provinceCol); // Add city data to picker let cityColData = this. citiesData [provinceCol. selectedIndex]. children; let cityCol; if (this. level> = 2) {cityCol = {name: 'city', options: cityColData. map (function (city) {return {text: city. name, value: city. code, disabled: false };}), selectedIndex: 0 }; let cityIndex = CityColData. findIndex (function (option) {return option. name = values [1] ;}); cityIndex = cityIndex ===-1? 0: cityIndex; cityCol. selectedIndex = cityIndex; this. picker. addColumn (cityCol);} // Add region data to picker let regionData, regionCol; if (this. level = 3) {regionData = this. citiesData [provinceCol. selectedIndex]. children [cityCol. selectedIndex]. children; regionCol = {name: 'region ', options: regionData. map (function (city) {return {text: city. name, value: city. code, disabled: false };}, s ElectedIndex: 0}; let regionIndex = regionData. findIndex (function (option) {return option. name = values [2];}); regionIndex =-1? 0: regionIndex; regionCol. selectedIndex = regionIndex; this. picker. addColumn (regionCol);} this. divyColumns (this. picker);}/** set the data display style * @ param picker */private divyColumns (picker) {let pickerColumns = this. picker. getColumns (); // get the column data let columns = []; pickerColumns. forEach (function (col, I) {columns. push (0); col. options. forEach (function (opt) {if (opt & opt. text & opt. text. length> colu Mns [I]) {columns [I] = opt. text. length ;}}) ;}); if (columns. length = 2) {let width = Math. max (columns [0], columns [1]); pickerColumns [0]. align = 'right'; pickerColumns [1]. align = 'left'; pickerColumns [0]. optionsWidth = pickerColumns [1]. optionsWidth = width * 17 + "px";} else if (columns. length = 3) {let width = Math. max (columns [0], columns [2]); pickerColumns [0]. align = 'right'; pickerColum Ns [1]. columnWidth = columns [1] * 33 + "px"; pickerColumns [0]. optionsWidth = pickerColumns [2]. optionsWidth = width * 17 + "px"; pickerColumns [2]. align = 'left';}/*** verify data * @ param picker */private validate (picker) {let _ this = this; let columns = picker. getColumns (); let provinceCol = columns [0]; let cityCol = columns [1]; let regionCol = columns [2]; if (cityCol & this. provinceCol! = ProvinceCol. selectedIndex) {cityCol. selectedIndex = 0; let cityColData = this. citiesData [provinceCol. selectedIndex]. children; cityCol. options = cityColData. map (function (city) {return {text: city. name, value: city. code, disabled: false };}); if (this. pickerColumnCmps & cityCol. options. length> 0) {setTimeout (function () {return _ this. pickerColumnCmps [1]. setSelected (0,100) ;}, 0) ;}} if (re GionCol & (this. cityCol! = CityCol. selectedIndex | this. provinceCol! = ProvinceCol. selectedIndex) {let regionData = this. citiesData [provinceCol. selectedIndex]. children [cityCol. selectedIndex]. children; regionCol. selectedIndex = 0; regionCol. options = regionData. map (function (city) {return {text: city. name, value: city. code, disabled: false };}); if (this. pickerColumnCmps & regionCol. options. length> 0) {setTimeout (function () {return _ this. pickerColumnCmps [2]. s EtSelected (0,100) ;}, 0) ;}} this. provinceCol = provinceCol. selectedIndex; this. cityCol = cityCol? CityCol. selectedIndex: 0; this. regionCol = regionCol? RegionCol. selectedIndex: 0;}/*** set value * @ param newData */private setValue (newData) {if (newData = null | newData = undefined) {this. value = '';} else {this. value = newData;}/*** get value * @ returns {string} */private getValue () {return this. value;}/*** change the display of value * @ param val */private onChange (val) {this. setValue (this. getString (val);}/*** obtain the currently selected region data * @ param newData * @ returns {string} */private getString (newData) {if (newData ['city']) {if (newData ['region']) {return "" + newData ['province ']. text + this. separator + (newData ['city']. text | '') + this. separator + (newData ['region']. text | '');} return" "+ newData ['province ']. text + this. separator + (newData ['city']. text | '');} return" "+ newData ['province ']. text ;}}

AreasSelect.com.html

In fact, the corresponding template is not required, but in order to pass parameters with the parent level, an empty template is created here.

<div></div>

Usage:

Call on the required page

Test.page.html

<Ion-content> <button ion-button block icon-left color = "light" (tap) = "showAreasSelect () "> region selection </button> </ion-content> <areas-select # areasSelect [level] =" 3 "(cancel) =" closeSelect () "(done) = "done ($ event)"> </areas-select>

Test. page. ts

import {Component, ElementRef, Injector, ViewChild} from "@angular/core";import {BasePage} from "../base.page";@Component({ templateUrl: 'test.page.html', styles: []})export class TestPage extends BasePage { constructor(protected rt: ElementRef, protected ij: Injector) { super(rt, ij); } @ViewChild('areasSelect') areasSelect; showAreasSelect() { this.areasSelect.open(); } done(data) { this.showAlert(JSON.stringify(data)); } closeSelect() { this.showAlert('you click close'); } }

Files with no region data json or ts can be retrieved here: http://xiazai.jb51.net/201707/yuanma/regional_data (jb51.net).rar

Summary

The above is all the content of this article. I hope the content of this article will help you in your study or work. If you have any questions, please leave a message, thank you for your support.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.