/* * Licensed to the Apache Software Foundation (ASF) under one * or more contributor license agreements. See the NOTICE file * distributed with this work for additional information * regarding copyright ownership. The ASF licenses this file * to you 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 org.apache.isis.viewer.wicket.ui.components.collectioncontents.multiple; import org.apache.isis.viewer.wicket.model.hints.IsisEnvelopeEvent; import org.apache.isis.viewer.wicket.model.hints.IsisSelectorEvent; import org.apache.isis.viewer.wicket.model.models.EntityCollectionModel; import org.apache.isis.viewer.wicket.model.models.EntityModel; import org.apache.isis.viewer.wicket.model.util.ComponentHintKey; import org.apache.isis.viewer.wicket.ui.ComponentFactory; import org.apache.isis.viewer.wicket.ui.ComponentType; import org.apache.isis.viewer.wicket.ui.components.collection.count.CollectionCountProvider; import org.apache.isis.viewer.wicket.ui.components.collection.selector.CollectionSelectorHelper; import org.apache.isis.viewer.wicket.ui.components.collection.selector.CollectionSelectorPanel; import org.apache.isis.viewer.wicket.ui.components.collection.selector.CollectionSelectorProvider; import org.apache.isis.viewer.wicket.ui.panels.PanelAbstract; import org.apache.isis.viewer.wicket.ui.util.CssClassAppender; import org.apache.isis.viewer.wicket.ui.util.CssClassRemover; import org.apache.wicket.AttributeModifier; import org.apache.wicket.Component; import org.apache.wicket.ajax.AjaxRequestTarget; import org.apache.wicket.event.IEvent; import java.util.List; /** * Subscribes to events generated by {@link org.apache.isis.viewer.wicket.ui.components.collection.selector.CollectionSelectorPanel}, rendering the appropriate {@link ComponentType#COLLECTION_CONTENTS} * view for a backing {@link EntityCollectionModel}. */ public class CollectionContentsMultipleViewsPanel extends PanelAbstract<EntityCollectionModel> implements CollectionCountProvider { private static final long serialVersionUID = 1L; private static final String INVISIBLE_CLASS = "link-selector-panel-invisible"; private static final int MAX_NUM_UNDERLYING_VIEWS = 10; private static final String UIHINT_VIEW = EntityCollectionModel.HINT_KEY_SELECTED_ITEM; private final String underlyingIdPrefix; private final CollectionSelectorHelper selectorHelper; private Component selectedComponent; private Component[] underlyingViews; public CollectionContentsMultipleViewsPanel( final String id, final EntityCollectionModel model) { super(id, model); this.underlyingIdPrefix = ComponentType.COLLECTION_CONTENTS.toString(); final EntityModel entityModel = model.getEntityModel(); final ComponentHintKey selectedItemSessionAttribute = entityModel != null ? ComponentHintKey.<String>create(this, EntityCollectionModel.HINT_KEY_SELECTED_ITEM) : null; selectorHelper = new CollectionSelectorHelper( model, getComponentFactoryRegistry(), selectedItemSessionAttribute); } /** * Build UI only after added to parent. */ @Override public void onInitialize() { super.onInitialize(); addUnderlyingViews(); } private void addUnderlyingViews() { final EntityCollectionModel model = getModel(); final List<ComponentFactory> componentFactories = selectorHelper.getComponentFactories(); final CollectionSelectorPanel selectorDropdownPanelIfAny = CollectionSelectorProvider.Util.getCollectionSelectorProvider(this); final String selected; if (selectorDropdownPanelIfAny != null) { selected = selectorHelper.honourViewHintElseDefault(selectorDropdownPanelIfAny); } else { selected = componentFactories.get(0).getName(); } // create all, hide the one not selected int i = 0; int selectedIdx = 0; underlyingViews = new Component[MAX_NUM_UNDERLYING_VIEWS]; final EntityCollectionModel emptyModel = model.asDummy(); for (ComponentFactory componentFactory : componentFactories) { final String underlyingId = underlyingIdPrefix + "-" + i; final boolean isSelected = selected.equals(componentFactory.getName()); final Component underlyingView = componentFactory.createComponent(underlyingId, isSelected ? model : emptyModel); if(isSelected) { selectedIdx = i; } underlyingViews[i++] = underlyingView; this.addOrReplace(underlyingView); } // hide any unused placeholders while(i<MAX_NUM_UNDERLYING_VIEWS) { String underlyingId = underlyingIdPrefix + "-" + i; permanentlyHide(underlyingId); i++; } this.setOutputMarkupId(true); for(i=0; i<MAX_NUM_UNDERLYING_VIEWS; i++) { Component component = underlyingViews[i]; if(component != null) { if(i != selectedIdx) { component.add(new CssClassAppender(INVISIBLE_CLASS)); } else { selectedComponent = component; } } } } @Override public void onEvent(IEvent<?> event) { super.onEvent(event); final IsisSelectorEvent selectorEvent = IsisEnvelopeEvent.openLetter(event, IsisSelectorEvent.class); if(selectorEvent == null) { return; } final CollectionSelectorPanel selectorDropdownPanel = CollectionSelectorProvider.Util.getCollectionSelectorProvider(this); if(selectorDropdownPanel == null) { // not expected, because this event shouldn't be called. // but no harm in simply returning... return; } String selectedView = selectorEvent.hintFor(selectorDropdownPanel, UIHINT_VIEW); if (selectedView == null) { return; } int underlyingViewNum = selectorHelper.lookup(selectedView); final EntityCollectionModel dummyModel = getModel().asDummy(); for(int i=0; i<MAX_NUM_UNDERLYING_VIEWS; i++) { final Component component = underlyingViews[i]; if(component == null) { continue; } final boolean isSelected = i == underlyingViewNum; applyCssVisibility(component, isSelected); component.setDefaultModel(isSelected? getModel(): dummyModel); } this.selectedComponent = underlyingViews[underlyingViewNum]; final AjaxRequestTarget target = selectorEvent.getTarget(); if(target != null) { target.add(this, selectorDropdownPanel); } } protected static void applyCssVisibility(final Component component, final boolean visible) { if(component == null) { return; } AttributeModifier modifier = visible ? new CssClassRemover(INVISIBLE_CLASS) : new CssClassAppender(INVISIBLE_CLASS); component.add(modifier); } @Override public Integer getCount() { if(selectedComponent instanceof CollectionCountProvider) { final CollectionCountProvider collectionCountProvider = (CollectionCountProvider) selectedComponent; return collectionCountProvider.getCount(); } else { return null; } } }