view dwtx/draw2d/ScrollPaneSolver.d @ 98:95307ad235d9

Added Draw2d code, still work in progress
author Frank Benoit <benoit@tionex.de>
date Sun, 03 Aug 2008 00:52:14 +0200
parents
children
line wrap: on
line source

/*******************************************************************************
 * Copyright (c) 2000, 2005 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *     IBM Corporation - initial API and implementation
 * Port to the D programming language:
 *     Frank Benoit <benoit@tionex.de>
 *******************************************************************************/
module dwtx.draw2d.ScrollPaneSolver;

import dwt.dwthelper.utils;

import dwtx.draw2d.geometry.Dimension;
import dwtx.draw2d.geometry.Insets;
import dwtx.draw2d.geometry.Rectangle;
import dwtx.draw2d.Viewport;

/**
 * This class handles the calculation of solving for the area of a
 * {@link dwtx.draw2d.ScrollPane}'s viewport and insets. Also determines if
 * the horizontal and vertical scrollbars should be visible.
 */
public class ScrollPaneSolver {

/** Scrollbar visibility constants -- never show scrollbars **/
public static const int NEVER = 0;
/** Scrollbar visibility constants -- show scrollbars automatically **/
public static const int AUTOMATIC = 1;
/** Scrollbar visibility constants -- always show scrollbars **/
public static const int ALWAYS = 2;

/**
 * Container class for the results of ScrollPaneSolver's solve method
 */
public static class Result {
    /** Show horizontal scrollbar bool **/
    public bool showH;

    /** Show vertical scrollbar bool **/
    public bool showV;

    /** Area of ScrollPane's viewport **/
    public Rectangle viewportArea;

    /** Insets of ScrollPane **/
    public Insets insets;
}

/**
 * Solves for the viewport area, insets, and visibility of horizontal and vertical
 * scrollbars of a ScrollPane
 * @param clientArea The ScrollPane's client area
 * @param viewport The ScrollPane's Viewport
 * @param hVis Horizontal scrollbar visibility
 * @param vVis Vertical scrollbar visibility
 * @param vBarWidth Width of vertical scrollbar
 * @param hBarHeight Height of horizontal scrollbar
 * @return the Result
 */
public static Result solve(Rectangle clientArea, Viewport viewport, int hVis, int vVis,
                            int vBarWidth, int hBarHeight) {
    Result result = new Result();
    result.insets = new Insets();
    result.insets.bottom = hBarHeight;
    result.insets.right  = vBarWidth;

    Dimension available  = clientArea.getSize();
    Dimension guaranteed = (new Dimension(available)).shrink(
                (vVis is NEVER ? 0 : result.insets.right),
                (hVis is NEVER ? 0 : result.insets.bottom));
    guaranteed.width = Math.max(guaranteed.width, 0);
    guaranteed.height = Math.max(guaranteed.height, 0);
    int wHint = guaranteed.width;
    int hHint = guaranteed.height;

    Dimension preferred  = viewport.getPreferredSize(wHint, hHint).getCopy();
    Insets viewportInsets = viewport.getInsets();
    /*
     * This was calling viewport.getMinimumSize(), but viewport's minimum size was really
     * small, and wasn't a function of its contents.
     */
    Dimension viewportMinSize = new Dimension(
            viewportInsets.getWidth(), viewportInsets.getHeight());
    if (viewport.getContents() !is null) {
        if (viewport.getContentsTracksHeight() && hHint > -1)
            hHint = Math.max(0, hHint - viewportInsets.getHeight());
        if (viewport.getContentsTracksWidth() && wHint > -1)
            wHint = Math.max(0, wHint - viewportInsets.getWidth());
        viewportMinSize.expand(
            viewport.getContents().getMinimumSize(wHint, hHint));
    }

    /*
     * Adjust preferred size if tracking flags set.  Basically, tracking is "compress view
     * until its minimum size is reached".
     */
    if (viewport.getContentsTracksHeight())
        preferred.height = viewportMinSize.height;
    if (viewport.getContentsTracksWidth())
        preferred.width = viewportMinSize.width;

    bool none = available.contains(preferred),
            both = !none && preferred.containsProper(guaranteed),
           showV = both || preferred.height > available.height,
           showH = both || preferred.width  > available.width;

    //Adjust for visibility override flags
    result.showV = vVis !is NEVER && (showV || vVis is ALWAYS);
    result.showH = hVis !is NEVER && (showH || hVis is ALWAYS);

    if (!result.showV)
        result.insets.right = 0;
    if (!result.showH)
        result.insets.bottom = 0;
    result.viewportArea = clientArea.getCropped(result.insets);
    viewport.setBounds(result.viewportArea);
    return result;
}

}