2/6/08

How to modify the VBContentManager to load other content types

Here's an example of how you can teach the VBContentManager to load other content types.

This sample code below shows you what to add (in bold) in order to load .fbx models. Please note that to actually display a 3D model, you'll have to write your own 3D rendering code - 3D is out of scope of my 2D engine blog. This just demonstrates how you can teach the VBContentManager to load other content types, the example just happens to use .fbx models.

Public Class VBContentManager
 Inherits ContentManager

 'Add a Hashtable(Of Model) called Modles, to
 'give your models a place to arrive in memory...

 Public Models As Hashtable(Of Model)

 'Add "intDupeModel" variable to this series...
 'This allows the VBContentManager to append a
 'unique number to any duplicate filenames it
 'may encounter when loading models from disk

 Private intDupeSound, intDupeTexture, intDupeFont, intDupeEffect, intDupeModel As Integer

 'Add "Models" to the ContentTypes enumeration,
 'and make it the next available value

 Public Enum ContentTypes
 Textures = 0
 Fonts = 1
 Sounds = 2
 Effects = 3
 Models = 4
 End Enum

 'Add "FbxImporter" to the ImporterName enumeration
 'Make sure it has the same value as Models in the
 'ContentTypes enumeration...

 Private Enum ImporterName
 TextureImporter = 0
 FontDescriptionImporter = 1
 XactImporter = 2
 EffectImporter = 3
 FbxImporter = 4
 End Enum

 'Add "ModelProcessor" to the ProcessorName enumeration
 'Make sure it has the same value as Models in the
 'ContentTypes enumeration.

 Private Enum ProcessorName
 TextureProcessor = 0
 FontDescriptionProcessor = 1
 XactProcessor = 2
 EffectProcessor = 3
 ModelProcessor = 4
 End Enum

 'In Public Sub New, add code to instantiate the Models hashtable
 'you added above

 Public Sub New(ByVal ServiceProvider As IServiceProvider, ByVal ContentFolder As String)

 '(existing code omitted)

 'Add code to instantiate the models hashtable

 Me.Models = New Hashtable(Of Model)

 End Sub

 'In LoadAllContent, add a Try block for Model importing in the
 'Catch block for Effects, and move the unknown file handler
 'to the catch block for attempted Model load

 Public Sub LoadAllContent()

 '(existing code omitted)

 Try

 'Effect?

 With file.FullName.ToLower
 Me.Effects.Add(file.Name.Replace(file.Extension, ""), Me.Load(Of Effect)(.Replace(Me.strExecutingFolder & "\""").Replace(file.Extension, "")))
 End With

 'Instead of giving up at this point, catch this as notAnEffect,
 'and add 1 more check to see if the file is a model...

 Catch notAnEffect As Exception

 Try

 'Model?

 With file.FullName.ToLower
 Me.Models.Add(file.Name.Replace(file.Extension, ""), Me.Load(Of Model)(.Replace(Me.strExecutingFolder & "\""").Replace(file.Extension, "")))
 End With


 'If that doesn't work, then I've run out of things
 'to try, so...

 Catch unknown As Exception
 strUnknownFiles &= vbCrLf & file.FullName
 End Try

 End Try


 '(existing code omitted)

 End Sub

 'In HarvestContent, add code to search for .fbx files.  Also,
 'I'm going to add code to look for .tga texture files as well
 'in case I need those too.

 Private Sub HarvestContent()

 '(existing code omitted)

 'Add code to look for .tga files...

 For Each texture As System.IO.FileInfo In objRoot.GetFiles("*.tga", IO.SearchOption.AllDirectories)
 If Me.objContent.Contains(New ContentFile(ContentTypes.Textures, texture, texture.Name.Replace(texture.Extension, ""))) Then
 Me.intDupeTexture += 1
 Me.objContent.Add(New ContentFile(ContentTypes.Textures, texture, texture.Name.Replace(texture.Extension, "") & Me.intDupeTexture.ToString))
 Else
 Me.objContent.Add(New ContentFile(ContentTypes.Textures, texture, texture.Name.Replace(texture.Extension, "")))
 End If
 Next


 'Add code to look for .fbx files... these are similar
 'code blocks, just change the ContentType enumeration and the
 'extension we want to look for from all the existing ones in
 'this sub

 For Each model As System.IO.FileInfo In objRoot.GetFiles("*.fbx", IO.SearchOption.AllDirectories)
 If Me.objContent.Contains(New ContentFile(ContentTypes.Models, model, model.Name.Replace(model.Extension, ""))) Then
 Me.intDupeModel += 1
 Me.objContent.Add(New ContentFile(ContentTypes.Models, model, model.Name.Replace(model.Extension, "") & Me.intDupeModel.ToString))
 Else
 Me.objContent.Add(New ContentFile(ContentTypes.Models, model, model.Name.Replace(model.Extension, "")))
 End If
 Next


 End Sub


The VBContentManager code should now be able to import .fbx files. Create a folder called Models in your Content folder in the solution explorer, and put .fbx files in there:



Here I copied all the models (and textures) from the SpaceWar example, and they now compile & load into the Models hashtable of the VBContentManager.

0 comments: