Archive for the 'cocoa' Category

06th Apr 2007

Report-an-Apple-Bug Friday! 1

My first! I’m so excited.

Title: NSCalendarDate’s descriptionWithCalendarFormat method doesn’t work properly
Product: Mac OS X
Version: 10.4.9
Classification: Other Bug
Is it Reproducible?: Always

Summary:
When using NSCalendarDate’s descriptionWithCalendarFormat method, incorrect values are returned.

Steps to Reproduce:
1. Create a Cocoa app. Use the following code it in:

NSCalendarDate *time = [NSCalendarDate calendarDate];

NSString *timeOfDay = [time descriptionWithCalendarFormat:@”%X”];
NSString *dayName = [time descriptionWithCalendarFormat:@”%A”];

NSLog(@”Today is %@, and the time is %@.”, dayName, timeOfDay”);

Expected Results:
The app should print “Today is Friday, and the time is 11:02 PM.” (Assuming it actually is Friday at 11:02PM, and those your time formats are the same.)

Actual Results:
The app prints “Today is Friday, and the time is 23:02:23 Canada/Eastern.”, which is not how the time should look according to the documentation for %X. If you use descriptionWithCalendarFormat:@”%X” locale:[[NSUserDefaults standardUserDefaults] dictionaryRepresentation], the output is not much better: “Today is Friday, and the time is Friday, April 6, 2007 11:08:51 PM Canada/Eastern”.

The dates and times programming guide states that %X should return “time using the time representation for the locale”. This is obviously not happening.

Regression:
Always occurs. Other regressions unknown.

Notes:
No Known work arounds, other than specifying the time format explicitly (@”%1I:%M %p”) which is ugly and doesn’t take into account localized formats.

Posted by Posted by patrick under Filed under AppleBugFriday, apple, cocoa, code Comments No Comments »

31st Mar 2007

Adium Time Zone Plugin 1.0 is Out!

Good news: The Adium Time Zone Plugin is now out. I hoped to have it out by the end of the week, and (I think) I squashed the last two bugs that were preventing me from releasing, so off it goes! I made a page for it that I will keep updated with the latest version and other news. The BSD licensed source code is also there if you want to check it out.

I’m proud of the code. I’m not super proud of the model, in fact I’m sure it will become something that I will look back on one day and say “What the hell was I thinking?!”. I’ll probably refactor it in the future, it’s just that I’ve held off on releasing this for long enough, and with my finals looming I was scared that If I didn’t release by my self-imposed deadline of this week then I wouldn’t have time to work on it again in a while.

I hope you like it. I hope it doesn’t sink your Adium. Please send me some feedback if it does (or if it doesn’t). Thanks!

Posted by Posted by patrick under Filed under adium, cocoa, code, open-source, universalbinary Comments 6 Comments »

23rd Mar 2007

Unit Testing Adium (Part 2)

Last time I wrote about unit testing Adium, I was actually writing about unit testing Adium.framework - The public API that plugin developers and the like can use to tie into Adium. After talking with David Smith from Adium about some of my other SoC Ideas (such as improving plugin support) I realized that Adium’s API really shouldn’t be considered stable, and that using it as a starting point for unit testing is a bad idea.

That being said, I switched gears and started again, this time unit testing the application itself as oppose to the framework. In hindsight I guess I probably should have started here first, but being familiar with Adium.framework from my plugin development, I assumed that would come more quickly. Wrongo.

Anyways, thanks again to Chris Hanson, his short tutorial on getting unit testing up and running in cocoa apps helped me get started, and everything is now working as expected. When you build the test bundle, it launches the Adium build, executes it’s tests, quits, and reports any failures. Good stuff.

Here’s a bit of what my AIEmoticonPack unit test looks like:

- (void)setUp
{
	fileManager = [NSFileManager defaultManager];
	//NSLog(@"Current Directory is %@/", [fileManager currentDirectoryPath]);

	emoticonPack = [AIEmoticonPack emoticonPackFromPath:[[fileManager currentDirectoryPath] stringByAppendingString:EMOTICONSET_PATH1]];
	//NSLog(@"Testing Emoticon Pack: %@", emoticonPack);

	NSArray *fooarray = [emoticonPack emoticons];
	//NSLog(@"Foo: %@", fooarray);
}

- (void)tearDown
{
	// No necessary tear down.
}

- (void)testPath
{
	NSString *expectedPath = [[fileManager currentDirectoryPath] stringByAppendingString:EMOTICONSET_PATH1];

	STAssertEqualObjects(expectedPath, [emoticonPack path], @"Path wasn't right, should have been %@ but was %@", expectedPath, [emoticonPack path]);
}

- (void)testName
{
	NSString *expectedName = [[[NSString stringWithString:EMOTICONSET_PATH1] lastPathComponent] stringByDeletingPathExtension];

	STAssertEqualObjects(expectedName, [emoticonPack name], @"Name wasn't right, should have been %@ but was %@", expectedName, [emoticonPack name]);
}

- (void)testEnabled
{
	[emoticonPack setIsEnabled:YES];
	STAssertTrue([emoticonPack isEnabled], @"Emoticon Pack isn't enabled by default");
	[emoticonPack setIsEnabled:NO];
	STAssertFalse([emoticonPack isEnabled], @"Emoticon Pack is enabled when it shouldn't be");
	[emoticonPack setIsEnabled:YES];
	STAssertTrue([emoticonPack isEnabled], @"Emoticon Pack isn't enabled when it shouldn't be");
}

Hmm. I really need to write my own wordpress theme.

Adium devs look out, incoming SoC application! :)

Posted by Posted by patrick under Filed under Summerofcode, adium, cocoa, code, open-source, unittesting Comments No Comments »

01st Mar 2007

How-to: Create an Adium Plugin

Creating a Plugin for Adium is actually really easy. Here’s a quick guide through the proper set up to help get you started. There is even a skeleton project at the end.

  1. Create a new Xcode project, choose Bundle -> Cocoa Bundle.
  2. Add the following frameworks to your project:
    • Adium.framework
    • AIUtilities.framework
    • FriBidi.framework

    These are necessary if you plan on using or changing any part of Adium, which you will likely be doing.

  3. Create your main class. It should be named something like ABMyTestPlugin. Your class should inherit from AIPlugin, found in Adium/AIPlugin. So you will need to import that.
  4. Override the -installPlugin and (if necessary) -uninstallPlugin methods. The meat of your code goes there.
  5. Override -pluginAuthor, -pluginVersion, -pluginDescription, and -pluginURL as well, to all return appropriate NSStrings. This isn’t required, but is good practice, so do it anyways.
  6. Get info on the build target (your bundle). Change the build settings to add the following:
    • Other Linker Flags: -undefined dynamic_lookup
    • Wrapper Extension: AdiumPlugin

    Also, under the Properties tab change the Creator to “AdiM” and the set the Principal class to the name of your main class (ABMyTestPlugin).

  7. Build your bundle, drag and drop it onto the Adium icon and test it out.

That’s pretty much all there is to it. More information on what you can do once you hook into adium can be found at the Map of Adium. It’s not really complete, but if you poke around inside the Adium.framework headers you will find that most of the methods are “self-documenting” and not to difficult to figure out. I’d also suggest looking at some existing plugins, like my Time Zone Plugin and the ones included within Adium itself.

If you’d like a skeleton of the Xcode project, grab it right here: AdiumTestPlugin.zip

You might want to also grab the Adium Source and compile your own frameworks since the ones included may be out of date.

Update: luapffuh pointed me to Toby’s guide to creating an Adium Plugin. Although mostly the same, his has bit more detail and is definitely worth checking out.

Posted by Posted by patrick under Filed under adium, cocoa, code, how-to, open-source Comments 3 Comments »

23rd Feb 2007

Adium Time Zone Plug-in Preview

UPDATE: This is now out of date! Get the latest version by clicking on the Adium Time Zone Plugin page in the sidebar.

Today I’m announcing the preview release of my Adium Time Zone Plug-in. This plug-in adds functionality to Adium by letting you set time zones for each individual contact. Once set, you can view the local time of the contact in their tooltip.

It looks something like this:

It’s a preview release because I’m interested in soliciting feedback as to it’s implementation before I make it totally public and tell all my friends to download it. Please try it out and let me know what you think and how it can be improved.

Note of interest:

  • The city names are all taken from Apple’s NSTimeZone class. I assume I could add more, but it might be hectic/ugly to manage two separate lists; a real one and one that just maps it’s contents to the real one.
  • I tried to follow the implementation of ESAuthorizationWindowController, if you were wondering why I did some of the things I did in the controller class.
  • I plan on writing out a How-to on writing your own Adium plug-ins soon, so watch for that.

The plug-in can be downloaded here: Adium Time Zone Plug-in

The source (GPL Licensed) can be downloaded here: Adium Time Zone Plug-in Source

Enjoy and please let me know what you think!

Posted by Posted by patrick under Filed under adium, cocoa, code, open-source, universalbinary Comments 2 Comments »