JRT和检验共用的打印层实现

之前对接的打印和导出是C#实现的,如果要完全Java化就需要用Java把打印元素绘制协议用Java实现,这次介绍实现主体搭建,最终使JRT达到完全信创和跨平台目标。到这篇后,所有的Java难题都解决完毕,几天到几周之内就可以把打印元素绘制协议完全实现,实现看着很快。至此可以一马平川的用Java了,没有M,一样可以领先,哈哈哈哈,框架完全体快出来了。

首先抽取消息处理接口

package Monitor.Msg;

import org.java_websocket.WebSocket;

/**
 * 抽取的处理前端传来的消息接口,不同类型的消息处理实现此接口从而实现不同的功能
 */
public interface IMessageDeal {
    /**
     * 处理消息
     * @param socket 套接字,可以获得id,发送消息给socket
     * @param message 约定#分割的第一位描述消息类型,收到的消息内容
     * @return 是否继续往后传递消息,true是,false否
     */
    public boolean DealMessage(WebSocket socket, String message);
}

然后实现打印消息处理

package Monitor.Msg;
import Monitor.Util.LogUtils;
import javafx.scene.control.Alert;
import org.java_websocket.WebSocket;

/**
 * 处理打印消息
 */
public class MessagePrintDeal implements Monitor.Msg.IMessageDeal {
    /**
     * 处理消息
     * @param socket 套接字,可以获得id,发送消息给socket
     * @param message 约定#分割的第一位描述消息类型,收到的消息内容
     * @return 是否继续往后传递消息,true是,false否
     */
    public boolean DealMessage(WebSocket socket, String message)
    {
        LogUtils.WriteDebugLog("识别以print#开头的消息");
        //识别打印消息
        if (message.split("#")[0].equals("print"))
        {
            LogUtils.WriteDebugLog("确定为打印消息,准备处理");
            int index = message.indexOf('#');
            String msg = message.substring(index + 1);
            String[] arrMsg = msg.split("@");

            //报告打印消息直接处理,不驱动exe,提高速度
            if (arrMsg.length > 5 && (!arrMsg[4].contains("PDF#")) && (arrMsg[0].equals("iMedicalLIS://0") || arrMsg[0].equals("iMedicalLIS://1")) && (!arrMsg[4].equals("ReportView")))
            {
                String cmdLine = msg.substring(14);
                String[] tmpStrings = cmdLine.split((char)64+"");
                String printFlag = tmpStrings[0];
                String connectString = tmpStrings[1].replace("&", "&");
                String rowids = tmpStrings[2];
                String userCode = tmpStrings[3];
                //PrintOut:打印  PrintPreview打印预览
                String printType = tmpStrings[4];
                //参数模块名称(LIS工作站,DOC医生,SELF自助,OTH其它)
                String paramList = tmpStrings[5];

                String clsName = "";
                String funName = "";
                if (tmpStrings.length >= 8)
                {
                    clsName = tmpStrings[6];
                    funName = tmpStrings[7];
                }

                //没传报告主键退出
                if (rowids == "" && printType != "ReportView")
                {
                    javafx.application.Platform.runLater(()->{

                        Alert alert = new Alert(Alert.AlertType.INFORMATION);
                        alert.setTitle("提示");
                        alert.setHeaderText("打印参数异常");
                        alert.setContentText("未传入报告主键");
                        alert.showAndWait();
                    });
                    return true;
                };
                String ip = "";
                String hostName = "";
                String mac = "";
                paramList = paramList + "^HN" + hostName + "^IP" + ip + "^MAC" + mac;
                //printFlag  0:打印所有报告 1:循环打印每一份报告
                if (printFlag.substring(0, 1).equals("0"))
                {
                    Monitor.Print.PrintProtocol reportPrint = new Monitor.Print.PrintProtocol(rowids, userCode, paramList, connectString, printType, clsName, funName);
                }
                else
                {
                    String[] tmpRowids = rowids.split((char)94+"");
                    for (int i = 0; i < tmpRowids.length; i++)
                    {
                        rowids = tmpRowids[i];
                        if (rowids != "")
                        {
                            Monitor.Print.PrintProtocol reportPrint = new Monitor.Print.PrintProtocol(rowids, userCode, paramList, connectString, printType, clsName, funName);
                        }
                    }
                }
            }
            return false;
        }
        LogUtils.WriteDebugLog("不是打印消息,传递消息链");
        return true;
    }
}

然后实现Websockt对接消息、

package Monitor.Websocket;

import Monitor.Util.LogUtils;
import org.java_websocket.WebSocket;
import org.java_websocket.handshake.ClientHandshake;
import org.java_websocket.server.WebSocketServer;
import Monitor.Msg.IMessageDeal;

import java.net.InetSocketAddress;
import java.util.ArrayList;
import java.util.List;

public class WebsocketServer extends WebSocketServer {
    /**
     * 存所有套接字
     */
    private static List<WebSocket> allSockets = new ArrayList<>();

    /**
     * 处理消息链对象
     */
    public List<IMessageDeal> LinkList=new ArrayList<>();

    /**
     * 构造函数
     * @param port
     */
    public WebsocketServer(int port) {
        super(new InetSocketAddress(port));
        Monitor.Util.LogUtils.WriteDebugLog("启动Websockt在"+port);
    }

    /**
     * 打开链接
     * @param conn 连接
     * @param handshake 握手
     */
    @Override
    public void onOpen(WebSocket conn, ClientHandshake handshake) {
        LogUtils.WriteDebugLog("新客户端接入:" + conn.getRemoteSocketAddress());
        allSockets.add(conn);
    }

    /**
     * 断开连接
     * @param conn 连接
     * @param code 代码
     * @param reason 原因
     * @param remote 是否远程
     */
    @Override
    public void onClose(WebSocket conn, int code, String reason, boolean remote) {
        LogUtils.WriteDebugLog("客户端断开:" + conn.getRemoteSocketAddress());
        allSockets.remove(conn);
    }

    /**
     * 收到消息
     * @param conn 连接
     * @param message 消息
     */
    @Override
    public void onMessage(WebSocket conn, String message) {
        System.out.println("收到消息:" + conn.getRemoteSocketAddress() + ": " + message);
        LogUtils.WriteDebugLog("#WS消息服务准备调用消息链...");
        try
        {
            if (LinkList.size() > 0)
            {
                for(IMessageDeal deal:LinkList)
                {
                    LogUtils.WriteDebugLog("#WS调用:" + deal.getClass().getName() + "...");
                    boolean ret = deal.DealMessage(conn, message);
                    LogUtils.WriteDebugLog("#WS调用:" + deal.getClass().getName() + "结束...");
                    //返回false不传递消息了
                    if (ret == false)
                    {
                        LogUtils.WriteDebugLog("#WS消息链不继续传递消息...");
                        break;
                    }
                }
            }
            LogUtils.WriteDebugLog("#WS消息服务调用消息链结束...");
        }
        catch (Exception ex)
        {
            LogUtils.WriteExceptionLog("#WS消息服务调用消息链异常", ex);
        }
    }

    /**
     * 发生错误
     * @param conn 连接
     * @param ex 异常
     */
    @Override
    public void onError(WebSocket conn, Exception ex) {
        LogUtils.WriteExceptionLog("发生错误:" + conn.getRemoteSocketAddress(),ex);
    }

    /**
     * 启动事件
     */
    @Override
    public void onStart() {

    }

}

包装log4j

package Monitor.Util;


import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class LogUtils {

    //调试日志
    static final Logger loggerDebug = LoggerFactory.getLogger("Debug");


    /**
     * 书写调试日志
     * @param message 日志内容
     */
    public static void WriteDebugLog(String message)
    {
        loggerDebug.error(message);
    }

    /**
     * 书写异常日志
     * @param message 描述
     * @param exception 异常
     */
    public static void WriteExceptionLog(String message, Exception exception)
    {
        loggerDebug.error(message, exception);
    }

}

实现exe程序

package Monitor;

import javafx.application.Application;
import javafx.fxml.FXMLLoader;
import javafx.geometry.Insets;
import javafx.geometry.Orientation;
import javafx.scene.Parent;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.control.Label;
import javafx.scene.control.SplitPane;
import javafx.scene.control.TextArea;
import javafx.scene.layout.HBox;
import javafx.scene.layout.VBox;
import javafx.stage.Stage;
import Monitor.Websocket.WebsocketServer;
import Monitor.Msg.MessagePrintDeal;

import java.net.URL;
import java.nio.file.Paths;

public class Main extends Application {

    // 创建一个TextArea控件
    TextArea textInfo = new TextArea();

    //日志路径
    String logPath="";

    @Override
    public void start(Stage primaryStage) throws Exception{
        String projectPath = System.getProperty("user.dir");
        Monitor.Util.LogUtils.WriteDebugLog("项目路径:" + projectPath);
        URL url = Main.class.getResource("");
        String bashPath = url.getPath();
        Monitor.Util.LogUtils.WriteDebugLog("程序路径:"+bashPath);
        //日志路径
        logPath= Paths.get(projectPath,"logs","Debug.log").toString();


        // 设置文本自动换行
        textInfo.setWrapText(true);

        Monitor.Util.LogUtils.WriteDebugLog("启动Websockt");
        WebsocketServer server=new WebsocketServer(8082);
        MessagePrintDeal printDeal=new MessagePrintDeal();
        server.LinkList.add(printDeal);
        server.start();

        SplitPane splitPane = new SplitPane();
        splitPane.setOrientation(Orientation.VERTICAL);

        // 刷新日志按钮
        Button btnRefresh = new Button("刷新日志");
        btnRefresh.setOnMouseClicked(e -> {
            RefreshLogs();
        });
        btnRefresh.setPrefHeight(30);

        // 清空日志按钮
        Button btnDelete = new Button("清空日志");
        btnDelete.setOnMouseClicked(e -> {
            DeleteLogs();
        });
        btnDelete.setPrefHeight(30);


        HBox top  = new HBox(20,btnRefresh,btnDelete);
        top.setPadding(new Insets(5,5,5,5));
        top.setPrefHeight(40);
        top.setMaxHeight(40);

        HBox bottom = new HBox(textInfo);
        textInfo.prefWidthProperty().bind(bottom.widthProperty());
        RefreshLogs();
        //VBox left = new VBox(new Label("left"));
        //VBox center = new VBox(new Label("center"));
        //VBox right = new VBox(new Label("right"));
        //SplitPane splitPane1 = new SplitPane();
        //splitPane1.getItems().setAll(left,center,right);

        splitPane.getItems().addAll(top, bottom);
        Scene scene = new Scene(splitPane);
        //primaryStage.setScene(scene);

        //Parent root = FXMLLoader.load(getClass().getResource("Main.fxml"));
        //primaryStage.setTitle("JRTClient");
        primaryStage.setOnCloseRequest(event -> {
            try {
                server.stop();
            }
            catch (Exception ex)
            {

            }
        });
        primaryStage.setScene(scene);
        primaryStage.setMaximized(true);
        primaryStage.show();

    }

    /**
     * 刷新日志
     */
    public void RefreshLogs()
    {
        try {
            textInfo.setText(Monitor.Util.TxtUtil.ReadTextStr(logPath));
        }
        catch (Exception ex)
        {
        }
    }

    /**
     * 清空日志
     */
    public void DeleteLogs()
    {
        try {
            Monitor.Util.TxtUtil.WriteText2File(logPath,"");
            textInfo.setText("");
        }
        catch (Exception ex)
        {
        }
    }


    public static void main(String[] args) {
        launch(args);
    }
}

实现打印画图类

package Monitor.Print;

import java.awt.*;
import java.awt.print.*;

public class PrintProtocol implements Printable {
    /**
     * 按打印元素绘制协议实现打印
     * @param rowids 数据主键
     * @param userCode 用户
     * @param paramList 参数
     * @param connectString 连接串
     * @param printFlag 打印标识
     * @param className 调用类名
     * @param funcName 方法名称
     */
    public PrintProtocol(String rowids, String userCode, String paramList, String connectString, String printFlag, String className, String funcName){
        try {
            // 通俗理解就是书、文档
            Book book = new Book();
            // 设置成竖打
            PageFormat pf = new PageFormat();
            pf.setOrientation(PageFormat.PORTRAIT);

            // 通过Paper设置页面的空白边距和可打印区域。必须与实际打印纸张大小相符。
            Paper paper = new Paper();
            // 设置纸张大小为 A4 大小(210 mm × 297 mm)
            double width = 827;
            double height = 1169;
            double margin = 10.0;
            paper.setSize(width, height);
            paper.setImageableArea(margin, margin, width - 2 * margin, height - 2 * margin);
            pf.setPaper(paper);
            book.append(this, pf,2);

            // 获取打印服务对象
            PrinterJob job = PrinterJob.getPrinterJob();
            // 设置打印类
            job.setPageable(book);
            job.print();
        } catch (PrinterException e) {
            e.printStackTrace();
        }
    }

    /**
     * 安逸画图
     * @param graphics
     * @param pageFormat
     * @param pageIndex
     * @return
     * @throws PrinterException
     */
    @Override
    public int print(Graphics graphics, PageFormat pageFormat, int pageIndex) throws PrinterException {
        // 转换成Graphics2D 拿到画笔
        Graphics2D g2 = (Graphics2D) graphics;
        // 设置打印颜色为黑色
        g2.setColor(Color.black);

        //打印起点坐标
        double x = pageFormat.getImageableX();
        double y = pageFormat.getImageableY();
        if(pageIndex==0) {
            //设置打印字体(字体名称、样式和点大小)(字体名称可以是物理或者逻辑名称)
            Font font = new Font("宋体", Font.BOLD, 14);
            // 设置字体
            g2.setFont(font);
            //字体高度
            float heigth = font.getSize2D();
            g2.drawString("Java打印测试", (float) 10, 10);
            font = new Font("宋体", Font.BOLD, 12);
            // 设置字体
            g2.setFont(font);
            // 字体高度
            heigth = font.getSize2D();
            g2.drawString("张联珠", (float) 10, 60);
            g2.drawString("1890075****", (float) 10, 90);
            g2.drawString("张联珠", 10, 120);
            g2.drawString("0947809", 120, 120);

            font = new Font("宋体", Font.BOLD, 12);
            g2.setFont(font);
            heigth = font.getSize2D();
            g2.drawString("湖南长沙", 10, 150);
            g2.drawString("pageIndex:" + pageIndex, 10, 180);
            return PAGE_EXISTS;
        }
        else if(pageIndex==1) {
            //设置打印字体(字体名称、样式和点大小)(字体名称可以是物理或者逻辑名称)
            Font font = new Font("宋体", Font.BOLD, 14);
            // 设置字体
            g2.setFont(font);
            //字体高度
            float heigth = font.getSize2D();
            g2.drawString("Java打印测试", (float) 10, 10);
            font = new Font("宋体", Font.BOLD, 12);
            // 设置字体
            g2.setFont(font);
            // 字体高度
            heigth = font.getSize2D();
            g2.drawString("张联珠", (float) 10, 60);
            g2.drawString("18900752521", (float) 10, 90);
            g2.drawString("张联珠", 10, 120);
            g2.drawString("0947809", 120, 120);

            font = new Font("宋体", Font.BOLD, 12);
            g2.setFont(font);
            heigth = font.getSize2D();
            g2.drawString("湖南长沙", 10, 150);
            g2.drawString("第2页" , 10, 180);
            return PAGE_EXISTS;
        }
        else
        {
            return NO_SUCH_PAGE;
        }

    }
}

测试
在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

  • 8
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

小乌鱼

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值