package org.sigmah.client.ui.view.contact.dashboardlist; /* * #%L * Sigmah * %% * Copyright (C) 2010 - 2016 URD * %% * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as * published by the Free Software Foundation, either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this program. If not, see * <http://www.gnu.org/licenses/gpl-3.0.html>. * #L% */ import java.util.Arrays; import java.util.Date; import com.extjs.gxt.ui.client.Style; import com.extjs.gxt.ui.client.data.BaseFilterPagingLoadConfig; import com.extjs.gxt.ui.client.data.BasePagingLoader; import com.extjs.gxt.ui.client.data.PagingLoadResult; import com.extjs.gxt.ui.client.data.PagingLoader; import com.extjs.gxt.ui.client.store.ListStore; import com.extjs.gxt.ui.client.widget.ContentPanel; import com.extjs.gxt.ui.client.widget.Html; import com.extjs.gxt.ui.client.widget.grid.ColumnConfig; import com.extjs.gxt.ui.client.widget.grid.ColumnData; import com.extjs.gxt.ui.client.widget.grid.ColumnModel; import com.extjs.gxt.ui.client.widget.grid.Grid; import com.extjs.gxt.ui.client.widget.grid.GridCellRenderer; import com.extjs.gxt.ui.client.widget.grid.filters.DateFilter; import com.extjs.gxt.ui.client.widget.grid.filters.GridFilters; import com.extjs.gxt.ui.client.widget.grid.filters.StringFilter; import com.extjs.gxt.ui.client.widget.toolbar.PagingToolBar; import com.extjs.gxt.ui.client.widget.toolbar.ToolBar; import com.google.gwt.event.dom.client.ClickEvent; import com.google.gwt.event.dom.client.ClickHandler; import com.google.gwt.i18n.client.DateTimeFormat; import com.google.gwt.user.client.ui.Anchor; import com.google.gwt.user.client.ui.HTML; import com.google.gwt.user.client.ui.Widget; import org.sigmah.client.i18n.I18N; import org.sigmah.client.ui.notif.N10N; import org.sigmah.client.ui.presenter.contact.dashboardlist.ContactsListWidget; import org.sigmah.client.ui.res.icon.IconImageBundle; import org.sigmah.client.ui.view.base.AbstractView; import org.sigmah.client.ui.widget.button.Button; import org.sigmah.client.ui.widget.panel.Panels; import org.sigmah.client.util.DateUtils; import org.sigmah.shared.command.result.ContactHistory; import org.sigmah.shared.dto.ContactDTO; import org.sigmah.shared.dto.referential.ContactModelType; public class ContactsListView extends AbstractView implements ContactsListWidget.View { // CSS style names. private static final String STYLE_IMPORTANT_LABEL = "important-label"; private static final String STYLE_CONTACT_GRID_NAME = "contact-grid-name"; private ContentPanel contactTreePanel; private Grid<DashboardContact> contactTreeGrid; private GridFilters gridFilters; private ToolBar toolbar; private PagingToolBar pagingToolBar; private PagingContactsProxy proxy; private PagingLoader<PagingLoadResult<DashboardContact>> pagingLoader; private Button addContactButton; private Button importButton; private Button exportButton; // Specific Handlers provided by presenter. private GridEventHandler<DashboardContact> treeHandler; /** * Initializes the widget view. */ @Override public void initialize() { // Paging proxy = new PagingContactsProxy(); pagingLoader = new BasePagingLoader<PagingLoadResult<DashboardContact>>(proxy) { @Override protected Object newLoadConfig() { return new BaseFilterPagingLoadConfig(); } }; pagingLoader.setRemoteSort(true); pagingToolBar = new PagingToolBar(10); pagingToolBar.bind(pagingLoader); // Store. final ListStore<DashboardContact> contactStore = new ListStore<DashboardContact>(pagingLoader); contactStore.setMonitorChanges(true); // Default sort order of the contacts grid. pagingLoader.setSortField(ContactHistory.UPDATED_AT); pagingLoader.setSortDir(Style.SortDir.DESC); // Grid. contactTreeGrid = new Grid<DashboardContact>(contactStore, buildContactGridColumnModel()); contactTreeGrid.setBorders(true); contactTreeGrid.setTrackMouseOver(false); // Apply grid filters gridFilters = new GridFilters(); initGridFilters(); contactTreeGrid.addPlugin(gridFilters); toolbar = new ToolBar(); addContactButton = new Button(I18N.CONSTANTS.addContact()); toolbar.add(addContactButton); importButton = new Button(I18N.CONSTANTS.importContact()); toolbar.add(importButton); // Preparing 'export' functionality. exportButton = new Button(I18N.CONSTANTS.exportAll(), IconImageBundle.ICONS.excel()); toolbar.add(exportButton); // Panel contactTreePanel = Panels.content(I18N.CONSTANTS.contacts()); contactTreePanel.setTopComponent(toolbar); contactTreePanel.setBottomComponent(pagingToolBar); } /** * {@inheritDoc} */ @Override public Widget asWidget() { return contactTreePanel; } /** * {@inheritDoc} */ @Override public void updateAccessibilityState(final boolean authorized) { contactTreePanel.removeAll(); if (authorized) { contactTreePanel.add(contactTreeGrid); } else { final HTML insufficient = new HTML(I18N.CONSTANTS.permViewContactsInsufficient()); insufficient.addStyleName(STYLE_IMPORTANT_LABEL); contactTreePanel.add(insufficient); } } /** * {@inheritDoc} */ @Override public ContentPanel getContactsPanel() { return contactTreePanel; } /** * {@inheritDoc} */ @Override public GridFilters getGridFilters() { return gridFilters; } /** * {@inheritDoc} */ @Override public Button getAddButton() { return addContactButton; } /** * {@inheritDoc} */ @Override public Button getImportButton() { return importButton; } /** * {@inheritDoc} */ @Override public Button getExportButton() { return exportButton; } /** * {@inheritDoc} */ @Override public Grid<DashboardContact> getGrid() { return contactTreeGrid; } @Override public void addContact(DashboardContact contact) { proxy.addContact(contact); pagingToolBar.refresh(); } @Override public void clearContacts() { proxy.clearContacts(); } /** * {@inheritDoc} */ @Override public ListStore<DashboardContact> getStore() { return contactTreeGrid.getStore(); } /** * {@inheritDoc} */ @Override public void setGridEventHandler(final GridEventHandler<DashboardContact> handler) { this.treeHandler = handler; } /** * {@inheritDoc} */ @Override public void updateToolbar(final boolean addContact, final boolean importContact, final boolean exportContact) { toolbar.remove(addContactButton); toolbar.remove(importButton); toolbar.remove(exportButton); if (addContact) { toolbar.add(addContactButton); } if (importContact) { toolbar.add(importButton); } if (exportContact) { toolbar.add(exportButton); } } /** * {@inheritDoc} */ @Override public void syncSize() { contactTreeGrid.syncSize(); } // --------------------------------------------------------------------------------------------------------- // // UTILITY METHODS. // // --------------------------------------------------------------------------------------------------------- /** * Builds and returns the columns model for the contacts tree grid. * * @return The contact tree grid columns model. */ private ColumnModel buildContactGridColumnModel() { final DateTimeFormat format = DateUtils.DATE_SHORT; // Type final ColumnConfig typeColumn = new ColumnConfig(ContactDTO.TYPE, I18N.CONSTANTS.contactTypeLabel(), 75); typeColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { ContactModelType type = (ContactModelType) model.get(property); String typeLabel = I18N.CONSTANTS.contactTypeIndividualLabel(); if(type == ContactModelType.ORGANIZATION) { typeLabel = I18N.CONSTANTS.contactTypeOrganizationLabel(); } return createContactGridText(typeLabel); } }); // Name final ColumnConfig nameColumn = new ColumnConfig(ContactDTO.NAME, I18N.CONSTANTS.contactName(), 100); nameColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { final Anchor nameLink = new Anchor((String) model.get(property)); nameLink.addClickHandler(new ClickHandler() { @Override public void onClick(ClickEvent event) { if (treeHandler == null) { N10N.warn("Not implemented yet."); return; } treeHandler.onRowClickEvent(model); } }); final com.google.gwt.user.client.ui.Grid panel = new com.google.gwt.user.client.ui.Grid(1, 1); panel.setCellPadding(0); panel.setCellSpacing(0); panel.setWidget(0, 0, nameLink); panel.getCellFormatter().addStyleName(0, 0, STYLE_CONTACT_GRID_NAME); return panel; } }); // Firstname final ColumnConfig firstnameColumn = new ColumnConfig(ContactDTO.FIRSTNAME, I18N.CONSTANTS.contactFirstName(), 75); firstnameColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { return createContactGridText((String) model.get(property)); } }); // Change type final ColumnConfig changeTypeColumn = new ColumnConfig(ContactHistory.FORMATTED_CHANGE_TYPE, I18N.CONSTANTS.contactChangeType(), 100); firstnameColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { return createContactGridText((String) model.get(property)); } }); // Change subject final ColumnConfig changeSubjectColumn = new ColumnConfig(ContactHistory.SUBJECT, I18N.CONSTANTS.contactChangeSubject(), 75); firstnameColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { return createContactGridText((String) model.get(property)); } }); // Change value final ColumnConfig changeValueColumn = new ColumnConfig(ContactHistory.FORMATTED_VALUE, I18N.CONSTANTS.contactChangeValue(), 75); firstnameColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { return createContactGridText((String) model.get(property)); } }); // Email final ColumnConfig emailColumn = new ColumnConfig(ContactDTO.EMAIL, I18N.CONSTANTS.contactEmailAddress(), 150); emailColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { return createContactGridText((String) model.get(property)); } }); emailColumn.setHidden(true); // Id final ColumnConfig idColumn = new ColumnConfig(ContactDTO.ID, I18N.CONSTANTS.contactId(), 100); emailColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { return createContactGridText((String) model.get(property)); } }); idColumn.setHidden(true); // Organization final ColumnConfig organizationColumn = new ColumnConfig(DashboardContact.PARENT_NAME, I18N.CONSTANTS.contactDirectMembership(), 100); organizationColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { return createContactGridText((String)model.get(property)); } }); organizationColumn.setHidden(true); // Root organization final ColumnConfig rootOrganizationColumn = new ColumnConfig(DashboardContact.ROOT_NAME, I18N.CONSTANTS.contactTopMembership(), 100); rootOrganizationColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { return createContactGridText((String)model.get(property)); } }); rootOrganizationColumn.setHidden(true); // Change date final ColumnConfig changeDateColumn = new ColumnConfig(ContactHistory.UPDATED_AT, I18N.CONSTANTS.contactChangeDate(), 100); changeDateColumn.setDateTimeFormat(format); firstnameColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { final Date d = model.get(property); return createContactGridText(d != null ? format.format(d) : ""); } }); changeDateColumn.setHidden(true); // Change comment final ColumnConfig changeCommentColumn = new ColumnConfig(ContactHistory.COMMENT, I18N.CONSTANTS.contactChangeComment(), 100); firstnameColumn.setRenderer(new GridCellRenderer<DashboardContact>() { @Override public Object render(final DashboardContact model, final String property, final ColumnData config, final int rowIndex, final int colIndex, final ListStore<DashboardContact> store, final Grid<DashboardContact> grid) { return createContactGridText((String) model.get(property)); } }); changeCommentColumn.setHidden(true); return new ColumnModel(Arrays.asList(typeColumn, nameColumn, firstnameColumn, changeTypeColumn, changeSubjectColumn, changeValueColumn, emailColumn, idColumn, organizationColumn, rootOrganizationColumn, changeDateColumn, changeCommentColumn)); } private static Widget createContactGridText(final String content) { final Html label = new Html(content); return label; } /** * Grid filters for contacts' TreeGrid. */ private void initGridFilters() { gridFilters.setLocal(false); // Data index of each filter should be identical with column id in ColumnConfig of TreeGrid. // Common filters gridFilters.addFilter(new StringFilter(ContactDTO.TYPE)); gridFilters.addFilter(new StringFilter(ContactDTO.NAME)); gridFilters.addFilter(new StringFilter(ContactDTO.FIRSTNAME)); gridFilters.addFilter(new StringFilter(ContactHistory.FORMATTED_CHANGE_TYPE)); gridFilters.addFilter(new StringFilter(ContactHistory.SUBJECT)); gridFilters.addFilter(new StringFilter(ContactHistory.FORMATTED_VALUE)); gridFilters.addFilter(new StringFilter(ContactDTO.EMAIL)); gridFilters.addFilter(new StringFilter(ContactDTO.ID)); gridFilters.addFilter(new StringFilter(DashboardContact.PARENT_NAME)); gridFilters.addFilter(new StringFilter(DashboardContact.ROOT_NAME)); gridFilters.addFilter(new DateFilter(ContactHistory.UPDATED_AT)); gridFilters.addFilter(new StringFilter(ContactHistory.COMMENT)); } }