CruiseControl.NET Misadventures

Posted May 28, 2009 by Jerry Lin
Categories: CruiseControl.NET

Tags: , , ,

For the past week, I’ve been pretending to be a build engineer and trying to set up CruiseControl.NET to automate our builds. On previous teams, I’ve been fortunate to have a dedicated build engineer dedicated solely to this type of task, and after trying to set up CC.NET myself, I can honestly say I appreciate what they do – this entire process has been *NSFW* *NSFW*.

Case in point: CC.NET installs and sets up a web dashboard for teams to be able to look at the status of their builds from a browser. Ideally, it would work out of the box, but we know in reality that’s often not the case. Even after following the detailed instructions to set up the dashboard manually, I kept getting a Page Not Found error.

After pouring through the blogs and forums without luck, and nearly breaking down in tears, I remembered that the CC.NET server is supposed to generate the dashboard’s ASP.NET pages, and I chanced on this setting in IIS:

CCNet_Dashboard

After allowing ASP.NET extensions in IIS, the dashboard rendered correctly.

M-V-VM

Posted January 7, 2009 by Jerry Lin
Categories: WPF

Happy New Year! Hope 2009 is going well for everyone so far. Sorry for the lack of updates on the site. I was busy for the past few months preparing for Jing Pro’s release, but [unfortunately] most of my development was not WPF related.

Also, I have been learning Cocoa and iPhone development during my free time, and hope to blog about my experience migrating to Mac development in the coming weeks.

Now that I am somewhat familiar with Mac development, one aspect that I’ve really become endeared to is how Apple adheres to the MVC pattern – it’s really convinced me it’s a saner way to make stable, decently maintainable code. This prompted me to start thinking about how to follow MVC in WPF development.

Luckily I didn’t have to figure anything out. Karl Shifflett, one of the guys who makes Mole, has a series of posts on a variation of MVC called M-V-VM. M-V-VM stands for Model-View-ViewModel. From what I understand, like MVC, it is a clean way to separate the logic for the UI and your business/data models. The View would be represented by your XAML, the Model is still your data/business stuff. In place of the Controller is the ViewModel, which provides an abstraction of the Model. This is accomplished by exposing properties, implemented with IPropertyNotifyChanged, and commands that your XAML files bind to. The ViewModels then, become the main agents in manipulating your data models. I likes!

Theoretically, this virtually eliminates the need for code-behind logic, freeing UI designers to not have to write code, makes unit-testing because all the logic and behavior has been isolated from the XAML and rendering related objects. Another nice benefit is eliminating almost all value converters, since your XAML would bind directly to properties in the ViewModel. I would love to try this on my next project, but until then Karl has a nice diagram summarizing M-V-VM here:

http://karlshifflett.wordpress.com/2008/11/08/learning-wpf-m-v-vm/

Restarting a WPF app

Posted December 17, 2008 by Jerry Lin
Categories: WPF

Tags: ,

We recently needed a way to easily restart a running Jing process, for reasons that will become apparent in an upcoming release, to which I stumbled on this entry from one of Rob Reylea’s blogs:

http://rrelyea.spaces.live.com/Blog/cns!167AD7A5AB58D5FE!2258.entry

Essentially, you make these two calls to restart a running WPF process:

System.Windows.Forms.Application.Restart();

System.Windows.Application.Current.Shutdown();

Be careful though. After confirming with Reflector, calling Shutdown() is an asynchronous call, so it’s possible to have the new instance of your process running before the current one has terminated, so make sure your app has all your data saved/in a safe state before you make these calls.

Artifacting on Vista

Posted August 19, 2008 by Jerry Lin
Categories: WPF

Tags: , ,

Last week tech support kept telling us that Vista users were reporting really weird artifacts in the Launcher and our Preferences windows:

Since those two windows are layered windows, and layered windows have had performance problems in Vista until .NET 3.5 SP1, I wondered about it and stumbled on this MSDN article:

HKEY_CURRENT_USER\SOFTWARE\Microsoft\Avalon.Graphics\DisableHWAcceleration DWORD

The disable hardware acceleration option enables you to turn off hardware acceleration for debugging and test purposes. When you see rendering artifacts in an application, try turning off hardware acceleration. If the artifact disappears, the problem might be with your video driver.

The disable hardware acceleration option is a DWORD value that is either 0 or 1. A value of 1 disables hardware acceleration. A value of 0 enables hardware acceleration, provided the system meets hardware acceleration requirements; for more information, see

After spending some time convincing Tech Support to have the users try setting this registry key, forcing software rendering in WPF took care of the rendering problems. So we had the users update their graphics card drivers and hardware acceleration worked again.

So if you are not running on .NET 3.5 SP1 and see artifacts and rendering problems in layered windows on Vista, force software rendering to see if the issue might be caused by a bug in the graphics card’s driver.

Jing Listed on PC World’s Top 100 Products!

Posted May 27, 2008 by Jerry Lin
Categories: Uncategorized

Tags: ,

This morning, everyone on the Jing team was informed that it made PC World’s top 100 product list for 2008. Needless to say, we’re all excited! When we launched about a year ago, we felt that we were onto something by making it simple (and hopefully fun) to take and share screenshots and videos. Although we placed last on the list, it’s still a great feeling to know that there are people out there who feel the same way we do about this little program.

I know this sounds like an advertisement for Microsoft, but I truly feel that WPF enabled us to make Jing possible. Of course, programmatically taking screenshots is a simple bit-blit with some GDI function calls, but what I’m talking about is the overall user experience. From the sun splash screen that moves and animates to Jing’s docked position, to how the sun launcher reacts to the user’s mouse movement, it was WPF that allowed the team to try and create a program that would be not only useful, but fun. Not only that, but because WPF was built on top of .NET’s extensive APIs, it allowed us to be iterative, adapt to changing requirements, and encouraged us to be experimental with our UI designs. In other words, it let us be agile. Although we’ve stretched WPF’s capabilities, and there are some APIs that really should have a WPF equivalent (Screens *cough*cough*), I tremble thinking of how much more difficult development would be had we stuck with “good ol’” MFC/Win32.

Sun Launcher, made possible by WPF

Here’s hoping Microsoft keeps promoting and improving WPF, and that we’ll continue to take advantage of it here on the Jing team :-)

On Being AWOL

Posted May 6, 2008 by Jerry Lin
Categories: Uncategorized

Hi,

You may or may have noticed that this blog hasn’t been updated in a while. Unfortunately I haven’t been doing any development in WPF for the last two months. On the bright side, there’s some exciting stuff that we’re working on for Jing that we can hopefully show you in the next few months. Until then, thanks for your continued patience, and if things go smoothly, I’ll be writing articles for this blog on a regular basis again.

Jerry

Embedding PNGs into RTF files

Posted March 18, 2008 by Jerry Lin
Categories: Rich Text Format

Tags: , ,

Recently I had to implement drag and drop of PNG images in WPF so that if you dragged an image from a WPF app to a document in Word or Outlook, the PNG would be displayed as a part of it. As it turned out, MS Word and Outlook plays well with Rich Text Format, so I had to figure out how to embed a PNGs into an RTF stream.

The code for this wasn’t difficult, but finding out how to do it was an adventure. First, I found out the structure that the RTF had to be written as:

{\rtf1\ansi\deff0{\pict\pngblip\picwX\pichY

*The data for the PNG image converted into hex*

}}

The first line tells RTF parsers that we have a png embedded (the \pict\pnblip control words), with \picw and \pich describing the pixel width and height of the image (X and Y).

Following the that, you write the data representing the PNG file. However, you have to write the PNG in a way that RTF parsers understand. Specifically, you have to convert the binary values that represent the encoded PNG into hexadecimal characters. From looking at example files floating around on the web, I also grouped the hex into separate lines composed of 64 character chunks.

After that, I wrote the footer, }}. All of this was done encoding the final stream as ASCII, since RTF seems to understand that well. That’s it, I had a valid RTF stream that Word and Outlook could parse.

As a demonstration to help you get started, I’ve included a demo app, aptly named PngToRtfConverter. The app is a window asking you to select a PNG file to convert into an RTF file. I’ve also factored the actual conversion part into helper classes, but note that since this code was for learning/demonstration purposes, so it isn’t necessarily efficient nor is there extensive error checking.

This demo app was written in Visual Studio 2008:

PngToRtfConverter.zip

ListBox Grouping and Virtualization

Posted February 22, 2008 by Jerry Lin
Categories: WPF

Tags: , , , , ,

I would like to give a big “Thanks!” to Microsoft’s Ben Carter for providing me the high-level solution to this difficult problem, and making work over the past month a little bit less frustrating.

Update 3/3/2008: I have reworked my solution to prevent virtualization from not working when sorting the ListBox with the CollectionView sort descriptors. I apologize for any inconvenience this may have caused.

Previously, I discussed how turning on grouping in a ListBox would prevent a virtualizing panel from, well, performing virtualization or lazy-loading of UI elements. When you turn grouping on, your visual tree should look similar to:

groupingvisualtree.png

When you turn on grouping, you are silently adding a StackPanel to your window’s visual tree, which is the one that communicates with the parent ScrollViewer object. Also, note how the virtualizing WrapPanel is wrapped inside a GroupingItem instance. Fixing this requires you to write a custom panel for ListBox.GroupingStyle.

The idea is the panel you write for grouping (to replace the StackPanel) will communicate with the virtualizing panel that’s being used in ListBox.ItemsPanelTemplate. The inner panel should be able to query the outer panel for the viewport size on each layout pass so it knows which children it needs to realize/unrealize. Conversely, because the outer panel is the one controlling scrolling, it needs to call the appropriate methods in the inner panel any time its scroll offsets change.

However, the sequence of events in this can be tricky so I will explain at a high level how I implemented this (hack) fix. Since I did this under company time, I cannot share my source code with you. Sorry.

Assumptions

You have implemented a virtualizing panel and want it to work with ListBox grouping.

The panel I wrote for grouping mimics a vertically oriented StackPanel, but you should write one to suit your needs (if you have VS 2008, you can look at Microsoft’s panel source code to make things easier).

WTF Moment: Object Lifetime Events

Posted February 19, 2008 by Jerry Lin
Categories: WPF

Tags: ,

I was reading the MSDN docs for Object Lifetime Events (click and see highlighted portion):

object-lifetime-events.png

Blindly believing this because having OnInitialized act as a bubbling event makes sense, I override OnInitialized for two panels, one nested inside the other. This was so that the two could communicate with each other by having the outer panel set some properties in the inner. Noticing some properties weren’t being set in the nested panel, I set break points in the debugger and it turns out OnInitialized is NOT bubbling, but appears as tunneling.

Am I smoking crack, or is there something going on in these Object Lifetime Events that I’m not aware of?

Making a Virtualizing WrapPanel

Posted February 6, 2008 by Jerry Lin
Categories: WPF

Tags: , , , ,

If you use Jing, you may have noticed that loading times for the History bin can be really long. As discussed in this post, we’ve already implemented some techniques to improve this, except for one: implementing a virtualizing panel.

In response, I’ve spent the last two months implementing one to significantly cut down on loading times. To be blunt, I can’t say it was an enjoyable experience – it was rather frustrating. Although Dan Crevier has a series of posts on implementing a virtualizing panel, his example is not ready to be used in production.

In this post, I will discuss how I made a virtualizing WrapPanel at a high level, and hopefully make the process a little bit easier.

Disclaimers

Since I wrote my virtualizing WrapPanel under company time, I cannot list its source code as I would be violating my NDA with TechSmith.

Also, I am assuming you already know what the purpose of virtualizing panels are, and have read Dan Crevier’s tutorial on how to write one since I use many of the terms that he does.