SpriteBatch.cs - Effect.cs - "This does not appear to be a MonoGame MGFX file!"

Attempting to import a super simple 'Monogame Windows project' to 'PSM'.

Only gets as far as trying to create a new SpriteBatch then the exception
"This does not appear to be a MonoGame MGFX file!"is thrown.

Passes the
"Microsoft.Xna.Framework.PSSuite.Graphics.Resources.SpriteEffect.cgx"as shader.

Been struggling to find a workaround for this for many hours; it’s broken my brain.


Code:

AppMain.cs

using System;
using System.Collections.Generic;
using Sce.PlayStation.Core;
using Sce.PlayStation.Core.Environment;
using Sce.PlayStation.Core.Graphics;
using Sce.PlayStation.Core.Input;

namespace GameWin
{
	public class AppMain
	{
		private static GraphicsContext graphics;
		private static Game1 game1;
			
		public static void Main (string[] args)
		{
			//Initialize ();
   			game1 = new Game1();
			
			while (true) {
				game1.Run();
				//SystemEvents.CheckEvents ();
				//Update ();
				//Render ();
			}
		}

	//	public static void Initialize ()
	//	{
	//		// Set up the graphics system
	//		graphics = new GraphicsContext ();
	//	}
	//
	//	public static void Update ()
	//	{
	//		// Query gamepad for current state
	//		var gamePadData = GamePad.GetData (0);
	//	}
	//
	//	public static void Render ()
	//	{
	//		// Clear the screen
	//		graphics.SetClearColor (0.0f, 0.0f, 0.0f, 0.0f);
	//		graphics.Clear ();
	//
	//		// Present the screen
	//		graphics.SwapBuffers ();
	//	}
	}
}

Game1.cs

#region Using Statements
using System;
using System.Collections.Generic;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Storage;
using Microsoft.Xna.Framework.GamerServices;
#endregion

namespace GameWin
{
    /// <summary>
    /// This is the main type for your game
    /// </summary>
    public class Game1 : Game
    {
        GraphicsDeviceManager graphics;
        SpriteBatch spriteBatch;
        private Texture2D bombTexture;

        public Game1()
            : base()
        {
            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); //<<< BREAKS HERE :( 

            bombTexture = Content.Load<Texture2D>("bomb");

            // 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)
        {
            if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed || Keyboard.GetState().IsKeyDown(Keys.Escape))
                Exit();

            // 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);

            // TODO: Add your drawing code here
            spriteBatch.Begin();
            spriteBatch.Draw(bombTexture, new Vector2(19,19), Color.White);
            spriteBatch.End();

            base.Draw(gameTime);
        }
    }
}

Not very elegant but it'll do for now

Inside
MonoGame.Framework.Graphics.Effect.Effect()
I re-rigged the contents of the constructor to bypass the MGFX Header Reader and then swapped out some of it’s guts with some older source.

Then inside
MonoGame.Framework.Graphics.SpriteBatch.Begin()
I added a little null reference check, and bam!, it worked :smile:

A little bit ‘amateur-hour’, but it works damn-it!

Still on the lookout for a better solution.
(More details posted in code below)


Effect.cs MonoGame.Framework.Graphics.Effect.Effect()

//---------------------------ORIGINAL BLOCK------------------------------
    //Read the header
    //MGFXHeader header = ReadHeader(effectCode);
    // First look for it in the cache.
    //
    //Effect cloneSource;
    //if (!EffectCache.TryGetValue(header.EffectKey, out cloneSource))
    //{
    //    using (var stream = new MemoryStream(effectCode, header.HeaderSize, effectCode.Length - header.HeaderSize, false))
    //	using (var reader = new BinaryReader(stream))
    //{
    //    // Create one.
    //    cloneSource = new Effect(graphicsDevice);
    //        cloneSource.ReadEffect(reader);
	//
    //    // Cache the effect for later in its original unmodified state.
    //        EffectCache.Add(header.EffectKey, cloneSource);
    //    }
    //}
//-------------------------ORIGINAL BLOCK (END)---------------------------
	
//----------------------NEW BLOCK FROM OLD SOURCE----------------------- 
    var effectKey = MonoGame.Utilities.Hash.ComputeHash(effectCode);
    Effect cloneSource;
    if (!EffectCache.TryGetValue(effectKey, out cloneSource))
    {
        // Create one.
        cloneSource = new Effect(graphicsDevice);
        using (var stream = new MemoryStream(effectCode))
        using (var reader = new BinaryReader(stream))
            cloneSource.ReadEffect(reader);

        // Cache the effect for later in its original unmodified state.
        EffectCache.Add(effectKey, cloneSource);
    }
//----------------------NEW BLOCK FROM OLD SOURCE (END)----------------------- 

SpriteBatch.cs MonoGame.Framework.Graphics.SpriteBatch.Begin()

// ----------------- NEW CHECK ----------------
if(effect == null)
	_effect = _spriteEffect;
else
// -----------------NEW CHECK (END)--------------
				_effect = effect;

If you haven’t already, it would be worth posting this up on github. PSM support doesn’t get used much, and it has a bunch of work arounds that occasionally get broken, without bug reports it will stay that way :frowning:

Hi!

I submitted this, alongside a patch to ease PSM song loading with XNA XNBs.