|
Îåêßíçóå áðü ôï ìÝëïò AlKiS. Τελευταία δημοσίευση από το μέλος AlKiS στις 11-11-2011, 19:43. Υπάρχουν 29 απαντήσεις.
-
27-10-2011, 22:17
|
-
AlKiS
-
-

-
Μέλος από τις 12-01-2007
-
Volos
-
Δημοσιεύσεις 312
-
-
|
VB.NET 2010 Εικόνα απο MS Access
Θέλω (μέσω ενός προγράμματος που έγραψα σε Visual Basic 2010 .NET) να κάνω retrieve μια εικόνα που έχω βάλει σε μια βάση δεδομένων Access. Έχω δοκιμάσει τα εξής 2 πράγματα, κανένα εκ των οποίων δεν δούλεψε pic.Image = Image.FromStream(AccessDataSet.Tables("FBICriminalsTable").Rows(0).Item("Picture")) και pic.Image = AccessDataSet.Tables("FBICriminalsTable").Rows(0).Item("Picture")
Το πρόβλημα που μου βγάζει έιναι το εξής: Unable to cast object of type 'System.Byte[]' to type 'System.IO.Stream' Η βάση δεδομένων είναι Access 2007 (.accdb) και την ανοίγω με "PROVIDER=Microsoft.ACE.OLEDB.12.0;"
Στο item "Picture" έχω πράγματι βάλη φώτο σε .jpg format και όταν ανοίγω τη βάση δεδομένων με την access, στο κουτί αυτό μου λέει: "package" και αν το κάνω 2πλο κλίκ ανοίγει η φώτο.
Τι πρέπει να κάνω για να γίνει retrieve η εικόνα?? (όλα τα κείμενα τα βγάζει κανονικά).
|
|
-
29-10-2011, 01:19
|
-
AlKiS
-
-

-
Μέλος από τις 12-01-2007
-
Volos
-
Δημοσιεύσεις 312
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
Καμιά ιδέα κανείς???
|
|
-
29-10-2011, 10:34
|
-
tasos
-
-

-
Μέλος από τις 13-11-2006
-
Θεσσαλονίκη
-
Δημοσιεύσεις 283
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
Το πεδίο που αποθηκεύεις την εικόνα είναι τύπου Attachment; Αν ναι, δες λίγο σε αυτό το άρθρο, έχει και sample κώδικα σε vb.net.
Τάσος Καραγιάννης Baby debugging steps...
|
|
-
29-10-2011, 11:42
|
-
AlKiS
-
-

-
Μέλος από τις 12-01-2007
-
Volos
-
Δημοσιεύσεις 312
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
Το πεδίο μου δεν είναι attachment αλλά δεν πειράζε. Το λίνκ που μου έδωσες είναι πολύ καλό, Ευχαριστώ.
Θα αφήσω για μια-δυο μέρες το τόπικ σαν μη επιλυμένο έτσι ώστε αν κάποιος ξέρει να μου πει τι ακριβώς να αλλάξω για να διαβαστεί η εικόνα, να μου πει. Αλλιώς θα αλλάξω εντελώς τον κώδικα και να τον κάνω σαν αυτό που είδα στο λίνκ σου για να δουλέψει.
|
|
-
30-10-2011, 11:03
|
-
tasos
-
-

-
Μέλος από τις 13-11-2006
-
Θεσσαλονίκη
-
Δημοσιεύσεις 283
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
AlKiS:Το πεδίο μου δεν είναι attachment αλλά δεν πειράζε. Το λίνκ που μου έδωσες είναι πολύ καλό,
Άρα είναι τύπου OLE Object, σωστά; Διάβασε εδώ όπου έχει την εξής function: Private Shared Function ConvertToImage(ByVal imageObj As Object) As Image
Dim ImageBytes As Byte() = CType(imageObj, Byte())
Dim sMemory As New IO.MemoryStream(ImageBytes)
Using sMemory
Return Image.FromStream(sMemory)
End Using
End Function
Τάσος Καραγιάννης Baby debugging steps...
|
|
-
30-10-2011, 14:14
|
-
AlKiS
-
-

-
Μέλος από τις 12-01-2007
-
Volos
-
Δημοσιεύσεις 312
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
ΩΩΩ! νομίζω ότι αυτό είναι ακριβώς αυτό που χρειάζομαι. Δεν είμαι στον υπολογιστή με το Visual Studio τώρα για να το επιβεβαιώσω αλλά είμαι 99% σίγουρος
Ευχαριστώ πραγματικά πολύ φίλε μου! :)
|
|
-
30-10-2011, 22:22
|
-
AlKiS
-
-

-
Μέλος από τις 12-01-2007
-
Volos
-
Δημοσιεύσεις 312
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
tasos: AlKiS:Το πεδίο μου δεν είναι attachment αλλά δεν πειράζε. Το λίνκ που μου έδωσες είναι πολύ καλό,
Άρα είναι τύπου OLE Object, σωστά; Διάβασε εδώ όπου έχει την εξής function: Private Shared Function ConvertToImage(ByVal imageObj As Object) As Image
Dim ImageBytes As Byte() = CType(imageObj, Byte())
Dim sMemory As New IO.MemoryStream(ImageBytes)
Using sMemory
Return Image.FromStream(sMemory)
End Using
End Function
Δυστυχώς μου βγάζει το εξής πρόβλημα: System.ArguementException: Paramater is not valid. at system.Drawing.Image.FromStream(Stream stream, Boolean useEmbeddedColorManagement, Boolean validateImageData) at system.DrawingImage.FromStream(Stream stream) at F.B.I.HQ.frmSearchEngine.ConvertToImage(object imageObj) in C:\.......\frmSearchEngine.vb:Line171 at C:\......\frmSearchEngine.vb:Line 235
Λοιπών, η σειρά 171 γράφει: Using sMemory
Και η σειρά 235: pic.Image = ConvertToImage(AccessDataSet.Tables("FBICriminalsTable").Rows(ResultRow).Item("Picture"))
|
|
-
31-10-2011, 00:01
|
-
tasos
-
-

-
Μέλος από τις 13-11-2006
-
Θεσσαλονίκη
-
Δημοσιεύσεις 283
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
Τζάμπα ο ενθουσιασμός..  Με λίγο search βρήκα πως το object που σου επιστρέφει το query δεν είναι το image, αλλά ένα ole object που περιέχει το image και πριν το image έχει κάποια header information. Οπότε για να παίξει πρέπει να κάνεις remove το header information για να σου μείνει η εικόνα που έχεις αποθηκεύσει. Δες αυτό το άρθρο που έχει μία function που κάνει αυτή τη διαδικασία. Οπότε η function πρέπει να γίνει κάπως έτσι χρησιμοποιώντας αυτή που δίνει το προηγούμενο άρθρο: Private Shared Function ConvertToImage(ByVal imageObj As Object) As Bitmap
Dim ImageBytes As Byte() = CType(imageObj, Byte())
Dim CleanImageBytes() As Byte = GetImageBytesFromOLEField(ImageBytes)
Dim sMemory As New IO.MemoryStream(CleanImageBytes)
Using sMemory
Return Bitmap.FromStream(sMemory, False, True)
End Using
End Function Για το conversion από C# σε VB.NET εδώ. Υ.Γ. Μου έκανε εντύπωση πάντως που δεν βρήκα κάποια σχετική πληροφορία στο msdn, ενώ βρήκα κόσμο να γράφει ότι δεν υπάρχει σχετικό documentation.
Τάσος Καραγιάννης Baby debugging steps...
|
|
-
31-10-2011, 19:11
|
-
AlKiS
-
-

-
Μέλος από τις 12-01-2007
-
Volos
-
Δημοσιεύσεις 312
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
tasos:Τζάμπα ο ενθουσιασμός..  Με λίγο search βρήκα πως το object που σου επιστρέφει το query δεν είναι το image, αλλά ένα ole object που περιέχει το image και πριν το image έχει κάποια header information. Οπότε για να παίξει πρέπει να κάνεις remove το header information για να σου μείνει η εικόνα που έχεις αποθηκεύσει. Δες αυτό το άρθρο που έχει μία function που κάνει αυτή τη διαδικασία. Οπότε η function πρέπει να γίνει κάπως έτσι χρησιμοποιώντας αυτή που δίνει το προηγούμενο άρθρο: Private Shared Function ConvertToImage(ByVal imageObj As Object) As Bitmap
Dim ImageBytes As Byte() = CType(imageObj, Byte())
Dim CleanImageBytes() As Byte = GetImageBytesFromOLEField(ImageBytes)
Dim sMemory As New IO.MemoryStream(CleanImageBytes)
Using sMemory
Return Bitmap.FromStream(sMemory, False, True)
End Using
End Function Για το conversion από C# σε VB.NET εδώ. Υ.Γ. Μου έκανε εντύπωση πάντως που δεν βρήκα κάποια σχετική πληροφορία στο msdn, ενώ βρήκα κόσμο να γράφει ότι δεν υπάρχει σχετικό documentation.
Πράγματι είναι αξιοπερίεργο... Ευχαριστώ και πάλι, το εκτιμώ πραγματικά. Δυστυχώς δεν είμαι σε υπολογιστή με Visual Studio αυτή τη στιγμή. Οπότε όπως την προηγούμενη φορά, μόλις πάω θα το δω και θα απαντήσω :)
|
|
-
01-11-2011, 21:02
|
-
Libra Storm
-
-

-
Μέλος από τις 28-01-2011
-
Χαϊδάρι
-
Δημοσιεύσεις 142
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
Το function που προτείνει ο Tasos δουλεύει (το δοκίμασα μόνο με JPG). Σίγουρα δεν καλύπτει όλες τις περιπτώσεις αφού μπορείς σε αυτού του τύπου πεδία να έχεις οτιδήποτε format (excel, word κλπ) αλλά δεν έχω κάτι καλύτερο να σου προτείνω. Επίσης Θα μπορούσες να αποφύγεις σίγουρα την μετατροπή του Byte array σε UTF7 γιά να κάνεις την δουλειά σου πιό γρήγορα. 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
| Public Class Form1
Private Sub Button1_Click(sender As System.Object, e As System.EventArgs) Handles Button1.Click
Dim ColumnName As String = "OLE_OBJ"
Dim TableName As String = "IMAGES"
Dim con As New OleDb.OleDbConnection("Provider=Microsoft.ACE.OLEDB.12.0;Data Source=C:\Users\Vangelis\Documents\MyDB.accdb")
con.Open()
Dim da = New OleDb.OleDbDataAdapter("SELECT TOP 1 " & ColumnName & " FROM " & TableName, con)
Dim dt = New DataTable
da.Fill(dt)
con.Close()
If dt.Rows.Count > 0 AndAlso Not dt.Rows(0).IsNull(ColumnName) Then
Me.BackgroundImage = Me.GetImageFromOLEField(CType(dt.Rows(0).Item(ColumnName), Byte()))
End If
End Sub
Private Function GetImageFromOLEField(oleFieldBytes As Byte()) As Image
Dim sFormats(4) As String
sFormats(0) = "BM" ' BITMAP
sFormats(1) = ChrW(&HFF) & ChrW(&HD8) & ChrW(&HFF) ' JPG
sFormats(2) = ChrW(137) & "PNG" & vbCrLf & ChrW(26) & vbLf ' PNG
sFormats(3) = "GIF8" ' GIF
sFormats(4) = "II*" & Chr(0) ' TIFF
' Get a UTF7 Encoded string version
Dim u8 As System.Text.Encoding = System.Text.Encoding.UTF7
Dim strTemp As String = u8.GetString(oleFieldBytes)
' Get the first 300 characters from the string
Dim strVTemp As String = strTemp.Substring(0, 300)
Dim iPos As Integer = -1
For Each s As String In sFormats
iPos = strVTemp.IndexOf(s)
If iPos <> -1 Then Exit For
Next
If iPos = -1 Then
' TODO
Return Nothing
End If
Dim ms As New IO.MemoryStream(oleFieldBytes, iPos, oleFieldBytes.Length - iPos)
Return Image.FromStream(ms)
End Function
End Class |
Το επόμενο παράδειγμα σου δείχνει πως εσύ μπορείς να αποθηκεύσεις τύπους ( ακόμα και δικούς σου ) σε binary μορφή, στην συγκεκριμένη περίπτωση σε Access table (ακόμα και image να είναι δεν θα διαβάζονtαι από την access σαν Package αλλά μόνο από .NET). Μετά φτιάχνει ένα Serializable Class ( με την χρήση ενός Attribute), το γράφει στην βάση και μετά το σηκώνει πάλι και βάζει το image property που έχει, σαν background image στην φόρμα. Η όλη διαδικασία λέγεται serialization - Deserialization. Φυσικά πρέπει να βρεις έναν τρόπο να ελέγχεις αν τα δεδομένα πρίν τα αποθηκεύσεις είναι serializable και αν είναι του τύπου που θέλεις πριν τα εμφανίσεις. 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
| Public Class Form1
<Serializable()>
Friend Class AClass
Friend Sub New(ByVal format As String, ByVal image As Image)
_Format = format
_image = image
End Sub
Private _Format As String
Friend ReadOnly Property Format As String
Get
Return _Format
End Get
End Property
Friend Property image As Image
End Class
Private Sub Button1_Click(sender As System.Object, e As System.EventArgs) Handles Button1.Click
Dim ColumnName As String = "OLE_OBJ"
Dim TableName As String = "IMAGES"
Dim con As New OleDb.OleDbConnection("Provider=Microsoft.ACE.OLEDB.12.0;Data Source=C:\Users\Vangelis\Documents\MyDB.accdb")
Dim image As Image = image.FromFile("C:\Users\Vangelis\Pictures\MyImage.bmp")
Dim bytes() As Byte = Conversion(Of AClass).Serialize(New AClass("BMP", image))
Dim command As OleDb.OleDbCommand
Dim da As OleDb.OleDbDataAdapter
Dim dt As DataTable
con.Open()
command = New OleDb.OleDbCommand("INSERT INTO " & TableName & " (" & ColumnName & ") VALUES (AByteArray)", con)
command.Parameters.Add("AByteArray", OleDb.OleDbType.VarBinary).Value = bytes
command.ExecuteNonQuery()
command.Dispose()
da = New OleDb.OleDbDataAdapter("SELECT TOP 1 " & ColumnName & " FROM " & TableName, con)
dt = New DataTable
da.Fill(dt)
da.Dispose()
con.Close()
Dim a As AClass = Conversion(Of AClass).DeSerialize(DirectCast(dt.Rows(0).Item(ColumnName), Byte()))
Me.BackgroundImage = a.image
dt.Dispose()
End Sub
End Class
Friend Class Conversion(Of AnyType) ' TODO AnyType Should be a serializable type only
Friend Shared Function Serialize(ByVal type As AnyType) As Byte()
Dim memStream As New IO.MemoryStream
Dim binF As New Runtime.Serialization.Formatters.Binary.BinaryFormatter
Dim bytes() As Byte
binF.Serialize(memStream, type)
bytes = memStream.ToArray
memStream.Close()
Return bytes
End Function
Friend Shared Function DeSerialize(ByVal data As Byte()) As AnyType
Dim memStream As New IO.MemoryStream(data)
Dim binF As New Runtime.Serialization.Formatters.Binary.BinaryFormatter
Dim any As AnyType
any = DirectCast(binF.Deserialize(memStream), AnyType)
memStream.Close()
Return any
End Function
End Class |
|
|
-
01-11-2011, 21:15
|
-
AlKiS
-
-

-
Μέλος από τις 12-01-2007
-
Volos
-
Δημοσιεύσεις 312
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
Πολύ ενδιαφέρων, θα τα δω και τα 2 :)
Ευχαριστώ!!
|
|
-
02-11-2011, 23:17
|
-
AlKiS
-
-

-
Μέλος από τις 12-01-2007
-
Volos
-
Δημοσιεύσεις 312
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
Ναι! Δούλεψε :)
Σας ευχαριστώ πολύ και τους 2 :)
|
|
-
03-11-2011, 10:19
|
-
AlKiS
-
-

-
Μέλος από τις 12-01-2007
-
Volos
-
Δημοσιεύσεις 312
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
Μια παρατήρηση σε σχέση με τον δεύτερο κώδικα. Βλέπω ότι μπορεί να αλλάξει μόνο το πρώτο row της βάσης δεδομένων, και δεν είμαι σίγουρος πως να το κάνω να αλλάζει αυτά που θέλω... δεν έχει πουθενά επιλογή για row(Νούμερο), ανταυτού έχει το "SELECT TOP 1" &
Αν μπορούσαμε να το κάνουμε με rows σώζομαι :)
|
|
-
03-11-2011, 14:02
|
-
Libra Storm
-
-

-
Μέλος από τις 28-01-2011
-
Χαϊδάρι
-
Δημοσιεύσεις 142
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
Βγάλε το TOP, φέρτα όλα ή βάλε WHERE. Μετά κάνε loop ή άλλαξε αυτά που θέλεις. Το παρακάτω παράδειγμα φέρνει όλα τα Rows και τα Columns και γεμίζει ένα FlawLayoutPanel Control, δείχνωντας και το Format Property σαν Τίτλο. Εξέτασε και το lambda και αν θες απάντησε στην ερώτηση: "Τα paint events των pictureboxes γίνονται handle από το ίδιο sub ή από διαφορετικά;". 1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
| Private Sub DisplayImages()
Dim ImageColumnName As String = "OLE_OBJ"
Dim con As New OleDb.OleDbConnection("Provider=Microsoft.ACE.OLEDB.12.0;Data Source=C:\Users\Vangelis\Documents\MyDB.accdb")
Dim da As OleDb.OleDbDataAdapter
Dim dt As DataTable
con.Open()
da = New OleDb.OleDbDataAdapter("SELECT * FROM IMAGES", con) ' Τώρα τα φέρνει όλα.
dt = New DataTable
da.Fill(dt)
da.Dispose()
con.Close()
Me.FlowLayoutPanel1.Controls.Clear() ' Βάλε ένα FlowLayoutPanel control στην φόρμα σου
Dim rows() As DataRow = dt.Select(ImageColumnName & " IS NOT NULL")
For Each row As DataRow In rows
Dim a As AClass = Conversion(Of AClass).DeSerialize(DirectCast(row.Item(ImageColumnName), Byte()))
Dim picBox As New PictureBox With {
.SizeMode = PictureBoxSizeMode.Zoom,
.Width = 150,
.Height = 150,
.Image = a.image,
.Tag = a.Format,
.BackColor = Color.LightBlue
}
AddHandler picBox.Paint, Sub(sender As Object, e As PaintEventArgs)
e.Graphics.DrawString(
DirectCast(sender, PictureBox).Tag.ToString,
Me.Font,
Brushes.Black,
New Point(2, 3))
End Sub
Me.FlowLayoutPanel1.Controls.Add(picBox)
Next
dt.Dispose()
End Sub |
|
|
-
04-11-2011, 21:23
|
-
AlKiS
-
-

-
Μέλος από τις 12-01-2007
-
Volos
-
Δημοσιεύσεις 312
-
-
|
Απ: VB.NET 2010 Εικόνα απο MS Access
Πράγματι τα φέρνει όλα τώρα, αλλά το θέμα έιναι ότι δεν μπορώ να του πω να μου περάσει την τάδε φώτο στο .row(τάδε) Και αυτό είναι κάτι που πραγματικά χρειάζομαι Οπότε απότι καταλαβαίνω, πρέπει να σβήσουμε το "For Each row As DataRow In rows" και να το αντικαταστήσουμε με κάτι άλλο. Αλλά τι θα είναι αυτό το άλλο όμως?
|
|
Σελίδα 1 από 2 (30 εγγραφές)
1
|
|
|