using System;
using System.Collections.Generic;
using System.Text;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Media;
using Sokoban3D;
using Sokoban3D.Scenes;

namespace Sokoban3D.Screens
{
    /// <summary>
    /// the base screen class that is used to draw 2D menus to handle transitions inside the game
    /// </summary>
    public abstract class Screen: DrawableGameComponent
    {
        // external variables
        private Sokoban3D game;
        protected SceneManager sceneManager;

        // screen related variables
        public Menu menu;
        private Boolean show;

        // graphic related variables
        protected Texture2D background;
        protected Rectangle imageRect;
        private SpriteFont normalFont, selectedFont;
        private SpriteBatch spriteBatch;

        // public set/get to hide/show the screen
        public Boolean visible
        {
            get { return show; }
            set { this.show = value; }
        }

        /// <summary>
        /// Initializes the Screen object with necessary variables. SceneManager
        /// is used to affect the current scene from the menus.
        /// </summary>
        /// <param name="game">Main game object.</param>
        /// <param name="items">Menu items to be displayed.</param>
        /// <param name="sceneManager">SceneManager object to access scenes.</param>
        /// <param name="background">Background picture for the menu.</param>
        public Screen(Sokoban3D game, String[] items, SceneManager sceneManager, Texture2D background)
            :base(game)
        {
            this.game = game;
            this.sceneManager = sceneManager;

            // set background image calculations
            this.background = background;
            this.imageRect = new Rectangle((game.Window.ClientBounds.Width - background.Width) / 2, (game.Window.ClientBounds.Height - background.Height) / 2, background.Width, background.Height);

            // create menu from the items supplied
            menu = new Menu(game, normalFont, selectedFont);
            menu.SetMenuItems(items);
            menu.Position = new Vector2((Game.Window.ClientBounds.Width -
                              menu.Width) / 2, Game.Window.ClientBounds.Height / 3);

            spriteBatch = (SpriteBatch)Game.Services.GetService(
                                            typeof(SpriteBatch));

            this.show = false;
        }

        /// <summary>
        /// Base update function for the screen objects.
        /// </summary>
        /// <param name="gameTime">Current gametime</param>
        public virtual void update(GameTime gameTime)
        {
            if (this.visible)
            {
                menu.Update(gameTime);
                base.Update(gameTime);
            }
        }

        /// <summary>
        /// Base drawinf function for the screen objects.
        /// </summary>
        /// <param name="gameTime"></param>
        public virtual void draw(GameTime gameTime)
        {
            if (this.visible)
            {
                this.spriteBatch.Draw(background, imageRect, Color.White);
                menu.Draw(gameTime);
            }
            base.Draw(gameTime);
        }
    }
}
