package open.dolphin.client; import java.awt.BorderLayout; import java.awt.Frame; import java.awt.Point; import java.awt.event.ActionEvent; import java.beans.PropertyChangeEvent; import java.beans.PropertyChangeListener; import java.text.MessageFormat; import java.text.SimpleDateFormat; import java.util.*; import java.util.concurrent.ExecutionException; import javax.swing.*; import open.dolphin.delegater.MasudaDelegater; import open.dolphin.delegater.OrcaDelegater; import open.dolphin.delegater.OrcaDelegaterFactory; import open.dolphin.helper.ComponentMemory; import open.dolphin.helper.InfiniteProgressBar; import open.dolphin.infomodel.*; import open.dolphin.util.StringTool; /** * 薬剤併用チェックを行うためのパネル * * @author masuda, Masuda Naika */ public class CheckInteractionPanel { private Chart context; private JDialog dialog; private long karteId; private HashMap<String, String[]> rirekiItems; // カルテに記録されている薬剤 private HashMap<String, String> kensakuItems; // 検索にマッチした薬剤 private static final String yakuzaiClassCode = "2"; // 薬剤のclaim class code private static final int searchPeriod = 3; private BlockGlass blockGlass; private JButton btn_Exit; private JButton btn_Search; private JLabel lbl_Info; private JLabel lbl_Past_count; private JLabel lbl_Name; private JLabel lbl_Result; private JTextField keywordFld; private JTextArea resultArea; private JPanel view; private InfiniteProgressBar progressBar; public CheckInteractionPanel() { initComponents(); } public void enter(Chart chart) { context = chart; karteId = context.getKarte().getId(); final SwingWorker worker = new SwingWorker<Void, Void>() { @Override protected Void doInBackground() throws Exception { collectMedicine(); return null; } @Override protected void done() { try { get(); progressBar.stop(); progressBar = null; showDialog(); } catch (InterruptedException | ExecutionException ex) { ex.printStackTrace(System.err); } } }; worker.addPropertyChangeListener(new PropertyChangeListener() { @Override public void propertyChange(PropertyChangeEvent e) { if (e.getNewValue()==SwingWorker.StateValue.STARTED) { progressBar = new InfiniteProgressBar(ClientContext.getMyBundle(CheckInteractionPanel.class).getString("message.progress.checkInteraction"), ClientContext.getMyBundle(CheckInteractionPanel.class).getString("note.progress.fetchingRPHistory"), context.getFrame()); progressBar.start(); } else if (e.getNewValue()==SwingWorker.StateValue.DONE) { worker.removePropertyChangeListener(this); } } }); worker.execute(); } private void showDialog(){ java.util.ResourceBundle bundle = ClientContext.getMyBundle(CheckInteractionPanel.class); if (rirekiItems!=null) { int cnt = rirekiItems.size(); StringBuilder sb = new StringBuilder(); sb.append(bundle.getString("totalKindsOfMedication")).append(cnt); lbl_Past_count.setText(sb.toString()); } dialog = new JDialog((Frame)context.getFrame(), true); dialog.setContentPane(view); blockGlass = new BlockGlass(); dialog.setGlassPane(blockGlass); blockGlass.setSize(dialog.getSize()); // dialogのタイトルを設定 StringBuilder sb = new StringBuilder(); sb.append(context.getPatient().getFullName()); sb.append("("); sb.append(context.getPatient().getKanaName()); sb.append(") : "); sb.append(context.getPatient().getPatientId()); sb.append(bundle.getString("contraindicationsSearch")); dialog.setTitle(ClientContext.getFrameTitle(sb.toString())); dialog.pack(); ComponentMemory cm = new ComponentMemory(dialog, new Point(100, 100), dialog.getPreferredSize(), CheckInteractionPanel.this); cm.setToPreferenceBounds(); dialog.setVisible(true); } private void collectMedicine() { rirekiItems = new HashMap<>(); // 過去3ヶ月の薬剤・注射ののModuleModelを取得する MasudaDelegater del = MasudaDelegater.getInstance(); List<String> entities = new ArrayList<>(); entities.add(IInfoModel.ENTITY_MED_ORDER); entities.add(IInfoModel.ENTITY_INJECTION_ORDER); GregorianCalendar gcTo = new GregorianCalendar(); gcTo.add(GregorianCalendar.DAY_OF_MONTH,1); Date toDate = gcTo.getTime(); GregorianCalendar gcFrom = new GregorianCalendar(); gcFrom.add(GregorianCalendar.MONTH, -searchPeriod); Date fromDate = gcFrom.getTime(); List<ModuleModel> pastModuleList = del.getModulesEntitySearch(karteId, fromDate, toDate, entities); if (pastModuleList == null) { return; } // ModuleModelの薬剤を取得 for (ModuleModel mm : pastModuleList) { ClaimBundle cb = (ClaimBundle) mm.getModel(); for (ClaimItem ci : cb.getClaimItem()) { if (yakuzaiClassCode.equals(ci.getClassCode())) { // 用法などじゃなくて薬剤なら、薬剤リストに追加 final SimpleDateFormat frmt = new SimpleDateFormat("yyyy-MM-dd"); String code = ci.getCode(); // コード String name = ci.getName(); // 薬剤名 String date = frmt.format(mm.getStarted()); // 処方日 rirekiItems.put(code, new String[]{name, date}); } } } } private void closePanel() { dialog.setVisible(false); dialog.dispose(); } private void search() { final SwingWorker worker = new SwingWorker() { @Override protected Object doInBackground() throws Exception { blockGlass.block(); searchTask(); return null; } @Override protected void done() { try { get(); blockGlass.unblock(); } catch (InterruptedException | ExecutionException ex) { } } }; worker.execute(); } private void searchTask() { final int minKeywordLength = 3; // キーワードの最短文字数制限 // 空白だったらそのままリターン final String targetName = StringTool.hiraganaToKatakana(keywordFld.getText()); if ("".equals(targetName)) { resultArea.setText(""); return; } java.util.ResourceBundle bundle = ClientContext.getMyBundle(CheckInteractionPanel.class); // キーワードが短すぎるなら if (targetName.length() < minKeywordLength) { String fmt = bundle.getString("meesageFormat.medicineNameLength"); String msg = new MessageFormat(fmt).format(new Object[]{minKeywordLength}); resultArea.setText(msg); return; } // 処方履歴がなかったら if (rirekiItems.isEmpty()) { resultArea.setText(bundle.getString("noHistory")); return; } StringBuilder sb = new StringBuilder(); kensakuItems = new HashMap<>(); // ORCAでキーワードに当てはまる薬剤を取得する。 SimpleDateFormat effectiveFormat = new SimpleDateFormat("yyyyMMdd"); String d = effectiveFormat.format(new Date()); //SqlMasterDao daoMaster = SqlMasterDao.getInstance(); OrcaDelegater daoMaster = OrcaDelegaterFactory.create(); List<TensuMaster> medicineEntries = null; try { medicineEntries = daoMaster.getTensuMasterByName(targetName, d, false); } catch (Exception e) { } // 検索薬剤がなかったら if (medicineEntries==null || medicineEntries.isEmpty()) { resultArea.setText(bundle.getString("cannotFindTargetMedicine")); return; } // 検索対象のコードと薬剤名を記録する for (TensuMaster me : medicineEntries) { kensakuItems.put(me.getSrycd(), me.getName()); } // 検索する薬剤コードと名前の配列を用意する Collection<String> codes1 = kensakuItems.keySet(); // 過去処方薬のコードの配列を用意する。 Collection<String> codes2 = rirekiItems.keySet(); // データベースで検索する。まとめてSQLをなげる OrcaDelegater odl = OrcaDelegaterFactory.create(); List<DrugInteractionModel> list = null; try { list = odl.checkInteraction(codes1, codes2); } catch (Exception e) { } // 結果の処理 if (list != null && !list.isEmpty()) { for (DrugInteractionModel model : list){ sb.append(kensakuItems.get(model.getSrycd1())); sb.append(bundle.getString("text.and")); String[] data = rirekiItems.get(model.getSrycd2()); sb.append(data[0]); sb.append(" ("); sb.append(data[1]); sb.append(")\n"); sb.append(model.getSskijo()); sb.append(" "); sb.append(model.getSyojyoucd()); sb.append("\n"); } } if (sb.length() == 0) { sb.append(bundle.getString("targetMedicineToSearch")); for (String str : kensakuItems.values()) { sb.append(str); sb.append("\n"); } sb.append(bundle.getString("CouldnotFindTheInteractionData")); } resultArea.setText(sb.toString()); } private void initComponents() { java.util.ResourceBundle bundle = ClientContext.getMyBundle(CheckInteractionPanel.class); lbl_Info = new JLabel(bundle.getString("checkPast3monthOfMedicationANdContradication")); lbl_Past_count = new JLabel(bundle.getString("numMedications")); lbl_Name = new JLabel(bundle.getString("medicineName")); lbl_Result = new JLabel(bundle.getString("results")); keywordFld = new JTextField(); btn_Exit = new JButton(bundle.getString("quit")); btn_Search = new JButton(bundle.getString("search")); resultArea = new JTextArea(); JScrollPane scroll = new JScrollPane(resultArea); view = new JPanel(); view.setLayout(new BorderLayout()); JPanel north = new JPanel(); north.setLayout(new BoxLayout(north, BoxLayout.Y_AXIS)); north.add(Box.createVerticalStrut(5)); lbl_Info.setAlignmentX(JComponent.LEFT_ALIGNMENT); JPanel panel = new JPanel(); panel.setLayout(new BoxLayout(panel, BoxLayout.X_AXIS)); panel.add(lbl_Info); panel.add(Box.createHorizontalGlue()); panel.add(lbl_Past_count); north.add(panel); north.add(Box.createVerticalStrut(5)); panel = new JPanel(); panel.setLayout(new BoxLayout(panel, BoxLayout.X_AXIS)); panel.add(lbl_Name); panel.add(keywordFld); panel.add(btn_Search); north.add(panel); view.add(north, BorderLayout.NORTH); panel = new JPanel(); panel.setLayout(new BoxLayout(panel, BoxLayout.Y_AXIS)); panel.add(Box.createVerticalStrut(5)); lbl_Result.setAlignmentX(JComponent.LEFT_ALIGNMENT); panel.add(lbl_Result); scroll.setAlignmentX(JComponent.LEFT_ALIGNMENT); panel.add(scroll); view.add(panel, BorderLayout.CENTER); panel = new JPanel(); panel.setLayout(new BoxLayout(panel, BoxLayout.X_AXIS)); panel.add(Box.createHorizontalGlue()); panel.add(btn_Exit); view.add(panel, BorderLayout.SOUTH); view.setBorder(BorderFactory.createEmptyBorder(12, 12, 11, 11)); resultArea.setLineWrap(true); btn_Search.addActionListener((ActionEvent e) -> { search(); }); btn_Exit.addActionListener((ActionEvent e) -> { closePanel(); }); keywordFld.addFocusListener(AutoKanjiListener.getInstance()); keywordFld.addActionListener((ActionEvent e) -> { search(); }); } }