mysql创建分区表指令
“Simplicity is the soul of efficiency.” — Austin Freeman
“简单是效率的灵魂。” —奥斯汀·弗里曼
The Twitter developer community is one of the best developer hangouts that I came across. I recently started being more active and I am finding it a lot of fun, learning, and inspiration.
吨他的Twitter开发者社区是最好的开发者去处,我碰到的一个。 我最近开始变得更加活跃,并且发现它带来了很多乐趣,学习和启发。
The following tweet by Alex Inkin inspired me to write this article.
Alex Inkin的以下推文启发了我写这篇文章。
Tweet by Alex Inkin
Alex Inkin发的推文
The snippet above is an Angular directive that can be used to resize any table columns. I personally find this incredibly useful and will set a really good example in learning Angular directives and rxjs
basics.
上面的代码段是一个Angular指令,可用于调整任何表列的大小。 我个人认为这非常有用,它将为学习Angular指令和rxjs
基础知识树立一个非常好的榜样。
Let’s get to it
让我们开始吧
(The plan)
The basic idea here is nothing fairly simple. We are going to take the following steps to achieve this.
这里的基本思想并不十分简单。 我们将采取以下步骤来实现这一目标。
Note: Width of a table column is effectively the width of the respective header cell(
<th>
).注意:表列的宽度实际上是相应标题单元格(
<th>
)的宽度。
- Introduce more templates to
<th>
element by creating a new component.
通过创建新组件,将更多模板引入<th>
元素。 - Style these templates to reflect the table border styles.
- On dragging the along the border, increase/decrease the width of
<th>
element.
沿边框拖动时,增加/减小<th>
元素的宽度。
(Creating the component)
The whole point here is to have pseudo(so to say) templates in the table header cell. For this reason, we need to introduce a new component with the template.
这里的重点是在表头单元格中具有伪(可以这么说)模板。 因此,我们需要在模板中引入一个新组件。
ng generate component resizable
Let’s introduce our template to it
让我们为其介绍模板
<div class="wrapper">
<div class="content">
<ng-content></ng-content>
</div>
<div class="bar" (resizable)="onResize($event)"></div>
</div>
You see that we are using content projection here and interestingly we also have a custom event named resizable
on the .bar
element.
您会看到我们在这里使用内容投影,有趣的是,我们在.bar
元素上还有一个名为resizable
的自定义事件。
Implementing the controller
实施控制器
@Component({
selector: 'th[resizable]',
templateUrl: './resizable.component.html',
})
export class ResizableComponent {
constructor() {}
@HostBinding('style.width.px')
width: number | null = null;
onResize(width: any) {
this.width = width;
}
}
It worth noting that the component selector is th[resizable]
which will select all <th>
elements with the [resizable]
directive.
值得注意的是,组件选择器是th[resizable]
,它将使用[resizable]
指令选择所有<th>
元素。
You can read more about the above selector approach in the below article that I have written.
您可以在我撰写的以下文章中了解有关上述选择器方法的更多信息。
We are also binding the width of the host(th
) to the property width
using @HostBinding
. The width of the element is now dynamically updated with the onResize(width)
function. This event will later be triggered by theresizable
directive.
我们还使用@HostBinding
将host( th
)的宽度绑定到属性width
。 现在,可以使用onResize(width)
函数动态更新元素的onResize(width)
。 此事件稍后将由resizable
指令触发。
We need to have some CSS styling in place as well to imitate the table borders. You can find it here.
我们还需要具有一些CSS样式,以模仿表格边框。 你可以在这里找到它。
That will be all about the component implementation.
这将全部与组件实现有关。
(Creating the directive)
Let us now create the resizable
directive.
现在让我们创建resizable
指令。
ng generate directive resizable
The sole purpose of our resizable
directive is to emit an event (resizable
) on dragging the column borders. This event is then consumed by the resizable
component to manipulate table cell width property.
resizable
指令的唯一目的是在拖动列边框时发出一个事件( resizable
)。 然后,该事件由resizable
组件消耗,以操纵表格单元格的宽度属性。
import { DOCUMENT } from '@angular/common';
import { Directive, ElementRef, Inject, Output } from '@angular/core';
import {distinctUntilChanged, map, switchMap, takeUntil, tap,} from 'rxjs/operators';
import { fromEvent } from 'rxjs';
@Directive({
selector: '[resizable]',
})
export class ResizableDirective {
@Output()
readonly resizable = fromEvent<MouseEvent>(
this.elementRef.nativeElement,
'mousedown'
).pipe(
tap((e) => e.preventDefault()),
switchMap(() => {
const { width, right } = this.elementRef.nativeElement
.closest('th')!
.getBoundingClientRect();
return fromEvent<MouseEvent>(this.documentRef, 'mousemove').pipe(
map(({ clientX }) => width + clientX - right),
distinctUntilChanged(),
takeUntil(fromEvent(this.documentRef, 'mouseup'))
);
})
);
constructor(
@Inject(DOCUMENT) private readonly documentRef: Document,
@Inject(ElementRef)
private readonly elementRef: ElementRef<HTMLElement>
) {}
}
We are Injecting DOCUMENT
and ElementRef
in the constructor
to indirectly access respective APIs.
我们在constructor
中注入DOCUMENT
和ElementRef
以间接访问各自的API。
Then we also have the readonly
@Output
event that we are emitting using the directive. We are taking the help of rxjs operators
to create an observable and pipe the values to the desired form.
然后,我们还有使用指令发出的readonly
@Output
事件。 我们正在利用rxjs operators
的帮助来创建一个可观察的并将值通过管道传递给所需的形式。
Let us break down the above code implementation to these following smaller steps.
让我们将以上代码实现分解为以下较小的步骤。
- Create an observable from native
mousedown
event on the host component(the custom template we introduced to<th>
in our case) usingfromEvent()
function ofrxjs
.
创建从本地可观察到mousedown
主机组件事件(自定义模板给大家介绍的<th>
在我们的例子)使用fromEvent()
的函数rxjs
。 - Use
pipe()
method to combine multiplerxjs
operators.
使用pipe()
方法组合多个rxjs
运算符。 - Use
tap
operator to executepreventdefault()
function which is important to avoid any undesirable side effects.
使用tap
运算符执行preventdefault()
函数,该函数对于避免任何不良副作用非常重要。 - Apply
switchMap
operator to make sure that we cancel anymousedown
event duringmousemove
to avoid multiple emits.
应用switchMap
运算符以确保我们在mousemove
期间取消任何mousedown
事件,以避免多次发射。 - Get information (width and position in DOM) of the closest
th
(host element).
获取最接近的th
(主机元素)的信息(DOM中的宽度和位置)。 - Calculate the new position of the header cell right bound.
- Use
distinctUntilChanged()
to filter out values that are same as the previous value(holding the mouse on the same position)
使用distinctUntilChanged()
筛选出与上一个值相同的值(将鼠标保持在同一位置) - Stop emitting values on the
mouseup
event.
停止在mouseup
事件上发出值。
That’s all of it! We now have an Angular directive that we can use throughout the application to give resizing superpower to our table columns 😃.
仅此而已! 现在,我们有了一个Angular指令,可以在整个应用程序中使用它来为表列res调整大小。
(Testing it)
Let’s see how to use this on a component.
让我们看看如何在组件上使用它。
<table>
<thead>
<tr>
<th resizable>Name</th>
<th resizable>E-mail</th>
<th>Address</th>
</tr>
</thead>
<tbody>
<tr *ngFor="let person of persons">
<td>{{ person.name }}</td>
<td>{{ person.email }}</td>
<td>{{ person.address }}</td>
</tr>
</tbody>
</table>
As elegant as that!
那样的优雅!