diff --git a/org.adempiere.base/src/org/compiere/model/GridField.java b/org.adempiere.base/src/org/compiere/model/GridField.java index 354e2ca333..595bcdb2d5 100644 --- a/org.adempiere.base/src/org/compiere/model/GridField.java +++ b/org.adempiere.base/src/org/compiere/model/GridField.java @@ -511,9 +511,7 @@ public class GridField if (checkContext && getGridTab() != null && !Env.getContext(ctx, m_vo.WindowNo,m_vo.TabNo, "IsActive").equals("Y")) return false; - // ultimately visibility decides - if(isGrid) - return isDisplayedGrid(); + return isDisplayed (ctx, checkContext); } // isEditable diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/AbstractADWindowContent.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/AbstractADWindowContent.java index 4cc8dc70f3..15df4f3a34 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/AbstractADWindowContent.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/AbstractADWindowContent.java @@ -3101,6 +3101,8 @@ public abstract class AbstractADWindowContent extends AbstractUIPart implements } /** + * show dialog to customize fields (hidden, display, order of field) in grid mode + * @see CustomizeGridViewDialog * @see ToolbarListener#onCustomize() */ public void onCustomize() { @@ -3111,6 +3113,9 @@ public abstract class AbstractADWindowContent extends AbstractUIPart implements Map columnsWidth = new HashMap(); ArrayList gridFieldIds = new ArrayList(); for (int i = 0; i < fields.length; i++) { + // 2 is offset of num of column in grid view and actual data fields. + // in grid view, add two function column, indicator column and selection (checkbox) column + // @see GridView#setupColumns Column column = (Column) columnList.get(i+2); String width = column.getWidth(); columnsWidth.put(fields[i].getAD_Field_ID(), width); diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/GridTabRowRenderer.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/GridTabRowRenderer.java index d7210202a7..de637b5285 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/GridTabRowRenderer.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/GridTabRowRenderer.java @@ -94,7 +94,11 @@ public class GridTabRowRenderer implements RowRenderer, RowRendererExt private int currentRowIndex = -1; private AbstractADWindowContent m_windowPanel; private ActionListener buttonListener; - + /** + * Flag detect this view has customized column or not + * value is set at {@link #render(Row, Object[], int)} + */ + private boolean isGridViewCustomized = false; /** DefaultFocusField */ private WEditor defaultFocusField = null; @@ -164,14 +168,33 @@ public class GridTabRowRenderer implements RowRenderer, RowRendererExt return checkBox; } - private String getDisplayText(Object value, GridField gridField, int rowIndex) + /** + * call {@link #getDisplayText(Object, GridField, int, boolean)} with isForceGetValue = false + * @param value + * @param gridField + * @param rowIndex + * @return + */ + private String getDisplayText(Object value, GridField gridField, int rowIndex){ + return getDisplayText(value, gridField, rowIndex, false); + } + + /** + * Get display text of a field. when field have isDisplay = false always return empty string, except isForceGetValue = true + * @param value + * @param gridField + * @param rowIndex + * @param isForceGetValue + * @return + */ + private String getDisplayText(Object value, GridField gridField, int rowIndex, boolean isForceGetValue) { if (value == null) return ""; if (rowIndex >= 0) { GridRowCtx gridRowCtx = new GridRowCtx(Env.getCtx(), gridTab, rowIndex); - if (!gridField.isDisplayed(gridRowCtx, true)) { + if (!isForceGetValue && !gridField.isDisplayed(gridRowCtx, true)) { return ""; } } @@ -188,8 +211,18 @@ public class GridTabRowRenderer implements RowRenderer, RowRendererExt else return value.toString(); } - - private Component getDisplayComponent(int rowIndex, Object value, GridField gridField) { + + /** + * get component to display value of a field. + * when display is boolean or button, return correspond component + * other return a label with text get from {@link #getDisplayText(Object, GridField, int, boolean)} + * @param rowIndex + * @param value + * @param gridField + * @param isForceGetValue + * @return + */ + private Component getDisplayComponent(int rowIndex, Object value, GridField gridField, boolean isForceGetValue) { Component component; if (gridField.getDisplayType() == DisplayType.YesNo) { component = createReadonlyCheckbox(value); @@ -202,7 +235,7 @@ public class GridTabRowRenderer implements RowRenderer, RowRendererExt editor.addActionListener(buttonListener); component = editor.getComponent(); } else { - String text = getDisplayText(value, gridField, rowIndex); + String text = getDisplayText(value, gridField, rowIndex, isForceGetValue); Label label = new Label(); setLabelText(text, label); @@ -315,7 +348,6 @@ public class GridTabRowRenderer implements RowRenderer, RowRendererExt int columnCount = 0; GridField[] gridPanelFields = null; GridField[] gridTabFields = null; - boolean isGridViewCustomized = false; if (gridPanel != null) { if (!gridPanel.isVisible()) { @@ -426,7 +458,8 @@ public class GridTabRowRenderer implements RowRenderer, RowRendererExt } } - if (!gridPanelFields[i].isDisplayedGrid() || gridPanelFields[i].isToolbarButton()) { + // IDEMPIERE-2148: when has tab customize, ignore check properties isDisplayedGrid + if ((!isGridViewCustomized && gridPanelFields[i].isDisplayedGrid()) || gridPanelFields[i].isToolbarButton()) { continue; } colIndex ++; @@ -435,7 +468,7 @@ public class GridTabRowRenderer implements RowRenderer, RowRendererExt String divStyle = CELL_DIV_STYLE; org.zkoss.zul.Column column = (org.zkoss.zul.Column) columns.getChildren().get(colIndex); if (column.isVisible()) { - Component component = getDisplayComponent(rowIndex, currentValues[i], gridPanelFields[i]); + Component component = getDisplayComponent(rowIndex, currentValues[i], gridPanelFields[i], isGridViewCustomized); div.appendChild(component); div.setAttribute("display.component", component); @@ -445,8 +478,12 @@ public class GridTabRowRenderer implements RowRenderer, RowRendererExt else if (DisplayType.isNumeric(gridPanelFields[i].getDisplayType())) { divStyle = CELL_DIV_STYLE_ALIGN_RIGHT; } + GridRowCtx ctx = new GridRowCtx(Env.getCtx(), gridTab, rowIndex); - component.setVisible(gridPanelFields[i].isDisplayed(ctx, true)); + if (!gridPanelFields[i].isDisplayed(ctx, true)){ + // IDEMPIERE-2253 + div.removeChild(component); + } } div.setStyle(divStyle); div.setWidth("100%"); @@ -553,7 +590,7 @@ public class GridTabRowRenderer implements RowRenderer, RowRendererExt //skip selection and indicator column int colIndex = 1; for (int i = 0; i < columnCount; i++) { - if (!gridPanelFields[i].isDisplayedGrid() || gridPanelFields[i].isToolbarButton()) { + if ((!isGridViewCustomized && !gridPanelFields[i].isDisplayedGrid()) || gridPanelFields[i].isToolbarButton()) { continue; } colIndex ++; @@ -584,11 +621,11 @@ public class GridTabRowRenderer implements RowRenderer, RowRendererExt Properties ctx = isDetailPane() ? new GridRowCtx(Env.getCtx(), gridTab, gridTab.getCurrentRow()) : gridPanelFields[i].getVO().ctx; //check context - if (!gridPanelFields[i].isDisplayedGrid() || - !gridPanelFields[i].isDisplayed(ctx, true)) - { - editor.setVisible(false); + if (!gridPanelFields[i].isDisplayed(ctx, true)){ + // IDEMPIERE-2253 + div.removeChild(editor.getComponent()); } + editor.setReadWrite(gridPanelFields[i].isEditableGrid(true)); } } diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/GridView.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/GridView.java index b13954748e..33dcee6587 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/GridView.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/adwindow/GridView.java @@ -97,6 +97,10 @@ public class GridView extends Vbox implements EventListener, IdSpace, IFi private int pageSize = DEFAULT_PAGE_SIZE; + /** + * list field display in grid mode, in case user customize grid + * this list container only customize list. + */ private GridField[] gridField; private AbstractTableModel tableModel; @@ -129,6 +133,8 @@ public class GridView extends Vbox implements EventListener, IdSpace, IFi private boolean detailPaneMode; protected Checkbox selectAll; + + boolean isHasCustomizeData = false; public GridView() { @@ -245,7 +251,7 @@ public class GridView extends Vbox implements EventListener, IdSpace, IFi parent = parent.getParent(); } } - + private void setupFields(GridTab gridTab) { this.gridTab = gridTab; gridTab.addStateChangeListener(this); @@ -254,8 +260,9 @@ public class GridView extends Vbox implements EventListener, IdSpace, IFi columnWidthMap = new HashMap(); GridField[] tmpFields = ((GridTable)tableModel).getFields(); MTabCustomization tabCustomization = MTabCustomization.get(Env.getCtx(), Env.getAD_User_ID(Env.getCtx()), gridTab.getAD_Tab_ID(), null); - if (tabCustomization != null && tabCustomization.getAD_Tab_Customization_ID() > 0 - && tabCustomization.getCustom() != null && tabCustomization.getCustom().trim().length() > 0) { + isHasCustomizeData = tabCustomization != null && tabCustomization.getAD_Tab_Customization_ID() > 0 + && tabCustomization.getCustom() != null && tabCustomization.getCustom().trim().length() > 0; + if (isHasCustomizeData) { String custom = tabCustomization.getCustom().trim(); String[] customComponent = custom.split(";"); String[] fieldIds = customComponent[0].split("[,]"); @@ -266,7 +273,8 @@ public class GridView extends Vbox implements EventListener, IdSpace, IFi int AD_Field_ID = Integer.parseInt(fieldIdStr); for(GridField gridField : tmpFields) { if (gridField.getAD_Field_ID() == AD_Field_ID) { - if(gridField.isDisplayedGrid() && !gridField.isToolbarButton()) + // IDEMPIERE-2204 add field in tabCustomization list to display list event this field have showInGrid = false + if((gridField.isDisplayedGrid() || gridField.isDisplayed()) && !gridField.isToolbarButton()) fieldList.add(gridField); break; @@ -477,9 +485,11 @@ public class GridView extends Vbox implements EventListener, IdSpace, IFi Map colnames = new HashMap(); int index = 0; + for (int i = 0; i < numColumns; i++) { - if (gridField[i].isDisplayedGrid() && !gridField[i].isToolbarButton()) + // IDEMPIERE-2148: when has tab customize, ignore check properties isDisplayedGrid + if ((isHasCustomizeData || gridField[i].isDisplayedGrid()) && !gridField[i].isToolbarButton()) { colnames.put(index, gridField[i].getHeader()); index++; @@ -959,7 +969,7 @@ public class GridView extends Vbox implements EventListener, IdSpace, IFi Properties ctx = isDetailPane() ? new GridRowCtx(Env.getCtx(), gridTab, gridTab.getCurrentRow()) : mField.getVO().ctx; - comp.setVisible(mField.isDisplayedGrid() && mField.isDisplayed(ctx, true)); + comp.setVisible((isHasCustomizeData || mField.isDisplayedGrid()) && mField.isDisplayed(ctx, true)); } } } @@ -1044,6 +1054,10 @@ public class GridView extends Vbox implements EventListener, IdSpace, IFi updateModel(); } + /** + * list field display in grid mode, in case user customize grid + * this list container only customize list. + */ public GridField[] getFields() { return gridField; } diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/panel/CustomizeGridViewPanel.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/panel/CustomizeGridViewPanel.java index 77c7fb7d21..45ccebcbe4 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/panel/CustomizeGridViewPanel.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/panel/CustomizeGridViewPanel.java @@ -16,9 +16,6 @@ *****************************************************************************/ package org.adempiere.webui.panel; -import java.sql.PreparedStatement; -import java.sql.ResultSet; -import java.sql.SQLException; import java.util.ArrayList; import java.util.Arrays; import java.util.HashMap; @@ -27,6 +24,7 @@ import java.util.Map; import java.util.Set; import java.util.logging.Level; +import org.adempiere.exceptions.DBException; import org.adempiere.model.MTabCustomization; import org.adempiere.webui.LayoutUtils; import org.adempiere.webui.adwindow.GridView; @@ -43,9 +41,12 @@ import org.adempiere.webui.component.SimpleListModel; import org.adempiere.webui.factory.ButtonFactory; import org.adempiere.webui.theme.ThemeManager; import org.adempiere.webui.window.FDialog; +import org.compiere.model.MField; import org.compiere.model.MRefList; +import org.compiere.model.MRole; +import org.compiere.model.MTab; +import org.compiere.model.Query; import org.compiere.util.CLogger; -import org.compiere.util.DB; import org.compiere.util.Env; import org.compiere.util.Msg; import org.compiere.util.NamePair; @@ -295,27 +296,31 @@ public class CustomizeGridViewPanel extends Panel yesModel.removeAllElements(); noModel.removeAllElements(); boolean baseLanguage = Env.isBaseLanguage(Env.getCtx(), "AD_Field"); - String sql; - if (baseLanguage) - sql = "SELECT f.AD_Field_ID,f.Name FROM AD_Field f WHERE f.AD_Tab_ID=? AND (f.IsDisplayed='Y' OR f.IsDisplayedGrid='Y') AND f.IsActive='Y' ORDER BY f.SeqNoGrid,f.Name,f.SeqNo"; - else - sql = "SELECT f.AD_Field_ID,trl.Name FROM AD_Field f JOIN AD_Field_Trl trl ON (f.AD_Field_ID = trl.AD_Field_ID)" - + " WHERE f.AD_Tab_ID=? AND (f.IsDisplayed='Y' OR f.IsDisplayedGrid='Y') AND f.IsActive='Y' AND trl.AD_Language=? ORDER BY f.SeqNoGrid,f.Name,f.SeqNo"; - PreparedStatement pstmt = null; - ResultSet rs = null; + Query query = null; + + query = new Query(Env.getCtx(), MField.Table_Name, "AD_Tab_ID=? AND (IsDisplayed='Y' OR IsDisplayedGrid='Y') AND IsActive='Y'", null); + query.setOrderBy("SeqNoGrid, Name, SeqNo"); + query.setParameters(new Object [] {m_AD_Tab_ID}); + query.setApplyAccessFilter(true); + try { - pstmt = DB.prepareStatement(sql, null); - pstmt.setInt(1, m_AD_Tab_ID); - if (!baseLanguage) - pstmt.setString(2, Env.getAD_Language(Env.getCtx())); - rs = pstmt.executeQuery(); - + List lsFieldsOfGrid = query.list(); HashMap curTabSel = new HashMap(); - while (rs.next()) + MTab tab = new MTab(Env.getCtx(), m_AD_Tab_ID, null); + + for (MField field : lsFieldsOfGrid) { - int key = rs.getInt(1); - String name = rs.getString(2); + if (!MRole.getDefault(Env.getCtx(), false).isColumnAccess(tab.getAD_Table_ID(), field.getAD_Column_ID(), true)) + continue; + + int key = field.get_ID(); + String name = null; + if (baseLanguage) + name = field.getName(); + else + name = field.get_Translation(MField.COLUMNNAME_Name); + ListElement pp = new ListElement(key, name); if (tableSeqs != null && tableSeqs.size() > 0 ) { if (tableSeqs.contains(key)) { @@ -335,16 +340,10 @@ public class CustomizeGridViewPanel extends Panel } } } - catch (SQLException e) + catch (DBException e) { - log.log(Level.SEVERE, sql.toString(), e); + log.log(Level.SEVERE, e.getMessage(), e); } - finally - { - DB.close(rs, pstmt); - rs = null; pstmt = null; - } - bAdd.setEnabled(true); bRemove.setEnabled(true); diff --git a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/CustomizeGridViewDialog.java b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/CustomizeGridViewDialog.java index 9e32cc83a3..b258a51500 100644 --- a/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/CustomizeGridViewDialog.java +++ b/org.adempiere.ui.zk/WEB-INF/src/org/adempiere/webui/window/CustomizeGridViewDialog.java @@ -61,6 +61,7 @@ public class CustomizeGridViewDialog extends Window { * @param WindowNo window no * @param AD_Tab_ID * @param columnsWidth + * @param gridFieldIds list fieldId current display in gridview */ public static boolean showCustomize (int WindowNo, int AD_Tab_ID, Map columnsWidth,ArrayList gridFieldIds,GridView gridPanel) {