├── .github
└── FUNDING.yml
├── bin
└── Debug
│ ├── ObserverPattern.exe
│ ├── ObserverPattern.pdb
│ ├── ObserverPattern.vshost.exe
│ ├── Microsoft.VisualBasic.PowerPacks.Vs.dll
│ └── ObserverPattern.vshost.exe.manifest
├── obj
└── x86
│ └── Debug
│ ├── ObserverPattern.exe
│ ├── ObserverPattern.pdb
│ ├── ObserverPattern.MainForm.resources
│ ├── ObserverPattern.BallObserver.resources
│ ├── DesignTimeResolveAssemblyReferences.cache
│ ├── ObserverPattern.MovingBallObserver.resources
│ ├── ObserverPattern.csproj.GenerateResource.Cache
│ ├── DesignTimeResolveAssemblyReferencesInput.cache
│ ├── ObserverPattern.Properties.Resources.resources
│ ├── ObserverPattern.csprojResolveAssemblyReference.cache
│ ├── ObserverPattern.ObserverPattern.Observer.SimpleObserver.resources
│ └── ObserverPattern.csproj.FileListAbsolute.txt
├── Properties
├── Settings.settings
├── Settings.Designer.cs
├── AssemblyInfo.cs
├── Resources.Designer.cs
└── Resources.resx
├── ObserverPattern
├── Observer
│ ├── IObserver.cs
│ ├── SimpleObserver.cs
│ ├── BallObserver.cs
│ ├── SimpleObserver.Designer.cs
│ ├── MovingBallObserver.cs
│ ├── MovingBallObserver.Designer.cs
│ ├── BallObserver.Designer.cs
│ ├── BallObserver.resx
│ ├── SimpleObserver.resx
│ └── MovingBallObserver.resx
└── Subject
│ ├── ISubject.cs
│ └── ColorSubject.cs
├── Program.cs
├── Others
├── CircleShape.cs
└── ColorComboBox.cs
├── MainForm.cs
├── MainForm.Designer.cs
├── ObserverPattern.csproj
├── README.md
└── MainForm.resx
/.github/FUNDING.yml:
--------------------------------------------------------------------------------
1 | # These are supported funding model platforms
2 |
3 | github: [zied-snoussi]
4 |
--------------------------------------------------------------------------------
/bin/Debug/ObserverPattern.exe:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/bin/Debug/ObserverPattern.exe
--------------------------------------------------------------------------------
/bin/Debug/ObserverPattern.pdb:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/bin/Debug/ObserverPattern.pdb
--------------------------------------------------------------------------------
/obj/x86/Debug/ObserverPattern.exe:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/obj/x86/Debug/ObserverPattern.exe
--------------------------------------------------------------------------------
/obj/x86/Debug/ObserverPattern.pdb:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/obj/x86/Debug/ObserverPattern.pdb
--------------------------------------------------------------------------------
/bin/Debug/ObserverPattern.vshost.exe:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/bin/Debug/ObserverPattern.vshost.exe
--------------------------------------------------------------------------------
/bin/Debug/Microsoft.VisualBasic.PowerPacks.Vs.dll:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/bin/Debug/Microsoft.VisualBasic.PowerPacks.Vs.dll
--------------------------------------------------------------------------------
/obj/x86/Debug/ObserverPattern.MainForm.resources:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/obj/x86/Debug/ObserverPattern.MainForm.resources
--------------------------------------------------------------------------------
/obj/x86/Debug/ObserverPattern.BallObserver.resources:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/obj/x86/Debug/ObserverPattern.BallObserver.resources
--------------------------------------------------------------------------------
/obj/x86/Debug/DesignTimeResolveAssemblyReferences.cache:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/obj/x86/Debug/DesignTimeResolveAssemblyReferences.cache
--------------------------------------------------------------------------------
/obj/x86/Debug/ObserverPattern.MovingBallObserver.resources:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/obj/x86/Debug/ObserverPattern.MovingBallObserver.resources
--------------------------------------------------------------------------------
/obj/x86/Debug/ObserverPattern.csproj.GenerateResource.Cache:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/obj/x86/Debug/ObserverPattern.csproj.GenerateResource.Cache
--------------------------------------------------------------------------------
/obj/x86/Debug/DesignTimeResolveAssemblyReferencesInput.cache:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/obj/x86/Debug/DesignTimeResolveAssemblyReferencesInput.cache
--------------------------------------------------------------------------------
/obj/x86/Debug/ObserverPattern.Properties.Resources.resources:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/obj/x86/Debug/ObserverPattern.Properties.Resources.resources
--------------------------------------------------------------------------------
/obj/x86/Debug/ObserverPattern.csprojResolveAssemblyReference.cache:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/obj/x86/Debug/ObserverPattern.csprojResolveAssemblyReference.cache
--------------------------------------------------------------------------------
/obj/x86/Debug/ObserverPattern.ObserverPattern.Observer.SimpleObserver.resources:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/zied-snoussi/ObserverPattern/HEAD/obj/x86/Debug/ObserverPattern.ObserverPattern.Observer.SimpleObserver.resources
--------------------------------------------------------------------------------
/Properties/Settings.settings:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
--------------------------------------------------------------------------------
/ObserverPattern/Observer/IObserver.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.Linq;
4 | using System.Text;
5 | using System.Drawing;
6 |
7 | namespace ObserverPattern
8 | {
9 | public interface IObserver
10 | {
11 | void ColorChanged(Color newColor);
12 | }
13 | }
14 |
--------------------------------------------------------------------------------
/ObserverPattern/Subject/ISubject.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.Linq;
4 | using System.Text;
5 |
6 | namespace ObserverPattern
7 | {
8 | public interface ISubject
9 | {
10 | void Register(IObserver observer);
11 | void Unregister(IObserver observer);
12 |
13 | void Notify();
14 | }
15 | }
16 |
--------------------------------------------------------------------------------
/bin/Debug/ObserverPattern.vshost.exe.manifest:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
--------------------------------------------------------------------------------
/Program.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.Linq;
4 | using System.Windows.Forms;
5 |
6 | namespace ObserverPattern
7 | {
8 | static class Program
9 | {
10 | ///
11 | /// The main entry point for the application.
12 | ///
13 | [STAThread]
14 | static void Main()
15 | {
16 | Application.EnableVisualStyles();
17 | Application.SetCompatibleTextRenderingDefault(false);
18 | Control.CheckForIllegalCrossThreadCalls = false;
19 | Application.Run(new MainForm());
20 | }
21 | }
22 | }
23 |
--------------------------------------------------------------------------------
/ObserverPattern/Observer/SimpleObserver.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.ComponentModel;
4 | using System.Data;
5 | using System.Drawing;
6 | using System.Linq;
7 | using System.Text;
8 | using System.Windows.Forms;
9 |
10 | namespace ObserverPattern.ObserverPattern.Observer
11 | {
12 | public partial class SimpleObserver : Form, IObserver
13 | {
14 | public SimpleObserver()
15 | {
16 | InitializeComponent();
17 | }
18 |
19 | #region IObserver Members
20 |
21 | public void ColorChanged(Color newColor)
22 | {
23 | this.BackColor = newColor;
24 | }
25 |
26 | #endregion
27 | }
28 | }
29 |
--------------------------------------------------------------------------------
/ObserverPattern/Observer/BallObserver.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.ComponentModel;
4 | using System.Data;
5 | using System.Drawing;
6 | using System.Linq;
7 | using System.Text;
8 | using System.Windows.Forms;
9 |
10 | namespace ObserverPattern
11 | {
12 | public partial class BallObserver : Form, IObserver
13 | {
14 | public BallObserver()
15 | {
16 | InitializeComponent();
17 | }
18 |
19 | #region IObserver Members
20 |
21 | public void ColorChanged(Color newColor)
22 | {
23 | circleShape1.FillColor = newColor;
24 | circleShape2.FillColor = newColor;
25 | circleShape3.FillColor = newColor;
26 | }
27 |
28 | #endregion
29 | }
30 | }
31 |
--------------------------------------------------------------------------------
/Others/CircleShape.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.Linq;
4 | using System.Text;
5 | using System.Windows.Forms;
6 | using System.Drawing;
7 |
8 | namespace ObserverPattern.Others
9 | {
10 | public class CircleShape : Control
11 | {
12 | private Color _FillColor = Color.Blue;
13 | private SolidBrush _brush;
14 |
15 | public CircleShape()
16 | {
17 | _brush = new SolidBrush(_FillColor);
18 | }
19 |
20 | public Color FillColor
21 | {
22 | get { return _FillColor; }
23 | set
24 | {
25 | _FillColor = value;
26 | _brush.Color = value;
27 |
28 | this.Invalidate();
29 | }
30 | }
31 |
32 | protected override void OnPaint(PaintEventArgs e)
33 | {
34 | e.Graphics.FillEllipse(_brush, 0, 0, this.Width - 1, this.Height - 1);
35 | }
36 | }
37 | }
38 |
--------------------------------------------------------------------------------
/ObserverPattern/Subject/ColorSubject.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.Linq;
4 | using System.Text;
5 | using System.Drawing;
6 |
7 | namespace ObserverPattern.ObserverPattern.Subject
8 | {
9 | public class ColorSubject : ISubject
10 | {
11 | private Color _Color = Color.Blue;
12 |
13 | public Color Color
14 | {
15 | get { return _Color; }
16 | set
17 | {
18 | _Color = value;
19 | Notify();
20 | }
21 | }
22 |
23 | #region ISubject Members
24 |
25 | private HashSet _observers = new HashSet();
26 |
27 | public void Register(IObserver observer)
28 | {
29 | _observers.Add(observer);
30 | }
31 |
32 | public void Unregister(IObserver observer)
33 | {
34 | _observers.Remove(observer);
35 | }
36 |
37 | public void Notify()
38 | {
39 | _observers.ToList().ForEach(o => o.ColorChanged(Color));
40 | }
41 |
42 | #endregion
43 | }
44 | }
45 |
--------------------------------------------------------------------------------
/Properties/Settings.Designer.cs:
--------------------------------------------------------------------------------
1 | //------------------------------------------------------------------------------
2 | //
3 | // This code was generated by a tool.
4 | // Runtime Version:4.0.30319.225
5 | //
6 | // Changes to this file may cause incorrect behavior and will be lost if
7 | // the code is regenerated.
8 | //
9 | //------------------------------------------------------------------------------
10 |
11 | namespace ObserverPattern.Properties
12 | {
13 |
14 |
15 | [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]
16 | [global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.VisualStudio.Editors.SettingsDesigner.SettingsSingleFileGenerator", "10.0.0.0")]
17 | internal sealed partial class Settings : global::System.Configuration.ApplicationSettingsBase
18 | {
19 |
20 | private static Settings defaultInstance = ((Settings)(global::System.Configuration.ApplicationSettingsBase.Synchronized(new Settings())));
21 |
22 | public static Settings Default
23 | {
24 | get
25 | {
26 | return defaultInstance;
27 | }
28 | }
29 | }
30 | }
31 |
--------------------------------------------------------------------------------
/Properties/AssemblyInfo.cs:
--------------------------------------------------------------------------------
1 | using System.Reflection;
2 | using System.Runtime.CompilerServices;
3 | using System.Runtime.InteropServices;
4 |
5 | // General Information about an assembly is controlled through the following
6 | // set of attributes. Change these attribute values to modify the information
7 | // associated with an assembly.
8 | [assembly: AssemblyTitle("ObserverPattern")]
9 | [assembly: AssemblyDescription("")]
10 | [assembly: AssemblyConfiguration("")]
11 | [assembly: AssemblyCompany("")]
12 | [assembly: AssemblyProduct("ObserverPattern")]
13 | [assembly: AssemblyCopyright("Copyright © 2011")]
14 | [assembly: AssemblyTrademark("")]
15 | [assembly: AssemblyCulture("")]
16 |
17 | // Setting ComVisible to false makes the types in this assembly not visible
18 | // to COM components. If you need to access a type in this assembly from
19 | // COM, set the ComVisible attribute to true on that type.
20 | [assembly: ComVisible(false)]
21 |
22 | // The following GUID is for the ID of the typelib if this project is exposed to COM
23 | [assembly: Guid("f2de286b-7337-4fd0-8d39-6d631433c7c7")]
24 |
25 | // Version information for an assembly consists of the following four values:
26 | //
27 | // Major Version
28 | // Minor Version
29 | // Build Number
30 | // Revision
31 | //
32 | // You can specify all the values or you can default the Build and Revision Numbers
33 | // by using the '*' as shown below:
34 | // [assembly: AssemblyVersion("1.0.*")]
35 | [assembly: AssemblyVersion("1.0.0.0")]
36 | [assembly: AssemblyFileVersion("1.0.0.0")]
37 |
--------------------------------------------------------------------------------
/ObserverPattern/Observer/SimpleObserver.Designer.cs:
--------------------------------------------------------------------------------
1 | namespace ObserverPattern.ObserverPattern.Observer
2 | {
3 | partial class SimpleObserver
4 | {
5 | ///
6 | /// Required designer variable.
7 | ///
8 | private System.ComponentModel.IContainer components = null;
9 |
10 | ///
11 | /// Clean up any resources being used.
12 | ///
13 | /// true if managed resources should be disposed; otherwise, false.
14 | protected override void Dispose(bool disposing)
15 | {
16 | if (disposing && (components != null))
17 | {
18 | components.Dispose();
19 | }
20 | base.Dispose(disposing);
21 | }
22 |
23 | #region Windows Form Designer generated code
24 |
25 | ///
26 | /// Required method for Designer support - do not modify
27 | /// the contents of this method with the code editor.
28 | ///
29 | private void InitializeComponent()
30 | {
31 | this.SuspendLayout();
32 | //
33 | // SimpleObserver
34 | //
35 | this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
36 | this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
37 | this.ClientSize = new System.Drawing.Size(263, 167);
38 | this.Name = "SimpleObserver";
39 | this.Text = "Simple Observer";
40 | this.ResumeLayout(false);
41 |
42 | }
43 |
44 | #endregion
45 | }
46 | }
--------------------------------------------------------------------------------
/obj/x86/Debug/ObserverPattern.csproj.FileListAbsolute.txt:
--------------------------------------------------------------------------------
1 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\bin\Debug\ObserverPattern.exe
2 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\bin\Debug\ObserverPattern.pdb
3 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\bin\Debug\Microsoft.VisualBasic.PowerPacks.Vs.dll
4 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\bin\Debug\Microsoft.VisualBasic.PowerPacks.Vs.xml
5 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\obj\x86\Debug\ObserverPattern.csprojResolveAssemblyReference.cache
6 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\obj\x86\Debug\ObserverPattern.BallObserver.resources
7 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\obj\x86\Debug\ObserverPattern.MainForm.resources
8 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\obj\x86\Debug\ObserverPattern.MovingBallObserver.resources
9 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\obj\x86\Debug\ObserverPattern.ObserverPattern.Observer.SimpleObserver.resources
10 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\obj\x86\Debug\ObserverPattern.Properties.Resources.resources
11 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\obj\x86\Debug\ObserverPattern.csproj.GenerateResource.Cache
12 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\obj\x86\Debug\ObserverPattern.exe
13 | E:\Game Engine Programming\ObserverPattern\ObserverPattern\ObserverPattern\obj\x86\Debug\ObserverPattern.pdb
14 |
--------------------------------------------------------------------------------
/MainForm.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.ComponentModel;
4 | using System.Data;
5 | using System.Drawing;
6 | using System.Linq;
7 | using System.Text;
8 | using System.Windows.Forms;
9 | using ObserverPattern.ObserverPattern.Subject;
10 | using ObserverPattern.ObserverPattern.Observer;
11 |
12 | namespace ObserverPattern
13 | {
14 | public partial class MainForm : Form
15 | {
16 | private ColorSubject _subject = new ColorSubject();
17 |
18 | public MainForm()
19 | {
20 | InitializeComponent();
21 |
22 | // Initialize
23 | nextLeft = 0;
24 | ColorCombo.SelectedColor = _subject.Color;
25 | Application.DoEvents();
26 | Add3ObserverForms();
27 | }
28 |
29 | private int nextTop = 0;
30 | private int nextLeft = 0;
31 |
32 | private void Add3ObserverForms()
33 | {
34 | for (int i = 1; i <= 5; i++)
35 | {
36 | SetCommonProperties(new BallObserver());
37 | SetCommonProperties(new SimpleObserver());
38 | SetCommonProperties(new MovingBallObserver());
39 | nextLeft += 300;
40 | nextTop = 0;
41 | }
42 | }
43 |
44 | private void SetCommonProperties(Form form)
45 | {
46 | form.Left = nextLeft;
47 | form.Top = nextTop;
48 | form.StartPosition = FormStartPosition.Manual;
49 | (form as IObserver).ColorChanged(_subject.Color);
50 | form.Show();
51 |
52 | _subject.Register(form as IObserver);
53 |
54 | nextTop += form.Height;
55 | }
56 |
57 | private void ColorCombo_SelectedIndexChanged(object sender, EventArgs e)
58 | {
59 | _subject.Color = ColorCombo.SelectedColor;
60 | }
61 | }
62 | }
63 |
--------------------------------------------------------------------------------
/ObserverPattern/Observer/MovingBallObserver.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.ComponentModel;
4 | using System.Data;
5 | using System.Drawing;
6 | using System.Linq;
7 | using System.Text;
8 | using System.Windows.Forms;
9 | using System.Threading;
10 |
11 | namespace ObserverPattern
12 | {
13 | public partial class MovingBallObserver : Form, IObserver
14 | {
15 | public MovingBallObserver()
16 | {
17 | InitializeComponent();
18 |
19 | Application.DoEvents();
20 | StartThread();
21 | }
22 |
23 | private void StartThread()
24 | {
25 | circleShape1.Left = new Random().Next(this.Width - 100);
26 | circleShape1.Top = new Random().Next(this.Height - 100);
27 |
28 | ThreadStart threadStart = new ThreadStart(MoveBall);
29 | Thread thread = new Thread(threadStart);
30 | thread.Start();
31 | }
32 |
33 | #region IObserver Members
34 |
35 | public void ColorChanged(Color newColor)
36 | {
37 | circleShape1.FillColor = newColor;
38 | }
39 |
40 | #endregion
41 |
42 | private int _changeX = 5, _changeY = 5;
43 |
44 | public void MoveBall()
45 | {
46 | Thread.Sleep(500);
47 | Application.DoEvents();
48 |
49 | while (true)
50 | {
51 | try
52 | {
53 | circleShape1.Left += _changeX;
54 | circleShape1.Top += _changeY;
55 | }catch{}
56 |
57 | if ((circleShape1.Left + circleShape1.Width > this.Width - 15)
58 | ||
59 | (circleShape1.Left < 0))
60 | _changeX = _changeX * (-1);
61 |
62 | if ((circleShape1.Top + circleShape1.Height > this.Height - circleShape1.Height)
63 | ||
64 | (circleShape1.Top < 0))
65 | _changeY = _changeY * (-1);
66 |
67 | Thread.Sleep(50);
68 | }
69 | }
70 | }
71 | }
72 |
--------------------------------------------------------------------------------
/ObserverPattern/Observer/MovingBallObserver.Designer.cs:
--------------------------------------------------------------------------------
1 | using ObserverPattern.Others;
2 | namespace ObserverPattern
3 | {
4 | partial class MovingBallObserver
5 | {
6 | ///
7 | /// Required designer variable.
8 | ///
9 | private System.ComponentModel.IContainer components = null;
10 |
11 | ///
12 | /// Clean up any resources being used.
13 | ///
14 | /// true if managed resources should be disposed; otherwise, false.
15 | protected override void Dispose(bool disposing)
16 | {
17 | if (disposing && (components != null))
18 | {
19 | components.Dispose();
20 | }
21 | base.Dispose(disposing);
22 | }
23 |
24 | #region Windows Form Designer generated code
25 |
26 | ///
27 | /// Required method for Designer support - do not modify
28 | /// the contents of this method with the code editor.
29 | ///
30 | private void InitializeComponent()
31 | {
32 | this.circleShape1 = new CircleShape();
33 | this.SuspendLayout();
34 | //
35 | // circleShape1
36 | //
37 | this.circleShape1.FillColor = System.Drawing.Color.Blue;
38 | this.circleShape1.Location = new System.Drawing.Point(48, 91);
39 | this.circleShape1.Name = "circleShape1";
40 | this.circleShape1.Size = new System.Drawing.Size(49, 41);
41 | this.circleShape1.TabIndex = 0;
42 | this.circleShape1.Text = "circleShape1";
43 | //
44 | // MovingBallObserver
45 | //
46 | this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
47 | this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
48 | this.BackColor = System.Drawing.Color.White;
49 | this.ClientSize = new System.Drawing.Size(276, 193);
50 | this.Controls.Add(this.circleShape1);
51 | this.Name = "MovingBallObserver";
52 | this.Text = "Moving Ball Observer";
53 | this.ResumeLayout(false);
54 |
55 | }
56 |
57 | #endregion
58 |
59 | private Others.CircleShape circleShape1;
60 |
61 | }
62 | }
--------------------------------------------------------------------------------
/Properties/Resources.Designer.cs:
--------------------------------------------------------------------------------
1 | //------------------------------------------------------------------------------
2 | //
3 | // This code was generated by a tool.
4 | // Runtime Version:4.0.30319.225
5 | //
6 | // Changes to this file may cause incorrect behavior and will be lost if
7 | // the code is regenerated.
8 | //
9 | //------------------------------------------------------------------------------
10 |
11 | namespace ObserverPattern.Properties
12 | {
13 |
14 |
15 | ///
16 | /// A strongly-typed resource class, for looking up localized strings, etc.
17 | ///
18 | // This class was auto-generated by the StronglyTypedResourceBuilder
19 | // class via a tool like ResGen or Visual Studio.
20 | // To add or remove a member, edit your .ResX file then rerun ResGen
21 | // with the /str option, or rebuild your VS project.
22 | [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "4.0.0.0")]
23 | [global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
24 | [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]
25 | internal class Resources
26 | {
27 |
28 | private static global::System.Resources.ResourceManager resourceMan;
29 |
30 | private static global::System.Globalization.CultureInfo resourceCulture;
31 |
32 | [global::System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")]
33 | internal Resources()
34 | {
35 | }
36 |
37 | ///
38 | /// Returns the cached ResourceManager instance used by this class.
39 | ///
40 | [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)]
41 | internal static global::System.Resources.ResourceManager ResourceManager
42 | {
43 | get
44 | {
45 | if ((resourceMan == null))
46 | {
47 | global::System.Resources.ResourceManager temp = new global::System.Resources.ResourceManager("ObserverPattern.Properties.Resources", typeof(Resources).Assembly);
48 | resourceMan = temp;
49 | }
50 | return resourceMan;
51 | }
52 | }
53 |
54 | ///
55 | /// Overrides the current thread's CurrentUICulture property for all
56 | /// resource lookups using this strongly typed resource class.
57 | ///
58 | [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)]
59 | internal static global::System.Globalization.CultureInfo Culture
60 | {
61 | get
62 | {
63 | return resourceCulture;
64 | }
65 | set
66 | {
67 | resourceCulture = value;
68 | }
69 | }
70 | }
71 | }
72 |
--------------------------------------------------------------------------------
/ObserverPattern/Observer/BallObserver.Designer.cs:
--------------------------------------------------------------------------------
1 | using ObserverPattern.Others;
2 | namespace ObserverPattern
3 | {
4 | partial class BallObserver
5 | {
6 | ///
7 | /// Required designer variable.
8 | ///
9 | private System.ComponentModel.IContainer components = null;
10 |
11 | ///
12 | /// Clean up any resources being used.
13 | ///
14 | /// true if managed resources should be disposed; otherwise, false.
15 | protected override void Dispose(bool disposing)
16 | {
17 | if (disposing && (components != null))
18 | {
19 | components.Dispose();
20 | }
21 | base.Dispose(disposing);
22 | }
23 |
24 | #region Windows Form Designer generated code
25 |
26 | ///
27 | /// Required method for Designer support - do not modify
28 | /// the contents of this method with the code editor.
29 | ///
30 | private void InitializeComponent()
31 | {
32 | this.circleShape1 = new CircleShape();
33 | this.circleShape2 = new CircleShape();
34 | this.circleShape3 = new CircleShape();
35 | this.SuspendLayout();
36 | //
37 | // circleShape1
38 | //
39 | this.circleShape1.Location = new System.Drawing.Point(12, 12);
40 | this.circleShape1.Name = "circleShape1";
41 | this.circleShape1.Size = new System.Drawing.Size(42, 38);
42 | this.circleShape1.TabIndex = 0;
43 | this.circleShape1.Text = "circleShape1";
44 | //
45 | // circleShape2
46 | //
47 | this.circleShape2.Location = new System.Drawing.Point(170, 23);
48 | this.circleShape2.Name = "circleShape2";
49 | this.circleShape2.Size = new System.Drawing.Size(94, 89);
50 | this.circleShape2.TabIndex = 1;
51 | this.circleShape2.Text = "circleShape2";
52 | //
53 | // circleShape3
54 | //
55 | this.circleShape3.Location = new System.Drawing.Point(68, 116);
56 | this.circleShape3.Name = "circleShape3";
57 | this.circleShape3.Size = new System.Drawing.Size(57, 48);
58 | this.circleShape3.TabIndex = 2;
59 | this.circleShape3.Text = "circleShape3";
60 | //
61 | // BallObserver
62 | //
63 | this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
64 | this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
65 | this.BackColor = System.Drawing.Color.White;
66 | this.ClientSize = new System.Drawing.Size(276, 193);
67 | this.Controls.Add(this.circleShape3);
68 | this.Controls.Add(this.circleShape2);
69 | this.Controls.Add(this.circleShape1);
70 | this.Name = "BallObserver";
71 | this.Text = "Ball Observer";
72 | this.ResumeLayout(false);
73 |
74 | }
75 |
76 | #endregion
77 |
78 | private Others.CircleShape circleShape1;
79 | private Others.CircleShape circleShape2;
80 | private Others.CircleShape circleShape3;
81 |
82 | }
83 | }
--------------------------------------------------------------------------------
/MainForm.Designer.cs:
--------------------------------------------------------------------------------
1 | using ObserverPattern.Others;
2 | namespace ObserverPattern
3 | {
4 | partial class MainForm
5 | {
6 | ///
7 | /// Required designer variable.
8 | ///
9 | private System.ComponentModel.IContainer components = null;
10 |
11 | ///
12 | /// Clean up any resources being used.
13 | ///
14 | /// true if managed resources should be disposed; otherwise, false.
15 | protected override void Dispose(bool disposing)
16 | {
17 | if (disposing && (components != null))
18 | {
19 | components.Dispose();
20 | }
21 | base.Dispose(disposing);
22 | }
23 |
24 | #region Windows Form Designer generated code
25 |
26 | ///
27 | /// Required method for Designer support - do not modify
28 | /// the contents of this method with the code editor.
29 | ///
30 | private void InitializeComponent()
31 | {
32 | System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(MainForm));
33 | this.label1 = new System.Windows.Forms.Label();
34 | this.ColorCombo = new ColorComboBoxApp.ColorComboBox();
35 | this.SuspendLayout();
36 | //
37 | // label1
38 | //
39 | this.label1.AutoSize = true;
40 | this.label1.Location = new System.Drawing.Point(25, 53);
41 | this.label1.Name = "label1";
42 | this.label1.Size = new System.Drawing.Size(71, 13);
43 | this.label1.TabIndex = 2;
44 | this.label1.Text = "Change Color";
45 | //
46 | // ColorCombo
47 | //
48 | this.ColorCombo.DataSource = ((object)(resources.GetObject("ColorCombo.DataSource")));
49 | this.ColorCombo.DrawMode = System.Windows.Forms.DrawMode.OwnerDrawFixed;
50 | this.ColorCombo.DropDownStyle = System.Windows.Forms.ComboBoxStyle.DropDownList;
51 | this.ColorCombo.FormattingEnabled = true;
52 | this.ColorCombo.Location = new System.Drawing.Point(28, 69);
53 | this.ColorCombo.Name = "ColorCombo";
54 | this.ColorCombo.SelectedColor = System.Drawing.Color.WhiteSmoke;
55 | this.ColorCombo.Size = new System.Drawing.Size(166, 21);
56 | this.ColorCombo.TabIndex = 3;
57 | this.ColorCombo.SelectedIndexChanged += new System.EventHandler(this.ColorCombo_SelectedIndexChanged);
58 | //
59 | // MainForm
60 | //
61 | this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
62 | this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
63 | this.BackColor = System.Drawing.Color.WhiteSmoke;
64 | this.ClientSize = new System.Drawing.Size(222, 172);
65 | this.Controls.Add(this.ColorCombo);
66 | this.Controls.Add(this.label1);
67 | this.Name = "MainForm";
68 | this.Text = "Observer Pattern";
69 | this.ResumeLayout(false);
70 | this.PerformLayout();
71 |
72 | }
73 |
74 | #endregion
75 |
76 | private System.Windows.Forms.Label label1;
77 | private ColorComboBoxApp.ColorComboBox ColorCombo;
78 | }
79 | }
80 |
81 |
--------------------------------------------------------------------------------
/Others/ColorComboBox.cs:
--------------------------------------------------------------------------------
1 | using System;
2 | using System.Collections.Generic;
3 | using System.Linq;
4 | using System.Text;
5 | using System.Windows.Forms;
6 | using System.Drawing;
7 | using System.Reflection;
8 | using System.Collections;
9 |
10 | namespace ColorComboBoxApp
11 | {
12 | ///
13 | /// Inherits from existing ComboBox
14 | ///
15 | public class ColorComboBox : ComboBox
16 | {
17 | public ColorComboBox()
18 | {
19 | FillColors();
20 |
21 | // Change DrawMode for custom drawing
22 | this.DrawMode = DrawMode.OwnerDrawFixed;
23 | this.DropDownStyle = ComboBoxStyle.DropDownList;
24 | }
25 |
26 | private void FillColors()
27 | {
28 | if (!DesignMode)
29 | {
30 | this.Items.Clear();
31 | var items = typeof(Color).GetProperties(BindingFlags.Static | BindingFlags.Public).Where(c => c.PropertyType == typeof(Color)).Select(c => (Color)c.GetValue(c, null)).ToList();
32 | foreach (Color color in items)
33 | this.Items.Add(color);
34 | }
35 | }
36 |
37 | ///
38 | /// Override Draw Method
39 | ///
40 | ///
41 | protected override void OnDrawItem(DrawItemEventArgs e)
42 | {
43 | if (e.Index >= 0)
44 | {
45 | Color color = (Color)(this.DataSource as IList)[e.Index];
46 |
47 | int nextX = 0;
48 |
49 | e.Graphics.FillRectangle(new SolidBrush(e.BackColor), e.Bounds);
50 | DrawColor(e, color, ref nextX);
51 | DrawText(e, color, nextX);
52 | }
53 | else
54 | base.OnDrawItem(e);
55 | }
56 |
57 | ///
58 | /// Draw the Color rectangle filled with item color
59 | ///
60 | ///
61 | ///
62 | ///
63 | private void DrawColor(DrawItemEventArgs e, Color color, ref int nextX)
64 | {
65 | int width = e.Bounds.Height * 2 - 8;
66 | Rectangle rectangle = new Rectangle(e.Bounds.X + 3, e.Bounds.Y + 3, width, e.Bounds.Height - 6);
67 | e.Graphics.FillRectangle(new SolidBrush(color), rectangle);
68 |
69 | nextX = width + 8;
70 | }
71 |
72 | ///
73 | /// Draw the color name next to the color rectangle
74 | ///
75 | ///
76 | ///
77 | ///
78 | private void DrawText(DrawItemEventArgs e, Color color, int nextX)
79 | {
80 | e.Graphics.DrawString(color.Name, e.Font, new SolidBrush(e.ForeColor), new PointF(nextX, e.Bounds.Y + (e.Bounds.Height - e.Font.Height) / 2));
81 | }
82 |
83 | ///
84 | /// Gets/sets the selected color of ComboBox
85 | /// (Default color is Black)
86 | ///
87 | public Color SelectedColor
88 | {
89 | get
90 | {
91 | if (this.SelectedItem != null)
92 | return (Color)this.SelectedItem;
93 |
94 | return Color.Black;
95 | }
96 | set
97 | {
98 | int ix = (this.DataSource as IList).IndexOf(value);
99 | if (ix >= 0)
100 | this.SelectedIndex = ix;
101 | }
102 | }
103 | }
104 | }
105 |
--------------------------------------------------------------------------------
/Properties/Resources.resx:
--------------------------------------------------------------------------------
1 |
2 |
3 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 |
101 |
102 |
103 |
104 |
105 |
106 | text/microsoft-resx
107 |
108 |
109 | 2.0
110 |
111 |
112 | System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
113 |
114 |
115 | System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
116 |
117 |
--------------------------------------------------------------------------------
/ObserverPattern.csproj:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | Debug
5 | x86
6 | 8.0.30703
7 | 2.0
8 | {F90988AE-FF29-43E4-920E-BB678A2A7BC4}
9 | WinExe
10 | Properties
11 | ObserverPattern
12 | ObserverPattern
13 | v4.0
14 | Client
15 | 512
16 |
17 |
18 | x86
19 | true
20 | full
21 | false
22 | bin\Debug\
23 | DEBUG;TRACE
24 | prompt
25 | 4
26 |
27 |
28 | x86
29 | pdbonly
30 | true
31 | bin\Release\
32 | TRACE
33 | prompt
34 | 4
35 |
36 |
37 |
38 |
39 |
40 |
41 |
42 |
43 |
44 |
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 | Form
53 |
54 |
55 | BallObserver.cs
56 |
57 |
58 | Form
59 |
60 |
61 | MovingBallObserver.cs
62 |
63 |
64 | Form
65 |
66 |
67 | SimpleObserver.cs
68 |
69 |
70 |
71 |
72 |
73 | Form
74 |
75 |
76 | MainForm.cs
77 |
78 |
79 | Component
80 |
81 |
82 | Component
83 |
84 |
85 |
86 |
87 | BallObserver.cs
88 |
89 |
90 | MainForm.cs
91 |
92 |
93 | MovingBallObserver.cs
94 |
95 |
96 | SimpleObserver.cs
97 |
98 |
99 | ResXFileCodeGenerator
100 | Resources.Designer.cs
101 | Designer
102 |
103 |
104 | True
105 | Resources.resx
106 |
107 |
108 | SettingsSingleFileGenerator
109 | Settings.Designer.cs
110 |
111 |
112 | True
113 | Settings.settings
114 | True
115 |
116 |
117 |
118 |
125 |
--------------------------------------------------------------------------------
/ObserverPattern/Observer/BallObserver.resx:
--------------------------------------------------------------------------------
1 |
2 |
3 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 |
101 |
102 |
103 |
104 |
105 |
106 |
107 |
108 |
109 | text/microsoft-resx
110 |
111 |
112 | 2.0
113 |
114 |
115 | System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
116 |
117 |
118 | System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
119 |
120 |
--------------------------------------------------------------------------------
/ObserverPattern/Observer/SimpleObserver.resx:
--------------------------------------------------------------------------------
1 |
2 |
3 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 |
101 |
102 |
103 |
104 |
105 |
106 |
107 |
108 |
109 | text/microsoft-resx
110 |
111 |
112 | 2.0
113 |
114 |
115 | System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
116 |
117 |
118 | System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
119 |
120 |
--------------------------------------------------------------------------------
/ObserverPattern/Observer/MovingBallObserver.resx:
--------------------------------------------------------------------------------
1 |
2 |
3 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 |
101 |
102 |
103 |
104 |
105 |
106 |
107 |
108 |
109 | text/microsoft-resx
110 |
111 |
112 | 2.0
113 |
114 |
115 | System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
116 |
117 |
118 | System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
119 |
120 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # Real-time Market Data Tracker
2 |
3 | ## :speech_balloon: Intent
4 | ***Real-time Market Data Tracker*** is a sophisticated financial analysis and monitoring system that leverages the Observer design pattern to deliver real-time market data updates to traders, investors, and financial analysts. It is designed to provide a competitive edge in the dynamic world of finance.
5 |
6 | 
7 |
8 | ## :frowning_face: Problem
9 | In the realm of financial markets, the ability to access and respond to real-time market data is paramount. Traders and investors require accurate, timely information to make informed decisions. Conventional methods of monitoring market data, such as manual tracking or email alerts, fall short in delivering the speed and precision demanded by the financial industry.
10 |
11 | 
12 |
13 | ## :blush: Solution
14 | The **Real-time Market Data Tracker** relies on the Observer pattern to provide immediate updates on market data. In this pattern, market data serves as the publisher, while analysis modules, user dashboards, and alert systems act as subscribers. This architecture ensures that users receive instant notifications and updates on market changes, enabling them to stay ahead of the curve.
15 |
16 | 
17 |
18 | ## :car: Real-World
19 | 
20 |
21 | The Observer pattern finds practical use in the financial industry. Just as subscribers receive magazines directly in their mailboxes after subscribing, financial professionals benefit from real-time market data updates delivered to their devices. Subscribers can easily opt in or out of specific updates, allowing for a tailored experience.
22 |
23 | ## :trident: Structure
24 | 
25 |
26 | 1. **Market Data Publisher**: Responsible for issuing events when market data changes. It maintains a subscription infrastructure to manage subscribers.
27 |
28 | 2. **Subscriber Interface**: Declares the notification interface, often consisting of a single update method. All subscribers implement this interface.
29 |
30 | 3. **Concrete Subscribers**: Respond to notifications issued by the market data publisher. Each subscriber class must implement the subscriber interface.
31 |
32 | 4. **Client**: Creates publisher and subscriber objects separately and registers subscribers for market data updates.
33 |
34 | ## :diamond_shape_with_a_dot_inside: Pseudocode
35 | In this example, the Observer pattern allows the market data publisher to notify various analysis modules and user dashboards about changes in market data.
36 |
37 | 
38 |
39 | The subscription list is dynamic, enabling objects to join or leave the list as needed, ensuring flexibility and scalability.
40 |
41 | ```python
42 | # Market data publisher class includes subscription management code and notification methods.
43 | class MarketDataPublisher:
44 | private field subscribers: hash map of event types and listeners
45 |
46 | method subscribe(eventType, listener) is
47 | subscribers.add(eventType, listener)
48 |
49 | method unsubscribe(eventType, listener) is
50 | subscribers.remove(eventType, listener)
51 |
52 | method notify(eventType, data) is
53 | foreach (listener in subscribers.of(eventType)) do
54 | listener.update(data)
55 |
56 | # Concrete market data publisher contains real business logic of tracking market data changes.
57 | class RealTimeMarketDataPublisher:
58 | public field events: MarketDataPublisher
59 | private field marketData: MarketData
60 |
61 | constructor RealTimeMarketDataPublisher() is
62 | events = new MarketDataPublisher()
63 |
64 | method trackMarketData() is
65 | # Logic for tracking market data changes
66 | # ...
67 |
68 | # Subscriber interface declares the notification interface.
69 | interface MarketDataSubscriber:
70 | method update(data)
71 |
72 | # Concrete subscribers respond to market data updates.
73 | class AnalysisModule implements MarketDataSubscriber is
74 | private field analysisData: AnalysisData
75 |
76 | method update(data) is
77 | analysisData.process(data)
78 |
79 | class UserDashboard implements MarketDataSubscriber is
80 | private field user: User
81 |
82 | method update(data) is
83 | user.displayData(data)
84 |
85 | # Client configures publishers and registers subscribers for market data updates.
86 | class FinancialApplication is
87 | method configure() is
88 | marketDataPublisher = new RealTimeMarketDataPublisher()
89 |
90 | analysisModule = new AnalysisModule()
91 | marketDataPublisher.events.subscribe("marketChange", analysisModule)
92 |
93 | userDashboard = new UserDashboard()
94 | marketDataPublisher.events.subscribe("marketChange", userDashboard)
95 | ```
96 |
97 | ## :bulb: Applicability
98 | ### Use the Observer pattern when changes to the state of one object must trigger changes in other objects, and the set
99 |
100 | of objects is not known in advance or changes dynamically.
101 |
102 | This pattern is highly suitable for graphical user interfaces. For example, when creating custom button classes, you can enable clients to attach custom code to buttons, allowing them to respond to button clicks dynamically.
103 |
104 | ### Use the pattern when some objects need to observe others, but only for a limited time or in specific cases.
105 |
106 | The subscription list is dynamic, allowing subscribers to join or leave as needed.
107 |
108 | ## :keyboard: How to Implement
109 |
110 | 1. Analyze your application's business logic to separate the core functionality (the publisher) from other code that will become subscriber classes.
111 |
112 | 2. Declare the subscriber interface, which should include at least a single update method.
113 |
114 | 3. Define the publisher interface with methods for adding and removing subscriber objects from the list. Ensure that publishers interact with subscribers solely through this interface.
115 |
116 | 4. Decide where to place the subscription list and the implementation of subscription methods. Often, this code remains consistent for various publishers, making it suitable for an abstract class derived directly from the publisher interface. Concrete publishers can extend this class to inherit the subscription behavior.
117 |
118 | 5. If applying the pattern to an existing class hierarchy, consider a composition-based approach. Create a separate object responsible for subscription logic and have all publishers use it.
119 |
120 | 6. Develop concrete publisher classes. Whenever a significant event occurs within a publisher, notify all subscribers.
121 |
122 | 7. Implement update notification methods in concrete subscriber classes. Most subscribers will require contextual information about the event, which can be passed as arguments to the notification method. Alternatively, the publisher can pass itself to allow subscribers to fetch necessary data directly.
123 |
124 | 8. The client should create all required subscribers and register them for publisher updates.
125 |
126 | ## :balance_scale: Pros and Cons
127 |
128 | :heavy_check_mark: Open/Closed Principle: You can introduce new subscriber classes without modifying the publisher's code (and vice versa if a publisher interface exists).
129 |
130 | :heavy_check_mark: Dynamic Relationships: Subscribers can join or leave the list as needed.
131 |
132 | :x: Random Notification Order: Subscribers are notified in a random order.
133 |
134 | ## :arrows_counterclockwise: Relations with Other Patterns
135 |
136 | - Chain of Responsibility, Command, Mediator, and Observer all address various methods of connecting senders and receivers of requests:
137 |
138 | - Chain of Responsibility passes a request sequentially along a dynamic chain of potential receivers until one handles it.
139 |
140 | - Command establishes unidirectional connections between senders and receivers.
141 |
142 | - Mediator eliminates direct connections between senders and receivers, forcing communication through a mediator object.
143 |
144 | - Observer enables receivers to dynamically subscribe to and unsubscribe from receiving requests.
145 |
146 | - The distinction between Mediator and Observer can sometimes be blurred. In many cases, you can implement either pattern or even both simultaneously. The primary goal of Mediator is to eliminate mutual dependencies among system components, while Observer allows one-way connections between objects. A popular implementation of Mediator uses Observer, where the mediator acts as the publisher, and components are subscribers. In this configuration, Mediator resembles Observer.
147 |
148 | When in doubt, remember that you can implement Mediator in different ways. For instance, you can permanently link all components to the same mediator object. While this implementation doesn't resemble Observer, it remains a form of the Mediator pattern.
149 |
--------------------------------------------------------------------------------
/MainForm.resx:
--------------------------------------------------------------------------------
1 |
2 |
3 |
62 |
63 |
64 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
81 |
82 |
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
93 |
94 |
95 |
96 |
97 |
98 |
99 |
100 |
101 |
102 |
103 |
104 |
105 |
106 |
107 |
108 |
109 | text/microsoft-resx
110 |
111 |
112 | 2.0
113 |
114 |
115 | System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
116 |
117 |
118 | System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
119 |
120 |
121 |
122 | AAEAAAD/////AQAAAAAAAAAMAgAAAFFTeXN0ZW0uRHJhd2luZywgVmVyc2lvbj00LjAuMC4wLCBDdWx0
123 | dXJlPW5ldXRyYWwsIFB1YmxpY0tleVRva2VuPWIwM2Y1ZjdmMTFkNTBhM2EEAQAAAIwBU3lzdGVtLkNv
124 | bGxlY3Rpb25zLkdlbmVyaWMuTGlzdGAxW1tTeXN0ZW0uRHJhd2luZy5Db2xvciwgU3lzdGVtLkRyYXdp
125 | bmcsIFZlcnNpb249NC4wLjAuMCwgQ3VsdHVyZT1uZXV0cmFsLCBQdWJsaWNLZXlUb2tlbj1iMDNmNWY3
126 | ZjExZDUwYTNhXV0DAAAABl9pdGVtcwVfc2l6ZQhfdmVyc2lvbgQAABZTeXN0ZW0uRHJhd2luZy5Db2xv
127 | cltdAgAAAAgICQMAAACNAAAAjQAAAAcDAAAAAAEAAAAAAQAABBRTeXN0ZW0uRHJhd2luZy5Db2xvcgIA
128 | AAAF/P///xRTeXN0ZW0uRHJhd2luZy5Db2xvcgQAAAAEbmFtZQV2YWx1ZQprbm93bkNvbG9yBXN0YXRl
129 | AQAAAAkHBwIAAAAKAAAAAAAAAAClAAEAAfv////8////CgAAAAAAAAAApgABAAH6/////P///woAAAAA
130 | AAAAAKQAAQAB+f////z///8KAAAAAAAAAAAbAAEAAfj////8////CgAAAAAAAAAAHAABAAH3/////P//
131 | /woAAAAAAAAAAB0AAQAB9v////z///8KAAAAAAAAAAAeAAEAAfX////8////CgAAAAAAAAAAHwABAAH0
132 | /////P///woAAAAAAAAAACAAAQAB8/////z///8KAAAAAAAAAAAhAAEAAfL////8////CgAAAAAAAAAA
133 | IgABAAHx/////P///woAAAAAAAAAACMAAQAB8P////z///8KAAAAAAAAAAAkAAEAAe/////8////CgAA
134 | AAAAAAAAJQABAAHu/////P///woAAAAAAAAAACYAAQAB7f////z///8KAAAAAAAAAAAnAAEAAez////8
135 | ////CgAAAAAAAAAAKAABAAHr/////P///woAAAAAAAAAACkAAQAB6v////z///8KAAAAAAAAAAAqAAEA
136 | Aen////8////CgAAAAAAAAAAKwABAAHo/////P///woAAAAAAAAAACwAAQAB5/////z///8KAAAAAAAA
137 | AAAtAAEAAeb////8////CgAAAAAAAAAALgABAAHl/////P///woAAAAAAAAAAC8AAQAB5P////z///8K
138 | AAAAAAAAAAAwAAEAAeP////8////CgAAAAAAAAAAMQABAAHi/////P///woAAAAAAAAAADIAAQAB4f//
139 | //z///8KAAAAAAAAAAAzAAEAAeD////8////CgAAAAAAAAAANAABAAHf/////P///woAAAAAAAAAADUA
140 | AQAB3v////z///8KAAAAAAAAAAA2AAEAAd3////8////CgAAAAAAAAAANwABAAHc/////P///woAAAAA
141 | AAAAADgAAQAB2/////z///8KAAAAAAAAAAA5AAEAAdr////8////CgAAAAAAAAAAOgABAAHZ/////P//
142 | /woAAAAAAAAAADsAAQAB2P////z///8KAAAAAAAAAAA8AAEAAdf////8////CgAAAAAAAAAAPQABAAHW
143 | /////P///woAAAAAAAAAAD4AAQAB1f////z///8KAAAAAAAAAAA/AAEAAdT////8////CgAAAAAAAAAA
144 | QAABAAHT/////P///woAAAAAAAAAAEEAAQAB0v////z///8KAAAAAAAAAABCAAEAAdH////8////CgAA
145 | AAAAAAAAQwABAAHQ/////P///woAAAAAAAAAAEQAAQABz/////z///8KAAAAAAAAAABFAAEAAc7////8
146 | ////CgAAAAAAAAAARgABAAHN/////P///woAAAAAAAAAAEcAAQABzP////z///8KAAAAAAAAAABIAAEA
147 | Acv////8////CgAAAAAAAAAASQABAAHK/////P///woAAAAAAAAAAEoAAQAByf////z///8KAAAAAAAA
148 | AABLAAEAAcj////8////CgAAAAAAAAAATAABAAHH/////P///woAAAAAAAAAAE0AAQABxv////z///8K
149 | AAAAAAAAAABOAAEAAcX////8////CgAAAAAAAAAATwABAAHE/////P///woAAAAAAAAAAFAAAQABw///
150 | //z///8KAAAAAAAAAABRAAEAAcL////8////CgAAAAAAAAAAUgABAAHB/////P///woAAAAAAAAAAFMA
151 | AQABwP////z///8KAAAAAAAAAABUAAEAAb/////8////CgAAAAAAAAAAVQABAAG+/////P///woAAAAA
152 | AAAAAFYAAQABvf////z///8KAAAAAAAAAABXAAEAAbz////8////CgAAAAAAAAAAWAABAAG7/////P//
153 | /woAAAAAAAAAAFkAAQABuv////z///8KAAAAAAAAAABaAAEAAbn////8////CgAAAAAAAAAAWwABAAG4
154 | /////P///woAAAAAAAAAAFwAAQABt/////z///8KAAAAAAAAAABdAAEAAbb////8////CgAAAAAAAAAA
155 | XgABAAG1/////P///woAAAAAAAAAAGAAAQABtP////z///8KAAAAAAAAAABfAAEAAbP////8////CgAA
156 | AAAAAAAAYQABAAGy/////P///woAAAAAAAAAAGIAAQABsf////z///8KAAAAAAAAAABjAAEAAbD////8
157 | ////CgAAAAAAAAAAZAABAAGv/////P///woAAAAAAAAAAGUAAQABrv////z///8KAAAAAAAAAABmAAEA
158 | Aa3////8////CgAAAAAAAAAAZwABAAGs/////P///woAAAAAAAAAAGgAAQABq/////z///8KAAAAAAAA
159 | AABpAAEAAar////8////CgAAAAAAAAAAagABAAGp/////P///woAAAAAAAAAAGsAAQABqP////z///8K
160 | AAAAAAAAAABsAAEAAaf////8////CgAAAAAAAAAAbQABAAGm/////P///woAAAAAAAAAAG4AAQABpf//
161 | //z///8KAAAAAAAAAABvAAEAAaT////8////CgAAAAAAAAAAcAABAAGj/////P///woAAAAAAAAAAHEA
162 | AQABov////z///8KAAAAAAAAAAByAAEAAaH////8////CgAAAAAAAAAAcwABAAGg/////P///woAAAAA
163 | AAAAAHQAAQABn/////z///8KAAAAAAAAAAB1AAEAAZ7////8////CgAAAAAAAAAAdgABAAGd/////P//
164 | /woAAAAAAAAAAHcAAQABnP////z///8KAAAAAAAAAAB4AAEAAZv////8////CgAAAAAAAAAAeQABAAGa
165 | /////P///woAAAAAAAAAAHoAAQABmf////z///8KAAAAAAAAAAB7AAEAAZj////8////CgAAAAAAAAAA
166 | fAABAAGX/////P///woAAAAAAAAAAH0AAQABlv////z///8KAAAAAAAAAAB+AAEAAZX////8////CgAA
167 | AAAAAAAAfwABAAGU/////P///woAAAAAAAAAAIAAAQABk/////z///8KAAAAAAAAAACBAAEAAZL////8
168 | ////CgAAAAAAAAAAggABAAGR/////P///woAAAAAAAAAAIMAAQABkP////z///8KAAAAAAAAAACEAAEA
169 | AY/////8////CgAAAAAAAAAAhQABAAGO/////P///woAAAAAAAAAAIYAAQABjf////z///8KAAAAAAAA
170 | AACHAAEAAYz////8////CgAAAAAAAAAAiAABAAGL/////P///woAAAAAAAAAAIkAAQABiv////z///8K
171 | AAAAAAAAAACKAAEAAYn////8////CgAAAAAAAAAAiwABAAGI/////P///woAAAAAAAAAAIwAAQABh///
172 | //z///8KAAAAAAAAAACNAAEAAYb////8////CgAAAAAAAAAAjgABAAGF/////P///woAAAAAAAAAAI8A
173 | AQABhP////z///8KAAAAAAAAAACQAAEAAYP////8////CgAAAAAAAAAAkQABAAGC/////P///woAAAAA
174 | AAAAAJIAAQABgf////z///8KAAAAAAAAAACTAAEAAYD////8////CgAAAAAAAAAAlAABAAF//////P//
175 | /woAAAAAAAAAAJUAAQABfv////z///8KAAAAAAAAAACWAAEAAX3////8////CgAAAAAAAAAAlwABAAF8
176 | /////P///woAAAAAAAAAAJgAAQABe/////z///8KAAAAAAAAAACZAAEAAXr////8////CgAAAAAAAAAA
177 | mgABAAF5/////P///woAAAAAAAAAAJsAAQABeP////z///8KAAAAAAAAAACcAAEAAXf////8////CgAA
178 | AAAAAAAAnQABAAF2/////P///woAAAAAAAAAAJ4AAQABdf////z///8KAAAAAAAAAACfAAEAAXT////8
179 | ////CgAAAAAAAAAAoAABAAFz/////P///woAAAAAAAAAAKEAAQABcv////z///8KAAAAAAAAAACiAAEA
180 | AXH////8////CgAAAAAAAAAAowABAAFw/////P///woAAAAAAAAAAKcAAQABb/////z///8KAAAAAAAA
181 | AAAAAAAAAW7////8////CgAAAAAAAAAAAAAAAAFt/////P///woAAAAAAAAAAAAAAAABbP////z///8K
182 | AAAAAAAAAAAAAAAAAWv////8////CgAAAAAAAAAAAAAAAAFq/////P///woAAAAAAAAAAAAAAAABaf//
183 | //z///8KAAAAAAAAAAAAAAAAAWj////8////CgAAAAAAAAAAAAAAAAFn/////P///woAAAAAAAAAAAAA
184 | AAABZv////z///8KAAAAAAAAAAAAAAAAAWX////8////CgAAAAAAAAAAAAAAAAFk/////P///woAAAAA
185 | AAAAAAAAAAABY/////z///8KAAAAAAAAAAAAAAAAAWL////8////CgAAAAAAAAAAAAAAAAFh/////P//
186 | /woAAAAAAAAAAAAAAAABYP////z///8KAAAAAAAAAAAAAAAAAV/////8////CgAAAAAAAAAAAAAAAAFe
187 | /////P///woAAAAAAAAAAAAAAAABXf////z///8KAAAAAAAAAAAAAAAAAVz////8////CgAAAAAAAAAA
188 | AAAAAAFb/////P///woAAAAAAAAAAAAAAAABWv////z///8KAAAAAAAAAAAAAAAAAVn////8////CgAA
189 | AAAAAAAAAAAAAAFY/////P///woAAAAAAAAAAAAAAAABV/////z///8KAAAAAAAAAAAAAAAAAVb////8
190 | ////CgAAAAAAAAAAAAAAAAFV/////P///woAAAAAAAAAAAAAAAABVP////z///8KAAAAAAAAAAAAAAAA
191 | AVP////8////CgAAAAAAAAAAAAAAAAFS/////P///woAAAAAAAAAAAAAAAABUf////z///8KAAAAAAAA
192 | AAAAAAAAAVD////8////CgAAAAAAAAAAAAAAAAFP/////P///woAAAAAAAAAAAAAAAABTv////z///8K
193 | AAAAAAAAAAAAAAAAAU3////8////CgAAAAAAAAAAAAAAAAFM/////P///woAAAAAAAAAAAAAAAABS///
194 | //z///8KAAAAAAAAAAAAAAAAAUr////8////CgAAAAAAAAAAAAAAAAFJ/////P///woAAAAAAAAAAAAA
195 | AAABSP////z///8KAAAAAAAAAAAAAAAAAUf////8////CgAAAAAAAAAAAAAAAAFG/////P///woAAAAA
196 | AAAAAAAAAAABRf////z///8KAAAAAAAAAAAAAAAAAUT////8////CgAAAAAAAAAAAAAAAAFD/////P//
197 | /woAAAAAAAAAAAAAAAABQv////z///8KAAAAAAAAAAAAAAAAAUH////8////CgAAAAAAAAAAAAAAAAFA
198 | /////P///woAAAAAAAAAAAAAAAABP/////z///8KAAAAAAAAAAAAAAAAAT7////8////CgAAAAAAAAAA
199 | AAAAAAE9/////P///woAAAAAAAAAAAAAAAABPP////z///8KAAAAAAAAAAAAAAAAATv////8////CgAA
200 | AAAAAAAAAAAAAAE6/////P///woAAAAAAAAAAAAAAAABOf////z///8KAAAAAAAAAAAAAAAAATj////8
201 | ////CgAAAAAAAAAAAAAAAAE3/////P///woAAAAAAAAAAAAAAAABNv////z///8KAAAAAAAAAAAAAAAA
202 | ATX////8////CgAAAAAAAAAAAAAAAAE0/////P///woAAAAAAAAAAAAAAAABM/////z///8KAAAAAAAA
203 | AAAAAAAAATL////8////CgAAAAAAAAAAAAAAAAEx/////P///woAAAAAAAAAAAAAAAABMP////z///8K
204 | AAAAAAAAAAAAAAAAAS/////8////CgAAAAAAAAAAAAAAAAEu/////P///woAAAAAAAAAAAAAAAABLf//
205 | //z///8KAAAAAAAAAAAAAAAAASz////8////CgAAAAAAAAAAAAAAAAEr/////P///woAAAAAAAAAAAAA
206 | AAABKv////z///8KAAAAAAAAAAAAAAAAASn////8////CgAAAAAAAAAAAAAAAAEo/////P///woAAAAA
207 | AAAAAAAAAAABJ/////z///8KAAAAAAAAAAAAAAAAASb////8////CgAAAAAAAAAAAAAAAAEl/////P//
208 | /woAAAAAAAAAAAAAAAABJP////z///8KAAAAAAAAAAAAAAAAASP////8////CgAAAAAAAAAAAAAAAAEi
209 | /////P///woAAAAAAAAAAAAAAAABIf////z///8KAAAAAAAAAAAAAAAAASD////8////CgAAAAAAAAAA
210 | AAAAAAEf/////P///woAAAAAAAAAAAAAAAABHv////z///8KAAAAAAAAAAAAAAAAAR3////8////CgAA
211 | AAAAAAAAAAAAAAEc/////P///woAAAAAAAAAAAAAAAABG/////z///8KAAAAAAAAAAAAAAAAARr////8
212 | ////CgAAAAAAAAAAAAAAAAEZ/////P///woAAAAAAAAAAAAAAAABGP////z///8KAAAAAAAAAAAAAAAA
213 | ARf////8////CgAAAAAAAAAAAAAAAAEW/////P///woAAAAAAAAAAAAAAAABFf////z///8KAAAAAAAA
214 | AAAAAAAAART////8////CgAAAAAAAAAAAAAAAAET/////P///woAAAAAAAAAAAAAAAABEv////z///8K
215 | AAAAAAAAAAAAAAAAARH////8////CgAAAAAAAAAAAAAAAAEQ/////P///woAAAAAAAAAAAAAAAABD///
216 | //z///8KAAAAAAAAAAAAAAAAAQ7////8////CgAAAAAAAAAAAAAAAAEN/////P///woAAAAAAAAAAAAA
217 | AAABDP////z///8KAAAAAAAAAAAAAAAAAQv////8////CgAAAAAAAAAAAAAAAAEK/////P///woAAAAA
218 | AAAAAAAAAAABCf////z///8KAAAAAAAAAAAAAAAAAQj////8////CgAAAAAAAAAAAAAAAAEH/////P//
219 | /woAAAAAAAAAAAAAAAABBv////z///8KAAAAAAAAAAAAAAAAAQX////8////CgAAAAAAAAAAAAAAAAEE
220 | /////P///woAAAAAAAAAAAAAAAABA/////z///8KAAAAAAAAAAAAAAAAAQL////8////CgAAAAAAAAAA
221 | AAAAAAEB/////P///woAAAAAAAAAAAAAAAABAP////z///8KAAAAAAAAAAAAAAAAAf/+///8////CgAA
222 | AAAAAAAAAAAAAAH+/v///P///woAAAAAAAAAAAAAAAAB/f7///z///8KAAAAAAAAAAAAAAAACw==
223 |
224 |
225 |
--------------------------------------------------------------------------------