Upon Reflection – Implementing Some Cool .Net Capabilities – Pt 1.

For a little while now I’ve been making references to (and no pun intended for once) Reflection in .Net and how this has been an incredible boon to me in the development of MixAction.  I promised I’d elaborate, so here goes…  ;-)

reflection1

To begin with we need to quickly go over a little bit of history, to put things in perspective.

With the advent of Windows, trickier but not impossible, if you wrote your own interfaces to achieve it, but not as common under DOS, one could take advantage of the built in support of the platform for Dynamic Link Libraries or “DLL’s”.  I doubt if any developers reading need an explanation on how DLL’s work in general, how one can use them and why – so I won’t enlarge on that here.

The thing with the DLL was that it was, in effect, a separate program, loaded dynamically as needed and requiring the main application, without an incredible amount of tricky code, to know something about it.  Whether this be via function calls, the message API or call backs.

Management of a standard Win32 DLL can be a lot of work, the more functionality it contains the more work one usually has to do, often to the point of wishing you’d just included the code in the main application executable.  ;-)

Delphi 3 hit the market it came with these new fangled things called “Packages”.  Packages had an enormous amount of potential.  While ostensibly they were DLL’s they were, as far as Delphi and Delphi code was concerned, fairly smart ones.

Making a complex DLL a “plug-in” in your application that “snaps in” is a lot of work.  In theory packages should have solved this.  Alas they came close, but still required some pretty convoluted tricks, hence an array of Delphi products to facilitate plug-in functionality for developers.  I tried most of them and found them unreliable and cumbersome for my purposes over many years.

Note that by plug-ins I’m referring to snap in DLL files that add functionality to a program beyond that or enhancing that which it already contains.

The “lot of work” part comes in when you need to access objects, methods etc inside the DLL.  If they are not directly exposed, via the exports of the DLL, you can’t easily get at them.  Sure you can pass objects in from the main application, then operate on the object and indeed pass stuff out in addition.  But your main application never knows what it’s really accessing.  Of course this can be as much of an advantage in certain circumstances as it is a disadvantage.

In short it’s a ton of work, a ton of management and it gets to be a bit dreary after a while, IMHO.

With Packages under Delphi you got access to the objects contained in the package, providing you coded it to allow that access.  But you had no access, as one might reasonably assume to variables, private methods and other stuff that can be an incredible time boost if but only you could.

Enter Reflection in .Net.  Not only can you access objects directly, as well as the usual suspects like functions and methods but you can access variables, private methods and pretty much most everything else within reason.

In fact a Reflected DLL written under .Net and called from your .Net program can treat these little critters as if they were part of the main program.

Now, for MixAction, this is cool!

Sending Messages And Throwing Around Objects

If you were reading back in July/August on this blog you may remember two posts that discussed  sending Windows messages and using Objects within MixAction.  The Windows messages were application and in some instances system level.  The objects mentioned referred to DLL’s in a sense, but also the manner in which MixAction treats audio in the user interface.  The original June application was a list of files, by August it had morphed into a list of objects that in turn had the ability to each hold a list of files, upon which a variety of audio operations could be performed.

When I switched to .Net from Delphi I was faced with finding a solution in the .Net world to duplicate this ability.  What I found was the capacity contained within Reflection.  This is where one of the biggest development boosts came in.  Reflection allowed me to quickly and relatively easily implement this object orientated audio interface stuff without bothering about messages directly.  That’s because a Reflected DLL works as if it’s inside the main program.  Messages are pretty cool, but they take a lot of management and can make code complex to read and maintain.  Access to variables and private methods inside the Reflected assembly means the need for having to write interfaces to objects, variables, functions etc via exports is gone.  MixAction can talk to it’s audio engine as if it’s part of the main program, when it isn’t.

What this means is that the engine is separate entirely from the UI.  I can make changes to the engine and not break the UI. I can add to the engine, fix issues etc and only replace the engine on the user’s machine, like a good little plug-in should be capable of doing.

I can also add new “engines”.  This is the critical part as far as MixAction is concerned.  MixAction is more than one audio engine.  Each engine is capable of a specific set of tasks.  The idea is similar to implementing a button object, a label object or a panel object in a visual designer – kind of like your IDE.

As you know these objects usually descend from a common ancestor object, they share basic fundamentals’ like “name”, “text” whether or not they are “windowed” controls etc.  So it goes for audio objects.  Each audio object, stored in a DLL of it’s own, has certain base properties and methods that they share.  This makes things easier for the GUI or primary UI application of MixAction to interact with any one of them equally.  However each is capable of different things to other.  The idea being to give the user simple access for a specific task rather than build a “suits all, fits none” approach that would be more the conventional method you see in most audio software programs that are in anyway similar to MixAction.

It also means I can add new engines and the main application need never know anything more other than knowing how to check and load anything new should it find it or if it’s been installed.

I’ll expand more on this in the next post.

Scott Kane

Quote of the day:
The trouble with our times is that the future is not what it used to be. – Paul Valery

Tags: , , , , , ,

Post Author

This post was written by Scott Kane who has written 189 posts on The Recursive ISV.

No comments yet.

Leave a Reply