Android啟動(dòng)流程源碼解析(二)

Android啟動(dòng)流程源碼解析(二)

在之前的Android啟動(dòng)流程源碼解析(一)源碼分析中,我們最后遺留下來(lái)一個(gè)問(wèn)題。那就是我們的Activity的啟動(dòng)是啥時(shí)候處理的啊?上萬(wàn)行的分析,也沒(méi)看到我們想要的onCreate啥的。其實(shí)就是resumeFocusedStacksTopActivities方法,所以我們這篇文章就從這個(gè)方法開(kāi)始。

resumeFocusedStacksTopActivities

   boolean resumeFocusedStacksTopActivities() {
        return resumeFocusedStacksTopActivities(null, null, null);
    }

    boolean resumeFocusedStacksTopActivities(ActivityStack targetStack, ActivityRecord target, ActivityOptions targetOptions) {
        boolean result = false;
        if (targetStack != null && (targetStack.isTopStackOnDisplay()|| getTopDisplayFocusedStack() == targetStack)) {
            //******重點(diǎn)方法******如果當(dāng)前的activitystack正好處于屏幕的頂部,那么直接調(diào)用將target設(shè)置到頂部顯示
            result = targetStack.resumeTopActivityUncheckedLocked(target, targetOptions);
        }

        for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) {
            //標(biāo)記是否已經(jīng)顯示在屏幕上
            boolean resumedOnDisplay = false;
            final ActivityDisplay display = mActivityDisplays.get(displayNdx);
            for (int stackNdx = display.getChildCount() - 1; stackNdx >= 0; --stackNdx) {
                final ActivityStack stack = display.getChildAt(stackNdx);
                //獲取到當(dāng)前ActivityStack頂部正在運(yùn)行的Activity
                final ActivityRecord topRunningActivity = stack.topRunningActivityLocked();
                if (!stack.isFocusableAndVisible() || topRunningActivity == null) {
                    continue;
                }
                if (stack == targetStack) {
                    //上面已經(jīng)做過(guò)resume處理了,所以這里我們就不再做處理了
                    resumedOnDisplay |= result;
                    continue;
                }
                if (display.isTopStack(stack) && topRunningActivity.isState(RESUMED)) {
                    stack.executeAppTransition(targetOptions);
                } else {
                    resumedOnDisplay |= topRunningActivity.makeActiveIfNeeded(target);
                }
            }
            //如果仍然沒(méi)有顯示在屏幕上,那么就獲取到屏幕當(dāng)前持有焦點(diǎn)的ActivityStack,然后將activity顯示在上面
            if (!resumedOnDisplay) {
                final ActivityStack focusedStack = display.getFocusedStack();
                if (focusedStack != null) {
                    focusedStack.resumeTopActivityUncheckedLocked(target, targetOptions);
                }
            }
        }
        return result;
    }

這里我們只需要關(guān)注一個(gè)方法 resumeTopActivityUncheckedLocked ,這個(gè)方法也特別長(zhǎng),我們就拆分開(kāi),只關(guān)注重點(diǎn)方法即可

    boolean resumeTopActivityUncheckedLocked(ActivityRecord prev, ActivityOptions options) {
        if (mInResumeTopActivity) {
            // Don't even start recursing.
            return false;
        }
        boolean result = false;
        try {
            // Protect against recursion.
            mInResumeTopActivity = true;
            //***重點(diǎn)關(guān)注******
            result = resumeTopActivityInnerLocked(prev, options);
            final ActivityRecord next = topRunningActivityLocked(true /* focusableOnly */);
            if (next == null || !next.canTurnScreenOn()) {
                checkReadyForSleep();
            }
        } finally {
            mInResumeTopActivity = false;
        }

        return result;
    }

這里我們也只關(guān)注resumeTopActivityInnerLocked方法

    private boolean resumeTopActivityInnerLocked(ActivityRecord prev, ActivityOptions options) {
       ...  
       if (mResumedActivity != null) {
            //****重點(diǎn)方法 ****** 調(diào)用acitivity的pause方法
            pausing |= startPausingLocked(userLeaving, false, next, false);
        }
        ...
        //進(jìn)行activity的創(chuàng)建處理
        mStackSupervisor.startSpecificActivityLocked(next, true, false);
        ...
    }

代碼也很長(zhǎng),我們只提取了兩個(gè)比較重要的函數(shù),一個(gè)是調(diào)用onPause生命周期函數(shù),另一個(gè)是調(diào)用onCreate生命周期函數(shù)的。

onPause的暫停過(guò)程

我們首先來(lái)看一下是如何一步步通過(guò)調(diào)度來(lái)執(zhí)行onPause的生命周期調(diào)度的

//ActivityStack.java
    final boolean startPausingLocked(boolean userLeaving, boolean uiSleeping, ActivityRecord resuming, boolean pauseImmediately) {
        ...
        //當(dāng)前正在顯示的Activity
        ActivityRecord prev = mResumedActivity;
        //當(dāng)前正在顯示的Activity需要執(zhí)行暫停操作了。
        //將其賦值給mPausingActivity成員變量。
        mPausingActivity = prev;
        mLastPausedActivity = prev;
        //Activity綁定了對(duì)應(yīng)的APP?難道有不綁定的情況么?
        if (prev.attachedToProcess()) {
               ...  
                //******重點(diǎn)方法****
 mService.getLifecycleManager().scheduleTransaction(prev.app.getThread(),prev.appToken, PauseActivityItem.obtain(prev.finishing, userLeaving,prev.configChangeFlags, pauseImmediately));
            ...

重點(diǎn)方法已經(jīng)標(biāo)注出來(lái)了。我們先看看它的參數(shù)的創(chuàng)建過(guò)程。

PauseActivityItem.obtain
//PauseActivityItem.java
    //從池中取出一個(gè)PauseActivityItem類
    public static PauseActivityItem obtain(boolean finished, boolean userLeaving, int configChanges, boolean dontReport) {
        PauseActivityItem instance = ObjectPool.obtain(PauseActivityItem.class);
        if (instance == null) {
            instance = new PauseActivityItem();
        }
        instance.mFinished = finished;
        instance.mUserLeaving = userLeaving;
        instance.mConfigChanges = configChanges;
        instance.mDontReport = dontReport;
        return instance;
    }
//ObjectPool.java
    public static <T extends ObjectPoolItem> T obtain(Class<T> itemClass) {
        synchronized (sPoolSync) {
            @SuppressWarnings("unchecked")
            final ArrayList<T> itemPool = (ArrayList<T>) sPoolMap.get(itemClass);
            if (itemPool != null && !itemPool.isEmpty()) {
                return itemPool.remove(itemPool.size() - 1);
            }
            return null;
        }
    }

可以看到,對(duì)于PauseActivityItem的獲取,是通過(guò)享元模式 來(lái)進(jìn)行處理的。

回到主干。

這的mService是ActivityTaskManagerServicegetLifecycleManager方法返回的是ClientLifecycleManager對(duì)象。

    private final ClientLifecycleManager mLifecycleManager;
    mLifecycleManager = new ClientLifecycleManager();
    ClientLifecycleManager getLifecycleManager() {
        return mLifecycleManager;
    }
scheduleTransaction
//ClientLifecycleManager.java
    //調(diào)用一次生命周期的調(diào)度請(qǐng)求
    void scheduleTransaction(@NonNull IApplicationThread client, @NonNull IBinder activityToken,@NonNull ActivityLifecycleItem stateRequest) throws RemoteException {
        final ClientTransaction clientTransaction = transactionWithState(client, activityToken,stateRequest);
        scheduleTransaction(clientTransaction);
    }
    //實(shí)際的調(diào)度方法
    void scheduleTransaction(ClientTransaction transaction) throws RemoteException {
        final IApplicationThread client = transaction.getClient();
        transaction.schedule();
        if (!(client instanceof Binder)) {
            //回收
            transaction.recycle();
        }
    }
    //創(chuàng)建一個(gè)持有狀態(tài)的事務(wù)類
    private static ClientTransaction transactionWithState(@NonNull IApplicationThread client,
            @NonNull IBinder activityToken, @NonNull ActivityLifecycleItem stateRequest) {
        final ClientTransaction clientTransaction = ClientTransaction.obtain(client, activityToken);
        clientTransaction.setLifecycleStateRequest(stateRequest);
        return clientTransaction;
    }

這里最終會(huì)調(diào)用ClientTransaction對(duì)象的schedule方法。

//ClientTransaction.java
    public void schedule() throws RemoteException {
        mClient.scheduleTransaction(this);
    }

這里的mClient是一個(gè)IApplicationThread,其Server端是ActivityThread#ApplicationThread。所以最終調(diào)用的是ApplicationThreadscheduleTransaction方法

//ActivityThread.java
    public void scheduleTransaction(ClientTransaction transaction) throws RemoteException {
            //會(huì)調(diào)用ActivityThread.scheduleTransaction方法->該方法位于ActivityThread的父類中
            ActivityThread.this.scheduleTransaction(transaction);
        }

//ClientTransactionHandler.java
    void scheduleTransaction(ClientTransaction transaction) {
        //執(zhí)行預(yù)處理
        transaction.preExecute(this);
        //通過(guò)Handler機(jī)制發(fā)送事務(wù)請(qǐng)求
        sendMessage(ActivityThread.H.EXECUTE_TRANSACTION, transaction);
    }

Handler消息機(jī)制就不貼出來(lái)了,直接看其是怎么處理的。

//ActivityThread.java
    private final TransactionExecutor mTransactionExecutor = new TransactionExecutor(this);

            case EXECUTE_TRANSACTION://執(zhí)行生命周期的調(diào)度工作
                    final ClientTransaction transaction = (ClientTransaction) msg.obj;
                    mTransactionExecutor.execute(transaction);

當(dāng)接收到Handler以后,會(huì)調(diào)用TransactionExecutorexecute()方法。

//TransactionExecutor.java
    public void execute(ClientTransaction transaction) {
        final IBinder token = transaction.getActivityToken();
        ...
        //循環(huán)遍歷回調(diào)請(qǐng)求的所有狀態(tài),并在適當(dāng)?shù)臅r(shí)間執(zhí)行它們
        executeCallbacks(transaction);
        //執(zhí)行生命周期的改變
        executeLifecycleState(transaction);
    }

ClientTransaction存在兩種事務(wù),

  • 一種是通過(guò)setLifecycleStateRequest設(shè)置一個(gè)對(duì)象的事務(wù)類型,用于表示事務(wù)執(zhí)行以后,客戶端應(yīng)該處于的生命周期狀態(tài)
  • 一種是addCallback,增加對(duì)客戶端的事務(wù)類型回調(diào),對(duì)客戶端一系列的回調(diào)。

這兩個(gè)不同的類型,在這里就會(huì)存在不同的處理方法。對(duì)于第一種會(huì)在executeCallbacks中進(jìn)行處理,第二種則會(huì)在executeLifecycleState中進(jìn)行處理。

我們這兒的暫停,是通過(guò)第二種來(lái)進(jìn)行設(shè)置的,所以我們直接看executeLifecycleState這個(gè)方法。

//TransactionExecutor.java
    //如果事務(wù)請(qǐng)求,則轉(zhuǎn)換到最終狀態(tài)
    private void executeLifecycleState(ClientTransaction transaction) {
        // ActivityStackSupervisor.java中進(jìn)行了這個(gè)設(shè)置
        // final ActivityLifecycleItem lifecycleItem;
        //                if (andResume) {
        //                    lifecycleItem = ResumeActivityItem.obtain(dc.isNextTransitionForward());
        //                } else {
        //                    lifecycleItem = PauseActivityItem.obtain();
        //                }
        //                clientTransaction.setLifecycleStateRequest(lifecycleItem);
        //所以這里的lifecycleItem可能是ResumeActivityItem或者PauseActivityItem或者其他的生命周期相關(guān)類
        final ActivityLifecycleItem lifecycleItem = transaction.getLifecycleStateRequest();
        if (lifecycleItem == null) {
            //如果不是通過(guò)setLifecycleStateRequest設(shè)置的,那么該方法不需要處理,直接返回即可
            return;
        }
        //使用適當(dāng)?shù)膮?shù)執(zhí)行最后的轉(zhuǎn)換
        lifecycleItem.execute(mTransactionHandler, token, mPendingActions);
        lifecycleItem.postExecute(mTransactionHandler, token, mPendingActions);
    }

我們這里的lifecycleItem是我們剛才創(chuàng)建的PauseActivityItem,這里會(huì)執(zhí)行其execute方法。

//PauseActivityItem.java
    @Override
    public void execute(ClientTransactionHandler client, IBinder token,  PendingTransactionActions pendingActions) {
        Trace.traceBegin(TRACE_TAG_ACTIVITY_MANAGER, "activityPause");
        //這里的client,是Activity獨(dú)享
        client.handlePauseActivity(token, mFinished, mUserLeaving, mConfigChanges, pendingActions,"PAUSE_ACTIVITY_ITEM");
        Trace.traceEnd(TRACE_TAG_ACTIVITY_MANAGER);
    }

這里的client對(duì)象我們需要回退去跟蹤一下

//ActivityThread.java
private final TransactionExecutor mTransactionExecutor = new TransactionExecutor(this);
//TransactionExecutor.java
//在ActivityThread類中中調(diào)用了mTransactionExecutor = new TransactionExecutor(this)這個(gè)方法,其中的mTransactionHandler是ActivityThread本身
    public TransactionExecutor(ClientTransactionHandler clientTransactionHandler) {
        mTransactionHandler = clientTransactionHandler;
    }

所以說(shuō),最終調(diào)用的是ActivityThreadhandlePauseActivity方法

//ActivityThread.java
    public void handlePauseActivity(IBinder token, boolean finished, boolean userLeaving,int configChanges, PendingTransactionActions pendingActions, String reason) {
        //獲取對(duì)應(yīng)的ActivityClientRecord對(duì)象
        ActivityClientRecord r = mActivities.get(token);
        if (r != null) {
            ...
            //***重點(diǎn)方法***,執(zhí)行pause方法
            performPauseActivity(r, finished, reason, pendingActions);
            ...
        }
    }

    private Bundle performPauseActivity(ActivityClientRecord r, boolean finished, String reason,
                                        PendingTransactionActions pendingActions) {
        ...
        //****重點(diǎn)方法****
        performPauseActivityIfNeeded(r, reason);
        ...
        return shouldSaveState ? r.state : null;
    }
    private void performPauseActivityIfNeeded(ActivityClientRecord r, String reason) {
            ...
            r.activity.mCalled = false;
            //重點(diǎn)方法,通過(guò)Instrumentation調(diào)用onPause生命周期
            mInstrumentation.callActivityOnPause(r.activity);
            ...
    }

最終會(huì)通過(guò)Instrumentation調(diào)用callActivityOnPause方法。

   //Instrumentation.java
    public void callActivityOnPause(Activity activity) {
        activity.performPause();
    }
    //Activity.java
    final void performPause() {
        dispatchActivityPrePaused();
        mDoReportFullyDrawn = false;
        //管理的Fragment的處理
        mFragments.dispatchPause();
        mCalled = false;
        //調(diào)用了onPause生命周期方法
        onPause();
        writeEventLog(LOG_AM_ON_PAUSE_CALLED, "performPause");
        //設(shè)置mResumed為false,表示當(dāng)前activity沒(méi)有展示
        mResumed = false;
        //調(diào)用一些回調(diào)函數(shù)
        dispatchActivityPostPaused();
    }

到這里為止,原來(lái)在我們面前展示的那個(gè)Activity調(diào)用了其onPause方法。

Activity的創(chuàng)建過(guò)程

回到主線的resumeTopActivityInnerLocked方法中,當(dāng)執(zhí)行完startPausingLocked方法后,會(huì)調(diào)用mStackSupervisor.startSpecificActivityLocked方法

    //ActivityStackSupervisor.java
    void startSpecificActivityLocked(ActivityRecord r, boolean andResume, boolean checkConfig) {
        //根據(jù)uid和pid,獲取activity對(duì)應(yīng)的進(jìn)行和線程信息
        final WindowProcessController wpc =mService.getProcessController(r.processName, r.info.applicationInfo.uid);
        boolean knownToBeDead = false;
        if (wpc != null && wpc.hasThread()) {
            //如果進(jìn)程和線程都存在,執(zhí)行后面的代碼
            try {
                realStartActivityLocked(r, wpc, andResume, checkConfig);
                return;
            } catch (RemoteException e) {
                Slog.w(TAG, "Exception when starting activity "
                        + r.intent.getComponent().flattenToShortString(), e);
            }

            knownToBeDead = true;
        }
            //通過(guò)message進(jìn)行進(jìn)程的啟動(dòng)。
            final Message msg = PooledLambda.obtainMessage(
                    ActivityManagerInternal::startProcess, mService.mAmInternal, r.processName,
                    r.info.applicationInfo, knownToBeDead, "activity", r.intent.getComponent());
            mService.mH.sendMessage(msg);
        } finally {
            Trace.traceEnd(TRACE_TAG_ACTIVITY_MANAGER);
        }
    }

如果要啟動(dòng)的activity所在的進(jìn)程和線程都存在,那么直接調(diào)用realStartActivityLocked方法進(jìn)行啟動(dòng),否則的話,就會(huì)調(diào)用Handler機(jī)制進(jìn)行進(jìn)程的創(chuàng)建。

realStartActivityLocked

    //真正執(zhí)行Activity啟動(dòng)的方法
    boolean realStartActivityLocked(ActivityRecord r, WindowProcessController proc, boolean andResume, boolean checkConfig) throws RemoteException {
        //如果還有activity沒(méi)有暫停,這里會(huì)直接返回false
        if (!mRootActivityContainer.allPausedActivitiesComplete()) {
            return false;
        }

        final TaskRecord task = r.getTaskRecord();
        final ActivityStack stack = task.getStack();
        //設(shè)置標(biāo)志位,不再接收其他activity的resume的操作
        beginDeferResume();
        try {
           ...
                //創(chuàng)建了一個(gè)Activity事務(wù)
                final ClientTransaction clientTransaction = ClientTransaction.obtain(proc.getThread(), r.appToken);
                final DisplayContent dc = r.getDisplay().mDisplayContent;
                //增加一個(gè)要執(zhí)行的事務(wù)LaunchActivityItem。
                clientTransaction.addCallback(LaunchActivityItem.obtain(new Intent(r.intent),
                        System.identityHashCode(r), r.info,
                        mergedConfiguration.getGlobalConfiguration(),
                        mergedConfiguration.getOverrideConfiguration(), r.compat,
                        r.launchedFromPackage, task.voiceInteractor, proc.getReportedProcState(),
                        r.icicle, r.persistentState, results, newIntents,
                        dc.isNextTransitionForward(), proc.createProfilerInfoIfNeeded(),
                                r.assistToken));
                final ActivityLifecycleItem lifecycleItem;
                //設(shè)置其生命周期LifecycleStateRequest
                if (andResume) {
                    lifecycleItem = ResumeActivityItem.obtain(dc.isNextTransitionForward());
                } else {
                    lifecycleItem = PauseActivityItem.obtain();
                }
                clientTransaction.setLifecycleStateRequest(lifecycleItem);
                //執(zhí)行事務(wù)的調(diào)度
                mService.getLifecycleManager().scheduleTransaction(clientTransaction);
        ...
        proc.onStartActivity(mService.mTopProcessState, r.info);
        return true;
    }

在這個(gè)方法里面,創(chuàng)建了一個(gè)事務(wù),在事務(wù)中增加了一個(gè)callback回調(diào),然后通過(guò)setLifecycleStateRequest設(shè)置了一個(gè)生命周期,最后通過(guò)scheduleTransaction執(zhí)行了調(diào)度。在前面的onPause中,我們梳理了整個(gè)調(diào)度的流程,最后會(huì)調(diào)用到LaunchActivityItemexecute,然后會(huì)調(diào)用生命周期所對(duì)應(yīng)的ResumeActivityItemexecute

我們挨個(gè)看,先看LaunchActivityItem的調(diào)用

//LaunchActivityItem.java
    //一般會(huì)在TransactionExecutor中調(diào)用這個(gè)方法
    //ClientTransactionHandler實(shí)際是ActivityThread對(duì)象,所以這里會(huì)執(zhí)行activitythread類中的handleLaunchActivity方法
    @Override
    public void execute(ClientTransactionHandler client, IBinder token,
                        PendingTransactionActions pendingActions) {
        Trace.traceBegin(TRACE_TAG_ACTIVITY_MANAGER, "activityStart");
        ActivityClientRecord r = new ActivityClientRecord(token, mIntent, mIdent, mInfo,
                mOverrideConfig, mCompatInfo, mReferrer, mVoiceInteractor, mState, mPersistentState,
                mPendingResults, mPendingNewIntents, mIsForward,
                mProfilerInfo, client, mAssistToken);
        //調(diào)用activitythread類中的handleLaunchActivity方法
        client.handleLaunchActivity(r, pendingActions, null /* customIntent */);
        Trace.traceEnd(TRACE_TAG_ACTIVITY_MANAGER);
    }

其本質(zhì)調(diào)用的是ActivityThread中的handleLaunchActivity方法。

這部分的功能,我們?cè)?a target="_blank">Android布局窗口繪制分析中進(jìn)行過(guò)解析。這里不再往下進(jìn)行解析了。

我們直接跳過(guò)這部分,來(lái)看看如果啟動(dòng)的activity所在的進(jìn)程和線程都存在。會(huì)進(jìn)行進(jìn)程的創(chuàng)建工作。這部分我們后面專門再進(jìn)行一篇關(guān)于進(jìn)程創(chuàng)建的解析工作。

本文由 開(kāi)了肯 發(fā)布!

同步公眾號(hào)[開(kāi)了肯]

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