低功耗藍(lán)牙BLE

Google在android 4.3(API Level 18)的android版本中引入了低功耗藍(lán)牙BLE核心API颊艳。低功耗藍(lán)牙BLE也就是我們經(jīng)常說(shuō)的藍(lán)牙4.0, 該技術(shù)擁有極低的運(yùn)行和待機(jī)功耗,使用一粒紐扣電池甚至可連續(xù)工作數(shù)年之久违诗。先不講藍(lán)牙協(xié)議與藍(lán)牙模塊一些類的作用與之間的關(guān)系牧牢,本章僅僅記錄android Ble開發(fā)中的掃描模塊及其一些細(xì)節(jié)。

一誓沸、聲明藍(lán)牙權(quán)限和定位權(quán)限

復(fù)制代碼

????由于藍(lán)牙掃描需要用到模糊定位權(quán)限,所以android6.0之后,除了在 AndroidManifest.xml中 申明權(quán)限之外,還需要?jiǎng)討B(tài)申請(qǐng)定位權(quán)限,才可進(jìn)行藍(lán)牙掃描,否則不會(huì)掃描到任何Ble設(shè)備梅桩。

二、中心設(shè)備與外圍設(shè)備

????Ble開發(fā)中,存在著兩個(gè)角色:中心設(shè)備角色和外圍設(shè)備角色拜隧。粗略了解下:

外圍設(shè)備:一般指非常小或者低功耗設(shè)備,更強(qiáng)大的中心設(shè)備可以連接外圍設(shè)備為中心設(shè)備提供數(shù)據(jù)宿百。外設(shè)會(huì)不停的向外廣播趁仙,讓中心設(shè)備知道它的存在。 例如小米手環(huán)垦页。

中心設(shè)備:可以掃描并連接多個(gè)外圍設(shè)備,從外設(shè)中獲取信息雀费。

外圍設(shè)備會(huì)設(shè)定一個(gè)廣播間隔,每個(gè)廣播間隔中痊焊,都會(huì)發(fā)送自己的廣播數(shù)據(jù)坐儿。廣播間隔越長(zhǎng),越省電宋光。一個(gè)沒(méi)有被連接的Ble外設(shè)會(huì)不斷發(fā)送廣播數(shù)據(jù)貌矿,這時(shí)可以被多個(gè)中心設(shè)備發(fā)現(xiàn)。一旦外設(shè)被連接罪佳,則會(huì)馬上停止廣播逛漫。

android 4.3 時(shí)引入的Ble核心Api只支持android手機(jī)作為中心設(shè)備角色,當(dāng)android 5.0 更新Api后,android手機(jī)支持充當(dāng)作為外設(shè)角色和中心角色赘艳。即 android 5.0 引入了外設(shè)角色的Api酌毡,同時(shí)也更新了部分中心角色的Api。比如:中心角色中蕾管,更新了藍(lán)牙掃描的Api枷踏。

三、打開藍(lán)牙

//初始化ble設(shè)配器BluetoothManager manager = (BluetoothManager) getSystemService(Context.BLUETOOTH_SERVICE);BluetoothAdapter mBluetoothAdapter = manager.getAdapter();//判斷藍(lán)牙是否開啟掰曾,如果關(guān)閉則請(qǐng)求打開藍(lán)牙if(mBluetoothAdapter == null || !mBluetoothAdapter.isEnabled()) {? ? //方式一:請(qǐng)求打開藍(lán)牙? ? Intent intent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);? ? startActivityForResult(intent, 1);? ? //方式二:半靜默打開藍(lán)牙? ? //低版本android會(huì)靜默打開藍(lán)牙旭蠕,高版本android會(huì)請(qǐng)求打開藍(lán)牙? ? //mBluetoothAdapter.enable();}復(fù)制代碼

????mBluetoothAdapter.isEnabled()判斷當(dāng)前藍(lán)牙是否打開,如果藍(lán)牙處于打開狀態(tài)返回true旷坦。

????同時(shí)可以在activity層通過(guò)廣播監(jiān)聽藍(lán)牙的關(guān)閉與開啟掏熬,進(jìn)行自己的邏輯處理:

newBroadcastReceiver() {? ? @Override? ? public void onReceive(Context context, Intent intent) {? ? ? ? //獲取藍(lán)牙廣播? 本地藍(lán)牙適配器的狀態(tài)改變時(shí)觸發(fā)? ? ? ? String action = intent.getAction();if(action.equals(BluetoothAdapter.ACTION_STATE_CHANGED)) {? ? ? ? ? ? //獲取藍(lán)牙廣播中的藍(lán)牙新狀態(tài)? ? ? ? ? ? int blueNewState = intent.getIntExtra(BluetoothAdapter.EXTRA_STATE, 0);? ? ? ? ? ? //獲取藍(lán)牙廣播中的藍(lán)牙舊狀態(tài)? ? ? ? ? ? int blueOldState = intent.getIntExtra(BluetoothAdapter.EXTRA_STATE, 0);? ? ? ? ? ? switch (blueNewState) {? ? ? ? ? ? ? ? //正在打開藍(lán)牙caseBluetoothAdapter.STATE_TURNING_ON:break;? ? ? ? ? ? ? ? ? ? //藍(lán)牙已打開caseBluetoothAdapter.STATE_ON:break;? ? ? ? ? ? ? ? ? ? //正在關(guān)閉藍(lán)牙caseBluetoothAdapter.STATE_TURNING_OFF:break;? ? ? ? ? ? ? ? ? ? //藍(lán)牙已關(guān)閉caseBluetoothAdapter.STATE_OFF:break;? ? ? ? ? ? }? ? ? ? }? ? }};復(fù)制代碼

四、掃描

android 4.3 掃描

在android 4.3 和 android 4.4進(jìn)行藍(lán)牙掃描中秒梅,可使用BluetoothAdapter.startLeScan(BluetoothAdapter.LeScanCallback)進(jìn)行藍(lán)牙掃描旗芬。

//開始掃描mBluetoothAdapter.startLeScan(mLeScanCallback);//停止掃描mBluetoothAdapter.stopLeScan(mLeScanCallback);復(fù)制代碼

android 5.0以上 掃描

????在 android 5.0之后的版本(包括 5.0)建議使用新的Api進(jìn)行藍(lán)牙掃描:

BluetoothLeScanner.startScan(ScanCallback)或

BluetoothLeScanner.startScan(List, ScanSettings, ScanCallback)。

//獲取 5.0 的掃描類實(shí)例mBLEScanner = mBluetoothAdapter.getBluetoothLeScanner();//開始掃描//可設(shè)置過(guò)濾條件捆蜀,在第一個(gè)參數(shù)傳入疮丛,但一般不設(shè)置過(guò)濾。mBLEScanner.startScan(null,mScanSettings,mScanCallback);//停止掃描mBLEScanner.stopScan(mScanCallback);復(fù)制代碼

藍(lán)牙掃描示例:

//如果沒(méi)打開藍(lán)牙辆它,不進(jìn)行掃描操作誊薄,或請(qǐng)求打開藍(lán)牙。if(!mBluetoothAdapter.isEnabled()) {return;} //處于未掃描的狀態(tài)if(!mScanning){? ? //android 5.0后if(android.os.Build.VERSION.SDK_INT >= 21) {? ? ? ? //標(biāo)記當(dāng)前的為掃描狀態(tài)? ? ? ? mScanning =true;? ? ? ? //獲取5.0新添的掃描類if(mBLEScanner == null){? ? ? ? ? ? //mBLEScanner是5.0新添加的掃描類娩井,通過(guò)BluetoothAdapter實(shí)例獲取暇屋。? ? ? ? ? ? mBLEScanner = mBluetoothAdapter.getBluetoothLeScanner();? ? ? ? }? ? ? ? //開始掃描? ? ? ? //mScanSettings是ScanSettings實(shí)例,mScanCallback是ScanCallback實(shí)例洞辣,后面進(jìn)行講解咐刨。? ? ? ? mBLEScanner.startScan(null,mScanSettings,mScanCallback);? ? }else{? ? ? ? //標(biāo)記當(dāng)前的為掃描狀態(tài)? ? ? ? mScanning =true;? ? ? ? //5.0以下? 開始掃描? ? ? ? //mLeScanCallback是BluetoothAdapter.LeScanCallback實(shí)例? ? ? ? mBluetoothAdapter.startLeScan(mLeScanCallback);? ? }? ? //設(shè)置結(jié)束掃描? ? mHandler.postDelayed(newRunnable() {? ? ? ? @Override? ? ? ? public voidrun() {? ? ? ? ? ? //停止掃描設(shè)備if(android.os.Build.VERSION.SDK_INT >= 21) {? ? ? ? ? ? ? ? //標(biāo)記當(dāng)前的為未掃描狀態(tài)? ? ? ? ? ? ? ? mScanning =false;? ? ? ? ? ? ? ? mBLEScanner.stopScan(mScanCallback);? ? ? ? ? ? }else{? ? ? ? ? ? ? ? //標(biāo)記當(dāng)前的為未掃描狀態(tài)? ? ? ? ? ? ? ? mScanning =false;? ? ? ? ? ? ? ? //5.0以下? 停止掃描? ? ? ? ? ? ? ? mBluetoothAdapter.stopLeScan(mLeScanCallback);? ? ? ? ? ? }? ? ? ? }? ? },SCAN_TIME);}復(fù)制代碼

????掃描代碼如上述所示昙衅,當(dāng)掃描到所需要的設(shè)備的時(shí)候,就要手動(dòng)馬上停止藍(lán)牙掃描定鸟,因?yàn)樗{(lán)牙掃描是耗電操作而涉。

注意事項(xiàng):

android 6.0 以上需要獲取到定位權(quán)限。否則會(huì)爆如下運(yùn)行時(shí)異常:

android 7.0 后不能在30秒內(nèi)掃描和停止超過(guò)5次联予。(官網(wǎng)沒(méi)特意說(shuō)明啼县,可自行測(cè)試,設(shè)置掃描時(shí)長(zhǎng)為3秒沸久,連續(xù)掃描10次季眷,穩(wěn)定復(fù)現(xiàn)5次后不能掃描到任何設(shè)備。android 藍(lán)牙模塊會(huì)打印當(dāng)前應(yīng)用掃描太頻繁的log日志,并在android 5.0 的ScanCallback回調(diào)中觸發(fā)onScanFailed(int),返回錯(cuò)誤碼:ScanCallback.SCAN_FAILED_APPLICATION_REGISTRATION_FAILED,表示app無(wú)法注冊(cè)卷胯,無(wú)法開始掃描)子刮。

五、掃描回調(diào)

android 4.3 掃描回調(diào):LeScanCallback

1窑睁、android 4.3 的掃描回調(diào)接口BluetoothAdapter.LeScanCallback:

回調(diào)接口中只有一個(gè)回調(diào)函數(shù)onLeScan挺峡,掃描到的設(shè)備會(huì)通過(guò)該方法返回。

參數(shù):

BluetoothDevice 掃描到的設(shè)備實(shí)例担钮,可從實(shí)例中獲取到相應(yīng)的信息橱赠。如:名稱,mac地址

rssi 可理解成設(shè)備的信號(hào)值箫津。該數(shù)值是一個(gè)負(fù)數(shù)狭姨,越大則信號(hào)越強(qiáng)。

scanRecord 遠(yuǎn)程設(shè)備提供的廣播數(shù)據(jù)的內(nèi)容鲤嫡。

//5.0以下mLeScanCallback = new BluetoothAdapter.LeScanCallback() {? ? @Override? ? public void onLeScan(BluetoothDevice device, int rssi, byte[] scanRecord) {? ? ? ? //對(duì)掃描到的設(shè)備進(jìn)行操作送挑。如:獲取設(shè)備信息。? ? ? ? ? ? }};復(fù)制代碼

獲取BluetoothDevice中的信息:

可以從中獲取到設(shè)備的mac地址暖眼,設(shè)備名稱,綁定狀態(tài)和設(shè)備類型等信息纺裁,并作相應(yīng)的保存诫肠。

mac可用于再創(chuàng)建BluetoothDevice對(duì)象進(jìn)行g(shù)att連接。

綁定狀態(tài):

BOND_NONE:數(shù)值 10

表示遠(yuǎn)程設(shè)備未綁定欺缘,沒(méi)有共享鏈接密鑰栋豫,因此通信(如果允許的話)將是未經(jīng)身份驗(yàn)證和未加密的。(掃描到未綁定的小米手環(huán))

????BOND_BONDING:數(shù)值 11 ????表示正在與遠(yuǎn)程設(shè)備進(jìn)行綁定;

????BOND_BONDED:數(shù)值 12 ????表示遠(yuǎn)程設(shè)備已綁定谚殊,遠(yuǎn)程設(shè)備本地存儲(chǔ)共享連接的密鑰丧鸯,因此可以對(duì)通信進(jìn)行身份驗(yàn)證和加密。(掃描到已綁定的小米手環(huán))

設(shè)備類型:一般是2嫩絮,表示LE設(shè)備

注:回調(diào)函數(shù)中盡量不要做耗時(shí)操作丛肢!

android 5.0 掃描回調(diào):ScanCallback

mScanCallback = newScanCallback() {? ? //當(dāng)一個(gè)藍(lán)牙ble廣播被發(fā)現(xiàn)時(shí)回調(diào)? ? @Override? ? public void onScanResult(int callbackType, ScanResult result) {? ? ? ? super.onScanResult(callbackType, result);? ? ? ? //掃描類型有開始掃描時(shí)傳入的ScanSettings相關(guān)? ? ? ? //對(duì)掃描到的設(shè)備進(jìn)行操作围肥。如:獲取設(shè)備信息。? ? ? ? ? ? }? ? //批量返回掃描結(jié)果? ? //@param results 以前掃描到的掃描結(jié)果列表蜂怎。? ? @Override? ? public void onBatchScanResults(List results) {? ? ? ? super.onBatchScanResults(results);? ? ? ? ? ? }? ? //當(dāng)掃描不能開啟時(shí)回調(diào)? ? @Override? ? public void onScanFailed(int errorCode) {? ? ? ? super.onScanFailed(errorCode);? ? ? ? //掃描太頻繁會(huì)返回ScanCallback.SCAN_FAILED_APPLICATION_REGISTRATION_FAILED穆刻,表示app無(wú)法注冊(cè),無(wú)法開始掃描杠步。? ? ? ? }};復(fù)制代碼

ScanCallback掃描回調(diào)存在三個(gè)回調(diào)函數(shù):

onScanResult(int,ScanResult):?

類似于BluetoothAdapter.LeScanCallback中的onLeScan()氢伟,可在ScanResult實(shí)例中獲取到BluetoothDevice藍(lán)牙設(shè)備對(duì)象,rssi信號(hào)值等信息幽歼,一般都是在該函數(shù)中回調(diào)獲取掃描到藍(lán)牙設(shè)備和信號(hào)值朵锣,在本函數(shù)中執(zhí)行onLeScan()中相同的邏輯處理即可。

onBatchScanResults(List) 批量返回掃描結(jié)果

onScanFailed(int) 掃描失敗返回錯(cuò)誤碼

一般藍(lán)牙設(shè)備對(duì)象都是通過(guò)onScanResult(int,ScanResult)返回甸私,而不會(huì)在onBatchScanResults(List)方法中返回猪勇,除非手機(jī)支持批量掃描模式并且開啟了批量掃描模式。批處理的開啟請(qǐng)查看ScanSettings颠蕴。

六泣刹、ScanSettings:

????????ScanSettings實(shí)例對(duì)象是通過(guò)ScanSettings.Builder構(gòu)建的。通過(guò)Builder對(duì)象為ScanSettings實(shí)例設(shè)置掃描模式犀被、回調(diào)類型椅您、匹配模式等參數(shù),用于配置android 5.0 的掃描參數(shù)寡键。

//創(chuàng)建ScanSettings的build對(duì)象用于設(shè)置參數(shù)ScanSettings.Builder builder = new ScanSettings.Builder()? ? //設(shè)置高功耗模式? ? .setScanMode(SCAN_MODE_LOW_LATENCY);? ? //android 6.0添加設(shè)置回調(diào)類型掀泳、匹配模式等if(android.os.Build.VERSION.SDK_INT >= 23) {? ? ? ? //定義回調(diào)類型? ? ? ? builder.setCallbackType(ScanSettings.CALLBACK_TYPE_ALL_MATCHES)? ? ? ? //設(shè)置藍(lán)牙LE掃描濾波器硬件匹配的匹配模式? ? ? ? builder.setMatchMode(ScanSettings.MATCH_MODE_STICKY);? ? }//芯片組支持批處理芯片上的掃描if(bluetoothadapter.isOffloadedScanBatchingSupported()) {? ? //設(shè)置藍(lán)牙LE掃描的報(bào)告延遲的時(shí)間(以毫秒為單位)? ? //設(shè)置為0以立即通知結(jié)果? ? builder.setReportDelay(0L);}builder.build();復(fù)制代碼

配置描述:

setScanMode() 設(shè)置掃描模式∥餍可選擇模式主要三種:

???? ScanSettings.SCAN_MODE_LOW_POWER 低功耗模式

???? ScanSettings.SCAN_MODE_BALANCED 平衡模式

???? ScanSettings.SCAN_MODE_LOW_LATENCY 高功耗模式

????從上到下员舵,會(huì)越來(lái)越耗電,但掃描間隔越來(lái)越短,即掃描速度會(huì)越來(lái)越快藕畔。

setCallbackType() 設(shè)置回調(diào)類型

可選擇模式主要三種:?

ScanSettings.CALLBACK_TYPE_ALL_MATCHES 數(shù)值: 1

尋找符合過(guò)濾條件的藍(lán)牙廣播马僻,如果沒(méi)有設(shè)置過(guò)濾條件,則返回全部廣播包

ScanSettings.CALLBACK_TYPE_FIRST_MATCH 數(shù)值: 2

僅針對(duì)與篩選條件匹配的第一個(gè)廣播包觸發(fā)結(jié)果回調(diào)注服。

ScanSettings.CALLBACK_TYPE_MATCH_LOST 數(shù)值: 4

????回調(diào)類型一般設(shè)置ScanSettings.CALLBACK_TYPE_ALL_MATCHES韭邓,有過(guò)濾條件時(shí)過(guò)濾,返回符合過(guò)濾條件的藍(lán)牙廣播溶弟。無(wú)過(guò)濾條件時(shí)女淑,返回全部藍(lán)牙廣播。

setMatchMode() 設(shè)置藍(lán)牙LE掃描濾波器硬件匹配的匹配模式

一般設(shè)置ScanSettings.MATCH_MODE_STICKY

Bluetoothadapter.isOffloadedScanBatchingSupported()

判斷當(dāng)前手機(jī)藍(lán)牙芯片是否支持批處理掃描辜御。如果支持掃描則使用批處理掃描鸭你,可通過(guò)ScanSettings.Builder對(duì)象調(diào)用setReportDelay(Long)方法來(lái)設(shè)置藍(lán)牙LE掃描的報(bào)告延遲的時(shí)間(以毫秒為單位)來(lái)啟動(dòng)批處理掃描模式。

ScanSettings.Builder.setReportDelay(Long);

當(dāng)設(shè)備藍(lán)牙芯片支持批處理掃描時(shí),用來(lái)設(shè)置藍(lán)牙LE掃描的報(bào)告延遲的時(shí)間(以毫秒為單位)袱巨。

????該參數(shù)默認(rèn)為 0阁谆,如果不修改它的值,則默認(rèn)只會(huì)在onScanResult(int,ScanResult)中返回掃描到的藍(lán)牙設(shè)備瓣窄,不會(huì)觸發(fā)不會(huì)觸發(fā)onBatchScanResults(List)方法笛厦。

????設(shè)置為0以立即通知結(jié)果,不開啟批處理掃描模式。即ScanCallback藍(lán)牙回調(diào)中俺夕,不會(huì)觸發(fā)onBatchScanResults(List)方法裳凸,但會(huì)觸發(fā)onScanResult(int,ScanResult)方法,返回掃描到的藍(lán)牙設(shè)備劝贸。

????當(dāng)設(shè)置的時(shí)間大于0L時(shí)姨谷,則會(huì)開啟批處理掃描模式。即觸發(fā)onBatchScanResults(List)方法映九,返回掃描到的藍(lán)牙設(shè)備列表梦湘。但不會(huì)觸發(fā)onScanResult(int,ScanResult)方法。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末件甥,一起剝皮案震驚了整個(gè)濱河市捌议,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌引有,老刑警劉巖瓣颅,帶你破解...
    沈念sama閱讀 217,734評(píng)論 6 505
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異譬正,居然都是意外死亡宫补,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,931評(píng)論 3 394
  • 文/潘曉璐 我一進(jìn)店門曾我,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)粉怕,“玉大人,你說(shuō)我怎么就攤上這事抒巢∑侗矗” “怎么了?”我有些...
    開封第一講書人閱讀 164,133評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵虐秦,是天一觀的道長(zhǎng)平酿。 經(jīng)常有香客問(wèn)我,道長(zhǎng)悦陋,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,532評(píng)論 1 293
  • 正文 為了忘掉前任筑辨,我火速辦了婚禮俺驶,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己暮现,他們只是感情好还绘,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,585評(píng)論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著栖袋,像睡著了一般拍顷。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上塘幅,一...
    開封第一講書人閱讀 51,462評(píng)論 1 302
  • 那天昔案,我揣著相機(jī)與錄音,去河邊找鬼电媳。 笑死踏揣,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的匾乓。 我是一名探鬼主播捞稿,決...
    沈念sama閱讀 40,262評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼拼缝!你這毒婦竟也來(lái)了娱局?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,153評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤咧七,失蹤者是張志新(化名)和其女友劉穎衰齐,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體猪叙,經(jīng)...
    沈念sama閱讀 45,587評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡娇斩,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,792評(píng)論 3 336
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了穴翩。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片犬第。...
    茶點(diǎn)故事閱讀 39,919評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖芒帕,靈堂內(nèi)的尸體忽然破棺而出歉嗓,到底是詐尸還是另有隱情,我是刑警寧澤背蟆,帶...
    沈念sama閱讀 35,635評(píng)論 5 345
  • 正文 年R本政府宣布鉴分,位于F島的核電站,受9級(jí)特大地震影響带膀,放射性物質(zhì)發(fā)生泄漏志珍。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,237評(píng)論 3 329
  • 文/蒙蒙 一垛叨、第九天 我趴在偏房一處隱蔽的房頂上張望伦糯。 院中可真熱鬧,春花似錦、人聲如沸敛纲。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,855評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)淤翔。三九已至翰绊,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間旁壮,已是汗流浹背监嗜。 一陣腳步聲響...
    開封第一講書人閱讀 32,983評(píng)論 1 269
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留寡具,地道東北人秤茅。 一個(gè)月前我還...
    沈念sama閱讀 48,048評(píng)論 3 370
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像童叠,于是被迫代替她去往敵國(guó)和親框喳。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,864評(píng)論 2 354

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