Jonathan Sawyer

The 666 gadget industry

I must say over the last couple of years I have had a torrid time with technology. I wouldn't consider myself to be a gadget geek, but if I look around I own a lot more than most people. Here they are in no particular order

Zune 30GB
Nokia E65
Nokia N95 8GB
PSP
IPod Nano
Zen Stone

My post today is about the treachery and total debauchery of the gadget industry! First lets start with Sony Eriksson ... for all purposes I will chose to blame the Swedes ... I know there social system is buckling under uncontrolled immigration ... but for heaven sake the W950i was a joke! For me this very clearly shows the Fins superiority - Go Kimi! Nokia reliably produce good quality handsets. What makes them so great? Well its very simply the software. I would love to know what goes into there development cycles. I think Nokia have really got a great thing going. The product speaks for itself!

Sony/Ericson W950i Hell (Blame the Swedes)

Now I had my handset replaced twice and all the bugs listed below I found in both! I real testament to poor software design and implementation!
Bugs
1. Alarm. Every time you create an alarm it creates a new alarm. Old alarms cannot be removed. That means you have about 10 alarms going off everyday. Some in a row.
2. Clock. The clock slows down every couple of weeks and has to be reset
3. Reception. The phone indicates that it has reception. Next thing you know you have a voice mail. So calls go directly to voice mail.
4. Locking. When the phone is locked the music player can still be activated .
5. Degrading. The software degrades very quickly! Menus start disappearing. The device slows down completely.

These issues are so small. However they affect the use of the product to such an extent the product becomes unusable! The phone overall was not even close to ready for release but they decided to do it anyway! Personally I will never buy a Sony Eriksson again. I think the best rule of thumb here is dont get stuff when its hot off the shelf. The phone just arrived and I should've waited for the reviews. Reading around on the net now its clear ... the phone bombed!

Product Rating. 1/10. Only because I dont give 0. Don't buy this! Even if all the bugs are fixed its rubbish.

Zune 30GB

Im a very happy microsoft programmer. Yes I do know how to do a hundred workarounds for most things. However I find the .NET framework to be a happy place for me to plot my path for evil world domination. I decided based on my belief that MS is doing a good job to checkout the Zune 30GB. It is the direct competitor for the IPod 30GB. Here are a few things you should know before purchasing this device.

1. Its not thin
2. Syncing takes forever - I mean forever. All files are converted to ZUNE compliant format.
3. It only supports a few formats. You have to convert everything to MS format ... MS then converts it a Zune format. I left mine running overnight and it loaded up two 800 MB movies. 
4. The software for loading up files is not user friendly and it took me a fair bit of time to get used to it. Things like auto syncing really annoyed me. It syncs directories ... so if you remove a file from your PC it removes it from the Zune.

The software on the device is excellent though! It is smooth quick to react and very intuitive! However I think that MS failed BIG time when deciding not to support more formats!

Product Rating 6/10. Lots of space. Good device software. Poor PC software. Nightmare on Sync street.

NOKIA N95 8GB

Consistency. Small steps. Keep it simple. What goes on at Nokia I would love to know. These Fins with their suicidal rally and F1 drivers seem to chern out the best phones year after year. I think its to cold up there so they just eat potatoes and have public discussions about the next Nokia. This is also further enhanced by some Rally driving, vodka drinking and wife carrying ... sometimes all together. Then its back to discussing the next Nokia.

If you are thinking about purchasing a Nokia N95 8GB ... DO IT! This in the same vein as the E65 is one of the best devices I have found. I sometimes find myself pondering when the next gadget that will fill the void in my life will be released. You know that gadget that begets all gadgets. The device with the Phone, Camera, Music, Video, Gaming, Internet, Business etc ... Well lets just say the void is very very close to being filled.

9/10 Because I dont give 10's.

Nokia represent wisdom in my book. All these products have been approached with a different philosophy. W950i must have been following Homer Simpsons ... Dope ... The alarm wont work ... Dope ... No one will figure it out.

I think we all can learn from Nokia! Long live the Finns!

Posted by jonno | with no comments

Agile Cowboy Fairy Tale!

Wow what a wonderfully deluded fairy tale. Hope you dont read it to your kids!

http://www.infoq.com/news/2008/03/agile-cowboy-fairytale


http://www.softwaremetrics.com/Agfa/Agile%20Paper.pdf

 

I would love to know what others think about this.

Posted by jonno | 1 comment(s)

XP and "Group Think"

XP and Group Think

A post I found at http://dotnet.org.za/virtualstaticvoid/archive/2008/02/28/convention-by-observation-amp-intuition.aspx got me thinking about how XP teams tend to develop code that is to the quality of the best or most influential developer within the pack. That in itself is an interesting observation and shows how important it is to have the right people in the influential position (NOTE: In general this is self appointed OR annointed and its not always a good thing!!) All the ideas streaming from the influential developer are spawned through thier grooming from various XP brain washing sessions, mental agile uploads, industry standards and offcourse Star Wars (Episode one). How does this come about? Through midnight code reviews between streaming porn and eating the last of the rusks, through pick and choose reviews, through stressful Monday morning boardroom discussions ... NOPE! It should happen everytime some checks in new business value.


Why does XP work ... well its the process that aids code quality! Its the process that enforces high standards and gets the best out of your team. Follow these rules for a flawless checkin and improved code quality.

 When you are ready to add business value (checkin)

1. Get someone within your team to review every line of code that different from that which is in the repository. I have heard the argument tons of times. If it takes to long. Well then clearly your checkin is to big. Try choosing someone new each time. Even the pimple faced fresh outta varsity geek! This either teaches them something and surprizingly more than not you will find that they didnt drop a 100 grand on an education for nothing!

2. Together you walk over the code that has been changed. Preferable with some dif application. Check for modifications etc. This should really take a couple of minutes 5 - 10 at max. Any problems are discussed and either the checkin is delayed (no quick fixes) or the matter is escalated to another team member if it cant be resolved within a short enough period.

3. Checkin and reward yourself with an office rusk

4. Code


5. Repeat.

 By doing this the code begins to look very similar and consistant. There is no "Hey I didnt write this thats Bobs code" ... "Wheres Bob??" ... "Bobs Dead". Everyone is made accountable!

NOTE: I know unit tests are important and essential in XP period! I havent included them just to show the basics. If they are involved then they need to run with the code from the server on your local machine. They also have to run on the server and the peer who is checking should confirm all public methods are tested adequetly (or automate)!

Posted by jonno | with no comments

BinaryFormatter The located assembly's manifest definition does not match the assembly reference.

BinaryFormatter The located assembly's manifest definition does not match the assembly reference. (Exception from HRESULT: 0x80131040) 

Now this is pretty cool. If you have played around with the BinaryFormatter and Deserialization you should be aware of this. During deserialization the assembly information that is used to reconstruct the object from a binary format is used to identify the unique assembly. This may or may be a bug. You will however encounter this all the way up to .NET 3.5.

Its mentioned in the following article
http://blogs.msdn.com/junfeng/archive/2004/03/25/95826.aspx

Confirmed problem
http://connect.microsoft.com/VisualStudio/feedback/ViewFeedback.aspx?FeedbackID=119402

 A pretty straight forward workaround. You have to manually resolve the name of the assembly. Very pretty for something that can leave you feeling pretty ugly!

       
ResolveEventHandler
loadComponentAssembly = new ResolveEventHandler(LoadComponentAssembly);
AppDomain.CurrentDomain.AssemblyResolve += loadComponentAssembly;

     try
            {               
                RijndaelManaged rijndael = new RijndaelManaged();
                ICryptoTransform decryptor = rijndael.CreateDecryptor(Key, IV);
                BinaryFormatter formatter = new BinaryFormatter();
                Stream input = File.Open(path, FileMode.Open);
                CryptoStream cryptoInput = new CryptoStream(input, decryptor, CryptoStreamMode.Read);
                List<MyObject> MyObjectGroups = formatter.Deserialize(cryptoInput) as List<MyObject>;               
                cryptoInput.Close();
                input.Close();
                return MyObjectGroups;
            }
            catch (CryptographicException cryptographicException)
            {
                throw new Exception(String.Format("An exception occured while decrpting file Path {0}. Exception {1}", path, cryptographicException.Message));
            }
            catch (Exception exception)
            {
                throw new Exception(String.Format("An exception occured while decrpting file Path {0}. Exception {1}", path, exception.Message));
            }
            finally
            {   
                AppDomain.CurrentDomain.AssemblyResolve -= loadComponentAssembly;
            }
        }

static Assembly LoadComponentAssembly(Object sender, ResolveEventArgs args)
{
string simpleName = args.Name.Substring(0, args.Name.IndexOf(','));
string assemblyPath = simpleName + ".dll";
return Assembly.LoadFrom(assemblyPath);
}

Posted by jonno | 9 comment(s)

Rijndael Binary Encryption Writer and Decryption Reader

I just found this code very simple. There are a lot of people who have problems with this on the net so decided to post it. Its based on the RijndaelManager and serializes and encrypts the data to a file. It also allow for deserializing and decryption of data. Checkout wikipedia for an explanation of Rijndael http://en.wikipedia.org/wiki/Advanced_Encryption_Standard

 

public static class RijndaelManagedBinaryConvertor

{

private static byte[] Key = { .... your key };
private static byte[] IV = { ..... your IV };
public static void EncryptDataToFile(List<MyObjects> myObjects, string path)
{
try

{

RijndaelManaged rijndael = new RijndaelManaged();
ICryptoTransform encryptor = rijndael.CreateEncryptor(Key, IV);
BinaryFormatter formatter =
new BinaryFormatter();
Stream output = File.Open(path, FileMode.Create);
CryptoStream cryptoOutput =
new CryptoStream(output, encryptor, CryptoStreamMode.Write);
formatter.Serialize(cryptoOutput, myObjects);
cryptoOutput.FlushFinalBlock();
cryptoOutput.Close();
output.Close();

}
catch (CryptographicException cryptographicException)

{

throw new Exception(String.Format("An exception occured while encrpting file Path {0}. Exception {1}", path, cryptographicException.Message));

}

catch (Exception exception)

{

throw new Exception(String.Format("An exception occured while encrpting file Path {0}. Exception {1}", path, exception.Message));

}

}

public static List<MyObjects> DecryptDataFromFile(string path)

{

try

{

RijndaelManaged rijndael = new RijndaelManaged();
ICryptoTransform decryptor = rijndael.CreateDecryptor(Key, IV);
BinaryFormatter formatter =
new BinaryFormatter();
Stream input = File.Open(path, FileMode.Open);
CryptoStream cryptoInput =
new CryptoStream(input, decryptor, CryptoStreamMode.Read);List<MyObjects> myObjects = formatter.Deserialize(cryptoInput) as List<MyObjects>;
cryptoInput.Close();
input.Close();
return myObjects;
}

catch (CryptographicException cryptographicException)

{

throw new Exception(String.Format("An exception occured while decrpting file Path {0}. Exception {1}", path, cryptographicException.Message));

}

catch (Exception exception)

{

throw new Exception(String.Format("An exception occured while decrpting file Path {0}. Exception {1}", path, exception.Message));

}

}

}

Posted by jonno | 1 comment(s)

Is Agile Fragile ... ?

When you decide to adopt something that people don’t understand and openly criticize as "Cow-Boyish/Girlish". You begin to realise that the ignorance that people widely consider to be common sense will be a greater problem to overcome than you anticipated. What reinforces this? Generally Fragile projects that have failed are a result of pick and choose and not adhering to the agile diet. They then claim … “We tried agile and it failed”. Yet all they do is write unit tests or adopt stand up meetings. You didn’t try agile dude you tried FRAGILE!

 Kent Beck the father of extreme programming clearly says first adopt the full methodology. Then gradually customize it to your needs. Starting with a few of the concepts will still reap benefits through unit tests, user stories or acceptance tests. However on more challenging projects this just won’t cut it!

It is agile after all! Start by adopting all, then through deep understanding modifying it to meet your needs.

Checkout http://www.extremeprogramming.org/ for one of the best overviews of XP I have seen!

 

 

Posted by jonno | with no comments

Designing a component library in ASP.NET

This is example has been tested for 2005 but I have done the same with 2003. Very often it becomes apparent that a control is going to be used more than once and may benefit other projects. It also may be easier and tidier to create controls when designing your application. Below I have shown how to create a very simple ASP.NET component using the control class.

For this example you will need an ASP.NET website. Right click your solution and click Add New Project. Select Class Library.

Add the project as a reference to your web project. Now add a new class to your control library project called DemoComponent.cs. And copy the following code into DemoComponent.cs file.

using System;
using System.Web.UI;
using System.Xml.XPath;
using System.Web.UI.WebControls;
using System.ComponentModel;
using System.ComponentModel.Design;
using System.Web.UI.Design;
using System.Web.UI.Design.WebControls;
namespace MyControls
{
[ToolboxData(
@"<{0}:DemoComponent runat=""server""></{0}:DemoComponent>")]
public class DemoComponent : Control
{
private bool _dataSourceSet = false;
private string[] _groups = null;
public DemoComponent() { }
public string[] DataSource
{
set
{
if (value == null)
throw new Exception("DataSource can't be NULL.");
_groups =
value;
_dataSourceSet =
true;
}
}

public override void DataBind()
{
if (!_dataSourceSet)
throw new Exception(String.Format("{0}.DataSource property needs to be set.", this.ID));
base.DataBind();
}

/// <summary>

/// Put your JavaScript here as this is rendered before the HTML is rendered. So that JavaScript references will be there when HTML is rendered

/// </summary>

/// <param name="e"></param>

protected override void OnPreRender(EventArgs e)
{
if (!Page.ClientScript.IsClientScriptBlockRegistered("PointLessMessage"))
{
string script = @"
<script language='javascript' type='text/javascript'>
function DisplayAlert()
{
alert('See JavaScript is fun!')
}
</script>
"
;
Page.ClientScript.RegisterClientScriptBlock(this.GetType(), "PointLessMessage", script);
}
base.OnPreRender(e);
}

/// <summary>
///
Put your HTML here
/// </summary>
///
<param name="writer"></param>
protected override void Render(HtmlTextWriter writer)
{
if (_groups == null)
return;  //Just doing this to render control properly


foreach (string value in _groups)
{
writer.Write(
@"<table border=""0"" onclick=""DisplayAlert()"" >
<tr>
<td width='30px'></td>
<td>"
+ value + @"
</td>
</tr>
</table>"
);
}
base.Render(writer);
}
/// <summary>
///
This section manages the state of the datasource
/// </summary>
///
<returns></returns>
protected override object SaveViewState()
{
object[] states = new object[2];
states[0] =
base.SaveViewState();
states[1] = _groups;
return states;
}
protected override void LoadViewState(object savedState)
{
object[] states = (object[])savedState;
base.LoadViewState(states[0]);
_groups = (
string[])states[1];
}
}
}

Now compile you control library and create a new file inside your ASP.NET application called HowzYourMother.aspx. Switch to design mode of the HowzYourMother.aspx page. Open up the toolbox and you should see a New Tab called the name of your components dll namespace. Under that you should find your control called DemoComponent. You can then proceed to drag the component onto your page.

If this does not happen automatically you can explicitly either add the compiled dll to your components menu in toolbox you will need to right click on your toolbox and go to Add Item and then follow the wizard to select you controls assembly.

If you switch to source view of the ASPX page it should look something like this depending on what you have named things.

<%@ Page Language="C#" AutoEventWireup="true" CodeFile="HowzYourMother.aspx.cs" Inherits="ASPTreeView" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<%@ Register TagPrefix="Demo" Namespace="MyControls" Assembly="MyControls" %>
<html xmlns="http://www.w3.org/1999/xhtml" >
<
head runat="server">
<
title>Untitled Page</title>
</
head>
<
body>
<
form id="form1" runat="server">
<
div>
<
Demo:DemoComponent ID="demoComponent" runat="server" />
</div>
</
form>
</
body>
</
html>

You then load your control by doing the following in the behind CS file.

protected void Page_Load(object sender, EventArgs e)
{
if (!this.IsPostBack)
{
demoComponent.DataSource = new string[] {
"Item 1", "Item 2", "Item 3", "Item 4" };
demoComponent.DataBind();
}
}

Now all you need is a little imagination and you can whip together anything. Its pretty simple!! in my next post I will explain how to extend this control to create your own custom control with AJAX support.

 

Posted by jonno | 6 comment(s)

Extreme Programming and Expressing intention

As I have worked with XP a fair bit, I tend to accept some things without really going into much though as to why I am thinking that way. I never considered adding comments as I had been coding by "Expressing my intention", in a previous post on my blog I tried to explain why I dont agree with commenting but now it’s become more apparent.

Expressing intention means to explain in more detail as to what your code does. It applies to single statements and works its way up through methods, classes and the application architecture. Without expressions.


Users u = User.All();
double tSalaries;
for(int i = 0; i < u.Count; i++)
{
      double tSalary;
      if(u.Job == "Prog")
      {
         double tSalary =  uIdea [I].Sal * 12;    
         tSalaries += tSalary;
      }
}
return totalSalaries;

Using a technique called expressing intention you would specify more clearly what you are doing.

Users programmerUsers = User.GetUsersFor(JobType.Programmers);
double yearlySalariesForAllProgrammers = 0.0;
const int TwelveMonthYear = 12;

for(int index = 0; index < programmerUsers.Count; index++)
{
      double yearlyProgrammerSalary +=  programmerUsers[index].MonthlySalary * TwelveMonthYear;    
      yearlySalariesForAllProgrammers += yearlyProgrammerSalary ;      
}
return yearlySalariesForAllProgrammers ;

Although this is just a slap together how’s your mother. It shows us a clearer example of another powerful language! ENGLISH or if you want to AFRIKAANS.
Many people will still use variable like i and x and z. They will abbreviate as much as possible but this just makes it more difficult for people to understand.

I think abbreviation can become necessary when you are trying to win the annual JavaScript 5k award. For example i rather than index is lighter. How many K's it saves you is all relative to how maintainable it is. On the subject I found a funny little bug in ICallbackEventHandler client side AJAX script WebResource.axd. The i is declared as a global - any variable declared inside a function that is being used without the var declaration becomes global. This means that they could infringe on your code if you had done the same thing. We will let you off this time MS ;)

function WebForm_CallbackComplete() {
for (
i = 0; i < __pendingCallbacks.length; i++) {

On the other hand ICallbackEventHandler is really cool!!! I slatted it a little but managed to manipulate it for my own good! If you are creating a control so you are inheriting from the control like such  public class TreeViewComponent : Control you can also implement the , ICallbackEventHandler.

So you will be looking at something like this

[ToolboxData(@"<{0}:TreeViewComponent runat=""server""></{0}:TreeViewComponent>")]
public class TreeViewComponent : Control, ICallbackEventHandler

This means you can create a control with AJAX support using
ICallbackEventHandler! If you havent try it I really suggest so! Its pretty awesome man!!!!!!!!!!

Some of the new controls like GridView and TreeView implement it already so if you want to add Asynch support for these controls its already provided.

Good luck and happy coding!!

 

Posted by jonno | with no comments

XSD.exe, Salad Tosser and Studio 2005

Man this post is exciting me so much and it really should you too! Handling XML through microsoft XSD.exe tool which can be found from the frameworks command line utility!

I'm not sure how studio 2003 handles this but 2005 has this brilliant little feature.

When you add an XSD file to your project it automatically generates the object hierarchy and creates a typed dataset that wraps the object hierarchy.

If im still talking greek or is it geek I will elaborate a little.

Create a simple xml file call it salad tosser

<?

xml version="1.0" encoding="UTF-8"?>
<tosser myNewLanguage='salad'>
            <saladTosser name='1' />
            <saladTosser name='2' />
            <saladTosser name='3' />
            <saladTosser name='4' />
            <saladTosser name='5' />
            <saladTosser name='6' />
</tosser>

Go to

1. Start > All Programs> Microsoft Visual Studio 2005 > Visual Studio 2005 > Visual Studio 2005 Command Prompt
2. Type in XSD.exe
3.Enter xsd.exe [your path to saladtosser.xml]
4. It will write you out an XSD file to a location (which you can specify if desired)
5. Add this to your project
6. WALA

Studio generates the typed dataset and object hierarchy!!!!!

You now have a typed dataset that handles loading files following the rules created in the xsd schema. There are still a few down sides one of them being that the typed datasets are all called NewDataSet. I know what most of you are saying ... yeah salad tosser is too simple! I have tried it on very complex schema's including namespaces and stuff and had very positive results!

Posted by jonno | 1 comment(s)

Ajax.NET and Microsofts blurry vision of Ajax

I've been a bit slow on the Ajax and Visual Studio 2005 uptake. So what I'm saying now may seem bloody obvious to a some!

One thing that irritated me initially is that studio 2005 has running documents moved to something called Script Editor. Its not enabled by default so you need to do the following in the Visual Studio 2005 IDE

* Tools > Customize.
* Select the Command Tab
* Select Debug from the list, on the right hand side drag Script Editor somewhere.

This will enable you to have running documents which allow you to debug client side script. Start up the application in debug mode. Navigate to the page you wish to debug and then have a look in Script Editor. You will see all active documents that are on the client. Insert a breakpoint as you would with normal server side code and wala. Unfortunitly you can only do this at runtime and it does not remember your breakpoints.

You also need to ensure that you have enabled browser debugging in IE (you have to go through IE even if your using other browsers)

In IE go to Tools > Internet Options... > Advanced > Uncheck Disable Script Debugging (Internet Explorer) or if your using another browser (other). Let me know if this works for you.

I decided to compare both Microsoft vision for Ajax (not Atlas just the ICallbackEventHandler) and "raw" Ajax.NET. I missioned around for a while with MS rather weird implementation but managed to create what I consider to be a very simple implementation of ICallbackEventHandler. The problem really is that all calls that you create will return to the same methods. This means with multiple calls you will have to handle them inside the same methods. The "multiple" offenders are RaiseCallbackEvent(string eventArgs) and GetCallbackResult(). Please for the love of Mass don't go down the route of semi implementing ICallbackEventHandler and Ajax.NET. It just makes things too complex! Its not a best of breads its a mongrel!!!

If you do need to have multiple calls and you want to use use ICallbackEventHandler the following control that I cleverly sweated out should do it for you.

The other option would be to implement it directly from your page public partial class _Default : System.Web.UI.Page, ICallbackEventHandler. I do predict that your code will be very messy if you choose the latter option!

The C#

using System.Web.UI;
using System;

public delegate string AjaxGetCallbackResult();
public delegate void AjaxRaiseCallbackEvent(string eventArgument);

public class AjaxEventControl : Control, ICallbackEventHandler

         public event AjaxGetCallbackResult AjaxGetCallbackResultEvent;
         public event AjaxRaiseCallbackEvent AjaxRaiseCallbackEventEvent;

         public void RaiseCallbackEvent(string eventArgument)
         {
                if (AjaxRaiseCallbackEventEvent != null)
               {
                           AjaxRaiseCallbackEventEvent(eventArgument);
               }else
               
{
                           throw new Exception("For the love of MASS!!!!! You have not implemented the AjaxRaiseCallbackEventEvent.");
               }
          }

         public string GetCallbackResult()
        {
               if (AjaxGetCallbackResultEvent != null)
                        return AjaxGetCallbackResultEvent();
               throw new Exception("For the love of MASS!!!!! You have not implemented the AjaxGetCallbackResultEvent.");   
         }
}

Declare an instance of AjaxEventControl inside your webpage.

public AjaxEventControl userAjaxEventControl = new AjaxEventControl();
private string userReturnFromServer = "";

You will need to setup the mapping inside the onInit event as such

protected override void OnInit(EventArgs e)
{
 userAjaxEventControl.AjaxGetCallbackResultEvent += new AjaxGetCallbackResult(userAjaxEventControl_AjaxGetCallbackResultEvent);

userAjaxEventControl.AjaxRaiseCallbackEventEvent += new AjaxRaiseCallbackEvent(userAjaxEventControl_AjaxRaiseCallbackEventEvent);

//AddParsedSubObject will add the control to the page hierarchy.
this
.AddParsedSubObject(this.userAjaxEventControl);
string callbackSource= Page.ClientScript.GetCallbackEventReference(userAjaxEventControl, "argument", "UserCallback", "context", "ErrorCallback", true);
string functionSource = @"function RetrieveDataRows(argument, context)
{ "
+ callbackSource + "; }";
Page.ClientScript.RegisterClientScriptBlock(
this.GetType(), "RetrieveDataRows", functionSource, true); base.OnInit(e);
}

void userAjaxEventControl_AjaxRaiseCallbackEventEvent(string eventArgument)
{
DataTable dataTable = AjaxRD.DataAccess.Users.Get(Convert.ToInt32(eventArgument));
HtmlTableFormatter htmlTableFormatter = new HtmlTableFormatter();
userReturnFromServer = htmlTableFormatter.GetHtml(dataTable);
}

string userAjaxEventControl_AjaxGetCallbackResultEvent()
{
return userReturnFromServer ;
}

 

The JavaScript is pretty simple.

<

script language="javascript" type="text/jscript">

function RetrieveInformation()
{
var numberOfRows = document.forms[0].numberOfRowsTextBox.value;
RetrieveDataRows(numberOfRows,
"RetrieveInformation");
}

function UserCallback( result, context )
{
      var userTableDivObject = document.getElementById('userTableDiv');
      userTableDivObject.innerHTML += result;
}

function ErrorCallback( error, context )
{
         var userTableDivObject = document.getElementById('userTableDiv');
         
 userTableDivObject.innerHTML += 'Something went wrong ' + error;
}

</

script>
<form id="Form1" runat="server">Number of Rows<br />
<input id="txtNumber" name="numberOfRowsTextBox" type="text"/>
<button id="retrieveInformationButton" onclick="RetrieveInformation()">Retrieve Info</button>
<div id="userTableDiv">
</div>
</form>

The benefit of doing this is you can declare multiple instances of AjaxEventControl and the events can be more easily controlled. I hope this is clear!! If its not please say so and I will provide the full source and more detailed explanation.

Now this is what cracks me up! The Ajax.Net implementation is really so much more simple!  The JavaScript and HTML

<

script language="javascript" type="text/javascript">

function

RetrieveInformation(divName)
{
var userInformation = AjaxDotNet.GetUserInformation( document.forms[0].numberOfRowsTextBox.value ).value;
var userTableDivObject = document.getElementById(divName);
userTableDivObject.innerHTML += userInformation;
}

</

script>
<form id="form1" runat="server">Number of Rows<br />
<input id="txtNumber" name="numberOfRowsTextBox" type="text" />
<button id="retrieveInformationButtonDiv1" onclick="RetrieveInformation('userTableDiv')" type="button">Retrieve Info Div 1</button>
<button id="retrieveInformationButtonDiv2" onclick="RetrieveInformation('userTableDiv2')" type="button">Retrieve Info Div 2</button><table>
<tr>
<td><div id="userTableDiv">
</div>
</td><td><div id="userTableDiv2">
</div>
</td>
</tr>
</table>
</form>

The C#

protected void Page_Load(object sender, EventArgs e)
{
AjaxPro.
Utility.RegisterTypeForAjax(typeof(AjaxDotNet));
}

[AjaxPro.

AjaxMethod]
public string GetUserInformation(int numberOfUsers)
{
DataTable dataTable = AjaxRD.DataAccess.Users.Get(numberOfUsers);
HtmlTableFormatter htmlTableFormatter = new HtmlTableFormatter();
return htmlTableFormatter.GetHtml(dataTable);
}

I can't see the point of using ICallbackEventHandler! The next problem I have is managing the data. Does anyone have any ideas as to the rendering of the string based data any paradigms or frameworks.

Posted by jonno | 4 comment(s)

Looking back over the other shoulder

Well yes you guessed it, I recently joined www.valtech.co.uk in London and have been here for a little less than a week now. London has been amazing to me! Its organzined and I'm having a lot of fun!

The lead scientest at valtech is Craig Larmen who is a well know and respected Agile auther with books like "Agile and Iterative Development" and Applying UML and Patterns: An Introduction to Object-Oriented Analysis and Design and Iterative Development" WOW thats a mouth full!

I started off my Agile adventures at www.digiata.com where I spent just over two years. Digiata uses an XP process with a few added hooks. Teams looking to implement it must realise that it requires a large amount of seemingly Kamakazi commitment (but no one dies)!

Communication, Simplicity, Feedback, and Courage are the four values that XP programmers carry with them. I would recommend that when implementing an XP process have courage and follow Kent Becks advice. Very often there is a temptation to implement only the steps that we feel comfortable with. This can work in some instances but generally its the important steps and proceedures that are not included. The process is then buffed up by other development crutches. XP has a proven track record and if implemented properly will leave your developers with a grin that will make colgate want to hire them.

 

 

Posted by jonno | 2 comment(s)

Factory Solution

I am currently working on a piece of software to manage parts of some future projects. A lot of the basics that every system requires like Editing, Adding and Deleting items are repetitive. I managed to abstract most of these into a useful little DataGrid Control. Generation of my core (no joins) dataaccess was done through MyGeneration which has really impressed me.

Anyways now my control couldn’t determine who was calling it except that it implemented IGeneratedDataAccess and. So I ended up writing a little data factory to handle this when bang! I found the most useful Method inside the System.Activator class called CreateInstance.

System.Activator.CreateInstance

 

public static IGeneratedDataAccess Get(Type type)

         return (IGeneratedDataAccess) System.Activator.CreateInstance(type);
}

This allows you to create an object just knowing what type it is ...  this can dramatically reduce your code when implementing a factory if you even still require one. I tore down all my pages of code (Classes with Attributes etc) and reduced it to these few lines.

Any object that now implements the interface IGeneratedDataAccess can now be created ... the code could also include a check to see whether the type is indeed a sub-class of IGeneratedDataAccess. So now all you do is generate your DataAccess scripts through MyGeneration. Pop-on the control and set the TypeOf property on the control and Wala. While I’m  on the automate your Job mind thread I have heard from a very persistent friend of mine that Ruby Rails really speeds up development by doing most of the repetitive tasks for you - I dont know if Mono Rails is the same. I am very careful of frameworks but I will leave that till my next post.

 

Posted by jonno | 1 comment(s)

Code Comments - I brief history of stink!

This is one of the things that I find most humarous within IT. A lot of developers love to write comments - The argument goes that other people will come in later and need to understand what they have done so therefore through comments they explain their logic. This is funny because it effectively means that the code is unreadable.

What really impresses managers is if you tell them that the code was so complex. They love this as they think they now have some brilliant developers working for them - and then theres the line but dont worry I commented it extensively so that everyone can understand it ... this cracks me up!

XP'ers see comments as code smells. They have to be maintainted along with the code (duplication) and on top of it all you could spend all that time writing code that is more readable. Martin Fowler lists comments as a time to refactor.

We all hate commenting and theres a reason for this - its wrong - we just need to reconfigure our aproach to coding and we wont need too! The next time you write a comment think about why your doing it! How could you avoid writing the comment by improving your code. Its effectively meta-data about meta-data.

Posted by jonno | 11 comment(s)

IE 6 - Bug

This should be called alternative ways to access executables from IE6. 

Copy an exe file to your desktop and rename it to notepad.exe.
Open IE6
View > Source
And walla the executable magically opens up.
You can try it with a folder named notepad.exe too.

One has to wonder what the programmer who was writing this module was thinking.

Anyway besides that I have been using IE7 for about a month now and I only managed to find 2 significant bugs.

1. The history doesnt work properly - it only records history for current date.
2. Try open your old msn conversations and you will be greated by

Cannot view XML input using XSL style sheet. Please correct the error and then click the Refresh button, or try again later.


The system cannot locate the resource specified. Error processing resource 'file:///C:/Documents and Settings/jonathan/My D...

According to the IE7 team this browser is completly standards complient so it may be that MSN is not rendering a fully compatible XML or XSL sheet. Firefox does seem to have a problem opening it though - weird...

Otherwise its about time that IE got tabs!!!!!!

 

 



Posted by jonno | with no comments
More Posts Next page »