Android ConstraintLayout的使用

圖片來(lái)自GitHub

ConstraintLayout是谷歌推出的一個(gè)新布局,字面意思是約束布局,距離發(fā)布已經(jīng)有一段時(shí)間了,下面會(huì)有一個(gè)復(fù)雜布局的代碼對(duì)比。
對(duì)于ConstraintLayout,有篇文章寫了關(guān)于它的性能優(yōu)勢(shì):解析ConstraintLayout的性能優(yōu)勢(shì)

我們知道,當(dāng)我們的布局越來(lái)越復(fù)雜的時(shí)候,所使用的嵌套就越來(lái)多,性能自然而然的就會(huì)有所下降,而ConstraintLayout恰恰就是為了這個(gè)操作而誕生的。

對(duì)于ConstraintLayout的可視化操作可以說(shuō)是非常牛逼啊,參考ConstraintLayout完全解析,但是我個(gè)人不習(xí)慣用可視化的去拖拽控件,所以在這里來(lái)寫在xml上面寫各種屬性。

事前準(zhǔn)備

引入ConstraintLayout

在Android Studio 2.3以后,默認(rèn)創(chuàng)建的布局就是ConstraintLayout布局,如果不是2.3以后的版本,在build.gradle文件中引入ConstraintLayout,當(dāng)前版本是1.0.2

dependencies {
    compile 'com.android.support.constraint:constraint-layout:1.0.2'
    // 3.0以前使用compile,3.0以后使用implementation
    // implementation 'com.android.support.constraint:constraint-layout:1.0.2'
}

轉(zhuǎn)換成ConstraintLayout

如果你需要將原來(lái)的布局轉(zhuǎn)成ConstraintLayout布局的話,可以在打開(kāi)xml文件后,點(diǎn)擊Design選項(xiàng),然后找到Component Tree窗口,最后右鍵布局,選擇Convert layout to ConstraintLayout選項(xiàng)

Convert

對(duì)比布局代碼

下面我們來(lái)通過(guò)一個(gè)布局,來(lái)對(duì)比ConstraintLayout和其他布局來(lái)實(shí)現(xiàn)下面的布局內(nèi)容的代碼:

Sample

首先有除了ConstraintLayout之外的布局來(lái)實(shí)現(xiàn),代碼太長(zhǎng),所以省去屬性,有能力的可以自己去寫一下:

<RelativeLayout>
  <ImageView />
  <FloatingActionButton />
  <RelativeLayout>
    <TextView />
    <LinearLayout>
      <TextView />
      <RelativeLayout>
        <EditText />
      </RelativeLayout>
    </LinearLayout>
    <LinearLayout>
      <TextView />
      <RelativeLayout>
        <EditText />
      </RelativeLayout>
    </LinearLayout>
    <TextView />
  </RelativeLayout>
  <LinearLayout >
    <Button />
    <Button />
  </LinearLayout>
</RelativeLayout>

夠復(fù)雜的,RelativeLayout布局嵌套LinearLayout布局,里面又嵌套多個(gè)布局,嚴(yán)重影響布局的繪制。
那么我們來(lái)看使用ConstraintLayout布局之后的代碼是怎么樣的:

<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context="top.jowanxu.constraintlayoutdemo.MainActivity">

    <ImageView
        android:id="@+id/banner"
        android:layout_width="0dp"
        android:layout_height="0dp"
        android:background="@color/colorAccent"
        android:gravity="center"
        app:layout_constraintDimensionRatio="16:6"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />

    <android.support.design.widget.FloatingActionButton
        android:id="@+id/fab"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="@dimen/fab_margin"
        app:layout_constraintBottom_toBottomOf="@+id/banner"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintHorizontal_bias="0.98"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toBottomOf="@+id/banner"
        app:srcCompat="@android:drawable/ic_dialog_email" />

    <TextView
        android:id="@+id/title"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_marginStart="10dp"
        android:layout_marginTop="10dp"
        android:text="Singapore"
        android:textAppearance="@style/Base.TextAppearance.AppCompat.Title"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toBottomOf="@id/banner" />

    <TextView
        android:id="@+id/camera"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginStart="10dp"
        android:layout_marginTop="10dp"
        android:padding="10dp"
        android:text="Camera"
        android:textAppearance="@style/TextAppearance.AppCompat.Tooltip"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toBottomOf="@id/title" />

    <EditText
        android:id="@+id/cameraEdit"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_marginEnd="10dp"
        android:hint="Leica M Typ 240"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toEndOf="@+id/camera"
        app:layout_constraintTop_toTopOf="@+id/camera" />

    <TextView
        android:id="@+id/settings"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginStart="10dp"
        android:layout_marginTop="10dp"
        android:padding="10dp"
        android:text="Settings"
        android:textAppearance="@style/TextAppearance.AppCompat.Tooltip"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toBottomOf="@+id/cameraEdit" />

    <EditText
        android:id="@+id/settingsEdit"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_marginEnd="10dp"
        android:hint="f/4 16s ISO 200"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toEndOf="@+id/settings"
        app:layout_constraintTop_toTopOf="@+id/settings" />

    <TextView
        android:id="@+id/content"
        android:layout_width="0dp"
        android:layout_height="0dp"
        android:layout_margin="10dp"
        android:layout_marginBottom="8dp"
        android:layout_marginEnd="8dp"
        android:layout_marginStart="8dp"
        android:text="Singapore offically the Republic of Singapore.Singapore offically the Republic of Singapore.Singapore offically the Republic of Singapore.Singapore offically the Republic of Singapore.Singapore offically the Republic of Singapore."
        android:textAppearance="@style/Base.TextAppearance.AppCompat.Body1"
        app:layout_constraintBottom_toTopOf="@+id/discard"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toBottomOf="@+id/settingsEdit" />

    <Button
        android:id="@+id/upload"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="UPLOAD"
        app:layout_constraintBottom_toBottomOf="@+id/discard"
        app:layout_constraintEnd_toStartOf="@+id/discard" />

    <Button
        android:id="@+id/discard"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginBottom="10dp"
        android:layout_marginEnd="10dp"
        android:text="DISCARD"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintEnd_toEndOf="parent" />

</android.support.constraint.ConstraintLayout>

簡(jiǎn)單概括就是,沒(méi)有一層嵌套,而且是一個(gè)完全扁平的層次結(jié)構(gòu):

<ConstraintLayout>
    <ImageView/>
    <FloatingActionButton/>
    <TextView/>
    <TextView/>
    <EditText/>
    <TextView/>
    <EditText/>
    <TextView/>
    <Button/>
    <Button/>
</ConstraintLayout>

開(kāi)始

ConstraintLayout所包含的約束有:

  • Dimension constraints
  • Relative positioning
  • Centering positioning
  • Margins
  • Visibility behavior
  • Chains

Dimensions constraints

Dimensions constraints字面意思就是尺寸約束,可以設(shè)置ConstraintLayout布局的大小,和設(shè)置布局里面控件的尺寸約束。

Minimum dimensions on ConstraintLayout

ConstraintLayout布局與其他布局一樣可以設(shè)置最大尺寸和最小尺寸:

  • android:minWidth
  • android:minHeight
  • android:maxWidth
  • android:maxHeight

Widgets dimension constraints

Dimension

設(shè)置布局里面控件的尺寸約束,我們知道,在普通布局里面,我們每個(gè)控件的寬高,都是在三個(gè)類型里面設(shè)置值的:

  • 固定的值(如100dp),對(duì)應(yīng)圖上a
  • wrap_content,對(duì)應(yīng)圖上a
  • match_parent,對(duì)應(yīng)圖上b,設(shè)置margin對(duì)應(yīng)c

但是在ConstraintLayout布局里面,控件的寬高變?yōu)椋?/p>

  • 固定的值(如100dp),對(duì)應(yīng)圖上a
  • wrap_content,對(duì)應(yīng)圖上a
  • match_constraint,也就是0dp,對(duì)應(yīng)圖上b,設(shè)置margin對(duì)應(yīng)c
ConstraintLayout

與其他布局不同的是ConstraintLayout里面沒(méi)有match_parent,而是用0dp也就是match_constraint替換了他,看下官網(wǎng)怎么說(shuō)的:

Important: MATCH_PARENT is not recommended for widgets contained in a ConstraintLayout. Similar behavior can be defined by using MATCH_CONSTRAINT with the corresponding left/right or top/bottom constraints being set to "parent".

意思是,ConstraintLayout已經(jīng)棄用MATCH_PARENT了,通過(guò)使用MATCH_CONSTRAINT,同時(shí)設(shè)置控件的left/right或者top/bottom來(lái)約束parent來(lái)達(dá)到與MATCH_PARENT一樣的效果,如:

android:layout_width="0dp"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"

下面舉個(gè)栗子,將RelativeLayout和ConstraintLayout寫一下下面的布局

[圖片上傳失敗...(image-b12e85-1516623694099)]

RelativeLayout里面

    <Button
        android:id="@+id/button"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentStart="true"
        android:layout_alignParentTop="true"
        android:text="Button" />

    <Button
        android:id="@+id/button2"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentTop="true"
        android:layout_toEndOf="@+id/button"
        android:layout_alignParentEnd="true"
        android:text="asdfasdfsdfasdfasdfasdfasdfasdfsadfsdafasdfasdfasdf" />
RelativeLayout

然后ConstraintLayout布局

    <Button
        android:id="@+id/button1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Button1"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />

    <Button
        android:id="@+id/button2"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="asdfasdfsdfasdfasdfasdfasdfasdfsadfsdafasdfasdfasdf"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toEndOf="@+id/button1"
        app:layout_constraintTop_toTopOf="parent" />
ConstraintLayout

為什么會(huì)出現(xiàn)這樣的情況呢,跟我們預(yù)期的不一樣,當(dāng)一個(gè)控件的兩邊都有約束的時(shí)候,會(huì)將這個(gè)控件居中,當(dāng)這個(gè)控件寬度或者高度特別大的時(shí)候(超出屏幕),則會(huì)將左右兩邊超出的距離相同,上面說(shuō)了,要達(dá)到MATCH_PARENT效果,需要將尺寸設(shè)置為MATCH_CONSTRAINT也就是0dp,我們來(lái)看一下結(jié)果:

MATCH_CONSTRAINT

Radio

ConstraintLayout里面可以設(shè)置控件的比例,對(duì)應(yīng)寬高比width:height,屬性為:

  • layout_constraintDimensionRatio
Radio

如果我們要把上面的16:6這樣的寫出來(lái),那么我們先要將左右的約束設(shè)置成parent,同時(shí)設(shè)置寬高為MATCH_CONSTRAINT,然后設(shè)置layout_constraintDimensionRatio16:6

    <Button
        android:id="@+id/button1"
        android:layout_width="0dp"
        android:layout_height="0dp"
        android:layout_marginTop="8dp"
        android:text="Button1"
        app:layout_constraintDimensionRatio="16:6"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent" />

而在LinearLayout上設(shè)置卻要這樣寫:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:weightSum="22">

    <Button
        android:id="@+id/button"
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="6"
        android:text="Button" />
</LinearLayout>

對(duì)比下,差別還是很明顯的,ConstraintLayout用起來(lái)還是非常舒服的。

當(dāng)然,還支持單方向的比例,相對(duì)應(yīng)的方向的尺寸設(shè)置為MATCH_CONSTRAINT

<!-- 寬度比例,對(duì)應(yīng)的寬度即為200dp -->
android:layout_width="0dp"
android:layout_height="100dp"
app:layout_constraintDimensionRatio="W,2:1"
<!-- 高度比例,對(duì)應(yīng)的高度即為100dp -->
android:layout_width="200dp"
android:layout_height="0dp"
app:layout_constraintDimensionRatio="H,2:1"

Relative positioning

Relative positioning字面意思是相對(duì)定位,這個(gè)的屬性類似與相對(duì)布局(RelativeLayout)的屬性,屬性的值包括parent和控件的id@+id/button,包含:

  • layout_constraintLeft_toLeftOf
  • layout_constraintLeft_toRightOf
  • layout_constraintRight_toLeftOf
  • layout_constraintRight_toRightOf
  • layout_constraintTop_toTopOf
  • layout_constraintTop_toBottomOf
  • layout_constraintBottom_toTopOf
  • layout_constraintBottom_toBottomOf
  • layout_constraintBaseline_toBaselineOf
  • layout_constraintStart_toEndOf
  • layout_constraintStart_toStartOf
  • layout_constraintEnd_toStartOf
  • layout_constraintEnd_toEndOf

通過(guò)上面我們可以看出,這里的屬性是layout_constraintXX_toYYOf的,這里的XXYY分別表示什么樣的方向?
我們先來(lái)通過(guò)一個(gè)方向的屬性來(lái)了解,其他以此類推:
layout_constraintStart_toStartOflayout_constraintStart_toEndOflayout_constraintEnd_toStartOflayout_constraintEnd_toEndOf


    <Button
        android:id="@+id/button1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Button1"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />

    <Button
        android:id="@+id/button2"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Button2"
        app:layout_constraintStart_toEndOf="@+id/button1"
        app:layout_constraintTop_toTopOf="parent" />

    <Button
        android:id="@+id/button3"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Button3"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintTop_toTopOf="parent" />

    <Button
        android:id="@+id/button4"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Button4"
        app:layout_constraintEnd_toStartOf="@+id/button3"
        app:layout_constraintStart_toEndOf="@+id/button2"
        app:layout_constraintTop_toTopOf="parent" />

我們來(lái)看預(yù)覽圖:

Preview

從上面看出,layout_constraintXX_toYYOf屬性的XX表示當(dāng)前控件的位置,YY則表示需要約束的控件的位置,下面是一個(gè)控件的各邊表示:

Relative Positioning Constraints

Centering positioning and bias

Centering Positioning

字面意思就是居中定位,當(dāng)我們?cè)谙鄬?duì)布局到時(shí)候,如果要居中一個(gè)控件的時(shí)候

<Button
        android:id="@+id/button"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerHorizontal="true"
        android:text="Button" />

在ConstraintLayout里面,可以這樣將控件居中

<Button
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="button"
        app:layout_constraintLeft_toLeftOf="parent"
        app:layout_constraintRight_toRightOf="parent"/>

預(yù)覽圖都是顯示居中

[圖片上傳失敗...(image-27caff-1516623694099)]

因?yàn)樵贑onstraintLayout里面,每個(gè)約束都是類似于在對(duì)應(yīng)方向上,有相反的力 去拉控件,而在這里,則會(huì)水平居中顯示。

bias

Centering Positioning with Bias

上面說(shuō)到每個(gè)約束都是一個(gè)拉力,而bias則表示這個(gè)拉力在兩邊的偏重,對(duì)應(yīng)橫向豎向偏重:

  • layout_constraintHorizontal_bias
  • layout_constraintVertical_bias

同樣用上面的栗子,加入app:layout_constraintHorizontal_bias="0.9"屬性,對(duì)應(yīng)左邊拉力偏重90%,右邊拉力偏重10%

0.9

Margins

ConstraintLayout里面的margin與普通的屬性一樣,只是值不能為負(fù)數(shù)

Note that a margin can only be positive or equals to zero, and takes a Dimension.

Margins when connected to a GONE widget

設(shè)置一個(gè)控件為GONE時(shí)的margin值,下面是包含的屬性:

  • layout_goneMarginStart
  • layout_goneMarginEnd
  • layout_goneMarginLeft
  • layout_goneMarginTop
  • layout_goneMarginRight
  • layout_goneMarginBottom

舉個(gè)栗子:

    <!-- 省去一些代碼 -->
    <Button
        android:id="@+id/button1"
        app:layout_constraintStart_toStartOf="parent" />
    <Button
        android:id="@+id/button2"
        android:layout_marginStart="60dp"
        app:layout_constraintStart_toEndOf="@+id/button1"
        app:layout_goneMarginStart="160dp" />
    <Button
        android:id="@+id/button3"
        app:layout_constraintStart_toStartOf="@+id/button1"
        app:layout_constraintTop_toBottomOf="@+id/button2" />
    <Button
        android:id="@+id/button4"
        android:layout_marginStart="60dp"
        app:layout_constraintStart_toEndOf="@+id/button3"
        app:layout_constraintTop_toBottomOf="@+id/button2"
        app:layout_goneMarginStart="160dp" />

預(yù)覽圖:

預(yù)覽

當(dāng)我們將button3的設(shè)置為GONE的時(shí)候,結(jié)果為:
[圖片上傳失敗...(image-b5a768-1516623694100)]

對(duì)比可以看出:

  • 當(dāng)設(shè)置了goneMargin屬性時(shí)候,約束的控件如果不是GONE的時(shí)候,則不會(huì)生效;
  • 當(dāng)goneMargin屬性和margin屬性同時(shí)存在的時(shí)候,margin屬性不會(huì)生效。

Visibility behavior

字面意思是可見(jiàn)性行為,當(dāng)一個(gè)控件設(shè)置為GONE的時(shí)候,在布局計(jì)算的時(shí)候仍會(huì)加進(jìn)去,在布局過(guò)程中,將被解析成一個(gè)點(diǎn),所有的margin也將為0,但是對(duì)于其他控件的約束仍然存在

Visibility

如果我們需要上面的圖,在A被隱藏后,仍然保持B的位置不變,那么我們就要設(shè)置BgoneMargin的值為A的寬度和marginBmargin值的和,也就是
goneMarginStart = A.width + A.marginStart + B.marginStart

<!-- 示例代碼 -->    
<Button
        android:id="@+id/button1"
        android:layout_width="100dp"
        android:layout_height="wrap_content"
        android:layout_marginStart="10dp"
        android:text="Button1"
        android:visibility="gone"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />

    <Button
        android:id="@+id/button2"
        android:layout_width="100dp"
        android:layout_height="wrap_content"
        android:layout_marginStart="10dp"
        android:text="Button2"
        app:layout_constraintStart_toEndOf="@+id/button1"
        app:layout_constraintTop_toTopOf="parent"
        app:layout_goneMarginStart="120dp" />

總結(jié)

ConstraintLayout比傳統(tǒng)布局的性能更出色,而且ConstraintLayout對(duì)于一些復(fù)雜的布局具有天然的優(yōu)勢(shì),所以還沒(méi)有使用ConstraintLayout的同學(xué),趕緊加入到里面來(lái)吧,ConstraintLayout還有一些內(nèi)容將在下一篇文章介紹(ChainGuideline)。

參考

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 227,156評(píng)論 6 529
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 97,866評(píng)論 3 413
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái),“玉大人,你說(shuō)我怎么就攤上這事。” “怎么了?”我有些...
    開(kāi)封第一講書人閱讀 174,880評(píng)論 0 373
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)。 經(jīng)常有香客問(wèn)我,道長(zhǎng),這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書人閱讀 62,398評(píng)論 1 308
  • 正文 為了忘掉前任,我火速辦了婚禮,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 71,202評(píng)論 6 405
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上,一...
    開(kāi)封第一講書人閱讀 54,743評(píng)論 1 320
  • 那天,我揣著相機(jī)與錄音,去河邊找鬼。 笑死,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 42,822評(píng)論 3 438
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書人閱讀 41,962評(píng)論 0 285
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 48,476評(píng)論 1 331
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 40,444評(píng)論 3 354
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 42,579評(píng)論 1 365
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 38,129評(píng)論 5 355
  • 正文 年R本政府宣布,位于F島的核電站,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 43,840評(píng)論 3 344
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開(kāi)封第一講書人閱讀 34,231評(píng)論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)。三九已至,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開(kāi)封第一講書人閱讀 35,487評(píng)論 1 281
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 51,177評(píng)論 3 388
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 47,568評(píng)論 2 370

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