
 // Michael McElroy
 // michaelmcelroy.net, 2010

    var mm_view = function ()
    
        {
        this . wm = "6D69636861656C406D69636861656C6D63656C726F792E6E6574";
        this . context = null;
        this . square_height = 64;
        this . square_width = this . square_height;
        this . board = null; // canvas
        this . board_picture = null;
        this . pieces_picture = null;
        this . check_picture = null;
        this . picture_count = 0;
        this . x_count = 8;
        this . y_count = this . x_count;
        this . border_thickness = 32;
        this . board_height = this . square_height * this . y_count + this . border_thickness * 2;
        this . board_width = this . board_height;
        this . allow_render = NO;
        this . show_play_prompt = NO;
        this . show_information_prompt = NO;
        this . show_exchange_prompt = NO;
        this . show_color_prompt = NO;
        this . show_promotion_prompt = NO;
        this . show_continue_prompt = NO;

        this . initialize = function ()
        
            {
            this . allow_render = YES;

            this . context = $ ("canvas") . getContext ("2d");
            this . load_pictures ();
            this . render_board ();
            this . render ();

            this . show_play_prompt = YES;
            this . show_information_prompt = YES;
            this . show_exchange_prompt = YES;
            this . show_color_prompt = NO;
            this . show_promotion_prompt = NO;
            this . show_continue_prompt = NO;
            
            return;
            };

        this . reset = function ()
        
            {
            this . view_field ($ ("opponent"));

            return;
            };
        
        this . view_field = function (node)
        
            {
            if (node . value == "") node . value = node . view_text;
            if (node . value == node . view_text) node . style . color = "#555555";

            return;
            };

        this . edit_field = function (node)
        
            {
            if (node . value == node . view_text)
            
                {
                node . style . color = "#0000BB";
                node . value = "";
                }

            return;
            };

        this . write_message = function (message)
        
            {
            remove_subnodes ($ ("message"));

            $ ("message") . appendChild (window . document . createTextNode (message));

            return;
            };

        this . render_board = function ()
        
            {
            if (this . board_picture . is_loaded)

                {
                if (this . board == null)
                
                    {
                    this . board = window . document . createElement ("canvas");
                    this . board . setAttribute ("width", this . board_width);
                    this . board . setAttribute ("height", this . board_height);
                    }

                try {this . board . getContext ("2d") . drawImage (this . board_picture, 62 + 0, 62 + 700 * 2, this . board_width, this . board_height, 0, 0, this . board_width, this . board_height);} catch (exception) {} // border
                
                for (var x = 0; x < this . x_count; x ++)
                for (var y = 0; y < this . y_count; y ++)
                
                    {            
                    try {this . board . getContext ("2d") . drawImage (this . board_picture, 62 + this . square_width * x + this . border_thickness, 62 + (((y % 2) == (x % 2)) ? 0 : 700) + this . square_height * y + this . border_thickness, this . square_width, this . square_height, this . border_thickness + this . square_width * x, this . border_thickness + this . square_height * y, this . square_width, this . square_height);} catch (exception) {}
                    }        
                }
            
            else
            
                {
                window . setTimeout ("view . render_board ();", SHORT_RENDER_DELAY);
                }

            return;
            };

        this . render = function ()
        
            {
            if (game . analysis == NO)
            if (this . allow_render)
            
                {
                try

                    {
                    $ ("play_prompt") . style . display = "none";
                    $ ("information_prompt") . style . display = "none";
                    $ ("continue_prompt") . style . display = "none";
                    $ ("exchange_prompt") . style . display = "none";
                    $ ("color_prompt") . style . display = "none";
                    $ ("promotion_prompt") . style . display = "none";
                    $ ("replay_option") . style . visibility = "hidden";

                    if (this . show_play_prompt)
                    
                        {
                        $ ("play_prompt") . style . display = "table";
                        this .  write_message ("Click on the board.");
                        }
                    
                    else if (this . show_information_prompt)
                    
                        {
                        $ ("information_prompt") . style . display = "table";
                        this .  write_message ("");
                        }
                    
                    else if (this . show_continue_prompt)
                    
                        {
                        $ ("continue_prompt") . style . display = "table";
                        this .  write_message ("");
                        }
                    
                    else if (this . show_exchange_prompt)
                    
                        {
                        $ ("exchange_prompt") . style . display = "table";
                        this .  write_message ("");
                        }
                    
                    else if (this . show_color_prompt)
                    
                        {
                        $ ("color_prompt") . style . display = "table";
                        this . write_message ("Select a color.")
                        }
                    
                    else if (this . show_promotion_prompt)
                    
                        {
                        $ ("promotion_prompt") . style . display = "table";
                        this . write_message ("Select a piece.")
                        }

                    else
                    
                        {
                        this .  write_message ("");

                        if (game . turn == null) this . write_message ("Waiting for your opponent to select a color.");
                        if (game . turn != null) this . write_message ((game . turn == game . self) ? "Your turn." : "Waiting for your opponent to move.");
                        if (game . winner != null) this . write_message ((game . winner == "stalemate") ? "Stalemate" : "Checkmate");
                        if ((game . turn == game . self) && game . settled && (game . tape . length == 0) && (game . moves . length >= 1)) $ ("replay_option") . style . visibility = "visible";
                        }

                
                 // board

                    this . context . drawImage (this . board, 0, 0, this . board_width, this . board_height, 0, 0, this . board_width, this . board_height);


                 // pieces and check messages

                    for (var pass = 0; pass < 2; pass ++)
                    
                        {
                     // recently captured piece

                        if (game . moves . length > 0)
                        if (game . draw_captured_piece)
                        
                            {
                            var piece = game . moves [game . moves . length - 1] . captured_piece;

                            if (piece != null)

                                {
                                this . context . save ();
                                this . context . translate (this . border_thickness, this . border_thickness);
                                
                                switch (pass)
                                
                                    {
                                    case 0: this . draw_piece (piece);
                                    case 1: this . draw_check (piece);
                                    }
                                
                                this . context . restore ();
                                }
                            }        


                     // stationary pieces

                        for (var i = 0; i < game . pieces . length; i ++)
                        
                            {
                            var piece = game . pieces [i];
                            
                            if (! game . was_captured (piece))
                            if (piece != game . selected_piece)
                            if ((piece . x_offset == 0) && (piece . y_offset == 0))
                            
                                {
                                this . context . save ();
                                this . context . translate (this . border_thickness, this . border_thickness);

                                switch (pass)
                                
                                    {
                                    case 0: this . draw_piece (piece);
                                    case 1: this . draw_check (piece);
                                    }

                                this . context . restore ();
                                }
                            }        


                     // moving pieces

                        for (var i = 0; i < game . pieces . length; i ++)
                        
                            {
                            var piece = game . pieces [i];

                            if (! game . was_captured (piece))
                            if (piece != game . selected_piece)
                            if ((piece . x_offset != 0) || (piece . y_offset != 0))

                                {
                                this . context . save ();
                                this . context . translate (this . border_thickness, this . border_thickness);

                                switch (pass)

                                    {
                                    case 0: this . draw_piece (piece);
                                    case 1: this . draw_check (piece);
                                    }

                                this . context . restore ();
                                }
                            }        


                     // selected piece

                        if (game . selected_piece != null)

                            {
                            this . context . save ();
                            this . context . translate (this . border_thickness, this . border_thickness);

                            switch (pass)

                                {
                                case 0: this . draw_piece (game . selected_piece);
                                case 1: this . draw_check (game . selected_piece);
                                }

                            this . context . restore ();
                            }
                        }
                    }
                    
                catch (exception)
                
                    {
                    }
                }

            window . setTimeout ("view . render ();", ((game . selected_piece == null) && game . settled) ? LONG_RENDER_DELAY : SHORT_RENDER_DELAY);

            return;
            };

        this . draw_piece = function (piece)

            {
            if (this . allow_render)
            if (this . pieces_picture . is_loaded)

                {
                var c = null;   // color
                var t = null;   // title

                switch (piece . color)
                
                    {
                    case "white": c = 0; break;
                    case "black": c = 1; break;
                    }
                
                switch (piece . title)
                
                    {
                    case "pawn"  : t = 0; break;
                    case "knight": t = 1; break;
                    case "bishop": t = 2; break;
                    case "rook"  : t = 3; break;
                    case "queen" : t = 4; break;
                    case "king"  : t = 5; break;
                    }
                
                try
                
                    {
                    var x = piece . frozen ? piece . frozen_x : piece . x;
                    var y = piece . frozen ? piece . frozen_y : piece . y;

                    var xo = piece . frozen ? 0 : piece . x_offset;
                    var yo = piece . frozen ? 0 : piece . y_offset;

                    this . context . drawImage
                
                        (
                        this . pieces_picture,
                        piece . width * t,
                        piece . height * c,
                        piece . width,
                        piece . height,
                        Math . floor ((x - 0 + xo) * this . square_width) - 1,
                        Math . floor ((y - 0 + yo) * this . square_height) - 1,
                        piece . width,
                        piece . height
                        );
                    }
                
                catch (exception)

                    {
                    }
                }

            return;
            };
        
        this . draw_check = function (piece)
        
            {
            if (this . allow_render)
            if (this . check_picture . is_loaded)

                {
                try
                
                    {
                    var x = piece . frozen ? piece . frozen_x : piece . x;
                    var y = piece . frozen ? piece . frozen_y : piece . y;

                    var xo = piece . frozen ? 0 : piece . x_offset;
                    var yo = piece . frozen ? 0 : piece . y_offset;

                    for (var p = 0; p < game . pieces . length; p ++)
                    
                        {
                        if (game . was_captured (game . pieces [p]) == NO)
                        if (game . pieces [p] . color != piece . color)
                        if (game . pieces [p] . title == "king")
                        
                            {
                            var king = game . pieces [p];
                            var move = new mm_move (piece . x, piece . y, king . x, king . y, null);
                            
                            if (game . is_legal (move))
                            
                                {
                                this . context . drawImage
                                
                                    (
                                    this . check_picture,
                                    0,
                                    0,
                                    this . check_picture . width,
                                    this . check_picture . height,
                                    Math . floor ((x - 0 + xo) * this . square_width + this . square_width / 2 - this . check_picture . width / 2) + 10,
                                    Math . floor ((y - 0 + yo) * this . square_height) - 14,
                                    this . check_picture . width,
                                    this . check_picture . height
                                    );

                                break;
                                }
                            }
                        }
                    }
                
                catch (exception)

                    {
                    }
                }

            return;
            };

        this . get_square_coordinates = function (event, integer)

            {
            var c = {x: 0, y: 0};

            c . x = ((event . pageX - $ ("canvas") . offsetLeft) - this . border_thickness) / this . square_width;
            c . y = ((event . pageY - $ ("canvas") . offsetTop) - this . border_thickness) / this . square_height;
            
            if (integer)
            
                {
                c . x = Math . floor (c . x);
                c . y = Math . floor (c . y);
                }

            return (c);
            };

        this . load_pictures = function ()
        
            {            
            this . board_picture = this . load_picture ("./pictures/board.jpg");
            this . pieces_picture = this . load_picture ("./pictures/pieces.png");
            this . check_picture = this . load_picture ("./pictures/check.png");

            return;
            };
            
        this . load_picture = function (picture)
        
            {
            var image = new Image ();
            
            image . src = picture;
            image . is_loaded = NO;
            image . onload = function () {this . is_loaded = YES; return;};
            
            return (image);
            };
        };