」工欲善其事,必先利其器。「—孔子《論語.錄靈公》
首頁 > 程式設計 > 掌握 Angular Table 中可調整大小的欄位:開發人員逐步指南

掌握 Angular Table 中可調整大小的欄位:開發人員逐步指南

發佈於2024-11-08
瀏覽:767

Mastering Resizable Columns in Angular Table: A Step-by-Step Guide for Developers

如何在 Angular 表中创建可调整大小的列:分步指南

Angular Material 表提供了一种时尚的数据显示方式。然而,用户通常需要额外的功能,例如调整表列大小以更好地控制数据显示的能力。在本指南中,我们将逐步介绍使用自定义指令在 Angular 表中创建可调整大小的列的过程。您将学习如何设置指令、调整大小的样式以及逐步实施列大小调整。

介绍

向 Angular Material 表添加可调整大小的列涉及创建侦听鼠标事件的自定义指令,允许用户单击并拖动列以调整其宽度。这为用户提供了灵活性,特别是在处理大型数据集时,改善了用户体验。

在本教程中,我们将:

  • 创建自定义列调整大小指令。
  • 处理鼠标事件以调整列大小。
  • 应用样式以获得流畅的用户体验。
  • 将指令附加到 Angular Material 表。

让我们深入探讨一下。

第 1 步:设置角度材质表

首先,确保您的 Angular 项目安装了 Angular Material。如果没有,请运行以下命令将 Angular Material 添加到您的项目中:

ng add @angular/material

安装 Angular Material 后,您可以使用以下代码创建基本表格。

表格的 HTML:

{{ column }} {{ element[column] }}

在这里,我们使用 Angular Material 中的 mat-table 来显示一个简单的表格。 appColumnResize 指令应用于 th(标题)元素以使列可调整大小。

表格数据:

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

export interface PeriodicElement {
  name: string;
  position: number;
  weight: number;
  symbol: string;
}

const ELEMENT_DATA: PeriodicElement[] = [
  { position: 1, name: 'Hydrogen', weight: 1.0079, symbol: 'H' },
  { position: 2, name: 'Helium', weight: 4.0026, symbol: 'He' },
  // ... add more data
];

@Component({
  selector: 'table-basic-example',
  styleUrls: ['table-basic-example.scss'],
  templateUrl: 'table-basic-example.html',
  encapsulation: ViewEncapsulation.None,
})
export class TableBasicExample {
  displayedColumns: string[] = ['position', 'name', 'weight', 'symbol'];
  dataSource = ELEMENT_DATA;
}

该组件包含周期性元素的数据,我们将在表中显示这些数据。

第 2 步:创建列调整大小指令

接下来,我们将实现一个自定义 Angular 指令,该指令支持调整表列大小的功能。

指令实施:

import {
  Directive,
  ElementRef,
  Renderer2,
  NgZone,
  Input,
  OnInit,
  OnDestroy,
} from '@angular/core';
import { fromEvent, Subject } from 'rxjs';
import { takeUntil } from 'rxjs/operators';

@Directive({
  selector: '[appColumnResize]',
})
export class ColumnResizeDirective implements OnInit, OnDestroy {
  @Input() resizableTable: HTMLElement | null = null;

  private startX!: number;
  private startWidth!: number;
  private isResizing = false;
  private column: HTMLElement;
  private resizer!: HTMLElement;
  private destroy$ = new Subject();

  constructor(
    private el: ElementRef,
    private renderer: Renderer2,
    private zone: NgZone
  ) {
    this.column = this.el.nativeElement;
  }

  ngOnInit() {
    this.createResizer();
    this.initializeResizeListener();
  }

  private createResizer() {
    this.resizer = this.renderer.createElement('div');
    this.renderer.addClass(this.resizer, 'column-resizer');
    this.renderer.setStyle(this.resizer, 'position', 'absolute');
    this.renderer.setStyle(this.resizer, 'right', '0');
    this.renderer.setStyle(this.resizer, 'top', '0');
    this.renderer.setStyle(this.resizer, 'width', '5px');
    this.renderer.setStyle(this.resizer, 'cursor', 'col-resize');
    this.renderer.appendChild(this.column, this.resizer);
  }

  private initializeResizeListener() {
    this.zone.runOutsideAngular(() => {
      fromEvent(this.resizer, 'mousedown')
        .pipe(takeUntil(this.destroy$))
        .subscribe((event: MouseEvent) => this.onMouseDown(event));

      fromEvent(document, 'mousemove')
        .pipe(takeUntil(this.destroy$))
        .subscribe((event: MouseEvent) => this.onMouseMove(event));

      fromEvent(document, 'mouseup')
        .pipe(takeUntil(this.destroy$))
        .subscribe(() => this.onMouseUp());
    });
  }

  private onMouseDown(event: MouseEvent) {
    event.preventDefault();
    this.isResizing = true;
    this.startX = event.pageX;
    this.startWidth = this.column.offsetWidth;
  }

  private onMouseMove(event: MouseEvent) {
    if (!this.isResizing) return;
    const width = this.startWidth   (event.pageX - this.startX);
    this.renderer.setStyle(this.column, 'width', `${width}px`);
  }

  private onMouseUp() {
    if (!this.isResizing) return;
    this.isResizing = false;
  }

  ngOnDestroy() {
    this.destroy$.next();
    this.destroy$.complete();
  }
}

解释:

  • createResizer():将调整器元素 (div) 添加到列标题。
  • onMouseDown():当用户点击缩放器时触发,记录初始位置。
  • onMouseMove():当用户拖动缩放器时更新列宽。
  • onMouseUp():当用户释放鼠标按钮时结束调整大小。

第 3 步:调整大小调整器的样式

我们需要设置调整大小的样式,以便用户知道它是可拖动的。将以下 CSS 添加到您的样式中:

.resizable-table {
  th {
    position: relative;

    .column-resizer {
      position: absolute;
      top: 0;
      right: 0;
      bottom: 0;
      width: 10px;
      cursor: col-resize;
      z-index: 1;

      &:hover {
        border-right: 2px solid red;
      }
    }

    &.resizing {
      user-select: none;
    }
  }

  &.resizing {
    cursor: col-resize;
    user-select: none;
  }
}

此 CSS 正确定位调整大小,添加悬停效果,并更改光标以指示可调整大小。

第 4 步:测试表

既然指令和样式都已就位,请尝试调整列的大小。您应该能够单击调整器,向左或向右拖动它,并动态调整每列的宽度。

常见问题解答

问:如果可调整大小的表格太宽会发生什么?

A:表格会溢出并根据容器的宽度进行调整。确保添加适当的滚动行为或容器调整来处理大型表格。

问:我可以使特定列不可调整大小吗?

答:是的,您可以使用 Angular 的内置结构指令(例如 *ngIf.

)有条件地将 appColumnResize 指令仅应用于特定列

问:这种方法对于大型表来说性能友好吗?

答:此解决方案适用于中等大小的桌子。然而,对于非常大的数据集,您可能希望通过使用 Angular 的更改检测策略或虚拟滚动机制来进一步优化。

结论

通过遵循本指南,您现在可以为 Angular Material 表提供功能齐全的可调整大小的列功能。这种自定义增强了表格的灵活性和可用性,提供更好的用户体验。快乐编码!

版本聲明 本文轉載於:https://dev.to/chintanonweb/mastering-resizable-columns-in-angular-table-a-step-by-step-guide-for-developers-4f5n?1如有侵犯,請洽study_golang @163.com刪除
最新教學 更多>
  • 釋放 Claude AI:用於經濟實惠且靈活的 AI 整合的非官方 API
    釋放 Claude AI:用於經濟實惠且靈活的 AI 整合的非官方 API
    由 Anthropic 開發的 Claude AI 以其令人印象深刻的能力在人工智慧界掀起了波瀾。然而,官方 API 對於許多開發人員和小型企業來說可能過於昂貴。這就是我們的非官方 Claude AI API 的用武之地,它提供了一個更實惠、更靈活的解決方案,將 Claude 的力量整合到您的專案中...
    程式設計 發佈於2024-11-08
  • 如何使用時間包確定 Go 中一個月的最後一天?
    如何使用時間包確定 Go 中一個月的最後一天?
    使用Time.Time 確定給定月份的最後一天處理基於時間的資料時,通常需要確定指定月份的最後一天。無論該月有 28 天、29 天(閏年)還是 30 天或 31 天,這都會使這成為一項具有挑戰性的任務。 時間包解決方案Go 時間包其日期函數提供了一個方便的解決方案。 Date 的語法為:func D...
    程式設計 發佈於2024-11-08
  • 如何在不支援的瀏覽器中實現“背景濾鏡”效果?
    如何在不支援的瀏覽器中實現“背景濾鏡”效果?
    CSS:為不可用的背景過濾器提供替代方案CSS 中的背景過濾器功能在大多數現代瀏覽器中仍然無法訪問。雖然我們預計其未來的支持,但發現替代解決方案勢在必行。 實現類似效果的一種方法是採用具有微妙透明度的背景。下面的 CSS 程式碼示範了這個方法:/* Slightly transparent fall...
    程式設計 發佈於2024-11-08
  • Python 的 len() 函數對於不同的資料結構有多有效率?
    Python 的 len() 函數對於不同的資料結構有多有效率?
    理解Python內建資料結構中len()函數的成本Python中內建len()函數是決定各種資料結構長度的重要工具。它的效率至關重要,尤其是在處理大型資料集時。本文深入研究了 len() 對於不同內建資料類型(例如列表、元組、字串和字典)的計算成本。 O(1) 跨內建類型的複雜性關鍵要點是 len(...
    程式設計 發佈於2024-11-08
  • 如何在 Python 中存取 Windows 剪貼簿文字?
    如何在 Python 中存取 Windows 剪貼簿文字?
    在 Python 中存取 Windows 剪貼簿文字從 Windows 剪貼簿檢索文字是程式設計中的常見任務。本文探討如何使用 Python 的 win32clipboard 模組來實現此目的。 pywin32 和 win32clipboardwin32clipboard 模組是 pywin32 的...
    程式設計 發佈於2024-11-08
  • 如何修復 CentOS 5 上由於檔案權限問題導致的 Nginx 403 Forbidden 錯誤?
    如何修復 CentOS 5 上由於檔案權限問題導致的 Nginx 403 Forbidden 錯誤?
    Nginx 403 Forbidden:文件存取權限故障排除當在Nginx 中遇到令人沮喪的「403禁止」錯誤時,確定根本原因可以是一個挑戰。此錯誤通常表示對檔案或目錄的存取被拒絕。在該特定場景中,使用者在 CentOS 5 上使用 PHP-FPM 配置了 Nginx,但無法提供指定來源目錄中的任何...
    程式設計 發佈於2024-11-08
  • React 中的函數和類別元件與 TypeScript
    React 中的函數和類別元件與 TypeScript
    在使用 TypeScript 的 React 中,我們可以使用兩種主要方法來建立元件:功能元件和類別元件。兩種方法都允許使用 props 和 state,但使用的範例略有不同。 TypeScript 透過提供靜態類型進一步增強了開發安全性,這使我們能夠精確定義 props 和 state 的形狀。 ...
    程式設計 發佈於2024-11-08
  • 如何使用 Clang 檢查編譯器產生的 C++ 模板實例化程式碼?
    如何使用 Clang 檢查編譯器產生的 C++ 模板實例化程式碼?
    檢查C 語言中編譯器產生的範本實例化在C 語言中,範本函數和類別允許透過定義通用功能來重用程式碼專門針對不同類型。要了解編譯器為模板實例化產生的程式碼,了解這些實例化的函數或類別會很有幫助。 Clang 的AST 列印功能一個工具提供這種可見性的是Clang 的抽象語法樹(AST) 列印功能,Cla...
    程式設計 發佈於2024-11-08
  • 我從使用 Vue.js 建立計算器中學到了什麼
    我從使用 Vue.js 建立計算器中學到了什麼
    對於我的第四個項目,我使用 Vue.js 開發了一個 計算器 應用程式。對於理解如何處理使用者輸入、顯示動態結果以及使用 JavaScript 執行計算來說,這是一次寶貴的經驗。以下是我在建立此應用程式時學到的主要經驗教訓的細分。 1. 處理使用者輸入並更新顯示 計算器需要接受使用...
    程式設計 發佈於2024-11-08
  • 在 Kubernetes 上設定 JFrog Artifactory 並連接 Spring Boot 應用程式
    在 Kubernetes 上設定 JFrog Artifactory 並連接 Spring Boot 應用程式
    本文档提供有关在 Kubernetes 集群中设置 JFrog Artifactory 的指南。它作为开发人员在本地计算机上运行的 Kubernetes 环境上安装和配置 JFrog 的基本教程。 设置本地环境来构建DevOps资源 我使用 Docker 容器为多个应用程序设置工作环...
    程式設計 發佈於2024-11-08
  • Angular 與 React:4 中你該選哪一個?
    Angular 與 React:4 中你該選哪一個?
    前端開發者總是面臨一個大問題:Angular 還是 React? 兩個框架都很強大,但哪一個真正適合你的開發需求? ? 在這個全面的比較中,我詳細分析了每個項目的主要差異、優勢和劣勢,幫助您為下一個項目做出正確的選擇。無論您是初學者還是經驗豐富的專業人士,本文都會為您提供做出明智決定所需的見解。...
    程式設計 發佈於2024-11-08
  • 如何將 Props 傳遞給 React Router 中的處理程序元件?
    如何將 Props 傳遞給 React Router 中的處理程序元件?
    使用React Router 將Props 傳遞給處理程序元件在利用React Router 的React.js 應用程式中,您可能會遇到需要將props 傳遞給特定處理程序組件的場景。考慮以下應用程式結構:var Dashboard = require('./Dashboard'); var Co...
    程式設計 發佈於2024-11-08
  • 透過 Maroto 在 Golang 中產生 PDF 來進行長期操作
    透過 Maroto 在 Golang 中產生 PDF 來進行長期操作
    Written by Subha Chanda✏️ Go, also known as Golang, is a statically typed, compiled programming language designed by Google. It combines the performan...
    程式設計 發佈於2024-11-08
  • 作業系統開發(真相)
    作業系統開發(真相)
    Table of Contents Introduction 1. The Bootloader: Kicking Things Off 2. Entering the Kernel: Where the Magic Happens 3. Choosing Your Languag...
    程式設計 發佈於2024-11-08
  • 按值傳遞或引用傳遞:「想要速度?按值傳遞」何時是真的?
    按值傳遞或引用傳遞:「想要速度?按值傳遞」何時是真的?
    “想要速度?按價值傳遞” - 探索性能影響Scott Meyers 的聲明“想要速度?按價值傳遞”提出了問題關於按值傳遞物件與按引用傳遞物件的效能優勢。在這種情況下,按值傳遞涉及複製操作,而按引用傳遞則避免了不必要的複製。 考慮以下結構體 X 和 Y 的例子:struct X { std::st...
    程式設計 發佈於2024-11-08

免責聲明: 提供的所有資源部分來自互聯網,如果有侵犯您的版權或其他權益,請說明詳細緣由並提供版權或權益證明然後發到郵箱:[email protected] 我們會在第一時間內為您處理。

Copyright© 2022 湘ICP备2022001581号-3