DrawToBitmap не делает скриншоты всех предметов

В настоящее время у меня есть этот полезный код, который я нашел в другом месте на StackOverflow:

<code>form.DrawToBitmap(bmp, new Rectangle(0, 0, bmp.Width, bmp.Height));
</code>

У меня есть форма с несколькими текстовыми полями / раскрывающимися списками и большим графическим полем. Затем у меня есть большие графические коробки, помещенные поверх этой большой картинной коробки.

Когда я просматриваю сделанный снимок экрана, он показывает форму, но меньшие графические блоки, которые были помещены над большим графическим блоком, по какой-то причине не отображаются?

 coder10 апр. 2012 г., 22:55
Можете ли вы опубликовать весь код, как с одной строкой кода, мы не можем решить, где на самом деле проблема.

Ответы на вопрос(2)

Спасибо KeithS за помощь!

Для тех, кому нужен код, чтобы сделать это наоборот перевернуть вещи назад, вот и вы:

    private void ReverseControlZIndex(Control parentControl)
    {
        var list = new List<Control>();
        foreach (Control i in parentControl.Controls)
        {
            list.Add(i);
        }
        var total = list.Count;
        for (int i = 0; i < total / 2; i++)
        {
            var left = parentControl.Controls.GetChildIndex( list[i]);
            var right = parentControl.Controls.GetChildIndex(list[total - 1 - i]);

            parentControl.Controls.SetChildIndex(list[i], right);
            parentControl.Controls.SetChildIndex(list[total - 1 - i], left);
        }                        
    }

    private void SaveImage()
    {
        SaveFileDialog sf = new SaveFileDialog();
        sf.Filter = "Bitmap Image (.bmp)|*.bmp|Gif Image (.gif)|*.gif|JPEG Image (.jpeg)|*.jpeg|Png Image (.png)|*.png|Tiff Image (.tiff)|*.tiff|Wmf Image (.wmf)|*.wmf";
        if (sf.ShowDialog() == DialogResult.OK)
        {
            int width = pnlCanvas.Size.Width;
            int height = pnlCanvas.Size.Height;

            Bitmap bm = new Bitmap(width, height);


            SuspendLayout();
            // reverse control z-index
            ReverseControlZIndex(pnlCanvas);

            pnlCanvas.DrawToBitmap(bm, new Rectangle(0, 0, width, height));

            // reverse control z-index back
            ReverseControlZIndex(pnlCanvas);
            ResumeLayout(true);

            bm.Save(sf.FileName, ImageFormat.Bmp);
        }

    }
Решение Вопроса

Я вижу это ограничение в документах для Control.DrawToBitmap ():

Controls inside containers are rendered in reverse order.

Это означало бы, что, если два элемента управления перекрывают друг друга, один элемент обычно отображается «под». другой (он рисуется первым, а затем перезаписывается перекрывающимся элементом управления) вместо этого будет отображаться последним (поэтому он будет перекрывать тот, который обычно перекрывает его). В вашем случае, когда меньший элемент управления рисуется полностью внутри границ большего элемента и поверх него, этот элемент управления будет скрыт этим обратным рендерингом.

Попробуйте обойти это, используя BringToFront () и SendToBack () на большом PictureBox, который перекрывается с меньшими. Вызовите BringToFront () непосредственно перед рисованием в растровом изображении, а затем SendToBack (), когда вы закончите. Если вы не хотите, чтобы пользователь видел мерцание экрана, попробуйте вызвать SuspendLayout (), прежде чем вносить какие-либо изменения в Z-порядок, затем ResumeLayout (true) после сброса на правильный Z-порядок.

 Mike9116 апр. 2012 г., 22:44
Большое спасибо за ваш ответ, Кит. Это сработало отлично. Как вы сказали, я только что вызвал BringToFront () на большом графическом блоке, сделал снимок экрана и затем вызвал SendToBack ().

Ваш ответ на вопрос