Fun Stuff · Games · The Legend of Zelda: Black Crown · XNA Framework

The Legend of Zelda: Black Crown featured!

My little fan game project The Legend of Zelda: Black Crown is the Featured Project over at Zelda Fan Game Central! \o/ You can discuss it on the Forum Thread or take a look at the Wiki Entry.

For any of you that have missed the game, here are some screenshots and the download link. It requires Windows, Microsoft .NET Framework 4.6.1 (https://www.microsoft.com/en-us/download/details.aspx?id=49981) and a GPU that supports Shader Model 2.0. Please poke me if you have any feedback or ideas on how to improve the game!

Download: http://paul.ennemoser.com/files/zelda/TLoZ%20-%20Black%20Crown.zip
Don’t forget to use the Zelda Updater after installing the game to get the latest patch.

BlackCrown_collage_1

BlackCrown_collage_2

Games · The Legend of Zelda: Black Crown · XNA Framework

Zelda video’n shots

TLoZ: BC is a free offline hack and slash RPG, best compared to Diablo.
In BC you hunt for the best items, steadily improving your stats and talents!

Here are some new screenshots and a simple gameplay video.

Game Download
http://paul.ennemoser.com/files/zelda/TLoZ%20-%20Black%20Crown.zip

Don’t forget to get latest patch by using the Zelda Updater! Requires  Microsoft .NET Framework 4.6.1

Programming · Source Code

C# <3 Ruby

IronRuby allows you to get some of the freedom and expressiveness of Ruby in the .NET biz. world. Recently I’ve been using it as a simple game scripting language.

Warning: This post is a beginner tutorial on how to get started with hosting IronRuby inside your C# application.
.
.
C# loves Ruby
.
Step 1
Download the IronRuby binaries from Codeplex: http://ironruby.codeplex.com/ Warning: As of writing this the IronRuby 1.1.3 installer won’t install the binaries.

Step 2
Add references to IronRuby.dll, Microsoft.Csharp.dll and Microsoft.Scripting.dll to your project.
.
Step 3
ScriptEngine and ScriptScope are the key classes of the Dynamic Language Runtime that allow us to run Ruby code: (Download Tutorial Source Code – Rename to Zip)

// Tutorial 1:

// Initiate the main object that drives IronRuby:
var engine = IronRuby.Ruby.CreateEngine();

// And here goes the magic:
engine.Execute( "puts 'Meow, from Ruby!'" );
// Tutorial 2:
var engine = IronRuby.Ruby.CreateEngine();

// ScriptScopes allow you to capture variables and methods
// within a specific non-global scope.
ScriptScope scope = engine.CreateScope();

// The ScriptScope API allows us to easily set variables
// from .NET:
scope.SetVariable( "score", 10 );

// You can also use Ruby to set variables:
engine.Execute( "max_score = 10", scope );

// Let us access the variables now. Note the usage of "%Q/ /"
// as a replacement of " " in our Ruby code.
engine.Execute( "puts %Q/Your score is #{score} of #{max_score}!/", scope );

.
Step 4 – Domain Specific Languages
We can ‘teach’ our scripts a set of specialized methods that make it easy to interact with the problem domain. With the help of Ruby’s expressiveness our scripts will look more like a custom language that is focused on the target domain. See Teta on github for a text adventure that is build around a Ruby DSL.

# Here's a silly example from my Zelda fangame:
on_time_changed do |time|
  if time == 'DayBegan' then
    if roll_1_in 100 then
      spawn_item 'Ruby1'

      after_seconds 2 do
         fairy_says "Oh, what's that? Lucky!"
      end
    end
  end
end
// Tutorial 3 - how to get started with a Ruby DSL from C#:
var engine = IronRuby.Ruby.CreateEngine();
var scope = engine.CreateScope();

string domain =
    @"
        class Universe
            attr_accessor :underlying_theory
            attr_accessor :groups

            def initialize()
                @groups = []
            end

            def to_s
                %Q/Universe based on #{underlying_theory} is filled with: #{groups}./
            end
        end

        class Group
            attr_accessor :name
            attr_accessor :galaxies

            def initialize()
                @galaxies = []
            end
        end

        class Galaxy
            attr_accessor :name
        end
    ";

// Now teach it about our domain. You could use normal C# classes too.
// But those might be at times be more awkward to access from within Ruby.
engine.Execute( domain, scope );

string dsl =
    @"
        # DSL:
        def universe(hash)
            u = @@current_u = Universe.new()
            u.underlying_theory = hash[:based_on]

            yield if block_given?
            u
        end

        def group(named)
            g = @@currrent_g = Group.new()
            g.name = named

            yield if block_given?
            @@current_u.groups << g
        end

        def galaxy(named)
            g = Galaxy.new()
            g.name = named

            @@currrent_g.galaxies << g
        end
    ";

// 'Enable' our tiny DSL:
engine.Execute( dsl, scope );

// And lets use it to create some universes:
string ruby =
    @"
        mt = universe based_on: 'M-Theory' do
            group 'Local group' do
                galaxy 'Milky Way'
                galaxy 'Andromeda Galaxy'
                galaxy 'Triangulum Galaxy'
            end

            group 'Virgo Cluster'
            group 'Centaurus Supercluster'
        end

        hlt = universe based_on: 'HL-Theory' do
            group 'Black Mesa' do
                galaxy 'On a Rail '
                galaxy 'Questionable Ethics'
                galaxy 'Lambda Core'
                galaxy 'Nihilanth'
            end
        end

        et = universe based_on: 'Empty-World Theory'
        [mt, hlt, et]
    ";

// ScriptEngine.Execute returns our list of universes as the result of the ruby code:
dynamic universes = engine.Execute( ruby, scope );

foreach( dynamic universe in universes )
{
    Console.WriteLine();
    Console.WriteLine( universe );
}

.
Step 5 – Miscellaneous Notes
I encourage you to use a Test/Specification Driven Development style when working with your Ruby scripts (It is imho a must with dynamic languages). Personally I can’t yet rate how easy/hard it is to get something like RSpec running with IronRuby and loose scripts.

The outside image of IronRuby looks a bit shady at the moment. The official website doesn’t link to the newest version, and all in all the project is fragmentted over too many different domains. It doesn’t help that the installer and Visual Studio integration (v 1.1.3) is somewhat bugged. From the inside we’ve got a very solid product that can get you some of the Ruby love inside the .NET world. Thanks to the open source community on continuing work on IronRuby and IronPython! <3

.
::Edit Step 6 – Tip: Compile from Source ::Edit (30.06.2012)
To get the best experience, until the IronRuby team decides to release a new version, you should compile IronRuby from source for your target framework. This has shown to give me a great performance increase. Great work!

.
Step 7 – Additional Resources
IronRuby Tutorial Source Code – Rename to Zip

IronRuby on Codeplex
IronRuby Mailing List
IronRuby Source Code
IronRuby Issue Tracker

Design Patterns & Best Practices · Programming

Code: Abstract Unit of Work

Today I’ve been tinkering about how to best implement the
Unit of Work/Repository patterns at the client (service)-side.

Warning! This blog post contains experimental source code!

What I want:
1. Simple to use. Usage is easy to explain.
2. Doesn’t leak the underlying data access framework.
3. Supports transactions.
4. Supports multiple parallel units of work when required.
5. Manages the session/context scope for me.
Not quite sure whether I need nested UoWs.

Here is what I have come up so far. I’ll update this post once I figure out something new about all of this.


// Scoped unit of work:
// 1. Quite simple
// 2. Repositories use the currently active UoW
// 3. Doesn't support multiple UoWs to be active
// 4. Using block scopes the current session/object context
// 5. Repositories are injected using the constructor
using( UnitOfWork.Start() )
{
   var user = this.userRepository.GetUserByName( "Paul" );
   var skill = this.skillRepository.GetSkillByName( "Ruby" );
   user.Award( skill );
}

// Scoped UoW, that also starts a new transaction:
// When the UoW is disposed it will be rolled-back
// unless it has been committed.
using( var uow = UnitOfWork.Start( transaction: true ) )
{
   var user = this.userRepository.GetUserByName( "Paul" );
   var skill = this.skillRepository.GetSkillByName( "Ruby" );
   user.Award( skill );
   uow.Commit();
}

Update:
If the current Unit of Work is marked to be unique for each thread (ThreadStaticAttribute) it can safely handle multiple ‘requests’ at the same time. No need for any >special case< handling.

Thanks to @pragmatrix for pointing this out on Twitter. :)

Fun Stuff · Games · The Legend of Zelda: Black Crown

New Release of Zelda – Black Crown: Updater!

And another update to my Zelda fan-game. Besides many new items, a new boss and more – the greatest new addition is an Updater / Patcher which allows you to get the very latest version without re-downloading the full game. Enjoy!
Zelda Updater / Patcher
.
.
For the people that are interested how I’ve implemented the Updater / Patcher:
When I decide to release a new version I run custom “Release Packager Tool”.

This tool creates, amongst other things, a manifest file that stores the date and time every file of the game has been modified. This manifest, including, all other files is then uploaded to my webspace. Now when you start the Updater / Patcher it downloads that manifest file and checks what other files need be updated by downloading them too.

To make the patcher itself update-able I am using a stub executable that runs the actual patcher executable in a separate AppDomain. That AppDomain has Shadow Copying of Files enabled. ShadowCopyFiles = “true” has the effect that the assembly and its dependencies are copied into a temporary folder upon execution -> as such the original patcher files are not locked and can be replaced.

var domainSetup = new AppDomainSetup() {
    ShadowCopyFiles = &quot;true&quot;
};

var domain = AppDomain.CreateDomain(
    &quot;Update Domain&quot;,
    AppDomain.CurrentDomain.Evidence,
    domainSetup
);

domain.ExecuteAssembly( updaterAssembly );
Tool Programming

The PropertyGrid – a great friend.

One of the greatest things in .Net is the System.Windows.Forms.PropertyGrid WinForms control.

This great class uses Reflection to access the visible properties of any object.
You can download the full c# source-code of this post HERE.

Let’s take a look how the PropertyGrid control looks in action:
A .net PropertyGrid which has been bound to a Light object.
In this screenshot I’ve bound the PropertyGrid, a WinForms control, to a Light object:

propertyGrid.SelectedObject = light;

Swush! The PropertyGrid is very simple to get started with and a great tool every .net programmer should know. Next we shall take a look at a very simple class we’d like to allow the user to edit:

using System;

namespace Blog.PropertyGrid
{
    /// <summary>
    /// This is just some really simple object
    /// that contains some properties.
    /// </summary>
    public class DummyObject
    {
        /// <summary>
        /// Gets or sets the name of this <see cref="DummyObject"/>.
        /// </summary>
        public string Name { get; set; }

        /// <summary>
        /// Gets or sets the position on the x-axis
        /// of this <see cref="DummyObject"/>.
        /// </summary>
        public float X { get; set; }

        /// <summary>
        /// Gets or sets the position on the y-axis
        /// of this <see cref="DummyObject"/>.
        /// </summary>
        public float Y { get; set; }

        /// <summary>
        /// Gets or sets some object that is usually loaden from a file.
        /// </summary>
        public object ObjectThatIsLoadenFromAFile { get; set; }

        /// <summary>
        /// Gets or sets a value that should not be set by the user
        /// of the application but only by the programmer.
        /// </summary>
        public bool ThisIsADangerousInternalProperty { get; set; }
    }
}

The following lines create a DummyObject and assign it to the PropertyGrid:

    propertyGrid.SelectedObject = new DummyObject()
    {
        Name = "Bar Object",
        X = 150.0f,
        Y = 200.0f,
        ThisIsADangerousInternalProperty = true
    };

This should make the PropertyGrid look like this:
PropertyGrid bound to a DummyObject

The next Step

Our next goal is to learn how to customize the entries in the PropertyGrid.
.net provides some nice Attributes in the System.ComponentModel namespace:

The CategoryAttribute, the DisplayNameAttribute,  the DefaultValueAttribute, the BrowsableAttribute and more.

Let us apply these Attributes to our great Object:

using System;
using System.ComponentModel;

namespace Blog.PropertyGrid
{
    /// <summary>
    /// This is just some really simple object
    /// that contains some properties.
    /// </summary>
    public class CustomizedDummyObject
    {
        /// <summary>
        /// Gets or sets the name of this <see cref="CustomizedDummyObject"/>.
        /// </summary>
        [Category( "Identification" )]
        [Description( "The name of the CustomizedDummyObject." )]
        public string Name { get; set; }

        /// <summary>
        /// Gets or sets the position on the x-axis
        /// of this <see cref="CustomizedDummyObject"/>.
        /// </summary>
        [DefaultValue( 0.0f )]
        [Category( "Translation" )]
        [Description( "The position of the CustomizedDummyObject on the x-axis." )]
        public float X { get; set; }

        /// <summary>
        /// Gets or sets the position on the y-axis
        /// of this <see cref="CustomizedDummyObject"/>.
        /// </summary>
        [DefaultValue( 0.0f )]
        [Category( "Translation" )]
        [Description( "The position of the CustomizedDummyObject on the y-axis." )]
        public float Y { get; set; }

        /// <summary>
        /// Gets or sets some object.
        /// </summary>
        [DisplayName( "Object That Is Loaden From A File" )]
        [Category( "Misc" )]
        [Description( "The strange object that wants to be loaden from a file." )]
        public object ObjectThatIsLoadenFromAFile { get; set; }

        /// <summary>
        /// Gets or sets a value that should not be set by the user
        /// of the application but only by the programmer.
        /// </summary>
        [Browsable(false)]
        public bool ThisIsADangerousInternalProperty { get; set; }
    }
}


The Attributes explained

BrowsableAttribute

Using the BrowsableAttribute we tell the ‘ThisIsADangerousInternalProperty ‘ property to not be visible in the PropertyGrid.

DisplayNameAttribute

The name says it all, the DisplayNameAttribute sets how the property should be named within the PropertyGrid.

CategoryAttribute

Using the CategoryAttribute we can group our properties into categories.

DescriptionAttribute

Using the DescriptionAttribute we can give the user a hint what a property does.

DefaultValueAttribute

Using the DefaultValueAttribute we can tell the PropertyGrid what the default value of the property is. Non-default values are displayed using a bold font setting.

Let us bind the PropertyGrid to an instance of the CustomizedDummyObject class:
PropertyGrid bound to a CustomizedDummyObject


Much better, isn’t it? Be we’re not quite there yet. What about the mysterious “Object That Is Loaden From a File”?
To solve this issue I’d like to introduce you a concept I like to call ‘Object Property Wrappers‘.


Object Property Wrappers

When your objects get more and more complex, such as when you inherit from a base class, simply customizing your properties gets out of hand. Or what if you want to provide customization to a class you can’t or don’t want to change?

My solution to this problem is the IObjectPropertyWrapper interface:

using System;
using System.ComponentModel;

namespace Blog.PropertyGrid
{
    /// <summary>
    /// An <see cref="IObjectPropertyWrapper"/> is responsible
    /// for exposing the properties of an Object which the user is intended to edit.
    /// </summary>
    interface IObjectPropertyWrapper : ICloneable, INotifyPropertyChanged
    {
        /// <summary>
        /// Gets or sets the object this <see cref="IObjectPropertyWrapper"/> wraps around.
        /// </summary>
        [Browsable( false )]
        object WrappedObject { get; set; }

        /// <summary>
        /// Receives the <see cref="Type"/> this <see cref="IObjectPropertyWrapper"/> wraps around.
        /// </summary>
        [Browsable( false )]
        Type WrappedType { get; }
    }

}


Implementation

Before we bound our PropertyGrid directly to our DummyObjects.
From now on we are going to bind the PropertyGrid to wrapper classes that implement the IObjectPropertyWrapper interface.

The above interface is the interface which is used in your application’s public interface.
The following abstract class is a basic implementation of the interface. This reduces the amount of work needed if we wish to create new Object Property Wrappers.

using System;
using System.ComponentModel;

namespace Blog.PropertyGrid
{
    /// <summary>
    /// Defines a basic implementation of the <see cref="IObjectPropertyWrapper"/> interface.
    /// </summary>
    /// <typeparam name="TObject">
    /// The type of the object that is beeing wrapped by this IObjectPropertyWrapper.
    /// </typeparam>
    abstract class BaseObjectPropertyWrapper<TObject> : IObjectPropertyWrapper
    {
        #region [ Events ]

        /// <summary>
        /// Fired when any property of this IObjectPropertyWrapper has changed.
        /// </summary>
        /// <remarks>
        /// Properties that wish to support binding, such as in Windows Presentation Foundation,
        /// must notify the user that they have change.
        /// </remarks>
        public event System.ComponentModel.PropertyChangedEventHandler PropertyChanged;

        #endregion

        #region [Properties]

        /// <summary>
        /// Gets or sets the object this <see cref="IObjectPropertyWrapper"/> wraps around.
        /// </summary>
        /// <exception cref="ArgumentException">
        /// If the Type of the given Object is not supported by this IObjectPropertyWrapper.
        /// </exception>
        [Browsable( false )]
        public TObject WrappedObject
        {
            get { return _wrappedObject; }
            set
            {
                if( value != null )
                {
                    if( !this.WrappedType.IsAssignableFrom( value.GetType() ) )
                    {
                        throw new ArgumentException(
                            "The Type of the given Object is not supported by this IObjectPropertyWrapper.",
                            "value"
                        );
                    }
                }

                _wrappedObject = value;
                OnPropertyChanged( "WrappedObject" );
            }
        }

        /// <summary>
        /// Gets or sets the object this <see cref="IObjectPropertyWrapper"/> wraps around.
        /// </summary>
        [Browsable( false )]
        object IObjectPropertyWrapper.WrappedObject
        {
            get { return this.WrappedObject;           }
            set { this.WrappedObject = (TObject)value; }
        }

        /// <summary>
        /// Receives the <see cref="Type"/> this <see cref="IObjectPropertyWrapper"/> wraps around.
        /// </summary>
        [Browsable( false )]
        public Type WrappedType
        {
            get { return typeof( TObject ); }
        }

        #endregion

        #region [ Methods ]

        /// <summary>
        /// Returns a clone of this <see cref="IObjectPropertyWrapper"/>.
        /// </summary>
        /// <remarks>
        /// The wrapped object is not cloned, only the IObjectPropertyWrapper.
        /// </remarks>
        /// <returns>
        /// The cloned IObjectPropertyWrapper.
        /// </returns>
        public abstract object Clone();

        /// <summary>
        /// Fires the <see cref="PropertyChanged"/> event.
        /// </summary>
        /// <param name="propertyName">
        /// The name of the property whose value has changed.
        /// </param>
        protected void OnPropertyChanged( string propertyName )
        {
            if( PropertyChanged != null )
                PropertyChanged( this, new PropertyChangedEventArgs( propertyName ) );
        }

        #endregion

        #region [ Fields ]

        /// <summary>
        /// Stores the object this <see cref="IObjectPropertyWrapper"/> wraps around.
        /// </summary>
        private TObject _wrappedObject;

        #endregion
    }
}


Time to write a Wrapper

The following picture shows a PropertyGrid that is bound to a ‘DummyObjectPropertyWrapper’, an IObjectPropertyWrapper that exposes the properties of a DummyObject.
Remember that DummyObject has zero Attributes that describe its properties.
PropertyGrid bound to an IObjectPropertyWrapper for DummyObjects.

Here is the implementation:

using System;
using System.ComponentModel;

namespace Blog.PropertyGrid
{
    /// <summary>
    /// Defines the IObjectPropertyWrapper for the <see cref="DummyObject"/> type.
    /// </summary>
    class DummyObjectPropertyWrapper : BaseObjectPropertyWrapper<DummyObject>
    {
        /// <summary>
        /// Initializes a new instance of the <see cref="DummyObjectPropertyWrapper"/> class.
        /// </summary>
        public DummyObjectPropertyWrapper()
        {
        }

        /// <summary>
        /// Initializes a new instance of the <see cref="DummyObjectPropertyWrapper"/> class.
        /// </summary>
        /// <param name="obj">The object the new DummyObjectPropertyWrapper wraps around.</param>
        public DummyObjectPropertyWrapper( DummyObject obj )
        {
            this.WrappedObject = obj;
        }

        /// <summary>
        /// Gets or sets the name of this <see cref="CustomizedDummyObject"/>.
        /// </summary>
        [Category( "Identification" )]
        [Description( "The name of the CustomizedDummyObject." )]
        public string Name
        {
            get { return this.WrappedObject.Name; }
            set { this.WrappedObject.Name = value; }
        }

        /// <summary>
        /// Gets or sets the position on the x-axis
        /// of this <see cref="CustomizedDummyObject"/>.
        /// </summary>
        [DefaultValue( 0.0f )]
        [Category( "Translation" )]
        [Description( "The position of the CustomizedDummyObject on the x-axis." )]
        public float X
        {
            get { return this.WrappedObject.X; }
            set { this.WrappedObject.X = value; }
        }

        /// <summary>
        /// Gets or sets the position on the y-axis
        /// of this <see cref="CustomizedDummyObject"/>.
        /// </summary>
        [DefaultValue( 0.0f )]
        [Category( "Translation" )]
        [Description( "The position of the CustomizedDummyObject on the y-axis." )]
        public float Y
        {
            get { return this.WrappedObject.Y; }
            set { this.WrappedObject.Y = value; }
        }

        /// <summary>
        /// Gets or sets some object that is usually loaden from a file.
        /// </summary>
        [DisplayName( "Object That Is Loaden From A File" )]
        [Category( "Misc" )]
        [Description( "The strange object that wants to be loaden from a file." )]
        [Editor( typeof( System.Windows.Forms.Design.FileNameEditor ), typeof( System.Drawing.Design.UITypeEditor ) )]
        public object ObjectThatIsLoadenFromAFile
        {
            get
            {
                return this.WrappedObject.ObjectThatIsLoadenFromAFile;
            }
            set
            {
                string fileName = (string)value;

                // load object here...

                // set object..
                this.WrappedObject.ObjectThatIsLoadenFromAFile = fileName;
            }
        }

        /// <summary>
        /// Returns a clone of this <see cref="DummyObjectWrapper"/>.
        /// </summary>
        /// <returns>
        /// The cloned IObjectPropertyWrapper.
        /// </returns>
        public override object Clone()
        {
            // We can initialize the clone here!
            return new DummyObjectPropertyWrapper();
        }
    }
}


The EditorAttribute

The ObjectThatIsLoadenFromAFile property of our Property Wrapper has an additional attribute.
It’s the quite complex EditorAttribute. Using the EditorAttribute you can tell the PropertyGrid how it should ‘edit’ that specific property.

In this case the editor I use is of type System.Windows.Forms.Design.FileNameEditor, a class you can find in the System.Design.dll. When the user edits the property, by clicking on the ‘…’ button, the FileNameEditor opens an OpenFileDialog and returns a string back to you.

There are many useful Editors and you can even define your own or customize an existing.


A few last words

There is more to know about the PropertyGrid class, such as how TypeConverters work or how you can place complex objects within other objects using ExpandableObjectConverter.

Now I’d like to thank you for reading this far. Thanks! (:
You can download the full c# source-code of this post HERE.

The code also shows how you can localize your properties using custom Attributes and create IObjectPropertyWrappers using a ObjectPropertyWrapperFactory; both very useful tools.