All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.activiti.designer.eclipse.util.Util Maven / Gradle / Ivy

The newest version!
/**
 * 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 org.activiti.designer.eclipse.util;

import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.Reader;
import java.io.StringWriter;
import java.io.Writer;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.activiti.bpmn.model.BaseElement;
import org.eclipse.core.resources.IFile;
import org.eclipse.core.resources.IFolder;
import org.eclipse.core.resources.IProject;
import org.eclipse.core.resources.IResource;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.emf.common.util.EList;
import org.eclipse.emf.common.util.URI;
import org.eclipse.emf.ecore.EObject;
import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.emf.ecore.resource.ResourceSet;
import org.eclipse.graphiti.mm.pictograms.Diagram;
import org.eclipse.graphiti.mm.pictograms.PictogramElement;

/**
 * Collection of general static helper methods.
 */
public class Util {

  private static final String DIAGRAM_NAME_PATTERN = "name=\"%s\"";
  private static final String DIAGRAM_NAME_DEFAULT = String.format(DIAGRAM_NAME_PATTERN, "my_bpmn2_diagram");

  /**
   * Moves the object at the source index of the list to the _target index of
   * the list and returns the moved object.
   * 
   * @param targetIndex
   *          the new position for the object in the list.
   * @param sourceIndex
   *          the old position of the object in the list.
   * @return the moved object.
   * @exception IndexOutOfBoundsException
   *              if either index isn't within the size range.
   */
  public static Object moveElementInList(List list, int targetIndex, int sourceIndex) {
    if (targetIndex >= list.size() || targetIndex < 0)
      throw new IndexOutOfBoundsException("targetIndex=" + targetIndex + ", size=" + list.size()); //$NON-NLS-1$ //$NON-NLS-2$

    if (sourceIndex >= list.size() || sourceIndex < 0)
      throw new IndexOutOfBoundsException("sourceIndex=" + sourceIndex + ", size=" + list.size()); //$NON-NLS-1$ //$NON-NLS-2$

    Object object = list.get(sourceIndex);
    if (targetIndex != sourceIndex) {
      list.remove(sourceIndex);
      list.add(targetIndex, object);
    }
    return object;
  }

  /**
   * Returns true, if the given objects equal, while null is also a valid value.
   * In detail the check is: (o1 == null && o2 == null) || (o1.equals(o2)).
   * 
   * @param o1
   *          The first Object to compare.
   * @param o2
   *          The second Object to compare.
   * @return true, if the given objects equal, while null is also a valid value.
   */
  public static boolean equalsWithNull(Object o1, Object o2) {
    if (o1 == null && o2 == null)
      return true;
    if (o1 == null || o2 == null)
      return false;
    return o1.equals(o2);
  }

  public static BaseElement[] getAllBpmnElements(IProject project, ResourceSet rSet) {
    // FIXME: always unload to have our resources refreshed, this is highly
    // non-performant
    EList resources = rSet.getResources();
    for (Resource resource : resources) {
      resource.unload();
    }
    IFolder folder = project.getFolder("src");
    IFolder folderDiagrams = project.getFolder("src/diagrams");
    Collection diagrams = new ArrayList();
    Set bpmnElements = new HashSet();
    if (folder.exists()) {
      List membersList = new ArrayList();
      try {
        membersList.addAll(Arrays.asList(folder.members()));
        membersList.addAll(Arrays.asList(folderDiagrams.members()));
      } catch (CoreException e) {
        return new BaseElement[0];
      }
      for (IResource resource : membersList) {
        if (resource instanceof IFile) {
          IFile file = (IFile) resource;
          if ("diagram".equals(file.getFileExtension()) || file.getName().equals("Predefined.data")) {
            // The following call extracts the diagram from the
            // given file. For the Tutorial diagrams always reside
            // in a file of their own and are the first root object.
            // This may of course be different in a concrete tool
            // implementation, so tool builders should use their own
            // way of retrieval here
            Diagram diag = org.eclipse.graphiti.ui.internal.services.GraphitiUiInternal.getEmfService().getDiagramFromFile(file, rSet);
            if (diag != null) {
              diagrams.add(diag);
            } else {
              // The following call tries to retrieve a URI from
              // any of the found files to check if there are any
              // EClasses inside this file. Concrete tools should
              // use their own logic to browse through their files
              // (e.g. known by a special extension or residing in
              // a special folder) instead of this generic logic.
              URI uri = org.eclipse.graphiti.ui.internal.services.GraphitiUiInternal.getEmfService().getFileURI(file);
              Resource fileResource = rSet.getResource(uri, true);
              if (fileResource != null) {
                EList contents = fileResource.getContents();
                for (EObject object : contents) {
                  if (object instanceof BaseElement && !(object instanceof PictogramElement)) {
                    bpmnElements.add((BaseElement) object);
                  }
                }
              }
            }
          }
        }
      }
    }
    for (Diagram diagram : diagrams) {
      Resource resource = diagram.eResource();
      if (resource == null)
        return new BaseElement[0];
      EList contents = resource.getContents();
      for (EObject object : contents) {
        if (object instanceof BaseElement && !(object instanceof PictogramElement)) {
          bpmnElements.add((BaseElement) object);
        }
      }
    }
    return bpmnElements.toArray(new BaseElement[bpmnElements.size()]);
  }

  public static InputStream getContentStream(final Content content) {
    return Util.class.getClassLoader().getResourceAsStream(content.getContentPath());
  }

  public enum Content {

    NEW_DIAGRAM_CONTENT("src/main/resources/content/new-diagram-content.xml"), NEW_SUBPROCESS_CONTENT("src/main/resources/content/new-subprocess-content.xml");

    private final String contentPath;

    private Content(String contentPath) {
      this.contentPath = contentPath;
    }

    public String getContentPath() {
      return contentPath;
    }

  }

  /**
   * Gets the {@link URI} where the diagram resource for a subprocess should be
   * stored.
   * 
   * @param diagram
   *          the parent diagram for the subprocess
   * @param subprocessId
   *          the id of the subprocess
   * @return the {@link URI} for the subprocess' resource
   */
  public static final URI getSubProcessURI(Diagram diagram, String subprocessId) {

    final URI baseURI = diagram.eResource().getURI().trimFileExtension();
    final URI subProcessURI = baseURI.appendFileExtension(subprocessId).appendFileExtension(diagram.eResource().getURI().fileExtension());

    return subProcessURI;
  }

  /**
   * Replaces the document name in the provided contentStream's content and
   * returns a new stream containing the new content.
   * 
   * @param diagramName
   *          the name of the document to use
   * @param contentStream
   *          the original content stream
   * @return
   */
  public static InputStream swapStreamContents(final String diagramName, final InputStream contentStream) {
    InputStream result = null;

    try {

      Writer writer = new StringWriter();
      char[] buffer = new char[1024];
      try {
        Reader reader = new BufferedReader(new InputStreamReader(contentStream, "UTF-8"));
        int n;
        while ((n = reader.read(buffer)) != -1) {
          writer.write(buffer, 0, n);
        }
      } finally {
        contentStream.close();
      }
      String contentString = writer.toString();
      contentString = contentString.replace(DIAGRAM_NAME_DEFAULT, String.format(DIAGRAM_NAME_PATTERN, diagramName));

      result = new ByteArrayInputStream(contentString.getBytes());
    } catch (Exception e) {
      // TODO
    }
    return result;
  }
}