Android 视频录制

想到视频录制,肯定又是运用MediaRecorder,这个类实在是方便,但是好用的东西一定要慎重,毕竟没有那么便宜的事,但是基本满足用户要求,但是对于比较苛刻的项目而言,那就很尴尬了,比如:拍摄的视频不聚焦,拍摄像素低,甚至在有些手机上面根本无法进行拍摄录制,这就导致无法很好的使用了。不过我还是提供出工具类。希望高手能修改,并完美运行。

importandroid.annotation.SuppressLint;

importandroid.app.AlertDialog;

importandroid.app.ProgressDialog;

importandroid.content.Context;

importandroid.content.DialogInterface;

importandroid.graphics.Bitmap;

importandroid.graphics.PixelFormat;

importandroid.hardware.Camera;

importandroid.media.MediaRecorder;

importandroid.media.MediaScannerConnection;

importandroid.net.Uri;

importandroid.os.Bundle;

importandroid.os.Environment;

importandroid.os.PowerManager;

importandroid.os.SystemClock;

importandroid.text.TextUtils;

importandroid.util.Log;

importandroid.view.SurfaceHolder;

importandroid.view.View;

importandroid.view.Window;

importandroid.view.WindowManager;

importandroid.widget.Button;

importandroid.widget.Chronometer;

importandroid.widget.ImageView;

importandroid.widget.RelativeLayout;

importandroid.widget.Toast;

importandroid.widget.VideoView;

importcom.lvgou.distribution.R;

importcom.lvgou.distribution.utils.PathUtil;

importcom.lvgou.distribution.utils.Utils;

importjava.io.BufferedOutputStream;

importjava.io.File;

importjava.io.FileOutputStream;

importjava.io.IOException;

importjava.util.Collections;

importjava.util.List;

/**

* Created by Administrator on 2017/6/14.

*/

publicclassMyRecorderVideoActivityextendsBaseActivityimplementsView.OnClickListener,SurfaceHolder.Callback,MediaRecorder.OnInfoListener,MediaRecorder.OnErrorListener{

privatestaticfinalStringTAG="RecorderVideoActivity";

privatefinalstaticStringCLASS_LABEL="RecordActivity";

privatePowerManager.WakeLockmWakeLock;

privateImageViewbtnStart;//开始拍摄

privateImageViewbtnStop;//停止拍摄

privateMediaRecordermediaRecorder;

privateVideoViewmVideoView;// 显示视频

StringlocalPath="";// 路径保存录像

privateCameramCamera;

privateintpreviewWidth=480;

privateintpreviewHeight=480;

privateChronometerchronometer;//时间

privateintfrontCamera=0;// 0是相机,1是前置摄像头

privateButtonbtn_switch;//切换摄像头

Camera.ParameterscameraParameters=null;

privateSurfaceHoldermSurfaceHolder;

intdefaultVideoFrameRate=-1;

@Override

publicvoidonCreate(BundlesavedInstanceState){

super.onCreate(savedInstanceState);

requestWindowFeature(Window.FEATURE_NO_TITLE);// 无标题

getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,

WindowManager.LayoutParams.FLAG_FULLSCREEN);// 全屏幕

// 半透明模式,用于表面的观点

getWindow().setFormat(PixelFormat.TRANSLUCENT);

setContentView(R.layout.my_recorder_activity);

PowerManagerpm=(PowerManager)getSystemService(Context.POWER_SERVICE);

mWakeLock=pm.newWakeLock(PowerManager.SCREEN_BRIGHT_WAKE_LOCK,

CLASS_LABEL);

mWakeLock.acquire();

initViews();

}

privateRelativeLayoutrl_back;

// 初始化控件

privatevoidinitViews(){

rl_back=(RelativeLayout)findViewById(R.id.rl_back);

rl_back.setOnClickListener(this);

btn_switch=(Button)findViewById(R.id.switch_btn);//切换摄像头

btn_switch.setOnClickListener(this);

btn_switch.setVisibility(View.VISIBLE);

mVideoView=(VideoView)findViewById(R.id.mVideoView);//视频控件显示视频

btnStart=(ImageView)findViewById(R.id.recorder_start);//开始拍摄

btnStop=(ImageView)findViewById(R.id.recorder_stop);//停止拍摄

btnStart.setOnClickListener(this);

btnStop.setOnClickListener(this);

mSurfaceHolder=mVideoView.getHolder();

mSurfaceHolder.addCallback(this);

mSurfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);

chronometer=(Chronometer)findViewById(R.id.chronometer);//时间

}

publicvoidback(Viewview){

releaseRecorder();

releaseCamera();

finish();

}

@Override

protectedvoidonResume(){

super.onResume();

if(mWakeLock==null){

// 保持唤醒

PowerManagerpm=(PowerManager)getSystemService(Context.POWER_SERVICE);

mWakeLock=pm.newWakeLock(PowerManager.SCREEN_BRIGHT_WAKE_LOCK,

CLASS_LABEL);

mWakeLock.acquire();

}

}

// 初始化照相机

@SuppressLint("NewApi")

privatebooleaninitCamera(){

try{

if(frontCamera==0){

mCamera=Camera.open(Camera.CameraInfo.CAMERA_FACING_BACK);

}else{

mCamera=Camera.open(Camera.CameraInfo.CAMERA_FACING_FRONT);

}

Camera.ParameterscamParams=mCamera.getParameters();

mCamera.lock();

mSurfaceHolder=mVideoView.getHolder();

mSurfaceHolder.addCallback(this);

mSurfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);

mCamera.setDisplayOrientation(90);

}catch(RuntimeExceptionex){

returnfalse;

}

returntrue;

}

privatevoidhandleSurfaceChanged(){

if(mCamera==null){

finish();

return;

}

booleanhasSupportRate=false;

ListsupportedPreviewFrameRates=mCamera.getParameters()

.getSupportedPreviewFrameRates();

if(supportedPreviewFrameRates!=null

&&supportedPreviewFrameRates.size()>0){

Collections.sort(supportedPreviewFrameRates);

for(inti=0;i

intsupportRate=supportedPreviewFrameRates.get(i);

if(supportRate==15){

hasSupportRate=true;

}

}

if(hasSupportRate){

defaultVideoFrameRate=15;

}else{

defaultVideoFrameRate=supportedPreviewFrameRates.get(0);

}

}

// 得到所有相机提供的决议

ListresolutionList=Utils.getResolutionList(mCamera);

if(resolutionList!=null&&resolutionList.size()>0){

Collections.sort(resolutionList,newUtils.ResolutionComparator());

Camera.SizepreviewSize=null;

booleanhasSize=false;

// 如果相机支持使用60 * 480

for(inti=0;i

Camera.Sizesize=resolutionList.get(i);

if(size!=null&&size.width==640&&size.height==480){

previewSize=size;

previewWidth=previewSize.width;

previewHeight=previewSize.height;

hasSize=true;

break;

}

}

// 使用中等分辨率如果相机不支持上述决议

if(!hasSize){

intmediumResolution=resolutionList.size()/2;

if(mediumResolution>=resolutionList.size())

mediumResolution=resolutionList.size()-1;

previewSize=resolutionList.get(mediumResolution);

previewWidth=previewSize.width;

previewHeight=previewSize.height;

}

}

}

@Override

protectedvoidonPause(){

super.onPause();

if(mWakeLock!=null){

mWakeLock.release();

mWakeLock=null;

}

}

@Override

publicvoidonClick(Viewview){

inti=view.getId();

if(i==R.id.switch_btn){

//切换摄像头

switchCamera();

}elseif(i==R.id.recorder_start){

// 开始录制

if(!startRecording())

return;

Toast.makeText(this,R.string.The_video_to_start,Toast.LENGTH_SHORT).show();

btn_switch.setVisibility(View.INVISIBLE);

btnStart.setVisibility(View.INVISIBLE);

btnStart.setEnabled(false);

btnStop.setVisibility(View.VISIBLE);

chronometer.setBase(SystemClock.elapsedRealtime());

chronometer.start();

}elseif(i==R.id.recorder_stop){

// 停止录制

btnStop.setEnabled(false);

stopRecording();

btn_switch.setVisibility(View.VISIBLE);

chronometer.stop();

btnStart.setVisibility(View.VISIBLE);

btnStop.setVisibility(View.INVISIBLE);

//弹出是否发送对话框

newAlertDialog.Builder(this)

.setMessage("是否使用该视频!")

.setPositiveButton(R.string.ok,

newDialogInterface.OnClickListener(){

@Override

publicvoidonClick(DialogInterfacedialog,intwhich){

dialog.dismiss();

//发送视频

sendVideo(null);

}

})

.setNegativeButton(R.string.cancel,

newDialogInterface.OnClickListener(){

@Override

publicvoidonClick(DialogInterfacedialog,intwhich){

if(localPath!=null){

Filefile=newFile(localPath);

if(file.exists())

file.delete();

}

finish();

}

}).setCancelable(false).show();

}elseif(i==R.id.rl_back){

if(localPath!=null){

Filefile=newFile(localPath);

if(file.exists())

file.delete();

}

finish();

}

}

@Override

publicvoidsurfaceChanged(SurfaceHolderholder,intformat,intwidth,

intheight){

mSurfaceHolder=holder;

}

@Override

publicvoidsurfaceCreated(SurfaceHolderholder){

if(mCamera==null){

if(!initCamera()){

showFailDialog();

return;

}

}

try{

mCamera.setPreviewDisplay(mSurfaceHolder);

mCamera.startPreview();

handleSurfaceChanged();

}catch(Exceptione1){

showFailDialog();

}

}

@Override

publicvoidsurfaceDestroyed(SurfaceHolderarg0){

}

publicbooleanstartRecording(){

if(mediaRecorder==null){

if(!initRecorder())

returnfalse;

}

mediaRecorder.setOnInfoListener(this);

mediaRecorder.setOnErrorListener(this);

mediaRecorder.start();

returntrue;

}

publicbooleanisSdcardExist(){

returnandroid.os.Environment.getExternalStorageState().equals(android.os.Environment.MEDIA_MOUNTED);

}

@SuppressLint("NewApi")

privatebooleaninitRecorder(){

if(!isSdcardExist()){

showNoSDCardDialog();

returnfalse;

}

if(mCamera==null){

if(!initCamera()){

showFailDialog();

returnfalse;

}

}

mVideoView.setVisibility(View.VISIBLE);

mCamera.stopPreview();

mediaRecorder=newMediaRecorder();

mCamera.unlock();

mediaRecorder.setCamera(mCamera);

mediaRecorder.setAudioSource(MediaRecorder.AudioSource.DEFAULT);

mediaRecorder.setVideoSource(MediaRecorder.VideoSource.CAMERA);

if(frontCamera==1){

mediaRecorder.setOrientationHint(270);

}else{

mediaRecorder.setOrientationHint(90);

}

mediaRecorder.setOutputFormat(MediaRecorder.OutputFormat.MPEG_4);

mediaRecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AAC);

mediaRecorder.setVideoEncoder(MediaRecorder.VideoEncoder.H264);

// 设置分辨率,应设置在格式和编码器

//        mediaRecorder.setVideoSize(previewWidth, previewHeight);

mediaRecorder.setVideoEncodingBitRate(384*1024);

// 设置帧率,应设置在格式和编码器

if(defaultVideoFrameRate!=-1){

mediaRecorder.setVideoFrameRate(defaultVideoFrameRate);

}

// 设置视频文件的路径

localPath=PathUtil.getInstance().getVideoPath()+"/"

+System.currentTimeMillis()+".mp4";

mediaRecorder.setOutputFile(localPath);

mediaRecorder.setMaxDuration(30000);

mediaRecorder.setPreviewDisplay(mSurfaceHolder.getSurface());

Log.i("fdsafasdfsadfasd","----------initRecorder-------"+localPath);

try{

mediaRecorder.prepare();

}catch(IllegalStateExceptione){

e.printStackTrace();

returnfalse;

}catch(IOExceptione){

e.printStackTrace();

returnfalse;

}

returntrue;

}

// 停止录制

publicvoidstopRecording(){

if(mediaRecorder!=null){

mediaRecorder.setOnErrorListener(null);

mediaRecorder.setOnInfoListener(null);

try{

mediaRecorder.stop();

}catch(Exceptione){

}

}

releaseRecorder();

if(mCamera!=null){

mCamera.stopPreview();

releaseCamera();

}

}

privatevoidreleaseRecorder(){

if(mediaRecorder!=null){

mediaRecorder.release();

mediaRecorder=null;

}

}

protectedvoidreleaseCamera(){

try{

if(mCamera!=null){

mCamera.stopPreview();

mCamera.release();

mCamera=null;

}

}catch(Exceptione){

}

}

// 切换摄像头

@SuppressLint("NewApi")

publicvoidswitchCamera(){

if(mCamera==null){

return;

}

if(Camera.getNumberOfCameras()>=2){

btn_switch.setEnabled(false);

if(mCamera!=null){

mCamera.stopPreview();

mCamera.release();

mCamera=null;

}

switch(frontCamera){

case0:

mCamera=Camera.open(Camera.CameraInfo.CAMERA_FACING_FRONT);

frontCamera=1;

break;

case1:

mCamera=Camera.open(Camera.CameraInfo.CAMERA_FACING_BACK);

frontCamera=0;

break;

}

try{

mCamera.lock();

mCamera.setDisplayOrientation(90);

mCamera.setPreviewDisplay(mVideoView.getHolder());

mCamera.startPreview();

}catch(IOExceptione){

mCamera.release();

mCamera=null;

}

btn_switch.setEnabled(true);

}

}

MediaScannerConnectionmsc=null;

ProgressDialogprogressDialog=null;

publicvoidsendVideo(Viewview){

if(TextUtils.isEmpty(localPath)){

return;

}

if(msc==null)

msc=newMediaScannerConnection(this,

newMediaScannerConnection.MediaScannerConnectionClient(){

@Override

publicvoidonScanCompleted(Stringpath,Uriuri){

msc.disconnect();

progressDialog.dismiss();

setResult(RESULT_OK,getIntent().putExtra("uri",uri));

finish();

/*  String[] proj = {MediaStore.Images.Media.DATA};

Cursor actualimagecursor = managedQuery(uri, proj, null, null, null);

int actual_image_column_index = actualimagecursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);

actualimagecursor.moveToFirst();

String img_path = actualimagecursor.getString(actual_image_column_index);

ArrayList file_list = new ArrayList<>();

File file = new File(img_path);

file_list.add(file);

Intent intent = new Intent();

intent.setClass(MyRecorderVideoActivity.this, MovieBuffAddVideoActivity.class);

Bundle bundle = new Bundle();

bundle.putSerializable("file_list", file_list);

bundle.putString("localPath", localPath);

intent.putExtras(bundle);

startActivity(intent);

onBackPressed();*/

}

@Override

publicvoidonMediaScannerConnected(){

msc.scanFile(localPath,"video/*");

}

});

if(progressDialog==null){

progressDialog=newProgressDialog(this);

progressDialog.setMessage("processing...");

progressDialog.setCancelable(false);

}

progressDialog.show();

msc.connect();

}

@Override

publicvoidonInfo(MediaRecordermr,intwhat,intextra){

if(what==MediaRecorder.MEDIA_RECORDER_INFO_MAX_DURATION_REACHED){

stopRecording();

btn_switch.setVisibility(View.VISIBLE);

chronometer.stop();

btnStart.setVisibility(View.VISIBLE);

btnStop.setVisibility(View.INVISIBLE);

chronometer.stop();

if(localPath==null){

return;

}

Stringst3=getResources().getString(R.string.Whether_to_send);

newAlertDialog.Builder(this)

.setMessage("是否使用该视频!")

.setPositiveButton(R.string.ok,

newDialogInterface.OnClickListener(){

@Override

publicvoidonClick(DialogInterfacearg0,

intarg1){

arg0.dismiss();

sendVideo(null);

}

}).setNegativeButton(R.string.cancel,null)

.setCancelable(false).show();

}

}

@Override

publicvoidonError(MediaRecordermr,intwhat,intextra){

stopRecording();

Toast.makeText(this,"Recording error has occurred. Stopping the recording",Toast.LENGTH_SHORT).show();

}

publicvoidsaveBitmapFile(Bitmapbitmap){

Filefile=newFile(Environment.getExternalStorageDirectory(),"a.jpg");

try{

BufferedOutputStreambos=newBufferedOutputStream(newFileOutputStream(file));

bitmap.compress(Bitmap.CompressFormat.JPEG,100,bos);

bos.flush();

bos.close();

}catch(IOExceptione){

e.printStackTrace();

}

}

@Override

protectedvoidonDestroy(){

super.onDestroy();

releaseCamera();

if(mWakeLock!=null){

mWakeLock.release();

mWakeLock=null;

}

}

@Override

publicvoidonBackPressed(){

back(null);

}

privatevoidshowFailDialog(){

newAlertDialog.Builder(this)

.setTitle(R.string.prompt)

.setMessage(R.string.Open_the_equipment_failure)

.setPositiveButton(R.string.ok,

newDialogInterface.OnClickListener(){

@Override

publicvoidonClick(DialogInterfacedialog,

intwhich){

finish();

}

}).setCancelable(false).show();

}

privatevoidshowNoSDCardDialog(){

newAlertDialog.Builder(this)

.setTitle(R.string.prompt)

.setMessage("No sd card!")

.setPositiveButton(R.string.ok,

newDialogInterface.OnClickListener(){

@Override

publicvoidonClick(DialogInterfacedialog,

intwhich){

finish();

}

}).setCancelable(false).show();

}

}

MyRecorderVideoActivity.java

下面是xml布局文件

android:layout_width="match_parent"

android:layout_height="match_parent"

android:orientation="vertical">

android:id="@+id/rl_title"

android:layout_width="match_parent"

android:layout_height="45dp"

android:background="@color/bg_white">

android:id="@+id/rl_back"

android:layout_width="45dp"

android:layout_height="match_parent"

android:layout_alignParentLeft="true">

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:layout_centerHorizontal="true"

android:layout_centerVertical="true"

android:layout_marginLeft="10dp"

android:background="@mipmap/rl_back"/>

android:id="@+id/tv_title"

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:layout_centerHorizontal="true"

android:layout_centerVertical="true"

android:text="录制视频"

android:textColor="@color/bg_text_black"

android:textSize="@dimen/sixteen"/>

android:layout_width="fill_parent"

android:layout_height="fill_parent">

android:id="@+id/mVideoView"

android:layout_width="fill_parent"

android:layout_height="fill_parent"/>

android:id="@+id/switch_btn"

android:layout_width="35dip"

android:layout_height="35dip"

android:layout_alignParentRight="true"

android:layout_alignParentTop="true"

android:background="@drawable/em_camera_switch_selector"

android:visibility="invisible"/>

android:id="@+id/chronometer"

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:layout_alignParentLeft="true"

android:layout_alignParentTop="true"

android:background="@color/btn_gray_normal"

android:gravity="center_horizontal"

android:textColor="#FFF"/>

android:id="@+id/recorder_start"

android:layout_width="60dp"

android:layout_height="60dp"

android:layout_alignParentBottom="true"

android:layout_centerHorizontal="true"

android:gravity="center"

android:src="@mipmap/em_video_recorder_start_btn"

android:visibility="visible"/>

android:id="@+id/recorder_stop"

android:layout_width="60dp"

android:layout_height="60dp"

android:layout_alignParentBottom="true"

android:layout_centerHorizontal="true"

android:gravity="center"

android:src="@mipmap/em_video_recorder_stop_btn"

android:visibility="invisible"/>

来自CODE的代码片

my_recorder_activity.xml

为此我也在网上找了一些资料,不过大部分demo的原理也是MediaRecorder。但是我看到了我拍摄照片的方式,就调用系统自带的摄像头,然后进行拍摄,获取路径就可以了。因此我就想到了拍摄视频如果使用系统自带的录制那就很好的能解决兼容性问题了。唯一不好的就是拍摄界面无法自己定义,各自手机自带的是什么样子的拍摄就保留怎样的拍摄。其实很简单:

Intent intent = new Intent(MediaStore.ACTION_VIDEO_CAPTURE);

//设置视频大小

intent.putExtra(Android.provider.MediaStore.EXTRA_SIZE_LIMIT, 768000);

intent.putExtra(MediaStore.EXTRA_VIDEO_QUALITY, 0);

//设置视频时间

intent.putExtra(android.provider.MediaStore.EXTRA_DURATION_LIMIT, 10);

startActivityForResult(intent, REQUEST_CODE_MAP);

然后就是接收了:

Uri uri = data.getData();

//                    Uri uri = data.getParcelableExtra("uri");

String[] projects = new String[]{MediaStore.Video.Media.DATA,

MediaStore.Video.Media.DURATION};

Cursor cursor = getContentResolver().query(uri,projects, null, null, null);

int duration = 0;

String copyfilepaths="";

String filePath = null;

if (cursor.moveToFirst()) {

// 路径:MediaStore.Audio.Media.DATA

filePath = cursor.getString(cursor.getColumnIndexOrThrow(MediaStore.Video.Media.DATA));

try {

copyfilepaths=PathUtil.getInstance().getVideoPath() + "/" + System.currentTimeMillis() + ".mp4";

copyFileTo(new File(filePath),new File(copyfilepaths));

} catch (IOException e) {

e.printStackTrace();

}

// 总播放时长:MediaStore.Audio.Media.DURATION

duration = cursor.getInt(cursor.getColumnIndexOrThrow(MediaStore.Video.Media.DURATION));

}

if (cursor != null) {

cursor.close();

cursor = null;

}

File file = new File(PathUtil.getInstance().getImagePath(), "thvideo" + System.currentTimeMillis());

FileOutputStream fos = new FileOutputStream(file);

Bitmap ThumbBitmap = ThumbnailUtils.createVideoThumbnail(filePath, 5);

ThumbBitmap.compress(Bitmap.CompressFormat.JPEG, 100, fos);

fos.close();

值得一提的是:必须要将保存下来的文件copy一次

因为在某些手机使用中,上传文件到服务器是不允许被上传的,然后就导致服务器那边就收不到文件,所以我写了一个方法来转换文件,其实也就是复制文件。

booleancopyFileTo(File srcFile, File destFile)throwsIOException {

if(srcFile.isDirectory() || destFile.isDirectory())

returnfalse;//判断是否是文件

FileInputStream fis =newFileInputStream(srcFile);

FileOutputStream fos =newFileOutputStream(destFile);

intreadLen =0;

byte[] buf =newbyte[1024];

while((readLen = fis.read(buf)) != -1) {

fos.write(buf,0, readLen);

}

fos.flush();

fos.close();

fis.close();

returntrue;

}

csdn项目地址:http://blog.csdn.net/greatdaocaoren/article/details/73497819

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 206,839评论 6 482
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 88,543评论 2 382
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 153,116评论 0 344
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 55,371评论 1 279
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 64,384评论 5 374
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,111评论 1 285
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,416评论 3 400
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,053评论 0 259
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 43,558评论 1 300
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,007评论 2 325
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,117评论 1 334
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,756评论 4 324
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,324评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,315评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,539评论 1 262
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,578评论 2 355
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,877评论 2 345

推荐阅读更多精彩内容