Block.java :  » Database-ORM » MMBase » org » mmbase » framework » Java Open Source

Java Open Source » Database ORM » MMBase 
MMBase » org » mmbase » framework » Block.java
/*

This software is OSI Certified Open Source Software.
OSI Certified is a certification mark of the Open Source Initiative.

The license (Mozilla version 1.0) can be read at the MMBase site.
See http://www.MMBase.org/license

*/
package org.mmbase.framework;
import java.util.*;
import org.mmbase.util.functions.*;
import org.mmbase.util.LocalizedString;

import org.mmbase.util.logging.Logger;
import org.mmbase.util.logging.Logging;

/**
 * A Block is a representation of a page within a component. It has 2 renderers,
 * 'head' and 'body', and a  processor.
 *
 * @author Johannes Verelst
 * @author Michiel Meeuwissen
 * @version $Id: Block.java,v 1.33 2008/02/23 16:46:19 michiel Exp $
 * @since MMBase-1.9
 */
public class Block {

    private static final Logger log = Logging.getLoggerInstance(Block.class);

    private final Map<Renderer.Type, Renderer> renderers = new EnumMap<Renderer.Type, Renderer>(Renderer.Type.class);
    Processor processor;

    protected Parameter.Wrapper specific;

    private final String name;
    private final String mimetype;
    private final Component parent;
    private final LocalizedString description;
    private final LocalizedString title;
    private final Type[] classification;

    public Block(String name, String mimetype, Component parent, Type[] cla) {
        if (name   == null) throw new IllegalArgumentException();
        if (parent == null) throw new IllegalArgumentException();
        if (cla    == null) throw new IllegalArgumentException();
        this.name = name;
        this.parent = parent;
        this.mimetype = mimetype; // can this be null?
        this.classification = cla;
        for (Type t : classification) {
            t.blocks.add(this);
        }
        this.description = new LocalizedString(name);
        this.title       = new LocalizedString(name);
    }

    /**
     * Name for this block. Never <code>null</code>
     */
    public String getName() {
        return name;
    }

    /**
     * A localized title for this block.
     */
    public LocalizedString getTitle() {
        return title;
    }

    /**
     * Mimetype for this block. E.g. "text/html".
     */
    public String getMimeType() {
        return mimetype;
    }

    /**
     * Returns the 'classification' of this block. For example the blocks
     * classified as 'mmbase.admin' are presented in the mmbase admin-pages.
     */
    public Type[] getClassification() {
        return classification;
    }

    /**
     * @todo This method is not yet implemented.
     */
    public Type[] getClassification(String filter) {
        String[] parts = filter.split("\\s*?[,\\s]\\s*");
        for (Type type : classification) {

        }
        return null;
    }

    /**
     * Description for this block. Never <code>null</code>
     */
    public LocalizedString getDescription() {
        return description;
    }

    /**
     * All renderers assiociated with this Block. This is not a public method (it is used to create
     * the block). Use {@link #getRenderer(Renderer.Type}).
     */
    Map<Renderer.Type, Renderer> getRenderers() {
        return renderers;
    }

    /**
     * @return A renderer for the given Render type. Never <code>null</code>
     */
    public Renderer getRenderer(Renderer.Type type) {
        Renderer rend = renderers.get(type);
        return rend == null ? type.getEmpty(this) : rend;
    }

    /**
     * @return The processor associated with this block. Never <code>null</code>
     */
    public Processor getProcessor() {
        return processor == null ? AbstractProcessor.getEmpty(this) : processor;
    }


    void addParameters(Parameter ... params) {
        List<Parameter> help = new ArrayList<Parameter>();
        if (specific != null) {
            help.addAll(Arrays.asList(specific.getArguments()));
        }
        for (Parameter p : params) {
            help.add(p);
        }
        specific = new Parameter.Wrapper(help.toArray(Parameter.emptyArray()));
        log.debug("Set parameters of " + this + " to " + help);
    }


    /**
     * Before rendering, it may have to be fed with certain parameters. Obtain a parameters
     * object which this method, fill it, and feed it back into {@link Renderer#render}.
     */
    public Parameters createParameters() {
        if (specific == null) {
            return new AutodefiningParameters();
        } else {
            return new Parameters(specific,
                                  new Parameter.Wrapper(getRenderer(Renderer.Type.HEAD).getParameters()),
                                  new Parameter.Wrapper(getRenderer(Renderer.Type.BODY).getParameters()),
                                  new Parameter.Wrapper(getProcessor().getParameters()));
        }
    }

    /**
     * @return the Component from which this block is a part.
     */
    public Component getComponent() {
        return parent;
    }

    public String toString() {
        return getName();
    }

    /**
     * Every block can be assigned a hierarchal 'Type', which can classify it.
     */
    public static class Type implements Comparable<Type> {
        public static final Type ROOT = new Type("ROOT");
        /**
         * All unclassified blocks are of this type
         */
        public static final Type NO   = new Type("");

        /**
         * @javadoc
         */
        public static Type[] getClassification(String p, boolean create) {
            if (p == null || "".equals(p)) return new Type[] {NO};
            List<Type> r = new ArrayList<Type>();
            PARTS:
            for (String part : p.split("\\s*?[,\\s]\\s*")) {
                Type t = ROOT;
                for (String e : part.split("\\.")) {
                    Type proposal = new Type(e, t);
                    int i = t.subs.indexOf(proposal);
                    if (i == -1) {
                        if (create) {
                            t.subs.add(proposal);
                        } else {
                            continue PARTS;
                        }
                    } else {
                        proposal = t.subs.get(i);
                    }
                    Collections.sort(t.subs);
                    t = proposal;
                }
                r.add(t);
            }
            return r.toArray(new Type[] {});
        }

        private final String name;
        private final Type parent;
        private int weight = 100;
        final List<Type>  subs   = new ArrayList<Type>();
        final List<Block> blocks = new ArrayList<Block>();
        private Type(String n) {
            name = n;
            parent = null;
        }
        protected Type(String n, Type p) {
            if (n == null) throw new IllegalArgumentException();
            if (p == null) throw new IllegalArgumentException();
            name = n;
            parent = p;
        }
        public List<Type> getSubTypes() {
            return Collections.unmodifiableList(subs);
        }

        public List<Block> getBlocks() {
            return Collections.unmodifiableList(blocks);
        }
        public String getName() {
            return name;
        }

        public void setWeight(int w) {
            weight = w;
            if (parent != null) {
                Collections.sort(parent.subs);
            }
        }
        public int getWeight() {
            return weight;
        }

        /**
         * @todo
         */
        public boolean contains(String test) {
            return false;
        }

        Type getParent() {
            return parent;
        }
        public boolean equals(Object o) {
            if (o instanceof Type) {
                Type t = (Type) o;
                return name.equals(t.name) && parent == t.parent;
            } else {
                return false;
            }
        }
        public int hashCode() {
            return name.hashCode();
        }
        public String toString() {
            return name + subs.toString();
        }

        public int compareTo(Type t) {
            int s = weight - t.weight;
            return s == 0 ? name.compareTo(t.name) : s;
        }
    }


}
java2s.com  | Contact Us | Privacy Policy
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.