Button and UAC shield

8 posts, 0 answers
  1. Tiago
    Tiago avatar
    3 posts
    Member since:
    Oct 2014

    Posted 11 Feb 2015 Link to this post

    Hi there,

    I need to show the UAC shield in a RadButton. How can I achieve it?

    We have an application which raise another process instance to a high privilege level under UAC and when the SO uses UAC (Windows Vista ou higher) I need to show the UAC shield in some buttons.

    You can find the demo application here: http://support.microsoft.com/kb/981778?wa=wsignin1.0.

    Please, tell me that it's doable otherwise I'll need to do the ugliest workaround of my life.

    Thanks,
    Tiago
  2. Tiago
    Tiago avatar
    3 posts
    Member since:
    Oct 2014

    Posted 11 Feb 2015 in reply to Tiago Link to this post

    Hi,

    One more comment... I believe just setting the FlatStyle property to System may solve my issue.

    btnTelerik.FlatStyle = FlatStyle.System;

    Thanks,

  3. UI for WinForms is Visual Studio 2017 Ready
  4. Dess
    Admin
    Dess avatar
    1605 posts

    Posted 12 Feb 2015 Link to this post

    Hello Tiago,

    Thank you for writing.

    The possible solution that I can suggest is to create a bitmap from the UAC shield and assign it to the RadButton.Image property. You can find a sample implementation on the following link: http://stackoverflow.com/questions/13758458/add-a-uac-shield-to-a-button-and-retain-its-background-image

    I am pasting the code snippet here as well in order the community to benefit from it:
    private void Form1_Load(object sender, EventArgs e)
    {
        Bitmap shield = GetUacShieldImage();
        this.radButton1.Image = shield;
        this.radButton1.Padding = new Padding(10, 0, 0, 0);
    }
     
    [DllImport("user32.dll")]
    public static extern int SendMessage(IntPtr hWnd, uint Msg, int wParam, int lParam);
     
    // Make the button display the UAC shield.
    public static void AddShieldToButton(Button btn)
    {
        const Int32 BCM_SETSHIELD = 0x160C;
     
        // Give the button the flat style and make it display the UAC shield.
        btn.FlatStyle = System.Windows.Forms.FlatStyle.System;
        SendMessage(btn.Handle, BCM_SETSHIELD, 0, 1);
    }
     
    // Return a bitmap containing the UAC shield.
    private static Bitmap shield_bm = null;
     
    public static Bitmap GetUacShieldImage()
    {
        if (shield_bm != null)
            return shield_bm;
     
        const int WID = 50;
        const int HGT = 50;
        const int MARGIN = 4;
     
        // Make the button. For some reason, it must
        // have text or the UAC shield won't appear.
        Button btn = new Button();
        btn.Text = " ";
        btn.Size = new Size(WID, HGT);
        AddShieldToButton(btn);
     
        // Draw the button onto a bitmap.
        Bitmap bm = new Bitmap(WID, HGT);
        btn.Refresh();
        btn.DrawToBitmap(bm, new Rectangle(0, 0, WID, HGT));
     
        // Find the part containing the shield.
        int min_x = WID, max_x = 0, min_y = HGT, max_y = 0;
     
        // Fill on the left.
        for (int y = MARGIN; y < HGT - MARGIN; y++)
        {
            // Get the leftmost pixel's color.
            Color target_color = bm.GetPixel(MARGIN, y);
     
            // Fill in with this color as long as we see the target.
            for (int x = MARGIN; x < WID - MARGIN; x++)
            {
                // See if this pixel is part of the shield.
                if (bm.GetPixel(x, y).Equals(target_color))
                {
                    // It's not part of the shield.
                    // Clear the pixel.
                    bm.SetPixel(x, y, Color.Transparent);
                }
                else
                {
                    // It's part of the shield.
                    if (min_y > y)
                        min_y = y;
                    if (min_x > x)
                        min_x = x;
                    if (max_y < y)
                        max_y = y;
                    if (max_x < x)
                        max_x = x;
                }
            }
        }
     
        // Clip out the shield part.
        int shield_wid = max_x - min_x + 1;
        int shield_hgt = max_y - min_y + 1;
        shield_bm = new Bitmap(shield_wid, shield_hgt);
        Graphics shield_gr = Graphics.FromImage(shield_bm);
        shield_gr.DrawImage(bm, 0, 0,
            new Rectangle(min_x, min_y, shield_wid, shield_hgt),
            GraphicsUnit.Pixel);
     
        // Return the shield.
        return shield_bm;
    }

    I hope this information helps. Should you have further questions, I would be glad to help.

    Regards,
    Dess
    Telerik
     

    Check out the Telerik Platform - the only platform that combines a rich set of UI tools with powerful cloud services to develop web, hybrid and native mobile apps.

     
  5. Tiago
    Tiago avatar
    3 posts
    Member since:
    Oct 2014

    Posted 12 Feb 2015 in reply to Dess Link to this post

    Hi Dess,

    Thank you for your prompt support.

    We need to change one line to get the code working properly:

    SendMessage(btn.Handle, BCM_SETSHIELD, 0, (IntPtr)1);

    Best regards,
    Tiago Moura
  6. Dess
    Admin
    Dess avatar
    1605 posts

    Posted 12 Feb 2015 Link to this post

    Hello Tiago,

    Thank you for writing back.

    When I modify the provided code snippet from my previous post to use the code you provided
    SendMessage(btn.Handle, BCM_SETSHIELD, 0, (IntPtr)1);

    I am unable to build my project as the SendMessage requires integer for the last parameter:
    "Error message - The best overloaded method match for 'SendMessage(System.IntPtr, uint, int, int)' has some invalid arguments".

    I hope this information helps. If you have any additional questions, please let me know.

    Regards,
    Dess
    Telerik
     

    Check out the Telerik Platform - the only platform that combines a rich set of UI tools with powerful cloud services to develop web, hybrid and native mobile apps.

     
  7. Lex
    Lex avatar
    3 posts
    Member since:
    Jul 2014

    Posted 02 Oct 2015 in reply to Dess Link to this post

    The SendMessage signature can vary, such as 

    public static extern uint SendMessage(IntPtr hWnd, uint msg, IntPtr wParam, IntPtr lParam);​

    Meanwhile, it should be noted that this call lets the shield icon shows,

    SendMessage(btn.Handle, BCM_SETSHIELD, 0, (IntPtr)1);

    while this call hides the shield, as explained by Microsoft at https://msdn.microsoft.com/en-us/library/aa361904.aspx 

    SendMessage(btn.Handle, BCM_SETSHIELD, 0, (IntPtr)0);

  8. Dess
    Admin
    Dess avatar
    1605 posts

    Posted 06 Oct 2015 Link to this post

    Hello Lex,

    Thank you for sharing this information with the community. I have also updated your Telerik points.
     
    Regards,
    Dess
    Telerik
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Feedback Portal and vote to affect the priority of the items
  9. Stefan
    Admin
    Stefan avatar
    2891 posts

    Posted 02 Sep Link to this post

    Here is yet another way to get the UAC icon and set it to any control you may need:
    System.Drawing.Icon myIcon = new System.Drawing.Icon(System.Drawing.SystemIcons.Shield, 16, 16);
    radButton1.Image = myIcon.ToBitmap();


    Regards,
    Stefan
    Telerik by Progress
    Check out the Windows Forms project converter, which aids the conversion process from standard Windows Forms applications written in C# or VB to Telerik UI for WinForms.For more information check out this blog post and share your thoughts.
Back to Top
UI for WinForms is Visual Studio 2017 Ready