New GroupTable data binding #718

This commit is contained in:
Yuriy Artamonov 2018-06-04 19:41:15 +04:00
parent e31111924d
commit 5e3a8ef4e0
49 changed files with 1129 additions and 1225 deletions

View File

@ -89,7 +89,7 @@ org.javassist/javassist = 3.22.0-GA
org.hibernate/hibernate-validator = 5.4.2.Final
org.glassfish.web/javax.el = 2.2.6
com.vaadin = 8.4.2-2-unstable
com.vaadin = 8.4.2-3-unstable
com.vaadin/vaadin-server = ${com.vaadin}
com.vaadin/vaadin-client = ${com.vaadin}
com.vaadin/vaadin-client-compiler = ${com.vaadin}

View File

@ -104,10 +104,10 @@ public class AttributeAccessSupport {
}
if (reset) {
component.setVisible(security.isEntityAttrReadPermitted(entityValueSource.getMetaClass(), propertyPath.toString()));
component.setVisible(security.isEntityAttrReadPermitted(entityValueSource.getEntityMetaClass(), propertyPath.toString()));
if (component instanceof Editable) {
((Editable) component).setEditable(security.isEntityAttrUpdatePermitted(entityValueSource.getMetaClass(), propertyPath.toString()));
((Editable) component).setEditable(security.isEntityAttrUpdatePermitted(entityValueSource.getEntityMetaClass(), propertyPath.toString()));
}
if (component instanceof Field) {
((Field) component).setRequired(propertyPath.getMetaProperty().isMandatory());
@ -156,7 +156,7 @@ public class AttributeAccessSupport {
protected SecurityState getSecurityState(Entity entity) {
if (entity instanceof BaseGenericIdEntity) {
return BaseEntityInternalAccess.getSecurityState((BaseGenericIdEntity) entity);
return BaseEntityInternalAccess.getSecurityState(entity);
} else {
return null;
}

View File

@ -140,7 +140,7 @@ public class UserBrowser extends AbstractLookup {
protected void initTimeZoneColumn() {
usersTable.addGeneratedColumn("timeZone", entity -> {
Label label = componentsFactory.createComponent(Label.class);
Label<String> label = componentsFactory.createComponent(Label.class);
if (Boolean.TRUE.equals(entity.getTimeZoneAuto())) {
label.setValue(messages.getMainMessage("timeZone.auto"));
} else if (entity.getTimeZone() != null) {

View File

@ -51,8 +51,8 @@
(ur.role.id in (?))
</custom>
</filter>
<!-- vaadin8 groupTable-->
<table id="usersTable" presentations="true" multiselect="true" width="100%">
<groupTable id="usersTable" presentations="true" multiselect="true" width="100%">
<actions>
<action id="create"/>
<action id="edit"/>
@ -84,6 +84,6 @@
<column id="changePasswordAtNextLogon"/>
</columns>
<rows datasource="usersDs"/>
</table>
</groupTable>
</layout>
</window>

View File

@ -18,6 +18,10 @@ package com.haulmont.cuba.gui.components;
import com.haulmont.chile.core.model.MetaPropertyPath;
import com.haulmont.cuba.core.entity.Entity;
import com.haulmont.cuba.gui.components.data.TableSource;
import com.haulmont.cuba.gui.components.data.table.CollectionDatasourceTableAdapter;
import com.haulmont.cuba.gui.components.data.table.GroupDatasourceTableAdapter;
import com.haulmont.cuba.gui.data.CollectionDatasource;
import com.haulmont.cuba.gui.data.GroupDatasource;
import com.haulmont.cuba.gui.data.GroupInfo;
@ -25,12 +29,26 @@ import javax.annotation.Nullable;
import java.util.List;
import java.util.Map;
/**
* todo JavaDoc
*
* @param <E>
*/
public interface GroupTable<E extends Entity> extends Table<E> {
String NAME = "groupTable";
@Deprecated
@Override
GroupDatasource getDatasource();
default GroupDatasource getDatasource() {
TableSource<E> tableSource = getTableSource();
if (tableSource == null) {
return null;
}
CollectionDatasourceTableAdapter adapter = (CollectionDatasourceTableAdapter) tableSource;
return (GroupDatasource) adapter.getDatasource();
}
/**
* Performs grouping by the given {@code properties}.

View File

@ -20,7 +20,7 @@ import com.haulmont.chile.core.model.MetaClass;
import com.haulmont.cuba.core.entity.Entity;
public interface EntityOptionsSource<E extends Entity> extends OptionsSource<E> {
MetaClass getMetaClass();
MetaClass getEntityMetaClass();
void setSelectedItem(E item);
}

View File

@ -24,7 +24,7 @@ import java.util.Collection;
// todo JavaDoc
public interface EntityTableSource<E extends Entity> extends TableSource<E> {
MetaClass getMetaClass();
MetaClass getEntityMetaClass();
// todo rename
Collection<MetaPropertyPath> getAutowiredProperties();

View File

@ -31,7 +31,7 @@ import java.util.function.Consumer;
* @param <V>
*/
public interface EntityValueSource<E extends Entity, V> extends ValueSource<V> {
MetaClass getMetaClass();
MetaClass getEntityMetaClass();
MetaPropertyPath getMetaPropertyPath();
E getItem();

View File

@ -0,0 +1,101 @@
/*
* Copyright (c) 2008-2018 Haulmont.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.haulmont.cuba.gui.components.data;
import com.haulmont.cuba.gui.data.GroupInfo;
import javax.annotation.Nullable;
import java.util.Collection;
import java.util.List;
public interface GroupTableSource<I> extends TableSource.Sortable<I> {
/**
* Perform grouping by the list of properties
*/
void groupBy(Object[] properties);
/**
* @return the list of root groups
*/
List<GroupInfo> rootGroups();
/**
* Indicates that group has nested groups
*/
boolean hasChildren(GroupInfo groupId);
/**
* @return the list of nested groups
*/
List<GroupInfo> getChildren(GroupInfo groupId);
/**
* @return the list of nested items
*/
List<I> getOwnChildItems(GroupInfo groupId);
/**
* @return the list of items from all nested group levels
*/
List<I> getChildItems(GroupInfo groupId);
/**
* @return the parent group of passed item
*/
@Nullable
GroupInfo getParentGroup(I item);
/**
* @return the path through all parent groups
*/
List<GroupInfo> getGroupPath(I item);
/**
* @return a group property
*/
Object getGroupProperty(GroupInfo groupId);
/**
* @return a group property value
*/
Object getGroupPropertyValue(GroupInfo groupId);
/**
* @return item ids that are contained in the selected group
*/
Collection<?> getGroupItemIds(GroupInfo groupId);
/**
* @return a count of items that are contained in the selected group
*/
int getGroupItemsCount(GroupInfo groupId);
/**
* Indicated that a datasource has groups
*/
boolean hasGroups();
/**
* @return group properties
*/
Collection<?> getGroupProperties();
/**
* Indicates that a group is contained in the groups tree
*/
boolean containsGroup(GroupInfo groupId);
}

View File

@ -43,7 +43,6 @@ public interface TableSource<I> {
}
Object getItemValue(Object itemId, Object propertyId);
void setItemValue(Object itemId, Object propertyId, Object newValue); // vaadin8 todo is not required
int size();
@ -80,6 +79,8 @@ public interface TableSource<I> {
interface Sortable<T> extends Ordered<T> {
void sort(Object[] propertyId, boolean[] ascending);
void resetSortOrder();
}
// todo

View File

@ -112,7 +112,7 @@ public class CollectionDatasourceOptions<E extends Entity<K>, K> implements Opti
}
@Override
public MetaClass getMetaClass() {
public MetaClass getEntityMetaClass() {
return datasource.getMetaClass();
}

View File

@ -28,7 +28,6 @@ import com.haulmont.cuba.gui.components.data.EntityTableSource;
import com.haulmont.cuba.gui.data.CollectionDatasource;
import com.haulmont.cuba.gui.data.Datasource;
import com.haulmont.cuba.gui.data.impl.CollectionDsHelper;
import org.apache.commons.lang3.NotImplementedException;
import javax.annotation.Nullable;
import java.util.Collection;
@ -116,12 +115,6 @@ public class CollectionDatasourceTableAdapter<E extends Entity<K>, K> implements
return datasource.getItemNN(itemId).getValueEx(propertyPath.toPathString());
}
@Override
public void setItemValue(Object itemId, Object propertyId, Object newValue) {
// vaadin8 todo
throw new NotImplementedException("todo");
}
@Override
public int size() {
return datasource.size();
@ -170,7 +163,7 @@ public class CollectionDatasourceTableAdapter<E extends Entity<K>, K> implements
}
@Override
public MetaClass getMetaClass() {
public MetaClass getEntityMetaClass() {
return datasource.getMetaClass();
}

View File

@ -0,0 +1,122 @@
/*
* Copyright (c) 2008-2018 Haulmont.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.haulmont.cuba.gui.components.data.table;
import com.haulmont.cuba.core.entity.Entity;
import com.haulmont.cuba.gui.components.data.GroupTableSource;
import com.haulmont.cuba.gui.data.CollectionDatasource;
import com.haulmont.cuba.gui.data.GroupDatasource;
import com.haulmont.cuba.gui.data.GroupInfo;
import javax.annotation.Nullable;
import java.util.Collection;
import java.util.List;
public class GroupDatasourceTableAdapter<E extends Entity<K>, K>
extends SortableCollectionDatasourceTableAdapter<E, K>
implements GroupTableSource<E> {
@SuppressWarnings("unchecked")
public GroupDatasourceTableAdapter(GroupDatasource<E, K> datasource) {
super((CollectionDatasource.Sortable<E, K>) datasource);
}
@SuppressWarnings("unchecked")
public GroupDatasource<E, K> getGroupDatasource() {
return (GroupDatasource<E, K>) datasource;
}
@Override
public void groupBy(Object[] properties) {
getGroupDatasource().groupBy(properties);
}
@Override
public List<GroupInfo> rootGroups() {
return getGroupDatasource().rootGroups();
}
@Override
public boolean hasChildren(GroupInfo groupId) {
return getGroupDatasource().hasChildren(groupId);
}
@Override
public List<GroupInfo> getChildren(GroupInfo groupId) {
return getGroupDatasource().getChildren(groupId);
}
@SuppressWarnings("unchecked")
@Override
public List<E> getOwnChildItems(GroupInfo groupId) {
return getGroupDatasource().getOwnChildItems(groupId);
}
@SuppressWarnings("unchecked")
@Override
public List<E> getChildItems(GroupInfo groupId) {
return getGroupDatasource().getChildItems(groupId);
}
@SuppressWarnings("unchecked")
@Nullable
@Override
public GroupInfo getParentGroup(E entity) {
return getGroupDatasource().getParentGroup(entity);
}
@SuppressWarnings("unchecked")
@Override
public List<GroupInfo> getGroupPath(E entity) {
return getGroupDatasource().getGroupPath(entity);
}
@Override
public Object getGroupProperty(GroupInfo groupId) {
return getGroupDatasource().getGroupProperty(groupId);
}
@Override
public Object getGroupPropertyValue(GroupInfo groupId) {
return getGroupDatasource().getGroupPropertyValue(groupId);
}
@Override
public Collection<?> getGroupItemIds(GroupInfo groupId) {
return getGroupDatasource().getGroupItemIds(groupId);
}
@Override
public int getGroupItemsCount(GroupInfo groupId) {
return getGroupDatasource().getGroupItemsCount(groupId);
}
@Override
public boolean hasGroups() {
return getGroupDatasource().hasGroups();
}
@Override
public Collection<?> getGroupProperties() {
return getGroupDatasource().getGroupProperties();
}
@Override
public boolean containsGroup(GroupInfo groupId) {
return getGroupDatasource().containsGroup(groupId);
}
}

View File

@ -82,4 +82,9 @@ public class SortableCollectionDatasourceTableAdapter<E extends Entity<K>, K>
getSortableDatasource().sort(new SortInfo[] {info});
}
}
@Override
public void resetSortOrder() {
getSortableDatasource().resetSortOrder();
}
}

View File

@ -26,7 +26,6 @@ import com.haulmont.cuba.core.global.MetadataTools;
import com.haulmont.cuba.gui.components.data.BindingState;
import com.haulmont.cuba.gui.components.data.EntityTableSource;
import com.haulmont.cuba.gui.model.CollectionContainer;
import org.apache.commons.lang3.NotImplementedException;
import javax.annotation.Nullable;
import java.util.Collection;
@ -83,12 +82,6 @@ public class CollectionContainerTableSource<E extends Entity> implements EntityT
return container.getItem(itemId).getValueEx(propertyPath.toPathString());
}
@Override
public void setItemValue(Object itemId, Object propertyId, Object newValue) {
// vaadin8 todo
throw new NotImplementedException("todo");
}
@Override
public int size() {
return container.getItems().size();
@ -151,7 +144,7 @@ public class CollectionContainerTableSource<E extends Entity> implements EntityT
}
@Override
public MetaClass getMetaClass() {
public MetaClass getEntityMetaClass() {
return container.getEntityMetaClass();
}
@ -165,4 +158,4 @@ public class CollectionContainerTableSource<E extends Entity> implements EntityT
// otherwise use all properties from meta-class
metadataTools.getPropertyPaths(container.getEntityMetaClass());
}
}
}

View File

@ -113,7 +113,7 @@ public class ContainerValueSource<E extends Entity, V> implements EntityValueSou
}
@Override
public MetaClass getMetaClass() {
public MetaClass getEntityMetaClass() {
return container.getEntityMetaClass();
}

View File

@ -81,7 +81,7 @@ public class DatasourceValueSource<E extends Entity, V> implements EntityValueSo
}
@Override
public MetaClass getMetaClass() {
public MetaClass getEntityMetaClass() {
return datasource.getMetaClass();
}

View File

@ -205,9 +205,8 @@ public class ValueBinder {
}
}
@SuppressWarnings("unchecked")
protected void sourceValueChanged(@SuppressWarnings("unused") ValueSource.ValueChangeEvent event) {
component.setValue((V) event.getValue());
protected void sourceValueChanged(ValueSource.ValueChangeEvent<V> event) {
component.setValue(event.getValue());
}
protected void sourceInstanceChanged(@SuppressWarnings("unused") EntityValueSource.InstanceChangeEvent<Entity> event) {

View File

@ -52,23 +52,23 @@ public interface GroupDatasource<T extends Entity<K>, K> extends CollectionDatas
/**
* @return the list of nested items
*/
List<Entity> getOwnChildItems(GroupInfo groupId);
List<T> getOwnChildItems(GroupInfo groupId);
/**
* @return the list of items from all nested group levels
*/
List<Entity> getChildItems(GroupInfo groupId);
List<T> getChildItems(GroupInfo groupId);
/**
* @return the parent group of passed item
*/
@Nullable
GroupInfo getParentGroup(Entity entity);
GroupInfo getParentGroup(T entity);
/**
* @return the path through all parent groups
*/
List<GroupInfo> getGroupPath(Entity entity);
List<GroupInfo> getGroupPath(T entity);
/**
* @return a group property
@ -104,4 +104,4 @@ public interface GroupDatasource<T extends Entity<K>, K> extends CollectionDatas
* Indicates that a group is contained in the groups tree
*/
boolean containsGroup(GroupInfo groupId);
}
}

View File

@ -23,10 +23,10 @@ public class GroupInfo<P> {
private LinkedMap groupingValues;
private P groupProperty;
@SuppressWarnings("unchecked")
public GroupInfo(LinkedMap groupingValues) {
this.groupingValues = new LinkedMap(groupingValues);
//noinspection unchecked
groupProperty = (P) groupingValues.get(groupingValues.size() - 1);
this.groupProperty = (P) groupingValues.get(groupingValues.size() - 1);
}
public Object getPropertyValue(P propertyPath) {
@ -49,9 +49,9 @@ public class GroupInfo<P> {
@Override
public String toString() {
final StringBuilder sb = new StringBuilder("{");
StringBuilder sb = new StringBuilder("{");
for (int groupIndex = 0; groupIndex < groupingValues.size(); groupIndex++) {
final Object value = groupingValues.getValue(groupIndex);
Object value = groupingValues.getValue(groupIndex);
sb.append("[")
.append(groupingValues.get(groupIndex))
.append(":")

View File

@ -27,7 +27,5 @@ import com.haulmont.cuba.core.entity.Entity;
public interface TreeTableDatasource <T extends Entity<K>, K>
extends HierarchicalDatasource<T, K> {
boolean isCaption(K itemId);
String getCaption(K itemId);
}
}

View File

@ -32,7 +32,7 @@ public abstract class AbstractTreeTableDatasource<T extends Entity<K>, K>
extends AbstractTreeDatasource<T, K>
implements TreeTableDatasource<T, K> {
private class TreeTableNodeComparator<T extends Entity> implements Comparator<Node<T>> {
protected static class TreeTableNodeComparator<T extends Entity> implements Comparator<Node<T>> {
private final EntityComparator<T> entityComparator;
private TreeTableNodeComparator(MetaPropertyPath propertyPath, boolean asc) {
@ -59,15 +59,15 @@ public abstract class AbstractTreeTableDatasource<T extends Entity<K>, K>
data.clear();
for (Node<T> node : tree.toList()) {
final T entity = node.getData();
final K id = entity.getId();
T entity = node.getData();
K id = entity.getId();
data.put(id, entity);
}
}
private void sort(List<Node<T>> nodesList) {
Collections.sort(nodesList, createEntityNodeComparator());
protected void sort(List<Node<T>> nodesList) {
nodesList.sort(createEntityNodeComparator());
for (Node<T> n :nodesList) {
if (n.getNumberOfChildren() > 0) {
sort(n.getChildren());

View File

@ -66,22 +66,22 @@ public class GroupDatasourceImpl<T extends Entity<K>, K>
}
@Override
public List<Entity> getOwnChildItems(GroupInfo groupId) {
public List<T> getOwnChildItems(GroupInfo groupId) {
return groupDelegate.getOwnChildItems(groupId);
}
@Override
public List<Entity> getChildItems(GroupInfo groupId) {
public List<T> getChildItems(GroupInfo groupId) {
return groupDelegate.getChildItems(groupId);
}
@Override
public GroupInfo getParentGroup(Entity entity) {
public GroupInfo getParentGroup(T entity) {
return groupDelegate.getParentGroup(entity);
}
@Override
public List<GroupInfo> getGroupPath(Entity entity) {
public List<GroupInfo> getGroupPath(T entity) {
return groupDelegate.getGroupPath(entity);
}

View File

@ -16,6 +16,7 @@
*/
package com.haulmont.cuba.gui.data.impl;
import com.google.common.collect.ImmutableList;
import com.haulmont.bali.util.Preconditions;
import com.haulmont.chile.core.model.MetaPropertyPath;
import com.haulmont.cuba.core.entity.Entity;
@ -25,18 +26,9 @@ import com.haulmont.cuba.gui.data.GroupInfo;
import com.haulmont.cuba.gui.data.PropertyDatasource;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.collections4.map.LinkedMap;
import org.apache.commons.lang.ArrayUtils;
import org.apache.commons.lang3.ArrayUtils;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.*;
import java.util.stream.Collectors;
public abstract class GroupDelegate<T extends Entity<K>, K> {
@ -114,10 +106,10 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
groupItems = new HashMap<>();
itemGroups = new HashMap<>();
final Collection<K> itemIds = datasource.getItemIds();
for (final K id : itemIds) {
final T item = datasource.getItem(id);
GroupInfo<MetaPropertyPath> groupInfo = groupItems(0, null, roots, item, new LinkedMap());
Collection<K> itemIds = datasource.getItemIds();
for (K id : itemIds) {
T item = datasource.getItem(id);
GroupInfo<MetaPropertyPath> groupInfo = groupItems(0, null, roots, item, new LinkedMap<>());
if (groupInfo == null) {
throw new IllegalStateException("Item group cannot be NULL");
@ -129,8 +121,8 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
}
protected GroupInfo<MetaPropertyPath> groupItems(int propertyIndex, GroupInfo parent, List<GroupInfo> children,
T item, final LinkedMap groupValues) {
final MetaPropertyPath property = (MetaPropertyPath) groupProperties[propertyIndex++];
T item, LinkedMap<MetaPropertyPath, Object> groupValues) {
MetaPropertyPath property = (MetaPropertyPath) groupProperties[propertyIndex++];
Object itemValue = getValueByProperty(item, property);
groupValues.put(property, itemValue);
@ -159,16 +151,16 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
protected void doGroupSort(CollectionDatasource.Sortable.SortInfo<MetaPropertyPath>[] sortInfo) {
if (hasGroups()) {
final MetaPropertyPath propertyPath = sortInfo[0].getPropertyPath();
final boolean asc = CollectionDatasource.Sortable.Order.ASC.equals(sortInfo[0].getOrder());
MetaPropertyPath propertyPath = sortInfo[0].getPropertyPath();
boolean asc = CollectionDatasource.Sortable.Order.ASC.equals(sortInfo[0].getOrder());
final int index = Arrays.asList(groupProperties).indexOf(propertyPath);
int index = ArrayUtils.indexOf(groupProperties, propertyPath);
if (index > -1) {
if (index == 0) { // Sort roots
roots.sort(new GroupInfoComparator(asc));
} else {
final Object parentProperty = groupProperties[index - 1];
for (final Map.Entry<GroupInfo, List<GroupInfo>> entry : children.entrySet()) {
Object parentProperty = groupProperties[index - 1];
for (Map.Entry<GroupInfo, List<GroupInfo>> entry : children.entrySet()) {
Object property = entry.getKey().getProperty();
if (property.equals(parentProperty)) {
entry.getValue().sort(new GroupInfoComparator(asc));
@ -176,8 +168,8 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
}
}
} else {
final Set<GroupInfo> groups = parents.keySet();
for (final GroupInfo groupInfo : groups) {
Set<GroupInfo> groups = parents.keySet();
for (GroupInfo groupInfo : groups) {
List<K> items = groupItems.get(groupInfo);
if (items != null) {
items.sort(new EntityByIdComparator<>(propertyPath, datasource, asc));
@ -207,6 +199,14 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
return Collections.emptyList();
}
// return collection as is
public List<GroupInfo> getChildrenInternal(GroupInfo groupId) {
if (hasChildren(groupId)) {
return children.get(groupId);
}
return Collections.emptyList();
}
public Object getGroupProperty(GroupInfo groupId) {
if (containsGroup(groupId)) {
return groupId.getProperty();
@ -225,13 +225,13 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
if (containsGroup(group)) {
List<K> itemIds;
if ((itemIds = groupItems.get(group)) == null) {
itemIds = new LinkedList<>();
final List<GroupInfo> children = getChildren(group);
for (final GroupInfo child : children) {
itemIds = new ArrayList<>();
List<GroupInfo> children = getChildrenInternal(group);
for (GroupInfo child : children) {
itemIds.addAll(getGroupItemIds(child));
}
}
return Collections.unmodifiableList(itemIds);
return ImmutableList.copyOf(itemIds);
}
return Collections.emptyList();
}
@ -241,8 +241,8 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
List<K> itemIds;
if ((itemIds = groupItems.get(groupId)) == null) {
int count = 0;
final List<GroupInfo> children = getChildren(groupId);
for (final GroupInfo child : children) {
List<GroupInfo> children = getChildrenInternal(groupId);
for (GroupInfo child : children) {
count += getGroupItemsCount(child);
}
return count;
@ -279,7 +279,7 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
}
}
public List<Entity> getOwnChildItems(GroupInfo groupId) {
public List<T> getOwnChildItems(GroupInfo groupId) {
if (groupItems == null) {
return Collections.emptyList();
}
@ -293,28 +293,25 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
return Collections.emptyList();
}
public List<Entity> getChildItems(GroupInfo groupId) {
public List<T> getChildItems(GroupInfo groupId) {
if (groupItems == null) {
return Collections.emptyList();
}
if (containsGroup(groupId)) {
List<Entity> entities = new ArrayList<>();
List<T> entities = new ArrayList<>();
// if current group contains other groups
if (hasChildren(groupId)) {
List<GroupInfo> children = getChildren(groupId);
List<GroupInfo> children = getChildrenInternal(groupId);
for (GroupInfo childGroup : children) {
entities.addAll(getChildItems(childGroup));
}
}
// if current group contains only items
List<K> idsList = groupItems.get(groupId);
if (CollectionUtils.isNotEmpty(idsList)) {
entities.addAll(idsList.stream()
.map(id -> datasource.getItem(id))
.collect(Collectors.toList()));
for (K id : groupItems.getOrDefault(groupId, Collections.emptyList())) {
T item = datasource.getItem(id);
entities.add(item);
}
return entities;
@ -322,9 +319,8 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
return Collections.emptyList();
}
@SuppressWarnings({"SuspiciousMethodCalls", "unchecked"})
public GroupInfo getParentGroup(Entity entity) {
K id = (K) entity.getId();
public GroupInfo getParentGroup(T entity) {
K id = entity.getId();
if (!datasource.containsItem(id)) {
throw new IllegalArgumentException("Datasource doesn't contain passed entity");
}
@ -335,9 +331,8 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
return itemGroups.get(entity.getId());
}
@SuppressWarnings({"SuspiciousMethodCalls", "unchecked"})
public List<GroupInfo> getGroupPath(Entity entity) {
K id = (K) entity.getId();
public List<GroupInfo> getGroupPath(T entity) {
K id = entity.getId();
if (!datasource.containsItem(id)) {
throw new IllegalArgumentException("Datasource doesn't contain passed entity");
}
@ -350,12 +345,12 @@ public abstract class GroupDelegate<T extends Entity<K>, K> {
if (groupInfo == null) {
return Collections.emptyList();
}
List<GroupInfo> parentGroups = new LinkedList<>();
LinkedList<GroupInfo> parentGroups = new LinkedList<>();
parentGroups.add(groupInfo);
GroupInfo parent = parents.get(groupInfo);
while (parent != null) {
parentGroups.add(0, parent);
parentGroups.addFirst(parent);
parent = parents.get(parent);
}

View File

@ -100,22 +100,22 @@ public class GroupPropertyDatasourceImpl<T extends Entity<K>, K>
}
@Override
public List<Entity> getOwnChildItems(GroupInfo groupId) {
public List<T> getOwnChildItems(GroupInfo groupId) {
return groupDelegate.getOwnChildItems(groupId);
}
@Override
public List<Entity> getChildItems(GroupInfo groupId) {
public List<T> getChildItems(GroupInfo groupId) {
return groupDelegate.getChildItems(groupId);
}
@Override
public GroupInfo getParentGroup(Entity entity) {
public GroupInfo getParentGroup(T entity) {
return groupDelegate.getParentGroup(entity);
}
@Override
public List<GroupInfo> getGroupPath(Entity entity) {
public List<GroupInfo> getGroupPath(T entity) {
return groupDelegate.getGroupPath(entity);
}
}

View File

@ -60,7 +60,7 @@ public class CubaGroupTableWidget extends CubaScrollTableWidget {
private void addGroupColumn(String colKey) {
if (groupColumns == null) {
groupColumns = new HashSet<String>();
groupColumns = new HashSet<>();
}
groupColumns.add(colKey);
}
@ -131,7 +131,7 @@ public class CubaGroupTableWidget extends CubaScrollTableWidget {
// CAUTION This method copied from VScrollTable
// Added grouping support
final int oldIndex = getColIndexByKey(columnKey);
int oldIndex = getColIndexByKey(columnKey);
// Change header order
tHead.moveCell(oldIndex, newIndex);
@ -166,7 +166,7 @@ public class CubaGroupTableWidget extends CubaScrollTableWidget {
}
}
final String oldKeyOnNewIndex = visibleColOrder[newIndex];
String oldKeyOnNewIndex = visibleColOrder[newIndex];
if (showRowHeaders) {
newIndex--; // columnOrder don't have rowHeader
}
@ -183,7 +183,7 @@ public class CubaGroupTableWidget extends CubaScrollTableWidget {
}
// finally we can build the new columnOrder for server
final String[] newOrder = new String[columnOrder.length];
String[] newOrder = new String[columnOrder.length];
for (int i = 0, j = 0; j < newOrder.length; i++) {
if (j == newIndex) {
newOrder[j] = columnKey;
@ -542,7 +542,7 @@ public class CubaGroupTableWidget extends CubaScrollTableWidget {
}
private void calcAndSetWidthForSpannedCell() {
final int cells = tHead.getVisibleCellCount();
int cells = tHead.getVisibleCellCount();
for (int i = 0; i < groupColIndex; i++) {
int w = CubaGroupTableWidget.this.getColWidth(getColKeyByIndex(i));
if (w < 0) {

View File

@ -18,7 +18,7 @@ package com.haulmont.cuba.web.widgets;
import com.haulmont.cuba.web.widgets.data.AggregationContainer;
import com.haulmont.cuba.web.widgets.data.GroupTableContainer;
import com.haulmont.cuba.web.widgets.data.util.GroupTableContainerWrapper;
import com.haulmont.cuba.web.widgets.data.util.NullGroupTableContainer;
import com.vaadin.server.KeyMapper;
import com.vaadin.server.PaintException;
import com.vaadin.server.PaintTarget;
@ -29,6 +29,7 @@ import org.apache.commons.collections4.CollectionUtils;
import javax.annotation.Nullable;
import java.util.*;
import java.util.stream.Collectors;
@SuppressWarnings("deprecation")
public class CubaGroupTable extends CubaTable implements GroupTableContainer {
@ -71,11 +72,13 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
@Override
public void setContainerDataSource(Container newDataSource) {
if (newDataSource == null) {
newDataSource = new IndexedContainer();
if (newDataSource == null || newDataSource instanceof IndexedContainer) { // if it is just created
newDataSource = new NullGroupTableContainer(new IndexedContainer());
} else if (!(newDataSource instanceof GroupTableContainer)) {
throw new IllegalArgumentException("CubaGroupTable supports only GroupTableContainer");
}
super.setContainerDataSource(new GroupTableContainerWrapper(newDataSource));
super.setContainerDataSource(newDataSource);
}
@Override
@ -83,11 +86,11 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
super.paintContent(target);
if (hasGroups()) {
final Collection groupProperties = getGroupProperties();
final String[] groupColumns = new String[groupProperties.size()];
Collection groupProperties = getGroupProperties();
String[] groupColumns = new String[groupProperties.size()];
int index = 0;
for (final Object groupColumnId : groupProperties) {
for (Object groupColumnId : groupProperties) {
groupColumns[index++] = _columnIdMap().key(groupColumnId);
}
target.addVariable(this, "groupColumns", groupColumns);
@ -108,8 +111,8 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
} else if (variables.containsKey("groupedcolumns")) {
focus();
final Object[] ids = (Object[]) variables.get("groupedcolumns");
final Object[] groupProperties = new Object[ids.length];
Object[] ids = (Object[]) variables.get("groupedcolumns");
Object[] groupProperties = new Object[ids.length];
for (int i = 0; i < ids.length; i++) {
groupProperties[i] = _columnIdMap().get(ids[i].toString());
}
@ -128,15 +131,16 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
}
if (variables.containsKey("collapsedcolumns")) {
final Object[] ids = (Object[]) variables
.get("collapsedcolumns");
Set<Object> idSet = new HashSet<>();
Object[] ids = (Object[]) variables.get("collapsedcolumns");
Set<Object> idSet = ids.length > 0 ? new HashSet<>() : Collections.emptySet();
for (Object id : ids) {
idSet.add(_columnIdMap().get(id.toString()));
}
boolean needToRegroup = false;
final List<Object> groupProperties = new ArrayList<>(getGroupProperties());
List<Object> groupProperties = new ArrayList<>(getGroupProperties());
for (int index = 0; index < groupProperties.size(); index++) {
final Object propertyId = groupProperties.get(index);
if (idSet.contains(propertyId)) {
@ -150,14 +154,16 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
}
}
if ((hasGroupDisallowedProperties(newGroupProperties) || fixedGrouping) && isGroupsChanged(newGroupProperties)) {
if ((hasGroupDisallowedProperties(newGroupProperties) || fixedGrouping)
&& isGroupsChanged(newGroupProperties)) {
requestColumnReorderingAllowed = false;
markAsDirty();
}
super.changeVariables(source, variables);
if (!(hasGroupDisallowedProperties(newGroupProperties) || fixedGrouping) && newGroupProperties != null && isGroupsChanged(newGroupProperties)) {
if (!(hasGroupDisallowedProperties(newGroupProperties) || fixedGrouping)
&& newGroupProperties != null && isGroupsChanged(newGroupProperties)) {
groupBy(newGroupProperties, true);
}
@ -250,6 +256,7 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
return !isGroup(itemId);
}
@SuppressWarnings("unchecked")
@Override
protected void paintRowAttributes(PaintTarget target, Object itemId) throws PaintException {
super.paintRowAttributes(target, itemId);
@ -262,11 +269,14 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
if (isGroup(itemId)) {
target.addAttribute("colKey", _columnIdMap().key(getGroupProperty(itemId)));
target.addAttribute("groupKey", groupIdMap.key(itemId));
if (isExpanded(itemId))
target.addAttribute("expanded", true);
final Object propertyValue = getGroupPropertyValue(itemId);
target.addAttribute("groupCaption", formatGroupPropertyValue(itemId, propertyValue));
if (isExpanded(itemId)) {
target.addAttribute("expanded", true);
}
Object propertyValue = getGroupPropertyValue(itemId);
String formattedValue = formatGroupPropertyValue(itemId, propertyValue);
target.addAttribute("groupCaption", formattedValue);
if (hasAggregation) {
paintGroupAggregation(target, itemId,
@ -279,11 +289,9 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
@Override
protected Collection<?> getAggregationItemIds() {
if (hasGroups()) {
List itemIds = new LinkedList();
for (final Object groupId : rootGroups()) {
itemIds.addAll(getGroupItemIds(groupId));
}
return itemIds;
return rootGroups().stream()
.flatMap(groupId -> getGroupItemIds(groupId).stream())
.collect(Collectors.toList());
} else {
return items.getItemIds();
}
@ -293,10 +301,10 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
throws PaintException {
boolean paintGroupProperty = false;
final Collection groupProperties = getGroupProperties();
final Object groupProperty = getGroupProperty(groupId);
Collection groupProperties = getGroupProperties();
Object groupProperty = getGroupProperty(groupId);
for (final Object columnId : _visibleColumns()) {
for (Object columnId : _visibleColumns()) {
if (columnId == null || isColumnCollapsed(columnId)) {
continue;
}
@ -310,7 +318,7 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
if (getCellStyleGenerator() != null) {
String cellStyle = getCellStyleGenerator().getStyle(this, null, columnId);
if (cellStyle != null && !cellStyle.equals("")) {
if (cellStyle != null && !cellStyle.isEmpty()) {
target.addAttribute("style-" + _columnIdMap().key(columnId), cellStyle + "-ag");
}
}
@ -327,26 +335,22 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
@Override
protected LinkedHashSet<Object> getItemIdsInRange(Object startItemId, final int length) {
Set<Object> rootIds = super.getItemIdsInRange(startItemId, length);
LinkedHashSet<Object> ids = new LinkedHashSet<>();
for (Object itemId: rootIds) {
// actual implementation moved to WebGroupTable
ids.add(itemId);
}
return ids;
// actual implementation moved to WebGroupTable
return new LinkedHashSet<>(rootIds);
}
@Override
protected boolean isColumnNeedsToRefreshRendered(Object colId) {
final GroupTableContainer items = (GroupTableContainer) this.items;
final boolean groupped = items.hasGroups();
GroupTableContainer items = (GroupTableContainer) this.items;
boolean groupped = items.hasGroups();
return !groupped || !getGroupProperties().contains(colId);
}
@Override
protected boolean isItemNeedsToRefreshRendered(Object itemId) {
final GroupTableContainer items = (GroupTableContainer) this.items;
final boolean groupped = items.hasGroups();
GroupTableContainer items = (GroupTableContainer) this.items;
boolean groupped = items.hasGroups();
return !groupped || !items.isGroup(itemId);
}
@ -358,7 +362,7 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
}
protected void expandAllInGroup(Object id, boolean rerender) {
final int pageIndex = getCurrentPageFirstItemIndex();
int pageIndex = getCurrentPageFirstItemIndex();
expandAllInGroup(id);
if (isMultiSelect()) {
selectAllInGroup(id);
@ -387,7 +391,7 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
}
protected void expand(Object id, boolean rerender) {
final int pageIndex = getCurrentPageFirstItemIndex();
int pageIndex = getCurrentPageFirstItemIndex();
((GroupTableContainer) items).expand(id);
setCurrentPageFirstItemIndex(pageIndex, false);
if (rerender) {
@ -398,7 +402,7 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
}
protected void collapse(Object id, boolean rerender) {
final int pageIndex = getCurrentPageFirstItemIndex();
int pageIndex = getCurrentPageFirstItemIndex();
((GroupTableContainer) items).collapse(id);
setCurrentPageFirstItemIndex(pageIndex, false);
if (rerender) {
@ -436,17 +440,19 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
if (!_columnGenerators().isEmpty()) {
List<Object> notGeneratedGroupProps = new ArrayList<>();
for (Object id : groupProperties) {
if (!_columnGenerators().containsKey(id) || isNonGeneratedProperty(id))
if (!_columnGenerators().containsKey(id) || isNonGeneratedProperty(id)) {
notGeneratedGroupProps.add(id);
}
}
return notGeneratedGroupProps;
} else
} else {
return groupProperties;
}
}
@Override
public void expandAll() {
final int pageIndex = getCurrentPageFirstItemIndex();
int pageIndex = getCurrentPageFirstItemIndex();
((GroupTableContainer) items).expandAll();
setCurrentPageFirstItemIndex(pageIndex, false);
resetPageBuffer();
@ -461,7 +467,7 @@ public class CubaGroupTable extends CubaTable implements GroupTableContainer {
@Override
public void collapseAll() {
final int pageIndex = getCurrentPageFirstItemIndex();
int pageIndex = getCurrentPageFirstItemIndex();
((GroupTableContainer) items).collapseAll();
setCurrentPageFirstItemIndex(pageIndex, false);
resetPageBuffer();

View File

@ -21,8 +21,7 @@ import com.haulmont.cuba.web.widgets.client.table.CubaTableClientRpc;
import com.haulmont.cuba.web.widgets.client.table.CubaTableServerRpc;
import com.haulmont.cuba.web.widgets.client.table.CubaTableState;
import com.haulmont.cuba.web.widgets.data.AggregationContainer;
import com.haulmont.cuba.web.widgets.data.PropertyValueStringify;
import com.haulmont.cuba.web.widgets.data.TableContainer;
import com.haulmont.cuba.web.widgets.data.TableSortableContainer;
import com.vaadin.event.Action;
import com.vaadin.event.ActionManager;
import com.vaadin.event.ShortcutListener;
@ -44,7 +43,7 @@ import java.util.function.Function;
import static com.google.common.base.Preconditions.checkNotNull;
public class CubaTable extends com.vaadin.v7.ui.Table implements TableContainer, CubaEnhancedTable {
public class CubaTable extends com.vaadin.v7.ui.Table implements TableSortableContainer, CubaEnhancedTable {
protected List<Object> editableColumns;
@ -252,10 +251,6 @@ public class CubaTable extends com.vaadin.v7.ui.Table implements TableContainer,
return customCellValueFormatter.getFormattedValue(rowId, colId, property);
}
if (property instanceof PropertyValueStringify) {
return ((PropertyValueStringify) property).getFormattedValue();
}
return super.formatPropertyValue(rowId, colId, property);
}
@ -420,8 +415,8 @@ public class CubaTable extends com.vaadin.v7.ui.Table implements TableContainer,
sortContainerPropertyId = null;
sortAscending = true;
if (items instanceof TableContainer) {
((TableContainer) items).resetSortOrder();
if (items instanceof TableSortableContainer) {
((TableSortableContainer) items).resetSortOrder();
}
}

View File

@ -22,8 +22,7 @@ import com.haulmont.cuba.web.widgets.client.table.CubaTableClientRpc;
import com.haulmont.cuba.web.widgets.client.table.CubaTableServerRpc;
import com.haulmont.cuba.web.widgets.client.treetable.CubaTreeTableState;
import com.haulmont.cuba.web.widgets.data.AggregationContainer;
import com.haulmont.cuba.web.widgets.data.PropertyValueStringify;
import com.haulmont.cuba.web.widgets.data.TableContainer;
import com.haulmont.cuba.web.widgets.data.TableSortableContainer;
import com.haulmont.cuba.web.widgets.data.TreeTableContainer;
import com.haulmont.cuba.web.widgets.data.util.TreeTableContainerWrapper;
import com.vaadin.event.Action;
@ -48,6 +47,7 @@ import java.util.function.Function;
import static com.google.common.base.Preconditions.checkNotNull;
@SuppressWarnings("deprecation")
public class CubaTreeTable extends com.vaadin.v7.ui.TreeTable implements TreeTableContainer, CubaEnhancedTable {
protected LinkedList<Object> editableColumns = null;
@ -78,6 +78,8 @@ public class CubaTreeTable extends com.vaadin.v7.ui.TreeTable implements TreeTab
protected Function<Object, Resource> iconProvider;
protected SpecificVariablesHandler specificVariablesHandler;
protected CellValueFormatter customCellValueFormatter;
public CubaTreeTable() {
//noinspection Convert2Lambda
registerRpc(new CubaTableServerRpc() {
@ -237,12 +239,6 @@ public class CubaTreeTable extends com.vaadin.v7.ui.TreeTable implements TreeTab
}
}
@Override
public boolean isCaption(Object itemId) {
return items instanceof TreeTableContainer
&& ((TreeTableContainer) items).isCaption(itemId);
}
@Override
public String getCaption(Object itemId) {
return ((TreeTableContainer) items).getCaption(itemId);
@ -416,8 +412,8 @@ public class CubaTreeTable extends com.vaadin.v7.ui.TreeTable implements TreeTab
@Override
protected String formatPropertyValue(Object rowId, Object colId, Property<?> property) {
if (property instanceof PropertyValueStringify) {
return ((PropertyValueStringify) property).getFormattedValue();
if (this.customCellValueFormatter != null) {
return customCellValueFormatter.getFormattedValue(rowId, colId, property);
}
return super.formatPropertyValue(rowId, colId, property);
@ -430,7 +426,7 @@ public class CubaTreeTable extends com.vaadin.v7.ui.TreeTable implements TreeTab
newDataSource = new HierarchicalContainer();
}
super.setContainerDataSource(new TreeTableContainerWrapper(newDataSource));
super.setContainerDataSource(new TreeTableContainerWrapper((TreeTableContainer) newDataSource));
}
public void expandAll() {
@ -497,8 +493,8 @@ public class CubaTreeTable extends com.vaadin.v7.ui.TreeTable implements TreeTab
sortContainerPropertyId = null;
sortAscending = true;
if (items instanceof TableContainer) {
((TableContainer) items).resetSortOrder();
if (items instanceof TableSortableContainer) {
((TableSortableContainer) items).resetSortOrder();
}
}
@ -930,13 +926,12 @@ public class CubaTreeTable extends com.vaadin.v7.ui.TreeTable implements TreeTab
@Override
public void setCustomCellValueFormatter(CellValueFormatter cellValueFormatter) {
// todo
this.customCellValueFormatter = cellValueFormatter;
}
@Override
public CellValueFormatter getCustomCellValueFormatter() {
// todo
return null;
return customCellValueFormatter;
}
@Override

View File

@ -18,8 +18,8 @@ package com.haulmont.cuba.web.widgets.data;
import com.vaadin.v7.data.Container;
import java.util.Map;
import java.util.Collection;
import java.util.Map;
public interface AggregationContainer extends Container {
@ -41,7 +41,7 @@ public interface AggregationContainer extends Container {
Map<Object, Object> aggregate(Context context);
class Context {
private final Collection itemIds;
private Collection itemIds;
public Context(Collection itemIds) {
this.itemIds = itemIds;

View File

@ -18,7 +18,7 @@ package com.haulmont.cuba.web.widgets.data;
import java.util.Collection;
public interface GroupTableContainer extends TableContainer {
public interface GroupTableContainer extends TableSortableContainer {
void groupBy(Object[] properties);
boolean isGroup(Object id);

View File

@ -1,22 +0,0 @@
/*
* Copyright (c) 2008-2017 Haulmont.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.haulmont.cuba.web.widgets.data;
public interface PropertyValueStringify {
String getFormattedValue();
}

View File

@ -1,26 +0,0 @@
/*
* Copyright (c) 2008-2016 Haulmont.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/
package com.haulmont.cuba.web.widgets.data;
import com.vaadin.v7.data.Container;
// todo rename, move to GUI
public interface TableContainer extends Container.Sortable {
void resetSortOrder();
}

View File

@ -12,13 +12,14 @@
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/
package com.haulmont.cuba.web.widgets.data;
import com.vaadin.v7.data.Container;
public interface DataGridContainer extends Container.Sortable {
public interface TableSortableContainer extends Container.Sortable {
void resetSortOrder();
}
}

View File

@ -18,9 +18,7 @@ package com.haulmont.cuba.web.widgets.data;
import com.vaadin.v7.data.Container;
public interface TreeTableContainer extends TableContainer, Container.Hierarchical {
boolean isCaption(Object itemId);
public interface TreeTableContainer extends TableSortableContainer, Container.Hierarchical {
String getCaption(Object itemId);
boolean setCaption(Object itemId, String caption);

View File

@ -1,251 +0,0 @@
/*
* Copyright (c) 2008-2016 Haulmont.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/
package com.haulmont.cuba.web.widgets.data.util;
import com.haulmont.cuba.web.widgets.data.AggregationContainer;
import com.haulmont.cuba.web.widgets.data.GroupTableContainer;
import com.haulmont.cuba.web.widgets.data.TableContainer;
import com.vaadin.v7.data.Container;
import com.vaadin.v7.data.util.ContainerOrderedWrapper;
import java.util.Collection;
import java.util.Map;
public class GroupTableContainerWrapper extends ContainerOrderedWrapper
implements GroupTableContainer, AggregationContainer {
private boolean isGroupTableContainer;
private GroupTableContainer groupTableContainer;
private Container container;
public GroupTableContainerWrapper(Container toBeWrapped) {
super(toBeWrapped);
isGroupTableContainer = toBeWrapped instanceof GroupTableContainer;
if (isGroupTableContainer)
groupTableContainer = (GroupTableContainer) toBeWrapped;
container = toBeWrapped;
}
@Override
public void groupBy(final Object[] properties) {
if (isGroupTableContainer) {
groupTableContainer.groupBy(properties);
} else {
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
}
@Override
public boolean isGroup(Object id) {
return isGroupTableContainer && groupTableContainer.isGroup(id);
}
@Override
public Collection<?> rootGroups() {
if (isGroupTableContainer) {
return groupTableContainer.rootGroups();
} else {
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
}
@Override
public boolean hasChildren(Object id) {
return isGroupTableContainer && groupTableContainer.hasChildren(id);
}
@Override
public Collection<?> getChildren(Object id) {
if (isGroupTableContainer) {
return groupTableContainer.getChildren(id);
} else {
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
}
@Override
public boolean hasGroups() {
return isGroupTableContainer && groupTableContainer.hasGroups();
}
@Override
public Object getGroupProperty(Object itemId) {
if (isGroupTableContainer) {
return groupTableContainer.getGroupProperty(itemId);
}
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
@Override
public Object getGroupPropertyValue(Object itemId) {
if (isGroupTableContainer) {
return groupTableContainer.getGroupPropertyValue(itemId);
}
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
@Override
public Collection<?> getGroupItemIds(Object itemId) {
if (isGroupTableContainer) {
return groupTableContainer.getGroupItemIds(itemId);
}
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
@Override
public int getGroupItemsCount(Object itemId) {
if (isGroupTableContainer) {
return groupTableContainer.getGroupItemsCount(itemId);
}
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
@Override
public Collection<?> getGroupProperties() {
if (isGroupTableContainer) {
return groupTableContainer.getGroupProperties();
}
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
@Override
public void expand(Object id) {
if (isGroupTableContainer) {
groupTableContainer.expand(id);
} else {
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
}
@Override
public boolean isExpanded(Object id) {
return isGroupTableContainer && groupTableContainer.isExpanded(id);
}
@Override
public void expandAll() {
if (isGroupTableContainer) {
groupTableContainer.expandAll();
} else {
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
}
@Override
public void collapseAll() {
if (isGroupTableContainer) {
groupTableContainer.collapseAll();
} else {
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
}
@Override
public void collapse(Object id) {
if (isGroupTableContainer) {
groupTableContainer.collapse(id);
} else {
throw new IllegalStateException("Wrapped container is not GroupTableContainer:"
+ container.getClass());
}
}
@Override
public Collection getAggregationPropertyIds() {
if (container instanceof AggregationContainer) {
return ((AggregationContainer) container).getAggregationPropertyIds();
}
throw new IllegalStateException("Wrapped container is not AggregationContainer: "
+ container.getClass());
}
@Override
public Type getContainerPropertyAggregation(Object propertyId) {
if (container instanceof AggregationContainer) {
return ((AggregationContainer) container).getContainerPropertyAggregation(propertyId);
}
throw new IllegalStateException("Wrapped container is not AggregationContainer: "
+ container.getClass());
}
@Override
public void addContainerPropertyAggregation(Object propertyId, Type type) {
if (container instanceof AggregationContainer) {
((AggregationContainer) container).addContainerPropertyAggregation(propertyId, type);
} else {
throw new IllegalStateException("Wrapped container is not AggregationContainer: "
+ container.getClass());
}
}
@Override
public void removeContainerPropertyAggregation(Object propertyId) {
if (container instanceof AggregationContainer) {
((AggregationContainer) container).removeContainerPropertyAggregation(propertyId);
} else {
throw new IllegalStateException("Wrapped container is not AggregationContainer: "
+ container.getClass());
}
}
@Override
public Map<Object, Object> aggregate(Context context) {
if (container instanceof AggregationContainer) {
return ((AggregationContainer) container).aggregate(context);
}
throw new IllegalStateException("Wrapped container is not AggregationContainer: "
+ container.getClass());
}
@Override
public void sort(Object[] propertyId, boolean[] ascending) {
if (container instanceof Sortable) {
((Sortable) container).sort(propertyId, ascending);
} else {
throw new IllegalStateException("Wrapped container is not Sortable: "
+ container.getClass());
}
}
@Override
public Collection<?> getSortableContainerPropertyIds() {
if (container instanceof Sortable) {
return ((Sortable) container).getSortableContainerPropertyIds();
}
throw new IllegalStateException("Wrapped container is not Sortable: "
+ container.getClass());
}
@Override
public void resetSortOrder() {
if (container instanceof TableContainer) {
((TableContainer) container).resetSortOrder();
}
}
}

View File

@ -0,0 +1,155 @@
/*
* Copyright (c) 2008-2018 Haulmont.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.haulmont.cuba.web.widgets.data.util;
import com.haulmont.cuba.web.widgets.data.AggregationContainer;
import com.haulmont.cuba.web.widgets.data.GroupTableContainer;
import com.vaadin.v7.data.Container;
import com.vaadin.v7.data.util.ContainerOrderedWrapper;
import java.util.Collection;
import java.util.Map;
@SuppressWarnings("deprecation")
public class NullGroupTableContainer extends ContainerOrderedWrapper
implements GroupTableContainer, AggregationContainer {
public static final String ERROR_MESSAGE = "Wrapped container is not GroupTableContainer";
public NullGroupTableContainer(Container groupTableContainer) {
super(groupTableContainer);
}
@Override
public void groupBy(Object[] properties) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public boolean isGroup(Object id) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public Collection<?> rootGroups() {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public boolean hasChildren(Object id) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public Collection<?> getChildren(Object id) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public boolean hasGroups() {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public Object getGroupProperty(Object itemId) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public Object getGroupPropertyValue(Object itemId) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public Collection<?> getGroupItemIds(Object itemId) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public int getGroupItemsCount(Object itemId) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public Collection<?> getGroupProperties() {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public void expand(Object id) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public boolean isExpanded(Object id) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public void expandAll() {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public void collapseAll() {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public void collapse(Object id) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public Collection getAggregationPropertyIds() {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public Type getContainerPropertyAggregation(Object propertyId) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public void addContainerPropertyAggregation(Object propertyId, Type type) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public void removeContainerPropertyAggregation(Object propertyId) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public Map<Object, Object> aggregate(Context context) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public void sort(Object[] propertyId, boolean[] ascending) {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public Collection<?> getSortableContainerPropertyIds() {
throw new IllegalStateException(ERROR_MESSAGE);
}
@Override
public void resetSortOrder() {
throw new IllegalStateException(ERROR_MESSAGE);
}
}

View File

@ -18,7 +18,6 @@
package com.haulmont.cuba.web.widgets.data.util;
import com.haulmont.cuba.web.widgets.data.AggregationContainer;
import com.haulmont.cuba.web.widgets.data.TableContainer;
import com.haulmont.cuba.web.widgets.data.TreeTableContainer;
import com.vaadin.v7.data.Container;
import com.vaadin.v7.data.Item;
@ -26,27 +25,25 @@ import com.vaadin.v7.data.util.ContainerHierarchicalWrapper;
import java.util.*;
@SuppressWarnings("deprecation")
public class TreeTableContainerWrapper
extends ContainerHierarchicalWrapper
implements TreeTableContainer, AggregationContainer, Container.Ordered, Container.Sortable {
implements TreeTableContainer, AggregationContainer, Container.Ordered {
protected Set<Object> expanded; // Contains expanded items ids
protected LinkedList<Object> inline; // Contains visible (including children of expanded items) items ids inline
protected Hashtable<Object, String> captions;
protected Map<Object, String> captions;
protected Object first;
protected boolean treeTableContainer;
public TreeTableContainerWrapper(Container toBeWrapped) {
public TreeTableContainerWrapper(TreeTableContainer toBeWrapped) {
super(toBeWrapped);
treeTableContainer = toBeWrapped instanceof TreeTableContainer;
inline = new LinkedList<>();
expanded = new HashSet<>();
captions = new Hashtable<>();
captions = new HashMap<>();
}
@Override
@ -58,10 +55,11 @@ public class TreeTableContainerWrapper
if (inline == null || expanded == null || captions == null) {
inline = new LinkedList<>();
expanded = new HashSet<>();
captions = new Hashtable<>();
captions = new HashMap<>();
} else {
inline.clear();
final Set<Object> s = new HashSet<>();
Set<Object> s = new HashSet<>();
s.addAll(expanded);
s.addAll(captions.keySet());
for (Object o : s) {
@ -110,14 +108,14 @@ public class TreeTableContainerWrapper
@Override
public boolean setParent(Object itemId, Object newParentId) {
if (itemId == null) {
throw new NullPointerException("Item id cannot be NULL");
throw new IllegalArgumentException("Item id cannot be NULL");
}
if (!_container().containsId(itemId)) {
return false;
}
final Object oldParentId = getParent(itemId);
Object oldParentId = getParent(itemId);
if ((newParentId == null && oldParentId == null)
|| (newParentId != null && newParentId.equals(oldParentId))) {
@ -126,7 +124,7 @@ public class TreeTableContainerWrapper
boolean b = super.setParent(itemId, newParentId);
if (b) {
final LinkedList<Object> inlineList = new LinkedList<>();
LinkedList<Object> inlineList = new LinkedList<>();
inlineList.add(itemId);
inlineList.addAll(getInlineChildren(itemId));
@ -207,57 +205,28 @@ public class TreeTableContainerWrapper
throw new UnsupportedOperationException();
}
@Override
public boolean isCaption(Object itemId) {
if (itemId != null) {
if (!treeTableContainer) {
return captions.containsKey(itemId);
} else {
return ((TreeTableContainer) _container()).isCaption(itemId);
}
}
throw new NullPointerException("Item id cannot be NULL");
}
@Override
public String getCaption(Object itemId) {
if (itemId != null) {
if (!treeTableContainer) {
return captions.get(itemId);
} else {
return ((TreeTableContainer) _container()).getCaption(itemId);
}
return captions.get(itemId);
}
throw new NullPointerException("Item id cannot be NULL");
throw new IllegalArgumentException("Item id cannot be NULL");
}
@Override
public boolean setCaption(Object itemId, String caption) {
if (itemId != null) {
if (!treeTableContainer) {
if (caption != null) {
captions.put(itemId, caption);
} else {
captions.remove(itemId);
}
return true;
} else {
return ((TreeTableContainer) _container()).setCaption(itemId, caption);
}
return _container().setCaption(itemId, caption);
}
throw new NullPointerException("Item id cannot be NULL");
throw new IllegalArgumentException("Item id cannot be NULL");
}
@Override
public int getLevel(Object itemId) {
if (itemId != null) {
if (!treeTableContainer) {
return getItemLevel(itemId);
} else {
return ((TreeTableContainer) _container()).getLevel(itemId);
}
return _container().getLevel(itemId);
}
throw new NullPointerException("Item id cannot be NULL");
throw new IllegalArgumentException("Item id cannot be NULL");
}
protected int getItemLevel(Object itemId) {
@ -272,14 +241,14 @@ public class TreeTableContainerWrapper
public boolean isExpanded(Object itemId) {
if (itemId == null) {
throw new NullPointerException("Item id cannot be NULL");
throw new IllegalArgumentException("Item id cannot be NULL");
}
return expanded.contains(itemId);
}
public boolean setExpanded(Object itemId) {
if (itemId == null) {
throw new NullPointerException("Item id cannot be NULL");
throw new IllegalArgumentException("Item id cannot be NULL");
}
if (areChildrenAllowed(itemId)) {
@ -301,28 +270,25 @@ public class TreeTableContainerWrapper
return false;
}
public boolean setCollapsed(Object itemId) {
public void setCollapsed(Object itemId) {
if (itemId == null) {
throw new NullPointerException("Item id cannot be NULL");
throw new IllegalArgumentException("Item id cannot be NULL");
}
if (areChildrenAllowed(itemId)) {
if (!isExpanded(itemId)) {
return true;
return;
}
if (containsInline(itemId)) {
final List<Object> inlineChildren = getInlineChildren(itemId);
List<Object> inlineChildren = getInlineChildren(itemId);
if (inlineChildren != null) {
inline.removeAll(inlineChildren);
}
}
expanded.remove(itemId);
return true;
}
return false;
}
public void expandAll() {
@ -331,7 +297,7 @@ public class TreeTableContainerWrapper
expandAll(rootItemIds());
} else {
if (_children() != null) {
for (final Object itemId : _children().keySet()) {
for (Object itemId : _children().keySet()) {
setExpanded(itemId);
}
}
@ -339,7 +305,7 @@ public class TreeTableContainerWrapper
}
protected void expandAll(Collection itemIds) {
for (final Object itemId : itemIds) {
for (Object itemId : itemIds) {
if (areChildrenAllowed(itemId) && hasChildren(itemId)) {
setExpanded(itemId);
expandAll(getChildren(itemId));
@ -368,7 +334,7 @@ public class TreeTableContainerWrapper
protected LinkedList<Object> getInlineChildren(Object itemId) {
if (areChildrenAllowed(itemId)) {
final LinkedList<Object> inlineChildren = new LinkedList<>();
LinkedList<Object> inlineChildren = new LinkedList<>();
if (isExpanded(itemId)) {
makeInlineElements(inlineChildren, getChildren(itemId));
}
@ -377,9 +343,9 @@ public class TreeTableContainerWrapper
return null;
}
private void makeInlineElements(final List<Object> inline, final Collection elements) {
private void makeInlineElements(List<Object> inline, Collection elements) {
if (elements != null) {
for (final Object e : elements) {
for (Object e : elements) {
inline.add(e);
if (areChildrenAllowed(e) && isExpanded(e)) {
makeInlineElements(inline, getChildren(e));
@ -415,19 +381,13 @@ public class TreeTableContainerWrapper
@Override
public void sort(Object[] propertyId, boolean[] ascending) {
if (_container() instanceof Sortable) {
((Sortable) _container()).sort(propertyId, ascending);
updateHierarchicalWrapper();
} else
throw new IllegalStateException("Wrapped container is not Sortable: " + _container().getClass());
_container().sort(propertyId, ascending);
updateHierarchicalWrapper();
}
@Override
public Collection getSortableContainerPropertyIds() {
if (_container() instanceof Sortable)
return ((Sortable) _container()).getSortableContainerPropertyIds();
else
throw new IllegalStateException("Wrapped container is not Sortable: " + _container().getClass());
return _container().getSortableContainerPropertyIds();
}
@Override
@ -479,8 +439,11 @@ public class TreeTableContainerWrapper
@Override
public void resetSortOrder() {
if (_container() instanceof TableContainer) {
((TableContainer) _container()).resetSortOrder();
}
_container().resetSortOrder();
}
@Override
protected TreeTableContainer _container() {
return (TreeTableContainer) super._container();
}
}

View File

@ -16,6 +16,7 @@
*/
package com.haulmont.cuba.web.gui.components;
import com.google.common.base.Strings;
import com.haulmont.bali.util.Dom4j;
import com.haulmont.bali.util.Preconditions;
import com.haulmont.chile.core.datatypes.Datatype;
@ -290,7 +291,6 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
}
}
@Override
public void setSelected(E item) {
if (item == null) {
@ -465,12 +465,15 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
columns.remove(column.getId());
columnsOrder.remove(column);
// vaadin8 it seems that it is not required
if (!(component.getContainerDataSource() instanceof com.vaadin.v7.data.Container.ItemSetChangeNotifier)) {
component.refreshRowCache();
}
column.setOwner(null);
}
// vaadin8 rework this cache
@SuppressWarnings("unchecked")
@Override
public Datasource getItemDatasource(Entity item) {
@ -590,7 +593,7 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
protected void enableEditableColumns(EntityTableSource<E> entityTableSource,
Collection<MetaPropertyPath> propertyIds) {
MetaClass metaClass = entityTableSource.getMetaClass();
MetaClass metaClass = entityTableSource.getEntityMetaClass();
List<MetaPropertyPath> editableColumns = new ArrayList<>(propertyIds.size());
for (MetaPropertyPath propertyId : propertyIds) {
@ -1030,26 +1033,21 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
if (styleProviders == null) {
return null;
}
TableSource<E> tableSource = getTableSource();
if (tableSource == null) {
return null;
}
E item = tableSource.getItem(itemId);
StringBuilder joinedStyle = null;
for (StyleProvider styleProvider : styleProviders) {
String styleName = styleProvider.getStyleName(item, propertyId == null ? null : propertyId.toString());
if (styleName != null) {
if (joinedStyle == null) {
joinedStyle = new StringBuilder(styleName);
} else {
joinedStyle.append(" ").append(styleName);
}
}
}
return joinedStyle != null ? joinedStyle.toString() : null;
String propertyStringId = propertyId == null ? null : propertyId.toString();
String joinedStyle = styleProviders.stream()
.map(sp -> sp.getStyleName(item, propertyStringId))
.filter(Objects::nonNull)
.collect(Collectors.joining(" "));
return Strings.emptyToNull(joinedStyle);
}
@Override
@ -1092,9 +1090,8 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
Window.Lookup lookup = (Window.Lookup) window;
com.haulmont.cuba.gui.components.Component lookupComponent = lookup.getLookupComponent();
if (lookupComponent != this)
action.actionPerform(WebAbstractTable.this);
else if (action.getId().equals(WindowDelegate.LOOKUP_ITEM_CLICK_ACTION_ID)) {
if (lookupComponent != this
|| WindowDelegate.LOOKUP_ITEM_CLICK_ACTION_ID.equals(action.getId())) {
action.actionPerform(WebAbstractTable.this);
}
}
@ -1237,14 +1234,14 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
.filter(c -> {
MetaPropertyPath propertyPath = c.getBoundProperty();
return propertyPath != null
&& security.isEntityAttrReadPermitted(entityTableSource.getMetaClass(), propertyPath.toPathString());
&& security.isEntityAttrReadPermitted(entityTableSource.getEntityMetaClass(), propertyPath.toPathString());
})
.map(Column::getBoundProperty)
.collect(Collectors.toList());
}
protected void setupColumnSettings(EntityTableSource<E> entityTableSource) {
MetaClass metaClass = entityTableSource.getMetaClass();
MetaClass metaClass = entityTableSource.getEntityMetaClass();
List<MetaPropertyPath> editableColumns = Collections.emptyList();
@ -1369,13 +1366,17 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
@SuppressWarnings("unchecked")
@Override
public void setDatasource(CollectionDatasource datasource) {
TableSource<E> tableSource;
if (datasource instanceof CollectionDatasource.Sortable) {
tableSource = new SortableCollectionDatasourceTableAdapter((CollectionDatasource.Sortable) datasource);
if (datasource == null) {
setTableSource(null);
} else {
tableSource = new CollectionDatasourceTableAdapter(datasource);
TableSource<E> tableSource;
if (datasource instanceof CollectionDatasource.Sortable) {
tableSource = new SortableCollectionDatasourceTableAdapter((CollectionDatasource.Sortable) datasource);
} else {
tableSource = new CollectionDatasourceTableAdapter(datasource);
}
setTableSource(tableSource);
}
setTableSource(tableSource);
}
protected boolean canBeSorted(@Nullable TableSource<E> tableSource) {
@ -1460,7 +1461,7 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
protected List<Object> getInitialVisibleColumnIds(EntityTableSource<E> entityTableSource) {
List<Object> result = new ArrayList<>();
MetaClass metaClass = entityTableSource.getMetaClass();
MetaClass metaClass = entityTableSource.getEntityMetaClass();
for (Column column : columnsOrder) {
if (column.getId() instanceof MetaPropertyPath) {
MetaPropertyPath propertyPath = (MetaPropertyPath) column.getId();
@ -1599,14 +1600,12 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
@Override
public int getRowHeaderWidth() {
// CAUTION: vaadin considers null as row header property id;
return component.getColumnWidth(null);
return component.getColumnWidth(ROW_HEADER_PROPERTY_ID);
}
@Override
public void setRowHeaderWidth(int width) {
// CAUTION: vaadin considers null as row header property id;
component.setColumnWidth(null, width);
component.setColumnWidth(ROW_HEADER_PROPERTY_ID, width);
}
@Override
@ -1658,7 +1657,7 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
}
protected void applyColumnSettings(Element element) {
final Element columnsElem = element.element("columns");
Element columnsElem = element.element("columns");
Object[] oldColumns = component.getVisibleColumns();
List<Object> newColumns = new ArrayList<>();
@ -1708,7 +1707,7 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
@SuppressWarnings("unchecked")
EntityTableSource<E> entityTableSource = (EntityTableSource) getTableSource();
MetaPropertyPath sortProperty = entityTableSource.getMetaClass().getPropertyPath(sortProp);
MetaPropertyPath sortProperty = entityTableSource.getEntityMetaClass().getPropertyPath(sortProp);
if (newColumns.contains(sortProperty)) {
boolean sortAscending = Boolean.parseBoolean(columnsElem.attributeValue("sortAscending"));
@ -1859,7 +1858,7 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
EntityTableSource<E> entityTableSource = (EntityTableSource<E>) getTableSource();
MetaPropertyPath targetCol = entityTableSource != null ?
entityTableSource.getMetaClass().getPropertyPath(columnId) : null;
entityTableSource.getEntityMetaClass().getPropertyPath(columnId) : null;
Object generatedColumnId = targetCol != null ? targetCol : columnId;
@ -1955,7 +1954,7 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
EntityTableSource<E> entityTableSource = (EntityTableSource<E>) getTableSource();
MetaPropertyPath targetCol = entityTableSource != null ?
entityTableSource.getMetaClass().getPropertyPath(columnId) : null;
entityTableSource.getEntityMetaClass().getPropertyPath(columnId) : null;
removeGeneratedColumnInternal(targetCol == null ? columnId : targetCol);
}
@ -2161,7 +2160,7 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
}
protected Map<Object, Object> __aggregate(AggregationContainer container, AggregationContainer.Context context) {
List<AggregationInfo> aggregationInfos = new LinkedList<>();
List<AggregationInfo> aggregationInfos = new ArrayList<>();
for (Object propertyId : container.getAggregationPropertyIds()) {
Table.Column column = columns.get(propertyId);
AggregationInfo aggregation = column.getAggregation();
@ -2245,8 +2244,7 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
boolean needReload = false;
if (isUsePresentations() && presentations != null) {
final Presentations p = getPresentations();
Presentations p = getPresentations();
if (p.getCurrent() != null && p.isAutoSave(p.getCurrent()) && needUpdatePresentation(variables)) {
Element e = p.getSettings(p.getCurrent());
@ -2469,7 +2467,7 @@ public abstract class WebAbstractTable<T extends com.vaadin.v7.ui.Table & CubaEn
EntityTableSource<E> entityTableSource = (EntityTableSource<E>) getTableSource();
propertyPath = entityTableSource != null ?
entityTableSource.getMetaClass().getPropertyPath(propertyId.toString()) : null;
entityTableSource.getEntityMetaClass().getPropertyPath(propertyId.toString()) : null;
}
if (propertyPath != null) {

View File

@ -53,7 +53,6 @@ import com.haulmont.cuba.web.gui.data.DataGridIndexedCollectionDsWrapper;
import com.haulmont.cuba.web.gui.data.SortableDataGridIndexedCollectionDsWrapper;
import com.haulmont.cuba.web.gui.icons.IconResolver;
import com.haulmont.cuba.web.widgets.*;
import com.haulmont.cuba.web.widgets.data.DataGridContainer;
import com.vaadin.contextmenu.Menu;
import com.vaadin.contextmenu.MenuItem;
import com.vaadin.event.ShortcutAction.KeyCode;
@ -2570,8 +2569,7 @@ public class WebDataGrid<E extends Entity> extends WebAbstractComponent<CubaGrid
}
protected class SortableDataGridDsWrapper
extends SortableDataGridIndexedCollectionDsWrapper
implements DataGridContainer {
extends SortableDataGridIndexedCollectionDsWrapper {
public SortableDataGridDsWrapper(CollectionDatasource.Indexed datasource,
Collection<MetaPropertyPath> properties,
@ -2607,13 +2605,6 @@ public class WebDataGrid<E extends Entity> extends WebAbstractComponent<CubaGrid
}
return ids;
}
@Override
public void resetSortOrder() {
if (datasource instanceof CollectionDatasource.Sortable) {
((CollectionDatasource.Sortable) datasource).resetSortOrder();
}
}
}
protected class RowStyleGeneratorAdapter implements Grid.RowStyleGenerator {

View File

@ -16,27 +16,23 @@
*/
package com.haulmont.cuba.web.gui.components;
import com.haulmont.bali.util.Preconditions;
import com.haulmont.chile.core.model.Instance;
import com.haulmont.chile.core.model.MetaClass;
import com.haulmont.chile.core.model.MetaPropertyPath;
import com.haulmont.cuba.core.app.dynamicattributes.DynamicAttributesUtils;
import com.haulmont.cuba.core.entity.Entity;
import com.haulmont.cuba.core.global.View;
import com.haulmont.cuba.gui.components.GroupTable;
import com.haulmont.cuba.gui.components.Table;
import com.haulmont.cuba.gui.components.data.GroupTableSource;
import com.haulmont.cuba.gui.components.data.TableSource;
import com.haulmont.cuba.gui.components.data.table.GroupDatasourceTableAdapter;
import com.haulmont.cuba.gui.data.CollectionDatasource;
import com.haulmont.cuba.gui.data.Datasource;
import com.haulmont.cuba.gui.data.GroupDatasource;
import com.haulmont.cuba.gui.data.GroupInfo;
import com.haulmont.cuba.gui.data.impl.CollectionDsListenersWrapper;
import com.haulmont.cuba.web.gui.data.ItemWrapper;
import com.haulmont.cuba.web.gui.data.SortableCollectionDsWrapper;
import com.haulmont.cuba.web.gui.components.table.GroupTableDataContainer;
import com.haulmont.cuba.web.gui.components.table.TableDataContainer;
import com.haulmont.cuba.web.widgets.CubaGroupTable;
import com.haulmont.cuba.web.widgets.CubaGroupTable.GroupAggregationContext;
import com.haulmont.cuba.web.widgets.data.AggregationContainer;
import com.haulmont.cuba.web.widgets.data.GroupTableContainer;
import com.vaadin.v7.data.Item;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang.StringUtils;
import org.dom4j.Element;
@ -47,6 +43,7 @@ import javax.annotation.Nullable;
import java.util.*;
import java.util.stream.Collectors;
import static com.google.common.base.Strings.emptyToNull;
import static com.haulmont.bali.util.Preconditions.checkNotNullArgument;
@SuppressWarnings("deprecation")
@ -60,59 +57,50 @@ public class WebGroupTable<E extends Entity> extends WebAbstractTable<CubaGroupT
protected GroupCellValueFormatter<E> groupCellValueFormatter;
public WebGroupTable() {
component = createGroupTableComponent();
component = createComponent();
}
@Override
public void setTableSource(TableSource<E> tableSource) {
if (tableSource != null &&
!(tableSource instanceof GroupTableSource)) {
throw new IllegalArgumentException("GroupTable supports only GroupTableSource data binding");
}
super.setTableSource(tableSource);
}
@SuppressWarnings("unchecked")
@Override
public void setDatasource(CollectionDatasource datasource) {
if (datasource == null) {
setTableSource(null);
} else {
if (!(datasource instanceof GroupDatasource)) {
throw new IllegalArgumentException("GroupTable supports only GroupDatasource");
}
setTableSource(new GroupDatasourceTableAdapter((GroupDatasource) datasource));
}
}
@Override
protected TableDataContainer<E> createTableDataContainer(TableSource<E> tableSource) {
return new GroupTableDataContainer<>((GroupTableSource<E>) tableSource, this);
}
@SuppressWarnings("unchecked")
@Override
protected void initComponent(CubaGroupTable component) {
super.initComponent(component);
// vaadin8 replace with method reference
component.setGroupPropertyValueFormatter(new AggregatableGroupPropertyValueFormatter());
component.setGroupPropertyValueFormatter((groupId, value) ->
formatAggregatableGroupPropertyValue((GroupInfo<MetaPropertyPath>) groupId, value)
);
}
protected CubaGroupTable createGroupTableComponent() {
return new CubaGroupTable() {
@Override
protected boolean isNonGeneratedProperty(Object id) {
return (id instanceof MetaPropertyPath);
}
@Override
public void groupBy(Object[] properties) {
groupBy(properties, rerender);
}
@Override
protected LinkedHashSet<Object> getItemIdsInRange(Object startItemId, final int length) {
Set<Object> rootIds = super.getItemIdsInRange(startItemId, length);
LinkedHashSet<Object> ids = new LinkedHashSet<>();
for (Object itemId: rootIds) {
if (itemId instanceof GroupInfo) {
if (!isExpanded(itemId)) {
Collection<?> itemIds = getGroupItemIds(itemId);
ids.addAll(itemIds);
expand(itemId, true);
}
List<GroupInfo> children = (List<GroupInfo>) getChildren(itemId);
for (GroupInfo groupInfo : children) {
if (!isExpanded(groupInfo)) {
expand(groupInfo, true);
}
}
} else {
ids.add(itemId);
}
}
return ids;
}
};
}
@Override
public GroupDatasource getDatasource() {
return (GroupDatasource) super.getDatasource();
protected CubaGroupTable createComponent() {
return new CubaGroupTableExt();
}
@Override
@ -130,13 +118,14 @@ public class WebGroupTable<E extends Entity> extends WebAbstractTable<CubaGroupT
groupPropertiesElement = element.addElement("groupProperties");
/* vaadin8 disabled temporarily
for (Object groupProperty : component.getGroupProperties()) {
if (getNotCollapsedColumns().contains(getColumn(groupProperty.toString()))) {
Column<E> column = getColumn(groupProperty.toString());
if (getNotCollapsedColumns().contains(column)) {
Element groupPropertyElement = groupPropertiesElement.addElement("property");
groupPropertyElement.addAttribute("id", groupProperty.toString());
}
}*/
}
return true;
}
@ -167,7 +156,8 @@ public class WebGroupTable<E extends Entity> extends WebAbstractTable<CubaGroupT
}
@Override
protected Map<Object, Object> __handleAggregationResults(AggregationContainer.Context context, Map<Object, Object> results) {
protected Map<Object, Object> __handleAggregationResults(AggregationContainer.Context context,
Map<Object, Object> results) {
if (context instanceof GroupAggregationContext) {
GroupAggregationContext groupContext = (GroupAggregationContext) context;
@ -198,7 +188,7 @@ public class WebGroupTable<E extends Entity> extends WebAbstractTable<CubaGroupT
}
protected List<Object> collectPropertiesByColumns(String... columnIds) {
List<Object> properties = new ArrayList<>();
List<Object> properties = new ArrayList<>(columnIds.length);
for (String columnId : columnIds) {
Column column = getColumn(columnId);
@ -223,7 +213,7 @@ public class WebGroupTable<E extends Entity> extends WebAbstractTable<CubaGroupT
@Override
public void groupBy(Object[] properties) {
Preconditions.checkNotNullArgument(properties);
checkNotNullArgument(properties);
validateProperties(properties);
component.groupBy(properties);
@ -232,14 +222,14 @@ public class WebGroupTable<E extends Entity> extends WebAbstractTable<CubaGroupT
@Override
public void groupByColumns(String... columnIds) {
Preconditions.checkNotNullArgument(columnIds);
checkNotNullArgument(columnIds);
groupBy(collectPropertiesByColumns(columnIds).toArray());
}
@Override
public void ungroupByColumns(String... columnIds) {
Preconditions.checkNotNullArgument(columnIds);
checkNotNullArgument(columnIds);
Object[] remainingGroups = CollectionUtils
.removeAll(component.getGroupProperties(), collectPropertiesByColumns(columnIds))
@ -376,37 +366,18 @@ public class WebGroupTable<E extends Entity> extends WebAbstractTable<CubaGroupT
}
if (itemId instanceof GroupInfo) {
List<GroupStyleProvider> groupStyleProviders = null;
GroupInfo groupInfo = (GroupInfo) itemId;
for (StyleProvider styleProvider : styleProviders) {
if (styleProvider instanceof GroupStyleProvider) {
if (groupStyleProviders == null) {
groupStyleProviders = new LinkedList<>();
}
String joinedStyle = styleProviders.stream()
.filter(sp -> sp instanceof GroupStyleProvider)
.map(sp -> ((GroupStyleProvider) sp).getStyleName(groupInfo))
.filter(Objects::nonNull)
.collect(Collectors.joining(" "));
groupStyleProviders.add((GroupStyleProvider) styleProvider);
}
}
if (groupStyleProviders != null) {
StringBuilder joinedStyle = null;
for (GroupStyleProvider groupStyleProvider : groupStyleProviders) {
String styleName = groupStyleProvider.getStyleName((GroupInfo) itemId);
if (styleName != null) {
if (joinedStyle == null) {
joinedStyle = new StringBuilder(styleName);
} else {
joinedStyle.append(" ").append(styleName);
}
}
}
return joinedStyle != null ? joinedStyle.toString() : null;
}
return emptyToNull(joinedStyle);
} else {
return super.getGeneratedCellStyle(itemId, propertyId);
}
return null;
}
@Override
@ -414,495 +385,60 @@ public class WebGroupTable<E extends Entity> extends WebAbstractTable<CubaGroupT
return component.aggregate(new GroupAggregationContext(component, info));
}
protected class GroupTableDsWrapper extends SortableCollectionDsWrapper
implements GroupTableContainer, AggregationContainer {
protected String formatAggregatableGroupPropertyValue(GroupInfo<MetaPropertyPath> groupId, @Nullable Object value) {
String formattedValue = formatGroupPropertyValue(groupId, value);
protected boolean groupDatasource;
protected List<Object> aggregationProperties = null;
//Supports items expanding
protected final Set<GroupInfo> expanded = new HashSet<>();
protected Set<GroupInfo> expandState = new HashSet<>();
//Items cache
protected LinkedList<Object> cachedItemIds;
protected Object first;
protected Object last;
public GroupTableDsWrapper(CollectionDatasource datasource, Collection<MetaPropertyPath> properties,
CollectionDsListenersWrapper collectionDsListenersWrapper) {
super(datasource, properties, true, collectionDsListenersWrapper);
groupDatasource = datasource instanceof GroupDatasource;
}
@Override
protected void createProperties(View view, MetaClass metaClass) {
if (columns.isEmpty()) {
super.createProperties(view, metaClass);
} else {
for (Map.Entry<Object, Column<E>> entry : columns.entrySet()) {
if (entry.getKey() instanceof MetaPropertyPath) {
properties.add((MetaPropertyPath) entry.getKey());
}
}
}
}
@Override
public void groupBy(Object[] properties) {
if (groupDatasource) {
doGroup(properties);
}
}
protected void doGroup(Object[] properties) {
saveState();
((GroupDatasource) datasource).groupBy(properties);
restoreState();
resetCachedItems();
if (aggregationCells != null) {
if (hasGroups()) {
if (groupAggregationCells == null) {
groupAggregationCells = new HashMap<>();
} else {
groupAggregationCells.clear();
}
fillGroupAggregationCells(groupAggregationCells);
} else {
groupAggregationCells = null;
}
}
}
protected void saveState() {
//save expanding state
expandState.clear();
expandState.addAll(expanded);
}
protected void restoreState() {
collapseAll();
//restore groups expanding
if (hasGroups()) {
for (final GroupInfo groupInfo : expandState) {
expand(groupInfo);
}
}
expandState.clear();
}
protected void fillGroupAggregationCells(Map<Table.Column, GroupAggregationCells> cells) {
Collection roots = rootGroups();
for (Object rootGroup : roots) {
__fillGroupAggregationCells(rootGroup, cells);
}
}
protected void __fillGroupAggregationCells(Object groupId, Map<Table.Column, GroupAggregationCells> cells) {
Set<Table.Column> aggregatableColumns = aggregationCells.keySet();
for (final Column column : aggregatableColumns) {
if (!columns.get(getGroupProperty(groupId)).equals(column)) {
GroupAggregationCells groupCells = cells.get(column);
if (groupCells == null) {
groupCells = new GroupAggregationCells();
cells.put(column, groupCells);
}
groupCells.addCell(groupId, "");
}
}
if (hasChildren(groupId)) {
Collection children = getChildren(groupId);
for (final Object child : children) {
__fillGroupAggregationCells(child, cells);
}
}
}
@Override
public Collection<?> rootGroups() {
if (hasGroups()) {
return ((GroupDatasource) datasource).rootGroups();
}
return Collections.emptyList();
}
@Override
public boolean hasChildren(Object id) {
return isGroup(id) && ((GroupDatasource) datasource).hasChildren((GroupInfo) id);
}
@Override
public Collection<?> getChildren(Object id) {
if (isGroup(id)) {
return ((GroupDatasource) datasource).getChildren((GroupInfo) id);
}
return Collections.emptyList();
}
@Override
public Collection<?> getGroupItemIds(Object id) {
if (isGroup(id)) {
return ((GroupDatasource) datasource).getGroupItemIds((GroupInfo) id);
}
return Collections.emptyList();
}
@Override
public int getGroupItemsCount(Object id) {
if (isGroup(id)) {
return ((GroupDatasource) datasource).getGroupItemsCount((GroupInfo) id);
}
return 0;
}
@Override
public boolean isGroup(Object id) {
return (id instanceof GroupInfo) && ((GroupDatasource) datasource).containsGroup((GroupInfo) id);
}
@Override
public Object getGroupProperty(Object id) {
if (isGroup(id)) {
return ((GroupDatasource) datasource).getGroupProperty((GroupInfo) id);
}
return null;
}
@Override
public Object getGroupPropertyValue(Object id) {
if (isGroup(id)) {
return ((GroupDatasource) datasource).getGroupPropertyValue((GroupInfo) id);
}
return null;
}
@Override
public boolean hasGroups() {
return groupDatasource && ((GroupDatasource) datasource).hasGroups();
}
@Override
public Collection<?> getGroupProperties() {
if (hasGroups()) {
return ((GroupDatasource) datasource).getGroupProperties();
}
return Collections.emptyList();
}
@Override
public void expandAll() {
if (hasGroups()) {
this.expanded.clear();
expand(rootGroups());
resetCachedItems();
}
}
protected void expand(Collection groupIds) {
for (final Object groupId : groupIds) {
expanded.add((GroupInfo) groupId);
if (hasChildren(groupId)) {
expand(getChildren(groupId));
}
}
}
@Override
public void expand(Object id) {
if (isGroup(id)) {
expanded.add((GroupInfo) id);
resetCachedItems();
}
}
@Override
public void collapseAll() {
if (hasGroups()) {
expanded.clear();
resetCachedItems();
}
}
@Override
public void collapse(Object id) {
if (isGroup(id)) {
//noinspection RedundantCast
expanded.remove((GroupInfo) id);
resetCachedItems();
}
}
@Override
public boolean isExpanded(Object id) {
//noinspection RedundantCast
return isGroup(id) && expanded.contains((GroupInfo) id);
}
@Override
public Collection getAggregationPropertyIds() {
if (aggregationProperties != null) {
return Collections.unmodifiableList(aggregationProperties);
}
return Collections.emptyList();
}
@Override
public Type getContainerPropertyAggregation(Object propertyId) {
throw new UnsupportedOperationException();
}
@Override
public void addContainerPropertyAggregation(Object propertyId, Type type) {
if (aggregationProperties == null) {
aggregationProperties = new LinkedList<>();
} else if (aggregationProperties.contains(propertyId)) {
throw new IllegalStateException("Such aggregation property is already exists");
}
aggregationProperties.add(propertyId);
}
@Override
public void removeContainerPropertyAggregation(Object propertyId) {
if (aggregationProperties != null) {
aggregationProperties.remove(propertyId);
if (aggregationProperties.isEmpty()) {
aggregationProperties = null;
}
}
}
@SuppressWarnings("unchecked")
@Override
public Map<Object, Object> aggregate(Context context) {
return __aggregate(this, context);
}
@Override
public Object firstItemId() {
if (hasGroups()) {
return first;
}
return super.firstItemId();
}
@Override
public Object lastItemId() {
if (hasGroups()) {
return last;
}
return super.lastItemId();
}
@Override
public Object nextItemId(Object itemId) {
if (hasGroups()) {
if (itemId == null) {
return null;
}
if (isLastId(itemId)) {
return null;
}
int index = getCachedItemIds().indexOf(itemId);
return getCachedItemIds().get(index + 1);
}
return super.nextItemId(itemId);
}
@Override
public Object prevItemId(Object itemId) {
if (hasGroups()) {
if (itemId == null) {
return null;
}
if (isFirstId(itemId)) {
return null;
}
int index = getCachedItemIds().indexOf(itemId);
return getCachedItemIds().get(index - 1);
}
return super.prevItemId(itemId);
}
@Override
public boolean isFirstId(Object itemId) {
if (hasGroups()) {
return itemId != null && itemId.equals(first);
}
return super.isFirstId(itemId);
}
@Override
public boolean isLastId(Object itemId) {
if (hasGroups()) {
return itemId != null && itemId.equals(last);
}
return super.isLastId(itemId);
}
@Override
public Object addItemAfter(Object previousItemId) throws UnsupportedOperationException {
throw new UnsupportedOperationException();
}
@Override
public Item addItemAfter(Object previousItemId, Object newItemId) throws UnsupportedOperationException {
throw new UnsupportedOperationException();
}
@Override
public Collection getItemIds() {
if (hasGroups()) {
return getCachedItemIds();
} else {
return super.getItemIds();
}
}
@Override
public void sort(Object[] propertyId, boolean[] ascending) {
resetCachedItems();
super.sort(propertyId, ascending);
}
protected LinkedList getCachedItemIds() {
if (cachedItemIds == null) {
LinkedList<Object> result = new LinkedList<>();
//noinspection unchecked
List<GroupInfo> roots = ((GroupDatasource) datasource).rootGroups();
for (GroupInfo root : roots) {
result.add(root);
collectItemIds(root, result);
}
cachedItemIds = result;
if (!cachedItemIds.isEmpty()) {
first = cachedItemIds.peekFirst();
last = cachedItemIds.peekLast();
}
}
return cachedItemIds;
}
protected void collectItemIds(GroupInfo groupId, final List<Object> itemIds) {
if (expanded.contains(groupId)) {
if (((GroupDatasource) datasource).hasChildren(groupId)) {
@SuppressWarnings("unchecked")
List<GroupInfo> children = ((GroupDatasource) datasource).getChildren(groupId);
for (final GroupInfo child : children) {
itemIds.add(child);
collectItemIds(child, itemIds);
}
} else {
itemIds.addAll(((GroupDatasource) datasource).getGroupItemIds(groupId));
}
}
}
protected void resetCachedItems() {
cachedItemIds = null;
first = null;
last = null;
}
@Override
public int size() {
if (hasGroups()) {
return getItemIds().size();
}
return super.size();
}
@Override
protected Datasource.StateChangeListener createStateChangeListener() {
return new ContainerDatasourceStateChangeListener() {
@Override
public void stateChanged(Datasource.StateChangeEvent e) {
rerender = false;
Collection groupProperties = component.getGroupProperties();
component.groupBy(groupProperties.toArray());
super.stateChanged(e);
rerender = true;
}
};
}
@Override
protected CollectionDatasource.CollectionChangeListener createCollectionChangeListener() {
return new ContainerDatasourceCollectionChangeListener(){
@Override
public void collectionChanged(CollectionDatasource.CollectionChangeEvent e) {
Collection groupProperties = component.getGroupProperties();
component.groupBy(groupProperties.toArray());
super.collectionChanged(e);
}
};
}
@Override
public void resetSortOrder() {
if (datasource instanceof CollectionDatasource.Sortable) {
((CollectionDatasource.Sortable) datasource).resetSortOrder();
}
}
}
protected class AggregatableGroupPropertyValueFormatter extends DefaultGroupPropertyValueFormatter {
@Override
public String format(Object groupId, @Nullable Object value) {
String formattedValue = super.format(groupId, value);
if (groupCellValueFormatter != null) {
List<Entity> groupItems = component.getGroupItemIds(groupId).stream()
.map(itemId -> ((ItemWrapper) component.getItem(itemId)).getItem())
if (groupCellValueFormatter != null) {
List<Entity> groupItems = component.getGroupItemIds(groupId).stream()
.map(itemId -> {
TableDataContainer container = (TableDataContainer) component.getContainerDataSource();
return (Entity) container.getInternalItem(itemId);
})
.collect(Collectors.toList());
GroupCellContext<E> context = new GroupCellContext<>((GroupInfo) groupId, value, formattedValue,
(List<E>) groupItems);
return groupCellValueFormatter.format(context);
}
@SuppressWarnings("unchecked")
GroupCellContext<E> context = new GroupCellContext<>(groupId, value, formattedValue, (List<E>) groupItems);
return groupCellValueFormatter.format(context);
}
if (showItemsCountForGroup) {
int count = WebGroupTable.this.component.getGroupItemsCount(groupId);
return String.format("%s (%d)", formattedValue == null ? "" : formattedValue, count);
} else {
return formattedValue == null ? "" : formattedValue;
}
if (showItemsCountForGroup) {
int count = this.component.getGroupItemsCount(groupId);
return String.format("%s (%d)", formattedValue == null ? "" : formattedValue, count);
} else {
return formattedValue == null ? "" : formattedValue;
}
}
protected class DefaultGroupPropertyValueFormatter implements CubaGroupTable.GroupPropertyValueFormatter {
@SuppressWarnings("unchecked")
@Override
public String format(Object groupId, @Nullable Object value) {
if (value == null) {
return "";
}
MetaPropertyPath propertyPath = ((GroupInfo<MetaPropertyPath>) groupId).getProperty();
Table.Column column = columns.get(propertyPath);
if (column != null && column.getXmlDescriptor() != null) {
String captionProperty = column.getXmlDescriptor().attributeValue("captionProperty");
if (column.getFormatter() != null) {
return column.getFormatter().format(value);
} else if (StringUtils.isNotEmpty(captionProperty)) {
Collection<?> children = component.getGroupItemIds(groupId);
if (children.isEmpty()) {
return null;
}
Object itemId = children.iterator().next();
Instance item = ((ItemWrapper) component.getItem(itemId)).getItem();
final Object captionValue = item.getValueEx(captionProperty);
return captionValue != null ? String.valueOf(captionValue) : null;
}
}
return metadataTools.format(value, propertyPath.getMetaProperty());
@SuppressWarnings("unchecked")
protected String formatGroupPropertyValue(GroupInfo<MetaPropertyPath> groupId, @Nullable Object value) {
if (value == null) {
return "";
}
MetaPropertyPath propertyPath = groupId.getProperty();
Table.Column column = columns.get(propertyPath);
if (column != null && column.getXmlDescriptor() != null) {
String captionProperty = column.getXmlDescriptor().attributeValue("captionProperty"); // vaadin8 move to Column
if (column.getFormatter() != null) {
return column.getFormatter().format(value);
} else if (StringUtils.isNotEmpty(captionProperty)) {
Collection<?> children = component.getGroupItemIds(groupId);
if (children.isEmpty()) {
return null;
}
Object itemId = children.iterator().next();
TableDataContainer container = (TableDataContainer) component.getContainerDataSource();
Instance item = (Instance) container.getInternalItem(itemId);
Object captionValue = item.getValueEx(captionProperty);
// vaadin8 use metadataTools format with metaproperty
return metadataTools.format(captionValue);
}
}
return metadataTools.format(value, propertyPath.getMetaProperty());
}
protected static class GroupAggregationCells {
@ -918,9 +454,47 @@ public class WebGroupTable<E extends Entity> extends WebAbstractTable<CubaGroupT
}
@Override
public void addColumn(Column column) {
public void addColumn(Column<E> column) {
super.addColumn(column);
setColumnGroupAllowed(column, column.isGroupAllowed());
}
protected class CubaGroupTableExt extends CubaGroupTable {
@Override
protected boolean isNonGeneratedProperty(Object id) {
return (id instanceof MetaPropertyPath);
}
@Override
public void groupBy(Object[] properties) {
groupBy(properties, rerender);
}
@Override
protected LinkedHashSet<Object> getItemIdsInRange(Object startItemId, int length) {
Set<Object> rootIds = super.getItemIdsInRange(startItemId, length);
LinkedHashSet<Object> ids = new LinkedHashSet<>();
for (Object itemId: rootIds) {
if (itemId instanceof GroupInfo) {
if (!isExpanded(itemId)) {
Collection<?> itemIds = getGroupItemIds(itemId);
ids.addAll(itemIds);
expand(itemId, true);
}
@SuppressWarnings("unchecked")
List<GroupInfo> children = (List<GroupInfo>) getChildren(itemId);
for (GroupInfo groupInfo : children) {
if (!isExpanded(groupInfo)) {
expand(groupInfo, true);
}
}
} else {
ids.add(itemId);
}
}
return ids;
}
}
}

View File

@ -37,6 +37,7 @@ import com.vaadin.v7.data.Item;
import java.util.*;
import java.util.stream.Collectors;
@SuppressWarnings("deprecation")
public class WebTreeTable<E extends Entity> extends WebAbstractTable<CubaTreeTable, E> implements TreeTable<E> {
protected String hierarchyProperty;
@ -239,12 +240,6 @@ public class WebTreeTable<E extends Entity> extends WebAbstractTable<CubaTreeTab
}
}
@SuppressWarnings("unchecked")
@Override
public boolean isCaption(Object itemId) {
return treeTableDatasource && ((TreeTableDatasource) datasource).isCaption(itemId);
}
@SuppressWarnings("unchecked")
@Override
public String getCaption(Object itemId) {
@ -276,16 +271,18 @@ public class WebTreeTable<E extends Entity> extends WebAbstractTable<CubaTreeTab
public void sort(Object[] propertyId, boolean[] ascending) {
List<CollectionDatasource.Sortable.SortInfo> infos = new ArrayList<>();
for (int i = 0; i < propertyId.length; i++) {
final MetaPropertyPath propertyPath = (MetaPropertyPath) propertyId[i];
MetaPropertyPath propertyPath = (MetaPropertyPath) propertyId[i];
final CollectionDatasource.Sortable.SortInfo<MetaPropertyPath> info =
CollectionDatasource.Sortable.SortInfo<MetaPropertyPath> info =
new CollectionDatasource.Sortable.SortInfo<>();
info.setPropertyPath(propertyPath);
info.setOrder(ascending[i] ? CollectionDatasource.Sortable.Order.ASC : CollectionDatasource.Sortable.Order.DESC);
infos.add(info);
}
((CollectionDatasource.Sortable) datasource).sort(infos.toArray(new CollectionDatasource.Sortable.SortInfo[infos.size()]));
((CollectionDatasource.Sortable) datasource)
.sort(infos.toArray(new CollectionDatasource.Sortable.SortInfo[0]));
}
@Override

View File

@ -69,6 +69,8 @@ public class TablePresentations extends VerticalLayout {
this.tableImpl = (CubaEnhancedTable) WebComponentsHelper.unwrap(table);
setMargin(false);
setSizeUndefined();
setStyleName(TABLE_PREFS_STYLENAME);
setParent((HasComponents) WebComponentsHelper.unwrap(component));
@ -243,18 +245,18 @@ public class TablePresentations extends VerticalLayout {
menuBar.removeItems();
presentationsMenuMap = new HashMap<>();
final Presentations p = table.getPresentations();
Presentations p = table.getPresentations();
for (final Object presId : p.getPresentationIds()) {
final MenuBar.MenuItem item = menuBar.addItem(
for (Object presId : p.getPresentationIds()) {
MenuBar.MenuItem item = menuBar.addItem(
defaultString(p.getCaption(presId)),
selectedItem -> table.applyPresentation(presId)
);
final Presentation current = p.getCurrent();
Presentation current = p.getCurrent();
if (current != null && presId.equals(current.getId())) {
setCurrentItemStyle(item);
}
final Presentation defaultPresentation = p.getDefault();
Presentation defaultPresentation = p.getDefault();
if (defaultPresentation != null && presId.equals(defaultPresentation.getId())) {
setDefaultItemStyle(item);
}

View File

@ -0,0 +1,310 @@
/*
* Copyright (c) 2008-2018 Haulmont.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.haulmont.cuba.web.gui.components.table;
import com.haulmont.cuba.gui.components.data.BindingState;
import com.haulmont.cuba.gui.components.data.GroupTableSource;
import com.haulmont.cuba.gui.data.GroupInfo;
import com.haulmont.cuba.web.widgets.data.GroupTableContainer;
import java.util.*;
public class GroupTableDataContainer<I> extends SortableDataContainer<I> implements GroupTableContainer {
protected Set<GroupInfo> expandedGroups = new HashSet<>();
protected List<Object> cachedItemIds;
protected Object first;
protected Object last;
public GroupTableDataContainer(GroupTableSource<I> tableSource,
TableSourceEventsDelegate<I> dataEventsDelegate) {
super(tableSource, dataEventsDelegate);
}
protected GroupTableSource<I> getGroupTableSource() {
return (GroupTableSource<I>) tableSource;
}
@Override
public void groupBy(Object[] properties) {
doGroup(properties);
}
protected Set<GroupInfo> saveState() {
//save expanding state
return new HashSet<>(expandedGroups);
}
protected void restoreState(Set<GroupInfo> expandState) {
collapseAll();
//restore groups expanding
if (hasGroups()) {
for (GroupInfo groupInfo : expandState) {
expand(groupInfo);
}
}
}
protected void doGroup(Object[] properties) {
Set<GroupInfo> expandState = saveState();
getGroupTableSource().groupBy(properties);
restoreState(expandState);
resetCachedItems();
// todo aggregation
}
@Override
public boolean isGroup(Object id) {
return id instanceof GroupInfo && getGroupTableSource().containsGroup((GroupInfo) id);
}
@Override
public Collection<?> rootGroups() {
return getGroupTableSource().rootGroups();
}
@Override
public boolean hasChildren(Object id) {
return isGroup(id) && getGroupTableSource().hasChildren((GroupInfo) id);
}
@Override
public Collection<?> getChildren(Object id) {
if (isGroup(id)) {
return getGroupTableSource().getChildren((GroupInfo) id);
}
return Collections.emptyList();
}
@Override
public Object getGroupProperty(Object id) {
if (isGroup(id)) {
return getGroupTableSource().getGroupProperty((GroupInfo) id);
}
return null;
}
@Override
public Object getGroupPropertyValue(Object id) {
if (isGroup(id)) {
return getGroupTableSource().getGroupPropertyValue((GroupInfo) id);
}
return null;
}
@Override
public Collection<?> getGroupItemIds(Object id) {
if (isGroup(id)) {
return getGroupTableSource().getGroupItemIds((GroupInfo) id);
}
return Collections.emptyList();
}
@Override
public int getGroupItemsCount(Object id) {
if (isGroup(id)) {
return getGroupTableSource().getGroupItemsCount((GroupInfo) id);
}
return 0;
}
@Override
public boolean hasGroups() {
return getGroupTableSource().hasGroups();
}
@Override
public Collection<?> getGroupProperties() {
if (hasGroups()) {
return getGroupTableSource().getGroupProperties();
}
return Collections.emptyList();
}
@Override
public void expandAll() {
if (hasGroups()) {
expandedGroups.clear();
expand(rootGroups());
resetCachedItems();
}
}
protected void expand(Collection groupIds) {
for (Object groupId : groupIds) {
expandedGroups.add((GroupInfo) groupId);
if (hasChildren(groupId)) {
expand(getChildren(groupId));
}
}
}
@Override
public void expand(Object id) {
if (isGroup(id)) {
expandedGroups.add((GroupInfo) id);
resetCachedItems();
}
}
@Override
public void collapseAll() {
if (hasGroups()) {
expandedGroups.clear();
resetCachedItems();
}
}
@Override
public void collapse(Object id) {
if (isGroup(id)) {
//noinspection RedundantCast
expandedGroups.remove((GroupInfo) id);
resetCachedItems();
}
}
@Override
public boolean isExpanded(Object id) {
//noinspection RedundantCast
return isGroup(id) && expandedGroups.contains((GroupInfo) id);
}
@Override
public Collection<?> getItemIds() {
if (tableSource.getState() == BindingState.INACTIVE) {
return Collections.emptyList();
}
return getCachedItemIds();
}
protected List getCachedItemIds() {
if (cachedItemIds == null) {
List<Object> result = new ArrayList<>();
//noinspection unchecked
List<GroupInfo> roots = getGroupTableSource().rootGroups();
for (GroupInfo root : roots) {
result.add(root);
collectItemIds(root, result);
}
cachedItemIds = result;
if (!cachedItemIds.isEmpty()) {
first = cachedItemIds.get(0);
last = cachedItemIds.get(cachedItemIds.size() - 1);
}
}
return cachedItemIds;
}
protected void collectItemIds(GroupInfo groupId, List<Object> itemIds) {
if (expandedGroups.contains(groupId)) {
GroupTableSource<I> groupTableSource = getGroupTableSource();
if (groupTableSource.hasChildren(groupId)) {
List<GroupInfo> children = groupTableSource.getChildren(groupId);
for (GroupInfo child : children) {
itemIds.add(child);
collectItemIds(child, itemIds);
}
} else {
itemIds.addAll(groupTableSource.getGroupItemIds(groupId));
}
}
}
protected void resetCachedItems() {
cachedItemIds = null;
first = null;
last = null;
}
@Override
public int size() {
if (hasGroups()) {
return getItemIds().size();
}
return super.size();
}
@Override
public Object firstItemId() {
if (hasGroups()) {
return first;
}
return super.firstItemId();
}
@Override
public Object lastItemId() {
if (hasGroups()) {
return last;
}
return super.lastItemId();
}
@Override
public Object nextItemId(Object itemId) {
if (hasGroups()) {
if (itemId == null) {
return null;
}
if (isLastId(itemId)) {
return null;
}
int index = getCachedItemIds().indexOf(itemId);
return getCachedItemIds().get(index + 1);
}
return super.nextItemId(itemId);
}
@Override
public Object prevItemId(Object itemId) {
if (hasGroups()) {
if (itemId == null) {
return null;
}
if (isFirstId(itemId)) {
return null;
}
int index = getCachedItemIds().indexOf(itemId);
return getCachedItemIds().get(index - 1);
}
return super.prevItemId(itemId);
}
@Override
public boolean isFirstId(Object itemId) {
if (hasGroups()) {
return itemId != null && itemId.equals(first);
}
return super.isFirstId(itemId);
}
@Override
public boolean isLastId(Object itemId) {
if (hasGroups()) {
return itemId != null && itemId.equals(last);
}
return super.isLastId(itemId);
}
}

View File

@ -17,13 +17,14 @@
package com.haulmont.cuba.web.gui.components.table;
import com.haulmont.cuba.gui.components.data.TableSource;
import com.haulmont.cuba.web.widgets.data.TableSortableContainer;
import com.vaadin.v7.data.Container;
import com.vaadin.v7.data.Item;
import java.util.Collection;
@SuppressWarnings("deprecation")
public class SortableDataContainer<I> extends TableDataContainer<I> implements Container.Sortable {
public class SortableDataContainer<I> extends TableDataContainer<I> implements Container.Sortable, TableSortableContainer {
public SortableDataContainer(TableSource.Sortable<I> tableDataSource, TableSourceEventsDelegate<I> dataEventsDelegate) {
super(tableDataSource, dataEventsDelegate);
@ -31,10 +32,10 @@ public class SortableDataContainer<I> extends TableDataContainer<I> implements C
@Override
public void sort(Object[] propertyId, boolean[] ascending) {
getSortableDataSource().sort(propertyId, ascending);
getSortableTableSource().sort(propertyId, ascending);
}
protected TableSource.Sortable getSortableDataSource() {
protected TableSource.Sortable getSortableTableSource() {
return (TableSource.Sortable) tableSource;
}
@ -45,32 +46,32 @@ public class SortableDataContainer<I> extends TableDataContainer<I> implements C
@Override
public Object nextItemId(Object itemId) {
return getSortableDataSource().nextItemId(itemId);
return getSortableTableSource().nextItemId(itemId);
}
@Override
public Object prevItemId(Object itemId) {
return getSortableDataSource().prevItemId(itemId);
return getSortableTableSource().prevItemId(itemId);
}
@Override
public Object firstItemId() {
return getSortableDataSource().firstItemId();
return getSortableTableSource().firstItemId();
}
@Override
public Object lastItemId() {
return getSortableDataSource().lastItemId();
return getSortableTableSource().lastItemId();
}
@Override
public boolean isFirstId(Object itemId) {
return getSortableDataSource().isFirstId(itemId);
return getSortableTableSource().isFirstId(itemId);
}
@Override
public boolean isLastId(Object itemId) {
return getSortableDataSource().isLastId(itemId);
return getSortableTableSource().isLastId(itemId);
}
@Override
@ -82,4 +83,9 @@ public class SortableDataContainer<I> extends TableDataContainer<I> implements C
public Item addItemAfter(Object previousItemId, Object newItemId) throws UnsupportedOperationException {
throw new UnsupportedOperationException();
}
@Override
public void resetSortOrder() {
getSortableTableSource().resetSortOrder();
}
}

View File

@ -36,11 +36,8 @@ public class TableItemPropertyWrapper implements Property, Property.ValueChangeN
@Override
public void setValue(Object newValue) throws ReadOnlyException {
if (readOnly) {
throw new ReadOnlyException();
}
itemWrapper.setPropertyValue(propertyId, newValue);
// Table does not support setting new value with Vaadin API
throw new ReadOnlyException();
}
@Override

View File

@ -74,10 +74,6 @@ public class TableItemWrapper implements Item {
return tableDataContainer.getTableSource().getItemValue(itemId, propertyId);
}
public void setPropertyValue(Object propertyId, Object newValue) {
tableDataContainer.getTableSource().setItemValue(itemId, propertyId, newValue);
}
public void addValueChangeListener(Property.ValueChangeListener propertyValueChangeListener) {
tableDataContainer.addValueChangeListener(propertyValueChangeListener);
}

View File

@ -24,23 +24,19 @@ import com.haulmont.chile.core.model.MetaPropertyPath;
import com.haulmont.chile.core.model.Range;
import com.haulmont.chile.core.model.utils.InstanceUtils;
import com.haulmont.cuba.core.global.AppBeans;
import com.haulmont.cuba.core.global.MetadataTools;
import com.haulmont.cuba.core.global.UserSessionSource;
import com.haulmont.cuba.gui.data.Datasource;
import com.haulmont.cuba.gui.data.impl.WeakItemChangeListener;
import com.haulmont.cuba.gui.data.impl.WeakItemPropertyChangeListener;
import com.haulmont.cuba.web.widgets.data.PropertyValueStringify;
import com.vaadin.v7.data.Property;
import com.vaadin.v7.data.util.converter.Converter;
import java.text.ParseException;
public class PropertyWrapper extends AbstractPropertyWrapper implements PropertyValueStringify, UnsubscribableDsWrapper {
public class PropertyWrapper extends AbstractPropertyWrapper implements UnsubscribableDsWrapper {
protected MetaPropertyPath propertyPath;
protected MetadataTools metadataTools = AppBeans.get(MetadataTools.NAME);
protected Datasource.ItemChangeListener dsItemChangeListener;
protected WeakItemChangeListener weakItemChangeListener;
@ -145,10 +141,6 @@ public class PropertyWrapper extends AbstractPropertyWrapper implements Property
return propertyPath.getRangeJavaClass();
}
@Override
public String getFormattedValue() {
return metadataTools.format(getValue(), propertyPath.getMetaProperty());
}
@SuppressWarnings("unchecked")
@Override

View File

@ -30,6 +30,8 @@ import java.util.List;
import static com.haulmont.cuba.gui.data.CollectionDatasource.Sortable.Order;
import static com.haulmont.cuba.gui.data.CollectionDatasource.Sortable.SortInfo;
// for removal
@Deprecated
public class SortableCollectionDsWrapper extends CollectionDsWrapper implements Container.Sortable {
public SortableCollectionDsWrapper(CollectionDatasource datasource, Collection<MetaPropertyPath> properties,