/*
 * AllergyPanel.java
 *
 * Created on 2007/11/29, 9:11
 */
package open.dolphin.plugin;

import java.awt.Rectangle;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.List;
import javax.swing.JMenuItem;
import javax.swing.JPopupMenu;
import javax.swing.JSeparator;
import javax.swing.JTabbedPane;
import javax.swing.ListSelectionModel;

import open.dolphin.client.IChart;
import open.dolphin.client.IChartDocument;
import open.dolphin.project.GlobalSettings;
import open.dolphin.delegater.remote.RemoteDocumentDelegater;
import open.dolphin.helper.DBTask;
import open.dolphin.infomodel.AllergyModel;
import open.dolphin.infomodel.IInfoModel;
import open.dolphin.infomodel.ModelUtils;
import open.dolphin.infomodel.ObservationModel;
import open.dolphin.project.GlobalVariables;
import open.dolphin.table.ObjectReflectTableModel;
import open.dolphin.table.OddEvenRowRenderer;

/**
 *　カルテの左側に表示されるアレルギーのリスト
 * @author  kazm
 */
public class AllergyPanel extends javax.swing.JPanel implements IChartDocument {

    /**
     *
     */
    public static final String TITLE = "アレルギ";
    private ObjectReflectTableModel<AllergyModel> tableModel;  // TableModel
    private IChart parent;
    private String title;

    /** This method is called from within the constructor to
     * initialize the form.
     * WARNING: Do NOT modify this code. The content of this method is
     * always regenerated by the Form Editor.
     */
    // <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
    private void initComponents() {

        scroller = new javax.swing.JScrollPane();
        table = new javax.swing.JTable();

        setName("Form"); // NOI18N

        scroller.setName("scroller"); // NOI18N

        table.setModel(new javax.swing.table.DefaultTableModel(
            new Object [][] {
                {null, null, null}
            },
            new String [] {
                "要 因", "反応程度", "同定日"
            }
        ));
        table.setName("table"); // NOI18N
        table.addMouseListener(new java.awt.event.MouseAdapter() {
            public void mousePressed(java.awt.event.MouseEvent evt) {
                tableMousePressed(evt);
            }
            public void mouseReleased(java.awt.event.MouseEvent evt) {
                tableMouseReleased(evt);
            }
        });
        scroller.setViewportView(table);

        org.jdesktop.layout.GroupLayout layout = new org.jdesktop.layout.GroupLayout(this);
        this.setLayout(layout);
        layout.setHorizontalGroup(
            layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)
            .add(scroller, org.jdesktop.layout.GroupLayout.DEFAULT_SIZE, 242, Short.MAX_VALUE)
        );
        layout.setVerticalGroup(
            layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)
            .add(scroller, org.jdesktop.layout.GroupLayout.DEFAULT_SIZE, 86, Short.MAX_VALUE)
        );
    }// </editor-fold>//GEN-END:initComponents

    private void tableMousePressed(java.awt.event.MouseEvent evt) {//GEN-FIRST:event_tableMousePressed
        showPopup(evt);
    }//GEN-LAST:event_tableMousePressed

    private void tableMouseReleased(java.awt.event.MouseEvent evt) {//GEN-FIRST:event_tableMouseReleased
        showPopup(evt);
    }//GEN-LAST:event_tableMouseReleased
    // Variables declaration - do not modify//GEN-BEGIN:variables
    private javax.swing.JScrollPane scroller;
    private javax.swing.JTable table;
    // End of variables declaration//GEN-END:variables

    /**
     *
     * @return
     */
    @Override
    public TYPE getType() {
        return TYPE.Plugin;
        //     return TYPE.AllergyPanel;
    }

    /**
     *
     * @return
     */
    public javax.swing.JTable getTable() {
        return table;
    }

    /**
     * AllergyInspectorオブジェクトを生成する。
     * @param parent
     */
    public AllergyPanel(IChart parent) {
        this.title = TITLE;
        this.parent = parent;
        initComponents();
        initCustomComponents();
        update();
    }

    /**
     *
     */
    public void clear() {
        tableModel.clear();
    }

    private void showPopup(MouseEvent e) {
        if (e.isPopupTrigger()) {
            JPopupMenu popupMenu = new JPopupMenu();
            JMenuItem menuItem = new JMenuItem("追加");
            popupMenu.add(menuItem);
            menuItem.addActionListener(new ActionListener() {

                @Override
                public void actionPerformed(ActionEvent e) {
                    new AllergyEditorPanel(AllergyPanel.this);
                }
            });
            final int row = table.rowAtPoint(e.getPoint());
            if (tableModel.getObject(row) != null) {
                popupMenu.add(new JSeparator());
                JMenuItem item2 = new JMenuItem("削除");
                popupMenu.add(item2);
                item2.addActionListener(new ActionListener() {

                    @Override
                    public void actionPerformed(ActionEvent e) {
                        delete(row);
                    }
                });
            }
            popupMenu.show(e.getComponent(), e.getX(), e.getY());
        }
    }

    /**
     * GUIコンポーネントを初期化する。
     */
    private void initCustomComponents() {
        // アレルギーテーブルを設定する
        String[] columnNames = {"要 因", "反応程度", "同定日"};
        int startNumRows = 1;
        String[] methodNames = {"getFactor", "getSeverity", "getIdentifiedFormatDate"};
        tableModel = new ObjectReflectTableModel<AllergyModel>(columnNames, startNumRows, methodNames, null);
        table.setModel(tableModel);
        table.getSelectionModel().setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
        table.setDefaultRenderer(Object.class, new OddEvenRowRenderer());  // レンダラを設定する
        scroller.getViewport().setBackground(GlobalSettings.getColors(GlobalSettings.Parts.TABLE_BACKGROUND));
    }

    private void scroll(boolean ascending) {

        int cnt = tableModel.getObjectCount();
        if (cnt > 0) {
            int row = 0;
            if (ascending) {
                row = cnt - 1;
            }
            Rectangle r = table.getCellRect(row, row, true);
            table.scrollRectToVisible(r);
        }
    }

    /**
     * アレルギー情報を表示する。
     */
    public void update() {
        List list = getParentContext().getKarte().getEntryCollection("allergy");
        if (list != null && list.size() > 0) {
            boolean asc = GlobalVariables.getPreferences().getBoolean(GlobalVariables.DOC_HISTORY_ASCENDING, false);
            if (asc) {
                Collections.sort(list);
            } else {
                Collections.sort(list, Collections.reverseOrder());
            }
            tableModel.setObjectList(list);
            scroll(asc);
        }
    }

    /**
     * アレルギーデータを追加する。
     * @param model
     */
    public void add(final AllergyModel model) {

        // GUI の同定日をTimeStampに変更する
        Date date = ModelUtils.getDateTimeAsObject(model.getIdentifiedDate() + "T00:00:00");

        final List<ObservationModel> addList = new ArrayList<ObservationModel>(1);
        ObservationModel observation = new ObservationModel();
        observation.setKarte(getParentContext().getKarte());
        observation.setCreator(GlobalVariables.getUserModel());
        observation.setObservation(IInfoModel.OBSERVATION_ALLERGY);
        observation.setPhenomenon(model.getFactor());
        observation.setCategoryValue(model.getSeverity());
        observation.setConfirmed(date);
        observation.setRecorded(new Date());
        observation.setStarted(date);
        observation.setStatus(IInfoModel.STATUS_FINAL);
        observation.setMemo(model.getMemo());
        addList.add(observation);

        DBTask task = new DBTask<List<Long>>(getParentContext()) {

            @Override
            protected List<Long> doInBackground() throws Exception {
                RemoteDocumentDelegater ddl = new RemoteDocumentDelegater();
                List<Long> ids = ddl.addObservations(addList);
                return ids;
            }

            @Override
            protected void succeeded(List<Long> result) {
                model.setObservationId(result.get(0));
                boolean asc = GlobalVariables.getPreferences().getBoolean(GlobalVariables.DOC_HISTORY_ASCENDING, false);
                if (asc) {
                    tableModel.addRow(model);
                } else {
                    tableModel.addRow(0, model);
                }
                scroll(asc);
            }
        };
        task.execute();
    }

    /**
     * テーブルで選択したアレルギーを削除する。
     * @param row
     */
    public void delete(final int row) {

        AllergyModel model = (AllergyModel) tableModel.getObject(row);

        if (model != null) {

            final List<Long> list = new ArrayList<Long>(1);
            list.add(new Long(model.getObservationId()));

            DBTask task = new DBTask<Void>(getParentContext()) {

                @Override
                protected Void doInBackground() throws Exception {
                    RemoteDocumentDelegater ddl = new RemoteDocumentDelegater();
                    ddl.removeObservations(list);
                    return null;
                }

                @Override
                protected void succeeded(Void result) {
                    tableModel.deleteRow(row);
                }
            };
            task.execute();
        }
    }

    /**
     *
     * @return
     */
    @Override
    public boolean itLayoutSaved() {
        return true;
    }

    /**
     *
     * @return
     */
    @Override
    public String getTitle() {
        return title;
    }

    /**
     *
     * @return
     */
    @Override
    public IChart getParentContext() {
        return parent;
    }

    /**
     *
     */
    @Override
    public void start() {
    }

    /**
     *
     */
    @Override
    public void stop() {
    }

    /**
     *
     */
    @Override
    public void enter() {
    }

    /**
     *
     * @return
     */
    @Override
    public boolean prepare() {
        return true;
    }

    /**
     *
     * @return
     */
    @Override
    public boolean isDirty() {
        return false;
    }

    /**
     *
     * @param dirty
     */
    @Override
    public void setDirty(boolean dirty) {
    }

    /**
     *
     * @param command
     * @return
     */
    @Override
    public boolean dispatchChartCommand(ChartCommand command) {
        return false;
    }

    /**
     *
     * @return
     */
    @Override
    public List<JTabbedPane> getTabbedPanels() {
        return null;
    }

    /**
     *
     * @param o
     * @return
     */
    @Override
    public boolean update(Object o) {
        return true;
    }
}
