Package org.richfaces.component.state

Source Code of org.richfaces.component.state.TreeState$Visitor

/**
* License Agreement.
*
*  JBoss RichFaces - Ajax4jsf Component Library
*
* Copyright (C) 2007  Exadel, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License version 2.1 as published by the Free Software Foundation.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301  USA
*/

package org.richfaces.component.state;

import java.io.IOException;
import java.util.HashSet;
import java.util.Set;

import javax.faces.application.FacesMessage;
import javax.faces.component.StateHolder;
import javax.faces.context.FacesContext;

import org.ajax4jsf.model.DataComponentState;
import org.ajax4jsf.model.DataVisitor;
import org.ajax4jsf.model.Range;
import org.richfaces.component.UITree;
import org.richfaces.component.state.events.TreeStateCommandsListener;
import org.richfaces.model.TreeRange;
import org.richfaces.model.TreeRowKey;

/**
* @author Nick Belaevski - nbelaevski@exadel.com created 23.11.2006
*
*/
public class TreeState implements DataComponentState, TreeStateCommandsListener, StateHolder {
  private final class Visitor implements DataVisitor {
    private TreeRowKey key;
    private UITree tree;

    public Visitor(TreeRowKey key, UITree tree) {
      super();
      this.key = key;
      this.tree = tree;
    }

    public void process(FacesContext context, Object rowKey, Object argument)
    throws IOException {
      tree.setRowKey(context, rowKey);
      if (tree.isRowAvailable()) {
        TreeRowKey nextKey = (TreeRowKey) rowKey;

        if (!tree.isLeaf() && nextKey != null) {
          if (key == null || nextKey.isSubKey(key)
              || nextKey.equals(key)) {
            if (tree.isImmediate()) {
              queuedExpandedNodes.add(nextKey);
            } else {
              expandedNodes.add(nextKey);
            }
            queuedCollapsedNodes.remove(nextKey);
          }
        }
      } else {
        FacesMessage message = new FacesMessage("Row key: " + rowKey
            + " isn't available!");
        message.setSeverity(FacesMessage.SEVERITY_ERROR);

        context.addMessage(tree.getBaseClientId(context), message);
      }
    }
  }

  private final static TreeRange RANGE_UNCONSTRAINED = new TreeRange() {
    public boolean processChildren(TreeRowKey rowKey) {
      return true;
    }

    public boolean processNode(TreeRowKey rowKey) {
      return true;
    }
  };
 
  private boolean stopInCollapsed = false;

  private TreeRowKey selectedNode = null;

  private Set expandedNodes = new HashSet();

  private Set queuedExpandedNodes = new HashSet();

  private Set queuedCollapsedNodes = new HashSet();

  public TreeState(boolean stopInCollapsed) {
    super();
    this.stopInCollapsed = stopInCollapsed;
  }

  public boolean isExpanded(TreeRowKey rowKey) {
    if (rowKey == null) {
      return true;
    }

    return expandedNodes.contains(rowKey)
    || queuedExpandedNodes.contains(rowKey);
  }

  public boolean isSelected(TreeRowKey rowKey) {
    return (rowKey == null && selectedNode == null) || (selectedNode != null && selectedNode.equals(rowKey));
  }

  public TreeRowKey getSelectedNode() {
    return selectedNode;
  }
 
  public void setSelected(TreeRowKey rowKey) {
    selectedNode = rowKey;
  }

  private boolean _transient;

  private transient TreeRange treeRange = null;

  public Range getRange() {
    if (treeRange != null) {
      return treeRange;
    }

    if (stopInCollapsed) {
      return new TreeRange() {

        public boolean processChildren(TreeRowKey rowKey) {
          if (rowKey == null) {
            return true;
          }

          return expandedNodes.contains(rowKey);
        }

        public boolean processNode(TreeRowKey rowKey) {
          return true;
        }
      };
    } else {
      return RANGE_UNCONSTRAINED;
    }
  }

  public boolean isTransient() {
    return _transient;
  }

  public void restoreState(FacesContext context, Object state) {
    Object[] _state = (Object[]) state;
    expandedNodes = (Set) _state[0];
    _transient = ((Boolean) _state[1]).booleanValue();
    stopInCollapsed = ((Boolean) _state[2]).booleanValue();
    selectedNode = (TreeRowKey) _state[3];
    queuedExpandedNodes = (Set) _state[4];
    queuedCollapsedNodes = (Set) _state[5];
  }

  public Object saveState(FacesContext context) {
    Object[] state = new Object[6];
    state[0] = expandedNodes;
    state[1] = new Boolean(_transient);
    state[2] = new Boolean(stopInCollapsed);
    state[3] = selectedNode;
    state[4] = queuedExpandedNodes;
    state[5] = queuedCollapsedNodes;
    return state;
  }

  public void setTransient(boolean newTransientValue) {
    this._transient = newTransientValue;
  }

  public boolean isStopInCollapsed() {
    return stopInCollapsed;
  }

  public void setStopInCollapsed(boolean stopInCollapsed) {
    this.stopInCollapsed = stopInCollapsed;
  }

  private void visitNodes(UITree tree, TreeRange treeRange, TreeRowKey rootKey)
  throws IOException {
    try {
      this.treeRange = treeRange;
      Object oldKey = tree.getRowKey();

      tree.walkModel(FacesContext.getCurrentInstance(), new Visitor(
          rootKey, tree), treeRange, rootKey, null);
      tree.setRowKey(oldKey);
    } finally {
      this.treeRange = null;
    }
  }

  public void expandAll(UITree tree) throws IOException {
    queuedCollapsedNodes.clear();
    // SubTreeChildrenAppender infoAppender = null;
    //
    // if (storedPersister != null) {
    // storedPersister.reset();
    // infoAppender = storedPersister.getAppender(null);
    // }

    visitNodes(tree, RANGE_UNCONSTRAINED, null);
  }

  public void collapseAll(UITree tree) throws IOException {
    expandedNodes.clear();
    queuedExpandedNodes.clear();
    // RequestUtils.setStoredPersister(tree.getBaseClientId(context),
    // context, null);
  }

  public void collapseNode(UITree tree, TreeRowKey rowKey) throws IOException {
    expandedNodes.remove(rowKey);
    queuedExpandedNodes.remove(rowKey);
    queuedCollapsedNodes.add(rowKey);
    // TreePersister storedPersister =
    // RequestUtils.getStoredPersister(tree.getBaseClientId(context),
    // context);
    // if (storedPersister != null) {
    // storedPersister.removeNode(rowKey);
    // }
  }

  public void expandNode(UITree tree, final TreeRowKey rowKey) throws IOException {
    // SubTreeChildrenAppender infoAppender;
    // if (storedPersister != null) {
    // infoAppender = storedPersister.getAppender(rowKey);
    // } else {
    // infoAppender = null;
    // }

    TreeRange range;
    // it's enough to traverse only subkeys of the node
    // we're opening
    range = new TreeRange() {
      public boolean processChildren(TreeRowKey nextKey) {
        return true;
      }

      public boolean processNode(TreeRowKey nextKey) {
        return (rowKey == null && nextKey == null)
        || nextKey.equals(rowKey)
        || nextKey.isSubKey(rowKey);
      }

    };
    visitNodes(tree, range, rowKey);

  }

  public void transferQueuedNodes() {
    expandedNodes.addAll(queuedExpandedNodes);
    queuedExpandedNodes.clear();
    expandedNodes.removeAll(queuedCollapsedNodes);
    queuedCollapsedNodes.clear();
  }

}
TOP

Related Classes of org.richfaces.component.state.TreeState$Visitor

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.