想想我们身边的一些例子,当你设置你的QQ头像后,再次登录你的头像就是上次你设置并保存的那个图片。那头像是存放在哪里了呢?存放方式有很多种,我们选择比较合适的方式就行。下面介绍一下我们系统使用的一种方法 。
一、需求
给粮库加载一张背景图片,并下次加载时显示出来。其实和保存QQ头像是一样的原理。
二、解决方案
1、将图片存放在数据库中
步骤:
-
在数据库中建立一张表,将存储的图片的字段类型设为Image类型
-
用FileStream类、BinaryReader把图片读成字节的形式,赋给一个字节数组
- 用ADO.SqlCommand对象的ExecuteNonQuery()方法把数据保存到数据库
实例:
U层
Private Sub FrmHouseLayoutSet_FormClosed(sender As Object, e As FormClosedEventArgs) Handles
Me.FormClosed
Dim storageBLL As New SetStorageBLL
Dim image As New DataTable
Try
‘如果openFileDialog中无图片
If OpenFileDialog1.FileName Is Nothing Then
Exit Sub
Else ‘有图片
‘将图片路径给fullpath,filename获取选定图片的文件名的字符串
Dim fullpath As String = OpenFileDialog1.FileName
‘使用指定的路径、创建模式、读/写权限和共享权限创建 FileStream 类的新实例
Dim fs As FileStream = New FileStream(fullpath, FileMode.Open, FileAccess.Read,
FileShare.Read)
‘length获取用字节表示的流长度
Dim imagebytes() As Byte = New Byte(fs.Length) {}
‘BinaryReader用特定的编码将基元数据类型读作二进制值
Dim br As BinaryReader = New BinaryReader(fs)
‘从当前流中读取指定的字节数以写入字节数组中,并将当前位置前移相应的字节数
imagebytes = br.ReadBytes(Convert.ToInt32(fs.Length))
‘保存图片
If storageBLL.SaveBackImage(imagebytes) = True Then ‘保存成功退出
Exit Sub
Else ‘失败弹出对话框
MsgBox("背景图片保存失败!", vbOKOnly, "信息提示!")
Exit Sub
End If
End If
Catch ex As Exception
MsgBox(ex.Message, MsgBoxStyle.OkOnly, "信息提示!")
End Try
End Sub
B层
‘‘‘ <summary>
‘‘‘ 保存背景图片
‘‘‘ </summary>
‘‘‘ <param name="byImage">图片的二进制形式</param>
‘‘‘ <returns>是否保存成功, 成功返回true 否则返回false</returns>
‘‘‘ <remarks>高晓青 2013-11-22</remarks>
Public Function SaveBackImage(ByVal byImage As Byte()) As Boolean
Dim iStorage As IStorageDevice
iStorage = factory.CreateStorageDevice
Return iStorage.SaveBackImage(byImage)
End Function
工厂层
‘‘‘ <summary>
‘‘‘ 仓房内设备
‘‘‘ </summary>
Public Function CreateStorageDevice() As IStorageDevice
Dim className As String ‘定义实例化类的名称
Dim storageDevice As IStorageDevice ‘定义类的返回类型
className = AssemblyName + "." + db + "StorageDeviceDAL"‘为实例化类名称赋值,程序集名称+类名
storageDevice = CType(Assembly.Load(AssemblyName).CreateInstance(className), IStorageDevice)
Return storageDevice ‘返回值
End Function
接口层
‘‘‘ <summary>
‘‘‘ 保存背景图片
‘‘‘ </summary>
‘‘‘ <param name="byImage">图片的二进制形式</param>
‘‘‘ <returns>是否保存成功, 成功返回true 否则返回false</returns>
‘‘‘ <remarks>高晓青 2013-11-22</remarks>
Function SaveBackImage(ByVal byImage As Byte()) As Boolean
D层
‘‘‘ <summary>
‘‘‘ 保存背景图片
‘‘‘ </summary>
‘‘‘ <param name="byImage">图片的二进制形式</param>
‘‘‘ <returns>是否保存成功, 成功返回true 否则返回false</returns>
‘‘‘ <remarks>高晓青 2013-11-22</remarks>
Public Function SaveBackImage(byImage As Byte()) As Boolean Implements IStorageDevice.SaveBackImage
Dim strSql As String = "if not exists(select * from T_SaveBackImage ) insert into " & _
"T_SaveBackImage(backImage)values(@BackImage) else update T_SaveBackImage set " & _
"backImage=@BackImage"
Dim helper As New SqlHelper
Dim sqlParamers As SqlParameter() = {New SqlParameter("@BackImage", byImage)}
Dim bolInsert = helper.UpdDelAlter(strSql, CommandType.Text, sqlParamers)
Return bolInsert
End Function
2、将图片从数据库中读取
步骤:
- 利用SqlDataReader从数据库中把Image字段值读出来,赋给一个Byte()字节数组
- 使用MemoryStream类与Bitmap把图片读取出来
实例:
U层 ‘读取背景图片,定义byte数组类型的变量imagebytes Dim imagebytes As Byte() ‘从数据库中读取图片 imagebytes = storageBLL.GetImage() ‘创建其支持存储区为内存的流,MemoryStream(imagebytes)基于指定的字节数组初始化 MemoryStream 类的无法调整大小的新实例 Dim ms As MemoryStream = New MemoryStream(imagebytes) ‘Bitmap 是用于处理由像素数据定义的图像的对象,Bitmap(ms)从指定的数据流初始化 Bitmap 类的新实例 Dim bmpt As Bitmap = New Bitmap(ms) ‘将数据库中的图片赋值给控件 plLocation.BackgroundImage = bmpt B层 ‘‘‘ <summary> ‘‘‘ 查询背景图片 ‘‘‘ </summary> ‘‘‘ <returns>背景图片的二进制保存形式</returns> ‘‘‘ <remarks></remarks> Public Function GetImage() As Byte() Dim iStorage As IStorageDevice iStorage = factory.CreateStorageDevice Return iStorage.GetImage() End Function 工厂层 ‘‘‘ <summary> ‘‘‘ 仓房内设备 ‘‘‘ </summary> Public Function CreateStorageDevice() As IStorageDevice Dim className As String ‘定义实例化类的名称 Dim storageDevice As IStorageDevice ‘定义类的返回类型 className = AssemblyName + "." + db + "StorageDeviceDAL" ‘为实例化类名称赋值,程序集名称+类名 storageDevice = CType(Assembly.Load(AssemblyName).CreateInstance(className), IStorageDevice) Return storageDevice ‘返回值 End Function 接口层 ‘‘‘ <summary> ‘‘‘ 查询背景图片 ‘‘‘ </summary> ‘‘‘ <returns>背景图片的二进制保存形式</returns> ‘‘‘ <remarks>高晓青 2013-11-22</remarks> Function GetImage() As Byte() D层 ‘‘‘ <summary> ‘‘‘ 查询背景图片 ‘‘‘ </summary> ‘‘‘ <returns>背景图片的二进制保存形式</returns> ‘‘‘ <remarks>高晓青 2013-11-22</remarks> Public Function GetImage() As Byte() Implements IStorageDevice.GetImage Dim strSql As String = "select backImage from T_SaveBackImage" Dim helper As New SqlHelper Dim bolInsert = helper.GetImage(strSql, CommandType.Text) Return bolInsert End Function现在功能实现了,但对文件存储及数据流学习刚刚开始,还需要进一步去理解这部分。