Package net.alteiar.campaign.player.gui.centerViews.explorer.tree

Source Code of net.alteiar.campaign.player.gui.centerViews.explorer.tree.MyTreeModel

package net.alteiar.campaign.player.gui.centerViews.explorer.tree;

import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;

import javax.swing.SwingUtilities;
import javax.swing.event.TreeModelListener;
import javax.swing.tree.DefaultMutableTreeNode;
import javax.swing.tree.DefaultTreeModel;
import javax.swing.tree.TreeModel;
import javax.swing.tree.TreePath;

import net.alteiar.WaitBeanListener;
import net.alteiar.campaign.CampaignClient;
import net.alteiar.campaign.CampaignListener;
import net.alteiar.campaign.player.tools.Threads;
import net.alteiar.documents.BeanBasicDocument;
import net.alteiar.documents.BeanDirectory;
import net.alteiar.documents.DocumentAdapter;
import net.alteiar.newversion.shared.bean.BasicBean;
import net.alteiar.player.Player;
import net.alteiar.shared.UniqueID;
import net.alteiar.thread.MyRunnable;
import net.alteiar.tree.DefaultMutableTreeNodeChildIterator;

public class MyTreeModel extends DocumentAdapter implements TreeModel {

  private final DefaultTreeModel fullModel;
  private final DefaultTreeModel printModel;

  /**
   * Avoid multiple concurrent refresh
   */
  private boolean needRefreshAllDocs = false;
  private boolean isRefreshingAllDocs = false;

  public MyTreeModel(DocumentNode root) {
    fullModel = new DefaultTreeModel(root);

    printModel = new DefaultTreeModel(root.clone());

    for (BeanBasicDocument doc : CampaignClient.getInstance()
        .getDocuments()) {
      doc.addPropertyChangeListener(MyTreeModel.this);
    }

    CampaignClient.getInstance().addCampaignListener(
        new CampaignListener() {

          @Override
          public void playerAdded(Player player) {

          }

          @Override
          public void beanRemoved(BeanBasicDocument bean) {
            bean.removePropertyChangeListener(MyTreeModel.this);
            refreshTree();
          }

          @Override
          public void beanAdded(BeanBasicDocument bean) {
            bean.addPropertyChangeListener(MyTreeModel.this);
            refreshTree();
          }
        });

    refreshTree();
  }

  @Override
  public void documentChanged(PropertyChangeEvent evt) {
    refreshModel();
  }

  private synchronized void refreshTree() {
    if (isRefreshingAllDocs) {
      needRefreshAllDocs = true;
      return;
    }
    needRefreshAllDocs = false;
    isRefreshingAllDocs = true;

    Threads.execute(new MyRunnable() {
      @Override
      public void run() {
        DocumentNode root = (DocumentNode) fullModel.getRoot();
        fillCompleteModel(root);

        // fullModel.reload();
        isRefreshingAllDocs = false;
        if (needRefreshAllDocs) {
          refreshTree();
        } else {
          refreshModel();
        }
      }

      @Override
      public String getTaskName() {
        return "refresh document tree";
      }
    });
  }

  private synchronized void fillCompleteModel(final DocumentNode parent) {
    BeanBasicDocument dir = parent.getUserObject();
    BeanDirectory beanDir = (BeanDirectory) dir;

    beanDir.addPropertyChangeListener(new PropertyChangeListener() {
      @Override
      public void propertyChange(PropertyChangeEvent evt) {
        refreshTree();
      }
    });

    Map<String, DocumentNode> existingDocs = new HashMap<>();

    for (int i = 0; i < parent.getChildCount(); i++) {
      DocumentNode childNode = (DocumentNode) parent.getChildAt(i);
      String documentId = childNode.getUserObject().getId().toString();
      existingDocs.put(documentId, childNode);
    }

    for (final UniqueID id : beanDir.getDocuments()) {
      BeanBasicDocument beanBasicDocument = CampaignClient.getInstance()
          .getBean(id);

      if (beanBasicDocument != null) {
        DocumentNode node = existingDocs.get(beanBasicDocument.getId()
            .toString());

        if (node != null) {
          existingDocs.remove(beanBasicDocument.getId().toString());
        } else {
          node = new DocumentNode(beanBasicDocument,
              beanBasicDocument.isDirectory());
          parent.add(node);
        }

        if (beanBasicDocument.isDirectory()) {
          fillCompleteModel(node);
        }
      } else {
        CampaignClient.getInstance().addWaitBeanListener(
            new WaitBeanListener() {
              @Override
              public UniqueID getBeanId() {
                return id;
              }

              @Override
              public void beanReceived(BasicBean bean) {
                refreshTree();
              }
            });
      }
    }

    if (!existingDocs.isEmpty()) {
      for (String docIdToRemove : existingDocs.keySet()) {
        Iterator<DefaultMutableTreeNode> itt = new DefaultMutableTreeNodeChildIterator(
            parent);

        boolean docRemoved = false;
        while (itt.hasNext() && !docRemoved) {
          DocumentNode childNode = (DocumentNode) itt.next();
          String documentId = childNode.getUserObject().getId()
              .toString();
          if (documentId.equals(docIdToRemove)) {
            itt.remove();
            docRemoved = true;
          }
        }
      }
    }
  }

  private synchronized void refreshModel() {
    DocumentNode root = (DocumentNode) fullModel.getRoot();

    DocumentNode rootNode = (DocumentNode) printModel.getRoot();
    rootNode.removeAllChildren();

    Player current = CampaignClient.getInstance().getCurrentPlayer();
    fillPrintNode(current, rootNode, root);

    SwingUtilities.invokeLater(new Runnable() {
      @Override
      public void run() {
        printModel.reload();
      }
    });
  }

  private void fillPrintNode(Player current, DocumentNode root,
      DocumentNode realNode) {
    for (int i = 0; i < realNode.getChildCount(); i++) {
      DocumentNode node = (DocumentNode) realNode.getChildAt(i);
      DocumentNode newNode = node.clone();
      if (node.getUserObject().isAllowedToSee(current)) {
        root.add(newNode);
        if (!node.isLeaf()) {
          fillPrintNode(current, newNode, node);
        }
      }
    }
  }

  @Override
  public Object getRoot() {
    return printModel.getRoot();
  }

  @Override
  public Object getChild(Object parent, int index) {
    return printModel.getChild(parent, index);
  }

  @Override
  public int getChildCount(Object parent) {
    return printModel.getChildCount(parent);
  }

  @Override
  public boolean isLeaf(Object node) {
    return printModel.isLeaf(node);
  }

  @Override
  public void valueForPathChanged(TreePath path, Object newValue) {
    printModel.valueForPathChanged(path, newValue);
  }

  @Override
  public int getIndexOfChild(Object parent, Object child) {
    return printModel.getIndexOfChild(parent, child);
  }

  @Override
  public void addTreeModelListener(TreeModelListener l) {
    printModel.addTreeModelListener(l);
  }

  @Override
  public void removeTreeModelListener(TreeModelListener l) {
    printModel.removeTreeModelListener(l);
  }

}
TOP

Related Classes of net.alteiar.campaign.player.gui.centerViews.explorer.tree.MyTreeModel

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.