Fabric.js介紹 第四部分

我們已經(jīng)在前幾個系列涵蓋了很多話題烤礁,從基礎(chǔ)對象操作到動畫讼积,事件,濾鏡脚仔,組合和子類勤众。但還有幾件非常有趣和有用的事情要討論!

自由繪畫

如果說有什么功能能讓<canvas>在眼前一亮鲤脏,那一定是它能夠很好的支持自由繪圖们颜!由于畫布只是一個2D位圖, Fabric為我們提供了一張紙:可以自由繪畫猎醇,而且非常自然窥突。

只需將Fabric canvas的isDrawingMode屬性設(shè)置為true即可實(shí)現(xiàn)自由繪制模式。這樣畫布上的點(diǎn)擊和移動就會被立刻解釋為鉛筆或刷子硫嘶。

當(dāng)isDrawingModetrue時波岛,您可以隨意在畫布上多次繪制,但是一旦你在畫布上做任何動作音半,然后觸發(fā)“mouseup”事件则拷,F(xiàn)abric就會觸發(fā)"path:created" 事件,并且將剛剛的繪畫轉(zhuǎn)變?yōu)?code>fabric.Path的實(shí)例曹鸠,

如果在任何時刻,將isDrawingMode設(shè)置為false彻桃,你創(chuàng)建的路徑對象會仍然存在于畫布上坛善。而且由于它們是fabric.Path對象,所以可以以任何方式修改它們: 移動邻眷,旋轉(zhuǎn)眠屎,縮放等。

還有兩個屬性可以定制自由繪圖: freeDrawingBrush.color and freeDrawingBrush.width肆饶,兩者都可以通過freeDrawingBrush實(shí)例在Fabric畫布實(shí)例上使用改衩。freeDrawingBrush.color可以是任何常規(guī)的顏色值,代表畫筆的顏色驯镊。freeDrawingBrush.width是一個像素葫督,代表畫筆的寬度。

在不久的將來板惑,我們計(jì)劃添加更多的自由繪圖選項(xiàng):各種版本的畫筆(如噴霧式或粉筆式)橄镜。還可以自定義畫筆模式,還有一個可以自己擴(kuò)展的選項(xiàng)冯乘,類似于Fabric圖像濾鏡洽胶。

自定義

一件有趣的事情是如何去自定義Fabric,您可以在canvascanvas對象上調(diào)整數(shù)十種各樣的參數(shù)裆馒,以使事情按照所需的方式運(yùn)行姊氓。我們來看看其中的一些丐怯。

鎖定對象

畫布上的每個對象都可以以幾種方式鎖定∷牛“l(fā)ockMovementX”响逢,“l(fā)ockMovementY”绒窑,“l(fā)ockRotation”棕孙,“l(fā)ockScalingX”,“l(fā)ockScalingY”是鎖定相應(yīng)對象動作的屬性些膨。所以將某個對象的lockMovementX屬性設(shè)置為true會阻止對象被水平移動蟀俊,此時你仍然可以垂直移動它。類似的订雾,lockRotation可以阻止旋轉(zhuǎn)肢预,lockScalingX / lockScalingY 可以阻止水平或者垂直縮放。所有這些都是可以疊加的洼哎,你可以將它們組合在一起使用烫映。

改變邊框和角

您可以通過“hasControls”和“hasBorders”屬性來控制對象的邊框和角的可見性。只是將它們設(shè)置為false噩峦。

object.hasBorders = false;
object.hasControls = false;

您還可以通過某些自定義屬性來調(diào)整它的外觀:“cornerDashArray”锭沟,“borderDashArray”,“borderColor”识补,“transparentCorners”“cornerColor”族淮,“cornerStrokeColor”,“cornerStyle”凭涂,“selectionBackgroundColor”祝辣,“padding”和“cornerSize”。

object.set({
  borderColor: 'red',
  cornerColor: 'green',
  cornerSize: 6
});
  object.set({
    transparentCorners: false,
    cornerColor: 'blue',
    cornerStrokeColor: 'red',
    borderColor: 'red',
    cornerSize: 12,
    padding: 10,
    cornerStyle: 'circle',
    borderDashArray: [3, 3]
  });
  

禁用選擇

您可以通過將canvas的“selection”屬性設(shè)置為false來禁用畫布上的對象選擇切油,這可以防止在畫布上選中任何對象蝙斜。如果只需要使某些對象不可選,則可以更改某個對象的“selectable”屬性澎胡,只是將其設(shè)置為false乍炉,并且對象失去其交互性。

自定義選擇

現(xiàn)在滤馍,如果你不想禁用選擇岛琼,而是要改變它的外觀呢?沒問題巢株。

canvas畫布上有4個屬性來控制它的表現(xiàn): "selectionColor", "selectionBorderColor", "selectionLikeWidth", and "selectionDashArray"槐瑞。這些都非常的語義化,讓我們來看一個例子:

canvas.add(new fabric.Circle({ radius: 30, fill: '#f55', top: 100, left: 100 }));

canvas.selectionColor = 'rgba(0,255,0,0.3)';
canvas.selectionBorderColor = 'red';
canvas.selectionLineWidth = 5;

最后一個屬性“selectionDashArray”可不是那么簡單阁苞,他允許我們使用虛線作為選擇線困檩。定義虛線模式的方式是通過數(shù)組指定間隔祠挫。因此,要創(chuàng)建一個模式悼沿,其中有一個大點(diǎn)的數(shù)字等舔,后面跟著一個小一點(diǎn)的數(shù)字來代表虛線的間隔,我們可以使用[10糟趾,5]慌植,作為“selectionDashArray”。這將畫出10px長的線义郑,然后跳過5px蝶柿,再畫一個10px長度的線,以此類推非驮。如果我們使用[2, 4, 6]的數(shù)組交汤,這樣將通過繪制2px長的線,然后跳過4px劫笙,然后繪制6px線芙扎,然后跳過2px,然后繪制4px線填大,然后跳過6px戒洼,以此類推。例如栋盹,這就是[5,10]規(guī)則的樣子:

虛線描邊

與canvas上的“selectionDashArray”類似施逾,所有Fabric對象都有“strokeDashArray”屬性,負(fù)責(zé)在對象上執(zhí)行虛線的描邊操作例获。

var rect = new fabric.Rect({
  fill: '#06538e',
  width: 125,
  height: 125,
  stroke: 'red',
  strokeDashArray: [5, 5]
});
canvas.add(rect);

可點(diǎn)擊區(qū)域

如你所知汉额,所有的Fabric對象都有邊界邊框,用于拖動榨汤、旋轉(zhuǎn)蠕搜、縮放。您可能已經(jīng)注意到收壕,當(dāng)用于控制的角和邊框存在時妓灌,即使在單擊沒有繪制內(nèi)容的對象邊框內(nèi)的空白時也可以拖動該對象。

看看這個圖像:

默認(rèn)情況下蜜宪,畫布上的所有Fabric對象都可以通過邊框拖動虫埂。如果你想要不同的行為,例如根據(jù)Fabric對象的實(shí)際內(nèi)容進(jìn)行點(diǎn)擊或拖拽圃验,您可以在對象上使用“perPixelTargetFind”屬性掉伏。只需將其設(shè)置為true即可獲得所需的行為。

旋轉(zhuǎn)控件

由于版本1.0 Fabric在默認(rèn)情況下使用默認(rèn)UI,對象不能同時縮放和旋轉(zhuǎn)斧散。作為代替的是每個對象都有一個單獨(dú)的旋轉(zhuǎn)控件供常。該控件的相應(yīng)屬性為“hasRotatingPoint”,默認(rèn)是true鸡捐,將其設(shè)置為false可以禁用旋轉(zhuǎn)控制栈暇。您也可以通過“rotatePointOffset”數(shù)字屬性自定義其相對于對象的偏移量。

Fabric對象變形

1.0版以來箍镜,F(xiàn)abric中還提供了許多其他與轉(zhuǎn)換相關(guān)的屬性源祈,其中一個是畫布實(shí)例上的“uniScaleTransform”。默認(rèn)為false鹿寨,可用于啟用對象的非均勻縮放;換句話說新博,它允許在通過角拖動時改變對象的比例薪夕。

有“centeredScaling”和“centeredRotation”屬性(在v1.3.4之前是一個屬性“centerTransform”)脚草。他們指定對象的中心是否應(yīng)該用作轉(zhuǎn)換的起點(diǎn)。當(dāng)它們都設(shè)置為true原献,對象總是從中心縮放/旋轉(zhuǎn)時馏慨,它會和1.0之前的行為相同。由于1.0變形原點(diǎn)是動態(tài)的姑隅,這樣可以在縮放對象時進(jìn)行更精細(xì)的控制写隶。

最后一對新屬性是“originX”和“originY”。默認(rèn)設(shè)置為“l(fā)eft”和“top”讲仰,它們允許以編程的方式更改變形的原點(diǎn)慕趴。當(dāng)你拖動對象的角時,就是這些屬性正在動態(tài)變化鄙陡。

那么什么時候需要我們手動更改它們冕房?舉個例子,當(dāng)我們處理文本對象時趁矾,當(dāng)您動態(tài)的改變文本并且文本框尺寸變大耙册,“originX”和“originY”指出了增長的位置。所以如果你需要文本對象居中時毫捣,你可以將originX設(shè)置為“center”详拙。如果讓文本移到右邊,你需要將“originX”設(shè)置為“right”等等蔓同。這種行為類似于CSS中的“position:absolute”饶辙。

畫布的背景和疊加

從第一部分可以記得,您可以指定一個顏色來填充整個畫布背景斑粱。只需將任意常規(guī)顏色值設(shè)置為canvas的“backgroundColor”屬性弃揽。

canvas.add(new fabric.Circle({ radius: 30, fill: '#f55', top: 100, left: 100 }));
canvas.backgroundColor = 'rgba(0,0,255,0.3)';
canvas.renderAll();

你可以進(jìn)一步去分配圖像作為背景。您需要使用setBackgroundImage方法,傳遞url和一個可選的完成回調(diào)蹋宦。

canvas.add(new fabric.Circle({ radius: 30, fill: '#f55', top: 100, left: 100 }));
canvas.setBackgroundImage('../assets/pug.jpg', canvas.renderAll.bind(canvas));

最后披粟,您還可以設(shè)置疊加圖像,在這種情況下冷冗,它將始終顯示在畫布上呈現(xiàn)的任何對象之上守屉。只需使用setOverlayImage,傳遞url和一個可選的完成回調(diào)蒿辙。

canvas.add(new fabric.Circle({ radius: 30, fill: '#f55', top: 100, left: 100 }));
canvas.setOverlayImage('../assets/jail_cell_bars.png', canvas.renderAll.bind(canvas));

Node.js上的Fabric

Fabric的獨(dú)特之處在于它不僅可以在客戶端拇泛,瀏覽器中也可以在服務(wù)器上工作!當(dāng)您要從客戶端發(fā)送數(shù)據(jù)并在服務(wù)器上直接創(chuàng)建該數(shù)據(jù)的映像時思灌,這可能很有用俺叭。或者如果您為了速度泰偿,方便性或其他原因熄守,只是想從控制臺使用Fabric API。

讓我們來看看如何設(shè)置在Node環(huán)境下運(yùn)行Fabric耗跛。

首先裕照,您需要安裝Node.js,如果還沒有调塌。有幾種方法來安裝Node晋南,具體取決于你的操作系統(tǒng)。您可以按照這些說明這些說明羔砾。

Node安裝成功之后负间,我們需要安裝node-canvas庫,node-canvas是NodeJS的Canvas實(shí)現(xiàn)姜凄。它依賴Cairo- 可以在Mac政溃,Linux或Windows上運(yùn)行的2D圖形庫。node-canvas具有專門的安裝說明檀葛,具體取決于您的操作系統(tǒng)玩祟。

由于Fabric運(yùn)行在Node上,它作為一個NPM包屿聋。所以下一步是安裝NPM空扎。您可以在其github repo中找到安裝說明,不過一般情況下當(dāng)您安裝Node的時候會自動安裝了NPM润讥。

最后一步是安裝Fabric包转锈,使用NPM。這通過運(yùn)行npm install fabric(或npm install -g fabric來全局安裝包)完成楚殿。

我們現(xiàn)在運(yùn)行Node控制臺撮慨,應(yīng)該就使用node-canvas和Fabric了:

> node
...
> typeof require('canvas'); // "function"
> typeof require('fabric'); // "object"

現(xiàn)在一切都準(zhǔn)備好了,我們可以嘗試一個簡單的“helloworld”的測試。讓我們創(chuàng)建一個helloworld.js文件:

var fs = require('fs'),
    fabric = require('fabric').fabric,
    out = fs.createWriteStream(__dirname + '/helloworld.png');

var canvas = fabric.createCanvasForNode(200, 200);
var text = new fabric.Text('Hello world', {
  left: 100,
  top: 100,
  fill: '#f55',
  angle: 15
});
canvas.add(text);

var stream = canvas.createPNGStream();
stream.on('data', function(chunk) {
  out.write(chunk);
});

然后運(yùn)行它作為node helloworld.js砌溺,打開helloworld.png:

那么這里發(fā)生了什么影涉?我們來看看這段代碼的重要部分。

首先规伐,我們引入了Fabricfabric = require('fabric').fabric蟹倾,然后我們用fabric.createCanvasForNode()替代了平時使用的new fabric.Canvas()來創(chuàng)建了Fabric的canvas畫布,此方法將width和height作為參數(shù)猖闪,并創(chuàng)建該大小的畫布(在這種不傳參的情況下為200x200)鲜棠。

然后有熟悉的對象創(chuàng)建(new fabric.Text())和添加到畫布(canvas.add(text))。

到目前做的一切都只是創(chuàng)建了一個Fabric畫布培慌,然后渲染了一個text文本豁陆,現(xiàn)在,如何創(chuàng)建在畫布上呈現(xiàn)的任何圖像吵护?在canvas實(shí)例上使用可用的createPNGStream方法盒音。createPNGStream返回Node的,然后可以使用on('data')輸出到圖像文件中何址,并將其寫入與圖像文件(fs.createWriteStream())對應(yīng)的流中里逆。

fabric.createCanvasForNodecanvas.createPNGStream幾乎是Node特有的唯一2種方法进胯,其他一切都是一樣的用爪。您仍然可以按照通常的方式創(chuàng)建對象,將它們添加到畫布上胁镐,修改偎血,渲染等。值得一提的是盯漂,當(dāng)您通過createCanvasForNode創(chuàng)建畫布時颇玷,它將使用nodeCanvas屬性進(jìn)行擴(kuò)展,該屬性是對原始節(jié)點(diǎn)畫布實(shí)例的引用就缆。

Node服務(wù)器與Fabric

例如帖渠,讓我們創(chuàng)建一個簡單的Node服務(wù)器,它將使用JSON格式的Fabric數(shù)據(jù)收聽傳入的請求竭宰,并輸出該數(shù)據(jù)的圖像空郊。整個腳本只有25行長!

var fabric = require('fabric').fabric,
    http = require('http'),
    url = require('url'),
    PORT = 8124;

var server = http.createServer(function (request, response) {
  var params = url.parse(request.url, true);
  var canvas = fabric.createCanvasForNode(200, 200);

  response.writeHead(200, { 'Content-Type': 'image/png' });

  canvas.loadFromJSON(params.query.data, function() {
    canvas.renderAll();

    var stream = canvas.createPNGStream();
    stream.on('data', function(chunk) {
      response.write(chunk);
    });
    stream.on('end', function() {
      response.end();
    });
  });
});

server.listen(PORT);

此片段中的大部分代碼應(yīng)該已經(jīng)很熟悉了切揭。它的要點(diǎn)在于服務(wù)器響應(yīng)狞甚。我們正在創(chuàng)建Fabric畫布,將JSON數(shù)據(jù)加載到其中廓旬,渲染它哼审,并將最終結(jié)果作為服務(wù)器響應(yīng)進(jìn)行流式傳輸。

要測試它,我們來獲取一個綠色涩盾,并且稍微旋轉(zhuǎn)的矩形:

{"objects":[{"type":"rect","left":103.85,"top":98.85,"width":50,"height":50,"fill":"#9ae759","overlayFill":null,"stroke":null,"strokeWidth":1,"strokeDashArray":null,"scaleX":1.39,"scaleY":1.39,"angle":30,"flipX":false,"flipY":false,"opacity":0.8,"selectable":true,"hasControls":true,"hasBorders":true,"hasRotatingPoint":false,"transparentCorners":true,"perPixelTargetFind":false,"rx":0,"ry":0}],"background":"rgba(0, 0, 0, 0)"}

URL編碼后:

%7B"objects"%3A%5B%7B"type"%3A"rect"%2C"left"%3A103.85%2C"top"%3A98.85%2C"width"%3A50%2C"height"%3A50%2C"fill"%3A"%239ae759"%2C"overlayFill"%3Anull%2C"stroke"%3Anull%2C"strokeWidth"%3A1%2C"strokeDashArray"%3Anull%2C"scaleX"%3A1.39%2C"scaleY"%3A1.39%2C"angle"%3A30%2C"flipX"%3Afalse%2C"flipY"%3Afalse%2C"opacity"%3A0.8%2C"selectable"%3Atrue%2C"hasControls"%3Atrue%2C"hasBorders"%3Atrue%2C"hasRotatingPoint"%3Afalse%2C"transparentCorners"%3Atrue%2C"perPixelTargetFind"%3Afalse%2C"rx"%3A0%2C"ry"%3A0%7D%5D%2C"background"%3A"rgba(0%2C%200%2C%200%2C%200)"%7D

并通過“data”查詢參數(shù)傳遞給服務(wù)器十气。立即回應(yīng)“image / png”的Content-type,如下所示:

正如你所看到的春霍,在服務(wù)器上使用Fabric是非常簡單直接的桦踊。隨意試驗(yàn)這個片段≈粘可以從URL參數(shù)中更改畫布尺寸籍胯,或者在返回圖像作為響應(yīng)之前修改客戶端數(shù)據(jù)。

在Node環(huán)境自定義Fabric的字體

在我們可以在Fabric中使用自定義字體之前离福,我們需要先加載它們杖狼。在瀏覽器(客戶端)中,加載字體的最常用方法是使用CSS3 @font-face規(guī)則妖爷。 在Node(服務(wù)器端)的Fabric中蝶涩,我們可以使用node-canvas的Font API加載字體。

下面的示例演示如何加載和使用自定義字體絮识。將其保存到customfont.js并確保字體文件的路徑正確绿聘。在這個例子中,我們使用Ubuntu作為自定義字體次舌。

var fs = require('fs'),
    fabric = require('fabric').fabric,
    canvas = fabric.createCanvasForNode(300, 250);

var font = new canvas.Font('Ubuntu', __dirname + '/fonts/Ubuntu-Regular.ttf');
font.addFace(__dirname + '/fonts/Ubuntu-Bold.ttf', 'bold');
font.addFace(__dirname + '/fonts/Ubuntu-Italic.ttf', 'normal', 'italic');
font.addFace(__dirname + '/fonts/Ubuntu-BoldItalic.ttf', 'bold', 'italic');

canvas.contextContainer.addFont(font);  // 使用 createPNGStream 或者 createJPEGStream 的時候
canvas.contextTop.addFont(font);        // 使用 toDataURL 或者 toDataURLWithMultiplier的時候

var text = new fabric.Text('regular', {
    left: 150,
    top: 50,
    fontFamily: 'Ubuntu'
});
canvas.add(text);

text = new fabric.Text('bold', {
    left: 150,
    top: 100,
    fontFamily: 'Ubuntu',
    fontWeight: 'bold'
});
canvas.add(text);

text = new fabric.Text('italic', {
    left: 150,
    top: 150,
    fontFamily: 'Ubuntu',
    fontStyle: 'italic'
});
canvas.add(text);

text = new fabric.Text('bold italic', {
    left: 150,
    top: 200,
    fontFamily: 'Ubuntu',
    fontWeight: 'bold',
    fontStyle: 'italic'
});
canvas.add(text);

var out = fs.createWriteStream(__dirname + '/customfont.png');
var stream = canvas.createPNGStream();
stream.on('data', function(chunk) {
    out.write(chunk);
});

運(yùn)行node customfont.js創(chuàng)建一個圖像(customfont.png)熄攘,如下所示:

讓我們仔細(xì)看看發(fā)生了什么。首先彼念,通過將字體名稱和路徑(作為常規(guī)字體文件)作為參數(shù)傳遞挪圾,創(chuàng)建一個字體對象new canvas.Font()。然后通過將字體path逐沙,weight和style作為參數(shù)傳遞哲思,使用font.addFace()添加其他字體。最后吩案,使用canvas.contextContainer.addFont()(當(dāng)使用createPNGStreamcreateJPEGStream時)或canvas.contextTop.addFont()(使用toDataURLtoDataURLWithMultiplier時)可以將字體添加到所需的上下文中棚赔。

現(xiàn)在我們可以通過將fabric.Text對象的fontFamily屬性設(shè)置為字體名稱來使用我們的字體。結(jié)合fontWeightfontStyle屬性徘郭,我們可以應(yīng)用我們添加的字體靠益。有關(guān)這些屬性的更多信息,請參閱第2部分崎岂。請注意捆毫,該示例顯示了如何在創(chuàng)建新文本對象時使用自定義字體,但這也適用于通過JSON加載的文本對象冲甘。

這就到了Fabric的4部分系列的結(jié)尾绩卤。我希望你現(xiàn)在擁有足夠的知識途样,創(chuàng)造有趣,酷濒憋,有用何暇,有趣,具有挑戰(zhàn)性凛驮,令人興奮的東西裆站!

下一章:Fabric.js介紹 第五部分

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市黔夭,隨后出現(xiàn)的幾起案子宏胯,更是在濱河造成了極大的恐慌,老刑警劉巖本姥,帶你破解...
    沈念sama閱讀 217,734評論 6 505
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件肩袍,死亡現(xiàn)場離奇詭異,居然都是意外死亡婚惫,警方通過查閱死者的電腦和手機(jī)氛赐,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,931評論 3 394
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來先舷,“玉大人艰管,你說我怎么就攤上這事〗ǎ” “怎么了牲芋?”我有些...
    開封第一講書人閱讀 164,133評論 0 354
  • 文/不壞的土叔 我叫張陵,是天一觀的道長尔破。 經(jīng)常有香客問我街图,道長,這世上最難降的妖魔是什么懒构? 我笑而不...
    開封第一講書人閱讀 58,532評論 1 293
  • 正文 為了忘掉前任,我火速辦了婚禮耘擂,結(jié)果婚禮上胆剧,老公的妹妹穿的比我還像新娘。我一直安慰自己醉冤,他們只是感情好秩霍,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,585評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著蚁阳,像睡著了一般铃绒。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上螺捐,一...
    開封第一講書人閱讀 51,462評論 1 302
  • 那天颠悬,我揣著相機(jī)與錄音矮燎,去河邊找鬼。 笑死赔癌,一個胖子當(dāng)著我的面吹牛诞外,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播灾票,決...
    沈念sama閱讀 40,262評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼峡谊,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了刊苍?” 一聲冷哼從身側(cè)響起既们,我...
    開封第一講書人閱讀 39,153評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎正什,沒想到半個月后贤壁,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,587評論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡埠忘,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,792評論 3 336
  • 正文 我和宋清朗相戀三年脾拆,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片莹妒。...
    茶點(diǎn)故事閱讀 39,919評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡名船,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出旨怠,到底是詐尸還是另有隱情渠驼,我是刑警寧澤,帶...
    沈念sama閱讀 35,635評論 5 345
  • 正文 年R本政府宣布鉴腻,位于F島的核電站迷扇,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏爽哎。R本人自食惡果不足惜蜓席,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,237評論 3 329
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望课锌。 院中可真熱鬧厨内,春花似錦、人聲如沸渺贤。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,855評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽志鞍。三九已至瞭亮,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間固棚,已是汗流浹背统翩。 一陣腳步聲響...
    開封第一講書人閱讀 32,983評論 1 269
  • 我被黑心中介騙來泰國打工仙蚜, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人唆缴。 一個月前我還...
    沈念sama閱讀 48,048評論 3 370
  • 正文 我出身青樓鳍征,卻偏偏與公主長得像,于是被迫代替她去往敵國和親面徽。 傳聞我的和親對象是個殘疾皇子艳丛,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,864評論 2 354