11 14th, 2008The System.Drawing.Image class is not serializable by default. This class can be used to serialize images as well as load the image from the IDataRecord.
1: Imports System.Drawing
2: Imports System.Runtime.Serialization
3: Imports System.Drawing.Imaging
4: Imports System.IO
5:
6: <Serializable()> _
7: Public Class SerializableImage
8: Implements ISerializable
9:
10: Private _master As MasterEnum = MasterEnum.Image
11: Private _imageBuffer As Byte()
12: Private _image As Image
13: Private _serializationFormat As ImageFormat = ImageFormat.Png
14:
15: Public Property Image() As Image
16: Get
17: If _master <> MasterEnum.Image Then
18: CreateImageFromBuffer()
19: End If
20: Return _image
21: End Get
22: Set(ByVal value As Image)
23: If (value Is _image) Then Return
24: _image = value
25: ‘The image becomes the master once the setter is used
26: _master = MasterEnum.Image
27: _imageBuffer = Nothing
28: End Set
29: End Property
30:
31: Private Sub CreateImageFromBuffer()
32: ‘Once this method is called, the image becomes the master
33: _master = MasterEnum.Image
34: ‘Check if there is a buffer
35: If _imageBuffer Is Nothing OrElse _imageBuffer.Length = 0 Then
36: Image = Nothing
37: Else
38: ‘http://support.microsoft.com/?id=814675
39: Using s As New MemoryStream(_imageBuffer)
40: If Not s Is System.IO.Stream.Null Then
41: Dim tempImage As Image = _
42: DirectCast(Bitmap.FromStream(s), Bitmap)
43: Image = New Bitmap(tempImage)
44: Dim g As Graphics = Graphics.FromImage(tempImage)
45: g.DrawImage(Image, New PointF(0, 0))
46: g.Dispose()
47: tempImage.Dispose()
48: End If
49: s.Close()
50: End Using
51: End If
52: End Sub
53:
54: Private Property ImageBuffer() As Byte()
55: Get
56: Select Case _master
57: Case MasterEnum.Image
58: ‘Used for serialization
59: Return CreateBufferFromImage()
60: Case MasterEnum.Buffer
61: Return _imageBuffer
62: End Select
63: Return _imageBuffer
64: End Get
65: Set(ByVal value As Byte())
66: If (value Is _imageBuffer) Then Return
67: _imageBuffer = value
68: ‘The Buffer becomes the master
69: _master = MasterEnum.Buffer
70: _image = Nothing
71: End Set
72: End Property
73:
74: Private Function CreateBufferFromImage() As Byte()
75: If _image Is Nothing Then Return Nothing
76: ‘Convert the image to a byte array using the serialization format
77: Using stream As New MemoryStream
78: _image.Save(stream, SerializationFormat)
79: Dim result As Byte() = stream.ToArray()
80: stream.Close()
81: Return result
82: End Using
83: End Function
84:
85: Public Property SerializationFormat() As ImageFormat
86: Get
87: Return _serializationFormat
88: End Get
89: Set(ByVal value As ImageFormat)
90: _serializationFormat = value
91: End Set
92: End Property
93:
94: Public Sub New()
95:
96: End Sub
97:
98: Public Sub New(ByVal image As Image)
99: Me.Image = image
100: End Sub
101:
102: Public Sub New(ByVal record As IDataRecord, ByVal fieldIndex As Integer)
103: Load(record, fieldIndex)
104: End Sub
105:
106: Public Sub New(ByVal record As IDataRecord, ByVal fieldName As String)
107: Load(record, fieldName)
108: End Sub
109:
110: Private Sub Load(ByVal record As IDataRecord, ByVal fieldName As String)
111: If record Is Nothing Then Throw New ArgumentNullException(“record”)
112: Load(record, record.GetOrdinal(fieldName))
113: End Sub
114:
115: Private Sub Load(ByVal record As IDataRecord, ByVal fieldIndex As Integer)
116: If record Is Nothing Then Throw New ArgumentNullException(“record”)
117: If record.IsDBNull(fieldIndex) Then Return
118: ImageBuffer = DirectCast(record.GetValue(fieldIndex), Byte())
119: End Sub
120:
121: Public Sub New(ByVal info As SerializationInfo, _
122: ByVal context As StreamingContext)
123: ‘Image
124: Dim data As Byte() = _
125: DirectCast(info.GetValue(“image”, GetType(Byte())), Byte())
126: If data IsNot Nothing AndAlso data.Length > 0 Then
127: ‘http://support.microsoft.com/?id=814675
128: Using s As New MemoryStream(data)
129: If Not s Is System.IO.Stream.Null Then
130: Dim tempImage As Image = _
131: DirectCast(Bitmap.FromStream(s), Bitmap)
132: Image = New Bitmap(tempImage)
133: Dim g As Graphics = Graphics.FromImage(tempImage)
134: g.DrawImage(Image, New PointF(0, 0))
135: g.Dispose()
136: tempImage.Dispose()
137: End If
138: s.Close()
139: End Using
140: End If
141: End Sub
142:
143: Public Sub GetObjectData(ByVal info As SerializationInfo, +
144: ByVal context As StreamingContext) Implements ISerializable.GetObjectData
145: info.AddValue(“image”, ImageBuffer, GetType(Byte()))
146: End Sub
147:
148: Private Enum MasterEnum
149: Buffer
150: Image
151: End Enum
152:
153: End Class
read comments (0)
07 18th, 2007It appears as if there is no timer available for Silverlight. I noticed two options that were utilized; one was using the Storyboard as a timer and another was using System.Windows.Browser.HtmlTimer. Although this causes an obsolete warning, it does work in Silverlight Alpha 1.1, and from some comments on a CodeProject page it looks as if some other timer will become available in the future. So for now I’m going to be using the HtmlTimer to provide the heartbeat for sprites.
1: using System.Windows.Browser;
2:
3: public class WorldBase
4: {
5: private HtmlTimer _heartBeat = new HtmlTimer();
6: private int _beatsPerSecond;
7: private DateTime _lastBeat;
8:
9: public WorldBase()
10: {
11: _lastBeat = DateTime.Now;
12: _heartBeat.Interval = 50;
13: _heartBeat.Tick += new EventHandler(_heartBeat_Tick);
14: _beatsPerSecond = 50;
15: _heartBeat.Enabled = true;
16: }
17:
18: void _heartBeat_Tick(object sender, EventArgs e)
19: {
20: //Update the BeatsPerSecond
21: _beatsPerSecond = 1 / (DateTime.Now - _lastBeat).Seconds;
22: //Provide a hearbeat for the world of sprites
23: ...
24: }
25: }
05 17th, 20071: Public Class Project
2: Inherits BusinessBase(Of Project)
3:
4: Public ReadOnly Property LineItems() As LineItemsCollection
5: Get
6: CanReadProperty(True)
7: If _lineItems Is Nothing Then
8: If Me.IsNew Then
9: _lineItems = LineItemList.NewLineItemList(Me)
10: Else
11: _lineItems = LineItemList.GetLineItems(Me)
12: End If
13: AddHandler _lineItems.ListChanged, _
14: AddressOf LineItemChangedHandler
15: End If
16: Return _lineItems
17: End Get
18: End Property
19:
20: Public Sub LineItemChangedHandler(_
21: ByVal sender As Object, _
22: ByVal e As System.ComponentModel.ListChangedEventArgs)
23: If (e.ListChangedType = ListChangedType.ItemAdded) Then
24: _lineItems(e.NewIndex).Project = Me
25: End If
26: End Sub
27:
28:
29: End Class
30:
31: Public Class LineItem
32: Inherits BusinessBase(Of LineItem)
33:
34: <NotUndoable()> <NonSerialized()> Private _project As Project
35:
36: Public Property Project() As Project
37: Get
38: If _project Is Nothing Then
39: _project = Project.GetProject(_projectId)
40: End If
41: Return _project
42: End Get
43: Friend Set(ByVal value As Project)
44: If Not value.ID = _projectId Then
45: _project = proj
46: ProjectId = proj.ID
47: End If
48: End Set
49: End Property
50:
51: Public Property ProjectId() As Guid
52: Get
53: CanReadProperty(True)
54: Return _projectId
55: End Get
56: Private Set(ByVal value As Guid)
57: If _projectId <> value Then
58: _projectId = value
59: PropertyHasChanged()
60: End If
61: End Set
62: End Property
63:
64: End Class
03 30th, 2007This example illustrates implementing a custom exception, implemeting the ISerializable interface and adding a property to the exception.
1: [Serializable]
2: public class DexException : System.ApplicationException, ISerializable
3: {
4: private DateTime _timeStamp;
5:
6: public DateTime TimeStamp
7: {
8: get { return _timeStamp; }
9: set { _timeStamp = value; }
10: }
11:
12: public DexException() : base()
13: {
14: _timeStamp = DateTime.Now;
15: }
16:
17: public DexException(string message) : base(message)
18: {
19: _timeStamp = DateTime.Now;
20: }
21:
22: protected DexException(SerializationInfo info,
23: StreamingContext context) : base(info, context)
24: {
25: _timeStamp = info.GetDateTime("TimeStamp");
26: }
27:
28: [SecurityPermissionAttribute(SecurityAction.Demand,
29: SerializationFormatter=true)]
30: public override void GetObjectData(
31: SerializationInfo info, StreamingContext context)
32: {
33: info.AddValue("TimeStamp", _timeStamp);
34: }
35: }
03 7th, 2007It’s strange, but this is the second project now, where I’ve found a use for what was originally called the TdoMatrix. It’s a simple name value pair class with a list of child classes of the same type. It only supports two methods, “Add” and “Find”. The class is used for building filter dependencies. Adding filter dependencies can be accomplished like this:
myMatrix.Add(”Toyota”).Add(”Camry”).Add(”Silver”).Value = MyCarPicture
Now if silver was available for many cars, you could do this:
myMatrix.Add(”Toyota”).Add(”Camry”, “Corolla”, “Echo”).Add(”Silver”)
You can call Add multiple times, if it already exists, the add will be ignored.
1: Imports system.ComponentModel
2:
3: Public Interface IMatrixNode(Of T)
4: ReadOnly Property Name() As String
5: Property Value() As T
6: Function Add(ByVal ParamArray nodeNames() As String) As IMatrixNode(Of T)
7: Function Find(ByVal name As String) As IMatrixNode(Of T)
8: End Interface
9:
10: Public Class MatrixNode(Of T)
11: Inherits List(Of IMatrixNode(Of T))
12: Implements IMatrixNode(Of T)
13:
14: Private _name As String
15: Private _value As T
16: Private _index As Dictionary(Of String, IMatrixNode(Of T)) = Nothing
17:
18: Public Sub New(ByVal aName As String)
19: _name = aName
20: End Sub
21:
22: Public ReadOnly Property Name() As String Implements IMatrixNode(Of T).Name
23: Get
24: Return _name
25: End Get
26: End Property
27:
28: Public Property Value() As T Implements IMatrixNode(Of T).Value
29: Get
30: Return _value
31: End Get
32: Set(ByVal value As T)
33: _value = value
34: End Set
35: End Property
36:
37: Private ReadOnly Property Index() As _
38: Dictionary(Of String, IMatrixNode(Of T))
39: Get
40: If (_index Is Nothing) Then _index = _
41: New Dictionary(Of String, IMatrixNode(Of T))
42: Return _index
43: End Get
44: End Property
45:
46: Private Overloads Function Add(ByVal ParamArray nodeNames() As String) _
47: As IMatrixNode(Of T) Implements IMatrixNode(Of T).Add
48: If (nodeNames.Length = 0) Then Return Nothing
49: Dim nodes(nodeNames.Length) As IMatrixNode(Of T)
50: For i As Integer = 0 To nodeNames.Length - 1
51: Dim iNode As IMatrixNode(Of T) = Nothing
52: If Not Index.TryGetValue(nodeNames(i), iNode) Then
53: iNode = New MatrixNode(Of T)(nodeNames(i))
54: Add(iNode)
55: Index.Add(iNode.Name, iNode)
56: End If
57: nodes(i) = iNode
58: Next
59: If (nodes.Length = 1) Then Return nodes(0)
60: Return New MatrixGroup(Of T)(nodes)
61: End Function
62:
63: Public Shadows Function Find(ByVal name As String) _
64: As IMatrixNode(Of T) Implements IMatrixNode(Of T).Find
65: Return Index(name)
66: End Function
67: End Class
68:
69: Public Class MatrixGroup(Of T)
70: Implements IMatrixNode(Of T)
71:
72: Private _childNodes() As IMatrixNode(Of T)
73:
74: Public Sub New(ByVal ParamArray nodes() As IMatrixNode(Of T))
75: _childNodes = nodes
76: End Sub
77:
78: Public Function Add(ByVal ParamArray nodeNames() As String) _
79: As IMatrixNode(Of T) Implements IMatrixNode(Of T).Add
80: For Each node As IMatrixNode(Of T) In _childNodes
81: node.Add(nodeNames)
82: Next
83: Return Me
84: End Function
85:
86: Public ReadOnly Property Name() As String Implements IMatrixNode(Of T).Name
87: Get
88: Return "Temporary Group"
89: End Get
90: End Property
91:
92: Public Property value() As T Implements IMatrixNode(Of T).Value
93: Get
94: If (_childNodes.Length > 0) Then Return _childNodes(0).Value
95: Return Nothing
96: End Get
97: Set(ByVal value As T)
98: For Each node As IMatrixNode(Of T) In _childNodes
99: node.Value = value
100: Next
101: End Set
102: End Property
103:
104: Public Shadows Function Find(ByVal name As String) _
105: As IMatrixNode(Of T) Implements IMatrixNode(Of T).Find
106: Throw New NotSupportedException( _
107: "Find cannot be executed on the MatrixGroup")
108: End Function
109:
110: End Class
11 6th, 2006There are several tricks that you need to know in order to generate the necessary synergy between Microsoft Project and Team Foundation Servers work items. One of those being, how do you update “PercentComplete” in Microsoft Project when the Developers only update CompletedWork and RemainingWork (and TFS does not allow complex mappings which could translate these into percent complete). One option is to generate a macro in MS Project that performs the necessary calculations. The other option would be to create a web service and register this service with TFS when any work item is updated. The web service would then query the work item, calculate and update the percentage. This also requires adding an additional “PercentComplete” field in the work item. I’d like to take this approach in the long term, but short-term, the following MS Project macro does the trick.
Sub CalcPercentComplete() Dim task As task Dim taskComplete As Long For Each task In ActiveProject.tasks If (Not task.Rollup) Then taskComplete = task.PercentComplete If (task.ActualWork = 0) Then taskComplete = 0 ElseIf (task.RemainingWork = 0) Then taskComplete = 100 Else taskComplete = Round(task.ActualWork * 100 / (task.ActualWork + task.RemainingWork)) End If task.PercentComplete = taskComplete End If Next task End Sub
11 2nd, 2006This little bit of code has been useful in a console application to automatically modify the AssemlbyInfo.cs files and update the version number.
static void Main(string[] args) { if (args.Length != 2) Console.WriteLine("Usage: ApplyVersionNo <folder> <version_no>"); else { Regex regexAsmVersion = new Regex(@"\[assembly: AssemblyVersion\(""([0-9.\*]*)""\)\]"); Regex regexAsmFileVersion = new Regex(@"\[assembly: AssemblyFileVersion\(""([0-9.\*]*)""\)\]"); string folder = args[0]; string version = args[1]; foreach (string filename in Directory.GetFiles( folder, "AssemblyInfo.cs", SearchOption.AllDirectories)) { string contents = File.ReadAllText(filename); string newContents = regexAsmVersion.Replace( contents, @"[assembly: AssemblyVersion(""" + version + @""")]"); newContents = regexAsmFileVersion.Replace( newContents, @"[assembly: AssemblyFileVersion(""" + version + @""")]"); File.WriteAllText(filename, newContents); } } }
10 25th, 2006There are few things that need to be done (albeit very obvious) that need to be done to allow forms embedded within a panel or other control.
//viewForm is of type Form, parent is of type
viewForm.TopLevel = False;
viewForm.Dock = DockStyle.Fill;
viewForm.FormBorderStyle = FormBorderStyle.None;
viewForm.Parent = parent;
viewForm.Show();
03 6th, 2006private Color ColorFade(Color fromColor, Color toColor, byte fade) { byte fromR = fromColor.R; byte fromG = fromColor.G; byte fromB = fromColor.B; byte toR = toColor.R; byte toG = toColor.G; byte toB = toColor.B; byte r = Fade(fromR, toR, fade); byte g = Fade(fromG, toG, fade); byte b = Fade(fromB, toB, fade); return Color.FromArgb(r, g, b); } private byte Fade(byte from, byte to, byte fade) { int h = (to >= from) ? to : from; int l = (to < from) ? to : from; int fadeInt = fade; return (byte)(l + (h-l) * fadeInt / 255); }