首页 > 解决方案 > 角度8,循环分组数据

问题描述

我有一个带有数据字段的 json 文件。我一直在尝试多种方法来按日期对数据进行分组,并将其与 ngFor 分组显示。这些方法都不起作用,我真的需要有人的帮助。有没有办法循环通过'datagrouped'?,我想要的只是显示按日期值分组的数据,如下例所示:27/11/19 task title1 task title2

import { Component, OnInit } from '@angular/core';
import  *  as  data  from  '../data.json';
import { Router } from '@angular/router';
import * as _ from 'lodash';

@Component({
  selector: 'app-tasklist',
  templateUrl: './tasklist.component.html',
  styleUrls: ['./tasklist.component.css']
})
export class TasklistComponent implements OnInit {

  mockData: any  = (data  as  any).default;

  show: boolean = false;
  value: string;
  id: number;
  array = this.mockData;
  datagrouped = _.groupBy(this.array, "date");

  constructor(private router: Router ) {}

  remove(id) {
    this.mockData = this.mockData.filter(item => {
      if (item.id !== id) {
        return item;
      }
    });
  }


  create(item) {

    this.datagrouped.push({
      id: Date.now(),
      title: item,
      done: false,
      date: new Date()
    });

  }

  update(title) {
    this.mockData.map(item => {
      if (item.id === this.id) {
        item['title'] = title;
      }
    });

    this.show = false;
  }

  edit(id, title) {
    this.show = true;
    this.value = title;
    this.id = id;
  }

  setTaskComplete(id) {
    this.mockData.map(item => {
      if (item.id === id) {
        item['done'] = true;
      }
    });
  }

  ngOnInit() {
  }

}
<p>tasklist works!</p>
<div class="col-sm-12 pt-5 text-right">
    <div class="col-md-12">
        <div class="edit-popup" *ngIf="show">
            <input type="text" name="" class="edit-item" value="{{value}}" #item>
            <button class="btn-primary" (click)="update(item.value)">Update</button>

          </div>
          <input type="text" name="" class="item" #item>
          <button class="btn-primary" (click)="create(item.value)">Add</button>

  </div>

  <div class="col-sm-12 pt-2">
    <div class="col-md-12">
        <table class="table table-bordered table-hover table-striped">
            <thead class="table-primary">
                <tr>

                    <th scope="col">Task</th>
                    <th scope="col">Date</th>
                    <th scope="col" class="text-center">Action</th>
                </tr>
            </thead>
            <tbody>
                <tr *ngFor="let item of datagrouped ">

                    <td>{{item.title}}</td>
                    <td>{{item.date | date: 'shortDate'}}</td>
                    <td width="150" class="text-center">
                        <button type="button" class="btn btn-info btn-sm mr-2" (click)="edit(item.id, item.title)">Edit</button> 
                        <button type="button" class="btn btn-danger btn-sm" (click)="remove(item.id)">Delete</button>
                    </td>
                </tr>
            </tbody>
        </table>
    </div>
  </div>

[{
    "id": "1",
    "title": "This is the longest task ever.",
    "done": false,
    "date": "333"
}, {
    "id": "2",
    "title": "This is the second longest task ever.",
    "done": true,
    "date": "444"
}, {
    "id": "3",
    "title": "This is the third longest task ever.",
    "done": false,
    "date": "333"
}, {
    "id": "4",
    "title": "This is the fourth longest task ever.",
    "done": false,
    "date": "444"
}]
``

标签: angulargroupingngfor

解决方案


27/11/19 任务标题1 任务标题2

组件的组功能:

group(arr:any){
  let dates:any = {};
  arr.forEach((data) => {
    dates[data.date] = null;
  });
  dates = Object.keys(dates);

  let datagrouped = {};
  dates.forEach((date) => {
    datagrouped[date] = arr.reduce((dataArr, data) => {
      if(data.date == date){
        dataArr.push(data);
      }
      return dataArr;
    }, []);
  });
}

这种情况下的结构应该是这样的(我没有测试代码):

// datagrouped = 
//   {
//     date1: [
//       {...},
//       {...}
//     ],
//     date2 : ...,
//   }
// 

所以你可以打电话:

this.datagrouped = this.group(this.mockData);

在您的模板中,您可以像这样循环:

<div *ngFor="let date of datagrouped|keys">
  <span>{{date}}</span>
  <span *ngFor="let item of datagrouped[date]">task {{item.title}} </span>
</div>

如果您实现密钥管道并将其添加到您的 AppModule

import { Pipe, PipeTransform } from '@angular/core';

@Pipe({
    name: 'keys'
})
export class KeysPipe implements PipeTransform {

    transform(value:object|Map<any, any>): any {
      if(value instanceof Map){ return Array.from(value.keys()); }
      return Object.keys(value);
    }

}

推荐阅读