+*.log
build
Win_x86
Crow.userprefs
<CheckForOverflowUnderflow>true</CheckForOverflowUnderflow>
<Optimize>false</Optimize>
<OutputPath>$(SolutionDir)build\Debug</OutputPath>
- <DefineConstants>DEBUG_BINDING_FUNC_CALLS0;DEBUG_DRAGNDROP0;DEBUG_LOG0;XLIB_BACKEND0;DESIGN_MODE;DEBUG_UPDATE0;DEBUG_FOCUS0;DEBUG_DISPOSE0;TRACE0;DEBUG;MEASURE_TIME;DEBUG_LOAD0;DEBUG_BINDING0;DEBUG_CLIP_RECTANGLE0</DefineConstants>
+ <DefineConstants>TRACE0;DEBUG;DEBUG_BINDING_FUNC_CALLS0;DEBUG_DRAGNDROP0;DEBUG_LOG0;XLIB_BACKEND0;DESIGN_MODE;DEBUG_UPDATE0;DEBUG_FOCUS0;DEBUG_DISPOSE0;MEASURE_TIME;DEBUG_LOAD0;DEBUG_BINDING0;DEBUG_CLIP_RECTANGLE0</DefineConstants>
<EnvironmentVariables>
<EnvironmentVariables>
<Variable name="MONO_CAIRO_DEBUG_DISPOSE" value="1" />
/// </summary>
public struct Color
{
- internal static Type TColor = typeof(Color);
-
#region CTOR
public Color(double _R, double _G, double _B, double _A)
{
if (string.IsNullOrEmpty(s))
return White;
Color cc = default(Color);
- if (s.StartsWith ("#")) {
+ if (s.StartsWith ("#", StringComparison.Ordinal)) {
cc.R = int.Parse (s.Substring (1, 2), System.Globalization.NumberStyles.HexNumber) / 255.0;
cc.G = int.Parse (s.Substring (3, 2), System.Globalization.NumberStyles.HexNumber) / 255.0;
cc.B = int.Parse (s.Substring (5, 2), System.Globalization.NumberStyles.HexNumber) / 255.0;
}
public static bool operator ==(Color c, string n)
{
- return n.StartsWith("#") ?
+ return n.StartsWith("#", StringComparison.Ordinal) ?
string.Equals(c.HtmlCode, n, StringComparison.Ordinal) :
string.Equals(c.Name, n, StringComparison.Ordinal);
}
public static bool operator !=(Color c, string n)
{
- return n.StartsWith("#") ?
+ return n.StartsWith("#", StringComparison.Ordinal) ?
!string.Equals(c.HtmlCode, n, StringComparison.Ordinal) :
!string.Equals(c.Name, n, StringComparison.Ordinal);
}
}
public override bool Equals (object obj)
{
- return (obj == null || obj.GetType() != TColor) ?
+ return (obj == null || obj.GetType() != typeof(Color)) ?
false :
this == (Color)obj;
}
/// </summary>
internal static Dictionary<string, MethodInfo> knownExtMethods = new Dictionary<string, MethodInfo> ();
- internal static Type TObject = typeof(object);
internal static MethodInfo stringEquals = typeof (string).GetMethod("Equals", new Type [3] { typeof (string), typeof (string), typeof (StringComparison) });
internal static MethodInfo miObjToString = typeof(object).GetMethod("ToString");
internal static MethodInfo miGetType = typeof(object).GetMethod("GetType");
static MemberInfo getMemberInfoWithReflexion(object instance, string member){
Type t = instance.GetType();
#if DEBUG_BINDING_FUNC_CALLS
- Console.WriteLine ($"getMemberInfoWithReflexion ({instance},{member}); type:{t}");
+ Console.WriteLine ($"getMemberInfoWithReflexion ({instance},{member}); type:{t}");
#endif
MemberInfo mi = t.GetMember (member)?.FirstOrDefault();
if (mi == null)
try {
if (value != null) {
- if (destType == TObject)//TODO: check that test of destType is not causing problems
+ if (destType == typeof (object))//TODO: check that test of destType is not causing problems
convertedVal = value;
else {
origType = value.GetType ();
if (tmp != null)
return tmp;
- if (dstType == typeof(string) || dstType == CompilerServices.TObject)//TODO:object should be allowed to return null and not ""
+ if (dstType == typeof(string) || dstType == typeof (object))//TODO:object should be allowed to return null and not ""
return "";
if (dstType.IsValueType)
return Activator.CreateInstance (dstType);
/// Emit MSIL for conversion from orig type to dest type
/// </summary>
internal static void emitConvert(ILGenerator il, Type origType, Type destType){
- if (destType == CompilerServices.TObject)
+ if (destType == typeof(object))
return;
if (destType == typeof(string)) {
System.Reflection.Emit.Label emitNullStr = il.DefineLabel ();
else {
//implicit conversion can't be defined from or to object base class,
//so we will check if object underlying type is one of the implicit converter of destType
- if (origType == TObject) {//test all implicit converter to destType on obj
+ if (origType == typeof(object)) {//test all implicit converter to destType on obj
System.Reflection.Emit.Label emitTestNextImpOp;
System.Reflection.Emit.Label emitImpOpFound = il.DefineLabel ();
foreach (MethodInfo mi in destType.GetMethods(BindingFlags.Public|BindingFlags.Static)) {
il.MarkLabel (convert);
il.Emit (OpCodes.Ldnull);//null instance for invoke
il.Emit (OpCodes.Ldc_I4_1);
- il.Emit(OpCodes.Newarr, CompilerServices.TObject);
+ il.Emit(OpCodes.Newarr, typeof (object));
il.Emit (OpCodes.Dup);//duplicate the array ref
il.Emit (OpCodes.Ldc_I4_0);//push the index 0
il.Emit (OpCodes.Ldloc_0);//push the orig value to convert
- il.Emit (OpCodes.Stelem, CompilerServices.TObject);//set the array element at index 0
+ il.Emit (OpCodes.Stelem, typeof (object));//set the array element at index 0
il.Emit (OpCodes.Callvirt, miMIInvoke);
}
Type handlerArgsType = evtParams [1].ParameterType;
#endregion
- Type [] args = { CompilerServices.TObject, handlerArgsType };
+ Type [] args = { typeof (object), handlerArgsType };
DynamicMethod dm = new DynamicMethod ("dyn_eventHandler",
typeof(void),
args, true);
public static object Parse (string s){
if (string.IsNullOrEmpty (s))
return null;
- if (s.Substring (1).StartsWith ("gradient"))
+ if (s.Substring (1).StartsWith ("gradient", StringComparison.Ordinal))
return (Gradient)Gradient.Parse (s);
if (s.EndsWith (".svg", true, System.Globalization.CultureInfo.InvariantCulture))
- return SvgPicture.Parse (s);
+ return Parse (s);
if (s.EndsWith (".png", true, System.Globalization.CultureInfo.InvariantCulture) ||
s.EndsWith (".jpg", true, System.Globalization.CultureInfo.InvariantCulture) ||
s.EndsWith (".jpeg", true, System.Globalization.CultureInfo.InvariantCulture) ||
s.EndsWith (".bmp", true, System.Globalization.CultureInfo.InvariantCulture) ||
s.EndsWith (".gif", true, System.Globalization.CultureInfo.InvariantCulture))
- return BmpPicture.Parse (s);
+ return Parse (s);
return (SolidColor)SolidColor.Parse (s);
}
Size minimumSize = "0,0";
bool cacheEnabled = false;
bool clipToClientRect = true;
+ Type dataSourceType;
protected object dataSource;
bool rootDataLevel;
string style;
maximumSize = value;
- NotifyValueChanged ("MaximumSize", maximumSize);
+ 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")]
+ [DesignCategory ("Data")]
public virtual object DataSource {
set {
if (DataSource == value)
//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
+#region Delfault values Loading dynamic compilation
DynamicMethod dm = null;
ILGenerator il = null;
- /*dm = new DynamicMethod("dyn_loadDefValues",
- MethodAttributes.Family | MethodAttributes.FamANDAssem | MethodAttributes.NewSlot,
- CallingConventions.Standard,
- typeof(void),new Type[] {CompilerServices.TObject}, thisType, true);*/
-
- dm = new DynamicMethod("dyn_loadDefValues", null, new Type[] {CompilerServices.TObject}, thisType, true);
+ dm = new DynamicMethod("dyn_loadDefValues", null, new Type[] { typeof (object) }, thisType, true);
il = dm.GetILGenerator(256);
- il.DeclareLocal(CompilerServices.TObject);
+ 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);
//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.OrdinalIgnoreCase)){
+ 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
}
return false;
}
- #endregion
+#endregion
public virtual GraphicObject FindByName(string nameToFind){
return string.Equals(nameToFind, name, StringComparison.Ordinal) ? this : null;
using System.Linq;
using Crow.IML;
using System.Diagnostics;
+using System.IO;
namespace Crow
{
void loadPage(IList _data, Group page, string _dataTest)
{
#if DEBUG_LOAD
- Stopwatch loadingTime = new Stopwatch ();
- loadingTime.Start ();
+ Stopwatch loadingTime = Stopwatch.StartNew ();
#endif
// lock (CurrentInterface.LayoutMutex)
// items.AddChild (page);
- #if DEBUG_LOAD
+#if DEBUG_LOAD
loadingTime.Stop ();
- Debug.WriteLine("Listbox {2} Loading: {0} ticks \t, {1} ms",
- loadingTime.ElapsedTicks,
- loadingTime.ElapsedMilliseconds, this.ToString());
- #endif
+ using (StreamWriter sw = new StreamWriter ("loading.log", true)) {
+ sw.WriteLine ($"NEW ;{this.ToString(),-50};{loadingTime.ElapsedTicks,8};{loadingTime.ElapsedMilliseconds,8}");
+ }
+#endif
}
protected void loadItem(object o, Group page, string _dataTest){
/// </summary>
public class BindingDefinition
{
- public NodeAddress SourceNA = null;
- public string SourceMember = "";
- public NodeAddress TargetNA = null;
+ public NodeAddress SourceNA = null;//the widget declaring this binding in a member
+ public string SourceMember = "";//the member where the binding string has been found
+ public NodeAddress TargetNA = null;//
public string TargetMember = "";
public string TargetName = "";
- public bool TwoWay = false;
+ public bool TwoWay = false;//two way binding
+ public Type targetType = null;//added to store dataSourceType if set
#region CTOR
public BindingDefinition (NodeAddress _sourceNA, string _sourceMember){
int ptr = 0;
if (splitedExp.Length == 1) {
- if (splitedExp [0].StartsWith ("\'")) {
- if (!splitedExp [0].EndsWith ("\'"))
+ if (splitedExp [0].StartsWith ("\'",StringComparison.Ordinal)) {
+ if (!splitedExp [0].EndsWith ("\'", StringComparison.Ordinal))
throw new Exception (string.Format
("IML:malformed string constant in binding expression: {0}", splitedExp [0]));
Tokens = new string[] { splitedExp [0].Substring (1, splitedExp [0].Length - 2) };
{
RootType = rootType;
dm = new DynamicMethod ("dyn_instantiator",
- CompilerServices.TObject, new Type [] { typeof (Instantiator), typeof (Interface) }, true);
+ typeof (object), new Type [] { typeof (Instantiator), typeof (Interface) }, true);
il = dm.GetILGenerator (256);
il.DeclareLocal (typeof (GraphicObject));
if (bindDef.TwoWay)
StorePropertyBinding (bindDef.SourceNA, bindDef.SourceMember, bindDef.TargetNA, bindDef.TargetMember);
}
+ /// <summary>
+ /// Stores all the names found in current iml for binding resolution if any of them
+ /// are targeting named widget
+ /// </summary>
public void StoreCurrentName(string name){
if (!Names.ContainsKey(name))
Names[name] = new List<NodeAddress>();
if (string.IsNullOrEmpty (expression)) {
return bindingDef;
} else {
- if (expression.StartsWith ("²")) {
+ if (expression.StartsWith ("²", StringComparison.Ordinal)) {
bindingDef.TwoWay = true;
expression = expression.Substring (1);
}
iface = _iface;
sourcePath = srcPath;
#if DEBUG_LOAD
- Stopwatch loadingTime = new Stopwatch ();
- loadingTime.Start ();
+ Stopwatch loadingTime = Stopwatch.StartNew ();
#endif
try {
using (XmlReader itr = XmlReader.Create (stream)) {
} finally {
#if DEBUG_LOAD
loadingTime.Stop ();
- Debug.WriteLine ("IML Instantiator creation '{2}' : {0} ticks, {1} ms",
- loadingTime.ElapsedTicks, loadingTime.ElapsedMilliseconds, sourcePath);
+ using (StreamWriter sw = new StreamWriter ("loading.log", true)) {
+ sw.WriteLine ($"ITOR;{sourcePath,-50};{loadingTime.ElapsedTicks,8};{loadingTime.ElapsedMilliseconds,8}");
+ }
#endif
}
}
/// <summary>
/// Creates a new instance of the GraphicObject compiled in the instantiator
- /// and bind it the an interface
/// </summary>
/// <returns>The new graphic object instance</returns>
- /// <param name="iface">The interface to bind to</param>
public GraphicObject CreateInstance(){
+#if DEBUG_LOAD
+ Stopwatch loadingTime = Stopwatch.StartNew ();
+ GraphicObject o = loader (iface) as GraphicObject;
+ loadingTime.Stop ();
+ using (StreamWriter sw = new StreamWriter ("loading.log", true)) {
+ sw.WriteLine ($"NEW ;{sourcePath,-50};{loadingTime.ElapsedTicks,8};{loadingTime.ElapsedMilliseconds,8}");
+ }
+ return o;
+#else
return loader (iface) as GraphicObject;
+#endif
}
/// <summary>
/// Creates a new instance of T compiled in the instantiator
/// and bind it the an interface
/// </summary>
/// <returns>The new T instance</returns>
- /// <param name="iface">The interface to bind to</param>
public T CreateInstance<T>(){
+#if DEBUG_LOAD
+ Stopwatch loadingTime = Stopwatch.StartNew ();
+ T i = (T)loader (iface);
+ loadingTime.Stop ();
+ using (StreamWriter sw = new StreamWriter ("loading.log", true)) {
+ sw.WriteLine ($"NEW ;{sourcePath,-50};{loadingTime.ElapsedTicks,8};{loadingTime.ElapsedMilliseconds,8}");
+ }
+ return i;
+#else
return (T)loader (iface);
+#endif
}
List<DynamicMethod> dsValueChangedDynMeths = new List<DynamicMethod>();
List<Delegate> cachedDelegates = new List<Delegate>();
ctx.il.Emit (OpCodes.Ldstr, sourcePath);
ctx.il.Emit (OpCodes.Stfld, typeof(GraphicObject).GetField("design_imlPath"));
}
- #endif
-
+#endif
#region Styling and default values loading
//first check for Style attribute then trigger default value loading
if (reader.HasAttributes) {
if (mi.MemberType == MemberTypes.Event) {
foreach (string exp in CompilerServices.splitOnSemiColumnOutsideAccolades(reader.Value)) {
string trimed = exp.Trim();
- if (trimed.StartsWith ("{", StringComparison.OrdinalIgnoreCase))
+ if (trimed.StartsWith ("{", StringComparison.Ordinal))
compileAndStoreDynHandler (ctx, mi as EventInfo, trimed.Substring (1, trimed.Length - 2));
else
emitHandlerBinding (ctx, mi as EventInfo, trimed);
if (pi.Name == "Name")
ctx.StoreCurrentName (reader.Value);
- if (reader.Value.StartsWith ("{", StringComparison.OrdinalIgnoreCase))
+ if (reader.Value.StartsWith ("{", StringComparison.Ordinal))
readPropertyBinding (ctx, reader.Name, reader.Value.Substring (1, reader.Value.Length - 2));
else
CompilerServices.EmitSetValue (ctx.il, pi, reader.Value);
}
}
#endregion
-
+ /// <summary>
+ /// Reads binding expression found as attribute value in iml
+ /// </summary>
+ /// <param name="ctx">IML Context</param>
+ /// <param name="sourceMember">IML Attribute name</param>
+ /// <param name="expression">Binding Expression with accollades trimed</param>
void readPropertyBinding (IMLContext ctx, string sourceMember, string expression)
{
NodeAddress sourceNA = ctx.CurrentNodeAddress;
System.Reflection.Emit.Label endMethod = il.DefineLabel ();
- il.DeclareLocal (CompilerServices.TObject);
+ il.DeclareLocal (typeof(object));
il.Emit (OpCodes.Nop);
System.Reflection.Emit.Label endMethod = il.DefineLabel ();
- il.DeclareLocal (CompilerServices.TObject);
- ilPC.DeclareLocal (CompilerServices.TObject);//used for checking propery less bindings
+ il.DeclareLocal (typeof(object));
+ ilPC.DeclareLocal (typeof(object));//used for checking propery less bindings
ilPC.DeclareLocal (typeof(MemberInfo));//used for checking propery less bindings
System.Reflection.Emit.Label cancel = ilPC.DefineLabel ();
System.Reflection.Emit.Label endMethod = il.DefineLabel ();
- il.DeclareLocal (CompilerServices.TObject);
+ il.DeclareLocal (typeof(object));
il.Emit (OpCodes.Nop);
//by default, source value type is deducted from target member type to allow
//memberless binding, if targetMember exists, it will be used to determine target
//value type for conversion
-
CompilerServices.emitConvert (il, piSource.PropertyType);
if (!piSource.CanWrite)
il = dm.GetILGenerator (256);
- il.DeclareLocal (CompilerServices.TObject);//used for checking propery less bindings
+ il.DeclareLocal (typeof(object));//used for checking propery less bindings
il.DeclareLocal (typeof(MemberInfo));//used for checking propery less bindings
System.Reflection.Emit.Label cancel = il.DefineLabel ();
System.Reflection.Emit.Label newDSIsNull = il.DefineLabel ();
System.Reflection.Emit.Label endMethod = il.DefineLabel ();
- il.DeclareLocal (CompilerServices.TObject);
+ il.DeclareLocal (typeof(object));
il.Emit (OpCodes.Nop);
//load value changed member name onto the stack
{
Stream stream = null;
- if (path.StartsWith ("#")) {
+ if (path.StartsWith ("#", StringComparison.Ordinal)) {
string resId = path.Substring (1);
//try/catch added to prevent nunit error
try {
stream = System.Reflection.Assembly.GetEntryAssembly ().GetManifestResourceStream (resId);
- } catch{}
+ } catch {}
if (stream == null)//try to find ressource in Crow assembly
stream = System.Reflection.Assembly.GetExecutingAssembly ().GetManifestResourceStream (resId);
if (stream == null)
{
Stream stream = null;
- if (path.StartsWith ("#")) {
+ if (path.StartsWith ("#", StringComparison.Ordinal)) {
string resId = path.Substring (1);
//try/catch added to prevent nunit error
try {
ParameterInfo [] evtParams = evtInvoke.GetParameters ();
Type handlerArgsType = evtParams [1].ParameterType;
- Type [] args = { CompilerServices.TObject, CompilerServices.TObject, handlerArgsType };
+ Type [] args = { typeof(object), typeof(object), handlerArgsType };
#region Expand dyn meth
//DM is bound to templatedGroup root (arg0)
#region Items counting dyn method
//dm is unbound, arg0 is instance of Item container to expand
dm = new DynamicMethod ("dyn_count_" + fetchMethodName,
- typeof (bool), new Type[] {CompilerServices.TObject}, true);
+ typeof (bool), new Type[] {typeof(object)}, true);
il = dm.GetILGenerator (256);
//get the dataSource of the arg0
{
public struct Size
{
- internal static Type TSize = typeof(Size);
public static Size Zero
{ get { return new Size(0, 0); } }
}
public override bool Equals (object obj)
{
- return (obj == null || obj.GetType() != TSize) ?
+ return (obj == null || obj.GetType() != typeof(Size)) ?
false :
this == (Size)obj;
}
while (!r.EndOfStream) {
string s = r.ReadLine ().Trim();
if (skip) {
- if (s.EndsWith ("*/"))
+ if (s.EndsWith ("*/", StringComparison.Ordinal))
skip = false;
continue;
}
- if (s.StartsWith ("/*")) {
- if (!s.EndsWith ("*/"))
+ if (s.StartsWith ("/*", StringComparison.Ordinal)) {
+ if (!s.EndsWith ("*/", StringComparison.Ordinal))
skip = true;
continue;
}
- if (!s.StartsWith ("#define"))
+ if (!s.StartsWith ("#define", StringComparison.Ordinal))
continue;
string[] tmp = s.Split (new char[] {' ', '\t'}, StringSplitOptions.RemoveEmptyEntries);