我不能让XNA允许我在MAIN类之外使用texture2D对象

本文关键字:对象 texture2D MAIN 不能 XNA 允许我 | 更新日期: 2023-09-27 18:07:54

using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Content;
namespace TileEngine
{   
    class Renderer
    {
        GraphicsDevice mydevice;
        void doit()
        {
            int width = 400;
            int height = 400;
            Texture2D TEX = new Texture2D(mydevice, 400, 400);
            RenderTarget2D Mine = new RenderTarget2D(mydevice, width, height);
            GraphicsDevice.SetRenderTarget(Mine);
        }
    }
}

我得到的问题如下:

错误2当前上下文中不存在名称"Mine"C:'Users'Programming'Desktop' engine'TileEngine' Game1.cs 149 30 TileEngine

错误1非静态字段、方法或属性需要对象引用'Microsoft.Xna.Framework.Graphics.GraphicsDevice.SetRenderTarget(Microsoft.Xna.Framework.Graphics.RenderTarget2D)' C:'Users'Programming'Desktop' engine'TileEngine' Renderer.cs 18 13 TileEngine

我理解面向对象编程的方式。这在技术上应该是可行的。也许我根本不懂XNA。我还在学习,是的,就是这样。

我想有一个类外呈现主类的原因是,因为我将有几个功能来做繁重的工作为我和剪辑将改变取决于什么参考框架,我得到。我想抛出Texture2D对象的新实例基于这些设置的大小等,每次我做一个渲染(每帧)或可能每次的东西改变。也将有缩放,和扭曲的2d图像,以及缩放和照明效果。这是我想通过一个单独的类来处理的所有东西。

如果你不能给我一个解决方案,我做错了什么,以及如何修复它,请教我或告诉我正确的方法。

我现在已经修复了这个问题。嗯. .

似乎我必须包括所有从Microsoft.xna.Framework即使我在名称空间瓷砖引擎无论如何…难道它不应该继承这一切吗?也因为某些原因…起初,它不喜欢我在底部的那几行里使用"我的设备"然后. .错误又开始消失了吗?也许改变Game1.cs内的错误,顺便说一句,这是我删除的东西的参考,固定渲染器内部的错误?但这没有任何意义……如果Game1.cs

中有一个完全不同的对象引用错误,渲染器不应该说mydevice在当前上下文中不存在。

也许我不明白口译员是如何工作的,但在我看来,这绝对不应该发生。

这里是修复的代码,任何人有类似的问题(需要清理)

因为我还没有分离功能。LOL .

using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Media;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Content;
namespace TileEngine
{   
    class Renderer
    {
        GraphicsDevice mydevice;
        SpriteBatch spriteBatch;

        void doit()
        {
            int width = 400;
            int height = 400;
            Texture2D TEX = new Texture2D(mydevice, 400, 400);
            RenderTarget2D Mine = new RenderTarget2D(mydevice, width, height);
            mydevice.SetRenderTarget(Mine);
            mydevice.SetRenderTarget(null);
            Rectangle drawrect = new Rectangle(0, 0, 400, 400);
            spriteBatch.Begin();
            spriteBatch.Draw(Mine, drawrect, Color.White);
            spriteBatch.End();
        }

    }
}

无论如何,也许我的编译器或ide只是愚蠢的。它确实有一些重新编译故障与我的高清,我认为它的windows权限。Mehh . .谢谢每一个读到这篇文章的人。

================= 新的问题相同的代码来源从这里开始 ======================================好吧,现在我又有了同样的问题。Microsoft xna试图在函数生命周期开始时实例化这些对象。我似乎无法创建这个类的实例,它将设备对象传递回主类。我想说的是,这个解决方案行不通嘿,给我一个目标渲染对象。哦,给你。抓住谢谢,伙计。在第二个函数中使用渲染

这是它们最后一次工作时的两个函数…last worked huge statement.

唯一的问题是Game.Run()函数崩溃或我的主要类的绘图代码崩溃,由于图形设备是空的问题??

using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Media;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Content;
namespace TileEngine
{
    class Renderer
    {
        GraphicsDevice mydevice;
        public SpriteBatch spriteBatch;

        public RenderTarget2D new_texture(int width, int height)
        {
            RenderTarget2D Mine = new RenderTarget2D(mydevice, width, height);
            Texture2D TEX = new Texture2D(mydevice, width, height);   //create the texture to render to
            mydevice.SetRenderTarget(Mine); //set the render device to the reference provided
            //maybe base.draw can be used with spritebatch. Idk. We'll see if the order of operation
            //works out. Wish I could call base.draw here.
            return Mine;    //I'm hoping that this returns the same instance and not a copy.
        }
        public void draw_texture(int width, int height, RenderTarget2D Mine)
        {
            mydevice.SetRenderTarget(null); //Set the renderer to render to the backbuffer again
            Rectangle drawrect = new Rectangle(0, 0, width, height); //Set the rendering size to what we want
            spriteBatch.Begin();                        //This uses spritebatch to draw the texture directly to the screen  
            spriteBatch.Draw(Mine, drawrect, Color.White); //This uses the color white
            spriteBatch.End();      //ends the spritebatch
            //Call base.draw after this since it doesn't seem to recognize inside the function
            //maybe base.draw can be used with spritebatch. Idk. We'll see if the order of operation
            //works out. Wish I could call base.draw here.
        }

    }
}

这是它工作时的代码。下面是类处理下面代码时的代码:

using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.GamerServices;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Media;
namespace TileEngine
{
    /// <summary>
    /// This is the main type for your game
    /// </summary>
    public class Game1 : Microsoft.Xna.Framework.Game
    {
        public GraphicsDeviceManager graphics;
        SpriteBatch spriteBatch;
        Renderer tileclipping = new Renderer();
       
        
        
        
      
       
        TileMap myMap = new TileMap();
        int squaresAcross = 12;
        int squaresDown = 12;
        public Game1()
        {
             graphics = new GraphicsDeviceManager(this);
            Content.RootDirectory = "Content";
            
        }
        /// <summary>
        /// Allows the game to perform any initialization it needs to before starting to run.
        /// This is where it can query for any required services and load any non-graphic
        /// related content.  Calling base.Initialize will enumerate through any components
        /// and initialize them as well.
        /// </summary>
        protected override void Initialize()
        {
            // TODO: Add your initialization logic here
            base.Initialize();
        }
        /// <summary>
        /// LoadContent will be called once per game and is the place to load
        /// all of your content.
        /// </summary>
        protected override void LoadContent()
        {
            // Create a new SpriteBatch, which can be used to draw textures.
            spriteBatch = new SpriteBatch(GraphicsDevice);
            Tile.TileSetTexture = Content.Load<Texture2D>(@"Textures'TileSets'part1_tileset");
            // TODO: use this.Content to load your game content here
        }
        /// <summary>
        /// UnloadContent will be called once per game and is the place to unload
        /// all content.
        /// </summary>
        protected override void UnloadContent()
        {
            // TODO: Unload any non ContentManager content here
        }
        /// <summary>
        /// Allows the game to run logic such as updating the world,
        /// checking for collisions, gathering input, and playing audio.
        /// </summary>
        /// <param name="gameTime">Provides a snapshot of timing values.</param>
        protected override void Update(GameTime gameTime)
        {
            // Allows the game to exit
            if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed)
                this.Exit();
            KeyboardState ks = Keyboard.GetState();
            if (ks.IsKeyDown(Keys.Left))
            {
                Camera.Location.X = MathHelper.Clamp(Camera.Location.X - 8, 0, (myMap.MapWidth - squaresAcross) * 32);
            }
            if (ks.IsKeyDown(Keys.Right))
            {
                Camera.Location.X = MathHelper.Clamp(Camera.Location.X + 8, 0, (myMap.MapWidth - squaresAcross) * 32);
            }
            if (ks.IsKeyDown(Keys.Up))
            {
                Camera.Location.Y = MathHelper.Clamp(Camera.Location.Y - 8, 0, (myMap.MapHeight - squaresDown) * 32);
            }
            if (ks.IsKeyDown(Keys.Down))
            {
                Camera.Location.Y = MathHelper.Clamp(Camera.Location.Y + 8, 0, (myMap.MapHeight - squaresDown) * 32);
            }
            // TODO: Add your update logic here
            base.Update(gameTime);
        }
        /// <summary>
        /// This is called when the game should draw itself.
        /// </summary>
        /// <param name="gameTime">Provides a snapshot of timing values.</param>
        protected override void Draw(GameTime gameTime)
        {
            GraphicsDevice.Clear(Color.CornflowerBlue);
            //use the instance of renderer called tileclipping to generate a new texture of a specified size for tiles
            //this surface is 200 pixels by 200 pixels for the reason that it's the same as the clipping i'll choose
            

            Texture2D mytexture = new Texture2D(GraphicsDevice, 200, 200);
            RenderTarget2D Mine = new RenderTarget2D(graphics.GraphicsDevice, 200, 200);
            Mine = tileclipping.new_texture(200, 200);
            spriteBatch.Begin();
            Vector2 firstSquare = new Vector2(Camera.Location.X / 32, Camera.Location.Y / 32);
            int firstX = (int)firstSquare.X;
            int firstY = (int)firstSquare.Y;
            Vector2 squareOffset = new Vector2(Camera.Location.X % 32, Camera.Location.Y % 32);            
            int offsetX = (int)squareOffset.X;
            int offsetY = (int)squareOffset.Y;
            for (int y = 0; y < squaresDown; y++)
            {
                for (int x = 0; x < squaresAcross; x++)
                {
                    spriteBatch.Draw(
                        Tile.TileSetTexture,
                        new Rectangle((x * 32) - offsetX, (y * 32) - offsetY, 32, 32),
                        Tile.GetSourceRectangle(myMap.Rows[y + firstY].Columns[x + firstX].TileID),
                        Color.White);
                }
            }
            spriteBatch.End();
            // TODO: Add your drawing code here
            //There are two instances of mine
                //A new one is made each time tileclipping.new_texture is called
                    //This function can re use the copy created by new texture
                        //hopefully this saves on memory
                        tileclipping.draw_texture(200, 200, Mine);
           
                
           
            
            base.Draw(gameTime);
        }
        public CubeMapFace Tex2d { get; set; }
    }
}

请注意:我没有包括那些其他类,因为它们的功能没有引起任何问题。如果这个问题太令人困惑,我可以通过pastebin提供导致问题的来源链接。但基本上这个东西说的是

这是我得到的这个问题的两个错误:

警告2字段'TileEngine. renderer .device'从未分配给,并且始终具有其默认值null C:'Users'Programming'Desktop' engine'TileEngine' Renderer.cs 11 24 TileEngine

警告1字段'TileEngine.Renderer. '。spriteBatch'永远不会分配给,并且始终具有其默认值null C:'Users'Programming'Desktop' engine'TileEngine' Renderer.cs 10 28 TileEngine

,崩溃消息是:在创建新资源时,GraphicsDevice不能为空。参数名称:graphicsDevice

我将把我的工作留在这个状态,因为它是最后一个正确编译的状态。现在在等待帮助,谢谢。: 3

我不能让XNA允许我在MAIN类之外使用texture2D对象

您已经创建了texture2d的实例,但没有给它任何数据。如果您想从中绘制,则必须在其中设置数据,或者从硬盘驱动器上的文件加载数据,或者通过内容管道将其拉出(在这种情况下,必须在运行程序之前使用内容管道对其进行编译)。最后一个选项是推荐的方法(对于XNA和Monogame)。

除此之外,你是在正确的轨道上。呈现的典型设计是将其卸载给负责该对象其余部分的类。我建议您将SpriteBatch传递给绘图方法,而不是使其成为类的成员。这样在加载内容时更容易。

在你的渲染器中没有设置图形设备和精灵批处理。您可以为渲染器类创建一个构造函数。像这样:

public Renderer(GraphicsDevice device, SpriteBatch spriteBatch)
{
   this.myDevice = device;
   this.spriteBatch = spriteBatch;
}
然后,在initialize()中:
tileClipping = new Renderer(graphics.GraphicsDevice, spriteBatch);