angular4 + ts + es6 自造轮子,理解组件化操作。以及怎么应用一些需要数据展示的组件

1、为什么要将某个功能块拿出来做成一个组件。

2、改组件应该考虑哪些可塑性或者或使用者怎么进行自定义。

3、组件实现了什么功能?

4、怎么使用组件与当前的程序嵌合

eg:下拉选组件的制造

一、造组件

webstrom 的cmd(左下角的灰色方块点开选terminal)控制台可以快速创建组件。

html代码

<div class="row text-center base-dropdawn">

<div class="col">

<div ngbDropdown class="d-inline-block">

<button class="btn btn-outline-primary show-plan" id="dropdownBasic1" ngbDropdownToggle [ngStyle]="showStyle">{{showData[code]}}

<span class="glyphicon glyphicon-menu-down"></span>

</button>

<div class="select-plan" ngbDropdownMenu aria-labelledby="dropdownBasic1">

<!-- <button class="dropdown-item" (click)="checkSelect($event)"[ngStyle]="selectStyle">Action - 1</button>

<button class="dropdown-item" (click)="checkSelect($event)"[ngStyle]="selectStyle">Another Action</button>

<button class="dropdown-item" (click)="checkSelect($event)"[ngStyle]="selectStyle">Something elsehhhhhhh</button>-->

<button class="dropdown-item" *ngFor="let select of selectData, index as i" (click)="checkSelect($event,i)"[ngStyle]="selectStyle" [ngClass]="{'active': isIndex===i}">{{select}}</button>

</div>

</div>

</div>

</div>

ts代码

import {Component, OnInit, Output, EventEmitter, Input} from '@angular/core';

@Component({

selector: 'app-dropdawn',

templateUrl: './dropdawn.component.html',

styleUrls: ['./dropdawn.component.css']

})

export class DropdawnComponent implements OnInit {

showData: Array<any> = []; // 要展示的下拉选的数组

isIndex: number = 0; // 选中哪个选择项,默认为第一个

@Input() initShow: string = '';

@Input() showStyle: any= {}; // 展示面板的样式数据

@Input() selectStyle: any= {}; // 下拉面板的样式数据

@Input() selectData: any = []; // 待选择的下拉列表的数组

@Input() code: string = '';

@Output() selectChange: EventEmitter<any> = new EventEmitter<any>(); // 返回数据结构

constructor() {

}

ngOnInit() {

// 初始化数据

this.showData[this.code] = '请选择';

this.showData[this.code] = this.initShow || '请选择'; // 如果需要初始化可以赋值

this.selectData = ['上对我的', 'wwrweg d', '3r3f3'] ;

this.showStyle = {

color: '#666',

background: '#fff',

width: '120px',

height: '24px'

};

this.selectStyle = {

color: '#666',

background: '#fff',

width: '120px',

height: '24px'

};

}

checkSelect(event, i) {

const _event = event.target;

this.showData[this.code] = _event.innerText;

debugger;

// 判断哪个是正在激活的

this.isIndex = i;

console.log( this.showData);

this.selectChange.emit(this.showData);

}

}

css代码

.base-dropdawn button{

width:120px ;

height:24px;

line-height: 24px;

padding: 0;

padding-left: 5px;

margin: 0 auto ;

white-space:nowrap;

text-align: left;

text-overflow:ellipsis;

overflow: hidden;

}

/*固定下拉图标的位置*/

.base-dropdawn .show-plan{

position: relative;

}

.base-dropdawn .show-plan .glyphicon {

position: absolute;

top: 5px;

right: 5px;

}

.base-dropdawn .show-plan{

border: 1px solid #CCCCCC;

border-radius: 4px;

}

.base-dropdawn .select-plan{

overflow: hidden;

border-radius: 0;

width:122px ;

min-width: 60px;

padding: 0;

border-bottom-left-radius: 4px;

border-bottom-right-radius: 4px;

}

.base-dropdawn .select-plan button{

border: 0;

}

.base-dropdawn .select-plan button:hover{

background: #3484f5 !important;

color:#fff !important;

}

.active{

background: #3484f5 !important;

color:#fff !important;

}

二、其他组件调用

a、HTML代码(第一个初始化数据的,第二个没有初始化数据)

<app-dropdawn [code]="'demo'"[initShow]="this.showData[0].value" (selectChange)="selectChangeShow($event)"></app-dropdawn>

<app-dropdawn [code]="'work'" (selectChange)="selectChangeShow($event)"></app-dropdawn>

b、ts代码

 import {Component, OnInit} from '@angular/core';

import {Router} from '@angular/router';

import {UserService} from '../../service/user/user.service';

// 引入状态码

import { ERR_OK/*, ERR_OUTTIME*/ } from '../../../assets/configs/config';

// 引入状态管理

import { Store } from '@ngrx/store';

import { SET } from '../../store/user.reducer';

// 引入表单控制模块

import { FormBuilder, FormGroup, Validators } from '@angular/forms';

@Component({

  selector: 'app-login',

  templateUrl: './login.component.html',

  styleUrls: ['./login.component.css']

})

export class LoginComponent implements OnInit {

  // demo

  showData: Array<any> = [];

  userForm: FormGroup;                // 登录录入信息

  loginType: number = 1;             // 登录角色 1-会员 2-管理员

  showBtnGroup: boolean = true;     // 按钮

  showLoginForm: boolean = false;  // 是否显示登录框

  showRegistry: boolean = false;   // 是否显示注册框

  onSubmit: boolean = false;

  userInfo: object = {

    uuid: '',

    captcha: ''

  };

  constructor(

    private router: Router,

    private userService: UserService,

    private store: Store<object>,

    private fb: FormBuilder

  ) {

    this.userForm = fb.group({

      username: ['', [Validators.required, Validators.pattern(/^\d{11}$/)]],  // 用户名当前为 11位手机号码

      userpwd: ['', [Validators.required]],

      vcode: ['', [Validators.required, Validators.pattern(/^\d{4}$/)]]       // 验证码当前为 4位数字组合

    }, {validator: null});

  }

  ngOnInit() {

    // this.getCode();

    //demo

    this.showData = [

      {code: 'demo',

        value: ''

      },

      {code: 'work',

        value: ''

      }

    ];

  }

  /**

   * @desc 变更登录角色

   * @param type 角色类型 1-会员 2-管理员

   * */

  loginTypeChange(type) {

    this.showBtnGroup = false;

    this.showLoginForm = true;

    this.loginType = type;

  }

  /**

   * @desc 判断显示登录框或者注册框

   * @param type 1-登录 2-注册

   * */

  btnClick(type) {

    this.showBtnGroup = false;

    this.showLoginForm = type === 1;

    this.showRegistry = type === 2;

  }

  /**

   * @desc 执行登录

   * @param null

   * */

  doLogin() {

    this.onSubmit = true;

    Object.values(this.userForm.controls).forEach(val => val.disable());

    this.userService.login(Object.assign({}, this.userInfo, this.userForm.value)).then(res => {

      if (res && res[2].ANS_MSG_HDR.MSG_CODE === ERR_OK) {

        sessionStorage.setItem('SESSION_INFO', res[0][0].SESSION);

        sessionStorage.setItem('OP_USER', res[0][0].USER_CODE);

        sessionStorage.setItem('OP_ROLE', res[0][0].USER_ROLES.substr(0, 1));

        sessionStorage.setItem('OP_TYPE', this.loginType + '');                     // 记录是会员登录还是管理员登录

        sessionStorage.setItem('ACCOUNT', JSON.stringify(res[0][0]));

        this.store.dispatch({type: SET, payload: res[0][0]});

        this.router.navigate(['/home']);

      } else /*if (res && res[2].ANS_MSG_HDR.MSG_CODE === ERR_OUTTIME) */{

        this.getCode();

      }

      this.onSubmit = false;

      Object.values(this.userForm.controls).forEach(val => val.enable());

    }).catch(err => {

      this.onSubmit = false;

      Object.values(this.userForm.controls).forEach(val => val.enable());

    });

  }

  // 获取文件服务器返回的数据示例,判断e的数据类型

  selectChangeShow(e) {

    debugger

    console.log(Object.prototype.toString.call(e));

    // Object.prototype.toString.call(e)最精准的判断对象类型的方法,除此之外有instanceof 和typeof

   // instanceof运算符用来判断一个构造函数的prototype属性所指向的对象是否存在另外一个要检测对象的原型链上console.log(Object instanceof Object); //true

   //typeof typeof操作符返回一个字符串,表示未经计算的操作数的类型。 不能区分对象、数组、正则,对它们操作都返回"object"

console.log(typeof 42);
  // expected output: "number"

    if (Object.prototype.toString.call(e) === '[object Array]') {

      this.showData.forEach(val => {

        const d = e[val.code];

        if (d) {

          val.value = d;

        }

      });

    }

    console.log(this.showData);

  }

  /**

   * @desc 获取图形验证码

   * @param null

   * */

  getCode() {

    Object.assign(this.userInfo, this.userService.getCaptcha());

  }

}

三、

父组件与子组件通过本地变量互动

父组件通过#timer获得子组件的所有属性和方法

注释:typeof运算后返回的结果有

猜你喜欢

转载自my.oschina.net/u/2542841/blog/2961242
今日推荐