安卓開發(fā)小總結(jié)

柴鈺棋

歡迎大家挑錯,批評指正啊奄,謝謝

一、RecyclerView

我寫過的幾乎所有的軟件里都有Rv掀潮,其重要性自然不言而喻菇夸。

其實基本用法和ListView沒有多大差距。

1.RecyclerView適配器

RecyclerView不再使用諸如SimpleAdapter仪吧、ArrayAdapter以及BaseAdapter庄新,而是使用其專用的RecyclerView.Adapter,它實現(xiàn)了ViewHolder。

public class MyRvAdapter extends RecyclerView.Adapter<MyRvAdapter.ViewHolder>
{
    List<Map<String,String>>movieList;
    static class ViewHolder extends RecyclerView.ViewHolder{
        public ViewHolder(View view){
            //初始化控件
            super(view);
        }
    }

    public MyRvAdapter(List<Map<String,String>> movieList){
        //將傳遞數(shù)據(jù)進(jìn)來
        this.movieList = movieList;
    }

    @Override
    public MyRvAdapter.ViewHolder onCreateViewHolder(ViewGroup p1, int p2)
    {
        // 為RecyclerView子項設(shè)置布局
        if(mContext == null){
            mContext = p1.getContext();
        }
        View view = LayoutInflater.from(mContext).inflate(R.layout.item,p1,false);


        ViewHolder holder = new ViewHolder(view);

        return holder;
    }

    @Override
    public void onBindViewHolder(MyRvAdapter.ViewHolder p1, int p2)
    {
        // 為RecyclerVier填充數(shù)據(jù)择诈、設(shè)置事件
    }

    @Override
    public int getItemCount()
    {
        // 返回RecyclerView子項的數(shù)目
        return movieList.size();
    }
}
2.RecyclerView布局管理器

一共有三種布局形式

①LinearLayoutManager
效果與ListView一致

LinearLayoutManager manager = new LinearLayoutManager(this, LinearLayoutManager.HORIZONTAL, false);

參數(shù):Context,方向,數(shù)據(jù)是否倒序

②GridLayoutManager
效果與GridView一致

GridLayoutManager manager = new GridLayoutManager(this,2)

參數(shù):Context,列數(shù)

③StaggeredGridLayoutManager
瀑布流效果

StaggeredGridLayoutManager manager = new StaggeredGridLayoutManager(2,StaggeredGridLayoutManager.VERTICAL);

參數(shù):列數(shù),方向

3.RecyclerView定位及保存位置并恢復(fù)

在項目里有這樣一個需求:
電影分類下的數(shù)據(jù)

搜索結(jié)果

用同一個Rv展示分類數(shù)據(jù)和搜索結(jié)果械蹋,當(dāng)我退出搜索時,精確恢復(fù)到搜索前的位置吭从。

//搜索時保存位置
searchState = true;
View firstVirew = layoutManager.getChildAt(0);
savedTopHeight = firstVirew.getTop();
savedPosition = layoutManager.getPosition(firstVirew)

//searchState:當(dāng)前rv展示的是否為搜索結(jié)果
//firstView:當(dāng)前可見的第一個item
savedPosition:firstView在所有item中的位置
//savedTopHeight:firstView與RecyclerView頂部的距離
//關(guān)閉SearchView時恢復(fù)位置
if(searchState){
layoutManager.scrollToPositionWithOffset(savedPosition,savedTopHeight)
}

另外還有一個回到頂部的功能

//平滑滾動朝蜘,有一個過渡動畫
recyclerView.smoothScrollToPosition(position);
//滾動到指定位置
recyclerView.scrollToPosition(position);

//另外還有scrollBy(int x,int y)和layoutManager.scrollToPositionWithOffset(int position,int offset)

這里我們用scrollToPosition(0)來實現(xiàn)回到頂部的功能

4.RecyclerView上拉加載(滑動監(jiān)聽)

項目里的影片數(shù)據(jù)基于網(wǎng)頁,一頁就那么幾個數(shù)據(jù)涩金。當(dāng)我們滑動到Rv底部時谱醇,加載下一頁的數(shù)據(jù)并填充。

//設(shè)置滑動監(jiān)聽
        rv.setOnScrollListener(new RecyclerView.OnScrollListener(){

                public void onScrollStateChanged(RecyclerView recyclerView, int newState){
                    super.onScrollStateChanged(recyclerView,newState);
                    
                    //要調(diào)用的回調(diào)方法當(dāng)RecyclerView滾動狀態(tài)改變步做。
                    /**newState 一共有三種狀態(tài)
                     * SCROLL_STATE_IDLE代表RecyclerView現(xiàn)在不是滾動狀態(tài)副渴。
                    * SCROLL_STATE_DRAGGING代表RecyclerView處于被外力引導(dǎo)的滾動狀態(tài),比如手指正在拖著進(jìn)行滾動全度。
                    *SCROLL_STATE_SETTLING代表RecyclerView處于自動滾動的狀態(tài)煮剧,此時手指已經(jīng)離開屏幕,RecyclerView的滾動是自身的慣性在維持将鸵。
                     * */

                    //不是滾動狀態(tài)且能向下滾動(即內(nèi)容多于一屏)
                    if (newState == RecyclerView.SCROLL_STATE_IDLE && rv.canScrollVertically(-1)){
                        
                        //到底部=不能向上滾動
                        //1能否向上滾動 -1能否向下滾動
                        boolean isBottom = !rv.canScrollVertically(1);
                        
                        //當(dāng)?shù)降撞壳覜]有為RecyclerView加載數(shù)據(jù)(避免重復(fù)加載)
                        if(isBottom&&isLoading == false){
                            //當(dāng)所有數(shù)據(jù)加載完成                         
                            if(nextPage == null){
                                Snackbar.make(rv,"沒有更多了",Snackbar.LENGTH_SHORT)
                                    .setAction("回頂部", new View.OnClickListener(){

                                        @Override
                                        public void onClick(View p1)
                                        {
                                            // TODO: Implement this method
                                            rv.scrollToPosition(0);
                                        }
                                    })
                                    .show();
                                return;
                            }
                            
                            isLoading = true;
                            //為rv填充下一頁的數(shù)據(jù)
                            getHtmlCode(nextPage,"movieList");
                        }
                    }
                }
                
                @Override
                public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
                    if(dy>20){
                        //向上滾動距離大于20勉盅,隱藏回到頂部的按鈕
                        fab.setVisibility(View.GONE);
                    }
                    if(dy<-20){
                        //向下滾動的距離超過20,顯示按鈕
                        fab.setVisibility(View.VISIBLE);
                    }
                }
                
            });
        //滑動監(jiān)聽結(jié)束

二、Toolbar

Toolbar是一個非常靈活的控件顶掉,和design控件配合使用草娜,可以通過很少的代碼實現(xiàn)很多炫酷的效果。而這些效果由我們自己通過自定義控件去實現(xiàn)的話痒筒,是很困難的宰闰。
1.基本用法

布局中導(dǎo)入
<android.support.v7.widget.Toolbar
            android:id="@+id/toolbar"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:background="?android:attr/colorPrimary"/>

Activity中使用
Toolbar toolBar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolBar);

2.給Toolbar添加菜單控件

在res/menu目錄下新建toolbar.xml
<menu xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto">
    
    <item
        android:id="@+id/classes"
        android:orderInCategory="1"
        android:title="分類"
        app:actionViewClass="android.widget.Spinner"
        app:showAsAction="ifRoom"/>
    
    <item
        android:id="@+id/search"
        android:orderInCategory="2"
        android:title="搜索"
        app:actionViewClass="android.support.v7.widget.SearchView"
        app:showAsAction="ifRoom"/>
    
</menu>

android:orderInCategory 優(yōu)先級 值越小越靠前

app:showAsAction 顯示情況
alaways 始終顯示
ifRoom 有空間時顯示
never 從不顯示 收在菜單里

3-1.和design控件配合使用
CoordinatorLayout做根布局
AppBarLayout做父布局
實現(xiàn)向上滑動RecyclerView隱藏Toolbar,向下滑動重現(xiàn)的效果

<android.support.design.widget.CoordinatorLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
>

    <android.support.design.widget.AppBarLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
    >

        <android.support.v7.widget.Toolbar
            android:id="@+id/toolbar"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:background="?android:attr/colorPrimary"
            app:layout_scrollFlags="scroll|enterAlways|snap"
        />

    </android.support.design.widget.AppBarLayout>

    <android.support.v7.widget.RecyclerView
            android:id="@+id/recyclerView"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            app:layout_behavior="@string/appbar_scrolling_view_behavior"
        />
</android.support.design.widget.CoordinatorLayout>

只需要為RecyclerView設(shè)置app:layout_behavior="@string/appbar_scrolling_view_behavior"
使AppBarLayout子控件可以響應(yīng)其行為簿透。
為Toolbar設(shè)置app:layout_scrollFlags="scroll|enterAlways|snap"
指定其響應(yīng)rv后的行為
app:layout_scrollFlags屬性詳情看這里
這兩個屬性是它們作為CoordinatorLayout控件的子控件才生效的移袍。

效果圖

2-2.可折疊式標(biāo)題欄


圖片發(fā)自簡書App

這個效果很酷,但是用design控件實現(xiàn)起來很簡單老充。

<android.support.design.widget.CoordinatorLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:fitsSystemWindows="true" >

    <android.support.design.widget.AppBarLayout
        android:id="@+id/detailsAppBar"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:fitsSystemWindows="true"
    >

        <android.support.design.widget.CollapsingToolbarLayout
            android:id="@+id/detailsCollapsingToolbarLayout"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:fitsSystemWindows="true"
            app:contentScrim="?android:attr/colorPrimary"
            app:layout_scrollFlags="scroll|exitUntilCollapsed"
        >
        
        <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:gravity="center"
            >

            <ImageView
                android:id="@+id/cover"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:background="#FFAEAEAE"
                android:fitsSystemWindows="true"
                app:layout_collapseMode="parallax"
            />
        </LinearLayout>

            <android.support.v7.widget.Toolbar
                android:id="@+id/detailsToolbar"
                android:layout_width="match_parent"
                android:layout_height="?android:attr/actionBarSize"
                app:layout_collapseMode="pin"
            />

        </android.support.design.widget.CollapsingToolbarLayout>

    </android.support.design.widget.AppBarLayout>

    <android.support.v4.widget.NestedScrollView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:fillViewport="true"
        app:layout_behavior="@string/appbar_scrolling_view_behavior" >
        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:orientation="vertical" >
            <android.support.v7.widget.CardView
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_marginBottom="15dp"
                android:layout_marginLeft="15dp"
                android:layout_marginRight="15dp"
                android:layout_marginTop="35dp"
                app:cardCornerRadius="4dp"
            >
                <TextView
                    android:id="@+id/detailsTextView"
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:textSize="10sp"
                    android:layout_margin="10dp" />
            </android.support.v7.widget.CardView>
        </LinearLayout>
    </android.support.v4.widget.NestedScrollView>

    <android.support.design.widget.FloatingActionButton
        android:id="@+id/detailsFloatingActionButton"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_margin="20dp"
        android:src="@drawable/ic_launcher"
        app:layout_anchor="@id/detailsAppBar"
        app:layout_anchorGravity="bottom|end"
    />

</android.support.design.widget.CoordinatorLayout>

依舊是CoordinatorLayout作為根布局葡盗,相比3-1的布局,appBarLayout內(nèi)又包裹了一層CollapsingToolbarLayout,CollapsingToolbarLayout又包裹了Toolbar和其他控件蚂维。
CollapsingToolbarLayout是一個增強(qiáng)型的FrameLayout戳粒,我們將其android:fitsSystemWindows設(shè)置為true,使其可以出現(xiàn)在狀態(tài)欄,但是必須將其所有的父布局都設(shè)置上并且將狀態(tài)欄設(shè)為透明才會生效虫啥。

為該Activity定義一個style 繼承自AppTheme 只是將狀態(tài)欄改成透明
<style name="DetailsTheme" parent="AppTheme">
        <item name="android:statusBarColor">@android:color/transparent</item>
</style>
在AndroidManifest.xml中為該活動設(shè)置樣式
android:theme="@style/DetailsTheme"

對于NestedScrollView蔚约,和3-1布局RecyclerView一樣,設(shè)置了

app:layout_behavior="@string/appbar_scrolling_view_behavior"

但是響應(yīng)NestedScrollView的不再是Toolbar涂籽,而是CollapsingToolbarLayout苹祟,app:layout_scrollFlags的值也變了。因為我們實現(xiàn)了不同的效果,滾動到最后只剩下toolbar树枫,所以用exitUntilCollapsed直焙,使CollapsingToolbarLayout滾動到最小高度。
至于CollapsingToolbarLayout內(nèi)子控件的app:layout_collapseMode屬性砂轻,是指定子控件在隨父控件滾動折疊時的模式:“pin”:固定模式奔誓,在折疊的時候最后固定在頂端;“parallax”:視差模式搔涝,在折疊的時候會有個視差折疊的效果厨喂。

三.TabLayout+ViewPager+FragmentPagerAdapter

1.基本使用


圖片發(fā)自簡書App

這個選擇播放源和劇集的功能便是由TabLayout+ViewPager+FragmentPagerAdapter實現(xiàn),碎片的布局就是一個GridView庄呈。

當(dāng)初學(xué)習(xí)使用這個組合的時候蜕煌,一臉懵逼,這也不懂那也不會诬留。后來用了幾次斜纪,就縷清楚了。

先在Activity的布局里添加TabLayout和ViewPager,然后新建一個碎片或幾個碎片文兑,根據(jù)數(shù)據(jù)類型和功能為碎片寫上布局盒刚,最后自定義一個FragmentPagerAdapter將ViewPager和Fragment二者聯(lián)系起來。

①添加控件

<android.support.design.widget.TabLayout
                android:id="@+id/source_tabLayout"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                app:tabSelectedTextColor="#ff7a61"
                app:tabIndicatorHeight="0dp"
                app:tabBackground="@color/tabBg"
                app:tabMode="fixed"/>
            
            
            <android.support.v4.view.ViewPager
                android:id="@+id/movie_href_list_viewPager"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:layout_margin="10dp" />

②新建碎片及布局

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">
    
    <GridView
        android:id="@+id/detail_fragment_gridView"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:numColumns="5" />
    
</LinearLayout>

public class DetailFragment extends Fragment
{
    List<Map<String,String>> movieHrefList;
    
    View view = null;
    
    Context context;
    
    GridView gridView;
    
    public DetailFragment(List<Map<String,String>> movieHrefList){
        //把要給GridView填充的數(shù)據(jù)傳遞進(jìn)來
        this.movieHrefList = movieHrefList;
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)
    {
        // TODO: Implement this method
        //為碎片設(shè)置布局
        if(view ==null)
            view = inflater.inflate(R.layout.detail_fragment,container,false);
            
        context = view.getContext();
        gridView = (GridView) view.findViewById(R.id.detail_fragment_gridView);

    //為GridView設(shè)置適配器:繪制布局绿贞、填充數(shù)據(jù)              SimpleAdapter adapter = new SimpleAdapter(context, 
                                             movieHrefList,
                                             R.layout.movie_href_item,
                                             new String[] { "title" },
                                             new int[] { R.id.movie_href_itemTextView });
                                             
        gridView.setAdapter(adapter);
        //返回碎片的布局
        return view;
    }
}

③自定義FragmentPagerAdapter將碎片添加到ViewPager中伪冰,并使TabLayout和ViewPager實現(xiàn)聯(lián)動

public class DetailFragmentPagerAdapter extends FragmentPagerAdapter
{
    //要添加的碎片
    List<Fragment> fragList = new ArrayList<Fragment>();
    //TabLayout的標(biāo)題
    List<String> titleList = new ArrayList<String>();
    
    public DetailFragmentPagerAdapter(FragmentManager fm,List<Fragment> fragList,List<String> titleList){
        super(fm);
        this.fragList = fragList;
        this.titleList = titleList;
    }

    @Override
    public int getCount()
    {
        // 返回ViewPager的頁數(shù)
        return fragList.size();
    }

    @Override
    public Fragment getItem(int p1)
    {
        // 返回每一個碎片
        return fragList.get(p1);
    }

    @Override
    public CharSequence getPageTitle(int position)
    {
        // 返回TabLayout的標(biāo)題
        return titleList.get(position).toString();
    }
}

④為ViewPager設(shè)置適配器,并實現(xiàn)與TabLayout的聯(lián)動

DetailFragmentPagerAdapter adapter = new DetailFragmentPagerAdapter(getSupportFragmentManager(),fragList,movieSource);
viewPager.setAdapter(adapter);

//這一句呼應(yīng)適配器中重寫的getPageTitle方法樟蠕,如果沒有TabLayout,那么它們便不用寫
tabLayout.setupWithViewPager(viewPager);

2.遇到的問題
這里遇到的問題不是這個組合所產(chǎn)生的靠柑,而是由于控件嵌套使用造成的寨辩,比如:
①NestedScrollView嵌套ViewPager造成的
ViewPager不顯示(猜想是高度為0,沒有繪制出來)
不知道神馬原因歼冰,高度設(shè)置match或者wrap都不管用靡狞。
搜索一圈,解決方法如下:
設(shè)置NestedScrollView的fillViewPort屬性true|設(shè)置ViewPager為固定高度|動態(tài)計算ViewPager內(nèi)容的高度并賦值
我選了第一個隔嫡,本來想選第三個甸怕,那是最優(yōu)的解決辦法,但是實在是搞不出來腮恩,以后有時間再說梢杭。
②NestedScrollView嵌套GridView,GridView無法滾動秸滴、顯示不全
典型的滑動沖突武契,滑動操作全部被NestedScrollView消費(fèi)掉了,解決辦法:
自定義NestedScrollView,重寫onInterceptTouchEvent方法

public class DetailNestedScrollView extends NestedScrollView
{
    public DetailNestedScrollView(Context context){
        super(context);
    }
    
    public DetailNestedScrollView(Context context, AttributeSet attrs){
        super(context,attrs);
    }

    @Override
    public boolean onInterceptTouchEvent(MotionEvent ev)
    {
        // TODO: Implement this method
        return false;
    }
    
    
}

當(dāng)在其子控件上滑動時咒唆,不再由其消費(fèi)滑動届垫。
顯示不全,那就給子項的布局指定確切的高度全释。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末装处,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子浸船,更是在濱河造成了極大的恐慌妄迁,老刑警劉巖,帶你破解...
    沈念sama閱讀 219,270評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件糟袁,死亡現(xiàn)場離奇詭異判族,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)项戴,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,489評論 3 395
  • 文/潘曉璐 我一進(jìn)店門形帮,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人周叮,你說我怎么就攤上這事辩撑。” “怎么了仿耽?”我有些...
    開封第一講書人閱讀 165,630評論 0 356
  • 文/不壞的土叔 我叫張陵合冀,是天一觀的道長。 經(jīng)常有香客問我项贺,道長君躺,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,906評論 1 295
  • 正文 為了忘掉前任开缎,我火速辦了婚禮棕叫,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘奕删。我一直安慰自己俺泣,他們只是感情好,可當(dāng)我...
    茶點故事閱讀 67,928評論 6 392
  • 文/花漫 我一把揭開白布完残。 她就那樣靜靜地躺著伏钠,像睡著了一般。 火紅的嫁衣襯著肌膚如雪谨设。 梳的紋絲不亂的頭發(fā)上熟掂,一...
    開封第一講書人閱讀 51,718評論 1 305
  • 那天,我揣著相機(jī)與錄音铝宵,去河邊找鬼打掘。 笑死华畏,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的尊蚁。 我是一名探鬼主播亡笑,決...
    沈念sama閱讀 40,442評論 3 420
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼横朋!你這毒婦竟也來了仑乌?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,345評論 0 276
  • 序言:老撾萬榮一對情侶失蹤琴锭,失蹤者是張志新(化名)和其女友劉穎晰甚,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體决帖,經(jīng)...
    沈念sama閱讀 45,802評論 1 317
  • 正文 獨居荒郊野嶺守林人離奇死亡厕九,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,984評論 3 337
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了地回。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片扁远。...
    茶點故事閱讀 40,117評論 1 351
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖刻像,靈堂內(nèi)的尸體忽然破棺而出畅买,到底是詐尸還是另有隱情,我是刑警寧澤细睡,帶...
    沈念sama閱讀 35,810評論 5 346
  • 正文 年R本政府宣布谷羞,位于F島的核電站,受9級特大地震影響溜徙,放射性物質(zhì)發(fā)生泄漏湃缎。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 41,462評論 3 331
  • 文/蒙蒙 一蠢壹、第九天 我趴在偏房一處隱蔽的房頂上張望雁歌。 院中可真熱鬧,春花似錦知残、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,011評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至佳窑,卻和暖如春制恍,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背神凑。 一陣腳步聲響...
    開封第一講書人閱讀 33,139評論 1 272
  • 我被黑心中介騙來泰國打工净神, 沒想到剛下飛機(jī)就差點兒被人妖公主榨干…… 1. 我叫王不留何吝,地道東北人。 一個月前我還...
    沈念sama閱讀 48,377評論 3 373
  • 正文 我出身青樓鹃唯,卻偏偏與公主長得像爱榕,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子坡慌,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,060評論 2 355

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