/* 
   PXKScroller.m

   NSScroller for GNUstep GUI X/DPS Backend

   Copyright (C) 1996 Free Software Foundation, Inc.

   Author:  Pascal Forget <pascal@wsc.com>
   Date: October 1995
   
   This file is part of the GNUstep GUI X/DPS Backend.

   This library is free software; you can redistribute it and/or
   modify it under the terms of the GNU Library General Public
   License as published by the Free Software Foundation; either
   version 2 of the License, or (at your option) any later version.
   
   This library is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
   Library General Public License for more details.

   If you are interested in a warranty or support for this source code,
   contact Scott Christley <scottc@net-community.com> for more information.
   
   You should have received a copy of the GNU Library General Public
   License along with this library; if not, write to the Free
   Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/ 

#include <gnustep/xdps/PXKScroller.h>
#include <gnustep/xdps/PXKScrollView.h>
#include <gnustep/xdps/PXKView.h>
#include <gnustep/xdps/PXKButton.h>
#include <gnustep/xdps/PXKImage.h>

@implementation PXKScroller

- (BOOL)arrowsAreVisible;
{
    return showArrows;
}

- (float)currentValue;
{
    return currentValue;
}

- decrement;
{
    currentValue -= step;

    if (currentValue < minValue) {
	currentValue = minValue;
    }

    [(PXKScrollButton *)[sub_views objectAtIndex:0] adjustLocation];

    return self;
}

- (void)display;
{
    [self setBackgroundColor:"dark gray"];
    [super display];
    [self placeSubviews];
    [self drawBorder];
    XMapSubwindows(pxkDisplay, [(PXKView *)self xWindow]);
    [sub_views makeObjectsPerform:@selector(display)];
    XFlush(pxkDisplay);
}

- drawBorder;
{
  //    (void)load_font(&win_font);

    XDrawLine(pxkDisplay, [(PXKView *)self xWindow], pxkBlackGC, 
	      0, frame.size.height-1,
	      frame.size.width-1, frame.size.height-1);

    XDrawLine(pxkDisplay, [(PXKView *)self xWindow], pxkBlackGC, 
	      frame.size.width-1,
	      0, frame.size.width-1, frame.size.height-1);

    XDrawLine(pxkDisplay, [(PXKView *)self xWindow], pxkBlackGC, 0, 0,
	      frame.size.width-1, 0);

    XDrawLine(pxkDisplay, [(PXKView *)self xWindow], pxkBlackGC, 
	      0, 0, 0, frame.size.height-1);
    
#if 0
    XDrawRectangle(pxkDisplay, xWindow, pxkBlackGC,
		   frame.origin.x+1, frame.origin.y+1,
		   frame.size.width-1,
		   frame.size.height-1);
#endif
    
    return self;
}

- hideArrows;
{
    showArrows = NO;
    return self;
}

- increment;
{
    currentValue += step;

    if (currentValue > maxValue) {
	currentValue = maxValue;
    }

    [(PXKScrollButton *)[sub_views objectAtIndex:0] adjustLocation];

    return self;
}

- initWithSuperview:(PXKView *)aView;
{
    PXKScrollButton *button;

    [super initWithSuperview:aView];    
    maxValue = 1.0;
    minValue = 0.0;
    currentValue = 0.5;
    showArrows = YES;

    ratio = 1.0;
    step = 0.1;
    
    button = [[PXKScrollButton alloc] initWithSuperview:self];
    [self addSubview:button];
    [button setBackgroundColor:"light gray"];
    
    button = [[PXKButton alloc] initWithSuperview:self];
    [self addSubview:button];
    [button setTitle:[[NSString alloc] initWithCString:""]];
    [button setBackgroundColor:"light gray"];
    [button setTarget:self];
    [button setAction:@selector(decrement)];

    button = [[PXKButton alloc] initWithSuperview:self];
    [self addSubview:button];
    [button setTitle:[[NSString alloc] initWithCString:""]];
    [button setBackgroundColor:"light gray"];
    [button setTarget:self];
    [button setAction:@selector(increment)];

    return self;
}

- (float)maxValue;
{
    return maxValue;
}

- (float)minValue;
{
    return minValue;
}

- mouseDown:(XEvent *)e;
{
    XEvent event = *e;
    
    [[sub_views objectAtIndex:0] moveTo:event.xmotion.x :event.xmotion.y];
    return self;
}

- placeSubviews;
{
    NSRect rect;
    PXKScrollButton *button;
    PXKButton *arrow;

    puts("PXKScroller placeSubviews");
    
    /*
     * Place the origin (minimum value) arrow
     */
    rect.origin.x = 2;
    rect.origin.y = 2;
    rect.size.width = PXK_ARROW_SIZE;
    rect.size.height = PXK_ARROW_SIZE;

    arrow = [sub_views objectAtIndex:1];
    [arrow setFrame:rect];
    [arrow setState:0];
	  
    /*
     * Place the max value arrow
     */
    arrow = [sub_views objectAtIndex:2];
    if (vertical) {
	rect.origin.y = frame.size.height - PXK_ARROW_SIZE - 2;
    }
    rect.origin.x = frame.size.width - PXK_ARROW_SIZE - 2;
    [arrow setFrame:rect];
    [arrow setState:0];
    
    /*
     * Set the scrolling area for the scroll button
     */
    button = [sub_views objectAtIndex:0];
    [button setState:0];
    
    if (vertical) {
	if (showArrows) {
	    rect.origin.y = PXK_ARROW_SIZE + 3;
	    rect.size.height = frame.size.height - 2*(PXK_ARROW_SIZE + 2) - 2;
	} else {
	    rect.origin.y = 2;
	    rect.size.height = frame.size.width - 4;
	}
	rect.origin.x = 2;
	rect.size.width = PXK_ARROW_SIZE;

    } else {
	if (showArrows) {
	    rect.origin.x = PXK_ARROW_SIZE + 3;
	    rect.size.width = frame.size.width - 2*(PXK_ARROW_SIZE + 2) - 2;
	} else {
	    rect.origin.x = 2;
	    rect.size.width = frame.size.width - 4;
	}
	rect.origin.y = 2;
	rect.size.height = PXK_ARROW_SIZE;
    }

#if 0
    fprintf(stdout, "sx: %d sy: %d w: %d h: %d\n", rect.origin.x,
	    rect.origin.y,rect.size.width, rect.size.height);
#endif
    
    [button setScrollArea:rect];
    [button setRatio:ratio];
    [button setState:1];

    if ((super_view != nil) && ([super_view class] == [PXKScrollView class]))
    {
	[super_view updateScrollers];
    }
	  
    return self;
}

- (float)ratio;
{
    return ratio;
}

- (float)relativePosition;
{
    return currentValue/(maxValue-minValue);
}

- setCurrentValue:(float)value;
{
#if 0
    fprintf(stdout, "Scroller: new current value: %f\n", value);
#endif
    currentValue = value;
    if (vertical) {
	[super_view yScrolled];
    } else {
	[super_view xScrolled];
    }
    return self;
}

- setFrame:(NSRect)newFrame;
{
    NSRect r = newFrame;

    frame = r;

    if (frame.size.width > frame.size.height) {
	vertical = NO;
	[[sub_views objectAtIndex:1] setImage:
				    [PXKImage imageNamed:"pxkLeftArrow"]];

	[[sub_views objectAtIndex:2] setImage:
				    [PXKImage imageNamed:"pxkRightArrow"]];
    } else {
	vertical = YES;
	[[sub_views objectAtIndex:1] setImage:
				    [PXKImage imageNamed:"pxkUpArrow"]];

	[[sub_views objectAtIndex:2] setImage:
				    [PXKImage imageNamed:"pxkDownArrow"]];
	
    }

#if 1
    XMoveResizeWindow(pxkDisplay, [(PXKView *)self xWindow],
		      frame.origin.x, frame.origin.y,
		      frame.size.width, frame.size.height);
#else
    XMoveWindow(pxkDisplay, xWindow, frame.origin.x, frame.origin.y);
    XResizeWindow(pxkDisplay, xWindow, frame.size.width, frame.size.height);
#endif
    
    //[self display];
    return self;
}

- setMaxValue:(float)value;
{
    maxValue = value;
    return self;
}

- setMinValue:(float)value;
{
    minValue = value;
    return self;
}

- setRatio:(float)r;
{
    ratio = r;
    
    [[sub_views firstObject] setRatio:r];
    return self;
}

- setStep:(float)s;
{
    step = s;
    return self;
}

- showArrows;
{
    showArrows = YES;
    return self;
}

- (float)step;
{
    return step;
}

- (BOOL)vertical;
{
    return vertical;
}

@end
