Friday, May 30, 2008

[XAML] Using Width and Height of a Polygon/Polyline

So for awhile I was bashing my head against my desk trying to figure out how to get/set the height/width of a polygon so that I could perform a stretch type action on the element.

Originally I was not setting the width and height properties, and I was trying to find the bounding box of the item by iterating through each point in its point collection and then determining the width and height from there... which seemed to work, but if I tried to then change the width/height attribute directly the whole thing would bork on me. The width and height were returning NAN.

Turns out what I needed to do was set the Stretch property to "Fill" and then set the width and height accordingly.
Stretch [Fill] = The Shape object's contents are stretched to fill its layout space. Aspect ratio is not preserved.
Layout space = Is the amount of space the Shape is allocated by the layout system, because of either an explicit Width and Height setting or because of its HorizontalAlignment and VerticalAlignment settings.

polygon
name="PolyStretch"
points="-10,-1 200,200, -100,10"
fill="Blue"
width="50"
height="50"
stretch="Fill"
This means that I could not 'clip' a polygon while still using the stretch property... which makes sense, but my case I want changes to the layout space [height/width] to effect the points inside giving me the stretch operation - so everything is a-ok!

MSDN Reference

Tuesday, May 27, 2008

[Silverlight] XamlParseException when setting IsChecked flag in XAML

Alrighty, today I made a basic debug log to dump messages and test timings to. I wanted to setup a checkbox on my application to toggle the visibility [and to toggle off the logging/testing] of this debug panel... but when doing so I kept running into the exception:
A first chance exception of type 'System.Windows.Markup.XamlParseException' occurred in System.Windows.dll

Additional information: AG_E_PARSER_BAD_PROPERTY_VALUE [Line: 33 Position: 206]

My checkbox had two event handlers set up on them... one for Checked and one for Unchecked. These functions would toggle the visibility of the debug log. THIS is what I had done wrong however... I had also set in my XAML the IsChecked flag equal to true.

What this essentially did then, was call the event handler I had setup for Checked. Given that this event call was actually made before the entire page was loaded, I received an error when trying to toggle the visibility of the debug log which was not actually loaded into the DOM yet!

Thus here is my recommendation:
Never EVER set the IsChecked flag of a checkbox element in the XAML code itself, since there is a good chance that whatever elements you wish to command are not properly injected into the DOM yet.

After the page is initialized then add the line "[checkboxname].IsChecked = true" in the code behind... as this will guarantee that the DOM has been fully structured.

Monday, May 26, 2008

[C#] Accessors - get and set cleanliness

While looking at some example code, I bumped into some syntax that looked like a shorthand for declaring get and set methods for a given property - and I thought "well hey, isn't that cool".

Turns out that in C#, this is exactly the case...

"The accessor of a property contains the executable statements associated with getting (reading or computing) or setting (writing) the property. The accessor declarations can contain a get accessor, a set accessor, or both."

Instead of writing something like this which I do all the time:
class myClass
{
private int myProp;
public void getMyProp() { return myProp; }
public void setMyProp(int newProp) { myProp = newProp; }
}
We can do this in C#:
class myClass
{
private int myProp;
pubic int MyProp
{
get { return myProp; }
set { myProp = value; }
}
}
This is a little cleaner and allows us to access the get and set functionality in a very straight forward manner:
  • int whee = myClassInstance.myProp;
    • instead of --> int whee = myClassInstance.getMyProp();
  • myClassInstance.myProp = 22
    • instead of --> myClassInstance.setMyProp(22);
A few things to note:
  • Both the private property, and the public property containing the accessor functions may have very similar names, but do not confuse them.
  • May contain only set [write], only get [read] or both [read/write].
  • The 'value' seen in the set accessor is a C# keyword. It is a free variable that is created by the complier, and no other variables within the set accessor may share that name [duh].
  • There's more to it when talking about inheritance and abstract classes, but perhaps I'll save that for another day.
  • Can also be done for a public member variable, although to me this seems a little silly since you can directly access a public variable anyways. I just added this to show that the syntax was possible.
    class myClass
    {
    public myPublicProp
    {
    get { return myPublicProp; }
    set { myPublicProp = value; }
    }
    }

MSDN Documentation

Friday, May 23, 2008

I hate blogspots WYSIWYG

I apologize for the messy layout of the below posts. I seem to be having disagreements with the WYSIWYG editor, namely when trying to add <> symbols. Flipping back and forth between HTML and COMPOSE view will seemingly change these for me, even after I've hard coded them in the HTML view as "&lt" and "&gt".

Thursday, May 22, 2008

[C#] Nullable Types

I bumped into this in my web travels today: Nullable types. Introduced in the 2.0 .NET framework was the ability to represent the normal range of values for a given value type PLUS the null value.

Nullable types can only be VALUE types [including structs]. It cannot be applied to reference types. Syntactically they look as follows:
  • T? // Is actually shorthand for...
  • System.Nullable // A struct - see below for its properties.


Ex. int? or System.Nullable

The nullable struct brings with it two readonly properties:
  • HasValue: Returns true if the variable contains a value, and false if null.
    • ex. Can use (x.HasValue) or (x != null) pretty much interchangeably.
  • Value: Returns the value if one is assigned or throws an InvalidOperationException if not assigned. Often this function is used to help cast a nullable type to a non nullable type.
ex.
// Correct
int? iNull = null;

// Will not compile
int notNull = iNull;

// Will compile, but exc thrown if null.
int notNull2 = iNull.Value;


When using operators on nullable values, the result will be a null if any of the operands are null. When comparing nullables, if one of the values is null then the comparison is always FALSE.

Often used with Nullable types is the ?? operator. It returns the left-hand operand if it is not null, or else it returns the right operand.

int? iNull = null; int iNull2 = null;

// notNull will receive the value -1.
int notNull = iNull ?? -1;

// Can use the ?? multiple times...
int notNull2 = iNull ?? iNull2 ?? -1;


If using bool? then the variable may not be used in conditionals like if, or for. The code will not compile.

Reference MSDN

Wednesday, May 21, 2008

[C#] More on string concatenation - String.Join

After yesterday's post about "+=" vs StringBuilder, I did a little more looking around on the topic of string concatenation. It appears that if you can get the strings you wish to concatenate into an array then the String.Join(string, string[], int, int) method is actually faster then the StringBuilder.Append method.
public static string Join(
string separator,
string[] value,
int startIndex,
int count
)
Now, in my case, I have a dynamic number of strings I am concatenating together - so using String.Join is a little trickier because I seemingly have to create a List first and then copy over to a String[] before I can use the String.Join method.

My Test - String.Join vs. StringBuilder.Append vs. "+="
I was curious about this, wondering if those intermediate steps would slow things down enough to make String.Join worse than StringBuilder in efficiency... so I wrote up a small little test with timing:
...
int[] numStrings = { 100, 1000, 10000, 20000, 30000 };
foreach (int num in numStrings)
{
output += "*** NUM STRINGS = " + num.ToString() + " ***\r\n";

//---------------------------------
// String.Join
//---------------------------------
start = DateTime.Now;
poo = new List();
for (int i = 0; i < num; i++)
{
poo.Add("poo");
}
newArr = new String[poo.Count];
poo.CopyTo(newArr);
allPoo = String.Join(" ", newArr);
end = DateTime.Now;
diff = end.Subtract(start);
//---------------------------------
start = DateTime.Now;
output += "String.Join: " + diff.ToString() + "\r\n";

//---------------------------------
// StringBuilder.Append
//---------------------------------
newBuilder = new System.Text.StringBuilder();
for (int i = 0; i < num; i++)
{
newBuilder.Append("poo ");
}
end = DateTime.Now;
diff = end.Subtract(start);
//---------------------------------
start = DateTime.Now;
output += "StringBuilder: " + diff.ToString() + "\r\n";

//---------------------------------
// +=
//---------------------------------
myString = "";
for (int i = 0; i < num; i++)
{
myString += "poo ";
}
end = DateTime.Now;
diff = end.Subtract(start);
//---------------------------------
start = DateTime.Now;
output += "+=: " + diff.ToString() + "\r\n";
}
this.oam.addMessage(output);

To which the output was:
*** NUM STRINGS = 100 ***
String.Join: 00:00:00.2031224
StringBuilder: 00:00:00
=: 00:00:00

*** NUM STRINGS = 1000 ***
String.Join: 00:00:00
StringBuilder: 00:00:00
=: 00:00:00.0156248

*** NUM STRINGS = 10000 ***
String.Join: 00:00:00.0156248
StringBuilder: 00:00:00
=: 00:00:01.1249856

*** NUM STRINGS = 20000 ***
String.Join: 00:00:00.0156248
StringBuilder: 00:00:00
=: 00:00:06.5311664

*** NUM STRINGS = 30000 ***
String.Join: 00:00:00.0156248
StringBuilder: 00:00:00.0156248
=: 00:00:16.1404184

So as you can see in this test:
  • StringBuilder.Append only becomes more efficient then String.Join after 1000 strings, although even then the two seem very close in efficiency.
  • "+=" is the least efficient of the group, although it really only becomes noticeable after 1000 strings
My Conclusions
  • I'll probably try to use String.Join where ever possible when doing my large string concatenations, even if I have to place all the strings into a List before I use the method.





Tuesday, May 20, 2008

[C#] Efficient String Concatenation - "+=" vs StringBuilder

Again, in my short C# travels, I find myself very very often doing dynamic string concatenations. One major task I have tried to do is create a basic serialization function for XAML elements, so that I can store/save a XAML element to the server in my project. I thus end up doing many, many string concatenations.

Using "+=" to Concat
So often I end up doing this...:

String newStr = "";
if ([prop] != null) { newStr += "[prop]= " + obj.getValue([prop]).toString(); }

...for many, many properties. When actually compiled, every time the "+=" concatenation is used, an entirely new string must be created to hold the 'new' complete string. This can become very inefficient and slow if you do a large number of such string concats.


Using StringBuilder

What I didn't know about, was the StringBuilder class. Found under the System.Text library, StringBuilder maintains an internal buffer to which [via the function StringBuilder.Append()] will append to; thus a new string will not be created every time an append occurs. If the internal buffer is exceeded THEN a new buffer size will be allocated.

Thus the usage of StringBuilder *CAN* be more efficient then using "+=". Note that more overhead is needed to create and manage the StringBuilder object, so in all cases, StringBuilder will *NOT* be absolutely more efficient. It really depends on the size of the strings and the frequency of the concats.

General Rule of Thumb
  • If the concats can fit into one statement [or only a few statements], then the "+=" is probably the safest route to take.
  • If you have multiple long, or a dynamic amount of string concats, then StringBuilder may be able to increase efficiency.

Reference: www.yoda.archsys.com

Friday, May 16, 2008

[C#] More about Typecasting with 'as' and 'is'

Taken from this CodeGuru article I found by Jay Miller

Often in my programming experiences with C# I want to check if an object is a specific type without throwing a code stopping exception. So I end up writing something very similar to this:

if (myObject.GetType().ToString().Name == "Canvas")
{
// Wicked code goes here.
}

or

Canvas myCanvas = myObject as Canvas; // If invalid typecast this will return null.
if (myCanvas != null)
{
// Wicked code goes here.
}

I've found a slightly cleaner way to accomplish this:

Canvas myCanvas = myObject as Canvas;
if (myCanvas is Canvas)
{
// Wicked code goes here.
}

The change is subtle, but I think that it makes this comparison much more clear and easy to read. Also, according to the referenced article, this comparison via 'is' is slightly more efficient then comparing against null.

Thursday, May 15, 2008

[C#] Parameter Passing - "ref" and "out"

Before I get into parameter passing...

There are two different types in C#
1) Value-Types [http://msdn2.microsoft.com/en-us/library/s1ax56ch(VS.71).aspx]
- Structs
* Built in --> Numeric Types [int, double etc...], Bool.
* User defined
- Enums
- Unlike reference types, it is not possible for a value type to contain the null value.
2) Reference-Types [http://msdn2.microsoft.com/en-us/library/490f96s2(VS.71).aspx <-- seems to be broken]
- class, delegate, interface, object, string.
Parameter Passing
All value-type parameters are what we call "pass by value" and all changes made to that value in the function will have no affect on the original data.
All reference-type parameters are "pass by reference" and all changes made to it will be reflected in the original.
If you want to force a parameter to be pass by reference then we use the "ref" or "out" keyword.
Differences Between "ref" and "out"
"out": an out parameter of an array type must be assigned before it is used; that is, it must be assigned by the callee.
For example:
public static void MyMethod(out int[] arr)
{
arr = new int[10]; // definite assignment of arr
}
C#
"ref": a ref parameter of an array type must be definitely assigned by the caller. Therefore, there is no need to be definitely assigned by the callee. A ref parameter of an array type may be altered as a result of the call. For example, the array can be assigned the null value or can be initialized to a different array.
For example:
public static void MyMethod(ref int[] arr)
{
arr = new int[10]; // arr initialized to a different array
}

Wednesday, May 14, 2008

[C#] Explicit Typecasting - ( ) vs "as"

One thing that confused me when starting out, was the seemingly intangible difference between typecasting via ([type])object and object as [Type]. With a small amount of digging here is what I found.

Two Methods of Explicit Typecasting

- Will raise an exception if the typecast is not valid.
- Seems to have slightly more overhead in execution time [(1)][(2)]
- Works well with classic value types [int, double] [(1)]
- Will return null if the typecast is not valid.
- Seems to have slightly less overhead in execution time.
- Only works for reference conversions and boxing conversions [(1)]
* Note: I believe the following is "boxing":
int myInt = 4;
Object myObj = myInt; // <-- now myInt is boxed into myObj.
int testInt = myObj as int // <-- can do this with as operator.
References:

Checklist of problems I've ran into with developing my Project

Hopefully later I will fill in how I fixed these issues. For now this is a mental checklist for myself
  • Cloning a XAML element
    • XAMLWriter does not exist in 2.0, so do manually.
    • Reflection is an option perhaps, but very slow.
  • Problems with XAMLReader in 2.0
    • With 2.0 must now always include a namespace.
    • Wrapped my XAML elements in a Canvas containing namespace so that XAMLReader can properly load an element... and then remove the wrapping Canvas.
  • Exception of type 'System.ArgumentException'. Additional information: Value does not fall within the expected range.
    • Usually found when trying to add a child to an element/Collection?
    • If child already has a parent.
    • If name of object already exists in the DOM.
  • Httprequests in Silverlight
  • Reading/Writing files [XAML] from the server [using PHP]
    • Must give correct permissions to the folder you want to read/write to. In windows, I needed to give read/write access to the "Internet Guest Account" user.
  • Using multiple user controls in one Silverlight app.
    • For example if I have a separate ColorPicker I want to use... and it is it's own User Control, how can I incorporate it into my project and get access to the properties I need from it [namely hex color].