Skip to content

Instantly share code, notes, and snippets.

@mrtank
Created September 28, 2016 12:57
Show Gist options
  • Save mrtank/c33d43bf3b9033930d5bdb928a8145ad to your computer and use it in GitHub Desktop.
Save mrtank/c33d43bf3b9033930d5bdb928a8145ad to your computer and use it in GitHub Desktop.
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
Drawer drawer = new Drawer();
//MyTree.Items.Add(new Link(new CollectionInformation(new List<IElement>())));
MyTree.Items.Add(
new CollectionInformation(new List<IElement>
{
new Link(new CollectionInformation(new List<IElement> {new Link(new Circle(drawer))})),
new Link(null)}
));
((IDrawable)MyTree.Items[0]).Draw();
}
}
public class Circle: ICircleElement
{
private readonly Drawer _drawer;
public Circle(Drawer drawer)
{
_drawer = drawer;
}
public string ElementName
{
get { return "Circle"; }
set { throw new NotImplementedException(); }
}
public string ElementDescription
{
get { return "Circle desc"; }
set { throw new NotImplementedException(); }
}
public void DoUpdate(object arg)
{
// ...
}
public double Radius { get; set; }
public void Draw()
{
_drawer.Draw(this as dynamic);
}
}
public interface ICircleElement: IElement, ICircleInformation
{
}
// common interface. All node uses this.
public interface IElement: IDrawable
{
string ElementName { get; set; }
string ElementDescription { get; set; }
void DoUpdate(object arg);
}
public interface IDrawable
{
void Draw();
}
public interface ICircleInformation
{
double Radius { get; set; }
}
public class Drawer
{
public void Draw(Circle thingToDraw)
{
Console.WriteLine("I have just drawed a circle with radius: " + thingToDraw.Radius);
}
public void Draw(IElement anythingElse)
{
Console.WriteLine("Can't infere type");
}
}
public class Link : ILink
{
// IObs is constructor injected. Still I from SOLID
//private readonly IObs _obs;
public Link(IElement referencedElement/* , IObs obs */)
{
ReferencedElement = referencedElement;
//_obs = obs;
Click = new RelayCommand(UpdateLink, _ => true);
}
public string ElementName { get; set; } = "Link";
public string ElementDescription { get; set; } = "It is a link";
public IElement ReferencedElement { get; }
// needed for WPF ItemsSource. We should not add this.
public List<IElement> Children
{
get { return new List<IElement> {ReferencedElement}; }
}
public ICommand Click { get; private set; }
public void UpdateLink(object arg)
{
// now comes the real question. What we expect of an IElement. Should it have DoUpdate, which propagates further
// or check the next step ourselfs
// ILink referencedElement = ReferencedElement as ILink;
// if (referencedElement != null)
// {
// referencedElement.UpdateLink(arg);
// }
// propagation through external observer
if (ReferencedElement == null)
return;
//_obs.Notify(this, arg);
DoUpdate(arg);
}
public void DoUpdate(object arg)
{
Console.WriteLine("I did stuff");
}
public void Draw()
{
if (ReferencedElement != null)
{
ReferencedElement.Draw();
}
}
}
// I from SOLID. Link shows only the reachable property and method. User doesn't have to know about click, and other stuff.
public interface ILink : IElement
{
IElement ReferencedElement { get; }
void UpdateLink(object arg);
}
public class CollectionInformation : ICollectionInformation
{
public CollectionInformation(List<IElement> children)
{
ListOfChildren = children;
}
public List<IElement> ListOfChildren { get; }
public string ElementName { get; set; } = "Collection info";
public string ElementDescription { get; set; } = "desc";
public void DoUpdate(object arg)
{
Console.WriteLine("I did stuff");
}
public void Draw()
{
foreach (IElement element in ListOfChildren)
{
element.Draw();
}
}
}
// extended functionality type 2
public interface ICollectionInformation: IElement
{
List<IElement> ListOfChildren { get; }
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment