First of all, you have to target the 3.5 version of the framework but make your program loadable by the 4.0 framework by having an App.config
that looks like this (from How to force an application to use .NET 3.5 or above?):
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<startup>
<supportedRuntime version="v4.0"/>
<supportedRuntime version="v2.0.50727"/>
</startup>
</configuration>
As for how you activate the 4.0 feature, it depends on the feature you want to use. If it's a method on a built-in class, you can just look for it and use it if it exists. Here's an example in C# (it applies equally to VB):
var textOptions = Type.GetType("System.Windows.Media.TextOptions, " +
"PresentationFramework, Version=4.0.0.0, " +
"Culture=neutral, PublicKeyToken=31bf3856ad364e35");
if (textOptions != null)
{
var setMode = textOptions.GetMethod("SetTextFormattingMode");
if (setMode != null)
// don't bother to lookup TextFormattingMode.Display -- we know it's 1
setMode.Invoke(null, new object[] { this, 1 });
}
If you put this in your MainWindow
constructor, it will set TextFormattingMode
to Display
in apps running under the .NET 4.0 framework and do nothing under 3.5.
If you want to use a type that isn't available in 3.5, you have to create a new assembly for it. For example, create a class library project targetting 4.0 called "Factorial" with code like this (you'll have to add a reference to System.Numerics; same C# disclaimer):
using System.Numerics;
namespace Factorial
{
public class BigFactorial
{
public static object Factorial(int arg)
{
BigInteger accum = 1; // BigInteger is in 4.0 only
while (arg > 0)
accum *= arg--;
return accum;
}
}
}
Then create a project targetting 3.5 with code like this (same C# disclaimer):
using System;
using System.Reflection;
namespace runtime
{
class Program
{
static MethodInfo factorial;
static Program()
{ // look for Factorial.dll
try
{
factorial = Assembly.LoadFrom("Factorial.dll")
.GetType("Factorial.BigFactorial")
.GetMethod("Factorial");
}
catch
{ // ignore errors; we just won't get this feature
}
}
static object Factorial(int arg)
{
// if the feature is needed and available, use it
if (arg > 20 && factorial != null)
return factorial.Invoke(null, new object[] { arg });
// default to regular behavior
long accum = 1;
while (arg > 0)
accum = checked(accum * arg--);
return accum;
}
static void Main(string[] args)
{
try
{
for (int i = 0; i < 25; i++)
Console.WriteLine(i + ": " + Factorial(i));
}
catch (OverflowException)
{
if (Environment.Version.Major == 4)
Console.WriteLine("Factorial function couldn't be found");
else
Console.WriteLine("You're running " + Environment.Version);
}
}
}
}
If you copy the EXE and Factorial.DLL into the same directory and run it, you'll get all the first 25 factorials under 4.0 and only the factorials up to 20 along with an error message on 3.5 (or if it can't find the DLL).