Glide源碼的初始化----with()

Glide基本用法

基于glide4.7.1

Glide.with(context).load(obj).into(imageView)


  • 先上圖,with方法的流程圖,看完圖對(duì)基本流程有個(gè)了解划纽,再細(xì)看代碼
Glide初始化之with()解析.jpg
  • 這是跟Glide初始化相關(guān)的類(lèi)圖


    Glide初始化相關(guān)的類(lèi).png
  • 先看Glidewith(context)方法的實(shí)現(xiàn), 根據(jù)傳入的參數(shù)有以下方法的重載,發(fā)現(xiàn)都會(huì)調(diào)用getRetriever(context).get(context)方法,拆成兩部分來(lái)看
    • 第一部分,getRetriever(context)負(fù)責(zé)Glide的初始化工作花椭,并返回RequestManagerRetriever對(duì)象。
    • 第二部分房午,requestManagerRetriever.get(context),request請(qǐng)求如何綁定生命周期矿辽。
  public static RequestManager with(@NonNull Context context) {
    return getRetriever(context).get(context);
  }

  public static RequestManager with(@NonNull Activity activity) {
    return getRetriever(activity).get(activity);
  }

  public static RequestManager with(@NonNull FragmentActivity activity) {
    return getRetriever(activity).get(activity);
  }

  public static RequestManager with(@NonNull Fragment fragment) {
    return getRetriever(fragment.getActivity()).get(fragment);
  }

  public static RequestManager with(@NonNull android.app.Fragment fragment) {
    return getRetriever(fragment.getActivity()).get(fragment);
  }

  public static RequestManager with(@NonNull View view) {
    return getRetriever(view.getContext()).get(view);
  }


Glide的初始化過(guò)程

  • getRetriever(context)方法調(diào)用了Glide的get(context)方法返回Glide對(duì)象,然后調(diào)用getRequestManagerRetriever()方法返回RequestManagerRetriever對(duì)象郭厌,因此初始化工作主要在Glide.get(context)中進(jìn)行袋倔。
  private static RequestManagerRetriever getRetriever(@Nullable Context context) {
    ......
    return Glide.get(context).getRequestManagerRetriever();
  }
  • 進(jìn)入Glideget(Context)方法,內(nèi)部實(shí)現(xiàn)了一個(gè)單例模式折柠,調(diào)用checkAndInitializeGlide(context)檢查并初始化Glide對(duì)象宾娜。
  public static Glide get(@NonNull Context context) {
    if (glide == null) {
      synchronized (Glide.class) {
        if (glide == null) {
          checkAndInitializeGlide(context);
        }
      }
    }
    return glide;
  }
  • 先判斷初始化標(biāo)志位是否已經(jīng)被初始化了,如果不進(jìn)行檢查扇售,可能出現(xiàn)多個(gè)類(lèi)調(diào)用get(context)方法前塔,同時(shí)調(diào)用初始化方法嚣艇,這樣就保證了單線程Glide只會(huì)被初始化一次。
  private static void checkAndInitializeGlide(@NonNull Context context) {
    if (isInitializing) {
      throw new IllegalStateException("You cannot call Glide.get() in registerComponents(),"
          + " use the provided Glide instance instead");
    }
    isInitializing = true;
    initializeGlide(context);
    isInitializing = false;
  }
  • 進(jìn)入initializeGlide(context)方法华弓,new了一個(gè)GlideBuilder對(duì)象當(dāng)做實(shí)參
  private static void initializeGlide(@NonNull Context context) {
    initializeGlide(context, new GlideBuilder());
  }
  • 這部分初始化主要進(jìn)行了兩部分工作
    因?yàn)?code>Glide4支持自定義GlideModule食零,第一部分就是先獲取我們創(chuàng)建的module,如果存在第二部分就會(huì)調(diào)用applyOptions方法寂屏,就我們新建的builder傳入,從而可以讓開(kāi)發(fā)者自行配置參數(shù)贰谣,然后再調(diào)用builder.build(applicationContext)方法創(chuàng)建出Glide,開(kāi)發(fā)者在builder中配置的參數(shù)也會(huì)被應(yīng)用迁霎。最后調(diào)用
    annotationGeneratedModule.registerComponents(applicationContext, glide, glide.registry)方法注冊(cè)Glide組件吱抚。
private static void initializeGlide(@NonNull Context context, @NonNull GlideBuilder builder) {
    Context applicationContext = context.getApplicationContext();
    // 獲取自定義GlideModule
    GeneratedAppGlideModule annotationGeneratedModule = getAnnotationGeneratedGlideModules();
    List<com.bumptech.glide.module.GlideModule> manifestModules = Collections.emptyList();
    if (annotationGeneratedModule == null || annotationGeneratedModule.isManifestParsingEnabled()) {
      manifestModules = new ManifestParser(applicationContext).parse();
    }

    if (annotationGeneratedModule != null
        && !annotationGeneratedModule.getExcludedModuleClasses().isEmpty()) {
      Set<Class<?>> excludedModuleClasses =
          annotationGeneratedModule.getExcludedModuleClasses();
      Iterator<com.bumptech.glide.module.GlideModule> iterator = manifestModules.iterator();
      while (iterator.hasNext()) {
        com.bumptech.glide.module.GlideModule current = iterator.next();
        if (!excludedModuleClasses.contains(current.getClass())) {
          continue;
        }

        iterator.remove();
      }
    }

   // 第二部分初始化Glide,為module注冊(cè)組件和應(yīng)用參數(shù)設(shè)置
    RequestManagerRetriever.RequestManagerFactory factory =
        annotationGeneratedModule != null
            ? annotationGeneratedModule.getRequestManagerFactory() : null;
    builder.setRequestManagerFactory(factory);
    for (com.bumptech.glide.module.GlideModule module : manifestModules) {
      module.applyOptions(applicationContext, builder);
    }
    if (annotationGeneratedModule != null) {
      annotationGeneratedModule.applyOptions(applicationContext, builder);
    }

    // 構(gòu)建出glide對(duì)象
    Glide glide = builder.build(applicationContext);
    for (com.bumptech.glide.module.GlideModule module : manifestModules) {
      module.registerComponents(applicationContext, glide, glide.registry);
    }
    if (annotationGeneratedModule != null) {
      annotationGeneratedModule.registerComponents(applicationContext, glide, glide.registry);
    }
    applicationContext.registerComponentCallbacks(glide);
    Glide.glide = glide;
  }
  • 從上面得知glide是通過(guò)調(diào)用GlideBuilder中的build方法構(gòu)建的考廉。通過(guò)下面代碼可以看出秘豹,如果我們沒(méi)有在自定義的module中配置,在build中都會(huì)配置默認(rèn)參數(shù)
    下面這些配置的參數(shù)對(duì)應(yīng)的類(lèi)都可以對(duì)照上面的類(lèi)圖
    • 先創(chuàng)建了兩個(gè)線程池一個(gè)用于根據(jù)數(shù)據(jù)源加載圖片芝此,一個(gè)從緩存中加載圖片
    • 計(jì)算緩存Bitmap緩存池內(nèi)存大小憋肖,并且根據(jù)大小創(chuàng)建Bitamp緩存池
    • 創(chuàng)建數(shù)組對(duì)象池
    • 創(chuàng)建加載引擎
    • 創(chuàng)建需要返回的requestManagerRetriever
    • 調(diào)用構(gòu)造函數(shù),new 一個(gè)Glide對(duì)象婚苹,初始化完畢岸更。
 public Glide build(Context context) {
    if (sourceExecutor == null) {
      sourceExecutor = GlideExecutor.newSourceExecutor();
    }

    if (diskCacheExecutor == null) {
      diskCacheExecutor = GlideExecutor.newDiskCacheExecutor();
    }

    if (memorySizeCalculator == null) {
      memorySizeCalculator = new MemorySizeCalculator.Builder(context).build();
    }

    // 自己深入了解看看
    if (connectivityMonitorFactory == null) {
      connectivityMonitorFactory = new DefaultConnectivityMonitorFactory();
    }

    if (bitmapPool == null) {
      int size = memorySizeCalculator.getBitmapPoolSize();
      if (size > 0) {
        bitmapPool = new LruBitmapPool(size);
      } else {
        bitmapPool = new BitmapPoolAdapter();
      }
    }

    if (arrayPool == null) {
      arrayPool = new LruArrayPool(memorySizeCalculator.getArrayPoolSizeInBytes());
    }

    if (memoryCache == null) {
      memoryCache = new LruResourceCache(memorySizeCalculator.getMemoryCacheSize());
    }

    if (diskCacheFactory == null) {
      diskCacheFactory = new InternalCacheDiskCacheFactory(context);
    }

    if (engine == null) {
      engine = new Engine(memoryCache, diskCacheFactory, diskCacheExecutor, sourceExecutor,
          GlideExecutor.newUnlimitedSourceExecutor());
    }

    RequestManagerRetriever requestManagerRetriever = new RequestManagerRetriever(
        requestManagerFactory);

    return new Glide(
        context,
        engine,
        memoryCache,
        bitmapPool,
        arrayPool,
        requestManagerRetriever,
        connectivityMonitorFactory,
        logLevel,
        defaultRequestOptions.lock(),
        defaultTransitionOptions);
  }
  • 綜上,Glide第一部分初始化已經(jīng)完成。

Glide生命周期的綁定

  • RequestManagerRetrieverget()有多個(gè)方法重載
    • 共同點(diǎn):判斷是不是在后臺(tái)線程膊升,如果在后臺(tái)線程直接走Application生命周期
    • 如果傳入的是context,會(huì)根據(jù)FragmentActivity怎炊、Activity的實(shí)例還是ContextWrapper來(lái)調(diào)用對(duì)應(yīng)的方法。
    • 如果傳入的是FragmentActivity或者Fragment(來(lái)自v4包)廓译,調(diào)用supportFragmentGet
    • 如果傳入的是Activity(非v4包)评肆,調(diào)用fragmentGet
    • 如果傳入View通過(guò)調(diào)用view.getContext()對(duì)象進(jìn)行判斷,決定是調(diào)用fragmentGet還是supportFragmentGet
    • 通過(guò)上面分析關(guān)鍵方法就是supportFragmentGetfragmentGet非区,兩個(gè)方法實(shí)現(xiàn)邏輯基本一樣瓜挽,我們挑其中最常用的supportFragmentGet來(lái)看
public RequestManager get(Context context) {
    if (context == null) {
      throw new IllegalArgumentException("You cannot start a load on a null Context");
    } else if (Util.isOnMainThread() && !(context instanceof Application)) {
      if (context instanceof FragmentActivity) {
        return get((FragmentActivity) context);
      } else if (context instanceof Activity) {
        return get((Activity) context);
      } else if (context instanceof ContextWrapper) {
        return get(((ContextWrapper) context).getBaseContext());
      }
    }

    return getApplicationManager(context);
  }

  public RequestManager get(FragmentActivity activity) {
    if (Util.isOnBackgroundThread()) {
      return get(activity.getApplicationContext());
    } else {
      assertNotDestroyed(activity);
      FragmentManager fm = activity.getSupportFragmentManager();
      return supportFragmentGet(activity, fm, null /*parentHint*/);
    }
  }

  public RequestManager get(Fragment fragment) {
    if (Util.isOnBackgroundThread()) {
      return get(fragment.getActivity().getApplicationContext());
    } else {
      FragmentManager fm = fragment.getChildFragmentManager();
      return supportFragmentGet(fragment.getActivity(), fm, fragment);
    }
  }

  public RequestManager get(Activity activity) {
    if (Util.isOnBackgroundThread()) {
      return get(activity.getApplicationContext());
    } else {
      assertNotDestroyed(activity);
      android.app.FragmentManager fm = activity.getFragmentManager();
      return fragmentGet(activity, fm, null /*parentHint*/);
    }
  }

  public RequestManager get(View view) {
    if (Util.isOnBackgroundThread()) {
      return get(view.getContext().getApplicationContext());
    }

    Activity activity = findActivity(view.getContext());

    if (activity == null) {
      return get(view.getContext().getApplicationContext());
    }

    if (activity instanceof FragmentActivity) {
      Fragment fragment = findSupportFragment(view, (FragmentActivity) activity);
      if (fragment == null) {
        return get(activity);
      }
      return get(fragment);
    }

    android.app.Fragment fragment = findFragment(view, activity);
    if (fragment == null) {
      return get(activity);
    }
    return get(fragment);
  }
  • 干了兩件事情
  • 調(diào)用getSupportRequestManagerFragment獲取Fragment
  • 調(diào)用factory.build(glide, current.getGlideLifecycle(), current.getRequestManagerTreeNode())創(chuàng)建 了RequestManager對(duì)象
  private RequestManager supportFragmentGet(Context context, FragmentManager fm,
      Fragment parentHint) {
    SupportRequestManagerFragment current = getSupportRequestManagerFragment(fm, parentHint);
    RequestManager requestManager = current.getRequestManager();
    if (requestManager == null) {
      // TODO(b/27524013): Factor out this Glide.get() call.
      Glide glide = Glide.get(context);
      requestManager =
          factory.build(glide, current.getGlideLifecycle(), current.getRequestManagerTreeNode());
      current.setRequestManager(requestManager);
    }
    return requestManager;
  }
  • 通過(guò)Tag來(lái)查找Fragment,如果找不到征绸,就從等待隊(duì)列中找久橙,如果還是沒(méi)有就創(chuàng)建一個(gè),加入等待對(duì)列中,將FragmentActivity綁定管怠,并使用handler發(fā)送消息從隊(duì)列中移除Fragment淆衷。
  SupportRequestManagerFragment getSupportRequestManagerFragment(
      final FragmentManager fm, Fragment parentHint) {
    SupportRequestManagerFragment current =
        (SupportRequestManagerFragment) fm.findFragmentByTag(FRAGMENT_TAG);
    if (current == null) {
      current = pendingSupportRequestManagerFragments.get(fm);
      if (current == null) {
        current = new SupportRequestManagerFragment();
        current.setParentFragmentHint(parentHint);
        pendingSupportRequestManagerFragments.put(fm, current);
        fm.beginTransaction().add(current, FRAGMENT_TAG).commitAllowingStateLoss();
        handler.obtainMessage(ID_REMOVE_SUPPORT_FRAGMENT_MANAGER, fm).sendToTarget();
      }
    }
    return current;
  }
  • SupportRequestManagerFragment的構(gòu)造函數(shù)創(chuàng)建了一個(gè)ActivityFragmentLifecycle對(duì)象用來(lái)管理生命周期,在onStart方法中調(diào)用ActivityFragmentLifecycle的onStart方法渤弛,同理其他生命周期方法也是祝拯。
public class SupportRequestManagerFragment extends Fragment {
  public SupportRequestManagerFragment() {
    this(new ActivityFragmentLifecycle());
  }

  @VisibleForTesting
  @SuppressLint("ValidFragment")
  public SupportRequestManagerFragment(@NonNull ActivityFragmentLifecycle lifecycle) {
    this.lifecycle = lifecycle;
  }

  @Override
  public void onStart() {
    super.onStart();
    lifecycle.onStart();
  }

  @Override
  public void onStop() {
    super.onStop();
    lifecycle.onStop();
  }

  @Override
  public void onDestroy() {
    super.onDestroy();
    lifecycle.onDestroy();
    unregisterFragmentWithRoot();
  }
    
}
  • 下面來(lái)看RequestManger是如何構(gòu)造的并綁定了Fragment的生命周期
    • factory.build(glide, current.getGlideLifecycle(), current.getRequestManagerTreeNode()),current就是我們上面的SupportRequestManagerFragment對(duì)象她肯,將和他綁定的生命周期對(duì)象Lifecycle傳給了RequestManger構(gòu)造函數(shù)
 public RequestManager build(Glide glide, Lifecycle lifecycle,
        RequestManagerTreeNode requestManagerTreeNode) {
      return new RequestManager(glide, lifecycle, requestManagerTreeNode);
    }
  • RequestManager實(shí)現(xiàn)了LifecycleListener接口佳头,并且調(diào)用lifecycle.addListener(this)添加監(jiān)聽(tīng)器鹰贵。接口生命周期函數(shù)onStart()啟動(dòng)請(qǐng)求,onStop暫停請(qǐng)求
public class RequestManager implements LifecycleListener {
  RequestManager(
      Glide glide,
      Lifecycle lifecycle,
      RequestManagerTreeNode treeNode,
      RequestTracker requestTracker,
      ConnectivityMonitorFactory factory) {
    this.glide = glide;
    this.lifecycle = lifecycle;
    this.treeNode = treeNode;
    this.requestTracker = requestTracker;

    final Context context = glide.getGlideContext().getBaseContext();

    connectivityMonitor =
        factory.build(context, new RequestManagerConnectivityListener(requestTracker));

    if (Util.isOnBackgroundThread()) {
      mainHandler.post(addSelfToLifecycle);
    } else {
      lifecycle.addListener(this);
    }
    lifecycle.addListener(connectivityMonitor);

    setRequestOptions(glide.getGlideContext().getDefaultRequestOptions());

    glide.registerRequestManager(this);
  }

 @Override
  public void onStart() {
    resumeRequests();
    targetTracker.onStart();
  }

  @Override
  public void onStop() {
    pauseRequests();
    targetTracker.onStop();
  }

 
}
  • ActivtyFragmentLifecycle中如果添加了監(jiān)聽(tīng)器康嘉,在onStart調(diào)用監(jiān)聽(tīng)器的onStart方法砾莱,也就是調(diào)用RequsetManager中的onStart,同理onPause也是凄鼻。
class ActivityFragmentLifecycle implements Lifecycle {
  @Override
  public void addListener(LifecycleListener listener) {
    lifecycleListeners.add(listener);

    if (isDestroyed) {
      listener.onDestroy();
    } else if (isStarted) {
      listener.onStart();
    } else {
      listener.onStop();
    }
  }

  @Override
  public void removeListener(LifecycleListener listener) {
    lifecycleListeners.remove(listener);
  }

  void onStart() {
    isStarted = true;
    for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
      lifecycleListener.onStart();
    }
  }

  void onStop() {
    isStarted = false;
    for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
      lifecycleListener.onStop();
    }
  }

  void onDestroy() {
    isDestroyed = true;
    for (LifecycleListener lifecycleListener : Util.getSnapshot(lifecycleListeners)) {
      lifecycleListener.onDestroy();
    }
  }
}
  • 經(jīng)過(guò)上面的分析發(fā)現(xiàn)整個(gè)過(guò)程就理順了,先創(chuàng)建一個(gè)Fragment對(duì)象并在構(gòu)造函數(shù)中創(chuàng)建Lifecycle對(duì)象
    聚假,在創(chuàng)建RequestManager的時(shí)候會(huì)把Lifecycle對(duì)象傳遞進(jìn)去块蚌。
  • RequestManger則在構(gòu)造函數(shù)處為接收的Lifecycle添加監(jiān)聽(tīng)器,而RequestManager自身實(shí)現(xiàn)了LifecycleListener膘格,在實(shí)現(xiàn)的接口方法onStoponPause分別啟動(dòng)和暫停請(qǐng)求峭范。
  • Lifecycle對(duì)象在添加監(jiān)聽(tīng)器后,會(huì)在生命周期方法onStartonPauser分別調(diào)用監(jiān)聽(tīng)器對(duì)應(yīng)的方法瘪贱。
  • 因此當(dāng)Fragment會(huì)在生命周期方法中調(diào)用Lifecycle對(duì)應(yīng)的生命周期方法纱控,最終也就是在調(diào)用RequestManger中的生命周期方法,因此實(shí)現(xiàn)了請(qǐng)求和生命周期的綁定菜秦,從而可以根據(jù)生命周期來(lái)啟動(dòng)和暫停請(qǐng)求甜害。


  • 總結(jié)一下,with()方法主要初始化Glide和創(chuàng)建了RequestManger綁定SupportRequestManagerFragment的生命周期函數(shù)球昨,最后返回RequestManager尔店。
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市主慰,隨后出現(xiàn)的幾起案子嚣州,更是在濱河造成了極大的恐慌,老刑警劉巖共螺,帶你破解...
    沈念sama閱讀 219,270評(píng)論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件该肴,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡藐不,警方通過(guò)查閱死者的電腦和手機(jī)匀哄,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,489評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門(mén),熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)佳吞,“玉大人拱雏,你說(shuō)我怎么就攤上這事〉装猓” “怎么了铸抑?”我有些...
    開(kāi)封第一講書(shū)人閱讀 165,630評(píng)論 0 356
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)衷模。 經(jīng)常有香客問(wèn)我鹊汛,道長(zhǎng)蒲赂,這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,906評(píng)論 1 295
  • 正文 為了忘掉前任刁憋,我火速辦了婚禮滥嘴,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘至耻。我一直安慰自己若皱,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,928評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布尘颓。 她就那樣靜靜地躺著走触,像睡著了一般。 火紅的嫁衣襯著肌膚如雪疤苹。 梳的紋絲不亂的頭發(fā)上互广,一...
    開(kāi)封第一講書(shū)人閱讀 51,718評(píng)論 1 305
  • 那天,我揣著相機(jī)與錄音卧土,去河邊找鬼惫皱。 笑死,一個(gè)胖子當(dāng)著我的面吹牛尤莺,可吹牛的內(nèi)容都是我干的旅敷。 我是一名探鬼主播,決...
    沈念sama閱讀 40,442評(píng)論 3 420
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼缝裁,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼扫皱!你這毒婦竟也來(lái)了?” 一聲冷哼從身側(cè)響起捷绑,我...
    開(kāi)封第一講書(shū)人閱讀 39,345評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤韩脑,失蹤者是張志新(化名)和其女友劉穎,沒(méi)想到半個(gè)月后粹污,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體段多,經(jīng)...
    沈念sama閱讀 45,802評(píng)論 1 317
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,984評(píng)論 3 337
  • 正文 我和宋清朗相戀三年壮吩,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了进苍。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 40,117評(píng)論 1 351
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡鸭叙,死狀恐怖觉啊,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情沈贝,我是刑警寧澤杠人,帶...
    沈念sama閱讀 35,810評(píng)論 5 346
  • 正文 年R本政府宣布,位于F島的核電站,受9級(jí)特大地震影響嗡善,放射性物質(zhì)發(fā)生泄漏辑莫。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,462評(píng)論 3 331
  • 文/蒙蒙 一罩引、第九天 我趴在偏房一處隱蔽的房頂上張望各吨。 院中可真熱鬧,春花似錦袁铐、人聲如沸揭蜒。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 32,011評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)忌锯。三九已至,卻和暖如春领炫,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背张咳。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 33,139評(píng)論 1 272
  • 我被黑心中介騙來(lái)泰國(guó)打工帝洪, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人脚猾。 一個(gè)月前我還...
    沈念sama閱讀 48,377評(píng)論 3 373
  • 正文 我出身青樓葱峡,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親龙助。 傳聞我的和親對(duì)象是個(gè)殘疾皇子砰奕,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,060評(píng)論 2 355

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