折角标签本质是用带圆角的伪元素经旋转与定位实现视觉遮罩效果;关键在于设置transform-origin: bottom right使旋转轴精准咬合卡片右上角,并通过背景色覆盖与父容器圆角协同形成缺口。

折角标签的视觉本质是遮罩叠加
所谓“折角”,实际是用一个带 border-radius 的伪元素盖在卡片右上角,再配合 transform: rotate(45deg) 倾斜,使其一角对齐卡片顶点;关键不是“画角”,而是让这个倾斜块的右下角精准咬合卡片右上角,并留出圆角缺口。很多人直接旋转一个正方形,结果边缘溢出或对不齐,问题就出在没调整 transform-origin 和定位偏移。
::before 必须脱离文档流且精确定位
卡片容器需设 position: relative,::before 才能用绝对定位锚定右上角。常见错误是忘记设 content: ""(否则伪元素不渲染),或漏掉 z-index 导致被卡片内容遮挡。
-
position: absolute+top: 0+right: 0是起点,但仅靠这三项无法对齐折角顶点 - 必须加
transform-origin: bottom right,确保旋转轴落在伪元素自身右下角——这样旋转后,该点才不动,正好卡在卡片右上角 - 为预留圆角缺口,伪元素宽高建议略大于卡片圆角值(例如卡片
border-radius: 8px,伪元素设width: 32px、height: 32px)
圆角缺口靠背景色与父容器协同实现
纯 CSS 无法直接“挖空”一个圆角三角形,所以采用“覆盖+露底”策略:让伪元素背景色 = 卡片背景色,同时卡片自身右上角保持 border-radius。这样伪元素旋转后盖上去,其左上部分会超出卡片圆角范围,而右下部分刚好贴合直角边,视觉上就形成了带圆角的折角效果。
示例关键代码:
立即学习“前端免费学习笔记(深入)”;
.card {
position: relative;
border-radius: 8px;
background: #fff;
}
.card::before {
content: "";
position: absolute;
top: 0; right: 0;
width: 32px; height: 32px;
background: #fff; /* 必须和卡片背景一致 */
transform: rotate(45deg);
transform-origin: bottom right;
z-index: 1;
}文字内容与响应式适配的坑
如果要在折角里加文字(如“NEW”),不能直接写在 ::before 里(content 只支持字符串或计数器),得额外加一层 ::after 或真实子元素。另外,小屏幕下折角容易挤压变形:当卡片宽度小于 200px 时,固定 32px 宽高的伪元素会显得过大,建议用 vw 或媒体查询动态缩放。
- 文字层需单独定位,
transform: translate(-50%, -50%) rotate(-45deg)才能居中在折角内 - 移动端务必检查
transform-origin是否仍指向正确角落——有些浏览器对小尺寸元素 origin 计算有偏差 - 避免在
backdrop-filter或半透明卡片上用此方案,因为伪元素背景色无法完美匹配动态模糊背景
圆角折角真正难的不是旋转,而是让三个角(卡片右上角、伪元素旋转轴、文字基线)在不同缩放和颜色场景下始终对齐。动手前先用 outline: 1px solid red 轮廓调试伪元素位置,比反复猜 margin 有效得多。


















