diff --git a/docs/en-US/component/button.md b/docs/en-US/component/button.md
index b64bfd9e8f..8e1ac968b4 100644
--- a/docs/en-US/component/button.md
+++ b/docs/en-US/component/button.md
@@ -25,10 +25,16 @@ button/disabled
:::
-## Link Button
+## Link Button
-Since the last version, we deleted `type="link"` which was not really a smooth transition, so we added back `Link Button`,
-for some users `Link Button` is the suitable choice. Notably we would suggest using `Link` component to be more accessible.
+:::warning
+
+`type="text"` has been **deprecated**, and **will be** removed in , consider switching to new API.
+
+New API `type="link"` has been added in , you can use `type` API to set the
+theme of your link button
+
+:::
:::demo
diff --git a/packages/components/button/src/button.ts b/packages/components/button/src/button.ts
index 839051ad96..bd721eade1 100644
--- a/packages/components/button/src/button.ts
+++ b/packages/components/button/src/button.ts
@@ -11,6 +11,11 @@ export const buttonTypes = [
'warning',
'info',
'danger',
+ /**
+ * @deprecated
+ * Text type will be deprecated in the next major version (3.0.0)
+ */
+ 'text',
'',
] as const
export const buttonNativeTypes = ['button', 'submit', 'reset'] as const
diff --git a/packages/components/button/src/button.vue b/packages/components/button/src/button.vue
index d03476f21f..74719ded2e 100644
--- a/packages/components/button/src/button.vue
+++ b/packages/components/button/src/button.vue
@@ -44,6 +44,7 @@
import { Text, computed, inject, ref, useSlots } from 'vue'
import { ElIcon } from '@element-plus/components/icon'
import {
+ useDeprecated,
useDisabled,
useFormItem,
useGlobalConfig,
@@ -62,6 +63,17 @@ const props = defineProps(buttonProps)
const emit = defineEmits(buttonEmits)
const slots = useSlots()
+useDeprecated(
+ {
+ from: 'type.link',
+ replacement: 'text',
+ version: '3.0.0',
+ scope: 'props',
+ ref: 'https://element-plus.org/en-US/component/button.html#button-attributes',
+ },
+ computed(() => props.type === 'text')
+)
+
const buttonGroupContext = inject(buttonGroupContextKey, undefined)
const globalConfig = useGlobalConfig('button')
const ns = useNamespace('button')
diff --git a/packages/theme-chalk/src/button.scss b/packages/theme-chalk/src/button.scss
index d243b8335f..662c231a46 100644
--- a/packages/theme-chalk/src/button.scss
+++ b/packages/theme-chalk/src/button.scss
@@ -40,7 +40,7 @@ $button-icon-span-gap: map.merge(
vertical-align: middle;
-webkit-appearance: none;
- &:not(.is-text, .is-link) {
+ &:not(.is-text, .is-link, .#{$namespace}-button--text) {
background-color: getCssVar('button', 'bg-color');
border: getCssVar('border');
border-color: getCssVar('button', 'border-color');
@@ -236,6 +236,34 @@ $button-icon-span-gap: map.merge(
}
}
+ @include m(text) {
+ border-color: transparent;
+ background: transparent;
+ color: getCssVar('color', 'primary');
+ padding-left: 0;
+ padding-right: 0;
+ @include when(disabled) {
+ color: getCssVar('button', 'disabled', 'text-color');
+ background-color: transparent !important;
+ border-color: transparent !important;
+ }
+
+ &:not(.is-disabled) {
+ &:hover,
+ &:focus {
+ color: getCssVar('color', 'primary', 'light-3');
+ border-color: transparent;
+ background-color: transparent;
+ }
+
+ &:active {
+ color: getCssVar('color', 'primary', 'dark-2');
+ border-color: transparent;
+ background-color: transparent;
+ }
+ }
+ }
+
@include e(link) {
@include m(expand) {
letter-spacing: 0.3em;