element-ui 組件庫 button 源碼分析

前言

團(tuán)隊要根據(jù)新的 UI 規(guī)范實現(xiàn)一個組件庫挟炬,button 組件規(guī)范要支持多種主題換膚焰络,字體顏色戴甩、背景顏色、邊框和禁用使用新的規(guī)范闪彼,并且一種主題顏色主要組件上使用兩種主題顏色混合甜孤。另外协饲,增加多一種幽靈按鈕類型,經(jīng)過分析缴川,在 element-ui 的 button 組件上改造麻煩茉稠,不好維護(hù),所以需要造一個 button 組件把夸,閱讀 element-ui 組件庫 button 的源碼設(shè)計而线,參考 element-plus css 自定義變量 實現(xiàn)

element-ui 源碼分析 button

button 屬性

button文檔屬性 可以定義按鈕的尺寸(size),類型(type)恋日,樸素樣式(plain)膀篮,圓角(round),圓形(circle)岂膳,加載(loading)誓竿,禁用(disabled),圖標(biāo)(icon)谈截,是否聚焦(autofocus)等

參數(shù) 說明 類型 可選值 默認(rèn)值
size 尺寸 string medium / small / mini
type 類型 string primary / success / warning / danger / info / text
plain 是否樸素按鈕 boolean false
round 是否圓角按鈕 boolean false
circle 是否圓形按鈕 boolean false
loading 是否加載中狀態(tài) boolean false
disabled 是否禁用狀態(tài) boolean false
icon 圖標(biāo)類名 string
autofocus 是否默認(rèn)聚焦 boolean false
native-type 原生 type 屬性 string button / submit / reset button

button 使用

<template>
  <div>
    <el-button>默認(rèn)按鈕</el-button>

    <!-- 尺寸(size):medium(中等)筷屡,small(小型),mini(超恤の埂) -->
    <el-button size="medium">中等按鈕</el-button>

    <!-- 類型(type):default(默認(rèn))毙死,primary(主要),success(成功)娘赴,info(信息)规哲,warning(警告),danger(危險)诽表,text(文本) -->
    <el-button type="primary">主要按鈕</el-button>
    <el-button type="text">文字按鈕</el-button>

    <!-- 樸素(plain):true唉锌,false -->
    <el-button type="primary" plain>主要按鈕</el-button>

    <!-- 圓角(round):true,false -->
    <el-button round>主要按鈕</el-button>

    <!-- 圓形(circle):true竿奏,false袄简。一般與圖標(biāo) icon 連用 -->
    <el-button icon="el-icon-search" circle></el-button>

    <!-- 禁用(disabled):true,false泛啸。按鈕顏色變淺绿语,鼠標(biāo)懸浮出現(xiàn)禁止符號。 -->
    <el-button disabled>禁用按鈕</el-button>

    <!-- 圖標(biāo)(icon):設(shè)置icon屬性即可候址,可以參考 icon 組件吕粹。設(shè)置在文字右邊的 icon 岗仑,需要使用i標(biāo)簽驶赏,此時最好添加上 el-icon--right 類蚯姆。 -->
    <el-button type="primary" icon="el-icon-edit">圖標(biāo)按鈕</el-button>
    <el-button type="primary"
      >圖標(biāo)按鈕<i class="el-icon-edit el-icon--right"></i
    ></el-button>

    <!-- 加載(loading):true桐玻,false。為 true 時點擊事件失效。 -->
    <el-button type="primary" :loading="true">加載中</el-button>
  </div>
</template>

Button 源碼分析

相關(guān)文件路徑:

button.vue 文件

button.vue文件路徑

props 的屬性在文檔說明中都有提到明未,是對組件的擴(kuò)展

  • type: 拼接在 el-button-- 后面亲雪,生成不同的 class 類行疏,重新定義 color匆光、background-colorborder-color 覆蓋 el-button 默認(rèn)樣式
  • size:外部控制按鈕大小酿联,同時可以被表單元素和全局控制终息,el-button-- + size 類樣式,例如 el-button--small
  • icon:支持不同的圖標(biāo)贞让,加載中的圖標(biāo)只能使用 el-icon-loading
  • nativeType:按鈕的原生類型周崭,默認(rèn)是 button,可以是 submit喳张、reset
  • loading:加載中的狀態(tài)续镇,is-loading 樣式,按鈕會被禁用
  • disabled:禁用按鈕销部,is-disabled 類樣式摸航,使用 when(disabled) 生成
  • plain:樸素按鈕制跟,is-plain類樣式
  • autofocus:自動聚焦,focus 狀態(tài)樣式按鈕
  • round:圓角樣式 is-round
  • circle:圓心樣式 is-circle酱虎,一般配合 icon 圖標(biāo)使用
// button.vue 源碼

<template>
  <!-- 原生的 button 進(jìn)行樣式封裝雨膨。 -->
  <button
    class="el-button"
    @click="handleClick"
    :disabled="buttonDisabled || loading"
    :autofocus="autofocus"
    :type="nativeType"
    :class="[
      type ? 'el-button--' + type : '',
      buttonSize ? 'el-button--' + buttonSize : '',
      {
        'is-disabled': buttonDisabled,
        'is-loading': loading,
        'is-plain': plain,
        'is-round': round,
        'is-circle': circle
      }
    ]"
  >
    <!-- 
      1. el-icon-loading 是加載圖標(biāo)類,
      2. 這里使用了兩個 <i></i> 都是用來放圖標(biāo)的读串,會根據(jù) loading 的值進(jìn)行二選一
         并且 loading = ture 加載狀態(tài)無法使用其他圖標(biāo)聊记,同時外層 button 被設(shè)置為 disabled
    -->
    <i class="el-icon-loading" v-if="loading"></i>
    <i :class="icon" v-if="icon && !loading"></i>

    <!-- 按鈕文本插槽,default 屬性包括了所有沒有被包含在具名插槽中的節(jié)點 -->
    <span v-if="$slots.default"><slot></slot></span>
  </button>
</template>

SCSS 變量文件

common/var.scss 公共變量文件源碼 定義公共樣式和所有組件樣式變量的文件恢暖,例如主題顏色排监、字體顏色、字體大小等杰捂,可以通過這個文件實現(xiàn)組件庫的換膚

例如主題變量 $--color-primary

mix 函數(shù)是將兩種顏色按不同的占比混合生成一個新的顏色舆床,例如 mix($--color-white, $--color-primary, 10%), $--color-white 顏色占比 10%,$--color-primary 占比 90%琼娘,生成一種新的顏色

$--color-primary: #409EFF !default;
/// color|1|Background Color|4
$--color-white: #FFFFFF !default;
/// color|1|Background Color|4
$--color-black: #000000 !default;
$--color-primary-light-1: mix($--color-white, $--color-primary, 10%) !default; /* 53a8ff */
$--color-primary-light-2: mix($--color-white, $--color-primary, 20%) !default; /* 66b1ff */
$--color-primary-light-3: mix($--color-white, $--color-primary, 30%) !default; /* 79bbff */
$--color-primary-light-4: mix($--color-white, $--color-primary, 40%) !default; /* 8cc5ff */
$--color-primary-light-5: mix($--color-white, $--color-primary, 50%) !default; /* a0cfff */
$--color-primary-light-6: mix($--color-white, $--color-primary, 60%) !default; /* b3d8ff */
$--color-primary-light-7: mix($--color-white, $--color-primary, 70%) !default; /* c6e2ff */
$--color-primary-light-8: mix($--color-white, $--color-primary, 80%) !default; /* d9ecff */
$--color-primary-light-9: mix($--color-white, $--color-primary, 90%) !default; 

BEM CSS規(guī)范

element 的樣式規(guī)范是使用 bem 管理峭弟,根據(jù)規(guī)范生成類名,避免樣式污染脱拼,bem 函數(shù)的公共代碼片段定義在 packages/theme-chalk/src/mixins/mixins.scss 文件

theme-chalk/src/mixins/config.scss 定義命名空間

$namespace: 'el';
$element-separator: '__';
$modifier-separator: '--';
$state-prefix: 'is-';

1瞒瘸、bblock 的 mixin簡寫函數(shù),調(diào)用 @include b(button) 參數(shù) $block 賦值 button, 拼接命名空間變量 $namespace el 得到 el-button, !global 改為全局變量熄浓,可以給下文使用情臭, @content 占位符插入內(nèi)容

@mixin b($block) {
  $B: $namespace+'-'+$block !global;

  .#{$B} {
    @content;
  }
}

使用 @mixin b 代碼片段

@include b(button) {
  display: inline-block;
  line-height: 1;
}

編譯結(jié)果是

.el-button {
  display: inline-block;
  line-height: 1;
}

2、e 是 element 的簡寫函數(shù)赌蔑,@include e(icon) 調(diào)用俯在,$element 傳入 icon,在上面 b 函數(shù)已經(jīng)將 $B 賦值為全局變量 el-button娃惯,$currentSelector 拼接后得到 .el-button__icon@at-root 是跳出嵌套趾浅,和 .el-button 同級愕提,而不是 .el-button .el-button-icon 拼接在后面

@mixin e($element) {
  $E: $element !global;
  $selector: &;
  $currentSelector: "";
  @each $unit in $element {
    $currentSelector: #{$currentSelector + "." + $B + $element-separator + $unit + ","};
  }

  @if hitAllSpecialNestRule($selector) {
    @at-root {
      #{$selector} {
        #{$currentSelector} {
          @content;
        }
      }
    }
  } @else {
    @at-root {
      #{$currentSelector} {
        @content;
      }
    }
  }
}

3、m 修飾符函數(shù)皿哨,傳入 primary, 遍歷 $modifier 只有一個元素浅侨,遍歷結(jié)果后 $currentSelector 賦值是 &--primary,在scss 編譯证膨, & 是上級類 el-button如输,編輯是 el-button--primary

@mixin m($modifier) {
  $selector: &;
  $currentSelector: "";
  @each $unit in $modifier {
    $currentSelector: #{$currentSelector + & + $modifier-separator + $unit + ","};
  }

  @at-root {
    #{$currentSelector} {
      @content;
    }
  }
}

使用 m 函數(shù)

@include b(button) {
  @include m(primary) {
  
  }
}

編譯結(jié)果是

.el-button--primary {
  
}

button.scss 組件樣式

組件庫的樣式單獨單獨放在一個目錄管理,通過 gulp 打包,源碼路徑 packages/theme-chalk/src/button.scss

@include b(button) 定義 el-button 類樣式不见,& + & 相鄰兩個按鈕左間距 10px澳化,button-size 是生成按鈕的大小,設(shè)計水平脖祈、垂直的內(nèi)邊距肆捕,字體大小和邊框圓角,抽象出方法定義在 packages/theme-chalk/src/mixins/_button

@include b(button) {
  // 基本樣式盖高,默認(rèn)樣式,在未指定 type 之前
  display: inline-block;
  line-height: 1;
  white-space: nowrap;
  cursor: pointer;
  background: $--button-default-background-color;   // 默認(rèn)背景色眼虱, white
  border: $--border-base;   // 1px solid #DCDFE6
  border-color: $--button-default-border-color;     // #DCDFE6
  color: $--button-default-font-color;  // #606266
  -webkit-appearance: none;
  text-align: center;
  box-sizing: border-box;
  outline: none;
  margin: 0;
  transition: .1s;
  font-weight: $--button-font-weight;   // 500

  // 在 packages/theme-chalk/src/mixins/utils 喻奥,主要是 moz,webkit,ms 的用戶選擇設(shè)置
  @include utils-user-select(none);

  // 兄弟節(jié)點之間
  & + & {
    margin-left: 10px;
  }

  // 在 packages/theme-chalk/src/mixins/_button,設(shè)置按鈕邊距捏悬、字體撞蚕、邊框弧度
  @include button-size($--button-padding-vertical, $--button-padding-horizontal, $--button-font-size, $--button-border-radius);

  // 懸浮、聚焦按鈕樣式
  &:hover,
  &:focus {
    color: $--color-primary;
    border-color: $--color-primary-light-7;
    background-color: $--color-primary-light-9;
  }

  &::-moz-focus-inner {
    border: 0;
  }

  // 按鈕圖標(biāo)和文字的間距
  & [class*="el-icon-"] {
    & + span {
      margin-left: 5px;
    }
  }
  ...
}

when 函數(shù) 是定義不同狀態(tài)的樣式过牙,$state-prefixis-甥厦,傳入狀態(tài)類型拼接,例如 when(loading).el-button.is-loading

@mixin when($state) {
  @at-root {
    &.#{$state-prefix + $state} {
      @content;
    }
  }
}

when(plain)寇钉、when(active)刀疙、when(disabled)when(loading)扫倡、when(round)谦秧、when(circle) 分別定義 is-plainis-active撵溃、is-disabled疚鲤、is-loadingis-round缘挑、is-circle集歇,這也是 button prop 傳入的屬性,生成不同的類樣式顯示

@include when(plain) {
    &:hover,
    &:focus {
      background: $--color-white;
      border-color: $--color-primary;
      color: $--color-primary;
    }

    &:active {
      background: $--color-white;
      border-color: mix($--color-black, $--color-primary, $--button-active-shade-percent);
      color: mix($--color-black, $--color-primary, $--button-active-shade-percent);
      outline: none;
    }
  }

  @include when(active) {
    color: mix($--color-black, $--color-primary, $--button-active-shade-percent);
    border-color: mix($--color-black, $--color-primary, $--button-active-shade-percent);
  }

  @include when(disabled) {
    &,
    &:hover,
    &:focus {
      color: $--button-disabled-font-color;
      cursor: not-allowed;
      background-image: none;
      background-color: $--button-disabled-background-color;
      border-color: $--button-disabled-border-color;
    }

    &.el-button--text {
      background-color: transparent;
    }

    &.is-plain {
      &,
      &:hover,
      &:focus {
        background-color: $--color-white;
        border-color: $--button-disabled-border-color;
        color: $--button-disabled-font-color;
      }
    }
  }

  @include when(loading) {
    position: relative;
    pointer-events: none;

    &:before {
      pointer-events: none;
      content: '';
      position: absolute;
      left: -1px;
      top: -1px;
      right: -1px;
      bottom: -1px;
      border-radius: inherit;
      background-color: rgba(255,255,255,.35);
    }
  }
  @include when(round) {
    border-radius: 20px;
    padding: 12px 23px;
  }
  @include when(circle) {
    border-radius: 50%;
    padding: $--button-padding-vertical;
  }

例如 is-plain 樣式

組件傳入 type语淘,是通過下面 m() 函數(shù)定義不同的 class诲宇,button-variant 代碼片段是定義在 mixins/_button,

@include m(primary) {
    @include button-variant($--button-primary-font-color, $--button-primary-background-color, $--button-primary-border-color);
  }
  @include m(success) {
    @include button-variant($--button-success-font-color, $--button-success-background-color, $--button-success-border-color);
  }
  @include m(warning) {
    @include button-variant($--button-warning-font-color, $--button-warning-background-color, $--button-warning-border-color);
  }
  @include m(danger) {
    @include button-variant($--button-danger-font-color, $--button-danger-background-color, $--button-danger-border-color);
  }
  @include m(info) {
    @include button-variant($--button-info-font-color, $--button-info-background-color, $--button-info-border-color);
  }

button-variant 傳入不同的 colorbackground-color亏娜、border-color 變量覆蓋 default 默認(rèn)按鈕的字體顏色焕窝、背景顏色和邊框顏色,并且定義了偽類 hover维贺、focus它掂、activedisabled 交互狀態(tài),顏色變淺通過 mix白色 混合

@mixin button-variant($color, $background-color, $border-color) {
  color: $color;
  background-color: $background-color;
  border-color: $border-color;

  &:hover,
  &:focus {
    background: mix($--color-white, $background-color, $--button-hover-tint-percent);
    border-color: mix($--color-white, $border-color, $--button-hover-tint-percent);
    color: $color;
  }
  
  &:active {
    background: mix($--color-black, $background-color, $--button-active-shade-percent);
    border-color: mix($--color-black, $border-color, $--button-active-shade-percent);
    color: $color;
    outline: none;
  }

  &.is-active {
    background: mix($--color-black, $background-color, $--button-active-shade-percent);
    border-color: mix($--color-black, $border-color, $--button-active-shade-percent);
    color: $color;
  }

  &.is-disabled {
    &,
    &:hover,
    &:focus,
    &:active {
      color: $--color-white;
      background-color: mix($background-color, $--color-white);
      border-color: mix($border-color, $--color-white);
    }
  }

  &.is-plain {
    @include button-plain($background-color);
  }
}

&.is-plain 類覆蓋主要按鈕的顏色得到樸素按鈕虐秋,使用 button-plain($background-color) 定義在同一個文件榕茧,偽類也是定義 colorbackground-color客给、border-color 覆蓋

@mixin button-plain($color) {
  color: $color;
  background: mix($--color-white, $color, 90%);
  border-color: mix($--color-white, $color, 60%);

  &:hover,
  &:focus {
    background: $color;
    border-color: $color;
    color: $--color-white;
  }

  &:active {
    background: mix($--color-black, $color, $--button-active-shade-percent);
    border-color: mix($--color-black, $color, $--button-active-shade-percent);
    color: $--color-white;
    outline: none;
  }

  &.is-disabled {
    &,
    &:hover,
    &:focus,
    &:active {
      color: mix($--color-white, $color, 40%);
      background-color: mix($--color-white, $color, 90%);
      border-color: mix($--color-white, $color, 80%);
    }
  }
}

button 提供 4 種按鈕大小用押,默認(rèn)是最大的按鈕,還有 medium 中等靶剑、small 小的和 mini 特小的蜻拨,它是調(diào)用 button-size 傳入不同的垂直、水平的內(nèi)間距桩引、字體大小和邊框圓角變量值缎讼,定義按鈕的大小

  @include m(medium) {
    @include button-size($--button-medium-padding-vertical, $--button-medium-padding-horizontal, $--button-medium-font-size, $--button-medium-border-radius);
    @include when(circle) {
      padding: $--button-medium-padding-vertical;
    }
  }
  @include m(small) {
    @include button-size($--button-small-padding-vertical, $--button-small-padding-horizontal, $--button-small-font-size, $--button-small-border-radius);
    @include when(circle) {
      padding: $--button-small-padding-vertical;
    }
  }
  @include m(mini) {
    @include button-size($--button-mini-padding-vertical, $--button-mini-padding-horizontal, $--button-mini-font-size, $--button-mini-border-radius);
    @include when(circle) {
      padding: $--button-mini-padding-vertical;
    }
  }

button-size 代碼定義在 mixin/_button.scss

@mixin button-size($padding-vertical, $padding-horizontal, $font-size, $border-radius) {
  padding: $padding-vertical $padding-horizontal;
  font-size: $font-size;
  border-radius: $border-radius;
  &.is-round {
    padding: $padding-vertical $padding-horizontal;
  }
}

按鈕支持文本類型 el-button--text,將 border坑匠、background 變透明血崭,設(shè)置不同的字體顏色,定義偽類狀態(tài)

  @include m(text) {
    border-color: transparent;
    color: $--color-primary;
    background: transparent;
    padding-left: 0;
    padding-right: 0;

    &:hover,
    &:focus {
      color: mix($--color-white, $--color-primary, $--button-hover-tint-percent);
      border-color: transparent;
      background-color: transparent;
    }
    &:active {
      color: mix($--color-black, $--color-primary, $--button-active-shade-percent);
      border-color: transparent;
      background-color: transparent;
    }

    &.is-disabled,
    &.is-disabled:hover,
    &.is-disabled:focus {
      border-color: transparent;
    }
  }
}

總結(jié)一下厘灼,button 按鈕的樣式變量定義在 commont/var.scss 維護(hù)夹纫,其他組件也是這種做法,這樣就做到只需要修改 var.scss 文件就可以實現(xiàn)組件庫的換膚设凹。

按鈕的樣式規(guī)范使用 bem 規(guī)范舰讹,@include b(button) 定義基礎(chǔ)類樣式 el-button;按鈕大小是通過 @include button-size(...) 傳入內(nèi)邊距围来、字體大小變量控制顯示跺涤。

不同的按鈕 type 類型、偽類狀態(tài)還有樸素按鈕监透,通過修改 color桶错、background-colorborder-color 覆蓋默認(rèn)樣式胀蛮,顏色變淺通過 mix 函數(shù)混合白色生成新的顏色院刁,文本按鈕、按鈕組還有不同的按鈕狀態(tài)根據(jù) bem 規(guī)范生成類樣式定義粪狼。

通過學(xué)習(xí)優(yōu)秀的組件庫設(shè)計退腥,發(fā)現(xiàn)處處設(shè)計的很巧妙,站在巨人的肩膀上學(xué)習(xí)再榄。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末狡刘,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子困鸥,更是在濱河造成了極大的恐慌嗅蔬,老刑警劉巖剑按,帶你破解...
    沈念sama閱讀 206,214評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異澜术,居然都是意外死亡艺蝴,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,307評論 2 382
  • 文/潘曉璐 我一進(jìn)店門鸟废,熙熙樓的掌柜王于貴愁眉苦臉地迎上來猜敢,“玉大人,你說我怎么就攤上這事盒延∷趵蓿” “怎么了?”我有些...
    開封第一講書人閱讀 152,543評論 0 341
  • 文/不壞的土叔 我叫張陵兰英,是天一觀的道長撇叁。 經(jīng)常有香客問我,道長畦贸,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 55,221評論 1 279
  • 正文 為了忘掉前任楞捂,我火速辦了婚禮薄坏,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘寨闹。我一直安慰自己胶坠,他們只是感情好,可當(dāng)我...
    茶點故事閱讀 64,224評論 5 371
  • 文/花漫 我一把揭開白布繁堡。 她就那樣靜靜地躺著沈善,像睡著了一般。 火紅的嫁衣襯著肌膚如雪椭蹄。 梳的紋絲不亂的頭發(fā)上闻牡,一...
    開封第一講書人閱讀 49,007評論 1 284
  • 那天,我揣著相機(jī)與錄音绳矩,去河邊找鬼罩润。 笑死,一個胖子當(dāng)著我的面吹牛翼馆,可吹牛的內(nèi)容都是我干的割以。 我是一名探鬼主播,決...
    沈念sama閱讀 38,313評論 3 399
  • 文/蒼蘭香墨 我猛地睜開眼应媚,長吁一口氣:“原來是場噩夢啊……” “哼严沥!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起中姜,我...
    開封第一講書人閱讀 36,956評論 0 259
  • 序言:老撾萬榮一對情侶失蹤消玄,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體莱找,經(jīng)...
    沈念sama閱讀 43,441評論 1 300
  • 正文 獨居荒郊野嶺守林人離奇死亡酬姆,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 35,925評論 2 323
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了奥溺。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片辞色。...
    茶點故事閱讀 38,018評論 1 333
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖浮定,靈堂內(nèi)的尸體忽然破棺而出相满,到底是詐尸還是另有隱情,我是刑警寧澤桦卒,帶...
    沈念sama閱讀 33,685評論 4 322
  • 正文 年R本政府宣布立美,位于F島的核電站,受9級特大地震影響方灾,放射性物質(zhì)發(fā)生泄漏建蹄。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 39,234評論 3 307
  • 文/蒙蒙 一裕偿、第九天 我趴在偏房一處隱蔽的房頂上張望洞慎。 院中可真熱鬧,春花似錦嘿棘、人聲如沸劲腿。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,240評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽焦人。三九已至,卻和暖如春重父,著一層夾襖步出監(jiān)牢的瞬間花椭,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 31,464評論 1 261
  • 我被黑心中介騙來泰國打工坪郭, 沒想到剛下飛機(jī)就差點兒被人妖公主榨干…… 1. 我叫王不留个从,地道東北人。 一個月前我還...
    沈念sama閱讀 45,467評論 2 352
  • 正文 我出身青樓歪沃,卻偏偏與公主長得像嗦锐,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子沪曙,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 42,762評論 2 345

推薦閱讀更多精彩內(nèi)容