Moshe
Moshe

Reputation: 58097

What is a pipeline assembly in XNA 4?

I'm trying to build the demo of TiledLib by Nick Gravelyn. I downloaded the ZIP from BitBucket and opened it in Visual Studio 2010. When I try to build, I get the following error:

Error XNA 4

Essentially, this error for each of three projects:

Error 1 Error loading pipeline assembly "C:\Users\Moshe\Downloads\TiledLib_GS4\TiledLib GS4\References\ContentPipeline\TiledPipelineExtensions.dll". Demo [Windows]

I am new to .NET, so I'm sure that I'm missing some basic concepts. Where might this dependency be referenced, and why won't the assembly load? The file exists at the specified path.

What is a pipeline assembly in XNA 4 and why can't Visual Studio load it?

Upvotes: 3

Views: 2404

Answers (1)

Lzh
Lzh

Reputation: 3635

Update: To your content project, add a reference to: TiledLib_GS4\TiledLib GS4\References\ContentPipeline\TiledPipelineExtensions.dll

Customizing the content pipeline is an advanced game development topic but it is not hard at all (of course depending on what and how you're processing content).

Content Pipeline is the series of steps that are carried out to include content into your game. A wave sound file for example is processed throught the Content Pipeline so that you can use it in your game as a SoundEffect object. The same applies to images that are included in your game as textures (either Texture2D or Texture3D).

When you load content, let's say a 2D Texture, in your XNA game using Content.Load you are invoking a content importer and processor that are already defined within the XNA framework, namely Microsoft.Xna.Framework.Content.Pipeline.Processors.TextureProcessor and Microsoft.Xna.Framework.Content.Pipeline.TextureImporter. There are also similar classes for FBX, Video, Audio content types.

A Pipeline assembly is just that: as assembly that allows you to import content of a certain type. Before we get into more detail note that all of your content is in a special Content Project and this project references assemblies that contain a bunch of out-of-the-box importers that derive from a base Content processor and importer class. These classes allow the Content project type to populate the list of importers that you can use for a certain type, and which you can change using the properties window. Check the screen shots below.

Content import options in properties window

Content import references in a content project

As I gave example of above, there are predefined XNA Content Importers. XNA also allows you to extend the Content Pipeline with your own importing implementations. To do so, XNA provides you with two classes to extend in a Content Pipeline Extension project. The first is a Content Importer and the other is a Content Processor.

A Content Importer is a class that derives from Microsoft.Xna.Framework.Content.Pipeline.ContentImporter and overrides a method called Import that is passed a string filename and an import context object and returns some type of object (generic type T) to use in your game: Texture2D, string or your own sophisticated type. This is called first when you load content.

A Content Processor is a class that provides a method for tranforming content or converting one type of content into another. In XNA it is a subclass of Microsoft.Xna.Framework.Content.Pipeline.ContentProcessor that overrides a method named Process that takes a TInput object and a import context object and returns TOutput. It's called second after the content is imported. This is useful if you import a single type of content in some single way, but you have lots of options as to how to further process it.

To see this in action just add a Content Pipeline Extension project and add to it a Content Processor and Content Importer classes. Do this by adding a new item, there are Item Templates for these two types of classes so you easily a basic no-implementation pipeline. Still, you need your Content Project to reference this Content Pipeline Extension project before you can use it. Once you add this reference, your custom content pipeline appears as a choice in the content processor/importer list that appears in the properties window of an asset. You importer/processor is chosen automatically for assets whose extension matches the one defined in the ContentImporterAttribute decorating your content importer class.

//[using statements omitted for brevity]
// TODO: replace this with the type you want to import.
using TImport = System.String;

namespace ContentPipelineExtension1
{
    /// <summary>
    /// This class will be instantiated by the XNA Framework Content Pipeline
    /// to import a file from disk into the specified type, TImport.
    /// 
    /// This should be part of a Content Pipeline Extension Library project.
    /// 
    /// TODO: change the ContentImporter attribute to specify the correct file
    /// extension, display name, and default processor for this importer.
    /// </summary>
    [ContentImporter(".abc", DisplayName = "ABC Importer", DefaultProcessor = "AbcProcessor")]
    public class ContentImporter1 : ContentImporter<TImport>
    {
        //Microsoft.Xna.Framework.Content.Pipeline.ContentImporter<T>
        public override TImport Import(string filename, ContentImporterContext context)
        {
            return "This the simplest importer ever that doesn't even take into account the file being imported.";
        }
    }
}

// TODO: replace these with the processor input and output types.
using TInput = System.String;
using TOutput = System.String;

namespace ContentPipelineExtension1
{
    /// <summary>
    /// This class will be instantiated by the XNA Framework Content Pipeline
    /// to apply custom processing to content data, converting an object of
    /// type TInput to TOutput. The input and output types may be the same if
    /// the processor wishes to alter data without changing its type.
    ///
    /// This should be part of a Content Pipeline Extension Library project.
    ///
    /// TODO: change the ContentProcessor attribute to specify the correct
    /// display name for this processor.
    /// </summary>
    [ContentProcessor(DisplayName = "ContentPipelineExtension1.ContentProcessor1")]
    public class ContentProcessor1 : Microsoft.Xna.Framework.Content.Pipeline.ContentProcessor<TInput, TOutput>
    {
        public override TOutput Process(TInput input, ContentProcessorContext context)
        {
            return input + "processed!!!!";
        }
    }
}

I mention again that your content importer extension must be referenced by your content project. Check the snap shot of my Solution Explorer below.

Content project references content pipeline extension

Also, the content importer is now an option to choose to process your assets. An asset's importer and processor is chosen automatically according to its extension.

Content import options extended in properties window.

This is a great tool if you want other people to collaborate non-programmatically with you in your game. For example you want level designers to create XML files or text files that describe your levels. Now you let them do that and then create content importers that import those files and put them into game objects that you use in your game as if you created them programmatically in the first place.

Now where from does the error you see come from? There is content in your Content Project whose Content Importer and Content Processor properties are set to those that exist in some assembly that is not referenced, but to which the settings of some assets point to as a content importer. The content pipeline extension exists as a DLL in the ZIP you downloaded, see the first statement of the post for the path.

Wow, turns to be quite a post! Have to use it in my blog! :D

Upvotes: 6

Related Questions