-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Border Background="{./Background}" Foreground="{./Foreground}"
CornerRadius="{./CornerRadius}" BorderWidth="1">
<HorizontalStack Spacing="0">
<HueSelector Hue="{²./H}" Focusable="true" Name="hueSelector" Margin="0" Width="128" Height="20"/>
</VerticalStack>
<VerticalStack Margin="5" Spacing="1">
- <GraphicObject Width="34" Height="21" Background="{./SelectedColor}"/>
+ <Widget Width="34" Height="21" Background="{./SelectedColor}"/>
<Label Focusable="true" Selectable="true" Text="{./SelectedColor}" />
<HorizontalStack Height="Fit">
<Label Text="R" Width="Fit"/>
</VerticalStack>
</Template>
<HorizontalStack Height="Fit">
- <GraphicObject Width="12" Height="10"/>
+ <Widget Width="12" Height="10"/>
<VerticalStack Height="Fit" Name="ItemsContainer"/>
</HorizontalStack>
</Expandable>
-<?xml version="1.0"?>
-<!--<GraphicObject Background="{./Background}"/>-->
+<?xml version="1.0"?>
+<!--<Widget Background="{./Background}"/>-->
<Border BorderWidth="1" Foreground="Black" CornerRadius="{./CornerRadius}"
Background="{./Background}"
MouseEnter="./onBorderMouseEnter"
</HorizontalStack>
<HorizontalStack Background="vgradient|0:0.5,0.6,0.5,0.5|1:0.2,0.3,0.3,0.7"
Name="hs" Margin="0" Spacing="0" Height="Fit" Visible="{./IsFloating}">
- <GraphicObject Width="5"/>
+ <Widget Width="5"/>
<Image Margin="1" Width="10" Height="10" Path="{./Icon}"/>
<Label Width="Stretched" Foreground="White" Margin="1" TextAlignment="Left" Text="{./Caption}" />
<Border CornerRadius="6" BorderWidth="1" Foreground="Transparent" Height="10" Width="10"
<Image Focusable="true" Name="Image" Margin="0" Path="#Crow.Icons.exit2.svg"
MouseClick="./butQuitPress"/>
</Border>
- <GraphicObject Width="5"/>
+ <Widget Width="5"/>
</HorizontalStack>
<Container Name="Content" MinimumSize="50,50"/>
</VerticalStack>
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Border BorderWidth="1" Foreground="White" CornerRadius="{./CornerRadius}"
Background="{./Background}"
MouseEnter="./onBorderMouseEnter"
<VerticalStack Spacing="0">
<HorizontalStack Background="{./TitleBarBackground}"
Name="hs" Margin="2" Spacing="0" Height="Fit">
- <GraphicObject Width="5"/>
+ <Widget Width="5"/>
<Image Margin="1" Width="12" Height="12" Path="{./Icon}"/>
<Label Width="Stretched" Foreground="{./TitleBarForeground}" Margin="1" TextAlignment="Center" Text="{./Caption}" />
<Border CornerRadius="0" BorderWidth="1" Foreground="Transparent" Height="12" Width="12"
<Image Focusable="true" Name="Image" Margin="0" Width="Stretched" Height="Stretched" Path="#Crow.Icons.exit2.svg"
MouseClick="./butQuitPress"/>
</Border>
- <GraphicObject Width="5"/>
+ <Widget Width="5"/>
</HorizontalStack>
<Container Name="Content" MinimumSize="50,50" Background="Jet">
<VerticalStack Margin="1">
<ItemTemplate>
- <GraphicObject Height="16" Background="Red"/>
+ <Widget Height="16" Background="Red"/>
</ItemTemplate>
<ItemTemplate DataType="System.IO.FileInfo">
<HorizontalStack Focusable="true" Height="Fit">
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Container Background="{./Background}">
<Group>
<VerticalStack Spacing="0">
- <GraphicObject Height="6"/>
+ <Widget Height="6"/>
<Border CornerRadius="5" BorderWidth="1" Margin="10" Foreground="{./Foreground}">
<Container Name="Content" Margin="0" MinimumSize="70,10"/>
</Border>
<VerticalStack Name="ItemsContainer"/>
</Border>
</Popper>
-<GraphicObject Background="Green" Width="5" Height="5" Visible="{./AutomaticOpening}"/>
+<Widget Background="Green" Width="5" Height="5" Visible="{./AutomaticOpening}"/>
</HorizontalStack>
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Border CornerRadius="0"
MouseEnter="./onBorderMouseEnter"
MouseLeave="./onBorderMouseLeave">
<Border BorderWidth="0" Foreground="White" Height="Fit" Width="Stretched" MinimumSize="200,0"
Background="{./TitleBarBackground}">
<HorizontalStack Name="hs" Margin="2" Spacing="1" Height="Fit" >
- <GraphicObject Width="5" Height="5"/>
+ <Widget Width="5" Height="5"/>
<Image Margin="1" Width="12" Height="12" Path="{./Icon}"/>
<Label Width="Stretched" Foreground="{./TitleBarForeground}" Margin="1" TextAlignment="Center" Text="{./Caption}" />
<Border CornerRadius="3" BorderWidth="1" Foreground="Transparent" Height="12" Width="12"
<Image Focusable="true" Name="Image" Path="#Crow.Icons.exit2.svg"
MouseClick="./butQuitPress"/>
</Border>
- <GraphicObject Width="5" Height="5"/>
+ <Widget Width="5" Height="5"/>
</HorizontalStack>
</Border>
<HorizontalStack Margin="5" >
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Border BorderWidth="1" Foreground="White" CornerRadius="{./CornerRadius}"
Background="{./Background}"
MouseEnter="./onBorderMouseEnter"
Background="vgradient|0:0.4,0.6,0.0,0.5|1:0.0,0.8,0.8,0.9">-->
<HorizontalStack Background="{./TitleBarBackground}"
Name="hs" Margin="2" Spacing="0" Height="Fit">
- <GraphicObject Width="5"/>
+ <Widget Width="5"/>
<Image Margin="1" Width="12" Height="12" Path="{./Icon}"/>
<Label Width="Stretched" Foreground="{./TitleBarForeground}" Margin="1" TextAlignment="Center" Text="{./Caption}" />
<Border CornerRadius="6" BorderWidth="1" Foreground="Transparent" Height="12" Width="12"
<Image Focusable="true" Name="Image" Margin="0" Width="Stretched" Height="Stretched" Path="#Crow.Icons.exit2.svg"
MouseClick="./butQuitPress"/>
</Border>
- <GraphicObject Width="5"/>
+ <Widget Width="5"/>
</HorizontalStack>
<!-- </Border>-->
<Container Name="Content" MinimumSize="50,50" Background="0.5,0.5,0.5,0.5"/>
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Border BorderWidth="1" Foreground="Grey" CornerRadius="{./CornerRadius}"
Background="{./Background}"
MouseEnter="./onBorderMouseEnter"
Background="vgradient|0:0.4,0.6,0.0,0.5|1:0.0,0.8,0.8,0.9">-->
<HorizontalStack Background="{./TitleBarBackground}"
Name="hs" Margin="2" Spacing="0" Height="Fit">
- <GraphicObject Width="5"/>
+ <Widget Width="5"/>
<Image Margin="1" Width="12" Height="12" Path="{./Icon}"/>
<Label Width="Stretched" Foreground="{./TitleBarForeground}" Margin="2" TextAlignment="Center" Text="{./Caption}" />
<Border Visible="{./ShowMinimize}" BorderWidth="1" Foreground="Transparent" Height="12" Width="12"
<Image Focusable="true" Path="#Crow.Icons.exit2.svg"
MouseClick="./butQuitPress"/>
</Border>
- <GraphicObject Width="5"/>
+ <Widget Width="5"/>
</HorizontalStack>
<!-- </Border>-->
<Container Name="Content" MinimumSize="0,0" Background="0.5,0.5,0.5,0.5"/>
/// </summary>
public class BubblingMouseButtonEventArg: MouseButtonEventArgs
{
- public GraphicObject Focused;
+ public Widget Focused;
public BubblingMouseButtonEventArg(MouseButtonEventArgs mbe) : base(mbe){}
public BubblingMouseButtonEventArg(int x, int y, MouseButton button, bool pressed)
: base (x,y,button,pressed){}
internal static MethodInfo miDSChangeEmitHelper = typeof(Instantiator).GetMethod("dataSourceChangedEmitHelper", BindingFlags.Instance | BindingFlags.NonPublic);
internal static MethodInfo miDSReverseBinding = typeof(Instantiator).GetMethod("dataSourceReverseBinding", BindingFlags.Static | BindingFlags.NonPublic);
- internal static FieldInfo miSetCurIface = typeof(GraphicObject).GetField ("IFace", BindingFlags.Public | BindingFlags.Instance);
- internal static MethodInfo miFindByName = typeof (GraphicObject).GetMethod ("FindByName");
- internal static MethodInfo miGetGObjItem = typeof(List<GraphicObject>).GetMethod("get_Item", new Type[] { typeof(Int32) });
- internal static MethodInfo miLoadDefaultVals = typeof (GraphicObject).GetMethod ("loadDefaultValues");
- internal static PropertyInfo piStyle = typeof (GraphicObject).GetProperty ("Style");
- internal static MethodInfo miGetLogicalParent = typeof(GraphicObject).GetProperty("LogicalParent").GetGetMethod();
- internal static MethodInfo miGetDataSource = typeof(GraphicObject).GetProperty("DataSource").GetGetMethod ();
- internal static EventInfo eiLogicalParentChanged = typeof(GraphicObject).GetEvent("LogicalParentChanged");
+ internal static FieldInfo miSetCurIface = typeof(Widget).GetField ("IFace", BindingFlags.Public | BindingFlags.Instance);
+ internal static MethodInfo miFindByName = typeof (Widget).GetMethod ("FindByName");
+ internal static MethodInfo miGetGObjItem = typeof(List<Widget>).GetMethod("get_Item", new Type[] { typeof(Int32) });
+ internal static MethodInfo miLoadDefaultVals = typeof (Widget).GetMethod ("loadDefaultValues");
+ internal static PropertyInfo piStyle = typeof (Widget).GetProperty ("Style");
+ internal static MethodInfo miGetLogicalParent = typeof(Widget).GetProperty("LogicalParent").GetGetMethod();
+ internal static MethodInfo miGetDataSource = typeof(Widget).GetProperty("DataSource").GetGetMethod ();
+ internal static EventInfo eiLogicalParentChanged = typeof(Widget).GetEvent("LogicalParentChanged");
internal static MethodInfo miIFaceLoad = typeof(Interface).GetMethod ("CreateInstance", BindingFlags.Instance | BindingFlags.Public);
internal static MethodInfo miIFaceCreateTemplateInst = typeof (Interface).GetMethod ("CreateTemplateInstance", BindingFlags.Instance | BindingFlags.Public);
internal static FieldInfo fiVCMbName = typeof (ValueChangeEventArgs).GetField ("MemberName");
internal static MethodInfo miValueChangeAdd = eiValueChange.GetAddMethod ();
- internal static EventInfo eiDSChange = typeof (GraphicObject).GetEvent ("DataSourceChanged");
+ internal static EventInfo eiDSChange = typeof (Widget).GetEvent ("DataSourceChanged");
internal static MethodInfo miInvokeDSChange = eiDSChange.EventHandlerType.GetMethod ("Invoke");
internal static Type [] argsBoundDSChange = {typeof (object), typeof (object), miInvokeDSChange.GetParameters () [1].ParameterType };
internal static FieldInfo fiDSCNewDS = typeof (DataSourceChangeEventArgs).GetField ("NewDataSource");
//if left operand is member of current node, it's easy to fetch type, else we should use reflexion in msil
if (lopPI == null){//accept GraphicObj members, but it's restricive
//TODO: we should get the parse method by reflexion, or something else
- lopPI = typeof(GraphicObject).GetProperty (lop.Tokens [lop.Tokens.Length-1]);
+ lopPI = typeof(Widget).GetProperty (lop.Tokens [lop.Tokens.Length-1]);
if (lopPI == null)
throw new NotSupportedException ();
}
public bool cancelRequested = false;
Thread thread;
public event EventHandler Finished;
- public GraphicObject Host;
- public CrowThread (GraphicObject host, ThreadStart start){
+ public Widget Host;
+ public CrowThread (Widget host, ThreadStart start){
thread = new Thread (start);
thread.IsBackground = true;
Host = host;
/// <summary>
/// Source of the drag and drop operation
/// </summary>
- public GraphicObject DragSource;
+ public Widget DragSource;
/// <summary>
/// Target of the drag and drop operation
/// </summary>
- public GraphicObject DropTarget;
+ public Widget DropTarget;
//public DragDropEventArgs (GraphicObject source, GraphicObject target = null) : base()
- public DragDropEventArgs (GraphicObject source = null, GraphicObject target = null) : base()
+ public DragDropEventArgs (Widget source = null, Widget target = null) : base()
{
DragSource = source;
DropTarget = target;
{
public class DynAttribute
{
- public GraphicObject Source;
+ public Widget Source;
public string MemberName;
public String Value;
}
public FontSlant Slant {
get{
switch (Style) {
- case FontStyle.Normal:
- default:
- return FontSlant.Normal;
case FontStyle.Italic:
return FontSlant.Italic;
- }
+ default:
+ return FontSlant.Normal;
+ }
}
}
public FontWeight Wheight {
switch (Style) {
case FontStyle.Bold:
return FontWeight.Bold;
- case FontStyle.Italic:
- case FontStyle.Normal:
default:
return FontWeight.Normal;
}
public override string ToString()
{
- if (_style == FontStyle.Normal)
- return string.Format("{0},{1}", _name, _size);
- else
- return string.Format("{0} {1},{2}", _name, _style, _size);
+
+ return (_style == FontStyle.Normal) ? $"{_name},{_size}" : $"{_name} {_style},{_size}";
}
/// simple squarred rgb color selector
/// </summary>
[DesignIgnore]
- public class ColorSelector : GraphicObject
+ public class ColorSelector : Widget
{
#region CTOR
protected ColorSelector() : base(){}
public Container (Interface iface) : base(iface){}
#endregion
- [XmlIgnore]public GraphicObject Child {
+ [XmlIgnore]public Widget Child {
get { return child; }
set { base.SetChild(value); }
}
/// override this to handle specific steps in child addition in derived class,
/// and don't forget to call the base.SetChild
/// </summary>
- public virtual void SetChild(GraphicObject _child)
+ public virtual void SetChild(Widget _child)
{
base.SetChild (_child);
}
base.onInitialized (sender, e);
Background = Color.ColorDic.Values.ToList()[color++];
}*/
- public override void AddChild (GraphicObject g)
+ public override void AddChild (Widget g)
{
base.AddChild (g);
if (localLogicalParentIsNull)
else
g.LogicalParent = this.LogicalParent;
}
- public override void InsertChild (int idx, GraphicObject g)
+ public override void InsertChild (int idx, Widget g)
{
base.InsertChild (idx, g);
g.LogicalParent = this.LogicalParent;
Rectangle rIn = default(Rectangle);
double dockThresh = 0.2;
- GraphicObject focusedChild;
- internal GraphicObject stretchedChild;
+ Widget focusedChild;
+ internal Widget stretchedChild;
void getFocusedChild (Point lm) {
Rectangle cb = ClientRectangle;
childrenRWLock.EnterReadLock ();
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
Rectangle bounds = c.Slot + cb.Position;
if (!bounds.ContainsOrIsEqual (lm))
continue;
childrenRWLock.EnterReadLock ();
- foreach (GraphicObject g in Children)
+ foreach (Widget g in Children)
g.Paint (ref gr);
childrenRWLock.ExitReadLock ();
return;
}
//remove level and move remaining obj to level above
- GraphicObject g = Children [0];
+ Widget g = Children [0];
RemoveChild (g);
idx = dsp.Children.IndexOf (this);
dsp.RemoveChild (this);
{
int d = 0;
if (Orientation == Orientation.Horizontal) {
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
if (!c.Visible)
continue;
c.Slot.X = d;
d += c.Slot.Width + Spacing;
}
} else {
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
if (!c.Visible)
continue;
c.Slot.Y = d;
}
IsDirty = true;
}
- GraphicObject stretchedGO = null;
+ Widget stretchedGO = null;
public override bool UpdateLayout (LayoutingType layoutType)
{
RegisteredLayoutings &= (~layoutType);
public override void OnChildLayoutChanges (object sender, LayoutingEventArgs arg)
{
- GraphicObject go = sender as GraphicObject;
+ Widget go = sender as Widget;
//Debug.WriteLine ("child layout change: " + go.LastSlots.ToString() + " => " + go.Slot.ToString());
switch (arg.LayoutType) {
case LayoutingType.Width:
}
#endregion
- public override void RemoveChild (GraphicObject child)
+ public override void RemoveChild (Widget child)
{
if (child != stretchedGO) {
if (Orientation == Orientation.Horizontal)
+++ /dev/null
-//
-// GraphicObject.cs
-//
-// Author:
-// Jean-Philippe Bruyère <jp.bruyere@hotmail.com>
-//
-// Copyright (c) 2013-2017 Jean-Philippe Bruyère
-//
-// Permission is hereby granted, free of charge, to any person obtaining a copy
-// of this software and associated documentation files (the "Software"), to deal
-// in the Software without restriction, including without limitation the rights
-// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-// copies of the Software, and to permit persons to whom the Software is
-// furnished to do so, subject to the following conditions:
-//
-// The above copyright notice and this permission notice shall be included in
-// all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
-// THE SOFTWARE.
-
-using System;
-using System.Collections.Generic;
-using System.ComponentModel;
-using System.Xml.Serialization;
-using System.Reflection;
-using System.Reflection.Emit;
-using System.Runtime.CompilerServices;
-using Cairo;
-using System.Diagnostics;
-using Crow.IML;
-using System.Threading;
-
-
-#if DESIGN_MODE
-using System.Xml;
-using System.IO;
-#endif
-
-namespace Crow
-{
- /// <summary>
- /// The base class for all the graphic tree elements.
- /// </summary>
- public class GraphicObject : ILayoutable, IValueChange, IDisposable
- {
- internal ReaderWriterLockSlim parentRWLock = new ReaderWriterLockSlim();
- #if DEBUG_LOG
- //0 is the main graphic tree, for other obj tree not added to main tree, it range from 1->n
- //useful to track events for obj shown later, not on start, or never added to main tree
- public int treeIndex;
- public int yIndex;//absolute index in the graphic tree for debug draw
- public int xLevel;//x increment for debug draw
- #endif
- #if DESIGN_MODE
- static MethodInfo miDesignAddDefLoc = typeof(GraphicObject).GetMethod("design_add_style_location",
- BindingFlags.Instance | BindingFlags.NonPublic);
- static MethodInfo miDesignAddValLoc = typeof(GraphicObject).GetMethod("design_add_iml_location",
- BindingFlags.Instance | BindingFlags.NonPublic);
-
- public volatile bool design_HasChanged = false;
- public string design_id;
- public int design_line;
- public int design_column;
- public string design_imlPath;
- public bool design_isTGItem = false;//true if this is a templated item's root
- public Dictionary<string,string> design_iml_values = new Dictionary<string, string>();
- public Dictionary<string,string> design_style_values = new Dictionary<string, string>();
- //public Dictionary<string,FileLocation> design_iml_locations = new Dictionary<string, FileLocation>();
- public Dictionary<string,FileLocation> design_style_locations = new Dictionary<string, FileLocation>();
-
- internal void design_add_style_location (string memberName, string path, int line, int col) {
- if (design_style_locations.ContainsKey(memberName)){
- Console.WriteLine ("default value localtion already set for {0}{1}.{2}", this.GetType().Name, this.design_id, memberName);
- return;
- }
- design_style_locations.Add(memberName, new FileLocation(path,line,col));
- }
-// internal void design_add_iml_location (string memberName, string path, int line, int col) {
-// if (design_iml_locations.ContainsKey(memberName)){
-// Console.WriteLine ("IML value localtion already set for {0}{1}.{2}", this.GetType().Name, this.design_id, memberName);
-// return;
-// }
-// design_iml_locations.Add(memberName, new FileLocation(path,line,col));
-// }
-
- public virtual bool FindByDesignID(string designID, out GraphicObject go){
- go = null;
- if (this.design_id == designID){
- go = this;
- return true;
- }
- return false;
- }
-
- public string GetIML(){
- XmlDocument doc = new XmlDocument( );
-
- using (StringWriter sw = new StringWriter ()) {
- XmlWriterSettings settings = new XmlWriterSettings {
- Indent = true,
- IndentChars = "\t",
- };
- using (XmlWriter xtw = XmlWriter.Create (sw, settings)) {
- //(1) the xml declaration is recommended, but not mandatory
- XmlDeclaration xmlDeclaration = doc.CreateXmlDeclaration ("1.0", "UTF-8", null);
- doc.InsertBefore (xmlDeclaration, null);
- getIML (doc, (XmlNode)doc);
- doc.WriteTo (xtw);
- }
- this.design_HasChanged = false;
- return sw.ToString ();
- }
- }
-
- public virtual void getIML(XmlDocument doc, XmlNode parentElem) {
- if (this.design_isTGItem)
- return;
-
- XmlElement xe = doc.CreateElement(this.GetType().Name);
-
- foreach (KeyValuePair<string,string> kv in design_iml_values) {
- XmlAttribute xa = doc.CreateAttribute (kv.Key);
- xa.Value = kv.Value;
- xe.Attributes.Append (xa);
- }
-
- parentElem.AppendChild (xe);
- }
- public Surface CreateIcon (int dragIconSize = 32) {
- ImageSurface di = new ImageSurface (Format.Argb32, dragIconSize, dragIconSize);
- using (Context ctx = new Context (di)) {
- double div = Math.Max (LastPaintedSlot.Width, LastPaintedSlot.Height);
- double s = (double)dragIconSize / div;
- ctx.Scale (s, s);
- if (bmp == null)
- this.onDraw (ctx);
- else {
- if (LastPaintedSlot.Width>LastPaintedSlot.Height)
- ctx.SetSourceSurface (bmp, 0, (LastPaintedSlot.Width-LastPaintedSlot.Height)/2);
- else
- ctx.SetSourceSurface (bmp, (LastPaintedSlot.Height-LastPaintedSlot.Width)/2, 0);
- ctx.Paint ();
- }
- }
- return di;
- }
- public string DesignName {
- get { return GetType ().Name + design_id; }
- }
- #endif
-
- #region IDisposable implementation
- protected bool disposed = false;
-
- public void Dispose(){
- Dispose(true);
- GC.SuppressFinalize(this);
- }
- ~GraphicObject(){
- Debug.WriteLine(this.ToString() + " not disposed by user");
- Dispose(false);
- }
- protected virtual void Dispose(bool disposing){
- if (disposed){
- #if DEBUG_DISPOSE
- Debug.WriteLine ("Trying to dispose already disposed obj: {0}", this.ToString());
- #endif
- return;
- }
-
- if (disposing) {
- #if DEBUG_DISPOSE
- Debug.WriteLine ("Disposing: {0}", this.ToString());
- if (IsQueueForRedraw)
- throw new Exception("Trying to dispose an object queued for Redraw: " + this.ToString());
- #endif
-
- unshownPostActions ();
-
- if (!localDataSourceIsNull)
- DataSource = null;
-
- parentRWLock.EnterWriteLock();
- parent = null;
- parentRWLock.ExitWriteLock();
- } else
- Debug.WriteLine ("!!! Finalized by GC: {0}", this.ToString ());
- Clipping?.Dispose ();
- bmp?.Dispose ();
- disposed = true;
- }
- #endregion
-
- #if DEBUG_LOG
- internal static List<GraphicObject> GraphicObjects = new List<GraphicObject>();
- #endif
-
- internal bool isPopup = false;
- public GraphicObject focusParent {
- get { return (isPopup ? LogicalParent : parent) as GraphicObject; }
- }
-
- /// <summary>
- /// interface this widget is bound to, this should not be changed once the instance is created
- /// </summary>
- public Interface IFace = null;
-
- /// <summary>
- /// contains the dirty rectangles in the coordinate system of the cache. those dirty zones
- /// are repeated at each cached levels of the tree with correspondig coordinate system. This is done
- /// in a dedicated step of the update between layouting and drawing.
- /// </summary>
- public Region Clipping;
-
- #region IValueChange implementation
- /// <summary>
- /// Raise to notify that the value of a property has changed, the binding system
- /// rely mainly on this event. the member name may not be present in the class, this is
- /// used in **propertyless** bindings, this allow to raise custom named events without needing
- /// to create an new one in the class or a new property.
- /// </summary>
- public event EventHandler<ValueChangeEventArgs> ValueChanged;
- /// <summary>
- /// Helper function to raise the value changed event
- /// </summary>
- public virtual void NotifyValueChanged(string MemberName, object _value)
- {
- //Debug.WriteLine ("Value changed: {0}->{1} = {2}", this, MemberName, _value);
- ValueChanged.Raise(this, new ValueChangeEventArgs(MemberName, _value));
- }
- #endregion
-
- #region CTOR
- /// <summary>
- /// default private parameter less constructor use in instantiators, it should not be used
- /// when creating widget from code because widgets has to be bound to an interface before any other
- /// action.
- /// </summary>
- protected GraphicObject () {
- Clipping = new Region ();
- #if DEBUG_LOG
- GraphicObjects.Add (this);
- DebugLog.AddEvent(DbgEvtType.GOClassCreation, this);
- #endif
- }
- /// <summary>
- /// This constructor **must** be used when creating widget from code.
- ///
- /// When creating new widgets derived from GraphicObject, both parameterless and this constructors are
- /// facultatives, the compiler will create the parameterless one automaticaly if no other one exists.
- /// But if you intend to be able to create instances of the new widget in code and override the constructor
- /// with the Interface parameter, you **must** also provide the override of the parameterless constructor because
- /// compiler will not create it automatically because of the presence of the other one.
- /// </summary>
- /// <param name="iface">Iface.</param>
- public GraphicObject (Interface iface) : this()
- {
- IFace = iface;
- Initialize ();
- }
- #endregion
- //internal bool initialized = false;
- /// <summary>
- /// Initialize this Graphic object instance by setting style and default values and loading template if required
- /// </summary>
- public virtual void Initialize(){
- loadDefaultValues ();
- }
- #region private fields
- LayoutingType registeredLayoutings = LayoutingType.All;
- ILayoutable logicalParent;
- ILayoutable parent;
- string name;
- Fill background = Color.Transparent;
- Fill foreground = Color.White;
- Font font = "sans, 10";
- protected Measure width, height;
- int left, top;
- double cornerRadius = 0;
- int margin = 0;
- bool focusable = false;
- bool hasFocus = false;
- bool isActive = false;
- //bool isHover = false;
- bool mouseRepeat;
- protected bool isVisible = true;
- bool isEnabled = true;
- VerticalAlignment verticalAlignment = VerticalAlignment.Center;
- HorizontalAlignment horizontalAlignment = HorizontalAlignment.Center;
- Size maximumSize = "0,0";
- Size minimumSize = "0,0";
- bool cacheEnabled = false;
- bool clipToClientRect = true;
- Type dataSourceType;
- protected object dataSource;
- bool rootDataLevel;
- string style;
- object tag;
- bool isDragged;
- bool allowDrag;
- bool allowDrop;
- string tooltip;
- IList<Command> contextCommands;
- #endregion
-
- #region public fields
- /// <summary>
- /// Current size and position computed during layouting pass
- /// </summary>
- public Rectangle Slot = new Rectangle ();
- /// <summary>
- /// keep last slot components for each layouting pass to track
- /// changes and trigger update of other component accordingly
- /// </summary>
- public Rectangle LastSlots;
- /// <summary>
- /// keep last slot painted on screen to clear traces if moved or resized
- /// version to clear effective oldslot if parents have been moved or resized.
- /// IDEA is to add a ScreenCoordinates function that use only lastPaintedSlots
- /// </summary>
- //TODO: we should ensure the whole parsed widget tree is the last painted
- public Rectangle LastPaintedSlot;
- /// <summary>Prevent requeuing multiple times the same widget</summary>
- public bool IsQueueForClipping = false;
- /// <summary>drawing Cache, if null, a redraw is done, cached or not</summary>
- public Surface bmp;
- public bool IsDirty = true;
- /// <summary>
- /// This size is computed on each child' layout changes.
- /// In stacking widget, it is used to compute the remaining space for the stretched
- /// widget inside the stack, which is never added to the contentSize, instead, its size
- /// is deducted from (parent.ClientRectangle - contentSize)
- /// </summary>
- internal Size contentSize;
- #endregion
-
- #region ILayoutable
- [XmlIgnore]public LayoutingType RegisteredLayoutings { get { return registeredLayoutings; } set { registeredLayoutings = value; } }
- //TODO: it would save the recurent cost of a cast in event bubbling if parent type was GraphicObject
- // or we could add to the interface the mouse events
- /// <summary>
- /// Parent in the graphic tree, used for rendering and layouting
- /// </summary>
- [XmlIgnore]public virtual ILayoutable Parent {
- get { return parent; }
- set {
- if (parent == value)
- return;
- DataSourceChangeEventArgs e = new DataSourceChangeEventArgs (parent, value);
-
- parentRWLock.EnterWriteLock();
- parent = value;
- Slot = LastSlots = default(Rectangle);
- parentRWLock.ExitWriteLock();
-
- onParentChanged (this, e);
- }
- }
- [XmlIgnore]public ILayoutable LogicalParent {
- get { return logicalParent == null ? Parent : logicalParent; }
- set {
- if (logicalParent == value)
- return;
- if (logicalParent != null)
- (logicalParent as GraphicObject).DataSourceChanged -= onLogicalParentDataSourceChanged;
- DataSourceChangeEventArgs dsce = new DataSourceChangeEventArgs (LogicalParent, null);
- logicalParent = value;
- dsce.NewDataSource = LogicalParent;
- if (logicalParent != null)
- (logicalParent as GraphicObject).DataSourceChanged += onLogicalParentDataSourceChanged;
- onLogicalParentChanged (this, dsce);
- }
- }
- [XmlIgnore]public virtual Rectangle ClientRectangle {
- get {
- Rectangle cb = Slot.Size;
- cb.Inflate ( - margin);
- return cb;
- }
- }
- public virtual Rectangle ContextCoordinates(Rectangle r){
- GraphicObject go = Parent as GraphicObject;
- if (go == null)
- return r + Parent.ClientRectangle.Position;
- return go.CacheEnabled ?
- r + Parent.ClientRectangle.Position :
- Parent.ContextCoordinates (r);
- }
- public virtual Rectangle ScreenCoordinates (Rectangle r){
- try {
- return
- Parent.ScreenCoordinates(r) + Parent.getSlot().Position + Parent.ClientRectangle.Position;
- } catch (Exception ex) {
- Debug.WriteLine (ex);
- return default(Rectangle);
- }
- }
- public virtual Rectangle getSlot () { return Slot;}
- #endregion
- public Point ScreenPointToLocal(Point p){
- Point pt = p - ScreenCoordinates(Slot).TopLeft - ClientRectangle.TopLeft;
- if (pt.X < 0)
- pt.X = 0;
- if (pt.Y < 0)
- pt.Y = 0;
- return pt;
- }
-
- #region EVENT HANDLERS
- /// <summary>Occurs when mouse wheel is rolled in this object. It bubbles to the root</summary>
- public event EventHandler<MouseWheelEventArgs> MouseWheelChanged;
- /// <summary>Occurs when mouse button is released in this object. It bubbles to the root</summary>
- public event EventHandler<MouseButtonEventArgs> MouseUp;
- /// <summary>Occurs when mouse button is pressed in this object. It bubbles to the root</summary>
- public event EventHandler<MouseButtonEventArgs> MouseDown;
- /// <summary>Occurs when mouse button has been pressed then relesed in this object. It bubbles to the root</summary>
- public event EventHandler<MouseButtonEventArgs> MouseClick;
- /// <summary>Occurs when mouse button has been pressed then relesed 2 times in this object. It bubbles to the root</summary>
- public event EventHandler<MouseButtonEventArgs> MouseDoubleClick;
- /// <summary>Occurs when mouse mouve in this object. It bubbles to the root</summary>
- public event EventHandler<MouseMoveEventArgs> MouseMove;
- /// <summary>Occurs when mouse enter this object</summary>
- public event EventHandler<MouseMoveEventArgs> MouseEnter;
- /// <summary>Occurs when mouse leave this object</summary>
- public event EventHandler<MouseMoveEventArgs> MouseLeave;
- /// <summary>Occurs when key is pressed when this object is active</summary>
- public event EventHandler<KeyEventArgs> KeyDown;
- /// <summary>Occurs when key is released when this object is active</summary>
- public event EventHandler<KeyEventArgs> KeyUp;
- /// <summary>Occurs when translated key event occurs in the host when this object is active</summary>
- public event EventHandler<KeyPressEventArgs> KeyPress;
- /// <summary>Occurs when this object received focus</summary>
- public event EventHandler Focused;
- /// <summary>Occurs when this object loose focus</summary>
- public event EventHandler Unfocused;
- /// <summary>Occurs when mouse is over</summary>
- //public event EventHandler Hover;
- /// <summary>Occurs when this control is no longer the Hover one</summary>
- //public event EventHandler UnHover;
- /// <summary>Occurs when this object loose focus</summary>
- public event EventHandler Enabled;
- /// <summary>Occurs when the enabled state this object is set to false</summary>
- public event EventHandler Disabled;
-
- #region DragAndDrop Events
- public event EventHandler<DragDropEventArgs> StartDrag;
- public event EventHandler<DragDropEventArgs> DragEnter;
- public event EventHandler<DragDropEventArgs> DragLeave;
- public event EventHandler<DragDropEventArgs> EndDrag;
- public event EventHandler<DragDropEventArgs> Drop;
- #endregion
-
- /// <summary>
- /// Occurs when default value and styling are loaded, and for templated control,
- /// template is also loaded. Bindings should be functionnal as well.
- /// </summary>
- public event EventHandler Initialized;
-
- /// <summary>Occurs when one part of the rendering slot changed</summary>
- public event EventHandler<LayoutingEventArgs> LayoutChanged;
- /// <summary>Occurs when DataSource changed</summary>
- public event EventHandler<DataSourceChangeEventArgs> DataSourceChanged;
- /// <summary>Occurs when the parent has changed</summary>
- public event EventHandler<DataSourceChangeEventArgs> ParentChanged;
- /// <summary>Occurs when the logical parent has changed</summary>
- public event EventHandler<DataSourceChangeEventArgs> LogicalParentChanged;
- #endregion
-
- #region public properties
- /// <summary>Random value placeholder</summary>
- [DesignCategory ("Divers")]
- public object Tag {
- get { return tag; }
- set {
- if (tag == value)
- return;
- tag = value;
- NotifyValueChanged ("Tag", tag);
- }
- }
- /// <summary>
- /// If enabled, resulting bitmap of graphic object is cached
- /// speeding up rendering of complex object. Default is enabled.
- /// </summary>
- [DesignCategory ("Behavior")][DefaultValue(true)]
- public virtual bool CacheEnabled {
- get { return cacheEnabled; }
- set {
- if (cacheEnabled == value)
- return;
- cacheEnabled = value;
- NotifyValueChanged ("CacheEnabled", cacheEnabled);
- }
- }
- /// <summary>
- /// If true, rendering of GraphicObject is clipped inside client rectangle
- /// </summary>
- [DesignCategory ("Appearance")][DefaultValue(true)]
- public virtual bool ClipToClientRect {
- get { return clipToClientRect; }
- set {
- if (clipToClientRect == value)
- return;
- clipToClientRect = value;
- NotifyValueChanged ("ClipToClientRect", clipToClientRect);
- this.RegisterForRedraw ();
- }
- }
- #if DEBUG_LOG
- [XmlIgnore]public string TreePath {
- get { return this.GetType().Name + GraphicObjects.IndexOf(this).ToString (); }
- }
- #endif
- /// <summary>
- /// Name is used in binding to reference other GraphicObjects inside the graphic tree
- /// and by template controls to find special element in their template implementation such
- /// as a container or a group to put children in.
- /// </summary>
- [DesignCategory ("Divers")][DefaultValue(null)]
- public virtual string Name {
- get {
- #if DEBUG_LOG
- return string.IsNullOrEmpty(name) ? this.GetType().Name + GraphicObjects.IndexOf(this).ToString () : name;
- #else
- return name;
- #endif
- }
- set {
- if (name == value)
- return;
- name = value;
- NotifyValueChanged("Name", name);
- }
- }
- /// <summary>
- /// Vertical alignment inside parent, disabled if height is stretched
- /// or top coordinate is not null
- /// </summary>
- [DesignCategory ("Layout")][DefaultValue(VerticalAlignment.Center)]
- public virtual VerticalAlignment VerticalAlignment {
- get { return verticalAlignment; }
- set {
- if (verticalAlignment == value)
- return;
-
- verticalAlignment = value;
- NotifyValueChanged("VerticalAlignment", verticalAlignment);
- RegisterForLayouting (LayoutingType.Y);
- }
- }
- /// <summary>
- /// Horizontal alignment inside parent, disabled if width is stretched
- /// or left coordinate is not null
- /// </summary>
- [DesignCategory ("Layout")][DefaultValue(HorizontalAlignment.Center)]
- public virtual HorizontalAlignment HorizontalAlignment {
- get { return horizontalAlignment; }
- set {
- if (horizontalAlignment == value)
- return;
- horizontalAlignment = value;
- NotifyValueChanged("HorizontalAlignment", horizontalAlignment);
- RegisterForLayouting (LayoutingType.X);
- }
- }
- /// <summary>
- /// x position inside parent
- /// </summary>
- [DesignCategory ("Layout")][DefaultValue(0)]
- public virtual int Left {
- get { return left; }
- set {
- if (left == value)
- return;
- left = value;
- NotifyValueChanged ("Left", left);
- this.RegisterForLayouting (LayoutingType.X);
- }
- }
- /// <summary>
- /// y position inside parent
- /// </summary>
- [DesignCategory ("Layout")][DefaultValue(0)]
- public virtual int Top {
- get { return top; }
- set {
- if (top == value)
- return;
- top = value;
- NotifyValueChanged ("Top", top);
- this.RegisterForLayouting (LayoutingType.Y);
- }
- }
- /// <summary>
- /// Helper property used to set width and height to fit in one call
- /// </summary>
- [DesignCategory ("Layout")][DefaultValue(false)]
- public virtual bool Fit {
- get { return Width == Measure.Fit && Height == Measure.Fit ? true : false; }
- set {
- if (value == Fit)
- return;
-
- Width = Height = Measure.Fit;
- }
- }
- /// <summary>
- /// Width of this control, by default inherited from parent. May have special values
- /// such as Stretched or Fit. It may be proportionnal or absolute.
- /// </summary>
- [DesignCategory ("Layout")][DefaultValue("Inherit")]
- public virtual Measure Width {
- get {
- return width.Units == Unit.Inherit ?
- Parent is GraphicObject ? (Parent as GraphicObject).WidthPolicy :
- Measure.Stretched : width;
- }
- set {
- if (width == value)
- return;
- if (value.IsFixed) {
- if (value < minimumSize.Width || (value > maximumSize.Width && maximumSize.Width > 0))
- return;
- }
- Measure old = width;
- width = value;
- NotifyValueChanged ("Width", width);
- if (width == Measure.Stretched || old == Measure.Stretched) {
- //NotifyValueChanged ("WidthPolicy", width.Policy);
- //contentSize in Stacks are only update on childLayoutChange, and the single stretched
- //child of the stack is not counted in contentSize, so when changing size policy of a child
- //we should adapt contentSize
- //TODO:check case when child become stretched, and another stretched item already exists.
- GenericStack gs = Parent as GenericStack;
- if (gs != null){ //TODO:check if I should test Group instead
- if (gs.Orientation == Orientation.Horizontal) {
- if (width == Measure.Stretched)
- gs.contentSize.Width -= this.LastSlots.Width;
- else
- gs.contentSize.Width += this.LastSlots.Width;
- }
- }
- }
-
- this.RegisterForLayouting (LayoutingType.Width);
- }
- }
- /// <summary>
- /// Height of this control, by default inherited from parent. May have special values
- /// such as Stretched or Fit. It may be proportionnal or absolute.
- /// </summary>
- [DesignCategory ("Layout")][DefaultValue("Inherit")]
- public virtual Measure Height {
- get {
- return height.Units == Unit.Inherit ?
- Parent is GraphicObject ? (Parent as GraphicObject).HeightPolicy :
- Measure.Stretched : height;
- }
- set {
- if (height == value)
- return;
- if (value.IsFixed) {
- if (value < minimumSize.Height || (value > maximumSize.Height && maximumSize.Height > 0))
- return;
- }
- Measure old = height;
- height = value;
- NotifyValueChanged ("Height", height);
- if (height == Measure.Stretched || old == Measure.Stretched) {
- //NotifyValueChanged ("HeightPolicy", HeightPolicy);
- GenericStack gs = Parent as GenericStack;
- if (gs != null){ //TODO:check if I should test Group instead
- if (gs.Orientation == Orientation.Vertical) {
- if (height == Measure.Stretched)
- gs.contentSize.Height -= this.LastSlots.Height;
- else
- gs.contentSize.Height += this.LastSlots.Height;
- }
- }
- }
-
- this.RegisterForLayouting (LayoutingType.Height);
- }
- }
- /// <summary>
- /// Was Used for binding on dimensions, this property will never hold fixed size, but instead only
- /// Fit or Stretched, **with inherited state implementation, it is not longer used in binding**
- /// </summary>
- [XmlIgnore]public virtual Measure WidthPolicy { get {
- return Width.IsFit ? Measure.Fit : Measure.Stretched; } }
- /// <summary>
- /// Was Used for binding on dimensions, this property will never hold fixed size, but instead only
- /// Fit or Stretched, **with inherited state implementation, it is not longer used in binding**
- /// </summary>
- [XmlIgnore]public virtual Measure HeightPolicy { get {
- return Height.IsFit ? Measure.Fit : Measure.Stretched; } }
- /// <summary>
- /// Indicate that this object may received focus or not, if not focusable all the descendants are
- /// affected.
- /// </summary>
- [DesignCategory ("Behaviour")][DefaultValue(false)]
- public virtual bool Focusable {
- get { return focusable; }
- set {
- if (focusable == value)
- return;
- focusable = value;
- NotifyValueChanged ("Focusable", focusable);
- }
- }
- /// <summary>
- /// True when this control has the focus, only one control per interface may have it.
- /// </summary>
- [XmlIgnore]public virtual bool HasFocus {
- get { return hasFocus; }
- set {
- if (value == hasFocus)
- return;
-
- hasFocus = value;
- if (hasFocus)
- onFocused (this, null);
- else
- onUnfocused (this, null);
- NotifyValueChanged ("HasFocus", hasFocus);
- }
- }
- /// <summary>
- /// true if this control is active, this means that mouse has been pressed in it and not yet released. It could
- /// be used for other two states periferic action.
- /// </summary>
- [XmlIgnore]public virtual bool IsActive {
- get { return isActive; }
- set {
- if (value == isActive)
- return;
-
- isActive = value;
- NotifyValueChanged ("IsActive", isActive);
- }
- }
- /// <summary>
- /// true if this control has the pointer hover
- /// </summary>
- /*[XmlIgnore]public virtual bool IsHover {
- get { return isHover; }
- set {
- if (value == isHover)
- return;
-
- isHover = value;
-
- if (isHover)
- onHover (this, null);
- else
- onUnHover (this, null);
-
- NotifyValueChanged ("IsHover", isHover);
- }
- }*/
- /// <summary>
- /// true if holding mouse button down should trigger multiple click events
- /// </summary>
- [DesignCategory ("Behaviour")][DefaultValue(false)]
- public virtual bool MouseRepeat {
- get { return mouseRepeat; }
- set {
- if (mouseRepeat == value)
- return;
- mouseRepeat = value;
- NotifyValueChanged ("MouseRepeat", mouseRepeat);
- }
- }
- bool clearBackground = false;
- /// <summary>
- /// background fill of the control, maybe solid color, gradient, image, or svg
- /// </summary>
- [DesignCategory ("Appearance")][DefaultValue("Transparent")]
- public virtual Fill Background {
- get { return background; }
- set {
- if (background == value)
- return;
- clearBackground = false;
- if (value == null)
- return;
- background = value;
- NotifyValueChanged ("Background", background);
- RegisterForRedraw ();
- if (background is SolidColor) {
- if ((background as SolidColor).Equals (Color.Clear))
- clearBackground = true;
- }
- }
- }
- /// <summary>
- /// Foreground fill of the control, usage may be different among derived controls
- /// </summary>
- [DesignCategory ("Appearance")][DefaultValue("White")]
- public virtual Fill Foreground {
- get { return foreground; }
- set {
- if (foreground == value)
- return;
- foreground = value;
- NotifyValueChanged ("Foreground", foreground);
- RegisterForRedraw ();
- }
- }
- /// <summary>
- /// Font being used in many controls, it is defined in the base GraphicObject class.
- /// </summary>
- [DesignCategory ("Appearance")][DefaultValue("sans, 10")]
- public virtual Font Font {
- get { return font; }
- set {
- if (value == font)
- return;
- font = value;
- NotifyValueChanged ("Font", font);
- RegisterForGraphicUpdate ();
- }
- }
- /// <summary>
- /// to get rounded corners
- /// </summary>
- [DesignCategory ("Appearance")][DefaultValue(0.0)]
- public virtual double CornerRadius {
- get { return cornerRadius; }
- set {
- if (value == cornerRadius)
- return;
- cornerRadius = value;
- NotifyValueChanged ("CornerRadius", cornerRadius);
- RegisterForRedraw ();
- }
- }
- /// <summary>
- /// This is a single integer for the 4 direction, a gap between the control and it's container,
- /// by default it is filled with the background.
- /// </summary>
- [DesignCategory ("Layout")][DefaultValue(0)]
- public virtual int Margin {
- get { return margin; }
- set {
- if (value == margin)
- return;
- margin = value;
- NotifyValueChanged ("Margin", margin);
- RegisterForGraphicUpdate ();
- }
- }
- /// <summary>
- /// set the visible state of the control, invisible controls does reserve space in the layouting system.
- /// </summary>
- [DesignCategory ("Appearance")][DefaultValue(true)]
- public virtual bool Visible {
- get { return isVisible; }
- set {
- if (value == isVisible)
- return;
-
- isVisible = value;
-
- RegisterForLayouting (LayoutingType.Sizing);
-
- if (!isVisible && IFace.HoverWidget != null) {
- if (IFace.HoverWidget.IsOrIsInside (this)) {
- //IFace.HoverWidget = null;
- IFace.ProcessMouseMove (IFace.Mouse.X, IFace.Mouse.Y);
- }
- }
-
- NotifyValueChanged ("Visible", isVisible);
- }
- }
- /// <summary>
- /// get or set the enabled state, disabling a control will affect focuability and
- /// also it's rendering which will be grayed
- /// </summary>
- [DesignCategory ("Behaviour")][DefaultValue(true)]
- public virtual bool IsEnabled {
- get { return isEnabled; }
- set {
- if (value == isEnabled)
- return;
-
- isEnabled = value;
-
- if (isEnabled)
- onEnable (this, null);
- else
- onDisable (this, null);
-
- NotifyValueChanged ("IsEnabled", isEnabled);
- RegisterForRedraw ();
- }
- }
- /// <summary>
- /// Minimal width and height for this control
- /// </summary>
- [DesignCategory ("Layout")][DefaultValue("1,1")]
- public virtual Size MinimumSize {
- get { return minimumSize; }
- set {
- if (value == minimumSize)
- return;
-
- minimumSize = value;
-
- NotifyValueChanged ("MinimumSize", minimumSize);
- RegisterForLayouting (LayoutingType.Sizing);
- }
- }
- /// <summary>
- /// Maximum width and height for this control, unlimited if null.
- /// </summary>
- [DesignCategory ("Layout")][DefaultValue("0,0")]
- public virtual Size MaximumSize {
- get { return maximumSize; }
- set {
- if (value == maximumSize)
- return;
-
- maximumSize = value;
-
- NotifyValueChanged (nameof(MaximumSize), maximumSize);
- RegisterForLayouting (LayoutingType.Sizing);
- }
- }
- /// <summary>
- /// Fully qualify type name of expected data source.
- /// If set, datasource bindings will be speedup by avoiding reflexion in generated dyn methods.
- /// If an object of a different type is set as datasource, bindings will be canceled.
- /// It accepts all derived type.
- /// </summary>
- [DesignCategory ("Data")]
- public Type DataSourceType {
- get { return dataSourceType; }
- set { dataSourceType = value; }
- }
- /// <summary>
- /// Seek first logical tree upward if logicalParent is set, or seek graphic tree for
- /// a not null dataSource that will be active for all descendants having dataSource=null
- /// </summary>
- [DesignCategory ("Data")]
- public virtual object DataSource {
- set {
- if (DataSource == value)
- return;
-
- DataSourceChangeEventArgs dse = new DataSourceChangeEventArgs (DataSource, null);
- dataSource = value;
- dse.NewDataSource = DataSource;
-
- if (dse.NewDataSource == dse.OldDataSource)
- return;
-
- if (value != null)
- rootDataLevel = true;
-
- #if DEBUG_LOG
- DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GOLockLayouting, this);
- #endif
- lock (IFace.LayoutMutex) {
- OnDataSourceChanged (this, dse);
- NotifyValueChanged ("DataSource", DataSource);
- }
- #if DEBUG_LOG
- dbgEvt.end = DebugLog.chrono.ElapsedTicks;
- #endif
- }
- get {
- return rootDataLevel ? dataSource : dataSource == null ?
- LogicalParent == null ? null :
- LogicalParent is GraphicObject ? (LogicalParent as GraphicObject).DataSource : null :
- dataSource;
- }
- }
- /// <summary>
- /// If true, rendering of GraphicObject is clipped inside client rectangle
- /// </summary>
- [DesignCategory ("Data")][DefaultValue(false)]
- public virtual bool RootDataLevel {
- get { return rootDataLevel; }
- set {
- if (rootDataLevel == value)
- return;
- rootDataLevel = value;
- NotifyValueChanged ("RootDataLevel", rootDataLevel);
- this.RegisterForRedraw ();
- }
- }
- protected virtual void onLogicalParentDataSourceChanged(object sender, DataSourceChangeEventArgs e){
- if (localDataSourceIsNull)
- OnDataSourceChanged (this, e);
- }
- internal bool localDataSourceIsNull { get { return dataSource == null; } }
- public bool localLogicalParentIsNull { get { return logicalParent == null; } }
-
- public virtual void OnDataSourceChanged(object sender, DataSourceChangeEventArgs e){
- DataSourceChanged.Raise (this, e);
- #if DEBUG_LOG
- DebugLog.AddEvent(DbgEvtType.GONewDataSource, this);
- #endif
-
- #if DEBUG_BINDING
- Debug.WriteLine("New DataSource for => {0} \n\t{1}=>{2}", this.ToString(),e.OldDataSource,e.NewDataSource);
- #endif
- }
- /// <summary>
- /// Style key to use for this control
- /// </summary>
- [DesignCategory ("Appearance")]
- public virtual string Style {
- get { return style; }
- set {
- if (value == style)
- return;
-
- style = value;
-
- NotifyValueChanged ("Style", style);
- }
- }
- [DesignCategory ("Divers")]
- public virtual string Tooltip {
- get { return tooltip; }
- set {
- if (tooltip == value)
- return;
- tooltip = value;
- NotifyValueChanged("Tooltip", tooltip);
- }
- }
- [DesignCategory ("Divers")]
- public IList<Command> ContextCommands {
- get { return contextCommands; }
- set {
- if (contextCommands == value)
- return;
- contextCommands = value;
- NotifyValueChanged("ContextCommands", contextCommands);
- }
- }
- #endregion
-
- #region Default and Style Values loading
- /// <summary> Loads the default values from XML attributes default </summary>
- public void loadDefaultValues()
- {
- #if DEBUG_LOG
- DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GOInitialization, this);
- #endif
-
- Type thisType = this.GetType ();
-
- if (!string.IsNullOrEmpty (style)) {
- if (IFace.DefaultValuesLoader.ContainsKey (style)) {
- IFace.DefaultValuesLoader [style] (this);
- onInitialized (this, null);
- return;
- }
- } else if (IFace.DefaultValuesLoader.ContainsKey (thisType.FullName)) {
- IFace.DefaultValuesLoader [thisType.FullName] (this);
- onInitialized (this, null);
- return;
- } else if (IFace.DefaultValuesLoader.ContainsKey (thisType.Name)) {
- IFace.DefaultValuesLoader [thisType.Name] (this);
- onInitialized (this, null);
- return;
- }
-
- List<Style> styling = new List<Style>();
-
- //Search for a style matching :
- //1: Full class name, with full namespace
- //2: class name
- //3: style may have been registered with their ressource ID minus .style extention
- // those files being placed in a Styles folder
- string styleKey = style;
- if (!string.IsNullOrEmpty (style)) {
- if (IFace.Styling.ContainsKey (style)) {
- styling.Add (IFace.Styling [style]);
- }
- }
- if (IFace.Styling.ContainsKey (thisType.FullName)) {
- styling.Add (IFace.Styling [thisType.FullName]);
- if (string.IsNullOrEmpty (styleKey))
- styleKey = thisType.FullName;
- }
- if (IFace.Styling.ContainsKey (thisType.Name)) {
- styling.Add (IFace.Styling [thisType.Name]);
- if (string.IsNullOrEmpty (styleKey))
- styleKey = thisType.Name;
- }
-
- if (string.IsNullOrEmpty (styleKey))
- styleKey = thisType.FullName;
-
- //Reflexion being very slow compared to dyn method or delegates,
- //I compile the initial values coded in the CustomAttribs of the class,
- //all other instance of this type would not longer use reflexion to init properly
- //but will fetch the dynamic initialisation method compiled for this precise type
- //TODO:measure speed gain.
-#region Delfault values Loading dynamic compilation
- DynamicMethod dm = null;
- ILGenerator il = null;
-
- dm = new DynamicMethod("dyn_loadDefValues", null, new Type[] { typeof (object) }, thisType, true);
-
- il = dm.GetILGenerator(256);
- il.DeclareLocal(typeof (object));//store root
- il.Emit(OpCodes.Nop);
- //set local GraphicObject to root object passed as 1st argument
- il.Emit (OpCodes.Ldarg_0);
- il.Emit (OpCodes.Stloc_0);
-
- foreach (EventInfo ei in thisType.GetEvents(BindingFlags.Public | BindingFlags.Instance)) {
- string expression;
- if (!getDefaultEvent(ei, styling, out expression))
- continue;
- //TODO:dynEventHandler could be cached somewhere, maybe a style instanciator class holding the styling delegate and bound to it.
- foreach (string exp in CompilerServices.splitOnSemiColumnOutsideAccolades(expression)) {
- string trimed = exp.Trim();
- if (trimed.StartsWith ("{", StringComparison.Ordinal)){
- il.Emit (OpCodes.Ldloc_0);//load this as 1st arg of event Add
-
- //push eventInfo as 1st arg of compile
- il.Emit (OpCodes.Ldloc_0);
- il.Emit (OpCodes.Call, CompilerServices.miGetType);
- il.Emit (OpCodes.Ldstr, ei.Name);//push event name
- il.Emit (OpCodes.Call, CompilerServices.miGetEvent);
- //push expression as 2nd arg of compile
- il.Emit (OpCodes.Ldstr, trimed.Substring (1, trimed.Length - 2));
- //push null as 3rd arg, currentNode, not known when instanciing
- il.Emit (OpCodes.Ldnull);
- il.Emit (OpCodes.Call, CompilerServices.miCompileDynEventHandler);
- il.Emit (OpCodes.Castclass, ei.EventHandlerType);
- il.Emit (OpCodes.Call, ei.AddMethod);
- }else
- Debug.WriteLine("error in styling, event not handled : " + trimed);
- }
- }
-
- foreach (PropertyInfo pi in thisType.GetProperties(BindingFlags.Public | BindingFlags.Instance)) {
- if (pi.GetSetMethod () == null)
- continue;
- XmlIgnoreAttribute xia = (XmlIgnoreAttribute)pi.GetCustomAttribute (typeof(XmlIgnoreAttribute));
- if (xia != null)
- continue;
-
- object defaultValue;
-
- int styleIndex = -1;
- if (styling.Count > 0){
- for (int i = 0; i < styling.Count; i++) {
- if (styling[i].ContainsKey (pi.Name)){
- styleIndex = i;
- break;
- }
- }
- }
- if (styleIndex >= 0){
- if (pi.PropertyType.IsEnum)//maybe should be in parser..
- defaultValue = Enum.Parse(pi.PropertyType, (string)styling[styleIndex] [pi.Name], true);
- else
- defaultValue = styling[styleIndex] [pi.Name];
-
- #if DESIGN_MODE
- if (defaultValue != null){
- FileLocation fl = styling[styleIndex].Locations[pi.Name];
- il.Emit (OpCodes.Ldloc_0);
- il.Emit (OpCodes.Ldstr, pi.Name);
- il.Emit (OpCodes.Ldstr, fl.FilePath);
- il.Emit (OpCodes.Ldc_I4, fl.Line);
- il.Emit (OpCodes.Ldc_I4, fl.Column);
- il.Emit (OpCodes.Call, miDesignAddDefLoc);
-
- il.Emit (OpCodes.Ldloc_0);
- il.Emit (OpCodes.Ldfld, typeof(GraphicObject).GetField("design_style_values"));
- il.Emit (OpCodes.Ldstr, pi.Name);
- il.Emit (OpCodes.Ldstr, defaultValue.ToString());
- il.Emit (OpCodes.Call, CompilerServices.miDicStrStrAdd);
- }
- #endif
-
- }else {
- DefaultValueAttribute dv = (DefaultValueAttribute)pi.GetCustomAttribute (typeof (DefaultValueAttribute));
- if (dv == null)
- continue;
- defaultValue = dv.Value;
- }
-
- CompilerServices.EmitSetValue (il, pi, defaultValue);
- }
- il.Emit(OpCodes.Ret);
- #endregion
-
- try {
- IFace.DefaultValuesLoader[styleKey] = (Interface.LoaderInvoker)dm.CreateDelegate(typeof(Interface.LoaderInvoker));
- IFace.DefaultValuesLoader[styleKey] (this);
- } catch (Exception ex) {
- throw new Exception ("Error applying style <" + styleKey + ">:", ex);
- }
-
- #if DEBUG_LOG
- dbgEvt.end = DebugLog.chrono.ElapsedTicks;
- #endif
-
- onInitialized (this, null);
- }
- protected virtual void onInitialized (object sender, EventArgs e){
- Initialized.Raise(sender, e);
- }
- bool getDefaultEvent(EventInfo ei, List<Style> styling,
- out string expression){
- expression = "";
- if (styling.Count > 0){
- for (int i = 0; i < styling.Count; i++) {
- if (styling[i].ContainsKey (ei.Name)){
- expression = (string)styling[i] [ei.Name];
- return true;
- }
- }
- }
- return false;
- }
-#endregion
-
- public virtual GraphicObject FindByName(string nameToFind){
- return string.Equals(nameToFind, name, StringComparison.Ordinal) ? this : null;
- }
- public virtual bool Contains(GraphicObject goToFind){
- return false;
- }
- /// <summary>
- /// return true if this is contained inside go
- /// </summary>
- public bool IsOrIsInside(GraphicObject go){
- if (this == go)
- return true;
- ILayoutable p = this.Parent;
- while (p != null) {
- if (p == go)
- return true;
- p = p.Parent;
- }
- return false;
- }
-
- #region Drag&Drop
- [DesignCategory ("DragAndDrop")][DefaultValue(false)]
- public virtual bool AllowDrag {
- get { return allowDrag; }
- set {
- if (allowDrag == value)
- return;
- allowDrag = value;
- NotifyValueChanged ("AllowDrag", allowDrag);
- }
- }
- [DesignCategory ("DragAndDrop")][DefaultValue(false)]
- public virtual bool AllowDrop {
- get { return allowDrop; }
- set {
- if (allowDrop == value)
- return;
- allowDrop = value;
- NotifyValueChanged ("AllowDrop", allowDrop);
- }
- }
-
-// public List<Type> AllowedDroppedTypes;
-// public void AddAllowedDroppedType (Type newType){
-// if (AllowedDroppedTypes == null)
-// AllowedDroppedTypes = new List<Type> ();
-// AllowedDroppedTypes.Add (newType);
-// NotifyValueChanged ("AllowDrop", AllowDrop);
-// }
-// [XmlIgnore]public virtual bool AllowDrop {
-// get { return AllowedDroppedTypes?.Count>0; }
-// }
- [XmlIgnore]public virtual bool IsDragged {
- get { return isDragged; }
- set {
- if (isDragged == value)
- return;
- isDragged = value;
-
- NotifyValueChanged ("IsDragged", IsDragged);
- }
- }
- /// <summary>
- /// fired when drag and drop operation start
- /// </summary>
- protected virtual void onStartDrag (object sender, DragDropEventArgs e){
- IFace.HoverWidget = null;
- IsDragged = true;
- StartDrag.Raise (this, e);
- #if DEBUG_DRAGNDROP
- Debug.WriteLine(this.ToString() + " : START DRAG => " + e.ToString());
- #endif
- }
- /// <summary>
- /// Occured when dragging ends without dropping
- /// </summary>
- protected virtual void onEndDrag (object sender, DragDropEventArgs e){
- IsDragged = false;
- EndDrag.Raise (this, e);
- #if DEBUG_DRAGNDROP
- Debug.WriteLine(this.ToString() + " : END DRAG => " + e.ToString());
- #endif
- }
- protected virtual void onDragEnter (object sender, DragDropEventArgs e){
- e.DropTarget = this;
- DragEnter.Raise (this, e);
- #if DEBUG_DRAGNDROP
- Debug.WriteLine(this.ToString() + " : DRAG Enter => " + e.ToString());
- #endif
- }
- protected virtual void onDragLeave (object sender, DragDropEventArgs e){
- e.DropTarget = null;
- DragLeave.Raise (this, e);
- #if DEBUG_DRAGNDROP
- Debug.WriteLine(this.ToString() + " : DRAG Leave => " + e.ToString());
- #endif
- }
- protected virtual void onDrop (object sender, DragDropEventArgs e){
- IsDragged = false;
- Drop.Raise (this, e);
- //e.DropTarget.onDragLeave (this, e);//raise drag leave in target
- #if DEBUG_DRAGNDROP
- Debug.WriteLine(this.ToString() + " : DROP => " + e.ToString());
- #endif
- }
- public bool IsDropTarget {
- get { return IFace.DragAndDropOperation?.DropTarget == this; }
- }
-
- #endregion
-
- #region Queuing
- /// <summary>
- /// Register old and new slot for clipping
- /// </summary>
- public virtual void ClippingRegistration(){
- #if DEBUG_LOG
- DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GOClippingRegistration, this);
- #endif
- parentRWLock.EnterReadLock ();
- if (parent != null) {
- Parent.RegisterClip (LastPaintedSlot);
- Parent.RegisterClip (Slot);
- }
- parentRWLock.ExitReadLock ();
- #if DEBUG_LOG
- dbgEvt.end = DebugLog.chrono.ElapsedTicks;
- #endif
- }
- /// <summary>
- /// Add clip rectangle to this.clipping and propagate up to root
- /// </summary>
- /// <param name="clip">Clip rectangle</param>
- public virtual void RegisterClip(Rectangle clip){
- #if DEBUG_LOG
- DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GORegisterClip, this);
- #endif
- Rectangle cb = ClientRectangle;
- Rectangle r = clip + cb.Position;
- if (r.Right > cb.Right)
- r.Width -= r.Right - cb.Right;
- if (r.Bottom > cb.Bottom)
- r.Height -= r.Bottom - cb.Bottom;
- if (cacheEnabled && !IsDirty)
- Clipping.UnionRectangle (r);
- if (Parent == null)
- return;
- GraphicObject p = Parent as GraphicObject;
- if (p?.IsDirty == true && p?.CacheEnabled == true)
- return;
- Parent.RegisterClip (r + Slot.Position);
- #if DEBUG_LOG
- dbgEvt.end = DebugLog.chrono.ElapsedTicks;
- #endif
- }
- /// <summary> Full update, content and layouting, taking care of sizing policy </summary>
- [MethodImpl(MethodImplOptions.AggressiveInlining)]
- public void RegisterForGraphicUpdate ()
- {
- IsDirty = true;
- if (Width.IsFit || Height.IsFit)
- RegisterForLayouting (LayoutingType.Sizing);
- else if (RegisteredLayoutings == LayoutingType.None)
- IFace.EnqueueForRepaint (this);
- }
- /// <summary> query an update of the content without layouting changes</summary>
- [MethodImpl(MethodImplOptions.AggressiveInlining)]
- public void RegisterForRedraw ()
- {
- IsDirty = true;
- if (RegisteredLayoutings == LayoutingType.None)
- IFace.EnqueueForRepaint (this);
- }
- #endregion
-
- #region Layouting
-
- /// <summary> return size of content + margins </summary>
- protected virtual int measureRawSize (LayoutingType lt) {
- return lt == LayoutingType.Width ?
- contentSize.Width + 2 * margin: contentSize.Height + 2 * margin;
- }
- /// <summary> By default in groups, LayoutingType.ArrangeChildren is reset </summary>
- public virtual void ChildrenLayoutingConstraints(ref LayoutingType layoutType){
- }
- public virtual bool ArrangeChildren { get { return false; } }
- public virtual void RegisterForLayouting(LayoutingType layoutType){
- if (Parent == null)
- return;
- lock (IFace.LayoutMutex) {
- //prevent queueing same LayoutingType for this
- layoutType &= (~RegisteredLayoutings);
-
- if (layoutType == LayoutingType.None)
- return;
- //dont set position for stretched item
- if (Width == Measure.Stretched)
- layoutType &= (~LayoutingType.X);
- if (Height == Measure.Stretched)
- layoutType &= (~LayoutingType.Y);
-
- if (!ArrangeChildren)
- layoutType &= (~LayoutingType.ArrangeChildren);
-
- //apply constraints depending on parent type
- if (Parent is GraphicObject)
- (Parent as GraphicObject).ChildrenLayoutingConstraints (ref layoutType);
-
-// //prevent queueing same LayoutingType for this
- layoutType &= (~RegisteredLayoutings);
-
- if (layoutType == LayoutingType.None)
- return;
-
- //enqueue LQI LayoutingTypes separately
- if (layoutType.HasFlag (LayoutingType.Width))
- IFace.LayoutingQueue.Enqueue (new LayoutingQueueItem (LayoutingType.Width, this));
- if (layoutType.HasFlag (LayoutingType.Height))
- IFace.LayoutingQueue.Enqueue (new LayoutingQueueItem (LayoutingType.Height, this));
- if (layoutType.HasFlag (LayoutingType.X))
- IFace.LayoutingQueue.Enqueue (new LayoutingQueueItem (LayoutingType.X, this));
- if (layoutType.HasFlag (LayoutingType.Y))
- IFace.LayoutingQueue.Enqueue (new LayoutingQueueItem (LayoutingType.Y, this));
- if (layoutType.HasFlag (LayoutingType.ArrangeChildren))
- IFace.LayoutingQueue.Enqueue (new LayoutingQueueItem (LayoutingType.ArrangeChildren, this));
- }
- }
-
- /// <summary> trigger dependant sizing component update </summary>
- public virtual void OnLayoutChanges(LayoutingType layoutType)
- {
- switch (layoutType) {
- case LayoutingType.Width:
- RegisterForLayouting (LayoutingType.X);
- break;
- case LayoutingType.Height:
- RegisterForLayouting (LayoutingType.Y);
- break;
- }
- LayoutChanged.Raise (this, new LayoutingEventArgs (layoutType));
- }
- internal protected void raiseLayoutChanged(LayoutingEventArgs e){
- LayoutChanged.Raise (this, e);
- }
- /// <summary> Update layout component only one at a time, this is where the computation of alignement
- /// and size take place.
- /// The redrawing will only be triggered if final slot size has changed </summary>
- /// <returns><c>true</c>, if layouting was possible, <c>false</c> if conditions were not
- /// met and LQI has to be re-queued</returns>
- public virtual bool UpdateLayout (LayoutingType layoutType)
- {
- //unset bit, it would be reset if LQI is re-queued
- registeredLayoutings &= (~layoutType);
-
- switch (layoutType) {
- case LayoutingType.X:
- if (left == 0) {
-
- if (Parent.RegisteredLayoutings.HasFlag (LayoutingType.Width) ||
- RegisteredLayoutings.HasFlag (LayoutingType.Width))
- return false;
-
- switch (horizontalAlignment) {
- case HorizontalAlignment.Left:
- Slot.X = 0;
- break;
- case HorizontalAlignment.Right:
- Slot.X = Parent.ClientRectangle.Width - Slot.Width;
- break;
- case HorizontalAlignment.Center:
- Slot.X = Parent.ClientRectangle.Width / 2 - Slot.Width / 2;
- break;
- }
- } else
- Slot.X = left;
-
- if (LastSlots.X == Slot.X)
- break;
-
- IsDirty = true;
-
- OnLayoutChanges (layoutType);
-
- LastSlots.X = Slot.X;
- break;
- case LayoutingType.Y:
- if (top == 0) {
-
- if (Parent.RegisteredLayoutings.HasFlag (LayoutingType.Height) ||
- RegisteredLayoutings.HasFlag (LayoutingType.Height))
- return false;
-
- switch (verticalAlignment) {
- case VerticalAlignment.Top://this could be processed even if parent Height is not known
- Slot.Y = 0;
- break;
- case VerticalAlignment.Bottom:
- Slot.Y = Parent.ClientRectangle.Height - Slot.Height;
- break;
- case VerticalAlignment.Center:
- Slot.Y = Parent.ClientRectangle.Height / 2 - Slot.Height / 2;
- break;
- }
- } else
- Slot.Y = top;
-
- if (LastSlots.Y == Slot.Y)
- break;
-
- IsDirty = true;
-
- OnLayoutChanges (layoutType);
-
- LastSlots.Y = Slot.Y;
- break;
- case LayoutingType.Width:
- if (isVisible) {
- if (Width.IsFixed)
- Slot.Width = Width;
- else if (Width == Measure.Fit) {
- Slot.Width = measureRawSize (LayoutingType.Width);
- } else if (Parent.RegisteredLayoutings.HasFlag (LayoutingType.Width))
- return false;
- else if (Width == Measure.Stretched)
- Slot.Width = Parent.ClientRectangle.Width;
- else
- Slot.Width = (int)Math.Round ((double)(Parent.ClientRectangle.Width * Width) / 100.0);
-
- if (Slot.Width < 0)
- return false;
-
- //size constrain
- if (Slot.Width < minimumSize.Width) {
- Slot.Width = minimumSize.Width;
- //NotifyValueChanged ("WidthPolicy", Measure.Stretched);
- } else if (Slot.Width > maximumSize.Width && maximumSize.Width > 0) {
- Slot.Width = maximumSize.Width;
- //NotifyValueChanged ("WidthPolicy", Measure.Stretched);
- }
- } else
- Slot.Width = 0;
-
- if (LastSlots.Width == Slot.Width)
- break;
-
- IsDirty = true;
-
- OnLayoutChanges (layoutType);
-
- LastSlots.Width = Slot.Width;
- break;
- case LayoutingType.Height:
- if (isVisible) {
- if (Height.IsFixed)
- Slot.Height = Height;
- else if (Height == Measure.Fit) {
- Slot.Height = measureRawSize (LayoutingType.Height);
- } else if (Parent.RegisteredLayoutings.HasFlag (LayoutingType.Height))
- return false;
- else if (Height == Measure.Stretched)
- Slot.Height = Parent.ClientRectangle.Height;
- else
- Slot.Height = (int)Math.Round ((double)(Parent.ClientRectangle.Height * Height) / 100.0);
-
- if (Slot.Height < 0)
- return false;
-
- //size constrain
- if (Slot.Height < minimumSize.Height) {
- Slot.Height = minimumSize.Height;
- //NotifyValueChanged ("HeightPolicy", Measure.Stretched);
- } else if (Slot.Height > maximumSize.Height && maximumSize.Height > 0) {
- Slot.Height = maximumSize.Height;
- //NotifyValueChanged ("HeightPolicy", Measure.Stretched);
- }
- } else
- Slot.Height = 0;
-
- if (LastSlots.Height == Slot.Height)
- break;
-
- IsDirty = true;
-
- OnLayoutChanges (layoutType);
-
- LastSlots.Height = Slot.Height;
- break;
- }
-
- //if no layouting remains in queue for item, registre for redraw
- if (this.registeredLayoutings == LayoutingType.None && IsDirty)
- IFace.EnqueueForRepaint (this);
-
- return true;
- }
- #endregion
-
- #region Rendering
- /// <summary> This is the common overridable drawing routine to create new widget </summary>
- protected virtual void onDraw(Context gr)
- {
- #if DEBUG_LOG
- DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GODraw, this);
- #endif
-
- Rectangle rBack = new Rectangle (Slot.Size);
-
- background.SetAsSource (gr, rBack);
- CairoHelpers.CairoRectangle (gr, rBack, cornerRadius);
- gr.Fill ();
-
- #if DEBUG_LOG
- dbgEvt.end = DebugLog.chrono.ElapsedTicks;
- #endif
- }
-
- /// <summary>
- /// Internal drawing context creation on a cached surface limited to slot size
- /// this trigger the effective drawing routine </summary>
- protected virtual void RecreateCache ()
- {
- #if DEBUG_LOG
- DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GORecreateCache, this);
- #endif
-
- /*if (bmp == null)
- bmp = IFace.surf.CreateSimilar (Content.ColorAlpha, Slot.Width, Slot.Height);
- else if (LastPaintedSlot.Width != Slot.Width || LastPaintedSlot.Height != Slot.Height)
- bmp.SetSize (Slot.Width, Slot.Height);*/
- bmp?.Dispose ();
- bmp = new ImageSurface(Format.Argb32, Slot.Width, Slot.Height);
-
- using (Context gr = new Context (bmp)) {
- gr.Antialias = Interface.Antialias;
- onDraw (gr);
- }
-
- IsDirty = false;
-
- #if DEBUG_LOG
- dbgEvt.end = DebugLog.chrono.ElapsedTicks;
- #endif
- }
- protected virtual void UpdateCache(Context ctx){
- #if DEBUG_LOG
- DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GOUpdateCacheAndPaintOnCTX, this);
- #endif
-
- Rectangle rb = Slot + Parent.ClientRectangle.Position;
- if (clearBackground) {
- ctx.Save ();
- ctx.Operator = Operator.Clear;
- ctx.Rectangle (rb);
- ctx.Fill ();
- ctx.Restore ();
- }
-
- ctx.SetSourceSurface (bmp, rb.X, rb.Y);
- ctx.Paint ();
- Clipping.Dispose ();
- Clipping = new Region ();
- #if DEBUG_LOG
- dbgEvt.end = DebugLog.chrono.ElapsedTicks;
- #endif
- }
- /// <summary> Chained painting routine on the parent context of the actual cached version
- /// of the widget </summary>
- public virtual void Paint (ref Context ctx)
- {
- #if DEBUG_LOG
- DebugLog.AddEvent(DbgEvtType.GOPaint, this);
- #endif
- //TODO:this test should not be necessary
- if (Slot.Height < 0 || Slot.Width < 0 || parent == null)
- return;
- lock (this) {
- if (cacheEnabled) {
- if (Slot.Width > Interface.MaxCacheSize || Slot.Height > Interface.MaxCacheSize)
- cacheEnabled = false;
- }
-
- if (cacheEnabled) {
- if (IsDirty)
- RecreateCache ();
-
- UpdateCache (ctx);
- if (!isEnabled)
- paintDisabled (ctx, Slot + Parent.ClientRectangle.Position);
- } else {
- Rectangle rb = Slot + Parent.ClientRectangle.Position;
- ctx.Save ();
-
- ctx.Translate (rb.X, rb.Y);
-
- onDraw (ctx);
- if (!isEnabled)
- paintDisabled (ctx, Slot);
-
- ctx.Restore ();
- }
- LastPaintedSlot = Slot;
- }
- }
- void paintDisabled(Context gr, Rectangle rb){
- gr.Operator = Operator.Xor;
- gr.SetSourceRGBA (0.6, 0.6, 0.6, 0.3);
- gr.Rectangle (rb);
- gr.Fill ();
- gr.Operator = Operator.Over;
- }
- #endregion
-
- #region Keyboard handling
- public virtual void onKeyDown(object sender, KeyEventArgs e){
- KeyDown.Raise (this, e);
- }
- public virtual void onKeyUp(object sender, KeyEventArgs e){
- KeyUp.Raise (this, e);
- }
- public virtual void onKeyPress(object sender, KeyPressEventArgs e){
- KeyPress.Raise (this, e);
- }
- #endregion
-
- #region Mouse handling
- /// <summary>
- /// Recursive local coordinate point test.
- /// After test on parent, point m is in local coord system.
- /// </summary>
- /// <returns>return true, if point is in the bounds of this control</returns>
- /// <param name="m">by ref point to test, init value is not kept</param>
- public virtual bool PointIsIn(ref Point m)
- {
- if (parent == null)
- return false;
- if (!(isVisible & isEnabled)||IsDragged)
- return false;
- if (!parent.PointIsIn(ref m))
- return false;
- m -= (parent.getSlot().Position + parent.ClientRectangle.Position) ;
- return Slot.ContainsOrIsEqual (m);
- }
- public virtual bool MouseIsIn(Point m)
- {
- return (!(isVisible & isEnabled)||IsDragged) ? false : PointIsIn (ref m);
- }
- public virtual void checkHoverWidget(MouseMoveEventArgs e)
- {
- if (IFace.HoverWidget != this) {
- IFace.HoverWidget = this;
- onMouseEnter (this, e);
- }
-
- //this.onMouseMove (this, e);//without this, window border doesn't work, should be removed
- }
- public virtual void onMouseMove(object sender, MouseMoveEventArgs e)
- {
- if (allowDrag & hasFocus & e.Mouse.LeftButton == ButtonState.Pressed) {
- if (IFace.DragAndDropOperation == null) {
- IFace.DragAndDropOperation = new DragDropEventArgs (this);
- onStartDrag (this, IFace.DragAndDropOperation);
- }
- }
-
- //dont bubble event if dragged, mouse move is routed directely from iface
- //to let other control behind have mouse entering
- if (isDragged)
- return;
-
- //bubble event to the top
- GraphicObject p = focusParent;
- if (p != null)
- p.onMouseMove(sender,e);
-
- MouseMove.Raise (this, e);
- }
- public virtual void onMouseDown(object sender, MouseButtonEventArgs e){
- #if DEBUG_FOCUS
- Debug.WriteLine("MOUSE DOWN => " + this.ToString());
- #endif
-
- if (focusable && !Interface.FocusOnHover) {
- BubblingMouseButtonEventArg be = e as BubblingMouseButtonEventArg;
- if (be.Focused == null) {
- be.Focused = this;
- IFace.FocusedWidget = this;
- if (e.Button == MouseButton.Right && contextCommands != null)
- IFace.ShowContextMenu (this);
- }
- }
- //bubble event to the top
- GraphicObject p = focusParent;
- if (p != null)
- p.onMouseDown(sender,e);
-
- MouseDown.Raise (this, e);
- }
- public virtual void onMouseUp(object sender, MouseButtonEventArgs e){
- #if DEBUG_FOCUS
- Debug.WriteLine("MOUSE UP => " + this.ToString());
- #endif
-
- if (IFace.DragAndDropOperation != null){
- if (IFace.DragAndDropOperation.DragSource == this) {
- if (IFace.DragAndDropOperation.DropTarget != null)
- onDrop (this, IFace.DragAndDropOperation);
- else
- onEndDrag (this, IFace.DragAndDropOperation);
- IFace.DragAndDropOperation = null;
- }
- }
-
- //bubble event to the top
- GraphicObject p = focusParent;
- if (p != null)
- p.onMouseUp(sender,e);
-
- MouseUp.Raise (this, e);
- }
- public virtual void onMouseClick(object sender, MouseButtonEventArgs e){
-#if DEBUG_FOCUS
- Debug.WriteLine("CLICK => " + this.ToString());
-#endif
- if (MouseClick != null)
- {
- MouseClick.Raise(this, e);
- return;
- }
- GraphicObject p = focusParent;
- if (p != null)
- p.onMouseClick(sender,e);
- }
- public virtual void onMouseDoubleClick(object sender, MouseButtonEventArgs e){
-#if DEBUG_FOCUS
- Debug.WriteLine("DOUBLE CLICK => " + this.ToString());
-#endif
- if (MouseDoubleClick != null)
- {
- MouseDoubleClick.Raise(this, e);
- return;
- }
- GraphicObject p = focusParent;
- if (p != null)
- p.onMouseDoubleClick(sender,e);
- }
- public virtual void onMouseWheel(object sender, MouseWheelEventArgs e){
- if (MouseWheelChanged != null)
- {
- MouseWheelChanged.Raise(this, e);
- return;
- }
- GraphicObject p = focusParent;
- if (p != null)
- p.onMouseWheel(sender,e);
- }
- public virtual void onMouseEnter(object sender, MouseMoveEventArgs e)
- {
- #if DEBUG_FOCUS
- Debug.WriteLine("MouseEnter => " + this.ToString());
- #endif
-
- if (IFace.DragAndDropOperation != null) {
- GraphicObject g = this;
- while (g != null) {
- if (g.AllowDrop) {
- if (IFace.DragAndDropOperation.DragSource != this && IFace.DragAndDropOperation.DropTarget != this) {
- if (IFace.DragAndDropOperation.DropTarget != null)
- IFace.DragAndDropOperation.DropTarget.onDragLeave (this, IFace.DragAndDropOperation);
- g.onDragEnter (this, IFace.DragAndDropOperation);
- }
- break;
- }
- g = g.focusParent;
- }
- }
-
- MouseEnter.Raise (this, e);
- }
- public virtual void onMouseLeave(object sender, MouseMoveEventArgs e)
- {
- #if DEBUG_FOCUS
- Debug.WriteLine("MouseLeave => " + this.ToString());
- #endif
-
- MouseLeave.Raise (this, e);
- }
-
- #endregion
-
- protected virtual void onFocused(object sender, EventArgs e){
- if (IFace.FocusedWidget != this)
- IFace.FocusedWidget = this;
- #if DEBUG_FOCUS
- Debug.WriteLine("Focused => " + this.ToString());
- #endif
- Focused.Raise (this, e);
- }
- protected virtual void onUnfocused(object sender, EventArgs e){
- #if DEBUG_FOCUS
- Debug.WriteLine("UnFocused => " + this.ToString());
- #endif
- Unfocused.Raise (this, e);
- }
- public virtual void onEnable(object sender, EventArgs e){
- Enabled.Raise (this, e);
- }
- public virtual void onDisable(object sender, EventArgs e){
- Disabled.Raise (this, e);
- }
- protected virtual void onParentChanged(object sender, DataSourceChangeEventArgs e) {
-// if (e.NewDataSource != null) {
-// if (width == Measure.Inherit)
-// RegisterForLayouting (LayoutingType.Width);
-// if (height == Measure.Inherit)
-// RegisterForLayouting (LayoutingType.Height);
-// }
-
- ParentChanged.Raise (this, e);
- if (logicalParent == null)
- LogicalParentChanged.Raise (this, e);
- }
- protected virtual void onLogicalParentChanged(object sender, DataSourceChangeEventArgs e) {
- LogicalParentChanged.Raise (this, e);
- }
- internal void ClearTemplateBinding(){
- #if DEBUG_UPDATE
- Debug.WriteLine (string.Format("ClearTemplateBinding: {0}", this.ToString()));
- #endif
- if (ValueChanged == null)
- return;
- EventInfo eiEvt = this.GetType().GetEvent ("ValueChanged");
- foreach (Delegate d in ValueChanged.GetInvocationList()) {
- if (d.Method.Name == "dyn_tmpValueChanged") {
- eiEvt.RemoveEventHandler (this, d);
- #if DEBUG_BINDING
- Debug.WriteLine ("\t{0} template binding handler removed in {1} for: {2}", d.Method.Name, this, "ValueChanged");
- #endif
- }
- }
- }
- public override string ToString ()
- {
- string tmp ="";
-
- if (Parent != null)
- tmp = Parent.ToString () + tmp;
- #if DEBUG_LAYOUTING
- return Name == "unamed" ? tmp + "." + this.GetType ().Name + GraphicObjects.IndexOf(this).ToString(): tmp + "." + Name;
- #else
- return string.IsNullOrEmpty(Name) ? tmp + "." + this.GetType ().Name : tmp + "." + Name;
- #endif
- }
- /// <summary>
- /// Checks to handle when widget is removed from the visible graphic tree
- /// </summary>
- void unshownPostActions () {
- if (IFace.HoverWidget != null) {
- if (IFace.HoverWidget.IsOrIsInside (this)) {
- IFace.HoverWidget = null;
- IFace.ProcessMouseMove (IFace.Mouse.X, IFace.Mouse.Y);
- }
- }
- if (IFace.ActiveWidget != null) {
- if (IFace.ActiveWidget.IsOrIsInside (this))
- IFace.ActiveWidget = null;
- }
- if (IFace.FocusedWidget != null) {
- if (IFace.FocusedWidget.IsOrIsInside (this))
- IFace.FocusedWidget = null;
- }
- }
- }
-}
int idx = curY * ColumnCount + curX;
if (idx >= Children.Count)
return;
- GraphicObject c = Children [idx];
+ Widget c = Children [idx];
if (!c.Visible)
continue;
c.Slot.X = curX * (slotWidth + Spacing);
namespace Crow
{
- public class Group : GraphicObject
+ public class Group : Widget
{
#if DESIGN_MODE
- public override bool FindByDesignID(string designID, out GraphicObject go){
+ public override bool FindByDesignID(string designID, out Widget go){
go = null;
if (base.FindByDesignID (designID, out go))
return true;
childrenRWLock.EnterReadLock ();
- foreach (GraphicObject w in Children) {
+ foreach (Widget w in Children) {
if (!w.FindByDesignID (designID, out go))
continue;
childrenRWLock.ExitReadLock ();
if (this.design_isTGItem)
return;
base.getIML (doc, parentElem);
- foreach (GraphicObject g in Children) {
+ foreach (Widget g in Children) {
g.getIML (doc, parentElem.LastChild);
}
}
public event EventHandler<EventArgs> ChildrenCleared;
#endregion
- internal GraphicObject largestChild = null;
- internal GraphicObject tallestChild = null;
+ internal Widget largestChild = null;
+ internal Widget tallestChild = null;
bool _multiSelect = false;
- List<GraphicObject> children = new List<GraphicObject>();
+ List<Widget> children = new List<Widget>();
- public virtual List<GraphicObject> Children {
+ public virtual List<Widget> Children {
get { return children; }
}
[DefaultValue(false)]
get { return _multiSelect; }
set { _multiSelect = value; }
}
- public virtual void AddChild(GraphicObject g){
+ public virtual void AddChild(Widget g){
childrenRWLock.EnterWriteLock();
g.Parent = this;
g.LayoutChanged += OnChildLayoutChanges;
g.RegisterForLayouting (LayoutingType.Sizing | LayoutingType.ArrangeChildren);
}
- public virtual void RemoveChild(GraphicObject child)
+ public virtual void RemoveChild(Widget child)
{
child.LayoutChanged -= OnChildLayoutChanges;
//check if HoverWidget is removed from Tree
this.RegisterForLayouting (LayoutingType.Sizing | LayoutingType.ArrangeChildren);
}
- public virtual void DeleteChild(GraphicObject child)
+ public virtual void DeleteChild(Widget child)
{
RemoveChild (child);
child.Dispose ();
}
- public virtual void InsertChild (int idx, GraphicObject g) {
+ public virtual void InsertChild (int idx, Widget g) {
childrenRWLock.EnterWriteLock ();
g.Parent = this;
childrenRWLock.EnterWriteLock ();
while (Children.Count > 0) {
- GraphicObject g = Children [Children.Count - 1];
+ Widget g = Children [Children.Count - 1];
g.LayoutChanged -= OnChildLayoutChanges;
Children.RemoveAt (Children.Count - 1);
g.Dispose ();
base.OnDataSourceChanged (this, e);
childrenRWLock.EnterReadLock ();
- foreach (GraphicObject g in Children) {
+ foreach (Widget g in Children) {
if (g.localDataSourceIsNull & g.localLogicalParentIsNull)
g.OnDataSourceChanged (g, e);
}
childrenRWLock.ExitReadLock ();
}
- public void putWidgetOnTop(GraphicObject w)
+ public void putWidgetOnTop(Widget w)
{
if (Children.Contains(w))
{
childrenRWLock.ExitWriteLock ();
}
}
- public void putWidgetOnBottom(GraphicObject w)
+ public void putWidgetOnBottom(Widget w)
{
if (Children.Contains(w))
{
#region GraphicObject overrides
- public override GraphicObject FindByName (string nameToFind)
+ public override Widget FindByName (string nameToFind)
{
if (Name == nameToFind)
return this;
- GraphicObject tmp = null;
+ Widget tmp = null;
childrenRWLock.EnterReadLock ();
- foreach (GraphicObject w in Children) {
+ foreach (Widget w in Children) {
tmp = w.FindByName (nameToFind);
if (tmp != null)
break;
return tmp;
}
- public override bool Contains (GraphicObject goToFind)
+ public override bool Contains (Widget goToFind)
{
- foreach (GraphicObject w in Children) {
+ foreach (Widget w in Children) {
if (w == goToFind)
return true;
if (w.Contains (goToFind))
//position smaller objects in group when group size is fit
switch (layoutType) {
case LayoutingType.Width:
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
if (c.Width.IsRelativeToParent)
c.RegisterForLayouting (LayoutingType.Width);
else
}
break;
case LayoutingType.Height:
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
if (c.Height.IsRelativeToParent)
c.RegisterForLayouting (LayoutingType.Height);
else
childrenRWLock.EnterReadLock ();
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
if (!c.Visible)
continue;
if (Clipping.Contains (c.Slot + ClientRectangle.Position) == RegionOverlap.Out)
public virtual void OnChildLayoutChanges (object sender, LayoutingEventArgs arg)
{
- GraphicObject g = sender as GraphicObject;
+ Widget g = sender as Widget;
switch (arg.LayoutType) {
case LayoutingType.Width:
protected override void Dispose (bool disposing)
{
if (disposing) {
- foreach (GraphicObject c in children)
+ foreach (Widget c in children)
c.Dispose ();
}
base.Dispose (disposing);
/// </summary>
/// <remarks>
/// </remarks>
- public class Image : GraphicObject
+ public class Image : Widget
{
Picture _pic;
string _svgSub;
namespace Crow
{
- public class Label : GraphicObject
+ public class Label : Widget
{
#region CTOR
protected Label () : base(){}
}
#endregion
- public override void AddItem (GraphicObject g)
+ public override void AddItem (Widget g)
{
base.AddItem (g);
}
#endregion
- public override void AddItem (GraphicObject g)
+ public override void AddItem (Widget g)
{
base.AddItem (g);
g.NotifyValueChanged ("PopDirection", Alignment.Right);
}
- protected override void loadTemplate (GraphicObject template)
+ protected override void loadTemplate (Widget template)
{
base.loadTemplate (template);
NotifyValueChanged ("MsgIcon", "#Crow.Icons.iconInfo.svg");
bool _isPopped, _canPop;
Alignment popDirection;
- GraphicObject _content;
+ Widget _content;
Measure popWidth, popHeight;
public event EventHandler Popped;
}
#endregion
- public override GraphicObject Content {
+ public override Widget Content {
get { return _content; }
set {
if (_content != null) {
/// behave exactely as a container for layouting and drawing
/// </summary>
[DesignIgnore]
- public class PrivateContainer : GraphicObject
+ public class PrivateContainer : Widget
{
#region CTOR
protected PrivateContainer () : base(){}
#endregion
#if DESIGN_MODE
- public override bool FindByDesignID(string designID, out GraphicObject go){
+ public override bool FindByDesignID(string designID, out Widget go){
go = null;
if (base.FindByDesignID (designID, out go))
return true;
return child.FindByDesignID (designID, out go);
}
#endif
- protected GraphicObject child;
+ protected Widget child;
#if DEBUG_LOG
internal GraphicObject getTemplateRoot {
get { return child; }
}
#endif
- protected virtual void SetChild(GraphicObject _child)
+ protected virtual void SetChild(Widget _child)
{
if (child != null) {
this.RegisterForGraphicUpdate ();
}
- child = _child as GraphicObject;
+ child = _child as Widget;
if (child != null) {
child.Parent = this;
}
//dispose child if not null
protected virtual void deleteChild () {
- GraphicObject g = child;
+ Widget g = child;
SetChild (null);
if (g != null)
g.Dispose ();
#region GraphicObject Overrides
- public override GraphicObject FindByName (string nameToFind)
+ public override Widget FindByName (string nameToFind)
{
if (Name == nameToFind)
return this;
return child == null ? null : child.FindByName (nameToFind);
}
- public override bool Contains (GraphicObject goToFind)
+ public override bool Contains (Widget goToFind)
{
return child == goToFind ? true :
child == null ? false : child.Contains(goToFind);
}
public virtual void OnChildLayoutChanges (object sender, LayoutingEventArgs arg)
{
- GraphicObject g = sender as GraphicObject;
+ Widget g = sender as Widget;
if (arg.LayoutType == LayoutingType.Width) {
if (Width != Measure.Fit)
public ProgressBar(Interface iface) : base(iface){}
#endregion
- protected override void loadTemplate (GraphicObject template)
+ protected override void loadTemplate (Widget template)
{
}
}
#endregion
- public override void SetChild (GraphicObject _child)
+ public override void SetChild (Widget _child)
{
Group g = child as Group;
if (g != null)
/// generic class to build scrolling control in both directions
/// </summary>
[DesignIgnore]
- public class ScrollingObject : GraphicObject
+ public class ScrollingObject : Widget
{
#region CTOR
protected ScrollingObject ():base(){}
}
}
- public class Shape : GraphicObject
+ public class Shape : Widget
{
#region CTOR
protected Shape () : base() {}
#region implemented abstract members of TemplatedControl
- protected override void loadTemplate (GraphicObject template = null)
+ protected override void loadTemplate (Widget template = null)
{
}
/// control to add between children of a Stack to allow them to be resized
/// with the pointer
/// </summary>
- public class Splitter : GraphicObject
+ public class Splitter : Widget
{
#region CTOR
protected Splitter() : base(){}
Unit u1, u2;
int init1 = -1, init2 = -1, delta = 0, min1, min2, max1 , max2;
- GraphicObject go1 = null, go2 = null;
+ Widget go1 = null, go2 = null;
void initSplit(Measure m1, int size1, Measure m2, int size2){
if (m1 != Measure.Stretched) {
u2 = m2.Units;
}
}
- void convertSizeInPix(GraphicObject g1){
+ void convertSizeInPix(Widget g1){
}
internal TabView tview = null;
#region Private fields
- GraphicObject titleWidget;
+ Widget titleWidget;
int tabOffset;
bool isSelected;
Measure tabThickness;
#endregion
#region TemplatedControl overrides
- public override GraphicObject Content {
+ public override Widget Content {
get {
return _contentContainer == null ? null : _contentContainer.Child;
}
value.LogicalParent = this;
}
}
- protected override void loadTemplate(GraphicObject template = null)
+ protected override void loadTemplate(Widget template = null)
{
base.loadTemplate (template);
titleWidget = this.child.FindByName ("TabTitle");
}
- internal GraphicObject TabTitle { get { return titleWidget; }}
+ internal Widget TabTitle { get { return titleWidget; }}
#endregion
/// <summary>
}
#endregion
- public override void AddChild (GraphicObject child)
+ public override void AddChild (Widget child)
{
TabItem ti = child as TabItem;
if (ti == null)
SelectedTab = ti.ViewIndex = Children.Count - 1;
this.RegisterForLayouting (LayoutingType.ArrangeChildren);
}
- public override void RemoveChild (GraphicObject child)
+ public override void RemoveChild (Widget child)
{
TabItem ti = child as TabItem;
if (ti == null)
}
void Ti_MouseDown (object sender, MouseButtonEventArgs e)
{
- SelectedTab = Children.IndexOf (sender as GraphicObject);
+ SelectedTab = Children.IndexOf (sender as Widget);
}
}
}
/// <summary>
/// Single child of this templated container.
/// </summary>
- public virtual GraphicObject Content {
+ public virtual Widget Content {
get {
return _contentContainer == null ? null : _contentContainer.Child;
}
get { return _contentContainer?.Child != null; }
}
//TODO: move loadTemplate and ResolveBinding in TemplatedContainer
- protected override void loadTemplate(GraphicObject template = null)
+ protected override void loadTemplate(Widget template = null)
{
base.loadTemplate (template);
_contentContainer = this.child.FindByName ("Content") as Container;
}
#region GraphicObject overrides
- public override GraphicObject FindByName (string nameToFind)
+ public override Widget FindByName (string nameToFind)
{
if (Name == nameToFind)
return this;
return Content == null ? null : Content.FindByName (nameToFind);
}
- public override bool Contains (GraphicObject goToFind)
+ public override bool Contains (Widget goToFind)
{
if (Content == goToFind)
return true;
/// </summary>
/// <returns>widget identified by name, or null if not found</returns>
/// <param name="nameToFind">widget's name to find</param>
- public override GraphicObject FindByName (string nameToFind) => nameToFind == this.Name ? this : null;
+ public override Widget FindByName (string nameToFind) => nameToFind == this.Name ? this : null;
/// <summary>
///onDraw is overrided to prevent default drawing of background, template top container
/// Entry assembly is search first, then the one where the type is defined
/// </summary>
/// <param name="template">Optional template instance</param>
- protected virtual void loadTemplate(GraphicObject template = null)
+ protected virtual void loadTemplate(Widget template = null)
{
if (this.child != null)//template change, bindings has to be reset
this.ClearTemplateBinding();
it.getIML (doc, parentElem.LastChild);
}
- foreach (GraphicObject g in Items) {
+ foreach (Widget g in Items) {
g.getIML (doc, parentElem.LastChild);
}
}
/// Keep track of expanded subnodes and closed time to unload
/// </summary>
//Dictionary<GraphicObject, Stopwatch> nodes = new Dictionary<GraphicObject, Stopwatch>();
- internal List<GraphicObject> nodes = new List<GraphicObject>();
+ internal List<Widget> nodes = new List<Widget>();
/// <summary>
/// Item templates file path, on disk or embedded.
///
NotifyValueChanged("ItemTemplate", _itemTemplate);
}
}
- protected override void loadTemplate(GraphicObject template = null)
+ protected override void loadTemplate(Widget template = null)
{
base.loadTemplate (template);
}
#endregion
- public virtual List<GraphicObject> Items{
+ public virtual List<Widget> Items{
get {
return isPaged ? items.Children.SelectMany(x => (x as Group).Children).ToList()
: items.Children;
}
- public virtual void AddItem(GraphicObject g){
+ public virtual void AddItem(Widget g){
items.AddChild (g);
g.LogicalParent = this;
NotifyValueChanged ("HasChildren", true);
}
- public virtual void RemoveItem(GraphicObject g)
+ public virtual void RemoveItem(Widget g)
{
g.LogicalParent = null;
items.DeleteChild (g);
#region GraphicObject overrides
- public override GraphicObject FindByName (string nameToFind)
+ public override Widget FindByName (string nameToFind)
{
if (Name == nameToFind)
return this;
- foreach (GraphicObject w in Items) {
- GraphicObject r = w.FindByName (nameToFind);
+ foreach (Widget w in Items) {
+ Widget r = w.FindByName (nameToFind);
if (r != null)
return r;
}
return null;
}
- public override bool Contains (GraphicObject goToFind)
+ public override bool Contains (Widget goToFind)
{
- foreach (GraphicObject w in Items) {
+ foreach (Widget w in Items) {
if (w == goToFind)
return true;
if (w.Contains (goToFind))
protected void loadItem(object o, Group page, string _dataTest){
if (o == null)//TODO:surely a threading sync problem
return;
- GraphicObject g = null;
+ Widget g = null;
ItemTemplate iTemp = null;
Type dataType = o.GetType ();
string itempKey = dataType.FullName;
}
}
internal virtual void itemClick(object sender, MouseButtonEventArgs e){
- SelectedIndex = data.IndexOf((sender as GraphicObject).DataSource);
+ SelectedIndex = data.IndexOf((sender as Widget).DataSource);
}
- bool emitHelperIsAlreadyExpanded (GraphicObject go){
+ bool emitHelperIsAlreadyExpanded (Widget go){
if (nodes.Contains (go))
return true;
nodes.Add (go);
namespace Crow
{
- public class TestCairoPatch : GraphicObject
+ public class TestCairoPatch : Widget
{
void computeControlPoints (
double xc, double yc,
namespace Crow
{
[DesignIgnore]
- public class TextRun : GraphicObject
+ public class TextRun : Widget
{
#region CTOR
protected TextRun () : base(){}
//if their are expandable, some functions and events are added
public class TreeView : TemplatedGroup
{
- GraphicObject selectedItemContainer = null;
+ Widget selectedItemContainer = null;
bool isRoot;
#region CTOR
internal override void itemClick (object sender, MouseButtonEventArgs e)
{
- GraphicObject tmp = sender as GraphicObject;
+ Widget tmp = sender as Widget;
if (!tmp.HasFocus)
return;
/*if (selectedItemContainer != null) {
public void ExpandAll(){
foreach (Group grp in items.Children) {
- foreach (GraphicObject go in grp.Children) {
+ foreach (Widget go in grp.Children) {
Expandable exp = go as Expandable;
if (exp == null)
continue;
namespace Crow
{
- public class Trend : GraphicObject
+ public class Trend : Widget
{
#region private fields
double minValue, maxValue, lowThreshold, highThreshold;
--- /dev/null
+//
+// GraphicObject.cs
+//
+// Author:
+// Jean-Philippe Bruyère <jp.bruyere@hotmail.com>
+//
+// Copyright (c) 2013-2017 Jean-Philippe Bruyère
+//
+// Permission is hereby granted, free of charge, to any person obtaining a copy
+// of this software and associated documentation files (the "Software"), to deal
+// in the Software without restriction, including without limitation the rights
+// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+// copies of the Software, and to permit persons to whom the Software is
+// furnished to do so, subject to the following conditions:
+//
+// The above copyright notice and this permission notice shall be included in
+// all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+// THE SOFTWARE.
+
+using System;
+using System.Collections.Generic;
+using System.ComponentModel;
+using System.Xml.Serialization;
+using System.Reflection;
+using System.Reflection.Emit;
+using System.Runtime.CompilerServices;
+using Cairo;
+using System.Diagnostics;
+using Crow.IML;
+using System.Threading;
+
+
+#if DESIGN_MODE
+using System.Xml;
+using System.IO;
+#endif
+
+namespace Crow
+{
+ /// <summary>
+ /// The base class for all the graphic tree elements.
+ /// </summary>
+ public class Widget : ILayoutable, IValueChange, IDisposable
+ {
+ internal ReaderWriterLockSlim parentRWLock = new ReaderWriterLockSlim();
+ #if DEBUG_LOG
+ //0 is the main graphic tree, for other obj tree not added to main tree, it range from 1->n
+ //useful to track events for obj shown later, not on start, or never added to main tree
+ public int treeIndex;
+ public int yIndex;//absolute index in the graphic tree for debug draw
+ public int xLevel;//x increment for debug draw
+ #endif
+ #if DESIGN_MODE
+ static MethodInfo miDesignAddDefLoc = typeof(Widget).GetMethod("design_add_style_location",
+ BindingFlags.Instance | BindingFlags.NonPublic);
+ static MethodInfo miDesignAddValLoc = typeof(Widget).GetMethod("design_add_iml_location",
+ BindingFlags.Instance | BindingFlags.NonPublic);
+
+ public volatile bool design_HasChanged = false;
+ public string design_id;
+ public int design_line;
+ public int design_column;
+ public string design_imlPath;
+ public bool design_isTGItem = false;//true if this is a templated item's root
+ public Dictionary<string,string> design_iml_values = new Dictionary<string, string>();
+ public Dictionary<string,string> design_style_values = new Dictionary<string, string>();
+ //public Dictionary<string,FileLocation> design_iml_locations = new Dictionary<string, FileLocation>();
+ public Dictionary<string,FileLocation> design_style_locations = new Dictionary<string, FileLocation>();
+
+ internal void design_add_style_location (string memberName, string path, int line, int col) {
+ if (design_style_locations.ContainsKey(memberName)){
+ Console.WriteLine ("default value localtion already set for {0}{1}.{2}", this.GetType().Name, this.design_id, memberName);
+ return;
+ }
+ design_style_locations.Add(memberName, new FileLocation(path,line,col));
+ }
+// internal void design_add_iml_location (string memberName, string path, int line, int col) {
+// if (design_iml_locations.ContainsKey(memberName)){
+// Console.WriteLine ("IML value localtion already set for {0}{1}.{2}", this.GetType().Name, this.design_id, memberName);
+// return;
+// }
+// design_iml_locations.Add(memberName, new FileLocation(path,line,col));
+// }
+
+ public virtual bool FindByDesignID(string designID, out Widget go){
+ go = null;
+ if (this.design_id == designID){
+ go = this;
+ return true;
+ }
+ return false;
+ }
+
+ public string GetIML(){
+ XmlDocument doc = new XmlDocument( );
+
+ using (StringWriter sw = new StringWriter ()) {
+ XmlWriterSettings settings = new XmlWriterSettings {
+ Indent = true,
+ IndentChars = "\t",
+ };
+ using (XmlWriter xtw = XmlWriter.Create (sw, settings)) {
+ //(1) the xml declaration is recommended, but not mandatory
+ XmlDeclaration xmlDeclaration = doc.CreateXmlDeclaration ("1.0", "UTF-8", null);
+ doc.InsertBefore (xmlDeclaration, null);
+ getIML (doc, (XmlNode)doc);
+ doc.WriteTo (xtw);
+ }
+ this.design_HasChanged = false;
+ return sw.ToString ();
+ }
+ }
+
+ public virtual void getIML(XmlDocument doc, XmlNode parentElem) {
+ if (this.design_isTGItem)
+ return;
+
+ XmlElement xe = doc.CreateElement(this.GetType().Name);
+
+ foreach (KeyValuePair<string,string> kv in design_iml_values) {
+ XmlAttribute xa = doc.CreateAttribute (kv.Key);
+ xa.Value = kv.Value;
+ xe.Attributes.Append (xa);
+ }
+
+ parentElem.AppendChild (xe);
+ }
+ public Surface CreateIcon (int dragIconSize = 32) {
+ ImageSurface di = new ImageSurface (Format.Argb32, dragIconSize, dragIconSize);
+ using (Context ctx = new Context (di)) {
+ double div = Math.Max (LastPaintedSlot.Width, LastPaintedSlot.Height);
+ double s = (double)dragIconSize / div;
+ ctx.Scale (s, s);
+ if (bmp == null)
+ this.onDraw (ctx);
+ else {
+ if (LastPaintedSlot.Width>LastPaintedSlot.Height)
+ ctx.SetSourceSurface (bmp, 0, (LastPaintedSlot.Width-LastPaintedSlot.Height)/2);
+ else
+ ctx.SetSourceSurface (bmp, (LastPaintedSlot.Height-LastPaintedSlot.Width)/2, 0);
+ ctx.Paint ();
+ }
+ }
+ return di;
+ }
+ public string DesignName {
+ get { return GetType ().Name + design_id; }
+ }
+ #endif
+
+ #region IDisposable implementation
+ protected bool disposed = false;
+
+ public void Dispose(){
+ Dispose(true);
+ GC.SuppressFinalize(this);
+ }
+ ~Widget(){
+ Debug.WriteLine(this.ToString() + " not disposed by user");
+ Dispose(false);
+ }
+ protected virtual void Dispose(bool disposing){
+ if (disposed){
+ #if DEBUG_DISPOSE
+ Debug.WriteLine ("Trying to dispose already disposed obj: {0}", this.ToString());
+ #endif
+ return;
+ }
+
+ if (disposing) {
+ #if DEBUG_DISPOSE
+ Debug.WriteLine ("Disposing: {0}", this.ToString());
+ if (IsQueueForRedraw)
+ throw new Exception("Trying to dispose an object queued for Redraw: " + this.ToString());
+ #endif
+
+ unshownPostActions ();
+
+ if (!localDataSourceIsNull)
+ DataSource = null;
+
+ parentRWLock.EnterWriteLock();
+ parent = null;
+ parentRWLock.ExitWriteLock();
+ } else
+ Debug.WriteLine ("!!! Finalized by GC: {0}", this.ToString ());
+ Clipping?.Dispose ();
+ bmp?.Dispose ();
+ disposed = true;
+ }
+ #endregion
+
+ #if DEBUG_LOG
+ internal static List<GraphicObject> GraphicObjects = new List<GraphicObject>();
+ #endif
+
+ internal bool isPopup = false;
+ public Widget focusParent {
+ get { return (isPopup ? LogicalParent : parent) as Widget; }
+ }
+
+ /// <summary>
+ /// interface this widget is bound to, this should not be changed once the instance is created
+ /// </summary>
+ public Interface IFace = null;
+
+ /// <summary>
+ /// contains the dirty rectangles in the coordinate system of the cache. those dirty zones
+ /// are repeated at each cached levels of the tree with correspondig coordinate system. This is done
+ /// in a dedicated step of the update between layouting and drawing.
+ /// </summary>
+ public Region Clipping;
+
+ #region IValueChange implementation
+ /// <summary>
+ /// Raise to notify that the value of a property has changed, the binding system
+ /// rely mainly on this event. the member name may not be present in the class, this is
+ /// used in **propertyless** bindings, this allow to raise custom named events without needing
+ /// to create an new one in the class or a new property.
+ /// </summary>
+ public event EventHandler<ValueChangeEventArgs> ValueChanged;
+ /// <summary>
+ /// Helper function to raise the value changed event
+ /// </summary>
+ public virtual void NotifyValueChanged(string MemberName, object _value)
+ {
+ //Debug.WriteLine ("Value changed: {0}->{1} = {2}", this, MemberName, _value);
+ ValueChanged.Raise(this, new ValueChangeEventArgs(MemberName, _value));
+ }
+ #endregion
+
+ #region CTOR
+ /// <summary>
+ /// default private parameter less constructor use in instantiators, it should not be used
+ /// when creating widget from code because widgets has to be bound to an interface before any other
+ /// action.
+ /// </summary>
+ protected Widget () {
+ Clipping = new Region ();
+ #if DEBUG_LOG
+ GraphicObjects.Add (this);
+ DebugLog.AddEvent(DbgEvtType.GOClassCreation, this);
+ #endif
+ }
+ /// <summary>
+ /// This constructor **must** be used when creating widget from code.
+ ///
+ /// When creating new widgets derived from GraphicObject, both parameterless and this constructors are
+ /// facultatives, the compiler will create the parameterless one automaticaly if no other one exists.
+ /// But if you intend to be able to create instances of the new widget in code and override the constructor
+ /// with the Interface parameter, you **must** also provide the override of the parameterless constructor because
+ /// compiler will not create it automatically because of the presence of the other one.
+ /// </summary>
+ /// <param name="iface">Iface.</param>
+ public Widget (Interface iface) : this()
+ {
+ IFace = iface;
+ Initialize ();
+ }
+ #endregion
+ //internal bool initialized = false;
+ /// <summary>
+ /// Initialize this Graphic object instance by setting style and default values and loading template if required
+ /// </summary>
+ public virtual void Initialize(){
+ loadDefaultValues ();
+ }
+ #region private fields
+ LayoutingType registeredLayoutings = LayoutingType.All;
+ ILayoutable logicalParent;
+ ILayoutable parent;
+ string name;
+ Fill background = Color.Transparent;
+ Fill foreground = Color.White;
+ Font font = "sans, 10";
+ protected Measure width, height;
+ int left, top;
+ double cornerRadius = 0;
+ int margin = 0;
+ bool focusable = false;
+ bool hasFocus = false;
+ bool isActive = false;
+ //bool isHover = false;
+ bool mouseRepeat;
+ protected bool isVisible = true;
+ bool isEnabled = true;
+ VerticalAlignment verticalAlignment = VerticalAlignment.Center;
+ HorizontalAlignment horizontalAlignment = HorizontalAlignment.Center;
+ Size maximumSize = "0,0";
+ Size minimumSize = "0,0";
+ bool cacheEnabled = false;
+ bool clipToClientRect = true;
+ Type dataSourceType;
+ protected object dataSource;
+ bool rootDataLevel;
+ string style;
+ object tag;
+ bool isDragged;
+ bool allowDrag;
+ bool allowDrop;
+ string tooltip;
+ IList<Command> contextCommands;
+ #endregion
+
+ #region public fields
+ /// <summary>
+ /// Current size and position computed during layouting pass
+ /// </summary>
+ public Rectangle Slot = new Rectangle ();
+ /// <summary>
+ /// keep last slot components for each layouting pass to track
+ /// changes and trigger update of other component accordingly
+ /// </summary>
+ public Rectangle LastSlots;
+ /// <summary>
+ /// keep last slot painted on screen to clear traces if moved or resized
+ /// version to clear effective oldslot if parents have been moved or resized.
+ /// IDEA is to add a ScreenCoordinates function that use only lastPaintedSlots
+ /// </summary>
+ //TODO: we should ensure the whole parsed widget tree is the last painted
+ public Rectangle LastPaintedSlot;
+ /// <summary>Prevent requeuing multiple times the same widget</summary>
+ public bool IsQueueForClipping = false;
+ /// <summary>drawing Cache, if null, a redraw is done, cached or not</summary>
+ public Surface bmp;
+ public bool IsDirty = true;
+ /// <summary>
+ /// This size is computed on each child' layout changes.
+ /// In stacking widget, it is used to compute the remaining space for the stretched
+ /// widget inside the stack, which is never added to the contentSize, instead, its size
+ /// is deducted from (parent.ClientRectangle - contentSize)
+ /// </summary>
+ internal Size contentSize;
+ #endregion
+
+ #region ILayoutable
+ [XmlIgnore]public LayoutingType RegisteredLayoutings { get { return registeredLayoutings; } set { registeredLayoutings = value; } }
+ //TODO: it would save the recurent cost of a cast in event bubbling if parent type was GraphicObject
+ // or we could add to the interface the mouse events
+ /// <summary>
+ /// Parent in the graphic tree, used for rendering and layouting
+ /// </summary>
+ [XmlIgnore]public virtual ILayoutable Parent {
+ get { return parent; }
+ set {
+ if (parent == value)
+ return;
+ DataSourceChangeEventArgs e = new DataSourceChangeEventArgs (parent, value);
+
+ parentRWLock.EnterWriteLock();
+ parent = value;
+ Slot = LastSlots = default(Rectangle);
+ parentRWLock.ExitWriteLock();
+
+ onParentChanged (this, e);
+ }
+ }
+ [XmlIgnore]public ILayoutable LogicalParent {
+ get { return logicalParent == null ? Parent : logicalParent; }
+ set {
+ if (logicalParent == value)
+ return;
+ if (logicalParent != null)
+ (logicalParent as Widget).DataSourceChanged -= onLogicalParentDataSourceChanged;
+ DataSourceChangeEventArgs dsce = new DataSourceChangeEventArgs (LogicalParent, null);
+ logicalParent = value;
+ dsce.NewDataSource = LogicalParent;
+ if (logicalParent != null)
+ (logicalParent as Widget).DataSourceChanged += onLogicalParentDataSourceChanged;
+ onLogicalParentChanged (this, dsce);
+ }
+ }
+ [XmlIgnore]public virtual Rectangle ClientRectangle {
+ get {
+ Rectangle cb = Slot.Size;
+ cb.Inflate ( - margin);
+ return cb;
+ }
+ }
+ public virtual Rectangle ContextCoordinates(Rectangle r){
+ Widget go = Parent as Widget;
+ if (go == null)
+ return r + Parent.ClientRectangle.Position;
+ return go.CacheEnabled ?
+ r + Parent.ClientRectangle.Position :
+ Parent.ContextCoordinates (r);
+ }
+ public virtual Rectangle ScreenCoordinates (Rectangle r){
+ try {
+ return
+ Parent.ScreenCoordinates(r) + Parent.getSlot().Position + Parent.ClientRectangle.Position;
+ } catch (Exception ex) {
+ Debug.WriteLine (ex);
+ return default(Rectangle);
+ }
+ }
+ public virtual Rectangle getSlot () { return Slot;}
+ #endregion
+ public Point ScreenPointToLocal(Point p){
+ Point pt = p - ScreenCoordinates(Slot).TopLeft - ClientRectangle.TopLeft;
+ if (pt.X < 0)
+ pt.X = 0;
+ if (pt.Y < 0)
+ pt.Y = 0;
+ return pt;
+ }
+
+ #region EVENT HANDLERS
+ /// <summary>Occurs when mouse wheel is rolled in this object. It bubbles to the root</summary>
+ public event EventHandler<MouseWheelEventArgs> MouseWheelChanged;
+ /// <summary>Occurs when mouse button is released in this object. It bubbles to the root</summary>
+ public event EventHandler<MouseButtonEventArgs> MouseUp;
+ /// <summary>Occurs when mouse button is pressed in this object. It bubbles to the root</summary>
+ public event EventHandler<MouseButtonEventArgs> MouseDown;
+ /// <summary>Occurs when mouse button has been pressed then relesed in this object. It bubbles to the root</summary>
+ public event EventHandler<MouseButtonEventArgs> MouseClick;
+ /// <summary>Occurs when mouse button has been pressed then relesed 2 times in this object. It bubbles to the root</summary>
+ public event EventHandler<MouseButtonEventArgs> MouseDoubleClick;
+ /// <summary>Occurs when mouse mouve in this object. It bubbles to the root</summary>
+ public event EventHandler<MouseMoveEventArgs> MouseMove;
+ /// <summary>Occurs when mouse enter this object</summary>
+ public event EventHandler<MouseMoveEventArgs> MouseEnter;
+ /// <summary>Occurs when mouse leave this object</summary>
+ public event EventHandler<MouseMoveEventArgs> MouseLeave;
+ /// <summary>Occurs when key is pressed when this object is active</summary>
+ public event EventHandler<KeyEventArgs> KeyDown;
+ /// <summary>Occurs when key is released when this object is active</summary>
+ public event EventHandler<KeyEventArgs> KeyUp;
+ /// <summary>Occurs when translated key event occurs in the host when this object is active</summary>
+ public event EventHandler<KeyPressEventArgs> KeyPress;
+ /// <summary>Occurs when this object received focus</summary>
+ public event EventHandler Focused;
+ /// <summary>Occurs when this object loose focus</summary>
+ public event EventHandler Unfocused;
+ /// <summary>Occurs when mouse is over</summary>
+ //public event EventHandler Hover;
+ /// <summary>Occurs when this control is no longer the Hover one</summary>
+ //public event EventHandler UnHover;
+ /// <summary>Occurs when this object loose focus</summary>
+ public event EventHandler Enabled;
+ /// <summary>Occurs when the enabled state this object is set to false</summary>
+ public event EventHandler Disabled;
+
+ #region DragAndDrop Events
+ public event EventHandler<DragDropEventArgs> StartDrag;
+ public event EventHandler<DragDropEventArgs> DragEnter;
+ public event EventHandler<DragDropEventArgs> DragLeave;
+ public event EventHandler<DragDropEventArgs> EndDrag;
+ public event EventHandler<DragDropEventArgs> Drop;
+ #endregion
+
+ /// <summary>
+ /// Occurs when default value and styling are loaded, and for templated control,
+ /// template is also loaded. Bindings should be functionnal as well.
+ /// </summary>
+ public event EventHandler Initialized;
+
+ /// <summary>Occurs when one part of the rendering slot changed</summary>
+ public event EventHandler<LayoutingEventArgs> LayoutChanged;
+ /// <summary>Occurs when DataSource changed</summary>
+ public event EventHandler<DataSourceChangeEventArgs> DataSourceChanged;
+ /// <summary>Occurs when the parent has changed</summary>
+ public event EventHandler<DataSourceChangeEventArgs> ParentChanged;
+ /// <summary>Occurs when the logical parent has changed</summary>
+ public event EventHandler<DataSourceChangeEventArgs> LogicalParentChanged;
+ #endregion
+
+ #region public properties
+ /// <summary>Random value placeholder</summary>
+ [DesignCategory ("Divers")]
+ public object Tag {
+ get { return tag; }
+ set {
+ if (tag == value)
+ return;
+ tag = value;
+ NotifyValueChanged ("Tag", tag);
+ }
+ }
+ /// <summary>
+ /// If enabled, resulting bitmap of graphic object is cached
+ /// speeding up rendering of complex object. Default is enabled.
+ /// </summary>
+ [DesignCategory ("Behavior")][DefaultValue(true)]
+ public virtual bool CacheEnabled {
+ get { return cacheEnabled; }
+ set {
+ if (cacheEnabled == value)
+ return;
+ cacheEnabled = value;
+ NotifyValueChanged ("CacheEnabled", cacheEnabled);
+ }
+ }
+ /// <summary>
+ /// If true, rendering of GraphicObject is clipped inside client rectangle
+ /// </summary>
+ [DesignCategory ("Appearance")][DefaultValue(true)]
+ public virtual bool ClipToClientRect {
+ get { return clipToClientRect; }
+ set {
+ if (clipToClientRect == value)
+ return;
+ clipToClientRect = value;
+ NotifyValueChanged ("ClipToClientRect", clipToClientRect);
+ this.RegisterForRedraw ();
+ }
+ }
+ #if DEBUG_LOG
+ [XmlIgnore]public string TreePath {
+ get { return this.GetType().Name + GraphicObjects.IndexOf(this).ToString (); }
+ }
+ #endif
+ /// <summary>
+ /// Name is used in binding to reference other GraphicObjects inside the graphic tree
+ /// and by template controls to find special element in their template implementation such
+ /// as a container or a group to put children in.
+ /// </summary>
+ [DesignCategory ("Divers")][DefaultValue(null)]
+ public virtual string Name {
+ get {
+ #if DEBUG_LOG
+ return string.IsNullOrEmpty(name) ? this.GetType().Name + GraphicObjects.IndexOf(this).ToString () : name;
+ #else
+ return name;
+ #endif
+ }
+ set {
+ if (name == value)
+ return;
+ name = value;
+ NotifyValueChanged("Name", name);
+ }
+ }
+ /// <summary>
+ /// Vertical alignment inside parent, disabled if height is stretched
+ /// or top coordinate is not null
+ /// </summary>
+ [DesignCategory ("Layout")][DefaultValue(VerticalAlignment.Center)]
+ public virtual VerticalAlignment VerticalAlignment {
+ get { return verticalAlignment; }
+ set {
+ if (verticalAlignment == value)
+ return;
+
+ verticalAlignment = value;
+ NotifyValueChanged("VerticalAlignment", verticalAlignment);
+ RegisterForLayouting (LayoutingType.Y);
+ }
+ }
+ /// <summary>
+ /// Horizontal alignment inside parent, disabled if width is stretched
+ /// or left coordinate is not null
+ /// </summary>
+ [DesignCategory ("Layout")][DefaultValue(HorizontalAlignment.Center)]
+ public virtual HorizontalAlignment HorizontalAlignment {
+ get { return horizontalAlignment; }
+ set {
+ if (horizontalAlignment == value)
+ return;
+ horizontalAlignment = value;
+ NotifyValueChanged("HorizontalAlignment", horizontalAlignment);
+ RegisterForLayouting (LayoutingType.X);
+ }
+ }
+ /// <summary>
+ /// x position inside parent
+ /// </summary>
+ [DesignCategory ("Layout")][DefaultValue(0)]
+ public virtual int Left {
+ get { return left; }
+ set {
+ if (left == value)
+ return;
+ left = value;
+ NotifyValueChanged ("Left", left);
+ this.RegisterForLayouting (LayoutingType.X);
+ }
+ }
+ /// <summary>
+ /// y position inside parent
+ /// </summary>
+ [DesignCategory ("Layout")][DefaultValue(0)]
+ public virtual int Top {
+ get { return top; }
+ set {
+ if (top == value)
+ return;
+ top = value;
+ NotifyValueChanged ("Top", top);
+ this.RegisterForLayouting (LayoutingType.Y);
+ }
+ }
+ /// <summary>
+ /// Helper property used to set width and height to fit in one call
+ /// </summary>
+ [DesignCategory ("Layout")][DefaultValue(false)]
+ public virtual bool Fit {
+ get { return Width == Measure.Fit && Height == Measure.Fit ? true : false; }
+ set {
+ if (value == Fit)
+ return;
+
+ Width = Height = Measure.Fit;
+ }
+ }
+ /// <summary>
+ /// Width of this control, by default inherited from parent. May have special values
+ /// such as Stretched or Fit. It may be proportionnal or absolute.
+ /// </summary>
+ [DesignCategory ("Layout")][DefaultValue("Inherit")]
+ public virtual Measure Width {
+ get {
+ return width.Units == Unit.Inherit ?
+ Parent is Widget ? (Parent as Widget).WidthPolicy :
+ Measure.Stretched : width;
+ }
+ set {
+ if (width == value)
+ return;
+ if (value.IsFixed) {
+ if (value < minimumSize.Width || (value > maximumSize.Width && maximumSize.Width > 0))
+ return;
+ }
+ Measure old = width;
+ width = value;
+ NotifyValueChanged ("Width", width);
+ if (width == Measure.Stretched || old == Measure.Stretched) {
+ //NotifyValueChanged ("WidthPolicy", width.Policy);
+ //contentSize in Stacks are only update on childLayoutChange, and the single stretched
+ //child of the stack is not counted in contentSize, so when changing size policy of a child
+ //we should adapt contentSize
+ //TODO:check case when child become stretched, and another stretched item already exists.
+ GenericStack gs = Parent as GenericStack;
+ if (gs != null){ //TODO:check if I should test Group instead
+ if (gs.Orientation == Orientation.Horizontal) {
+ if (width == Measure.Stretched)
+ gs.contentSize.Width -= this.LastSlots.Width;
+ else
+ gs.contentSize.Width += this.LastSlots.Width;
+ }
+ }
+ }
+
+ this.RegisterForLayouting (LayoutingType.Width);
+ }
+ }
+ /// <summary>
+ /// Height of this control, by default inherited from parent. May have special values
+ /// such as Stretched or Fit. It may be proportionnal or absolute.
+ /// </summary>
+ [DesignCategory ("Layout")][DefaultValue("Inherit")]
+ public virtual Measure Height {
+ get {
+ return height.Units == Unit.Inherit ?
+ Parent is Widget ? (Parent as Widget).HeightPolicy :
+ Measure.Stretched : height;
+ }
+ set {
+ if (height == value)
+ return;
+ if (value.IsFixed) {
+ if (value < minimumSize.Height || (value > maximumSize.Height && maximumSize.Height > 0))
+ return;
+ }
+ Measure old = height;
+ height = value;
+ NotifyValueChanged ("Height", height);
+ if (height == Measure.Stretched || old == Measure.Stretched) {
+ //NotifyValueChanged ("HeightPolicy", HeightPolicy);
+ GenericStack gs = Parent as GenericStack;
+ if (gs != null){ //TODO:check if I should test Group instead
+ if (gs.Orientation == Orientation.Vertical) {
+ if (height == Measure.Stretched)
+ gs.contentSize.Height -= this.LastSlots.Height;
+ else
+ gs.contentSize.Height += this.LastSlots.Height;
+ }
+ }
+ }
+
+ this.RegisterForLayouting (LayoutingType.Height);
+ }
+ }
+ /// <summary>
+ /// Was Used for binding on dimensions, this property will never hold fixed size, but instead only
+ /// Fit or Stretched, **with inherited state implementation, it is not longer used in binding**
+ /// </summary>
+ [XmlIgnore]public virtual Measure WidthPolicy { get {
+ return Width.IsFit ? Measure.Fit : Measure.Stretched; } }
+ /// <summary>
+ /// Was Used for binding on dimensions, this property will never hold fixed size, but instead only
+ /// Fit or Stretched, **with inherited state implementation, it is not longer used in binding**
+ /// </summary>
+ [XmlIgnore]public virtual Measure HeightPolicy { get {
+ return Height.IsFit ? Measure.Fit : Measure.Stretched; } }
+ /// <summary>
+ /// Indicate that this object may received focus or not, if not focusable all the descendants are
+ /// affected.
+ /// </summary>
+ [DesignCategory ("Behaviour")][DefaultValue(false)]
+ public virtual bool Focusable {
+ get { return focusable; }
+ set {
+ if (focusable == value)
+ return;
+ focusable = value;
+ NotifyValueChanged ("Focusable", focusable);
+ }
+ }
+ /// <summary>
+ /// True when this control has the focus, only one control per interface may have it.
+ /// </summary>
+ [XmlIgnore]public virtual bool HasFocus {
+ get { return hasFocus; }
+ set {
+ if (value == hasFocus)
+ return;
+
+ hasFocus = value;
+ if (hasFocus)
+ onFocused (this, null);
+ else
+ onUnfocused (this, null);
+ NotifyValueChanged ("HasFocus", hasFocus);
+ }
+ }
+ /// <summary>
+ /// true if this control is active, this means that mouse has been pressed in it and not yet released. It could
+ /// be used for other two states periferic action.
+ /// </summary>
+ [XmlIgnore]public virtual bool IsActive {
+ get { return isActive; }
+ set {
+ if (value == isActive)
+ return;
+
+ isActive = value;
+ NotifyValueChanged ("IsActive", isActive);
+ }
+ }
+ /// <summary>
+ /// true if this control has the pointer hover
+ /// </summary>
+ /*[XmlIgnore]public virtual bool IsHover {
+ get { return isHover; }
+ set {
+ if (value == isHover)
+ return;
+
+ isHover = value;
+
+ if (isHover)
+ onHover (this, null);
+ else
+ onUnHover (this, null);
+
+ NotifyValueChanged ("IsHover", isHover);
+ }
+ }*/
+ /// <summary>
+ /// true if holding mouse button down should trigger multiple click events
+ /// </summary>
+ [DesignCategory ("Behaviour")][DefaultValue(false)]
+ public virtual bool MouseRepeat {
+ get { return mouseRepeat; }
+ set {
+ if (mouseRepeat == value)
+ return;
+ mouseRepeat = value;
+ NotifyValueChanged ("MouseRepeat", mouseRepeat);
+ }
+ }
+ bool clearBackground = false;
+ /// <summary>
+ /// background fill of the control, maybe solid color, gradient, image, or svg
+ /// </summary>
+ [DesignCategory ("Appearance")][DefaultValue("Transparent")]
+ public virtual Fill Background {
+ get { return background; }
+ set {
+ if (background == value)
+ return;
+ clearBackground = false;
+ if (value == null)
+ return;
+ background = value;
+ NotifyValueChanged ("Background", background);
+ RegisterForRedraw ();
+ if (background is SolidColor) {
+ if ((background as SolidColor).Equals (Color.Clear))
+ clearBackground = true;
+ }
+ }
+ }
+ /// <summary>
+ /// Foreground fill of the control, usage may be different among derived controls
+ /// </summary>
+ [DesignCategory ("Appearance")][DefaultValue("White")]
+ public virtual Fill Foreground {
+ get { return foreground; }
+ set {
+ if (foreground == value)
+ return;
+ foreground = value;
+ NotifyValueChanged ("Foreground", foreground);
+ RegisterForRedraw ();
+ }
+ }
+ /// <summary>
+ /// Font being used in many controls, it is defined in the base GraphicObject class.
+ /// </summary>
+ [DesignCategory ("Appearance")][DefaultValue("sans, 10")]
+ public virtual Font Font {
+ get { return font; }
+ set {
+ if (value == font)
+ return;
+ font = value;
+ NotifyValueChanged ("Font", font);
+ RegisterForGraphicUpdate ();
+ }
+ }
+ /// <summary>
+ /// to get rounded corners
+ /// </summary>
+ [DesignCategory ("Appearance")][DefaultValue(0.0)]
+ public virtual double CornerRadius {
+ get { return cornerRadius; }
+ set {
+ if (value == cornerRadius)
+ return;
+ cornerRadius = value;
+ NotifyValueChanged ("CornerRadius", cornerRadius);
+ RegisterForRedraw ();
+ }
+ }
+ /// <summary>
+ /// This is a single integer for the 4 direction, a gap between the control and it's container,
+ /// by default it is filled with the background.
+ /// </summary>
+ [DesignCategory ("Layout")][DefaultValue(0)]
+ public virtual int Margin {
+ get { return margin; }
+ set {
+ if (value == margin)
+ return;
+ margin = value;
+ NotifyValueChanged ("Margin", margin);
+ RegisterForGraphicUpdate ();
+ }
+ }
+ /// <summary>
+ /// set the visible state of the control, invisible controls does reserve space in the layouting system.
+ /// </summary>
+ [DesignCategory ("Appearance")][DefaultValue(true)]
+ public virtual bool Visible {
+ get { return isVisible; }
+ set {
+ if (value == isVisible)
+ return;
+
+ isVisible = value;
+
+ RegisterForLayouting (LayoutingType.Sizing);
+
+ if (!isVisible && IFace.HoverWidget != null) {
+ if (IFace.HoverWidget.IsOrIsInside (this)) {
+ //IFace.HoverWidget = null;
+ IFace.ProcessMouseMove (IFace.Mouse.X, IFace.Mouse.Y);
+ }
+ }
+
+ NotifyValueChanged ("Visible", isVisible);
+ }
+ }
+ /// <summary>
+ /// get or set the enabled state, disabling a control will affect focuability and
+ /// also it's rendering which will be grayed
+ /// </summary>
+ [DesignCategory ("Behaviour")][DefaultValue(true)]
+ public virtual bool IsEnabled {
+ get { return isEnabled; }
+ set {
+ if (value == isEnabled)
+ return;
+
+ isEnabled = value;
+
+ if (isEnabled)
+ onEnable (this, null);
+ else
+ onDisable (this, null);
+
+ NotifyValueChanged ("IsEnabled", isEnabled);
+ RegisterForRedraw ();
+ }
+ }
+ /// <summary>
+ /// Minimal width and height for this control
+ /// </summary>
+ [DesignCategory ("Layout")][DefaultValue("1,1")]
+ public virtual Size MinimumSize {
+ get { return minimumSize; }
+ set {
+ if (value == minimumSize)
+ return;
+
+ minimumSize = value;
+
+ NotifyValueChanged ("MinimumSize", minimumSize);
+ RegisterForLayouting (LayoutingType.Sizing);
+ }
+ }
+ /// <summary>
+ /// Maximum width and height for this control, unlimited if null.
+ /// </summary>
+ [DesignCategory ("Layout")][DefaultValue("0,0")]
+ public virtual Size MaximumSize {
+ get { return maximumSize; }
+ set {
+ if (value == maximumSize)
+ return;
+
+ maximumSize = value;
+
+ NotifyValueChanged (nameof(MaximumSize), maximumSize);
+ RegisterForLayouting (LayoutingType.Sizing);
+ }
+ }
+ /// <summary>
+ /// Fully qualify type name of expected data source.
+ /// If set, datasource bindings will be speedup by avoiding reflexion in generated dyn methods.
+ /// If an object of a different type is set as datasource, bindings will be canceled.
+ /// It accepts all derived type.
+ /// </summary>
+ [DesignCategory ("Data")]
+ public Type DataSourceType {
+ get { return dataSourceType; }
+ set { dataSourceType = value; }
+ }
+ /// <summary>
+ /// Seek first logical tree upward if logicalParent is set, or seek graphic tree for
+ /// a not null dataSource that will be active for all descendants having dataSource=null
+ /// </summary>
+ [DesignCategory ("Data")]
+ public virtual object DataSource {
+ set {
+ if (DataSource == value)
+ return;
+
+ DataSourceChangeEventArgs dse = new DataSourceChangeEventArgs (DataSource, null);
+ dataSource = value;
+ dse.NewDataSource = DataSource;
+
+ if (dse.NewDataSource == dse.OldDataSource)
+ return;
+
+ if (value != null)
+ rootDataLevel = true;
+
+ #if DEBUG_LOG
+ DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GOLockLayouting, this);
+ #endif
+ lock (IFace.LayoutMutex) {
+ OnDataSourceChanged (this, dse);
+ NotifyValueChanged ("DataSource", DataSource);
+ }
+ #if DEBUG_LOG
+ dbgEvt.end = DebugLog.chrono.ElapsedTicks;
+ #endif
+ }
+ get {
+ return rootDataLevel ? dataSource : dataSource == null ?
+ LogicalParent == null ? null :
+ LogicalParent is Widget ? (LogicalParent as Widget).DataSource : null :
+ dataSource;
+ }
+ }
+ /// <summary>
+ /// If true, rendering of GraphicObject is clipped inside client rectangle
+ /// </summary>
+ [DesignCategory ("Data")][DefaultValue(false)]
+ public virtual bool RootDataLevel {
+ get { return rootDataLevel; }
+ set {
+ if (rootDataLevel == value)
+ return;
+ rootDataLevel = value;
+ NotifyValueChanged ("RootDataLevel", rootDataLevel);
+ this.RegisterForRedraw ();
+ }
+ }
+ protected virtual void onLogicalParentDataSourceChanged(object sender, DataSourceChangeEventArgs e){
+ if (localDataSourceIsNull)
+ OnDataSourceChanged (this, e);
+ }
+ internal bool localDataSourceIsNull { get { return dataSource == null; } }
+ public bool localLogicalParentIsNull { get { return logicalParent == null; } }
+
+ public virtual void OnDataSourceChanged(object sender, DataSourceChangeEventArgs e){
+ DataSourceChanged.Raise (this, e);
+ #if DEBUG_LOG
+ DebugLog.AddEvent(DbgEvtType.GONewDataSource, this);
+ #endif
+
+ #if DEBUG_BINDING
+ Debug.WriteLine("New DataSource for => {0} \n\t{1}=>{2}", this.ToString(),e.OldDataSource,e.NewDataSource);
+ #endif
+ }
+ /// <summary>
+ /// Style key to use for this control
+ /// </summary>
+ [DesignCategory ("Appearance")]
+ public virtual string Style {
+ get { return style; }
+ set {
+ if (value == style)
+ return;
+
+ style = value;
+
+ NotifyValueChanged ("Style", style);
+ }
+ }
+ [DesignCategory ("Divers")]
+ public virtual string Tooltip {
+ get { return tooltip; }
+ set {
+ if (tooltip == value)
+ return;
+ tooltip = value;
+ NotifyValueChanged("Tooltip", tooltip);
+ }
+ }
+ [DesignCategory ("Divers")]
+ public IList<Command> ContextCommands {
+ get { return contextCommands; }
+ set {
+ if (contextCommands == value)
+ return;
+ contextCommands = value;
+ NotifyValueChanged("ContextCommands", contextCommands);
+ }
+ }
+ #endregion
+
+ #region Default and Style Values loading
+ /// <summary> Loads the default values from XML attributes default </summary>
+ public void loadDefaultValues()
+ {
+ #if DEBUG_LOG
+ DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GOInitialization, this);
+ #endif
+
+ Type thisType = this.GetType ();
+
+ if (!string.IsNullOrEmpty (style)) {
+ if (IFace.DefaultValuesLoader.ContainsKey (style)) {
+ IFace.DefaultValuesLoader [style] (this);
+ onInitialized (this, null);
+ return;
+ }
+ } else if (IFace.DefaultValuesLoader.ContainsKey (thisType.FullName)) {
+ IFace.DefaultValuesLoader [thisType.FullName] (this);
+ onInitialized (this, null);
+ return;
+ } else if (IFace.DefaultValuesLoader.ContainsKey (thisType.Name)) {
+ IFace.DefaultValuesLoader [thisType.Name] (this);
+ onInitialized (this, null);
+ return;
+ }
+
+ List<Style> styling = new List<Style>();
+
+ //Search for a style matching :
+ //1: Full class name, with full namespace
+ //2: class name
+ //3: style may have been registered with their ressource ID minus .style extention
+ // those files being placed in a Styles folder
+ string styleKey = style;
+ if (!string.IsNullOrEmpty (style)) {
+ if (IFace.Styling.ContainsKey (style)) {
+ styling.Add (IFace.Styling [style]);
+ }
+ }
+ if (IFace.Styling.ContainsKey (thisType.FullName)) {
+ styling.Add (IFace.Styling [thisType.FullName]);
+ if (string.IsNullOrEmpty (styleKey))
+ styleKey = thisType.FullName;
+ }
+ if (IFace.Styling.ContainsKey (thisType.Name)) {
+ styling.Add (IFace.Styling [thisType.Name]);
+ if (string.IsNullOrEmpty (styleKey))
+ styleKey = thisType.Name;
+ }
+
+ if (string.IsNullOrEmpty (styleKey))
+ styleKey = thisType.FullName;
+
+ //Reflexion being very slow compared to dyn method or delegates,
+ //I compile the initial values coded in the CustomAttribs of the class,
+ //all other instance of this type would not longer use reflexion to init properly
+ //but will fetch the dynamic initialisation method compiled for this precise type
+ //TODO:measure speed gain.
+#region Delfault values Loading dynamic compilation
+ DynamicMethod dm = null;
+ ILGenerator il = null;
+
+ dm = new DynamicMethod("dyn_loadDefValues", null, new Type[] { typeof (object) }, thisType, true);
+
+ il = dm.GetILGenerator(256);
+ il.DeclareLocal(typeof (object));//store root
+ il.Emit(OpCodes.Nop);
+ //set local GraphicObject to root object passed as 1st argument
+ il.Emit (OpCodes.Ldarg_0);
+ il.Emit (OpCodes.Stloc_0);
+
+ foreach (EventInfo ei in thisType.GetEvents(BindingFlags.Public | BindingFlags.Instance)) {
+ string expression;
+ if (!getDefaultEvent(ei, styling, out expression))
+ continue;
+ //TODO:dynEventHandler could be cached somewhere, maybe a style instanciator class holding the styling delegate and bound to it.
+ foreach (string exp in CompilerServices.splitOnSemiColumnOutsideAccolades(expression)) {
+ string trimed = exp.Trim();
+ if (trimed.StartsWith ("{", StringComparison.Ordinal)){
+ il.Emit (OpCodes.Ldloc_0);//load this as 1st arg of event Add
+
+ //push eventInfo as 1st arg of compile
+ il.Emit (OpCodes.Ldloc_0);
+ il.Emit (OpCodes.Call, CompilerServices.miGetType);
+ il.Emit (OpCodes.Ldstr, ei.Name);//push event name
+ il.Emit (OpCodes.Call, CompilerServices.miGetEvent);
+ //push expression as 2nd arg of compile
+ il.Emit (OpCodes.Ldstr, trimed.Substring (1, trimed.Length - 2));
+ //push null as 3rd arg, currentNode, not known when instanciing
+ il.Emit (OpCodes.Ldnull);
+ il.Emit (OpCodes.Call, CompilerServices.miCompileDynEventHandler);
+ il.Emit (OpCodes.Castclass, ei.EventHandlerType);
+ il.Emit (OpCodes.Call, ei.AddMethod);
+ }else
+ Debug.WriteLine("error in styling, event not handled : " + trimed);
+ }
+ }
+
+ foreach (PropertyInfo pi in thisType.GetProperties(BindingFlags.Public | BindingFlags.Instance)) {
+ if (pi.GetSetMethod () == null)
+ continue;
+ XmlIgnoreAttribute xia = (XmlIgnoreAttribute)pi.GetCustomAttribute (typeof(XmlIgnoreAttribute));
+ if (xia != null)
+ continue;
+
+ object defaultValue;
+
+ int styleIndex = -1;
+ if (styling.Count > 0){
+ for (int i = 0; i < styling.Count; i++) {
+ if (styling[i].ContainsKey (pi.Name)){
+ styleIndex = i;
+ break;
+ }
+ }
+ }
+ if (styleIndex >= 0){
+ if (pi.PropertyType.IsEnum)//maybe should be in parser..
+ defaultValue = Enum.Parse(pi.PropertyType, (string)styling[styleIndex] [pi.Name], true);
+ else
+ defaultValue = styling[styleIndex] [pi.Name];
+
+ #if DESIGN_MODE
+ if (defaultValue != null){
+ FileLocation fl = styling[styleIndex].Locations[pi.Name];
+ il.Emit (OpCodes.Ldloc_0);
+ il.Emit (OpCodes.Ldstr, pi.Name);
+ il.Emit (OpCodes.Ldstr, fl.FilePath);
+ il.Emit (OpCodes.Ldc_I4, fl.Line);
+ il.Emit (OpCodes.Ldc_I4, fl.Column);
+ il.Emit (OpCodes.Call, miDesignAddDefLoc);
+
+ il.Emit (OpCodes.Ldloc_0);
+ il.Emit (OpCodes.Ldfld, typeof(Widget).GetField("design_style_values"));
+ il.Emit (OpCodes.Ldstr, pi.Name);
+ il.Emit (OpCodes.Ldstr, defaultValue.ToString());
+ il.Emit (OpCodes.Call, CompilerServices.miDicStrStrAdd);
+ }
+ #endif
+
+ }else {
+ DefaultValueAttribute dv = (DefaultValueAttribute)pi.GetCustomAttribute (typeof (DefaultValueAttribute));
+ if (dv == null)
+ continue;
+ defaultValue = dv.Value;
+ }
+
+ CompilerServices.EmitSetValue (il, pi, defaultValue);
+ }
+ il.Emit(OpCodes.Ret);
+ #endregion
+
+ try {
+ IFace.DefaultValuesLoader[styleKey] = (Interface.LoaderInvoker)dm.CreateDelegate(typeof(Interface.LoaderInvoker));
+ IFace.DefaultValuesLoader[styleKey] (this);
+ } catch (Exception ex) {
+ throw new Exception ("Error applying style <" + styleKey + ">:", ex);
+ }
+
+ #if DEBUG_LOG
+ dbgEvt.end = DebugLog.chrono.ElapsedTicks;
+ #endif
+
+ onInitialized (this, null);
+ }
+ protected virtual void onInitialized (object sender, EventArgs e){
+ Initialized.Raise(sender, e);
+ }
+ bool getDefaultEvent(EventInfo ei, List<Style> styling,
+ out string expression){
+ expression = "";
+ if (styling.Count > 0){
+ for (int i = 0; i < styling.Count; i++) {
+ if (styling[i].ContainsKey (ei.Name)){
+ expression = (string)styling[i] [ei.Name];
+ return true;
+ }
+ }
+ }
+ return false;
+ }
+#endregion
+
+ public virtual Widget FindByName(string nameToFind){
+ return string.Equals(nameToFind, name, StringComparison.Ordinal) ? this : null;
+ }
+ public virtual bool Contains(Widget goToFind){
+ return false;
+ }
+ /// <summary>
+ /// return true if this is contained inside go
+ /// </summary>
+ public bool IsOrIsInside(Widget go){
+ if (this == go)
+ return true;
+ ILayoutable p = this.Parent;
+ while (p != null) {
+ if (p == go)
+ return true;
+ p = p.Parent;
+ }
+ return false;
+ }
+
+ #region Drag&Drop
+ [DesignCategory ("DragAndDrop")][DefaultValue(false)]
+ public virtual bool AllowDrag {
+ get { return allowDrag; }
+ set {
+ if (allowDrag == value)
+ return;
+ allowDrag = value;
+ NotifyValueChanged ("AllowDrag", allowDrag);
+ }
+ }
+ [DesignCategory ("DragAndDrop")][DefaultValue(false)]
+ public virtual bool AllowDrop {
+ get { return allowDrop; }
+ set {
+ if (allowDrop == value)
+ return;
+ allowDrop = value;
+ NotifyValueChanged ("AllowDrop", allowDrop);
+ }
+ }
+
+// public List<Type> AllowedDroppedTypes;
+// public void AddAllowedDroppedType (Type newType){
+// if (AllowedDroppedTypes == null)
+// AllowedDroppedTypes = new List<Type> ();
+// AllowedDroppedTypes.Add (newType);
+// NotifyValueChanged ("AllowDrop", AllowDrop);
+// }
+// [XmlIgnore]public virtual bool AllowDrop {
+// get { return AllowedDroppedTypes?.Count>0; }
+// }
+ [XmlIgnore]public virtual bool IsDragged {
+ get { return isDragged; }
+ set {
+ if (isDragged == value)
+ return;
+ isDragged = value;
+
+ NotifyValueChanged ("IsDragged", IsDragged);
+ }
+ }
+ /// <summary>
+ /// fired when drag and drop operation start
+ /// </summary>
+ protected virtual void onStartDrag (object sender, DragDropEventArgs e){
+ IFace.HoverWidget = null;
+ IsDragged = true;
+ StartDrag.Raise (this, e);
+ #if DEBUG_DRAGNDROP
+ Debug.WriteLine(this.ToString() + " : START DRAG => " + e.ToString());
+ #endif
+ }
+ /// <summary>
+ /// Occured when dragging ends without dropping
+ /// </summary>
+ protected virtual void onEndDrag (object sender, DragDropEventArgs e){
+ IsDragged = false;
+ EndDrag.Raise (this, e);
+ #if DEBUG_DRAGNDROP
+ Debug.WriteLine(this.ToString() + " : END DRAG => " + e.ToString());
+ #endif
+ }
+ protected virtual void onDragEnter (object sender, DragDropEventArgs e){
+ e.DropTarget = this;
+ DragEnter.Raise (this, e);
+ #if DEBUG_DRAGNDROP
+ Debug.WriteLine(this.ToString() + " : DRAG Enter => " + e.ToString());
+ #endif
+ }
+ protected virtual void onDragLeave (object sender, DragDropEventArgs e){
+ e.DropTarget = null;
+ DragLeave.Raise (this, e);
+ #if DEBUG_DRAGNDROP
+ Debug.WriteLine(this.ToString() + " : DRAG Leave => " + e.ToString());
+ #endif
+ }
+ protected virtual void onDrop (object sender, DragDropEventArgs e){
+ IsDragged = false;
+ Drop.Raise (this, e);
+ //e.DropTarget.onDragLeave (this, e);//raise drag leave in target
+ #if DEBUG_DRAGNDROP
+ Debug.WriteLine(this.ToString() + " : DROP => " + e.ToString());
+ #endif
+ }
+ public bool IsDropTarget {
+ get { return IFace.DragAndDropOperation?.DropTarget == this; }
+ }
+
+ #endregion
+
+ #region Queuing
+ /// <summary>
+ /// Register old and new slot for clipping
+ /// </summary>
+ public virtual void ClippingRegistration(){
+ #if DEBUG_LOG
+ DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GOClippingRegistration, this);
+ #endif
+ parentRWLock.EnterReadLock ();
+ if (parent != null) {
+ Parent.RegisterClip (LastPaintedSlot);
+ Parent.RegisterClip (Slot);
+ }
+ parentRWLock.ExitReadLock ();
+ #if DEBUG_LOG
+ dbgEvt.end = DebugLog.chrono.ElapsedTicks;
+ #endif
+ }
+ /// <summary>
+ /// Add clip rectangle to this.clipping and propagate up to root
+ /// </summary>
+ /// <param name="clip">Clip rectangle</param>
+ public virtual void RegisterClip(Rectangle clip){
+ #if DEBUG_LOG
+ DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GORegisterClip, this);
+ #endif
+ Rectangle cb = ClientRectangle;
+ Rectangle r = clip + cb.Position;
+ if (r.Right > cb.Right)
+ r.Width -= r.Right - cb.Right;
+ if (r.Bottom > cb.Bottom)
+ r.Height -= r.Bottom - cb.Bottom;
+ if (cacheEnabled && !IsDirty)
+ Clipping.UnionRectangle (r);
+ if (Parent == null)
+ return;
+ Widget p = Parent as Widget;
+ if (p?.IsDirty == true && p?.CacheEnabled == true)
+ return;
+ Parent.RegisterClip (r + Slot.Position);
+ #if DEBUG_LOG
+ dbgEvt.end = DebugLog.chrono.ElapsedTicks;
+ #endif
+ }
+ /// <summary> Full update, content and layouting, taking care of sizing policy </summary>
+ [MethodImpl(MethodImplOptions.AggressiveInlining)]
+ public void RegisterForGraphicUpdate ()
+ {
+ IsDirty = true;
+ if (Width.IsFit || Height.IsFit)
+ RegisterForLayouting (LayoutingType.Sizing);
+ else if (RegisteredLayoutings == LayoutingType.None)
+ IFace.EnqueueForRepaint (this);
+ }
+ /// <summary> query an update of the content without layouting changes</summary>
+ [MethodImpl(MethodImplOptions.AggressiveInlining)]
+ public void RegisterForRedraw ()
+ {
+ IsDirty = true;
+ if (RegisteredLayoutings == LayoutingType.None)
+ IFace.EnqueueForRepaint (this);
+ }
+ #endregion
+
+ #region Layouting
+
+ /// <summary> return size of content + margins </summary>
+ protected virtual int measureRawSize (LayoutingType lt) {
+ return lt == LayoutingType.Width ?
+ contentSize.Width + 2 * margin: contentSize.Height + 2 * margin;
+ }
+ /// <summary> By default in groups, LayoutingType.ArrangeChildren is reset </summary>
+ public virtual void ChildrenLayoutingConstraints(ref LayoutingType layoutType){
+ }
+ public virtual bool ArrangeChildren { get { return false; } }
+ public virtual void RegisterForLayouting(LayoutingType layoutType){
+ if (Parent == null)
+ return;
+ lock (IFace.LayoutMutex) {
+ //prevent queueing same LayoutingType for this
+ layoutType &= (~RegisteredLayoutings);
+
+ if (layoutType == LayoutingType.None)
+ return;
+ //dont set position for stretched item
+ if (Width == Measure.Stretched)
+ layoutType &= (~LayoutingType.X);
+ if (Height == Measure.Stretched)
+ layoutType &= (~LayoutingType.Y);
+
+ if (!ArrangeChildren)
+ layoutType &= (~LayoutingType.ArrangeChildren);
+
+ //apply constraints depending on parent type
+ if (Parent is Widget)
+ (Parent as Widget).ChildrenLayoutingConstraints (ref layoutType);
+
+// //prevent queueing same LayoutingType for this
+ layoutType &= (~RegisteredLayoutings);
+
+ if (layoutType == LayoutingType.None)
+ return;
+
+ //enqueue LQI LayoutingTypes separately
+ if (layoutType.HasFlag (LayoutingType.Width))
+ IFace.LayoutingQueue.Enqueue (new LayoutingQueueItem (LayoutingType.Width, this));
+ if (layoutType.HasFlag (LayoutingType.Height))
+ IFace.LayoutingQueue.Enqueue (new LayoutingQueueItem (LayoutingType.Height, this));
+ if (layoutType.HasFlag (LayoutingType.X))
+ IFace.LayoutingQueue.Enqueue (new LayoutingQueueItem (LayoutingType.X, this));
+ if (layoutType.HasFlag (LayoutingType.Y))
+ IFace.LayoutingQueue.Enqueue (new LayoutingQueueItem (LayoutingType.Y, this));
+ if (layoutType.HasFlag (LayoutingType.ArrangeChildren))
+ IFace.LayoutingQueue.Enqueue (new LayoutingQueueItem (LayoutingType.ArrangeChildren, this));
+ }
+ }
+
+ /// <summary> trigger dependant sizing component update </summary>
+ public virtual void OnLayoutChanges(LayoutingType layoutType)
+ {
+ switch (layoutType) {
+ case LayoutingType.Width:
+ RegisterForLayouting (LayoutingType.X);
+ break;
+ case LayoutingType.Height:
+ RegisterForLayouting (LayoutingType.Y);
+ break;
+ }
+ LayoutChanged.Raise (this, new LayoutingEventArgs (layoutType));
+ }
+ internal protected void raiseLayoutChanged(LayoutingEventArgs e){
+ LayoutChanged.Raise (this, e);
+ }
+ /// <summary> Update layout component only one at a time, this is where the computation of alignement
+ /// and size take place.
+ /// The redrawing will only be triggered if final slot size has changed </summary>
+ /// <returns><c>true</c>, if layouting was possible, <c>false</c> if conditions were not
+ /// met and LQI has to be re-queued</returns>
+ public virtual bool UpdateLayout (LayoutingType layoutType)
+ {
+ //unset bit, it would be reset if LQI is re-queued
+ registeredLayoutings &= (~layoutType);
+
+ switch (layoutType) {
+ case LayoutingType.X:
+ if (left == 0) {
+
+ if (Parent.RegisteredLayoutings.HasFlag (LayoutingType.Width) ||
+ RegisteredLayoutings.HasFlag (LayoutingType.Width))
+ return false;
+
+ switch (horizontalAlignment) {
+ case HorizontalAlignment.Left:
+ Slot.X = 0;
+ break;
+ case HorizontalAlignment.Right:
+ Slot.X = Parent.ClientRectangle.Width - Slot.Width;
+ break;
+ case HorizontalAlignment.Center:
+ Slot.X = Parent.ClientRectangle.Width / 2 - Slot.Width / 2;
+ break;
+ }
+ } else
+ Slot.X = left;
+
+ if (LastSlots.X == Slot.X)
+ break;
+
+ IsDirty = true;
+
+ OnLayoutChanges (layoutType);
+
+ LastSlots.X = Slot.X;
+ break;
+ case LayoutingType.Y:
+ if (top == 0) {
+
+ if (Parent.RegisteredLayoutings.HasFlag (LayoutingType.Height) ||
+ RegisteredLayoutings.HasFlag (LayoutingType.Height))
+ return false;
+
+ switch (verticalAlignment) {
+ case VerticalAlignment.Top://this could be processed even if parent Height is not known
+ Slot.Y = 0;
+ break;
+ case VerticalAlignment.Bottom:
+ Slot.Y = Parent.ClientRectangle.Height - Slot.Height;
+ break;
+ case VerticalAlignment.Center:
+ Slot.Y = Parent.ClientRectangle.Height / 2 - Slot.Height / 2;
+ break;
+ }
+ } else
+ Slot.Y = top;
+
+ if (LastSlots.Y == Slot.Y)
+ break;
+
+ IsDirty = true;
+
+ OnLayoutChanges (layoutType);
+
+ LastSlots.Y = Slot.Y;
+ break;
+ case LayoutingType.Width:
+ if (isVisible) {
+ if (Width.IsFixed)
+ Slot.Width = Width;
+ else if (Width == Measure.Fit) {
+ Slot.Width = measureRawSize (LayoutingType.Width);
+ } else if (Parent.RegisteredLayoutings.HasFlag (LayoutingType.Width))
+ return false;
+ else if (Width == Measure.Stretched)
+ Slot.Width = Parent.ClientRectangle.Width;
+ else
+ Slot.Width = (int)Math.Round ((double)(Parent.ClientRectangle.Width * Width) / 100.0);
+
+ if (Slot.Width < 0)
+ return false;
+
+ //size constrain
+ if (Slot.Width < minimumSize.Width) {
+ Slot.Width = minimumSize.Width;
+ //NotifyValueChanged ("WidthPolicy", Measure.Stretched);
+ } else if (Slot.Width > maximumSize.Width && maximumSize.Width > 0) {
+ Slot.Width = maximumSize.Width;
+ //NotifyValueChanged ("WidthPolicy", Measure.Stretched);
+ }
+ } else
+ Slot.Width = 0;
+
+ if (LastSlots.Width == Slot.Width)
+ break;
+
+ IsDirty = true;
+
+ OnLayoutChanges (layoutType);
+
+ LastSlots.Width = Slot.Width;
+ break;
+ case LayoutingType.Height:
+ if (isVisible) {
+ if (Height.IsFixed)
+ Slot.Height = Height;
+ else if (Height == Measure.Fit) {
+ Slot.Height = measureRawSize (LayoutingType.Height);
+ } else if (Parent.RegisteredLayoutings.HasFlag (LayoutingType.Height))
+ return false;
+ else if (Height == Measure.Stretched)
+ Slot.Height = Parent.ClientRectangle.Height;
+ else
+ Slot.Height = (int)Math.Round ((double)(Parent.ClientRectangle.Height * Height) / 100.0);
+
+ if (Slot.Height < 0)
+ return false;
+
+ //size constrain
+ if (Slot.Height < minimumSize.Height) {
+ Slot.Height = minimumSize.Height;
+ //NotifyValueChanged ("HeightPolicy", Measure.Stretched);
+ } else if (Slot.Height > maximumSize.Height && maximumSize.Height > 0) {
+ Slot.Height = maximumSize.Height;
+ //NotifyValueChanged ("HeightPolicy", Measure.Stretched);
+ }
+ } else
+ Slot.Height = 0;
+
+ if (LastSlots.Height == Slot.Height)
+ break;
+
+ IsDirty = true;
+
+ OnLayoutChanges (layoutType);
+
+ LastSlots.Height = Slot.Height;
+ break;
+ }
+
+ //if no layouting remains in queue for item, registre for redraw
+ if (this.registeredLayoutings == LayoutingType.None && IsDirty)
+ IFace.EnqueueForRepaint (this);
+
+ return true;
+ }
+ #endregion
+
+ #region Rendering
+ /// <summary> This is the common overridable drawing routine to create new widget </summary>
+ protected virtual void onDraw(Context gr)
+ {
+ #if DEBUG_LOG
+ DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GODraw, this);
+ #endif
+
+ Rectangle rBack = new Rectangle (Slot.Size);
+
+ background.SetAsSource (gr, rBack);
+ CairoHelpers.CairoRectangle (gr, rBack, cornerRadius);
+ gr.Fill ();
+
+ #if DEBUG_LOG
+ dbgEvt.end = DebugLog.chrono.ElapsedTicks;
+ #endif
+ }
+
+ /// <summary>
+ /// Internal drawing context creation on a cached surface limited to slot size
+ /// this trigger the effective drawing routine </summary>
+ protected virtual void RecreateCache ()
+ {
+ #if DEBUG_LOG
+ DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GORecreateCache, this);
+ #endif
+
+ /*if (bmp == null)
+ bmp = IFace.surf.CreateSimilar (Content.ColorAlpha, Slot.Width, Slot.Height);
+ else if (LastPaintedSlot.Width != Slot.Width || LastPaintedSlot.Height != Slot.Height)
+ bmp.SetSize (Slot.Width, Slot.Height);*/
+ bmp?.Dispose ();
+ bmp = new ImageSurface(Format.Argb32, Slot.Width, Slot.Height);
+
+ using (Context gr = new Context (bmp)) {
+ gr.Antialias = Interface.Antialias;
+ onDraw (gr);
+ }
+
+ IsDirty = false;
+
+ #if DEBUG_LOG
+ dbgEvt.end = DebugLog.chrono.ElapsedTicks;
+ #endif
+ }
+ protected virtual void UpdateCache(Context ctx){
+ #if DEBUG_LOG
+ DbgEvent dbgEvt = DebugLog.AddEvent(DbgEvtType.GOUpdateCacheAndPaintOnCTX, this);
+ #endif
+
+ Rectangle rb = Slot + Parent.ClientRectangle.Position;
+ if (clearBackground) {
+ ctx.Save ();
+ ctx.Operator = Operator.Clear;
+ ctx.Rectangle (rb);
+ ctx.Fill ();
+ ctx.Restore ();
+ }
+
+ ctx.SetSourceSurface (bmp, rb.X, rb.Y);
+ ctx.Paint ();
+ Clipping.Dispose ();
+ Clipping = new Region ();
+ #if DEBUG_LOG
+ dbgEvt.end = DebugLog.chrono.ElapsedTicks;
+ #endif
+ }
+ /// <summary> Chained painting routine on the parent context of the actual cached version
+ /// of the widget </summary>
+ public virtual void Paint (ref Context ctx)
+ {
+ #if DEBUG_LOG
+ DebugLog.AddEvent(DbgEvtType.GOPaint, this);
+ #endif
+ //TODO:this test should not be necessary
+ if (Slot.Height < 0 || Slot.Width < 0 || parent == null)
+ return;
+ lock (this) {
+ if (cacheEnabled) {
+ if (Slot.Width > Interface.MaxCacheSize || Slot.Height > Interface.MaxCacheSize)
+ cacheEnabled = false;
+ }
+
+ if (cacheEnabled) {
+ if (IsDirty)
+ RecreateCache ();
+
+ UpdateCache (ctx);
+ if (!isEnabled)
+ paintDisabled (ctx, Slot + Parent.ClientRectangle.Position);
+ } else {
+ Rectangle rb = Slot + Parent.ClientRectangle.Position;
+ ctx.Save ();
+
+ ctx.Translate (rb.X, rb.Y);
+
+ onDraw (ctx);
+ if (!isEnabled)
+ paintDisabled (ctx, Slot);
+
+ ctx.Restore ();
+ }
+ LastPaintedSlot = Slot;
+ }
+ }
+ void paintDisabled(Context gr, Rectangle rb){
+ gr.Operator = Operator.Xor;
+ gr.SetSourceRGBA (0.6, 0.6, 0.6, 0.3);
+ gr.Rectangle (rb);
+ gr.Fill ();
+ gr.Operator = Operator.Over;
+ }
+ #endregion
+
+ #region Keyboard handling
+ public virtual void onKeyDown(object sender, KeyEventArgs e){
+ KeyDown.Raise (this, e);
+ }
+ public virtual void onKeyUp(object sender, KeyEventArgs e){
+ KeyUp.Raise (this, e);
+ }
+ public virtual void onKeyPress(object sender, KeyPressEventArgs e){
+ KeyPress.Raise (this, e);
+ }
+ #endregion
+
+ #region Mouse handling
+ /// <summary>
+ /// Recursive local coordinate point test.
+ /// After test on parent, point m is in local coord system.
+ /// </summary>
+ /// <returns>return true, if point is in the bounds of this control</returns>
+ /// <param name="m">by ref point to test, init value is not kept</param>
+ public virtual bool PointIsIn(ref Point m)
+ {
+ if (parent == null)
+ return false;
+ if (!(isVisible & isEnabled)||IsDragged)
+ return false;
+ if (!parent.PointIsIn(ref m))
+ return false;
+ m -= (parent.getSlot().Position + parent.ClientRectangle.Position) ;
+ return Slot.ContainsOrIsEqual (m);
+ }
+ public virtual bool MouseIsIn(Point m)
+ {
+ return (!(isVisible & isEnabled)||IsDragged) ? false : PointIsIn (ref m);
+ }
+ public virtual void checkHoverWidget(MouseMoveEventArgs e)
+ {
+ if (IFace.HoverWidget != this) {
+ IFace.HoverWidget = this;
+ onMouseEnter (this, e);
+ }
+
+ //this.onMouseMove (this, e);//without this, window border doesn't work, should be removed
+ }
+ public virtual void onMouseMove(object sender, MouseMoveEventArgs e)
+ {
+ if (allowDrag & hasFocus & e.Mouse.LeftButton == ButtonState.Pressed) {
+ if (IFace.DragAndDropOperation == null) {
+ IFace.DragAndDropOperation = new DragDropEventArgs (this);
+ onStartDrag (this, IFace.DragAndDropOperation);
+ }
+ }
+
+ //dont bubble event if dragged, mouse move is routed directely from iface
+ //to let other control behind have mouse entering
+ if (isDragged)
+ return;
+
+ //bubble event to the top
+ Widget p = focusParent;
+ if (p != null)
+ p.onMouseMove(sender,e);
+
+ MouseMove.Raise (this, e);
+ }
+ public virtual void onMouseDown(object sender, MouseButtonEventArgs e){
+ #if DEBUG_FOCUS
+ Debug.WriteLine("MOUSE DOWN => " + this.ToString());
+ #endif
+
+ if (focusable && !Interface.FocusOnHover) {
+ BubblingMouseButtonEventArg be = e as BubblingMouseButtonEventArg;
+ if (be.Focused == null) {
+ be.Focused = this;
+ IFace.FocusedWidget = this;
+ if (e.Button == MouseButton.Right && contextCommands != null)
+ IFace.ShowContextMenu (this);
+ }
+ }
+ //bubble event to the top
+ Widget p = focusParent;
+ if (p != null)
+ p.onMouseDown(sender,e);
+
+ MouseDown.Raise (this, e);
+ }
+ public virtual void onMouseUp(object sender, MouseButtonEventArgs e){
+ #if DEBUG_FOCUS
+ Debug.WriteLine("MOUSE UP => " + this.ToString());
+ #endif
+
+ if (IFace.DragAndDropOperation != null){
+ if (IFace.DragAndDropOperation.DragSource == this) {
+ if (IFace.DragAndDropOperation.DropTarget != null)
+ onDrop (this, IFace.DragAndDropOperation);
+ else
+ onEndDrag (this, IFace.DragAndDropOperation);
+ IFace.DragAndDropOperation = null;
+ }
+ }
+
+ //bubble event to the top
+ Widget p = focusParent;
+ if (p != null)
+ p.onMouseUp(sender,e);
+
+ MouseUp.Raise (this, e);
+ }
+ public virtual void onMouseClick(object sender, MouseButtonEventArgs e){
+#if DEBUG_FOCUS
+ Debug.WriteLine("CLICK => " + this.ToString());
+#endif
+ if (MouseClick != null)
+ {
+ MouseClick.Raise(this, e);
+ return;
+ }
+ Widget p = focusParent;
+ if (p != null)
+ p.onMouseClick(sender,e);
+ }
+ public virtual void onMouseDoubleClick(object sender, MouseButtonEventArgs e){
+#if DEBUG_FOCUS
+ Debug.WriteLine("DOUBLE CLICK => " + this.ToString());
+#endif
+ if (MouseDoubleClick != null)
+ {
+ MouseDoubleClick.Raise(this, e);
+ return;
+ }
+ Widget p = focusParent;
+ if (p != null)
+ p.onMouseDoubleClick(sender,e);
+ }
+ public virtual void onMouseWheel(object sender, MouseWheelEventArgs e){
+ if (MouseWheelChanged != null)
+ {
+ MouseWheelChanged.Raise(this, e);
+ return;
+ }
+ Widget p = focusParent;
+ if (p != null)
+ p.onMouseWheel(sender,e);
+ }
+ public virtual void onMouseEnter(object sender, MouseMoveEventArgs e)
+ {
+ #if DEBUG_FOCUS
+ Debug.WriteLine("MouseEnter => " + this.ToString());
+ #endif
+
+ if (IFace.DragAndDropOperation != null) {
+ Widget g = this;
+ while (g != null) {
+ if (g.AllowDrop) {
+ if (IFace.DragAndDropOperation.DragSource != this && IFace.DragAndDropOperation.DropTarget != this) {
+ if (IFace.DragAndDropOperation.DropTarget != null)
+ IFace.DragAndDropOperation.DropTarget.onDragLeave (this, IFace.DragAndDropOperation);
+ g.onDragEnter (this, IFace.DragAndDropOperation);
+ }
+ break;
+ }
+ g = g.focusParent;
+ }
+ }
+
+ MouseEnter.Raise (this, e);
+ }
+ public virtual void onMouseLeave(object sender, MouseMoveEventArgs e)
+ {
+ #if DEBUG_FOCUS
+ Debug.WriteLine("MouseLeave => " + this.ToString());
+ #endif
+
+ MouseLeave.Raise (this, e);
+ }
+
+ #endregion
+
+ protected virtual void onFocused(object sender, EventArgs e){
+ if (IFace.FocusedWidget != this)
+ IFace.FocusedWidget = this;
+ #if DEBUG_FOCUS
+ Debug.WriteLine("Focused => " + this.ToString());
+ #endif
+ Focused.Raise (this, e);
+ }
+ protected virtual void onUnfocused(object sender, EventArgs e){
+ #if DEBUG_FOCUS
+ Debug.WriteLine("UnFocused => " + this.ToString());
+ #endif
+ Unfocused.Raise (this, e);
+ }
+ public virtual void onEnable(object sender, EventArgs e){
+ Enabled.Raise (this, e);
+ }
+ public virtual void onDisable(object sender, EventArgs e){
+ Disabled.Raise (this, e);
+ }
+ protected virtual void onParentChanged(object sender, DataSourceChangeEventArgs e) {
+// if (e.NewDataSource != null) {
+// if (width == Measure.Inherit)
+// RegisterForLayouting (LayoutingType.Width);
+// if (height == Measure.Inherit)
+// RegisterForLayouting (LayoutingType.Height);
+// }
+
+ ParentChanged.Raise (this, e);
+ if (logicalParent == null)
+ LogicalParentChanged.Raise (this, e);
+ }
+ protected virtual void onLogicalParentChanged(object sender, DataSourceChangeEventArgs e) {
+ LogicalParentChanged.Raise (this, e);
+ }
+ internal void ClearTemplateBinding(){
+ #if DEBUG_UPDATE
+ Debug.WriteLine (string.Format("ClearTemplateBinding: {0}", this.ToString()));
+ #endif
+ if (ValueChanged == null)
+ return;
+ EventInfo eiEvt = this.GetType().GetEvent ("ValueChanged");
+ foreach (Delegate d in ValueChanged.GetInvocationList()) {
+ if (d.Method.Name == "dyn_tmpValueChanged") {
+ eiEvt.RemoveEventHandler (this, d);
+ #if DEBUG_BINDING
+ Debug.WriteLine ("\t{0} template binding handler removed in {1} for: {2}", d.Method.Name, this, "ValueChanged");
+ #endif
+ }
+ }
+ }
+ public override string ToString ()
+ {
+ string tmp ="";
+
+ if (Parent != null)
+ tmp = Parent.ToString () + tmp;
+ #if DEBUG_LAYOUTING
+ return Name == "unamed" ? tmp + "." + this.GetType ().Name + GraphicObjects.IndexOf(this).ToString(): tmp + "." + Name;
+ #else
+ return string.IsNullOrEmpty(Name) ? tmp + "." + this.GetType ().Name : tmp + "." + Name;
+ #endif
+ }
+ /// <summary>
+ /// Checks to handle when widget is removed from the visible graphic tree
+ /// </summary>
+ void unshownPostActions () {
+ if (IFace.HoverWidget != null) {
+ if (IFace.HoverWidget.IsOrIsInside (this)) {
+ IFace.HoverWidget = null;
+ IFace.ProcessMouseMove (IFace.Mouse.X, IFace.Mouse.Y);
+ }
+ }
+ if (IFace.ActiveWidget != null) {
+ if (IFace.ActiveWidget.IsOrIsInside (this))
+ IFace.ActiveWidget = null;
+ }
+ if (IFace.FocusedWidget != null) {
+ if (IFace.FocusedWidget.IsOrIsInside (this))
+ IFace.FocusedWidget = null;
+ }
+ }
+ }
+}
#endregion
#region TemplatedContainer overrides
- protected override void loadTemplate(GraphicObject template = null)
+ protected override void loadTemplate(Widget template = null)
{
base.loadTemplate (template);
if (Parent is Interface)
(Parent as Interface).DeleteWidget (this);
else {
- GraphicObject p = Parent as GraphicObject;
+ Widget p = Parent as Widget;
if (p is Group) {
lock (IFace.UpdateMutex) {
RegisterClip (p.ScreenCoordinates (p.LastPaintedSlot));
if (Orientation == Orientation.Vertical) {
int tallestChild = 0;
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
if (!c.Visible)
continue;
if (dx + c.Slot.Width > ClientRectangle.Width) {
}
} else {
int largestChild = 0;
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
if (!c.Visible)
continue;
if (dy + c.Slot.Height > ClientRectangle.Height) {
public override void OnChildLayoutChanges (object sender, LayoutingEventArgs arg)
{
//children can't stretch in a wrapper
- GraphicObject go = sender as GraphicObject;
+ Widget go = sender as Widget;
//System.Diagnostics.Debug.WriteLine ("wrapper child layout change: " + go.LastSlots.ToString() + " => " + go.Slot.ToString());
switch (arg.LayoutType) {
case LayoutingType.Width:
childrenRWLock.EnterReadLock();
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
if (!c.Visible)
continue;
if (c.Height.IsRelativeToParent &&
childrenRWLock.EnterReadLock();
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
if (!c.Visible)
continue;
if (c.Width.IsRelativeToParent &&
#endif
switch (layoutType) {
case LayoutingType.Width:
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
if (c.Width.IsRelativeToParent)
c.RegisterForLayouting (LayoutingType.Width);
}
RegisterForLayouting (LayoutingType.X);
break;
case LayoutingType.Height:
- foreach (GraphicObject c in Children) {
+ foreach (Widget c in Children) {
if (c.Height.IsRelativeToParent)
c.RegisterForLayouting (LayoutingType.Height);
}
typeof (object), new Type [] { typeof (Instantiator), typeof (Interface) }, true);
il = dm.GetILGenerator (256);
- il.DeclareLocal (typeof (GraphicObject));
+ il.DeclareLocal (typeof (Widget));
il.Emit (OpCodes.Nop);
//set local GraphicObject to root object
ConstructorInfo ci = rootType.GetConstructor (
/// Creates a new instance of the GraphicObject compiled in the instantiator
/// </summary>
/// <returns>The new graphic object instance</returns>
- public GraphicObject CreateInstance(){
+ public Widget CreateInstance(){
#if DEBUG_LOAD
Stopwatch loadingTime = Stopwatch.StartNew ();
GraphicObject o = loader (iface) as GraphicObject;
}
return o;
#else
- return loader (iface) as GraphicObject;
+ return loader (iface) as Widget;
#endif
}
/// <summary>
void emitSetDesignAttribute (IMLContext ctx, string name, string value){
//store member value in iml
ctx.il.Emit (OpCodes.Ldloc_0);
- ctx.il.Emit (OpCodes.Ldfld, typeof(GraphicObject).GetField("design_iml_values"));
+ ctx.il.Emit (OpCodes.Ldfld, typeof(Widget).GetField("design_iml_values"));
ctx.il.Emit (OpCodes.Ldstr, name);
if (string.IsNullOrEmpty (value))
ctx.il.Emit (OpCodes.Ldnull);
IXmlLineInfo li = (IXmlLineInfo)reader;
ctx.il.Emit (OpCodes.Ldloc_0);
ctx.il.Emit (OpCodes.Ldstr, this.NextDesignID);
- ctx.il.Emit (OpCodes.Stfld, typeof(GraphicObject).GetField("design_id"));
+ ctx.il.Emit (OpCodes.Stfld, typeof(Widget).GetField("design_id"));
ctx.il.Emit (OpCodes.Ldloc_0);
ctx.il.Emit (OpCodes.Ldc_I4, ctx.curLine + li.LineNumber);
- ctx.il.Emit (OpCodes.Stfld, typeof(GraphicObject).GetField("design_line"));
+ ctx.il.Emit (OpCodes.Stfld, typeof(Widget).GetField("design_line"));
ctx.il.Emit (OpCodes.Ldloc_0);
ctx.il.Emit (OpCodes.Ldc_I4, li.LinePosition);
- ctx.il.Emit (OpCodes.Stfld, typeof(GraphicObject).GetField("design_column"));
+ ctx.il.Emit (OpCodes.Stfld, typeof(Widget).GetField("design_column"));
if (!string.IsNullOrEmpty (sourcePath)) {
ctx.il.Emit (OpCodes.Ldloc_0);
ctx.il.Emit (OpCodes.Ldstr, sourcePath);
- ctx.il.Emit (OpCodes.Stfld, typeof(GraphicObject).GetField("design_imlPath"));
+ ctx.il.Emit (OpCodes.Stfld, typeof(Widget).GetField("design_imlPath"));
}
#endif
#region Styling and default values loading
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.
+using System;
+using System.Collections.Generic;
+using System.Diagnostics;
+using System.Globalization;
+using System.IO;
using System.Linq;
using System.Reflection;
using System.Threading;
-using System.Xml;
-using System.Xml.Serialization;
using Cairo;
-using System.Globalization;
using Crow.IML;
-using System.Runtime.InteropServices;
-using System;
-using System.IO;
-using System.Diagnostics;
-using System.Collections.Generic;
namespace Crow
/// </summary>
protected static Interface CurrentInterface;
internal Stopwatch clickTimer = new Stopwatch();
- GraphicObject armedClickSender = null;
+ Widget armedClickSender = null;
MouseButtonEventArgs armedClickEvtArgs = null;
// internal GraphicObject EligibleForDoubleClick {
// get { return eligibleForDoubleClick; }
// clickTimer.Restart ();
// }
// }
- internal void armeClick (GraphicObject sender, MouseButtonEventArgs e){
+ internal void armeClick (Widget sender, MouseButtonEventArgs e){
armedClickSender = sender;
armedClickEvtArgs = e;
clickTimer.Restart ();
#region Public Fields
/// <summary>Graphic Tree of this interface</summary>
- public List<GraphicObject> GraphicTree = new List<GraphicObject>();
+ public List<Widget> GraphicTree = new List<Widget>();
/// <summary>Interface's resulting bitmap</summary>
public byte[] bmp;
/// <summary>resulting bitmap limited to last redrawn part</summary>
/// <summary>Store discarded lqi between two updates</summary>
public Queue<LayoutingQueueItem> DiscardQueue;
/// <summary>Main drawing queue, holding layouted controls</summary>
- public Queue<GraphicObject> ClippingQueue = new Queue<GraphicObject>();
+ public Queue<Widget> ClippingQueue = new Queue<Widget>();
public string Clipboard;//TODO:use object instead for complex copy paste
/// <summary>each IML and fragments (such as inline Templates) are compiled as a Dynamic Method stored here
/// on the first instance creation of a IML item.
/// </summary>
/// <returns>return the new instance for convenience, may be ignored</returns>
/// <param name="imlFragment">a valid IML string</param>
- public GraphicObject LoadIMLFragment (string imlFragment) {
+ public Widget LoadIMLFragment (string imlFragment) {
lock (UpdateMutex) {
- GraphicObject tmp = CreateITorFromIMLFragment (imlFragment).CreateInstance();
+ Widget tmp = CreateITorFromIMLFragment (imlFragment).CreateInstance();
AddWidget (tmp);
return tmp;
}
/// </summary>
/// <returns>new instance of graphic object created</returns>
/// <param name="path">path of the iml file to load</param>
- public GraphicObject Load (string path)
+ public Widget Load (string path)
{
lock (UpdateMutex) {
- GraphicObject tmp = CreateInstance (path);
+ Widget tmp = CreateInstance (path);
AddWidget (tmp);
return tmp;
}
/// </summary>
/// <returns>new instance of graphic object created</returns>
/// <param name="path">path of the iml file to load</param>
- public virtual GraphicObject CreateInstance (string path)
+ public virtual Widget CreateInstance (string path)
{
try {
return GetInstantiator (path).CreateInstance ();
/// </summary>
/// <returns>new instance of graphic object created</returns>
/// <param name="path">path of the iml file to load</param>
- public virtual GraphicObject CreateTemplateInstance (string path, Type declaringType)
+ public virtual Widget CreateTemplateInstance (string path, Type declaringType)
{
try {
if (!Templates.ContainsKey (path))
#endregion
#region focus
- GraphicObject _activeWidget; //button is pressed on widget
- GraphicObject _hoverWidget; //mouse is over
- GraphicObject _focusedWidget; //has keyboard (or other perif) focus
+ Widget _activeWidget; //button is pressed on widget
+ Widget _hoverWidget; //mouse is over
+ Widget _focusedWidget; //has keyboard (or other perif) focus
/// <summary>Widget is focused and button is down or another perif action is occuring
/// , it can not lose focus while Active</summary>
- public GraphicObject ActiveWidget
+ public Widget ActiveWidget
{
get { return _activeWidget; }
set
}
}
/// <summary>Pointer is over the widget</summary>
- public virtual GraphicObject HoverWidget
+ public virtual Widget HoverWidget
{
get { return _hoverWidget; }
set {
}
}
/// <summary>Widget has the keyboard or mouse focus</summary>
- public GraphicObject FocusedWidget {
+ public Widget FocusedWidget {
get { return _focusedWidget; }
set {
if (_focusedWidget == value)
/// GraphObj's property Set methods could trigger an update from another thread
/// Once in that queue, that means that the layouting of obj and childs have succeed,
/// the next step when dequeued will be clipping registration</summary>
- public void EnqueueForRepaint(GraphicObject g)
+ public void EnqueueForRepaint(Widget g)
{
lock (ClippingMutex) {
if (g.IsQueueForClipping)
if (ClippingQueue.Count > 0)
DebugLog.AddEvent (DbgEvtType.IFaceStartClipping);
#endif
- GraphicObject g = null;
+ Widget g = null;
while (ClippingQueue.Count > 0) {
lock (ClippingMutex) {
g = ClippingQueue.Dequeue ();
ctx.Operator = Operator.Over;
for (int i = GraphicTree.Count -1; i >= 0 ; i--){
- GraphicObject p = GraphicTree[i];
+ Widget p = GraphicTree[i];
if (!p.Visible)
continue;
if (clipping.Contains (p.Slot) == RegionOverlap.Out)
#region GraphicTree handling
/// <summary>Add widget to the Graphic tree of this interface and register it for layouting</summary>
- public GraphicObject AddWidget(GraphicObject g)
+ public Widget AddWidget(Widget g)
{
g.Parent = this;
int ptr = 0;
return g;
}
/// <summary>Set visible state of widget to false and delete if from the graphic tree</summary>
- public void DeleteWidget(GraphicObject g)
+ public void DeleteWidget(Widget g)
{
lock (UpdateMutex) {
RegisterClip (g.ScreenCoordinates (g.LastPaintedSlot));
}
}
/// <summary>Set visible state of widget to false and remove if from the graphic tree</summary>
- public void RemoveWidget(GraphicObject g)
+ public void RemoveWidget(Widget g)
{
// if (g.Contains(HoverWidget)) {
// while (HoverWidget != g.focusParent) {
while (GraphicTree.Count > 0) {
//TODO:parent is not reset to null because object will be added
//to ObjectToRedraw list, and without parent, it fails
- GraphicObject g = GraphicTree [0];
+ Widget g = GraphicTree [0];
RegisterClip (g.ScreenCoordinates (g.LastPaintedSlot));
GraphicTree.RemoveAt (0);
g.Dispose ();
#endif
}
/// <summary> Put widget on top of other root widgets</summary>
- public void PutOnTop(GraphicObject g, bool isOverlay = false)
+ public void PutOnTop(Widget g, bool isOverlay = false)
{
int ptr = 0;
Window newW = g as Window;
}
/// <summary>Search a Graphic object in the tree named 'nameToFind'</summary>
- public GraphicObject FindByName (string nameToFind)
+ public Widget FindByName (string nameToFind)
{
- foreach (GraphicObject w in GraphicTree) {
- GraphicObject r = w.FindByName (nameToFind);
+ foreach (Widget w in GraphicTree) {
+ Widget r = w.FindByName (nameToFind);
if (r != null)
return r;
}
(surf as XcbSurface).SetSize (clientRectangle.Width, clientRectangle.Height);
- foreach (GraphicObject g in GraphicTree)
+ foreach (Widget g in GraphicTree)
g.RegisterForLayouting (LayoutingType.All);
RegisterClip (clientRectangle);
if (HoverWidget != null) {
resetTooltip ();
//check topmost graphicobject first
- GraphicObject tmp = HoverWidget;
- GraphicObject topc = null;
- while (tmp is GraphicObject) {
+ Widget tmp = HoverWidget;
+ Widget topc = null;
+ while (tmp is Widget) {
topc = tmp;
tmp = tmp.focusParent;
}
//top level graphic obj's parsing
lock (GraphicTree) {
for (int i = 0; i < GraphicTree.Count; i++) {
- GraphicObject g = GraphicTree [i];
+ Widget g = GraphicTree [i];
if (g.MouseIsIn (e.Position)) {
g.checkHoverWidget (e);
if (g is Window)
if (HoverWidget == null)
return false;
- GraphicObject hoverFocused = HoverWidget;
+ Widget hoverFocused = HoverWidget;
while (!hoverFocused.Focusable) {
hoverFocused = hoverFocused.focusParent;
if (hoverFocused == null) {
#region Tooltip handling
Stopwatch tooltipTimer = new Stopwatch();
- GraphicObject ToolTipContainer = null;
+ Widget ToolTipContainer = null;
volatile bool tooltipVisible = false;
protected void initTooltip () {
while(true) {
if (tooltipTimer.ElapsedMilliseconds > ToolTipDelay) {
if (!tooltipVisible) {
- GraphicObject g = _hoverWidget;
+ Widget g = _hoverWidget;
while (g != null) {
if (!string.IsNullOrEmpty (g.Tooltip)) {
AddWidget (ToolTipContainer);
tooltipVisible = true;
break;
}
- g = g.LogicalParent as GraphicObject;
+ g = g.LogicalParent as Widget;
}
}
}
}
- public void ShowContextMenu (GraphicObject go) {
+ public void ShowContextMenu (Widget go) {
lock (UpdateMutex) {
if (ctxMenuContainer.Parent == null)
if (string.IsNullOrEmpty (sourcePath)) {
//inline item template
- using (GraphicObject go = this.CreateInstance())
+ using (Widget go = this.CreateInstance())
go.getIML (doc, xe);
} else {
xa = doc.CreateAttribute ("Path");
System.Reflection.Emit.Label gotoItemsContainerNotFound;
ILGenerator il = dm.GetILGenerator (256);
- il.DeclareLocal(typeof(GraphicObject));
+ il.DeclareLocal(typeof(Widget));
gotoEnd = il.DefineLabel ();
ifDataIsNull = il.DefineLabel ();
public void ProcessLayouting()
{
- GraphicObject go = Layoutable as GraphicObject;
+ Widget go = Layoutable as Widget;
// if (go == null) {
// Debug.WriteLine ("ERROR: processLayouting on something else than a graphic object: " + this.ToString ());
// return;
#endif
if (LayoutingTries < Interface.MaxLayoutingTries) {
Layoutable.RegisteredLayoutings |= LayoutType;
- (Layoutable as GraphicObject).IFace.LayoutingQueue.Enqueue (this);
+ (Layoutable as Widget).IFace.LayoutingQueue.Enqueue (this);
#if DEBUG_LOG
result = Result.Requeued;
#endif
LayoutingTries = 0;
DiscardCount++;
Layoutable.RegisteredLayoutings |= LayoutType;
- (Layoutable as GraphicObject).IFace.DiscardQueue.Enqueue (this);
+ (Layoutable as Widget).IFace.DiscardQueue.Enqueue (this);
}
#if DEBUG_LOG
else {
go.parentRWLock.ExitReadLock ();
}
- public static implicit operator GraphicObject(LayoutingQueueItem queueItem)
+ public static implicit operator Widget(LayoutingQueueItem queueItem)
{
- return queueItem.Layoutable as GraphicObject;
+ return queueItem.Layoutable as Widget;
}
public static implicit operator LayoutingType(LayoutingQueueItem lqi)
{
namespace Test
{
- public class ColorCircleSelector : GraphicObject
+ public class ColorCircleSelector : Widget
{
void computeControlPoints (
double xc, double yc,
namespace Crow
{
- public class LaggingGraphicObject : GraphicObject
+ public class LaggingGraphicObject : Widget
{
protected override void onDraw (Context gr)
{
namespace Tutorials
{
- public class SimpleGauge : GraphicObject
+ public class SimpleGauge : Widget
{
public SimpleGauge () : base() {}
public SimpleGauge (Interface iface): base (iface){}
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Container Background="DimGrey" Margin="10" Width="90%" Height="90%">
- <GraphicObject Margin="10" Background="SeaGreen"
+ <Widget Margin="10" Background="SeaGreen"
MinimumSize="50,50"/>
</Container>
\ No newline at end of file
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Container Background="Lust" Margin="10" Width="90%" Height="90%">
- <GraphicObject Margin="10" Width="50%" Height="50%" Background="Maize"
+ <Widget Margin="10" Width="50%" Height="50%" Background="Maize"
MinimumSize="50,50"/>
</Container>
\ No newline at end of file
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Container Background="MediumSeaGreen" Margin="10" Fit="true">
- <GraphicObject Margin="10" Width="50%" Height="50%" Background="DarkGreen"
+ <Widget Margin="10" Width="50%" Height="50%" Background="DarkGreen"
MinimumSize="50,50"/>
</Container>
\ No newline at end of file
</TabView>-->
<MessageBox Movable="false"/>
<ColorPicker SelectedColor="{²../go.Background}" Name="colorPicker" Margin="5" Fit="True" />
- <GraphicObject Name="go" Width="100" Height="60" Background="{../../colorList.SelectedItem}"/>
+ <Widget Name="go" Width="100" Height="60" Background="{../../colorList.SelectedItem}"/>
<Label Text="{../colorPicker.SelectedColor}"/>
</VerticalStack>
<Splitter/>
<Label Text="border test" Margin="3"/>
</GroupBox>
<Container Fit="true" Background="DimGrey" Margin="3">
- <GraphicObject Width="20" Height="20" Background="LightGrey"/>
+ <Widget Width="20" Height="20" Background="LightGrey"/>
</Container>-->
<!-- <ProgressBar Height="10" Width="150" Background="DimGrey" Value="50" />
<Slider Value="5" Width="150" Height="10"/>
<Label Text="border test" Margin="3"/>
</GroupBox>
<Container Height="Fit" Width="Stretched" Background="DimGrey" Margin="3">
- <GraphicObject Width="20" Height="20" Background="LightGrey"/>
+ <Widget Width="20" Height="20" Background="LightGrey"/>
</Container>
<ProgressBar Height="10" Width="Stretched" Background="DimGrey" Value="50" />
<Slider Value="5" Width="Stretched" Height="10"/>
</VerticalStack>-->
</HorizontalStack>
<!--<HorizontalStack Fit="true" Background="RoyalBlue" Margin="5">
- <GraphicObject Background="Red" Width="30" Height="20"/>
+ <Widget Background="Red" Width="30" Height="20"/>
<Spinner Maximum="10000000000" SmallIncrement="10" Value="0"/>
- <GraphicObject Background="Green" Width="30" Height="20"/>
+ <Widget Background="Green" Width="30" Height="20"/>
</HorizontalStack>-->
\ No newline at end of file
<?xml version="1.0"?>
<VerticalStack>
<ColorPicker SelectedColor="{²../go.Background}" Name="colorPicker" Background="DimGrey" Margin="5" Fit="True" />
- <GraphicObject Name="go" Width="100" Height="60" Background="DarkBlue"/>
- <GraphicObject Name="go" Width="100" Height="60" Background="{../colorPicker.SelectedColor}"/>
+ <Widget Name="go" Width="100" Height="60" Background="DarkBlue"/>
+ <Widget Name="go" Width="100" Height="60" Background="{../colorPicker.SelectedColor}"/>
<Label Text="{../colorPicker.SelectedColor}"/>
</VerticalStack>
\ No newline at end of file
-<?xml version="1.0"?>
-<GraphicObject Margin="10" Width="50%" Height="50%" Focusable="true"
+<?xml version="1.0"?>
+<Widget Margin="10" Width="50%" Height="50%" Focusable="true"
Background="hgradient|0:Red|0.25:Blue|0.5:Green|0.75:Yellow|1:Red"
MinimumSize="50,50" ContextCommands="{Commands}"/>
\ No newline at end of file
Height="Fit" Width="200" Margin="1" Focusable="true"
MouseEnter="{Background=hgradient|0:DarkRed|1:Transparent}"
MouseLeave="{Background=Transparent}">
- <GraphicObject Height="12" Width="20" Background="{}" Margin="0" CornerRadius="3"/>
+ <Widget Height="12" Width="20" Background="{}" Margin="0" CornerRadius="3"/>
<Label Text="{}" Margin="0" Width="Stretched"/>
</HorizontalStack>
</ItemTemplate>
<?xml version="1.0"?>
<Container Margin="20" Background="Red" >
<Container Margin="20" Background="Green" MouseDown="{../go1.Visible=True}" >
- <GraphicObject Name="go1" Margin="20" Background="DimGrey" Visible="false" MouseDown="{Visible=false}"
+ <Widget Name="go1" Margin="20" Background="DimGrey" Visible="false" MouseDown="{Visible=false}"
MouseEnter="{Background=Blue}"
MouseLeave="{Background=DimGrey}"/>
</Container>
<Label Foreground="Black" Font="mono, 12" Text="."/>
<Label Foreground="DimGrey" Font="mono, 12" Text="{Build}"/>
</HorizontalStack>
- <GraphicObject Height="30"/>
+ <Widget Height="30"/>
<Label Font="20" Text="Press <F2> and <F3> to cycle into the examples"/>
<Label Font="20" Text="Those are basic tests used to validate changes,"/>
- <GraphicObject Height="30"/>
+ <Widget Height="30"/>
<Label Foreground="DimGrey" Font="20" Text="<F5> => File dialog example"/>
<Label Foreground="DimGrey" Font="20" Text="<F6> => Window example"/>
</VerticalStack>
-<?xml version="1.0"?>
-<!--<GraphicObject Background="{./Background}"/>-->
+<?xml version="1.0"?>
+<!--<Widget Background="{./Background}"/>-->
<Border BorderWidth="1" Foreground="Black" CornerRadius="{./CornerRadius}"
Background="{./Background}"
MouseEnter="./onBorderMouseEnter"
</HorizontalStack>
<HorizontalStack Background="vgradient|0:0.5,0.6,0.5,0.5|1:0.2,0.3,0.3,0.7"
Name="hs" Margin="0" Spacing="0" Height="Fit" Visible="{./IsFloating}">
- <GraphicObject Width="5"/>
+ <Widget Width="5"/>
<Image Margin="1" Width="10" Height="10" Path="{./Icon}"/>
<Label Width="Stretched" Foreground="White" Margin="1" TextAlignment="Left" Text="{./Caption}" />
<Border CornerRadius="6" BorderWidth="1" Foreground="Transparent" Height="10" Width="10"
<Image Focusable="true" Name="Image" Margin="0" Path="#Crow.Icons.exit2.svg"
MouseClick="./butQuitPress"/>
</Border>
- <GraphicObject Width="5"/>
+ <Widget Width="5"/>
</HorizontalStack>
<Container Name="Content" MinimumSize="50,50"/>
</VerticalStack>
<!--<Group Background="DimGrey" Margin = "0" Focusable="true" >
- <Window Top="100" Left="100" Focusable="true" Caption="View 1" Width="300" Height="300"><GraphicObject Background="Green" Focusable="true" MouseEnter="{Background=Grey}" MouseLeave="{Background=Green}"/></Window>
- <Window Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></Window>
- <Window Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></Window>
- <Window Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></Window>
+ <Window Top="100" Left="100" Focusable="true" Caption="View 1" Width="300" Height="300"><Widget Background="Green" Focusable="true" MouseEnter="{Background=Grey}" MouseLeave="{Background=Green}"/></Window>
+ <Window Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></Window>
+ <Window Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></Window>
+ <Window Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></Window>
</Group>-->
<!--<Docker >
<DockWindow Resizable = "true" Top="100" Left="100" Caption="View 1" Width="300" Height="300">
<Label Text="{../../LogicalParent}" Background="Black"/>
</VerticalStack>
</DockWindow>
- <DockWindow Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></DockWindow>
- <DockWindow Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></DockWindow>
- <DockWindow Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></DockWindow>
+ <DockWindow Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></DockWindow>
+ <DockWindow Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></DockWindow>
+ <DockWindow Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></DockWindow>
</Docker>-->
\ No newline at end of file
<DockWindow Left="500" Top="500" Width="150" Height="150" Background="Yellow"/>
</Docker>
<!--<Group Background="DimGrey" Margin = "0" Focusable="true" >
- <Window Top="100" Left="100" Focusable="true" Caption="View 1" Width="300" Height="300"><GraphicObject Background="Green" Focusable="true" MouseEnter="{Background=Grey}" MouseLeave="{Background=Green}"/></Window>
- <Window Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></Window>
- <Window Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></Window>
- <Window Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></Window>
+ <Window Top="100" Left="100" Focusable="true" Caption="View 1" Width="300" Height="300"><Widget Background="Green" Focusable="true" MouseEnter="{Background=Grey}" MouseLeave="{Background=Green}"/></Window>
+ <Window Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></Window>
+ <Window Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></Window>
+ <Window Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></Window>
</Group>-->
<!--<Docker >
<DockWindow Resizable = "true" Top="100" Left="100" Caption="View 1" Width="300" Height="300">
<Label Text="{../../LogicalParent}" Background="Black"/>
</VerticalStack>
</DockWindow>
- <DockWindow Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></DockWindow>
- <DockWindow Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></DockWindow>
- <DockWindow Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></DockWindow>
+ <DockWindow Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></DockWindow>
+ <DockWindow Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></DockWindow>
+ <DockWindow Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></DockWindow>
</Docker>-->
\ No newline at end of file
<?xml version="1.0"?>
<Window Width="600" Height="500">
<VerticalStack Margin="20" Background="DimGrey" Spacing="10">
- <GraphicObject Height="100" Width="500" Background="Green"/>
+ <Widget Height="100" Width="500" Background="Green"/>
<Splitter/>
<HorizontalStack>
- <GraphicObject Height="Stretched" Width="100" Background="Red"/>
+ <Widget Height="Stretched" Width="100" Background="Red"/>
<Splitter/>
- <GraphicObject Height="Stretched" Width="100" Background="DarkRed"/>
+ <Widget Height="Stretched" Width="100" Background="DarkRed"/>
</HorizontalStack>
<Splitter/>
- <GraphicObject Height="100" Width="500" Background="Green"/>
+ <Widget Height="100" Width="500" Background="Green"/>
</VerticalStack>
</Window>
<!--<Group Background="DimGrey" Margin = "0" Focusable="true" >
- <Window Top="100" Left="100" Focusable="true" Caption="View 1" Width="300" Height="300"><GraphicObject Background="Green" Focusable="true" MouseEnter="{Background=Grey}" MouseLeave="{Background=Green}"/></Window>
- <Window Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></Window>
- <Window Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></Window>
- <Window Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></Window>
+ <Window Top="100" Left="100" Focusable="true" Caption="View 1" Width="300" Height="300"><Widget Background="Green" Focusable="true" MouseEnter="{Background=Grey}" MouseLeave="{Background=Green}"/></Window>
+ <Window Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></Window>
+ <Window Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></Window>
+ <Window Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></Window>
</Group>-->
<!--<Docker >
<DockWindow Resizable = "true" Top="100" Left="100" Caption="View 1" Width="300" Height="300">
<Label Text="{../../LogicalParent}" Background="Black"/>
</VerticalStack>
</DockWindow>
- <DockWindow Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></DockWindow>
- <DockWindow Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></DockWindow>
- <DockWindow Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><GraphicObject Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></DockWindow>
+ <DockWindow Top="200" Left="200" Focusable="true" Caption="View 2" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Blue" MouseEnter="{Background=Grey}" MouseLeave="{Background=Blue}"/></DockWindow>
+ <DockWindow Top="300" Left="300" Focusable="true" Caption="View 3" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Yellow" MouseEnter="{Background=Grey}" MouseLeave="{Background=Yellow}"/></DockWindow>
+ <DockWindow Top="400" Left="400" Focusable="true" Caption="View 4" Resizable = "true" Width="300" Height="300"><Widget Focusable="true" Background="Black" MouseEnter="{Background=Grey}" MouseLeave="{Background=Black}"/></DockWindow>
</Docker>-->
\ No newline at end of file
-<?xml version="1.0"?>
-<GraphicObject Margin="10" Width="150" Height="150" Background="SeaGreen"
+<?xml version="1.0"?>
+<Widget Margin="10" Width="150" Height="150" Background="SeaGreen"
MinimumSize="50,50"/>
\ No newline at end of file
-<?xml version="1.0"?>
-<GraphicObject Margin="10" Width="50%" Height="50%"
+<?xml version="1.0"?>
+<Widget Margin="10" Width="50%" Height="50%"
Background="hgradient|0:Red|0.25:Blue|0.5:Green|0.75:Yellow|1:Red"
MinimumSize="50,50"/>
\ No newline at end of file
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Group MinimumSize="50,50" Background="DimGrey" Margin="10" Width="90%" Height="90%">
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
VerticalAlignment="Top"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
VerticalAlignment="Bottom"
MinimumSize="10,10"/>
</Group>
\ No newline at end of file
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Group Background="DimGrey" Margin="10" Width="90%" Height="90%">
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Top"
HorizontalAlignment="Left"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Top"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Top"
HorizontalAlignment="Right"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
HorizontalAlignment="Left"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
HorizontalAlignment="Right"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Bottom"
HorizontalAlignment="Left"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Bottom"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Bottom"
HorizontalAlignment="Right"
MinimumSize="10,10"/>
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Group Background="DimGrey" Margin="10" Fit="true">
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Top"
HorizontalAlignment="Left"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Top"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Top"
HorizontalAlignment="Right"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
HorizontalAlignment="Left"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
HorizontalAlignment="Right"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Bottom"
HorizontalAlignment="Left"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Bottom"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Bottom"
HorizontalAlignment="Right"
MinimumSize="10,10"/>
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Group Background="DimGrey" Margin="10" Width="70%" Height="50%">
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Top"
HorizontalAlignment="Left"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Top"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Top"
HorizontalAlignment="Right"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="100%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="100%" Height="20%" Background="SeaGreen"
HorizontalAlignment="Left"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
HorizontalAlignment="Right"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Bottom"
HorizontalAlignment="Left"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Bottom"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Bottom"
HorizontalAlignment="Right"
MinimumSize="10,10"/>
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Group Background="DimGrey" Margin="10" Fit="true">
<Label Font="droid bold,40" Text="{fps}" Margin="10" Fit="true"/>
- <GraphicObject Margin="10" Width="20%" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="20%" Height="20%" Background="SeaGreen"
VerticalAlignment="Top"
MinimumSize="10,10"/>
</Group>
\ No newline at end of file
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<VerticalStack MinimumSize="50,50" Background="DimGrey" Margin="10" Width="90%" Height="90%">
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="10,10"/>
</VerticalStack>
\ No newline at end of file
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<HorizontalStack MinimumSize="50,50" Background="DimGrey" Margin="10" Width="90%" Height="90%">
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="10,10"/>
</HorizontalStack>
\ No newline at end of file
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<VerticalStack Background="DimGrey" Margin="10" Width="90%" Height="90%">
- <GraphicObject Margin="10" Width="Stretched" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="20%" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="60%" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="60%" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="20%" Background="SeaGreen"
MinimumSize="10,10"/>
</VerticalStack>
\ No newline at end of file
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<HorizontalStack Background="DimGrey" Margin="10" Width="90%" Height="90%">
- <GraphicObject Margin="10" Width="Stretched" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="20%" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="60%" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="60%" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="20%" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="20%" Background="SeaGreen"
MinimumSize="10,10"/>
</HorizontalStack>
\ No newline at end of file
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<VerticalStack Background="DimGrey" Margin="10" Width="90%" Height="100%">
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="Stretched" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Stretched" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="10,10"/>
</VerticalStack>
\ No newline at end of file
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<HorizontalStack Background="DimGrey" Margin="10" Width="90%" Height="100%">
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="Stretched" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Stretched" Background="SeaGreen"
MinimumSize="10,10"/>
- <GraphicObject Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="10" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="10,10"/>
</HorizontalStack>
\ No newline at end of file
<?xml version="1.0"?>
<VerticalStack Background="DimGrey" Margin="10" Width="90%" Height="90%">
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Stretched" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Stretched" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Stretched" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Stretched" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
</VerticalStack>
\ No newline at end of file
<?xml version="1.0"?>
<HorizontalStack Background="DimGrey" Margin="10" Width="90%" Height="90%">
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Stretched" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Stretched" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Stretched" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Stretched" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
- <GraphicObject Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
+ <Widget Margin="1" Width="Stretched" Height="Fit" Background="SeaGreen"
MinimumSize="2,2"/>
</HorizontalStack>
\ No newline at end of file
<RadioButton Caption="Bottom" Checked="change_alignment"/>
</VerticalStack>
</Border>
- <GraphicObject Height="200"/>
+ <Widget Height="200"/>
<Popper Caption="TestPopper" Width="100" Background="DimGrey" PopDirection="{alignment}">
<Border Fit="True" Background="SteelBlue">
<Image Fit="true" Path="#go.Images.Icons.tetra.png" Margin="10"/>
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Window Left="10" Top="10" Caption="Test window"
Width="250" Height="550" >
<VerticalStack Name="contentVSStack" Margin="10" Spacing="10" Background="0.4,0.4,0.4,0.4">
</GroupBox>
<HorizontalStack Width="Stretched" Height="Fit" Margin="10" CornerRadius="5" Background="SkyBlue">
<RadioButton Width="80" Height="Fit" Caption="Radio 2" IsChecked="true" />
- <GraphicObject Width="Stretched"/>
+ <Widget Width="Stretched"/>
<RadioButton Width="80" Height="Fit" Caption="Radio 3" />
</HorizontalStack>
<HorizontalStack Width="Stretched" Height="Stretched" MinimumSize="10,40" Margin="0" CornerRadius="5"
Background="vgradient|0:White|0.1:SteelBlue|0.9:SteelBlue|1:Transparent">
<CheckBox Height="Fit" Width="80"/>
- <GraphicObject Width="Stretched"/>
+ <Widget Width="Stretched"/>
<CheckBox Height="Fit" Width="80" IsChecked="true"/>
</HorizontalStack>
<Border Fit="true" CornerRadius="5" BorderWidth="1" >
</Container>
</Border>
<HorizontalStack Fit="true" Background="RoyalBlue" Margin="3">
- <GraphicObject Margin="10" Background="LimeGreen" Width="5" Height="5"/>
+ <Widget Margin="10" Background="LimeGreen" Width="5" Height="5"/>
<TextBox Font="droid, 16" Multiline="true" Text="this is a test\nmultiline" Margin="2"/>
- <GraphicObject Margin="10" Background="LimeGreen" Width="5" Height="5"/>
+ <Widget Margin="10" Background="LimeGreen" Width="5" Height="5"/>
</HorizontalStack>
</VerticalStack>
</Window>
\ No newline at end of file
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Window Left="10" Top="10" Caption="Test window" Width="200" Height="200" Background="0.5,0.5,0.5,0.8"
Focusable="True" CornerRadius="20" MinimumSize="100,100" MaximumSize="500,500">
<Template>
<Container Margin="20" Name="Content" Height="{../HeightPolicy}" Width="{../WidthPolicy}" Background="0.5,0.5,0.5,0.5"/>
</Template>
<!-- <Group Background="Green">-->
- <GraphicObject Height="50" Width="50" Background="Red" Margin="5"/>
+ <Widget Height="50" Width="50" Background="Red" Margin="5"/>
<!-- <Scrollbar Orientation="Vertical" Height="Stretched" Width="10" Background="Blue" Margin="0" HorizontalAlignment="Right"/>-->
<!-- </Group>-->
</Window>
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Border BorderWidth="2" Fit="true">
<VerticalStack Fit="true" Margin="5">
<ListBox Data="{TestList}" Background="0.5,0.5,0.5,0.7"
Height="Fit" Width="200" Margin="1" Focusable="true"
MouseEnter="{Background=hgradient|0:DarkRed|1:Transparent}"
MouseLeave="{Background=Transparent}">
- <GraphicObject Height="12" Width="20" Background="{}" Margin="0" CornerRadius="3"/>
+ <Widget Height="12" Width="20" Background="{}" Margin="0" CornerRadius="3"/>
<Label Text="{}" Margin="0" Width="Stretched"/>
</HorizontalStack>
</ItemTemplate>
<?xml version="1.0"?>
<Window Caption="Vertical Wrapper" Width="50%" Height="50%">
<Wrapper Orientation="Vertical" Height="Fit" Width="90%" Margin="5" Background="MediumSeaGreen" Spacing="1" >
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50%" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50%" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50%" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50%" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
</Wrapper>
</Window>
\ No newline at end of file
<?xml version="1.0"?>
<Window Caption="Vertical Wrapper" Width="50%" Height="50%">
<Wrapper Orientation="Vertical" Height="Fit" Width="Fit" Margin="5" Background="MediumSeaGreen" Spacing="1" >
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50%" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50%" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50%" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50%" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
</Wrapper>
</Window>
\ No newline at end of file
<?xml version="1.0"?>
<Window Caption="Horizontal Wrapper" Width="50%" Height="50%">
<Wrapper Orientation="Horizontal" Height="90%" Width="Fit" Margin="5" Background="MediumSeaGreen" Spacing="1" >
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50%" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50%" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50%" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50%" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
</Wrapper>
</Window>
\ No newline at end of file
<?xml version="1.0"?>
<Window Caption="Horizontal Wrapper" Width="50%" Height="50%">
<Wrapper HorizontalAlignment="Left" Orientation="Horizontal" Height="100%" Width="Fit" Margin="0" Background="MediumSeaGreen" Spacing="1" >
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50%" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50%" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50%" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50%" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50%" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50%" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50%" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50%" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50%" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50%" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50%" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50%" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
</Wrapper>
</Window>
\ No newline at end of file
<?xml version="1.0"?>
<Window Caption="Horizontal Wrapper" Width="50%" Height="50%">
<Wrapper Orientation="Horizontal" Height="Fit" Width="Fit" Margin="5" Background="MediumSeaGreen" Spacing="1" >
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50%" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50%" Background="SeaGreen"/>
- <GraphicObject Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50%" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
+ <Widget Width="50" Height="50%" Background="SeaGreen"/>
+ <Widget Width="50" Height="50" Background="SeaGreen"/>
</Wrapper>
</Window>
\ No newline at end of file
<HorizontalStack Margin="0"
MouseEnter="{Background=hgradient|0:DarkRed|1:Transparent}"
MouseLeave="{Background=Transparent}">
- <GraphicObject Height="12" Width="20" Background="{}" Margin="0" CornerRadius="3"/>
+ <Widget Height="12" Width="20" Background="{}" Margin="0" CornerRadius="3"/>
<Label Text="{}" Margin="0" Width="Stretched"/>
</HorizontalStack>
</Border>
<HorizontalStack Margin="0"
MouseEnter="{Background=CornflowerBlue}"
MouseLeave="{Background=Transparent}">
- <GraphicObject Height="8" Width="14" Background="{}" Margin="0" CornerRadius="2"/>
+ <Widget Height="8" Width="14" Background="{}" Margin="0" CornerRadius="2"/>
<Label Text="{}" Margin="0" Width="Stretched" Font="mono, 8"/>
</HorizontalStack>
</Border>
using (Showcase app = new Showcase ()) {
//app.Keyboard.KeyDown += App_KeyboardKeyDown;
- GraphicObject g = app.Load ("#Tests.ui.showcase.crow");
+ Widget g = app.Load ("#Tests.ui.showcase.crow");
g.DataSource = app;
app.crowContainer = g.FindByName ("CrowContainer") as Container;
//I set an empty object as datasource at this level to force update when new
lock (UpdateMutex) {
try
{
- GraphicObject g = CreateInstance(fi.FullName);
+ Widget g = CreateInstance(fi.FullName);
crowContainer.SetChild(g);
g.DataSource = this;
}
void Tb_TextChanged (object sender, TextChangeEventArgs e)
{
hideError();
- GraphicObject g = null;
+ Widget g = null;
try {
lock (UpdateMutex) {
Instantiator inst = null;
-<?xml version="1.0"?>
+<?xml version="1.0"?>
<Window Template="#Crow.ToolWindow.template" AlwaysOnTop="true" Width="400" Height="300"
HorizontalAlignment="Right" VerticalAlignment="Bottom">
<VerticalStack>
<Template>
<Border CornerRadius="0" Foreground="LightGrey">
<HorizontalStack Margin="0" Spacing="1">
- <!---<GraphicObject Height="8" Width="14" Background="{./Caption}" Margin="0" CornerRadius="2"/>-->
+ <!---<Widget Height="8" Width="14" Background="{./Caption}" Margin="0" CornerRadius="2"/>-->
<Label MinimumSize="80,10" Text="{./Caption}" Margin="0" Width="Stretched" Font="mono, 8"/>
<Button Width="14" Height="14" Focusable="false"
Template="#Crow.Templates.ArrowBut.template">
</Popper>
</Template>
</ComboBox>
- <GraphicObject Height="8" Width="14" Background="{Value}" Margin="0" CornerRadius="2"/>
+ <Widget Height="8" Width="14" Background="{Value}" Margin="0" CornerRadius="2"/>
</HorizontalStack>
<HorizontalStack>
<ListBox Name="kvpList" Data="{ColorsKVPList}" Margin="0"
<HorizontalStack Margin="0"
MouseEnter="{Background=CornflowerBlue}"
MouseLeave="{Background=Transparent}">
- <GraphicObject Height="8" Width="14" Background="{Value}" Margin="0" CornerRadius="2"/>
+ <Widget Height="8" Width="14" Background="{Value}" Margin="0" CornerRadius="2"/>
<Label Text="{Key}" Margin="0" Width="Stretched" Font="mono, 8"/>
</HorizontalStack>
</Border>