web-dev-qa-db-ja.com

WebページからZebraプリンターにバーコードを印刷する

WebページからZebraプリンターにバーコードを印刷しようとしています。

おそらく、Webフォントを使用して、プリンタ独自のフォントを使用して印刷する方法があるのか​​、使用されているフォント名を知っているのか疑問に思っています。

私は基本的にバーコードを含む画像を生成するPHPバーコードジェネレータを使用しようとしています。実際、私はすでに数日間、このアプローチを試みていますが、成功していません。

問題は、私がそれらを印刷するとき、それがスキャナーで読めないことです。プリンターの解像度(203dpi)に合わせて画像の解像度を変更しようとしましたが、画像のサイズと形式を試してみましたが、印刷後のバーコードはまだスキャンできません。

だから、これを経験した人はいますか?

プリンター:Zebra TLP 2844

ページごとに必要なバーコード:

  • 01 Code39水平(非常に特定のサイズとブラウザーで印刷された場合のみスキャン可能)
  • 01 Code128垂直(それでも機能しない、印刷は常に非常にぼやけており、スキャンされない)

===========

私は少し進歩しましたが、このプリンターはEPL2言語をサポートしていることがわかったので、それを使用してバーコードを印刷しようとしています。

最初にパススルーモードを有効にする必要がありました。[プリンタオプション]> [詳細設定]> [その他]で有効にしました。

これで、このコマンドを使用して、プリンターの組み込みフォント:Dを使用して、バーコードを完璧に印刷できます。

ZPL:B10,10,0,1,2,2,60、N、 "TEXT-GOES-HERE":ZPL

しかし、私はそれをメモ帳からしか印刷できません、私はまだブラウザからこれを印刷することができません...それはおそらくLF CR + LFに置き換えられている問題です...

この問題を克服する方法は??

===========

私が印刷しようとしているラベルには、実際にはバーコードの前にテキストが少しあり、いくつかのhtmlテーブルがうまくフォーマットされています。そのため、最初にこれを印刷する必要があり、途中でNiceラベルを貼り付けてからテキストを追加する必要があります。

だから私はすべてを印刷するために純粋なEPL2を使用することはできません、私は私の目標を達成するためにhtml + EPL2 + htmlの両方を使用できるかどうか疑問に思っていますか? = /

29
user1447134

いくつかの障害に直面しています:

1)OSがインストールされたプリンタードライバーを使用して印刷する場合、プリンタードライバーは送信されたデータを取得し、出力デバイス(Zebraプリンター)に対して(再)ラスタライズまたはスケーリングしようとします。プリンターは203dpiで比較的低い解像度であるため、バーコードの品質の一部の整合性を失わせるために、プリンタードライバーが行う必要のあるスケーリングに、それほど多くの時間をかけません。これが、直接ZPLコマンドを使用して生成されたバーコードがmuchより信頼できる理由です。

2)クライアントコンピューターへのアクセスを許可しないことによってWebブラウザーが意図的に提供するセキュリティのため、クライアントに接続されたプリンターと直接通信することはできません。このサンドボックス化は、悪意のあるWebサイトがクライアントマシンにファイルを書き込んだり、プリンターなどのデバイスに出力を直接送信したりできないように、ユーザーをマルウェアから保護するのに役立ちます。そのため、ブラウザを介してクライアントに接続されたプリンタにZPLコマンドを直接送信することはできません。

ただし、説明したことを実行する方法があります。通常、必要な手順は、Zebraプリンターに印刷しようとしているサイトにアクセスするクライアントコンピューターをある程度制御できる場合にのみ役立ちます。たとえば、これは会社のネットワーク上のマシン、または作成する必要のある小さなアプリケーションをインストールするクライアントによってのみ使用されます。これを行うには、次の手順を確認する必要があります。

A)独自のカスタムMIMEタイプを作成する必要があります。これは、基本的には、使用する任意の名前であり、 登録済みのMIMEタイプ と衝突することはありません。

B)次に、カスタムMIMEタイプにマップするファイル名拡張子を定義します。これを行うには、通常、Webサーバーを構成して(この手順は使用しているWebサーバーによって異なります)、定義する新しいMIMEタイプとこれらのタイプのファイルに使用されるファイル拡張子を許可する必要があります。

C)次に、WebアプリケーションでZPLデータを出力する場合、新しいMIMEタイプにマップされているファイル名拡張子を使用してファイルに書き込みます。その後、ファイルが生成されたら、そのファイルへのHTMLリンクを提供するか、クライアントブラウザーをファイルにリダイレクトできます。この時点で、作成したファイルをrawプリンターポートに直接手動でコピーすることにより、ファイルが正常に機能しているかどうかをテストできます。

D)次に、クライアントにインストールできる小さなアプリケーションを作成する必要があります。アプリケーションをインストールしたら、カスタムMIMEタイプの有効な消費アプリケーションとして登録する必要があります。ブラウザは、指定されたMIMEタイプのファイルにインストールされたアプリケーションがあることを検出した場合、クライアントマシンの一時ディレクトリにファイルを書き込み、次に、登録された同じMIMEタイプのアプリケーションを次の一時ファイルで起動しようとします。アプリケーションへのパラメーター。したがって、アプリケーションはブラウザから渡されたファイルを読み取り、プリンターに直接ダンプしようとします。

これは、あなたが説明していることを達成するためにあなたがする必要があることの概要です。特定の手順の一部は、使用しているWebサーバーのタイプとクライアントマシンのOSによって異なります。しかし、これはあなたがしようとしていることを成し遂げることができる高レベルの概要です。

20
dmarietta

Javaアプレットをロードすることを検討する場合、qz-print(以前のjzebra)は、説明どおりに正確に機能し、コメントで言及されているLP2844でうまく機能します。

https://code.google.com/p/jzebra/

8

Webアプリで行ったこと:

1)無料のprintfileアプリをダウンロードしてください http://www.lerup.com/printfile/

「PrintFileは、ファイルを高速かつ簡単に印刷できるフリーウェアのMS Windowsユーティリティプログラムです。このプログラムは、プレーンテキスト、PostScript、Encapsulated PostScript(EPS)およびバイナリ形式を認識します。このプログラムを使用すると、貴重な天然資源を節約します。」

初めてPrintFileを実行するときは、詳細オプションに進み、「プリンターに直接送信」を有効にします。

2)WindowsでZEBRAプリンターを汎用テキストプリンターとして設定します。

2)Webアプリで、プレーンテキストEPLファイルであるfile.prtファイルを生成します。

3)ダウンロードしたファイルをダブルクリックすると、バーコードが即座に印刷されます。魅力のように機能します。 GUIが表示されないようにPrintFileをセットアップすることもできます。

4
cmrichards

ここで似たようなものを開発しています。 webappからLP2844で印刷する必要があります。問題は、webappがクラウド(Amazon EC2)のリモートサーバーにあり、プリンターがウェアハウスデスクにあることです。

私の解決策:webappはバーコード付きのラベルに対して EPL2コード を生成し、 PubNubメッセージ を発行します。プリンターが接続されているコンピューターで実行される小さなC#プログラムを作成しました。プログラムはメッセージを受信し、コードをプリンターに送信します。

3
Mario Campa

また、ZPLコマンドをテキストファイルで送信し(1つのファイルに複数のラベルをパックできます)、ユーザーにWindowsのメモ帳でファイルを開いて印刷させることもできます。唯一の注意点は、デフォルトのヘッダーとフッターを削除する必要があることです(ファイル->ページ設定)。

少しのユーザートレーニングですが、クライアントマシンを制御できない場合は受け入れられる場合があります。

2
StingyJack

私は、アプリケーションに基づいて「Tres Finocchiaro」が提案したアイデアに従いました。

  1. ASP.NET 4.0
  2. IIS
  3. Chrome、IExplorer、Firefox
  4. ゼブラTLP 2844
  5. EPLプロトコル

残念ながら、 jzebra は、現在のブラウザのセキュリティの問題のため、正しく機能するためにいくつかの改善が必要です。

Jzebraのインストール

Downlod jzebdraとdistディレクトリからディレクトリにコピーします(例:mydir):

  • ウェブ
    • mydir
      • js
        • ..
        • deployJava.js
      • lib
        • ..
      • qz-print.jar
      • qz-print_jnlp.jnlp

Print.htmlを作成します

<html>
<script type="text/javascript" src="js/deployJava.js"></script>
<script type="text/javascript">
    /**
    * Optionally used to deploy multiple versions of the applet for mixed
    * environments.  Oracle uses document.write(), which puts the applet at the
    * top of the page, bumping all HTML content down.
    */
    deployQZ();

    /** NEW FUNCTION **/
    function initPrinter() {
        findPrinters();
        useDefaultPrinter();
    }

    /** NEW FUNCTION **/    
    function myalert(txt) {
        alert(txt);
    }


    /**
    * Deploys different versions of the applet depending on Java version.
    * Useful for removing warning dialogs for Java 6.  This function is optional
    * however, if used, should replace the <applet> method.  Needed to address 
    * MANIFEST.MF TrustedLibrary=true discrepency between JRE6 and JRE7.
    */
    function deployQZ() {
        var attributes = {id: "qz", code:'qz.PrintApplet.class', 
            archive:'qz-print.jar', width:1, height:1};
        var parameters = {jnlp_href: 'qz-print_jnlp.jnlp', 
            cache_option:'plugin', disable_logging:'false', 
            initial_focus:'false'};
        if (deployJava.versionCheck("1.7+") == true) {}
        else if (deployJava.versionCheck("1.6+") == true) {
            delete parameters['jnlp_href'];
        }
        deployJava.runApplet(attributes, parameters, '1.5');
    }

    /**
    * Automatically gets called when applet has loaded.
    */
    function qzReady() {
        // Setup our global qz object
        window["qz"] = document.getElementById('qz');
        var title = document.getElementById("title");
        if (qz) {
            try {
                title.innerHTML = title.innerHTML + " " + qz.getVersion();
                document.getElementById("content").style.background = "#F0F0F0";
            } catch(err) { // LiveConnect error, display a detailed meesage
                document.getElementById("content").style.background = "#F5A9A9";
                alert("ERROR:  \nThe applet did not load correctly.  Communication to the " + 
                    "applet has failed, likely caused by Java Security Settings.  \n\n" + 
                    "CAUSE:  \nJava 7 update 25 and higher block LiveConnect calls " + 
                    "once Oracle has marked that version as outdated, which " + 
                    "is likely the cause.  \n\nSOLUTION:  \n  1. Update Java to the latest " + 
                    "Java version \n          (or)\n  2. Lower the security " + 
                    "settings from the Java Control Panel.");
          }
      }
    }

    /**
    * Returns whether or not the applet is not ready to print.
    * Displays an alert if not ready.
    */
    function notReady() {
        // If applet is not loaded, display an error
        if (!isLoaded()) {
            return true;
        }
        // If a printer hasn't been selected, display a message.
        else if (!qz.getPrinter()) {
           /** CALL TO NEW FUNCTION **/
            initPrinter();
            return false;
        }
        return false;
    }

    /**
    * Returns is the applet is not loaded properly
    */
    function isLoaded() {
        if (!qz) {
            alert('Error:\n\n\tPrint plugin is NOT loaded!');
            return false;
        } else {
            try {
                if (!qz.isActive()) {
                    alert('Error:\n\n\tPrint plugin is loaded but NOT active!');
                    return false;
                }
            } catch (err) {
                alert('Error:\n\n\tPrint plugin is NOT loaded properly!');
                return false;
            }
        }
        return true;
    }

    /**
    * Automatically gets called when "qz.print()" is finished.
    */
    function qzDonePrinting() {
        // Alert error, if any
        if (qz.getException()) {
            alert('Error printing:\n\n\t' + qz.getException().getLocalizedMessage());
            qz.clearException();
            return; 
        }

        // Alert success message
        alert('Successfully sent print data to "' + qz.getPrinter() + '" queue.');
    }

    /***************************************************************************
    * Prototype function for finding the "default printer" on the system
    * Usage:
    *    qz.findPrinter();
    *    window['qzDoneFinding'] = function() { alert(qz.getPrinter()); };
    ***************************************************************************/
    function useDefaultPrinter() {
        if (isLoaded()) {
            // Searches for default printer
            qz.findPrinter();

            // Automatically gets called when "qz.findPrinter()" is finished.
            window['qzDoneFinding'] = function() {
                // Alert the printer name to user
                var printer = qz.getPrinter();
                myalert(printer !== null ? 'Default printer found: "' + printer + '"':
                    'Default printer ' + 'not found');

                // Remove reference to this function
                window['qzDoneFinding'] = null;
            };
        }
    }

    /***************************************************************************
    * Prototype function for finding the closest match to a printer name.
    * Usage:
    *    qz.findPrinter('zebra');
    *    window['qzDoneFinding'] = function() { alert(qz.getPrinter()); };
    ***************************************************************************/
    function findPrinter(name) {
        // Get printer name from input box
        var p = document.getElementById('printer');
        if (name) {
            p.value = name;
        }

        if (isLoaded()) {
            // Searches for locally installed printer with specified name
            qz.findPrinter(p.value);

            // Automatically gets called when "qz.findPrinter()" is finished.
            window['qzDoneFinding'] = function() {
                var p = document.getElementById('printer');
                var printer = qz.getPrinter();

                // Alert the printer name to user
                alert(printer !== null ? 'Printer found: "' + printer + 
                    '" after searching for "' + p.value + '"' : 'Printer "' + 
                    p.value + '" not found.');

                // Remove reference to this function
                window['qzDoneFinding'] = null;
            };
        }
    }

    /***************************************************************************
    * Prototype function for listing all printers attached to the system
    * Usage:
    *    qz.findPrinter('\\{dummy_text\\}');
    *    window['qzDoneFinding'] = function() { alert(qz.getPrinters()); };
    ***************************************************************************/
    function findPrinters() {
        if (isLoaded()) {
            // Searches for a locally installed printer with a bogus name
            qz.findPrinter('\\{bogus_printer\\}');

            // Automatically gets called when "qz.findPrinter()" is finished.
            window['qzDoneFinding'] = function() {
                // Get the CSV listing of attached printers
                var printers = qz.getPrinters().split(',');
                for (i in printers) {
                    myalert(printers[i] ? printers[i] : 'Unknown');      
                }

                // Remove reference to this function
                window['qzDoneFinding'] = null;
            };
        }
    }

    /***************************************************************************
    * Prototype function for printing raw EPL commands
    * Usage:
    *    qz.append('\nN\nA50,50,0,5,1,1,N,"Hello World!"\n');
    *    qz.print();
    ***************************************************************************/
    function print() {
        if (notReady()) { return; }

        // Send characters/raw commands to qz using "append"
        // This example is for EPL.  Please adapt to your printer language
        // Hint:  Carriage Return = \r, New Line = \n, Escape Double Quotes= \"
        qz.append('\nN\n');            
        qz.append('q609\n');
        qz.append('Q203,26\n');
        qz.append('B5,26,0,1A,3,7,152,B,"1234"\n');
        qz.append('A310,26,0,3,1,1,N,"SKU 00000 MFG 0000"\n');
        qz.append('A310,56,0,3,1,1,N,"QZ PRINT APPLET"\n');
        qz.append('A310,86,0,3,1,1,N,"TEST PRINT SUCCESSFUL"\n');
        qz.append('A310,116,0,3,1,1,N,"FROM SAMPLE.HTML"\n');
        qz.append('A310,146,0,3,1,1,N,"QZINDUSTRIES.COM"');

        // Append the rest of our commands
        qz.append('\nP1,1\n');

        // Tell the applet to print.
        qz.print();
     }

    /***************************************************************************
    * Prototype function for logging a PostScript printer's capabilites to the
    * Java console to expose potentially  new applet features/enhancements. 
    * Warning, this has been known to trigger some PC firewalls
    * when it scans ports for certain printer capabilities.
    * Usage: (identical to appendImage(), but uses html2canvas for png rendering)
    *    qz.setLogPostScriptFeatures(true);
    *    qz.appendHTML("<h1>Hello world!</h1>");
    *    qz.printPS();
    ***************************************************************************/ 
    function logFeatures() {
        if (isLoaded()) {
            var logging = qz.getLogPostScriptFeatures();
            qz.setLogPostScriptFeatures(!logging);
            alert('Logging of PostScript printer capabilities to console set to "' + !logging + '"');
        }
    }

    /***************************************************************************
    ****************************************************************************
    * *                          HELPER FUNCTIONS                             **
    ****************************************************************************
    ***************************************************************************/

    function getPath() {
        var path = window.location.href;
        return path.substring(0, path.lastIndexOf("/")) + "/";
    }

    /**
    * Fixes some html formatting for printing. Only use on text, not on tags!
    * Very important!
    *   1.  HTML ignores white spaces, this fixes that
    *   2.  The right quotation mark breaks PostScript print formatting
    *   3.  The hyphen/dash autoflows and breaks formatting  
    */
    function fixHTML(html) {
        return html.replace(/ /g, "&nbsp;").replace(/’/g, "'").replace(/-/g,"&#8209;"); 
    }

    /**
    * Equivelant of VisualBasic CHR() function
    */
    function chr(i) {
        return String.fromCharCode(i);
    }

    /***************************************************************************
    * Prototype function for allowing the applet to run multiple instances.
    * IE and Firefox may benefit from this setting if using heavy AJAX to
    * rewrite the page.  Use with care;
    * Usage:
    *    qz.allowMultipleInstances(true);
    ***************************************************************************/ 
    function allowMultiple() {
      if (isLoaded()) {
        var multiple = qz.getAllowMultipleInstances();
        qz.allowMultipleInstances(!multiple);
        alert('Allowing of multiple applet instances set to "' + !multiple + '"');
      }
    }
</script>

    <input type="button" onClick="print()" />
    </body>
</html>

提供されるコードは「jzebra_installation/dist/sample.html」に基づいています。

2
venergiac

QZ Tray を使用して、WebページからZebraサーマルプリンターにラベルを印刷します。

の中に demo/js QZトレイのフォルダには、QZトレイアプリケーションと通信するために必要な3つのJavaScriptファイルがあります-dependencies/rsvp-3.1.0.min.jsdependencies/sha-256.min.jsおよびqz-tray.js

これらのJavaScriptファイルを次のようにプロジェクトに含めます。

<script type="text/javascript" src="/lib/qz-tray/rsvp-3.1.0.min.js"></script>
<script type="text/javascript" src="/lib/qz-tray/sha-256.min.js"></script>
<script type="text/javascript" src="/lib/qz-tray/qz-tray.js"></script>

Zebraサーマルプリンターにラベルを印刷する最も簡単な方法を以下に示します。

<script type="text/javascript">
qz.websocket.connect().then(function() {
   // Pass the printer name into the next Promise
   return qz.printers.find("zebra");
}).then(function(printer) {
   // Create a default config for the found printer
   var config = qz.configs.create(printer);

   // Raw ZPL
   var data = ['^XA^FO50,50^ADN,36,20^FDRAW ZPL EXAMPLE^FS^XZ'];

   return qz.print(config, data);
}).catch(function(e) { console.error(e); });
</script>

詳細については、 WebページからZebraサーマルプリンターにラベルを印刷する方法 を参照してください。

2
Gyrocode.com

クライアント側で印刷を制御するWebSocketを作成して、ページからローカルホストにajaxでデータを送信してみてください。

/// websocket
using System;
using System.Net;
using System.Net.WebSockets;
using System.Text;
using System.Threading;

namespace Server
{
    class Program
    {
        public static WebsocketServer ws;
        static void Main(string[] args)
        {
            ws = new Server.WebsocketServer();
            ws.LogMessage += Ws_LogMessage;
            ws.Start("http://localhost:2645/service/");
            Console.WriteLine("Press any key to exit...");
            Console.ReadKey();
        }

        private static void Ws_LogMessage(object sender, WebsocketServer.LogMessageEventArgs e)
        {
            Console.WriteLine(e.Message);
        }
    }

    public class WebsocketServer
    {
        public event OnLogMessage LogMessage;
        public delegate void OnLogMessage(Object sender, LogMessageEventArgs e);
        public class LogMessageEventArgs : EventArgs
        {
            public string Message { get; set; }
            public LogMessageEventArgs(string Message)
            {
                this.Message = Message;
            }
        }

        public bool started = false;
        public async void Start(string httpListenerPrefix)
        {
            HttpListener httpListener = new HttpListener();
            httpListener.Prefixes.Add(httpListenerPrefix);
            httpListener.Start();
            LogMessage(this, new LogMessageEventArgs("Listening..."));
            started = true;

            while (started)
            {
                HttpListenerContext httpListenerContext = await httpListener.GetContextAsync();
                if (httpListenerContext.Request.IsWebSocketRequest)
                {
                    ProcessRequest(httpListenerContext);
                }
                else
                {
                    httpListenerContext.Response.StatusCode = 400;
                    httpListenerContext.Response.Close();
                    LogMessage(this, new LogMessageEventArgs("Closed..."));
                }
            }
        }

        public void Stop()
        {
            started = false;
        }
        private async void ProcessRequest(HttpListenerContext httpListenerContext)
        {
            WebSocketContext webSocketContext = null;

            try
            {
                webSocketContext = await httpListenerContext.AcceptWebSocketAsync(subProtocol: null);
                LogMessage(this, new LogMessageEventArgs("Connected"));
            }
            catch (Exception e)
            {
                httpListenerContext.Response.StatusCode = 500;
                httpListenerContext.Response.Close();
                LogMessage(this, new LogMessageEventArgs(String.Format("Exception: {0}", e)));
                return;
            }

            WebSocket webSocket = webSocketContext.WebSocket;
            try
            {


                while (webSocket.State == WebSocketState.Open)
                {

                    ArraySegment<Byte> buffer = new ArraySegment<byte>(new Byte[8192]);

                    WebSocketReceiveResult result = null;

                    using (var ms = new System.IO.MemoryStream())
                    {
                        do
                        {
                            result = await webSocket.ReceiveAsync(buffer, CancellationToken.None);
                            ms.Write(buffer.Array, buffer.Offset, result.Count);
                        }
                        while (!result.EndOfMessage);

                        ms.Seek(0, System.IO.SeekOrigin.Begin);

                        if (result.MessageType == WebSocketMessageType.Text)
                        {
                            using (var reader = new System.IO.StreamReader(ms, Encoding.UTF8))
                            {
                                var r = System.Text.Encoding.UTF8.GetString(ms.ToArray());
                                var t = Newtonsoft.Json.JsonConvert.DeserializeObject<Datos>(r);
                                bool valid = true;
                                byte[] toBytes = Encoding.UTF8.GetBytes(""); ;

                                if (t != null)
                                {
                                    if (t.printer.Trim() == string.Empty)
                                    {
                                        var printers = "";
                                        foreach (var imp in System.Drawing.Printing.PrinterSettings.InstalledPrinters)
                                        {
                                            printers += imp + "\n";
                                        }

                                        toBytes = Encoding.UTF8.GetBytes("No se Indicó la Impresora\nLas Impresoras disponibles son: " + printers);
                                        valid = false;
                                    }
                                    if (t.name.Trim() == string.Empty)
                                    {
                                        toBytes = Encoding.UTF8.GetBytes("No se Indicó el nombre del Documento");
                                        valid = false;
                                    }
                                    if (t.code == null)
                                    {
                                        toBytes = Encoding.UTF8.GetBytes("No hay datos para enviar a la Impresora");
                                        valid = false;
                                    }


                                    if (valid)
                                    {
                                        print.RawPrinter.SendStringToPrinter(t.printer, t.code, t.name);
                                        toBytes = Encoding.UTF8.GetBytes("Correcto...");
                                    }

                                    await webSocket.SendAsync(new ArraySegment<byte>(toBytes, 0, int.Parse(toBytes.Length.ToString())), WebSocketMessageType.Binary, result.EndOfMessage, CancellationToken.None);
                                }
                                else
                                {
                                    toBytes = Encoding.UTF8.GetBytes("Error...");
                                    await webSocket.SendAsync(new ArraySegment<byte>(toBytes, 0, int.Parse(toBytes.Length.ToString())), WebSocketMessageType.Binary, result.EndOfMessage, CancellationToken.None);
                                }
                            }
                        }
                    }
                }
            }
            catch (Exception e)
            {
                LogMessage(this, new LogMessageEventArgs(String.Format("Exception: {0} \nLinea:{1}", e, e.StackTrace)));
            }
            finally
            {
                if (webSocket != null)
                    webSocket.Dispose();
            }
        }
    }

    public class Datos
    {
        public string name { get; set; }
        public string code { get; set; }
        public string printer { get; set; } = "";
    }
}

生の印刷:

using Microsoft.VisualBasic;
using System;
using System.Collections;
using System.Collections.Generic;
using System.Data;
using System.Diagnostics;
using System.Runtime.InteropServices;
using System.IO;

namespace print
{
    public class RawPrinter
    {
        // Structure and API declarions:
        [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)]
        public class DOCINFOA
        {
            [MarshalAs(UnmanagedType.LPStr)]
            public string pDocName;
            [MarshalAs(UnmanagedType.LPStr)]
            public string pOutputFile;
            [MarshalAs(UnmanagedType.LPStr)]
            public string pDataType;
        }
        [DllImport("winspool.Drv", EntryPoint = "OpenPrinterA", SetLastError = true, CharSet = CharSet.Ansi, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
        public static extern bool OpenPrinter([MarshalAs(UnmanagedType.LPStr)]
string szPrinter, ref IntPtr hPriknter, IntPtr pd);

        [DllImport("winspool.Drv", EntryPoint = "ClosePrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
        public static extern bool ClosePrinter(IntPtr hPrinter);

        [DllImport("winspool.Drv", EntryPoint = "StartDocPrinterA", SetLastError = true, CharSet = CharSet.Ansi, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
        public static extern bool StartDocPrinter(IntPtr hPrinter, Int32 level, [In(), MarshalAs(UnmanagedType.LPStruct)]
DOCINFOA di);

        [DllImport("winspool.Drv", EntryPoint = "EndDocPrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
        public static extern bool EndDocPrinter(IntPtr hPrinter);

        [DllImport("winspool.Drv", EntryPoint = "StartPagePrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
        public static extern bool StartPagePrinter(IntPtr hPrinter);

        [DllImport("winspool.Drv", EntryPoint = "EndPagePrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
        public static extern bool EndPagePrinter(IntPtr hPrinter);

        [DllImport("winspool.Drv", EntryPoint = "WritePrinter", SetLastError = true, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
        public static extern bool WritePrinter(IntPtr hPrinter, IntPtr pBytes, Int32 dwCount, ref Int32 dwWritten);

        // SendBytesToPrinter()
        // When the function is given a printer name and an unmanaged array
        // of bytes, the function sends those bytes to the print queue.
        // Returns true on success, false on failure.
        public static bool SendBytesToPrinter(string szPrinterName, IntPtr pBytes, Int32 dwCount, string DocName = "")
        {
            Int32 dwError = 0;
            Int32 dwWritten = 0;
            IntPtr hPrinter = new IntPtr(0);
            DOCINFOA di = new DOCINFOA();
            bool bSuccess = false;
            // Assume failure unless you specifically succeed.
            di.pDocName = string.IsNullOrEmpty(DocName) ? "My C#.NET RAW Document" : DocName;
            di.pDataType = "RAW";

            // Open the printer.
            if (OpenPrinter(szPrinterName.Normalize(), ref hPrinter, IntPtr.Zero))
            {
                // Start a document.
                if (StartDocPrinter(hPrinter, 1, di))
                {
                    // Start a page.
                    if (StartPagePrinter(hPrinter))
                    {
                        // Write your bytes.
                        bSuccess = WritePrinter(hPrinter, pBytes, dwCount, ref dwWritten);
                        EndPagePrinter(hPrinter);
                    }
                    EndDocPrinter(hPrinter);
                }
                ClosePrinter(hPrinter);
            }
            // If you did not succeed, GetLastError may give more information
            // about why not.
            if (bSuccess == false)
            {
                dwError = Marshal.GetLastWin32Error();
            }
            return bSuccess;
        }

        public static bool SendFileToPrinter(string szPrinterName, string szFileName)
        {
            // Open the file.
            FileStream fs = new FileStream(szFileName, FileMode.Open);
            // Create a BinaryReader on the file.
            BinaryReader br = new BinaryReader(fs);
            // Dim an array of bytes big enough to hold the file's contents.
            Byte[] bytes = new Byte[fs.Length];
            bool bSuccess = false;
            // Your unmanaged pointer.
            IntPtr pUnmanagedBytes = new IntPtr(0);
            int nLength = 0;

            nLength = Convert.ToInt32(fs.Length);
            // Read the contents of the file into the array.
            bytes = br.ReadBytes(nLength);
            // Allocate some unmanaged memory for those bytes.
            pUnmanagedBytes = Marshal.AllocCoTaskMem(nLength);
            // Copy the managed byte array into the unmanaged array.
            Marshal.Copy(bytes, 0, pUnmanagedBytes, nLength);
            // Send the unmanaged bytes to the printer.
            bSuccess = SendBytesToPrinter(szPrinterName, pUnmanagedBytes, nLength);
            // Free the unmanaged memory that you allocated earlier.
            Marshal.FreeCoTaskMem(pUnmanagedBytes);
            return bSuccess;
        }
        public static bool SendStringToPrinter(string szPrinterName, string szString, string DocName = "")
        {
            IntPtr pBytes = default(IntPtr);
            Int32 dwCount = default(Int32);
            // How many characters are in the string?
            dwCount = szString.Length;
            // Assume that the printer is expecting ANSI text, and then convert
            // the string to ANSI text.
            pBytes = Marshal.StringToCoTaskMemAnsi(szString);
            // Send the converted ANSI string to the printer.
            SendBytesToPrinter(szPrinterName, pBytes, dwCount, DocName);
            Marshal.FreeCoTaskMem(pBytes);
            return true;
        }
    }
}

htmlページ:

<!DOCTYPE html>
<html>

<head>
</head>

<body ng-app="myapp">

    <div ng-controller="try as ctl">
        <input ng-model="ctl.ticket.nombre">

        <textarea ng-model="ctl.ticket.code"></textarea>

        <button ng-click="ctl.send()">Enviar</button>
    </div>


    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.6/angular.min.js"></script>
    <script>
        var ws = new WebSocket("ws://localhost:2645/service");
        ws.binaryType = "arraybuffer";
        ws.onopen = function () {
            console.log('connection is opened!!!');
        };

        ws.onmessage = function (evt) {
            console.log(arrayBufferToString(evt.data))

        };

        ws.onclose = function () {
            console.log("Connection is Closed...")
        };

        function arrayBufferToString(buffer) {
            var arr = new Uint8Array(buffer);
            var str = String.fromCharCode.apply(String, arr); 

           return  decodeURIComponent(escape(str));
        }
        var app = angular.module('myapp', []);
        app.controller('try', function () {
            this.ticket= {nombre:'', estado:''}

            this.send = () => {
                var toSend= JSON.stringify(this.ticket);
                ws.send(toSend);
            }
        });
    </script>
</body>

</html>

次に、htmlからZPLコードを送信します(これをtextareaコードに書き込みます)。

^XA
^FO200,50^BY2^B3N,N,80,Y,N^FD0123456789^FS
^PQ1^XZ
0
henoc salinas