/*
 * File: p04.java
 *
 * Description:  Okay, time to end these things properly.  We
 *       add a Quit button so we can exit the app without having
 *       to press control-c.  Also, we add an extention to the
 *       StringBuffer class to handle the manipulation of the
 *       incoming arguments (if any).
 *
 * Modifications:  11/5/95 CValcarcel Created.
 *
 * NO WARRANTY, EXPRESSED OR IMPLIED, BLAH, BLAH, BLAH.
 *
 * THIS IS EXAMPLE CODE AND SHOULD NOT BE USED FOR ANYTHING
 * EXCEPT INSTRUCTIONAL PURPOSES.
 *
 */

//
// There is no import java.lang.StringBuffer
// because it is implied.  We could list it
// if we wanted to (but why?).
//
import java.awt.BorderLayout;
import java.awt.Button;
import java.awt.Event;
import java.awt.Frame;
import java.awt.Label;
import java.awt.Panel;

//
// The name of the class has changed (so I know which
// example I'm running) but the "extends" is the same.
//
class EchoQuit extends Frame {
    //
    // Ah!  By setting up these variables as static we change
    // their status in the world:  they are no longer instance
    // variables (meaning they are ALWAYS created when this
    // class is instantiated) they are static variables which
    // means they are created ONCE by Java and you can access
    // them anytime you want (even before you instantiate a
    // EchoQuit object) by referencing EchoQuit.FRAME_WIDTH
    // or EchoQuit.FRAME_HEIGHT.  The equivalent in C would
    // be a #define or a const.
    //
    // Yes, FRAME_WIDTH and FRAME_HEIGHT are not very useful
    // names for these constants (but they'll do for now).
    //
    static int FRAME_WIDTH  = 200;
    static int FRAME_HEIGHT =  50;

    // We need some way to clump together our two GUI objects.
    // Panels allow us to do that.
    Panel pMain;

    //
    // We change the constructor name as the class name
    // has changed, but the incoming arguments are still
    // the same.
    //
    public EchoQuit( String title,
                     String message )
    {
        super( title );    // Create and title the Frame

        // Create a Panel and tell it what type of layout
        // to use.  In this case we use BorderLayout
        // which means place the incoming components based on
        // such vague mutterings as "North", "South", "East",
        // "West", and "Center".
        //
        // As we do not need to refer to the BorderLayout
        // object we are creating we just send it in as an
        // argument and don't worry about it.
        pMain = new Panel();
        pMain.setLayout( new BorderLayout() );

        // We don't need to remember anything about
        // the Label object so we throw it in as an
        // raw argument.
        pMain.add( "North", new Label(message) );

        // Same goes for the QuitButton as for the Label
        pMain.add( "South", new QuitButton() );

        // Add the Panel to the EchoQuit object which is
        // really a call to Frame.add()
        add( pMain );

        // Open the window to a certain size.  If the
        // string is very long it will simply be truncated.
        resize( FRAME_WIDTH, FRAME_HEIGHT );

        show(); // Display us

        // Don't let anyone resize this Frame!
        setResizable( false );
    }

    //
    // Okay, make sure we can see the contents of our Frame.
    // Even though the user cannot resize the window, this
    // will insure it is done properly at the start and whenever
    // the window is exposed.
    //
    public void repaint()                         
    {
         pMain.resize( size() );
    }

    //
    // Here we are again.
    //
    public static void main( String args[] )
    {
        //
        // Create one long string with the list of args
        // each separated by a space.
        //
        SuperString  strMsg = new SuperString( args );

        //
        // Call out new class.  Remember:  the second
        // argument has to be a String so we call toString()
        // which transforms out SuperString back into Clark
        // Kent...I mean a mild-mannered String.
        //
        EchoQuit app = new EchoQuit( "Display A String",
                                     strMsg.toString() );
    }
}

//
// For now the act of adding callback functionality to a
// button means extending the Button class.  Not wonderful,
// but it will until some other way is found.  It does force
// a very specific encapsulation, though.
//
class QuitButton extends Button
{
    public QuitButton()
    {
        super( "Quit" );
    }

    //
    // We don't really care what happened to this button.
    // If anything happens that causes handleEvent() to
    // be called then exit().  We override Button handleEvent()
    // to do that.  In alpha3 this would have been the
    // member function selected().
    //
    public boolean handleEvent( Event event )
    {
        System.exit(0);

        // The compiler insists on this even though the
        // above logic makes it superfluous.
        return true;
    }
}

//
// This is new.  In the third example I put the code
// to concatenate the arguments directly in
// main().  That is an OO no-no.  It is raw Structured
// Programming and we know how awful that is ;-).
//
// SuperString is a StringBuffer (String is final, so it
// cannot be sub-classed) and when it is created it
// executes the same code it did last time (the variable
// names have been changed to protect the innocent).  The use
// append in this case is actually an expense proposition
// because the StringBuffer is allocating more and more memory
// to contain the strings we keep sending in.
//
// FYI:  It would be more efficient to get a length count and
// call super(total_length) rather than the raw method used below.
//
class SuperString extends StringBuffer
{
    public SuperString( String wordlist[] )
    {
        if ( wordlist.length > 0 )
        {
            // Start stringing the strings together
            append( wordlist[0] );

            for ( int i = 1; i < wordlist.length; i++ )
                append( " " + wordlist[i] );
        }
        // else we have no wordlist to put together
    }
}
