2014-01-11 80 views
0

我想寫一個函數,該函數應該創建一個指定大小的新位圖並用指定的顏色填充它,問題是我得到一個異常試圖將位圖分配給任何屬性或以其他幾種方式使用它,例如從字典類型獲取位圖以讀取位圖屬性。不能在這個函數中返回一個Bitmap對象

例如對於這一點,不工作:

Private Shadows Sub Shown() Handles MyBase.Shown 

    PictureBox1.BackgroundImage = 
     CreateSolidBitmap(New Size(16, 16), Color.Red) 

End Sub 

而且這工作直到我嘗試讀取位圖

Private Shadows Sub Shown() Handles MyBase.Shown 

     Dim dict As New Dictionary(Of Color, Bitmap) From 
      { 
       {Color.Red, CreateSolidBitmap(New Size(16, 16), Color.Red)} 
      } 

     ' This throws the same exception above: 
     MsgBox(dict(Color.Red).Size.Width) 

    End Sub 

例外說,這一刻:

System.ArgumentException未處理消息:在S中發生類型爲'System.ArgumentException'的未處理異常 ystem.Drawing.dll 附加信息:無效的參數。

這是函數,我錯過了什麼?

''' <summary> 
''' Creates a bitmap filled with a solid color. 
''' </summary> 
''' <param name="FillColor">Color to fill the Bitmap.</param> 
''' <returns>System.Drawing.Bitmap.</returns> 
Private Function CreateSolidBitmap(ByVal Size As Size, 
            ByVal FillColor As Color) As Bitmap 

    ' Create a bitmap. 
    Using bmp As New Bitmap(Size.Width, Size.Height) 

     ' Create a graphics object. 
     Using g As Graphics = Graphics.FromImage(bmp) 

      ' Create a brush using the specified color. 
      Using br As New SolidBrush(FillColor) 

       ' Fill the graphics object with the brush. 
       g.FillRectangle(br, 0, 0, bmp.Width, bmp.Height) 

      End Using ' br 

     End Using ' g 

     Return bmp 

    End Using ' bmp 

End Function 

位圖是這個:

enter image description here

+0

您正在處理您嘗試存儲的相同位圖。 – Plutonix

回答

1

不是沒有,但有IS一種方法來優化這種方案。我有一個應用程序,可以存儲多達120個大小未知的圖像。我還必須創建/管理該圖像的縮略圖。而不是存儲的位圖,其是巨大的,將圖像保存到編碼爲PNG流:

Private Sub EncodeImage(ByVal bmp As Bitmap) 
    ' raw bitmaps are HUGE - 1080p can be 8MB while JPG is 400K and PNG is 2MB 

    ' optional: examine bmp and make a reasonable size thumbnail. 
    ' e.g. store 1080p as a max of 1600x900 or whatever. 
    'you can always restore the size 

    ' a backing field in the class this procedure is in 
    _MS = New MemoryStream 

    bmp.Save(mMS, System.Drawing.Imaging.ImageFormat.Png) 
End Sub 

解碼是簡單的:

_MS.Seek(0, SeekOrigin.Begin) 

Return System.Drawing.Image.FromStream(mMS, True, False) 

可以保存巨量和存儲器這樣巨量,有一個如果重複訪問同一圖像(如循環中),輕微的性能下降。沒有理由訴諸於這樣的16x16 單色位圖(OP),我甚至不會在這種情況下存儲位圖。但從評論(5000px bitmap)我會認爲這取決於這些是什麼。

也可以從編碼質量命中(這是一個更喜歡PNG到JPG的理由)。對於單色 bimtmaps,你不會注意到。對於實際的圖像,您可能會這樣做,但折衷是在應用程序中存儲少得多的圖像,或者通過使用磁盤臨時文件來降低速度。

HTH

+0

'用於16x16單色位圖(OP),我甚至不會在該情況下存儲位圖。只有16px大小,它用於在上下文菜單中顯示一種Most-Recent-Used顏色作爲下拉菜單項,但是如果在這種情況下甚至不存儲位圖,那麼我會提到你正在談論的是直接繪製矩形或什麼你的意思是其他想法?非常感謝您的時間! – ElektroStudios

+1

像往常一樣,魔鬼在(實施)的細節:對於MRU/CTM,是的,我可以保存圖像。從OP,它看起來像你可能會存儲一大堆單色bmps。儘管繪製/填充矩形具有無需跟蹤和處理事物的優勢,但速度並不慢。所有的ColorPicker控件在那裏繪製所有的顏色。在評論5000px後很難說出你的想法。乾杯! – Plutonix

2

變化

Using bmp As New Bitmap(Size.Width, Size.Height) 

Dim bmp As New Bitmap(Size.Width, Size.Height) 

End Using(在BM的p)被擊中,bmp將被丟棄。

+0

但如果我使用昏暗,那麼我的功能不會放棄任何新的位圖..增加內存。 – ElektroStudios

+0

位圖是一個類,因此是一個引用類型。如果你處理它,它將不會在稍後引用。 – Kevin

+0

@ElektroStudios什麼?如果是這樣,刪除子內的一切,並返回'CType(Nothing,Bitmap)'。 –

相關問題