/*
 * Java-Gnome Bindings Library
 *
 * Copyright 1998-2004 the Java-Gnome Team, all rights reserved.
 *
 * The Java-Gnome bindings library is free software distributed under
 * the terms of the GNU Library General Public License version 2.
 */

package org.gnu.gtk;

import org.gnu.glib.Type;
import org.gnu.glib.Handle;

/**
 * This is the base class of HBox and VBox. It has the code necessary to
 * maintain the contained list of widgets, but it does not position them.
 * <p>
 * Box uses a notion of <em>packing</em>. Packing refers to adding widgets
 * with reference to a particular position in a Container. For a Box, there are
 * two reference positions: the start and the end of the box. For a VBox, the
 * start is defined as the top of the box and the end is defined as the bottom.
 * For a HBox the start is defined as the left side and the end is defined as
 * the right side.
 * <p>
 * Use repeated calls to <code>packStart</code> to pack widgets into a Box
 * from start to end. Use <code>packEnd</code> to add widgets from end to
 * start. You may intersperse these calls and add widgets from both ends of the
 * same Box.
 */
public class Box extends Container {
    protected Box(Handle handle) {
        super(handle);
    }

    /**
     * Internal static factory method to be used by Java-Gnome only.
     */
    protected static Box getBox(Handle handle) {
        if (handle == null)
            return null;

        Box obj = (Box) getGObjectFromHandle(handle);
        if (obj == null)
            obj = new Box(handle);

        return obj;
    }

    /**
     * Adds child to the box, packed with reference to the start of box. The
     * child is packed after any other child packed with reference to the start
     * of box. This method takes the default values for expansion, fill and
     * padding.
     * 
     * @param child
     *            The widget to be added to the box.
     */
    public void packStart(Widget child) {
        gtk_box_pack_start_defaults(getHandle(), child.getHandle());
    }

    /**
     * Adds child to the box, packed with reference to the start of box. The
     * child is packed after any other child packed with reference to the start
     * of box. This method allows you to define the properties of the packing.
     * 
     * @param child
     *            The widget to be added.
     * @param expand
     *            TRUE if the new child is to be given extra space allocated to
     *            box. The extra space will be divided evenly between all
     *            children of box that use this option.
     * @param fill
     *            TRUE if space given to child by the expand option is actually
     *            allocated to child, rather than just padding it. This
     *            parameter has no effect if expand is set to FALSE. A child is
     *            always allocated the full height of a HBox and the full width
     *            of a VBox. This option affects the other dimension.
     * @param padding
     *            Extra space in pixels to put between this child and its
     *            neighbors, over and above the global amount specified by
     *            spacing in Box. If child is a widget at one of the reference
     *            ends of box, then padding pixels are also put between child
     *            and the reference edge of Box.
     */
    public void packStart(Widget child, boolean expand, boolean fill,
            int padding) {
        gtk_box_pack_start(getHandle(), child.getHandle(), expand, fill,
                padding);
    }

    /**
     * Adds child to the box, packed with reference to the end of box. The child
     * is packed before any other child packed with reference to the end of box.
     * This method takes the default values for expansion, fill and padding.
     * 
     * @param child
     *            The widget to be added to the box.
     */
    public void packEnd(Widget child) {
        gtk_box_pack_end_defaults(getHandle(), child.getHandle());
    }

    /**
     * Adds child to the box, packed with reference to the end of box. The child
     * is packed after any other child packed with reference to the end of box.
     * This method allows you to define the properties of the packing.
     * 
     * @param child
     *            The widget to be added.
     * @param expand
     *            TRUE if the new child is to be given extra space allocated to
     *            box. The extra space will be divided evenly between all
     *            children of box that use this option.
     * @param fill
     *            TRUE if space given to child by the expand option is actually
     *            allocated to child, rather than just padding it. This
     *            parameter has no effect if expand is set to FALSE. A child is
     *            always allocated the full height of a HBox and the full width
     *            of a VBox. This option affects the other dimension.
     * @param padding
     *            Extra space in pixels to put between this child and its
     *            neighbors, over and above the global amount specified by
     *            spacing in Box. If child is a widget at one of the reference
     *            ends of box, then padding pixels are also put between child
     *            and the reference edge of Box.
     */
    public void packEnd(Widget child, boolean expand, boolean fill, int padding) {
        gtk_box_pack_end(getHandle(), child.getHandle(), expand, fill, padding);
    }

    /**
     * Sets the <em>homogeneous</em> field of Box, controlling whether or not
     * all children of box are given equal space in the box.
     * 
     * @param homogenous
     *            A boolean value, TRUE to create equal allotments, FALSE for
     *            variable allotments.
     */
    public void setHomogeneous(boolean homogenous) {
        gtk_box_set_homogeneous(getHandle(), homogenous);
    }

    /**
     * Returns whether the box is homogeneous (all children are the same size).
     * 
     * @return TRUE if the box is homogeneous.
     * @see Box#setHomogeneous(boolean)
     */
    public boolean getHomogeneous() {
        return gtk_box_get_homogeneous(getHandle());
    }

    /**
     * Sets the number of pixels to place between children of the box.
     * 
     * @param spacing
     *            The number of pixels to put between children.
     */
    public void setSpacing(int spacing) {
        gtk_box_set_spacing(getHandle(), spacing);
    }

    /**
     * Gets the spacing between the children of the box.
     * 
     * @return Spacing between children
     */
    public int getSpacing() {
        return gtk_box_get_spacing(getHandle());
    }

    /**
     * Moves child to a new position in the list of box children.
     * <p>
     * A widget's position in the box children list determines where the widget
     * is packed into box. A child widget at some position in the list will be
     * packed just after all other widgets of the same packing type that appear
     * earlier in the list.
     * 
     * @param child
     *            The widget to move
     * @param position
     *            The new position for child in the box, starting from 0. If
     *            negative, the end of the list is used.
     */
    public void reorderChild(Widget child, int position) {
        gtk_box_reorder_child(getHandle(), child.getHandle(), position);
    }

    /**
     * Retrieve the runtime type used by the GLib library.
     */
    public static Type getType() {
        return new Type(gtk_box_get_type());
    }

    native static final protected int gtk_box_get_type();

    native static final protected void gtk_box_pack_start(Handle box,
            Handle child, boolean expand, boolean fill, int padding);

    native static final protected void gtk_box_pack_end(Handle box,
            Handle child, boolean expand, boolean fill, int padding);

    native static final protected void gtk_box_pack_start_defaults(Handle box,
            Handle child);

    native static final protected void gtk_box_pack_end_defaults(Handle box,
            Handle child);

    native static final protected void gtk_box_set_homogeneous(Handle box,
            boolean homogenous);

    native static final protected boolean gtk_box_get_homogeneous(Handle box);

    native static final protected void gtk_box_set_spacing(Handle box,
            int spacing);

    native static final protected int gtk_box_get_spacing(Handle box);

    native static final protected void gtk_box_reorder_child(Handle box,
            Handle child, int position);

    native static final protected void gtk_box_query_child_packing(Handle box,
            Handle child, boolean[] expand, boolean[] fill, int[] padding,
            int[] packType);

    native static final protected void gtk_box_set_child_packing(Handle box,
            Handle child, boolean expand, boolean fill, int padding,
            int packType);

}
