Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Keep track of screen change and screen resolution change in Windows Form Application to change form size

I want to change form size depending on Screen and it's resolution.

What I want is a correct event to track these screen changes as well as screen resolution changes at runtime.

In other words,

  1. If user is using two screens and move application to another screen, that should be tracked and change size accordingly, i.e. reduce size if new screen's resolution is low or increase size if resolution is larger.

  2. Also track screen resolution change on the same screen, and make changes to size accordingly.

I know how to change Form size, get current screen and it's resolution, just need these events to keep track of these changes.

like image 678
Indigo Avatar asked Jul 22 '13 13:07

Indigo


1 Answers

Going over this answer I've decided to improve it and add further information to form a more complete solution.

The Challenge

Tracking which screen a Form is currently being rendered on. This can change if a user drags the form to another monitor or unplugs a monitor. The resolution can change if a user manually drags a window to a different display or changes the resolution directly.

Firstly, tracking form location. We need to hook into a Move event for the form context, fortunately the .Net framework provides such an event, and it is named Control.Move Event.

Secondly, we will need to hook into a screen resolution changed event, we can do this with the SystemEvents.DisplaySettingsChanged event.

And putting it together, I got this:

struct Resolution
{
    public int Width;
    public int Height;
}

int previous = -1;
int current = -1;

private bool CheckScreenChanged()
{
    bool changed = false;
    current = GetScreenIndex();

    if (current != -1 && previous != -1 && current != previous) // form changed screen.
    {
        changed = true;
    }

    previous = current;

    return changed;
}

private int GetScreenIndex()
{
    return Array.IndexOf(Screen.AllScreens, Screen.FromControl(this));
}

private Resolution GetCurrentResolution()
{
    Screen screen = Screen.FromControl(this);
    Resolution res = new Resolution();
    res.Width = screen.Bounds.Width;
    res.Height = screen.Bounds.Height;

    return res;
}

private void SetResolutionLabel()
{
    Resolution res = GetCurrentResolution();
    label2.Text = String.Format("Width: {0}, Height: {1}", res.Width, res.Height);
}

private void ScreenChanged()
{
    label1.Text = "Screen " + current.ToString();
}

private void Form_Moved(object sender, System.EventArgs e)
{
    bool changed = CheckScreenChanged();
    if (changed == true)
    {
        ScreenChanged();
        SetResolutionLabel();
    }
}

public void SystemEvents_DisplaySettingsChanged(object sender, EventArgs e)
{
    SetResolutionLabel();
}

public void Initialize()
{
    this.Move += Form_Moved;
    SystemEvents.DisplaySettingsChanged += new
    EventHandler(SystemEvents_DisplaySettingsChanged);

    previous = GetScreenIndex();
    current = GetScreenIndex();
    ScreenChanged();
    SetResolutionLabel();
}

The code above is tested on a simple form with two labels called label1 and label2, which are updated when the screen the form is on changes or the resolution changes.

An image of this in action on my primary screen/display

Screen0

And on my secondary screen/display when the form has been dragged to it:

enter image description here

like image 111
Daniel Lane Avatar answered Sep 18 '22 20:09

Daniel Lane