在 Angular Material CDK 拖放中,如何防止项目随着元素移动而自动重新排列?

Posted

技术标签:

【中文标题】在 Angular Material CDK 拖放中,如何防止项目随着元素移动而自动重新排列?【英文标题】:In Angular Material CDK Drag Drop, How to Prevent Items from Automatically Rearranging as an Element Moves? 【发布时间】:2019-10-23 06:05:51 【问题描述】:

提前致谢。问题来了:

我正在使用Angular Material CDK Drag Drop(版本:@angular/ckd:7.3.7)

文档说“项目将随着元素的移动而自动重新排列。

我的问题是:如何防止项目在元素移动时自动重新排列?

Here is an animated gif of what I don't want。这是我制作的棋盘,您可以看到“项目(棋子)随着元素(棋子)移动而自动重新排列”

Here is an animated gif of what I want。我想要的是物品(棋子)不会随着元素(棋子)的移动而重新排列。

Here is a stackblitz with the code

【问题讨论】:

【参考方案1】:

只需创建一个 empy cdkDragPlaceholder,你需要将 img 包含在一个 div 中

<div class="square"
     [ngClass]="'white': square.row % 2 === square.col %2,
  'black': square.row % 2 !== square.col % 2"
  cdkDropList
   ...>
  <div cdkDrag cdkDragBoundary=".board">
    <img *ngIf="square.piece"
       class="piece"
       src="square.piece.img()"
       />
       <!---this is a empty dragPlaceHolder-->
       <div *cdkDragPlaceholder></div>
   </div>
</div>

【讨论】:

【参考方案2】:

从 Angular 8 开始,可以通过添加 cdkDropListSortingDisabled 来禁用此行为

【讨论】:

这是一个不正确的答案,当您尝试删除项目时,项目也会重新排列。 Op 预计物品在放置期间不会移动。【参考方案3】:

所以:

.cdk-drag-placeholder  display:none;  

应确保对象不会被虚拟插入限制此类行为的 DOM。

我认为它不适用于动态列表,但显然 .cdk-drag-placeholder display:none; 确实有效。

如果它不起作用,则意味着您正在尝试在组件上应用样式,并且这些样式已封装在组件中以避免样式泄漏。新添加的 DOM 元素不会“看到”应用的样式。一个解决方案是放置 ViewEncapsulation.None 以便允许样式从组件中泄漏并将 css 规则调整为:

#my-special-list 
    & > .cdk-drag-placeholder 
        display: none !important;
    

所以要确保它不会阻碍组件外部的样式。

【讨论】:

【参考方案4】:

项目的移动是通过使用transform: translate3d(Xpx, Ypx, Zpx); 规则向元素添加内联样式来完成的。

您可以通过将其设置为默认零值添加 !important 来覆盖元素的 css 内的此内联样式规则。当您执行此操作时,将不会应用规则并且行将保持原位。

/* This prevents cdk drag sorting from shuffling things around */
.piece 
  transform: translate3d(0px, 0px, 0px) !important;

我自己使用了这个技巧,它很有效。 我试图让它在你的 Stackblitz 中工作,但是代码太多,并且需要花费太多时间来弄清楚它的确切放置位置。如果需要,您应该提供一个“最小工作示例”,而不是提供整个应用程序。

【讨论】:

以上是关于在 Angular Material CDK 拖放中,如何防止项目随着元素移动而自动重新排列?的主要内容,如果未能解决你的问题,请参考以下文章

Angular CDK拖放 - 如何保持原始位置?

Angular Material 7 使用带有拖放功能的网格

cdk-drop 不是已知元素

如何在两个组件之间使用Angular7(角度材料)拖放

Angular CDK拖放,保持顺序直到下降

Angular 嵌套拖放 / CDK 材质 cdkDropListGroup cdkDropList nested