2017-05-05 6 views
0

HTMLキャンバスを使用する共有コード(サーバーとクライアントの両方で実行される)を作成しようとしています。サーバーとクライアントの両方で共有コードにキャンバスインターフェイスを表示する

クライアントでは、これは完全に正常に動作するはずです。サーバーでは、Nodeにキャンバス(またはDOM)がないため、ノードキャンバスのプラグインを使用したいと考えています。https://github.com/Automattic/node-canvas

しかし、私はwebpackにノードキャンバスをクライアントサイドのコード(webpackをクラッシュさせる)にバンドルしようとしないアクセス方法を試すことができません。ノードキャンバスをロードする方法はありますか?ブラウザで使用するのと同じコードで参照でき、Webpackのクラッシュをひどくしないでください。動作しませんでした


私の現在の努力、:

canvas.server.js

import Canvas from 'canvas'; 

const createCanvas = (width, height) => new Canvas(width, height); 

export default createCanvas; 

canvas.client.js

const createCanvas = (width, height) => { 
    const canvas = document.createElement('canvas'); 
    canvas.width = width; 
    canvas.height = height; 

    return canvas; 
}; 

export default createCanvas; 

canvas.js

let createCanvas; 

if (typeof document === 'undefined') { 
    // SERVER/node 
    createCanvas = require('./canvas.server.js'); 
} else { 
    // BROWSER 
    createCanvas = require('./canvas.client.js'); 
} 

export default createCanvas; 
使用中の

import createCanvas from './canvas'; 

const canvasElement = createCanvas(width, height); 
const ctx = canvasElement.getContext('2d'); 

は残念ながら、WebPACKのは、まだノードキャンバスにバンドルされています。

+0

サーバーとクライアントの両方で、キャンバスはその内容をデータURLにダンプします。データURLは、ページ上でとしてSVG内にレンダリングされます。これはすべて非常にハッキーで奇妙なことですが、とにかく動作しないでしょうが、試してみたいと思います。これは私が立ち往生しているステップです。 – futuraprime

+0

レンダリングされた同じキャンバスの2つの同一のコピーが必要な理由を理解できません。抽象化されたキャンバスのコピーをサーバーに保存しておき、イメージが必要になると(他のクライアント)、抽象的なイメージを送信して各クライアントにイメージをレンダリングさせます。すべてのnode.js canvas APIはソフトウェアレンダリングとSLOWです。サーバーが非常に迅速にシャッフルして、クライアントがGPU経由で簡単に処理できるようになります。 – Blindman67

+0

私はサーバープロセスがありません。キャンバスは、アプリケーション全体がフラットファイルに縮小されたビルド時に一度だけレンダリングされ、ユーザーが最初のビューから離れたときにクライアント上に再作成されます。 – futuraprime

答えて

0

node-canvaswhen the code is running in nodeを試しましたか?

実際にフロントエンドコードでrequireを呼び出さない場合、webpackはバンドルしません。これは、ファイルの先頭ではなく、前述の条件文の中に実際のrequireを呼び出すことを意味します。これは重要。また、node-canvasをwebpackのエントリポイントにしていないことを確認してください。

例:

// let's assume there is `isNode` variable as described in linked answer 
let canvas; 
if (isNode) { 
    const Canvas = require('canvas'); 
    canvas = new Canvas(x, y); 
else { 
    canvas = document.getElementById('canvas'); 
} 
// get canvas context and draw on it 

編集OPは、コード例を提供した後:

私は前述したように、これは働くべきであることを証明するためにthis WebpackBinで正確な構造を再現しました。結局のところ、これはcommon.js(およびその他のモジュールローダ)の機能であり、webpackでサポートされています。コードへ

マイ変化:(require(...).defaultする必要があります)export defaultrequireの固定間違った使用

  • その行で呼ばれるであろうもののconsole.logcanvas.client.jscanvas.server.jsでコードを置き換え

    1. 。無関係ですが、コードを動作させるためにはそれを行わなければなりませんでした。
    2. canvasElement.getContexコールを削除しました。サンプルコードではうまくいかず、とにかく無関係なので、それを嘲笑する必要はありません。
  • +0

    私はこれを試しました。 Webpackはそれをとにかくバンドルします。 – futuraprime

    +0

    @futuraprime私はちょうど私の答えを更新し、例を追加しました。このようにしましたか?また、 'node-canvas'がwebpackのエントリポイントではないことを確認して、そのパーツに注意してください。ベンダーファイルにバンドルされます。私はあなたがそれをこのようにすれば、ウェブパックはそれを束ねてはならないと確信しています。もしそうなら、あなたは私が提案した方法で何かをやっていません。 –

    +0

    現在の質問を質問に追加しました。これは、同じことをするよりラウンドアバウトな方法だと思います(これは、私がここで見た他のいくつかの回答に基づいていますが、ほとんどの人はどちらもうまくいきませんでした)。私のwebpackの設定には2つのエントリーポイント、index.jsとreact-hot-loaderしかありません。 – futuraprime

    関連する問題