/*
* PanelAnalyse.java
*
* Created on 12 Май 2008 г., 16:11
*/
package clips.analysis.laboratory;
import clips.delegate.doctor.checkup.CheckupLocal;
import clips.delegate.doctor.checkup.CheckupXMLData;
import clips.delegate.doctor.checkup.shedule.CheckupSheduleLocal;
import cli_fmw.delegate.DelegateLine2;
import cli_fmw.main.ClipsException;
import cli_fmw.main.ContentStateListener;
import cli_fmw.main.PageContainer;
import cli_fmw.main.PageGeneric;
import cli_fmw.main.Persistentable;
import cli_fmw.utils.MessageBox;
import cli_fmw.utils.sorted_table.renderer.simple.DefaultRenderer;
import cli_fmw.utils.table_config_states.StateSaver;
import cli_fmw.utils.tableizvrat.ColumnGroup;
import cli_fmw.utils.tableizvrat.GroupableTableHeader;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.FocusAdapter;
import java.awt.event.FocusEvent;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.Set;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.JViewport;
import javax.swing.ListSelectionModel;
import javax.swing.Timer;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;
import javax.swing.table.JTableHeader;
import javax.swing.table.TableColumnModel;
/**
*
* @author vip
*/
public class PanelAnalyse extends PageGeneric
implements Persistentable, ContentStateListener {
/**
* ширина столбца № пробы
*/
private static final int PROBE_NUMBER_WIDTH = 60;
/**
* ширина столбцов ввода значений
*/
private static final int PROBE_VALUE_WIDTH = 120;
private CheckupSheduleLocal shedule;
private ArrayList<CheckupLocal> checkupList;
private ArrayList<CheckupXMLData> xmlList;
private ArrayList<String> probeList;
private ArrayList<String> probeValueList;
private int colByGroup;
private PanelProbeInfo panelProbeInfo = new PanelProbeInfo();
private final Timer timer = new Timer(10 * 60 * 1000, null); //10 минут автосохранение
private JTable jTable1;
private JTable fixedTable;
/** Creates new form PanelAnalyse */
public PanelAnalyse(PageContainer container, CheckupSheduleLocal shedule) throws ClipsException {
super(container);
initComponents();
initTables();
jPanel2.add(panelProbeInfo);
this.shedule = shedule;
//запросили список чекапов
checkupList = new ArrayList<CheckupLocal>();
Set<CheckupLocal> chs = shedule.getCheckupSet();
for (Iterator<CheckupLocal> it = chs.iterator(); it.hasNext();) {
CheckupLocal checkup = it.next();
checkupList.add(checkup);
}
//создали список хмльных данных чекапов
xmlList = new ArrayList<CheckupXMLData>();
for (CheckupLocal checkup : checkupList) {
xmlList.add(checkup.getCheckupXMLData());
}
//добавим листенеры
for (CheckupXMLData xml : xmlList) {
xml.addContentStateListener(getContainer());
xml.addContentStateListener(this);
}
prepareTable();
//проверка права редактирования
if (!checkupList.get(0).canModify()) {
((TableModelAnalyse)jTable1.getModel()).setEditable(false, "Недостаточно прав для изменения анализов");
}
JViewport viewport = new JViewport();
viewport.setView(fixedTable);
jScrollPane1.setViewportView(jTable1);
viewport.setPreferredSize(fixedTable.getPreferredSize());
jScrollPane1.setRowHeaderView(viewport);
jScrollPane1.setCorner(JScrollPane.UPPER_LEFT_CORNER, fixedTable.getTableHeader());
timer.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
try {
if (getContainer().getActivePage() == PanelAnalyse.this) {
save();
}
} catch (ClipsException ex) {
timer.stop();
MessageBox.showException(ex);
timer.start();
}
}
});
timer.start();
StateSaver.excludeFromAttach(this, jTable1);
StateSaver.excludeFromAttach(this, fixedTable);
StateSaver.attachTo(this);
}
private void initTables() {
jTable1 = new JTable() { //вот такая вот переменная
@Override //в классе JTable переопределяем метод
protected JTableHeader createDefaultTableHeader() {
return new GroupableTableHeader(columnModel);
}
@Override
public void valueChanged(ListSelectionEvent e) {
super.valueChanged(e);
checkSelection(false);
}
};
fixedTable = new JTable() {
@Override
public void valueChanged(ListSelectionEvent e) {
super.valueChanged(e);
checkSelection(true);
}
};
fixedTable.setDefaultRenderer(Object.class, new DefaultRenderer());
fixedTable.getTableHeader().setReorderingAllowed(false);
}
/**
* подготовка таблицы к началу работы.
* создание списка методик которые надо выполнять
* при обновлении таблицы выполнять нельзя
*/
private void prepareTable() throws ClipsException {
//подготовка списка нужных проб
probeList = xmlList.get(0).getProbeList();
probeValueList = xmlList.get(0).getProbeValueList();
ArrayList<String> unsorted = new ArrayList<String>();
//по каждому чекапу
for (CheckupXMLData xml : xmlList) {
//покаждой пробе в чекапе
ArrayList<String> checkUpProbeList = xml.getProbeList();
for (int i = 0; i < checkUpProbeList.size(); i++) {
String probe = checkUpProbeList.get(i);
if (!unsorted.contains(probe) && xml.isProbeNeed(probe)) {
unsorted.add(probe);
}
}
}
boolean addAll = cbViewAllProbes.isSelected();
//приводим к сортированному
for (int i = probeList.size() - 1; i >= 0; i--) {
//если в несортированном нет элемента, то его убираем из сортированного
if (!unsorted.contains(probeList.get(i)) && !addAll ||
probeList.get(i).startsWith("separator")) {
probeList.remove(i);
}
}
//подготовка фиксированной таблицы
fixedTable.setModel(new TableModelFixedAnalyses(checkupList));
fixedTable.getSelectionModel().setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
fixedTable.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);
fixedTable.addFocusListener(new FocusAdapter() {
@Override
public void focusGained(FocusEvent e) {
viewProbeInfo();
}
});
TableColumnModel fixedcm = fixedTable.getColumnModel();
fixedcm.getColumn(TableModelFixedAnalyses.COL_FIO).setPreferredWidth(170);
//fixedcm.getColumn(TableModelFixedAnalyses.COL_DATE).setPreferredWidth(60);
//подготовка основной таблицы
jTable1.setModel(new TableModelAnalyse(xmlList, probeList));
jTable1.setDefaultRenderer(Object.class, new TableCellRendererAnalyse());
jTable1.getSelectionModel().setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
jTable1.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);
jTable1.setDefaultEditor(Object.class, new AnalyseCellEditor(xmlList, probeList));
ListSelectionListener listener = new ListSelectionListener() {
@Override
public void valueChanged(ListSelectionEvent e) {
viewProbeInfo();
}
};
jTable1.getSelectionModel().addListSelectionListener(listener);
jTable1.getColumnModel().getSelectionModel().addListSelectionListener(listener);
colByGroup = 1 + probeValueList.size();
GroupableTableHeader header = (GroupableTableHeader) jTable1.getTableHeader();
//заполняем группы заголовков и выставляем ширину столбцов
TableColumnModel cm = jTable1.getColumnModel();
for (int i = 0; i < probeList.size(); i++) {
ColumnGroup group = new ColumnGroup(xmlList.get(0).getProbeTitle(probeList.get(i)));
for (int j = 0; j < colByGroup; j++) {
group.add(cm.getColumn(i * colByGroup + j));
if (j == 0) {
cm.getColumn(i * colByGroup + j).setPreferredWidth(PROBE_NUMBER_WIDTH);
} else {
cm.getColumn(i * colByGroup + j).setPreferredWidth(PROBE_VALUE_WIDTH);
}
}
header.addColumnGroup(group);
}
jTable1.updateUI();
}
//синхронизирует выделение на фиксированной и основной таблицах
private void checkSelection(boolean isFixedTable) {
int fixedSelectedIndex = fixedTable.getSelectedRow();
int selectedIndex = jTable1.getSelectedRow();
System.out.println("checkSelection at" + fixedSelectedIndex);
if (fixedSelectedIndex != selectedIndex) {
if (isFixedTable && fixedSelectedIndex >= 0 && fixedSelectedIndex <
jTable1.getRowCount()) {
jTable1.setRowSelectionInterval(fixedSelectedIndex, fixedSelectedIndex);
} else if (selectedIndex >= 0 && selectedIndex <
fixedTable.getRowCount()) {
fixedTable.setRowSelectionInterval(selectedIndex, selectedIndex);
}
}
}
private void viewProbeInfo() {
//информацию о пробе выводим только если фокус не на фиксированной таблице
if (!fixedTable.hasFocus()) {
int row = jTable1.getSelectedRow();
int col = jTable1.getSelectedColumn();
int colInGroup = col % colByGroup;
if (colInGroup <= 0 || row < 0) {
panelProbeInfo.viewProbeInfoAt(null, null, null);
return;
}
String probeID = probeList.get(col / colByGroup);
String valueID = probeValueList.get(colInGroup - 1);
panelProbeInfo.viewProbeInfoAt(xmlList.get(row), probeID, valueID);
} else {
panelProbeInfo.viewProbeInfoAt(null, null, null);
}
}
/** 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() {
jScrollPane1 = new javax.swing.JScrollPane();
jPanel1 = new javax.swing.JPanel();
jPanel2 = new javax.swing.JPanel();
jPanel3 = new javax.swing.JPanel();
cbViewAllProbes = new javax.swing.JCheckBox();
btRenderService = new javax.swing.JButton();
setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));
setLayout(new java.awt.BorderLayout());
add(jScrollPane1, java.awt.BorderLayout.CENTER);
jPanel1.setLayout(new java.awt.BorderLayout(5, 5));
jPanel2.setBorder(javax.swing.BorderFactory.createTitledBorder(javax.swing.BorderFactory.createEtchedBorder(), "Информация о пробе"));
jPanel2.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.LEFT));
jPanel1.add(jPanel2, java.awt.BorderLayout.CENTER);
jPanel3.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));
jPanel3.setLayout(new java.awt.BorderLayout());
cbViewAllProbes.setText("Показывать все пробы");
cbViewAllProbes.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
cbViewAllProbesActionPerformed(evt);
}
});
jPanel3.add(cbViewAllProbes, java.awt.BorderLayout.PAGE_START);
btRenderService.setText("Анализы взяты");
btRenderService.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
btRenderServiceActionPerformed(evt);
}
});
jPanel3.add(btRenderService, java.awt.BorderLayout.PAGE_END);
jPanel1.add(jPanel3, java.awt.BorderLayout.LINE_END);
add(jPanel1, java.awt.BorderLayout.PAGE_END);
}// </editor-fold>//GEN-END:initComponents
/**
* Анализы взяты. За одну транзакцию оказываются услуги, чекапы выбывают
* из расписания
* @param evt
*/
private void btRenderServiceActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_btRenderServiceActionPerformed
//Сначала пробуем сохранить данные в чекапах
try {
save();
} catch (ClipsException ex) {
MessageBox.showException(ex);
//если не сохранились данные оставляем без изменений
return;
}
//проверка все ли чекапы были заполнены
boolean gettedAll = true;
//идем по всем чекапам
for (CheckupXMLData xml : xmlList) {
//идем по всем пробам в чекапе
for (int i = 0; i < probeList.size(); i++) {
String probeID = probeList.get(i);
//если проба нужна проверим заполнены ли ее значения
if (xml.isProbeNeed(probeID)) {
//идем по всем значениям
for (int j = 0; j < probeValueList.size(); j++) {
String valueID = probeValueList.get(j);
Object value = xml.getProbeValue(probeID, valueID);
if (value == null || value.equals("")) {
gettedAll = false;
}
}
}
}
}
//Если взяты не все анализы внесены спросим надо ли продолжать сохранение
if (!gettedAll) {
if (MessageBox.showConfirmYesNo(MessageBox.C_ANALYSE_RESULT_NOT_ALL) !=
MessageBox.ANSWER_YES) {
return;
}
}
//На данном этапе данные в чекапах уже сохранены
try {
shedule.finishRenderingServices();
MessageBox.showInfo("Анализы успешно сохранены,\nсвязанные с ними услуги оказаны.");
((TableModelAnalyse)jTable1.getModel()).setEditable(false, "Изменение невозможно - анализы сохранены, услуги оказаны");
btRenderService.setEnabled(false);
//getContainer().removePage(this, false);
} catch (ClipsException ex) {
MessageBox.showException(ex);
}
}//GEN-LAST:event_btRenderServiceActionPerformed
private void cbViewAllProbesActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_cbViewAllProbesActionPerformed
try {
if (jTable1.getCellEditor() != null) {
jTable1.getCellEditor().stopCellEditing();
}
prepareTable();//GEN-LAST:event_cbViewAllProbesActionPerformed
} catch (ClipsException ex) {
MessageBox.showException(ex);
}
}
// Variables declaration - do not modify//GEN-BEGIN:variables
private javax.swing.JButton btRenderService;
private javax.swing.JCheckBox cbViewAllProbes;
private javax.swing.JPanel jPanel1;
private javax.swing.JPanel jPanel2;
private javax.swing.JPanel jPanel3;
private javax.swing.JScrollPane jScrollPane1;
// End of variables declaration//GEN-END:variables
@Override
public String getPageTitle() {
return "Лаборатория анализов";
}
@Override
public boolean isDirty() {
boolean isDirty = false;
for (CheckupXMLData xml : xmlList) {
if (xml.isDirty()) {
isDirty = true;
break;
}
}
return isDirty;
}
@Override
public void save() throws ClipsException {
if (jTable1.getCellEditor() != null) {
jTable1.getCellEditor().stopCellEditing();
}
Exception myEx = null;
try {
for (int i = 0; i < checkupList.size(); i++) {
CheckupLocal checkupLocal = checkupList.get(i);
checkupLocal.setCheckupXMLData(xmlList.get(i));
checkupLocal.save1();
}
} catch (ClipsException ex) {
myEx = ex;
}
//Удалим листенеры
for (CheckupXMLData xml : xmlList) {
xml.removeContentStateListener(getContainer());
xml.removeContentStateListener(this);
}
//xmlList = new ArrayList<CheckupXMLData>();
xmlList.clear();
for (int i = 0; i < checkupList.size(); i++) {
CheckupLocal checkupLocal = checkupList.get(i);
try {
CheckupXMLData xml = checkupLocal.getCheckupXMLData();
xml.addContentStateListener(getContainer());
xml.addContentStateListener(this);
xmlList.add(xml);
prepareTable();
} catch (ClipsException ex) {
//эксепшен никогда не должен вылезти
ex.printStackTrace();
}
}
getContainer().contentStateChanged();
if (myEx != null) {
throw new ClipsException("Сохранены не все анализы", myEx);
}
}
@Override
public void restore() {
//Удалим листенеры
for (CheckupXMLData xml : xmlList) {
xml.removeContentStateListener(getContainer());
xml.removeContentStateListener(this);
}
//xmlList = new ArrayList<CheckupXMLData>();
xmlList.clear();
for (int i = 0; i < checkupList.size(); i++) {
CheckupLocal checkupLocal = checkupList.get(i);
try {
CheckupXMLData xml = checkupLocal.getCheckupXMLData();
xml.addContentStateListener(getContainer());
xml.addContentStateListener(this);
xmlList.add(xml);
prepareTable();
} catch (ClipsException ex) {
//эксепшен никогда не должен вылезти
ex.printStackTrace();
}
}
getContainer().contentStateChanged();
//refreshTable();
}
private void refreshTable() {
jTable1.updateUI();
}
//при изменении делегатов перерисовываем информацию о ячейке
@Override
public void contentStateChanged() {
viewProbeInfo();
}
@Override
public DelegateLine2 getDelegate() {
return shedule;
}
}