services   articles   contacts  
 
base .Net Hidden Gems up
.Net 1.X Tips

    1. Get the executing method name in code
    2. Why my stack trace is not as expected in release code?
    3. Avoid method inlining
    4. Read a private property or field from an external class
    5. Start the debugger in code
    6. Browse the GAC as a normal folder
    7. Mix mode application (Console and Windows)
    8. Get the .Net runtime version


.Net 2.0 Gems

    1. Form Shown event
    2. NetworkChange events
    3. Application.Restart
    4. Application.OpenForms
    5. Application.IsKeyLocked
    6. Icon.ExtractAssociatedIcon
    7. TextBox.UseSystemPasswordChar
    8. DNS
    9. ImageList.SetKeyName
    10. VisualStyleInformation.IsSupportedByOS /Application.RenderWithVisualStyles
    11. SystemEvents.SessionSwitch
    12. TabControl events
    13. Compare string without case sensitive
    14. DebuggerNonUserCodeAttribute

.Net 1.X Tips
1. Get the executing method name in code

    StackTrace trace = new StackTrace();
    string methodName = trace.GetFrame(0).GetMethod().Name;
    MessageBox.Show("Running in : " + methodName);

2. Why my stack trace is not as expected in release code

.Net Runtime optimize code in Release mode. That's mean that the call stack could change because of the inlining optimization. This reduces overhead associated with the function call, which is especially important for small and frequently called functions, and it helps call-site-specific compiler optimizations, especially constant propagation.

3. Avoid method inlining


Sometime you really need to have a specific call stack and you want to remove inlining for a specific method. Just use the MethodImplAttribute with MethodImplOptions.NoInlining to remove the inlining candidate.

    [MethodImpl(MethodImplOptions.NoInlining)]
    public static string GetCurrentMethodName() {
      StackTrace trace = new StackTrace();

      // 0 -> GetCurrentMethodName
      // 1 -> Calling Method
      return trace.GetFrame(1).GetMethod().Name;
    }


4. Read a private property or field from an external class

    public static object ReadFieldValue(Object aObject, String aFieldName) {
      if (aObject == null) {
        throw new Exception("Object is null");
      }

      if (String.IsNullOrEmpty(aFieldName)) {
        throw new Exception("FieldName is empty or null");
      }

      Type _Type = aObject.GetType();
      FieldInfo _FieldInfo = _Type.GetField(aFieldName,
        BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);

      if (_FieldInfo == null) {
        throw new Exception(String.Format(
         "Field '{0}' does not exist in type '{1}'",
         aFieldName, _Type.Name));
      }

      return _FieldInfo.GetValue(aObject);
    }
    public static object GetPropertyValue(Object aObject, String aPropertyName) {
      if (aObject == null) {
        throw new Exception("Object is null");
      }

      if (String.IsNullOrEmpty(aPropertyName)) {
        throw new Exception("PropertyName is empty or null");
      }

      Type _Type = aObject.GetType();
      PropertyInfo _PropertyInfo = _Type.GetProperty(aPropertyName,
         BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);

      if (_PropertyInfo == null) {
        throw new Exception(String.Format(
         "Property '{0}' does not exist in the type '{1}'",
         aPropertyName, aObject.GetType().Name));
      }

      return _PropertyInfo.GetValue(aObject, null);
    }

5. Start the debugger in code

By using the command System.Diagnostics.Debugger.Break();, the .Net runtime will ask witch debugger to choose. It's will be possible to attach a debugger to current process. Use this command to attach a debugger when the application is not started in debug mode or to debug only when a specific condition is found.

6. Browse the GAC as a normal folder


To browse the GAC as a normal folder, just unregister the dll named shfusion.dll with the command:

regsvr32 /u "C:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\ShFusion.dll".

You will be able to browse the folder "C:\WINDOWS\assembly" as a normal folder. Don't forget the register it when your done with the same command but without the /u :

regsvr32 "C:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\ShFusion.dll"

7. Mix mode application (Console and Windows)


When developing tools, there many situation where you want your application to start in console mode and in Windows mode. There is no perfect solutions. VS.NET uses the mix mode but with two executable, one named devenv.com, used in command prompt and an other named devenv.exe.

If you create a Windows application. Console.WriteLine will not appear in the command prompt, but if you create a console application, you will be able ton open a Windows Form but a blank command prompt screen will appear. The only solution that I found is to hide this Windows.

    private const Int32 SW_HIDE = 0;

    [DllImport("user32.dll")]
    private static extern Boolean ShowWindow(IntPtr hWnd, Int32 nCmdShow);

    [DllImport("Kernel32.dll")]
    private static extern IntPtr GetConsoleWindow();

    ...

    if (not inConsoleMode) {
      IntPtr hwnd = GetConsoleWindow();
      ShowWindow(hwnd, SW_HIDE);
      Application.Run(new Form1());
    } else {
      Console.WriteLine("Welcome");
    }
8. Get the .Net runtime version

It's possible to retreive the current .Net runtime version with this function.

    private static string InitializeRuntimeVersion() {
      string _Location = Path.GetDirectoryName(typeof(object).Assembly.Location);
      return Path.GetFileName(_Location);
    }

.Net 2.0 Gems
1. Form Shown event

This is new event called the first time a form is activated. With previous version, the only workaround was to set flag on the first activation in the Activated event.
2. NetworkChange events

Use NetworkChange.NetworkAvailabilityChanged to detect when the network went down.
3. Application.Restart

Use Application.Restart when you need to close and reexecute your application. This method was added for Click Once but it's available to you. Take note that Restart will launched your application with the command-line same options that was originally supplied.
4. Application.OpenForms

This property return all the open forms owned by this application.
5. Application.IsKeyLocked


The method indicate if the CAPS LOCK, NUM LOCK, or SCROLL LOCK key is in effect. It's not possible to use this method to check for other keys.

  • Keys.CapsLock
  • Keys.NumLock
  • Keys.ScrollLock

6. Icon.ExtractAssociatedIcon

This method return the Icon representation of an image used by Windows in Explorer. It's does not only return an image contained in the file, but also the associated image for a specific file.
    Icon ico1 = Icon.ExtractAssociatedIcon(@"c:\default.htm");
    Icon ico2 = Icon.ExtractAssociatedIcon(@"c:\windows\notepad.exe");
7. TextBox.UseSystemPasswordChar

This property indicate if text in the TextBox should appear as the default password character. In Windows XP, nice bullet will replace the text. The UseSystemPasswordChar property has precedence over the PasswordChar property.
8. DNS

Use the class Dns to get the IP address from a host name.
    string _IP = Dns.GetHostEntry("DEVOLUTIONS4").AddressList[0].ToString();
    MessageBox.Show(_IP);
9. ImageList Key Name


It's now possible to set a key name associated to an image in an ImageList. It's easier to access an image by name than by index.

    imageList1.Images.Add("home", new Bitmap(@"home.bmp"));

    //imageList1.Images.Add(new Bitmap(@"home.bmp"));
    //imageList1.Images.SetKeyName(0, "home");

    pictureBox1.Image = imageList1.Images["home"];

10. Visual styles / XP Themes


Use VisualStyleInformation.IsSupportedByOS to verify that the operating system supports visual styles (XP Themes).

Use VisualStyleInformation.IsEnabledByUser to verify that the user has enabled visual styles in the operating system.

Use Application.RenderWithVisualStyles to verify that the Visual Style are activated in the application. If Application.EnableVisualStyle is called in the application but Visual Style are disabled in the operating system, Application.RenderWithVisualStyles will return false.


11. SystemEvents.SessionSwitch

This event occurs when the currently logged-in user has changed.
12. TabControl events

In .Net 1.1, there was no easy way to cancel a tab index change, but .Net introduce a new event named Selecting and now possible to force the user to stay in the current tab.

Here is the events occurring when the current tab changes in a TabControl:

  • Deselecting

  • Deselected

  • Selecting

  • Selected


13. Compare string without case sensitive

.Net 2.0 offers a new method to compare a string with a parameter that specifies whether the comparison uses the current or invariant culture, honors or ignores case, and uses word or ordinal sort rules.

String.Compare


14. DebuggerNonUserCodeAttribute

This attribute identifies a type or member that is not part of the user code for an application. When the debugger encounters this attribute when stepping through user code, the user experience is to not see the designer provided code and to step to the next user-supplied code statement.
    [DebuggerNonUserCodeAttribute]
    public string GeneratedProperty {
      get{
        ...
      }
    }
Copyright ©2006, Devolutions inc.




Français