web-dev-qa-db-fra.com

Largeur automatique du contenu de la ComboBox

Est-ce que quelqu'un sait comment régler la largeur du contenu de la ComboBox

Je ne veux pas dire la ComboBox elle-même, mais simplement le contenu ouvert.

37
unicorn

Vous ne pouvez pas l'utiliser directement. 

Faites un tour

Commencez par parcourir tous les éléments de votre liste déroulante, puis vérifiez la largeur de chaque élément en affectant le texte à une étiquette. Ensuite, vérifiez la largeur à chaque fois, si la largeur de l'élément en cours devient supérieure aux éléments précédents, modifiez la largeur maximale.

int DropDownWidth(ComboBox myCombo)
{
    int maxWidth = 0;
    int temp = 0;
    Label label1 = new Label();

    foreach (var obj in myCombo.Items)
    {
        label1.Text = obj.ToString();
        temp = label1.PreferredWidth;
        if (temp > maxWidth)
        {
            maxWidth = temp;
        }
    }
    label1.Dispose();
    return maxWidth;           
}

private void Form1_Load(object sender, EventArgs e)
{
    comboBox1.DropDownWidth = DropDownWidth(comboBox1);
}

OU 

Comme suggéré par stakx , vous pouvez utiliser la classe TextRenderer

int DropDownWidth(ComboBox myCombo)
{
    int maxWidth = 0, temp = 0;
    foreach (var obj in myCombo.Items)
    {
        temp = TextRenderer.MeasureText(obj.ToString(), myCombo.Font).Width;
        if (temp > maxWidth)
        {
            maxWidth = temp;
        }
    }
    return maxWidth;
}
60
Javed Akram

Voici une solution très élégante. Souscrivez simplement votre liste déroulante à ce gestionnaire d'événements:

 private void AdjustWidthComboBox_DropDown(object sender, EventArgs e)
        {
            var senderComboBox = (ComboBox)sender;
            int width = senderComboBox.DropDownWidth;
            Graphics g = senderComboBox.CreateGraphics();
            Font font = senderComboBox.Font;

            int vertScrollBarWidth = (senderComboBox.Items.Count > senderComboBox.MaxDropDownItems)
                    ? SystemInformation.VerticalScrollBarWidth : 0;

            var itemsList = senderComboBox.Items.Cast<object>().Select(item => item.ToString());

            foreach (string s in itemsList)
            {
                int newWidth = (int)g.MeasureString(s, font).Width + vertScrollBarWidth;

                if (width < newWidth)
                {
                    width = newWidth;
                }
            }

            senderComboBox.DropDownWidth = width;
        }

Ce code provient du codeproject: Ajustez la largeur de la liste déroulante de la liste déroulante sur la plus grande largeur de chaîne .

14
algreat

obj.ToString () ne fonctionne pas pour moi, je suggère d'utiliser myCombo.GetItemText (obj). Cela fonctionne pour moi:

private int DropDownWidth(ComboBox myCombo)
{
    int maxWidth = 0, temp = 0;
    foreach (var obj in myCombo.Items)
    {
        temp = TextRenderer.MeasureText(myCombo.GetItemText(obj), myCombo.Font).Width;
        if (temp > maxWidth)
        {
            maxWidth = temp;
        }
    }
    return maxWidth + SystemInformation.VerticalScrollBarWidth;
}
11
user2361362

Généralement le même code que dans la deuxième suggestion de Javed Akram, mais la largeur de la barre de défilement verticale est ajoutée:

int setWidth_comboBox(ComboBox cb)
{
  int maxWidth = 0, temp = 0;
  foreach (string s in cb.Items)
  {
    temp = TextRenderer.MeasureText(s, cb.Font).Width;
    if (temp > maxWidth)
    {
      maxWidth = temp;
    }
  }
  return maxWidth + SystemInformation.VerticalScrollBarWidth;
}

Utilisez le code comme ceci (sur un formulaire avec une liste déroulante portant le nom myComboBox):

myComboBox.Width = setWidth_comboBox(myComboBox);
1
matsolof

C'est une vieille question, mais je viens de la rencontrer et de combiner quelques réponses pour ma solution. J'ai aimé la simplicité de la réponse acceptée, mais je voulais quelque chose qui fonctionnerait avec n'importe quel type d'objet dans la liste déroulante. Je voulais aussi utiliser cette méthode avec une méthode d'extension.

    public static int AutoDropDownWidth(this ComboBox myCombo)
    {
        return AutoDropDownWidth<object>(myCombo, o => o.ToString());
    }
    public static int AutoDropDownWidth<T>(this ComboBox myCombo, Func<T, string> description)
    {
        int maxWidth = 1;
        int temp = 1;
        int vertScrollBarWidth = (myCombo.Items.Count > myCombo.MaxDropDownItems)
                ? SystemInformation.VerticalScrollBarWidth : 0;

        foreach (T obj in myCombo.Items)
        {
            if (obj is T)
            {
                T t = (T)obj;
                temp = TextRenderer.MeasureText(description(t), myCombo.Font).Width;
                if (temp > maxWidth)
                {
                    maxWidth = temp;
                }
            }

        }
        return maxWidth + vertScrollBarWidth;
    }

De cette façon si ma classe est:

public class Person
{
    public string FullName {get;set;}
}

Je pourrais ajuster automatiquement la largeur de la liste déroulante comme suit:

cbPeople.DropDownWidth = cbPeople.AutoDropDownWidth<Person>(p => p.FullName);
0
Aaron Schooley

Vieux mais classique, espère travailler assez vite

private int GetDropDownWidth(ComboBox combo)
{
    object[] items = new object[combo.Items.Count];
    combo.Items.CopyTo(items, 0);
    return items.Select(obj => TextRenderer.MeasureText(combo.GetItemText(obj), combo.Font).Width).Max();
}
0
user1779049

Votez pour la réponse d’Algreat ci-dessous. 

J'ai simplement modifié la réponse d'algreat avec un code redimensionnant l'ensemble du contrôle.

Je l'aurais simplement ajouté en tant que commentaire mais je ne pourrais pas ajouter de code formaté sur le commentaire.

private void combo_DropDown(object sender, EventArgs e)
{
    //http://www.codeproject.com/Articles/5801/Adjust-combo-box-drop-down-list-width-to-longest-s
    ComboBox senderComboBox = (ComboBox)sender;
    int width = senderComboBox.DropDownWidth;
    Graphics g = senderComboBox.CreateGraphics();
    Font font = senderComboBox.Font;
    int vertScrollBarWidth =
        (senderComboBox.Items.Count > senderComboBox.MaxDropDownItems)
        ? SystemInformation.VerticalScrollBarWidth : 0;

    int newWidth;
    foreach (string s in ((ComboBox)sender).Items)
    {
        newWidth = (int)g.MeasureString(s, font).Width
            + vertScrollBarWidth;
        if (width < newWidth)
        {
            width = newWidth;
        }

        if (senderComboBox.Width < newWidth)
        {
            senderComboBox.Width = newWidth+ SystemInformation.VerticalScrollBarWidth;
        }
    }
    senderComboBox.DropDownWidth = width;
}
0
Gary Kindel