Wednesday, December 30, 2009

wheniwas19 Year in Review

2009 has been one strange year.

January. Organic, where I was working as their Manager of Integrated Media, moved me from Creative to Technology. Like the Dude, I abide.

July.I was hired at henderson bas as their Director of New Media. Five weeks later, I quit and went freelance. A bad fit is a bad fit and I was a bad fit at henderson bas.

September. I spoke at Flash on the Beach in Brighton. I outlined what I considered the 10 Best Excuses to NOT do Amazing Work. I then went on to do the same presentation for Sheridan College, Seneca College and a mini-version for the monthly FlashinTO gathering.

December. I worked on a little thing for Galaxy Goo.

From July until now, I was/am working on Tattoocapture. As of this moment, it's still in progress.

My first freelance project went live. Very Exciting.

The Estée Lauder site I worked on with many others in 2008, won some awards this year.

I'm looking forward to 2010. If 2009 is any indication, I'm in for some fun. I like working. If you have some work for me, get in touch!

Labels: ,

Thursday, December 17, 2009

TattooCapture Update



Here's the skinny on TattooCapture. I called myself out at Flash on the Beach, then Sheridan College, a FlashinTO user group meeting and finally Seneca College, for being a procrastinating chump (see my presentation 10 Best Excuses to NOT do Amazing Work)

Currently the site is still incomplete. I've spent quite a bit of time on it and have stricken plenty of items off my to do list but there are many many more items remaining.


image scaled roughly 50%

As you can see in the screengrab above I have a lot done. The design of the site is rough and will remain so until I can convince one of the many talented designers I know to make it pretty. But as Chris Pelsor has said "Get version 1 done and worry about the rest after".

What's working;
    Age verification
    Registration and account creation
    Login
    Account update (for facebook, twitter, etc)
    Avatar creation (using a webcam or uploaded image)
    Gallery creation
    Image creation (using a webcam or uploaded image)
    Adding images to a gallery
    Viewing galleries
    Viewing images
    A development notes window
    An instructions window


What isn't working (yet);
    Viewing updated user info
    Viewing specific users
    Search in any form
    The actual mechanism for a tattoocapture (take one image, put it on another, save)
    Add friend functionality
    Verify friend functionality
    Send in-site messages
    Ratings on images
    And much, much, sigh, much more


Anyway, I know the amount of egg on the face one wears when they commit to specific launch dates and can't make it. I'm relatively embarassed, but considering what's been accomplished so far, I can safely say I've done a lot.

Never fear, this is not the end. It's simply an update so you all know I didn't just stop. I'm really excited with the progress. If you want to play with the site as is, send me an email

Labels: , , ,

Wednesday, December 16, 2009

2010 Subaru Legacy

Firstly, I have to thank Tribal DDB Toronto for the opportunity to work on this project. Their timely assignment firmly planted me in my new freelance role.


Welcome to the 2010 Subaru Legacy

This project had some challenges. Not the least of which was the fact that when I was pitched it, the art director (the effervescent Missy Kelley) involved said they wanted PaperVision 3D. Although I took a workshop on PV3D with the inimitable John Grden, I can honestly say I still know next to nothing about how to implement this powerful class set. It's embarrassing to admit but I'll live.

At any rate, here comes the fun part; all the cool stuff I put to use. Either new to me or a finessing of things I already know.


Starting the audio experience

1. Audio triggering. I used flv video (f4v, actually) for the audio. The audio is in binaural format. Meaning if you happen to be wearing headphones, the audio will wrap your head in true surround sound. It's wicked cool. They want the image sets to appear based off timing in the audio. eg. the narrator is talking about the radio, the radio image ought to be front and center and the set that image is in ought to be the focus. To accomplish this, I used XML and a type of closed captioning. When using closed captioning, you can either set an event within the audio export or you can use XML with timecodes in it and look for these. I opted for the latter. A. because I couldn't be sure the audio wasn't going to change and I didn't want to have to input all the new events in the audio. B. because I'm really familiar with XML.


No PaperVision 3D? No problem. Sort of.

2. Fake 3D. Since I didn't know PV3D, I could use the 2.5D implemented in Flash 10 to allow for skewing and perspective. Therefore, when placing the images in their sets, I'd use a center point (locally, the 0,0 of the set) and randomly place the images around that point. Their distance from the center dictated the amount of perspective they would have. When that image becomes focused it swaps it's perspective on the vertical axis. It's a fairly good effect and easily set up.


Highlighting a feature.

3. Call outs. Now, having worked with auto minisites for pretty much my entire career, I know the four pinnacles of the industry; power, performance, comfort, safety. It never changes. Call it what you will, but those things are paramount. I think you can probably add cost in there now, but whatev. I used the image sets and XML to control callouts. If the callout existed (in the XML of an image) it popped open when that image was the focus.

4. swfObject loading issues. I blogged about this. Suffice it to say, thanks to Chris Pelsor and Stacey Mulcahy, this got sorted out.


Soundboard with downloadable MP3s

5. Downloading of files. There is a soundboard in this piece and the request to be able to download the MP3s came from on high. I'd never done that before, but it was fun to make happen.


En francais, s'il vous plait.

6. Localization. The request from a Canadian client was of course that this needed to be in french and english. I wanted to be able to easily access this portion by simply swapping a variable. eg. ?lang=fr (see french in action)

So that's Subaru Legacy in a nutshell. I'm pretty proud of this piece. Thanks again to the crew at Tribal DDB Toronto for the opportunity!


That's all she wrote

Labels: , , ,

Wednesday, December 09, 2009

The Hype Over Hype

I attended Joshua Davis' Hype Workshop last month at the RMI space in Toronto.

I had a hard time figuring applicability in my daily work life.

So I sat on Hype, undecided what I could do with it. What I missed in Josh's workshop was the fact that Hype is simply a collection of classes. Use what you want and ignore what you don't. Hopefully, I'm not the only one with that misconception. If I am, I'm dumber than I thought.

Yesterday I had some downtime as I wait on my friend to get to .NET changes for TattooCapture and decided to manufacture something I've always wanted: A class to plot points equally around 360°. Why? Well... that will become clear in the future. In the meantime, that was my goal. Feed it 8 points and it comes back with how many degrees each would be to be equally dispersed around a circle.

It was a pretty simple solution; divide the number of elements by 360. Tada! Then use that degree number within the class to return what degree an element would be. Further, use it to return what radian (what flash uses to calculate degrees) that element would be.

I ended up with the Orbit class right-click and 'save as'. Usage boils down to importing the class and an instantiation. Then using it's public functions. Therefore;

import com.orbit.Orbit;

var orbit:Orbit = new Orbit;
orbit.increment = 15; //15 being the total number of elements
var degree:Number = orbit.getDegree(8); //8 being the 8th element
var radian:Number = orbit.getRadians(degree);
//returns the radian value for the 8th element out of 15;

//alternatively, you can piggyback the calculations
var radian:Number = orbit.getRadians(orbit.getDegree(8));


So yeah.

Here's the first example. Each time you click the start button, the piece will pick a random number of elements, then run through that number and each element on stage in it's prescribed location. Sweet.

So once I figured that out, I started monkeying around with it, as is my wont. Change the number to see the progress.

In comes Hype.

Eventually, in version 4, I decided to muck about a bit with Hype. I wanted to draw to Bitmap was being done and with Hype, I had a built-in class to do just that. BitmapCanvas. Worked like a charm.

Messed around for another couple of versions and in version 8, added in FilterRhythm and TimeType. So far so good.

In version 10, I added in colorPool. Honestly, it all starts to get a bit silly and really I'm just messing around with minor alterations.

In version 13, I dumped my Event.ENTER_FRAME for SimpleRhythm.

Finally, with some more tweaks, I have this (basically) where I want it. Version 19. I might spend some more time with it, but it's in a place I like. I left it running while I wrote this post and this is what I got.


click the image to see it full-size

The moral of the story is; If you keep your eyes closed, you won't see the path in front of you. How's that for a fortune cookie? I oughta be a writer.

Labels: , ,

Friday, October 02, 2009

swfobject, IE7 and flash can get along.

Yesterday I got a panicked email from my client with a bug from their client. This sort of tertiary contact is part and parcel of being freelance.

The email contained a bug in my latest project. The bug was;

This is the exact error in IE7. I’m running Flash 10,0,2,54 Debug.

TypeError: Error #1009: Cannot access a property or method of a null object reference.
at com.utils::MainImporter()
at subaruLegacy/checkFlashVars()
at projectClass()


I love Flash errors. No, I really do. The fact that I can instantly look at this and know precisely where the problem lies is amazing. checkFlashVars is the function I use nearly instantly at instantiation of the entire project to grab the provided variables from swfobject. ie. project language "en" or "fr", location of the xml content, locations of external links. I didn't want to need to update this project after delivery so i externalized quite a bit of it for editing outside of flash. Always a good plan.

So back to the bug. What happened is swfobject isn't passing the flashVars to flash in time. The likeliest reason is the page isn't loading completely in time for swfobject to know precisely what it's sending. I didn't know this at the time, but I obviously knew something was amiss.

In comes Twitter.
wtf is with fp10 and IE7? they not friends? got an email from the client and they're freaking out.

You want to be concise? Use Twitter.

Nearly instantly, my good friend Chris Pelsor IM's me and says "We had the exact same problem, hold on." After over an hour of him cleaning up my html, asking Stacey Mulcahy to join in on the fun, having her ask "Is your code smart enough to know when it's failed?" and "What version of swfobject are you using? 2.1? Update, Hugh." and the both of them testing, Chris found the project where they figured out the solution. I don't want anyone else googling "IE7 flash player 10 not working" like I did initially. So here is the solution.



Obviously, you'll need a div called "content" or whatever you are determined to name it.

I had to admit a couple of things to two people in who's opinion I respect;
1. I know very little about html. I look stuff up, I copy, I paste.
2. I know even less about css. Copy, paste.
3. No, I don't know why there are three different methods of commenting in the html. Copy, paste.
4. I agree, I should learn. I've written it in my agenda.

Labels: , , ,

Friday, September 18, 2009

Estée Lauder win

Update September 25 Turns out Estée won in the "Beauty and Cosmetics" category at the OMMA Awards a few days ago! This thing is a monster.

I've found out the site I worked on, Estée Lauder, has won;

two WebAward awards (Outstanding Website, Best Fashion Website)
one Internet Advertising Award (Outstanding Achievement In Internet Advertising)

It's also an entry at Cannes! (Cosmetics, Beauty & Toiletries)

More after the jump;


Managing a team of five Flash developers and co-ordinating remotely with the New York office was a true test of my managerial abilities. The site went down to the wire, but in all, I was really pleased with the efforts of my team. Todd Fraser and Stephan Tanguay, especially.

Not to mention, it was my very first AS3 project. I've learned a ton since then in implementing AS3, but I cut my teeth with this project. My favourite self-built classes, TextFormatter and MainImporter were first coded for Estée Lauder. I owe Organic, a debt of thanks for being able to work on this project.

My focus, beyond management, was the Skin Care Diagnostic Tool




Honestly, what better way to start the day than to find out work you've done won awards?

In case I forget, FOTB, here I come!

Labels: , , , , ,

Thursday, September 03, 2009

Life/Career Update

Yesterday I quit as Director of Rich Media for henderson bas. There were a number of suprised comments that I wasn't there very long, 5 weeks. Sometimes you can recognize a bad fit in a short period of time. As I did. Better to end it than to drag it out.

On that note, I've rejoined the world of freelance! Although I'm apprehensive about a leap of this kind, I am also excited about the new possibilities. I've already found my first gig and looking forward to this chapter in my life.

If you have anything flash-related, big or small, send me an email. I'd be more than happy to do the work.

Labels: ,

Wednesday, September 02, 2009

Facts about Fees

I forgot to blog about the re-release of Fee & Processes on Bank of America. Now known as Facts about Fees.



This had several fun challenges. The flash was loaded and reloaded by the html wrapper every time the user changed sections, so I made extensive use of the SharedObject to store visits. This way, the user gets a different experience from the video on the first visit and subsequent visits. Quite fun.

There were some alterations to my base once I left Organic, but it's still functioning and I'm quite pleased with the site on the whole. Take note of the Asked & Answered windows with their cross-linking and the control you have over the video, muting, volume, etc.




Plus, I incorporated pre-existing AS2 demos from the original site and brand new demos from the InfoCenter engine. This piece is rife with yummy hugh goodness.

Labels: , ,

Thursday, August 20, 2009

FoTB 30 days away!

Things are really motoring. I've moved http://tattoocapture.com over to my friend John Breton's server. John is a .NET guy and knows his junk, lemmetellya.

I have never done so much using webservices. Registration, login, updating, uploading, friending, messages, world locations, etc, etc. I have exclusively been using Carlo Alducente's WebService class. It's been invaluable and I don't know where I'd be without it.

Soon enough I'll be making use of Senocular's Transform Tool.

Interested in being a beta-tester (or as I like to call it, Better Tester)? send me an email. I hope to be ready for full-scale testing in about a week. Many hands make light work, as they say. Many eyes make amazing work, I say.

The end goal for this is to be finished by Flash on the Beach where I am presenting my session The 10 Best Excuses to NOT do Amazing Work. I hope to see you there! I did say I would light a monkey on fire to compete with Quasimondo's presentation happening at the same time as mine.

I've been updates about TattooCapture.com development on Twitter : tattoocapture

Labels: , , , , ,

Wednesday, August 05, 2009

News wheniwas19 styles

It's been over a month since my last post. Things are afoot, as they sometimes are.

  • I've left Organic to take the position of Director of Rich Media with henderson bas. Todd Fraser, a Senior Flash Developer at Organic came with me. Very cool.

  • I've joined the cool kids and started a Twitter account

  • I'm working on the site I've been talking about for the last almost 3 years. I've mentioned it a few times. I renamed the site TattooCapture.com because Camgasm might seem funny, it's just not appropriate. Follow the development over Twitter

  • Not coincidentally, I am working on my presentation for FlashontheBeach in conjunction with building the site. "What? A presentation on how to get your work done, and you're doing work?", you ask. "Yeah, it's silly, but true.", I answer.


  • I am super happy to have a friends like John Breton. He has been instrumental in being my go to .NET and DB guy. Without him, I'd likely still be sitting around moping about how I can't make TattooCapture.com Also, I lucked out that Jason Munger will be doing some tattoo designs for me. He's a super-talented guy and I'm lucky to count him as a friend.

    Many thanks, John and Jason.

    Suffice it to say, there have been a lot of late nights and new challenges. I'm going to be looking for beta-testers sooner than later. If trying out something new appeals to you, let me know.

    Labels: , , , ,

    Friday, July 03, 2009

    Flash on the Beach Brighton '09

    I've blogged a couple of times about speaking at Flash on the Beach Brighton in September.

    Finally I took the time to fill out my session description.

    I've titled it The Ten Best Excuses to NOT do Amazing Work. Have you ever had an idea but found yourself unable to get started? Or, once you've started, unable to work on it? Or, once you're working unable to finish?

    There are ways to get past these little stumbling blocks before they become huge hurdles. I have run into these roadblocks from hurdles from stumbling blocks. I look at these situations with suspicion and wonder how much is self-manufactured and how much is legitimately stopping me from getting my work done.

    Honestly, this title could end with just "work" as opposed to "amazing work".

    Tickets are going fast!

    Labels: , , ,

    Sunday, May 24, 2009

    FlashontheBeach

    I am so excited about speaking at Flash on the Beach (or FoTB, depending on your interest in acronyms) Brighton.

    Get your tickets here.

    Suffice it to say, this is a must attend conference.

    Besides that, it appears there's a contest for a giveaway pass to the conference.



    To quote
    Put an FOTB09 badge on your site, link it to us, then fire us an email at badges@flashonthebeach.com to let us know the URL and we'll enter you in a draw for a full 3 day pass!

    Now that's a good deal.

    Labels: , ,

    Tuesday, February 24, 2009

    Keyboard Events

    There was a comment by Muaad for help on how to capture Keyboard Events in AS 3.0. I figured instead of filling up a comment box I'd just go ahead and do a little post on it.

    Keyboard Events and capturing them has been around for a long time. I'm going to assume Flash 4 days since I'd built a little animated typer in Flash 4 and can't recall doing it Flash 3.

    Like everything else in AS 3.0, you need to import the appropriate class(es);

    For capturing Keyboard Events, you'll need;

    import flash.events.KeyboardEvent;
    Add an eventListener to the stage for whatever you want to capture KEY_DOWN, KEY_UP, etc etc.
    stage.addEventListener(KeyboardEvent.KEY_DOWN,checkKey);

    List of Key Codes on Adobe

    Source files


    There you go, Muaad.

    Labels: ,

    Thursday, January 15, 2009

    RIP Flash on the Beach Miami '09

    It's a sad day to discover that due to the current economic climate, John Davey has canceled the upcoming Flash on the Beach Miami event.

    Everyone I know that was speaking, myself included, are thoroughly bummed out. John and his people have consistently put on a great event. Miami would have been John's first foray into North America and we all were excited at the prospect.

    Nothing but love, John.

    Labels: , , ,

    Monday, January 12, 2009

    Flash on the Beach Miami '09



    Very cool. John Davey is offering a once in a lifetime opportunity for $99 tickets to FoTB Miami ending Wednesday, January 14!

    Lee Brimelow explains the whole thing here!

    If you don't need to know anything beyond; "99 BUCKS!!!?!?!?! ENDS WEDNESDAY?!?!!?". The discount code is RSKNUTS1.

    Here's where you get the tickets.

    Labels: , , ,

    Tuesday, January 06, 2009

    Aspect Ratio

    I've been working on a little something and wanted to maintain a 16:9 aspect ratio no matter what size the browser window was.

    Essentially, the calculation is this;
    multiplier = 16/9 = 1.7777778

    In my test, I used the multiplier on the stageHeight and stageWidth to find out

    private function maintainAspectRatio(event:Event):void
    {
       width16x9 = stage.stageHeight*multiplier16x9
       height16x9 = stage.stageWidth/multiplier16x9
       if(width16x9 < stage.stageWidth){
          height16x9 = width16x9/multiplier16x9;
       }else{
          width16x9 = height16x9*multiplier16x9;
       }
    }


    So using an EventListener on the stage I can monitor the current stage size.

    stage.addEventListener(Event.RESIZE, maintainAspectRatio);

    And there you go.

    Here's the test.

    Labels: , ,

    Tuesday, December 23, 2008

    Seasons' Greetings from wheniwas19!

    While planning our little trip to see family for Christmas, I thought about a little something something to have for anyone who reads this blog.

    Because the build is randomly generated, it takes a while to get to something coherent, so here's a screenshot.

    *Edit*
    Thanks to a few phrases from my father-in-law, I had to crack this open to make some changes;
    1. There's an initial navigation to choose the animated build over just splashing the page randomly with specific numbers of iterations.
    2. You can go back and start over.
    3. I used setTint instead of Greensock's TweenLite to save on processor cycle(s).

    Thanks, John. I hate thinking I haven't done enough. Mind you, there are a few more things I'd like to do but I might save that for another project.




    If you do have time on your hands and want to see it in action, click here.

    So, Merry Christmas and Happy New Years.

    *Edit*
    I noticed some weirdness with this thing. Like when it finished it's loop, it would remove the last item(s) and not add them to the Bitmap Object. Looked into it and discovered I ignore the last set of items and just snapshot the ones before them. Fixed that.

    Just to explain what's going on under the hood;
    Step 1. place an MC on the stage. In this case, MERRY *LOGO* CHRISTMAS. Change it's visibility to false
    Step 2. randomly locate a pixel on the stage and sample the color of that pixel.
    Step 3. place a random MC on the stage at that location and tint it to the color of the pixel.
    Step 4. after 10 iterations, draw those clips to a bitmap and remove them (the clips). Increment a second iteration counter.
    Step 5. after 10 iteration on the second counter, draw the bitmaps to an overall bitmap and trash them (the bitmaps)
    Step 6. rinse and repeat.

    Labels: ,

    Tuesday, December 16, 2008

    Creative, Technology and Flash

    If you're not familiar with the standard agency model, you won't know that Flash development falls under either of the two silos of development; Creative and Technology (sometimes referred to as Engineering).

    Now that you are familiar, understand something, I have been in either of those two silos for the entirety of my professional career. Even when I had my own corporation, I was titled "Technical Director" and my partner "Creative Director".

    Why do we not recognize Flash as a separate entity? It's been around for over ten years. With the addition of widespread broadband, it's more prevalent than ever before. It has effectively knocked out all competitors in the online motion graphics realm. We have entire companies now that specialize in only flash dev and are contracting themselves out to agencies to execute their work.

    It's my opinion, such as it is, that agencies need to revisit their office model and alter their thinking. Flash Developers and Designers have been honing their craft since the invention of the software. There need to be advocates for the craft at agencies, not developers speaking to Creative Directors or Technical Directors, giving their opinions. A new person at the agency table is needed.

    An equal voice in the form of a Flash department. Equal to Technology, equal to Creative.

    It's long overdue.

    Labels: , ,

    Friday, December 12, 2008

    The Art of John Wall

    Announcing the launch of The Art of John Wall.

    Sometime in May, a friend of mine contacted me asking if I'd be willing to work on his site. "No rush," he said.

    Now unfortunately, I don't do well with no timelines. So when he followed in June and July with "How's it going, man?" I would respond with, "Ah, crap. Sorry."

    It's not intentional, I just need a deadline to motivate me. So when he called in August and I prepared to apologize once again for not working on his site, he asked, "No, no, I was wondering if you might want to work on a second site?"

    Usually when I've screwed the pooch for so long, a client would be inclined to fire me. Not this guy. To his credit, I think he got it. "This one has to be live by the end of November."

    Sweet mother of pearl. A deadline?!?

    I was given a lot of creative license with this site, so I packed it full of things I've wanted to try in AS3 but couldn't seem to talk Organic into trying;

    Full-window, liquid layout.
    A self-centering content box.
    All content in one spot. Text, images, doesn't matter. One GD spot.
    Navigation that goes away when it isn't needed. Fewer items on the screen, less clutter.



    Yes, in essence it's just another portfolio site. And yes, the concept of next previous buttons in an image isn't new, but it's a good idea, so why not do it?

    I'm just glad to have been given the opportunity to build something for someone so talented.

    Labels: , ,

    Wednesday, December 03, 2008

    Did You Attend FiTC TO 08?

    Did you attend my session OOP for the OOPless at FiTC TO 08?

    If you did, I'd like to hear your take on it. I've allowed anonymous posting to my blog because I'd like as much feedback as I can possibly get.

    Here's the post I put up shortly after my presentation.

    Thanks in advance. Good or bad, I need to hear it.

    *Edit I neglected to repeat the navigation instructions for the presentation. Apologies.

    Navigation is as follows:
    S (s) - show slide navigation
    H (h) - hide slide navigation
    if slide navigation is opened, you can click on individual slides to jump to a slide.
    right arrow key - next slide
    left arrow key - previous slide
    down arrow key - progress through slide

    Labels: , ,

    Tuesday, December 02, 2008

    Using External Libraries with Flash and Flex

    Over the past couple of years, I've really been trying to embrace my inner OOP-ness. There's been figuring things out slowly but surely and my latest wish was to externalize my libraries from my project(s).

    I have a few classes here and there that it would be simpler if they were in one spot. Theoretically, if I make an update to one class it's universally updated across the board. I might need to go into older projects and add an argument here or there if that project needs an update itself, but my classes would never need to move.

    Deciding where I'd like these classes to reside is a stressful thing. Forever is a long time, after all. I've been using Flex for almost a year now and I don't know why I was so reluctant to use it. Probably because I heard so many people saying "Oh, you HAVE to use Flex. You HAVE to." I alway get all obstinate when someone tells me I must do something. I'm crotchety. I tried Flex, and I never looked back.

    Anyway, here are the steps. I am sure they're outlined efficiently elsewhere, but since it's new to me, it must be new to someone else and I want to save them the effort of looking. As a caveat, I never say this is THE WAY to do things. This is MY WAY to do things.

    step 1. create a new project in Flex. Do whatever you do, name it whatever you name it, put it wherever you put it. Don't hit Finish yet.



    step 2. hit Next. Notice the Source Path tab with a big window underneath it? To the right of the window is an Add Folder… button. Click Add Folder… and find your code folder. When you click OK, that library will be added to your project.





    step 3. Hit Finish.



    Your project will be set up by flex. You'll see your project folder and inside it is [source path] yourLibrary. In my case, it's com

    That's not all though. There is a little housecleaning in Flex I find I still need to do. Right-click on your project and choose Properties.



    In ActionScript Compiler, deselect Copy non-embedded files to output folder and Generate HTML wrapper file BTW, this is a personal choice. I don't like them, so I dump them. It's up to you.



    Finally, create a new Flash file and save it to your new src folder. Now we move to;

    step 4. Open the Properties panel and under Document Class: enter in the main class. In my case, this is "Temporary_Project".



    step 5. Now, under Settings in the Properties panel, click the Formats tab and change the output location of your swf to ../bin/fileName.swf fileName being the name of your file.



    step 6. This is the big final set of steps that made the difference between Flash finding my class files and not. Under Flash, choose Preferences….



    step 7. In Categories, choose ActionScript. Click ActionScript 3.0 Settings….



    step 8. Click the bullseye and locate your code folder. Once you choose it, the path to your folder will appear in your ClassPath: window.




    And that's it. Flex will auto-complete your paths as normal, the classes will be available to your project and Flash will know where your classes are. It's a lot of screenshots, I know, but I spent 5 minutes trying to figure this out and was flummoxed at the very end when I neglected to add the Classpath to Flash.

    Hope this helps.

    Labels: , ,

    Friday, November 07, 2008

    Text Selection Discovery

    I was wracking my brain on and off for about a week trying to get a field to select all the text in it when it achieves focus. This happens automatically when you tab to it, but when you click in it, it sets the caret wherever you're clicked.

    Initially I was convinced that FocusEvent.FOCUS_IN should do the trick. In fact, I'm still convinced it is, but it doesn't work.

    var tmp:TextField = new TextField();
    tmp.addEventListener(FocusEvent.FOCUS_IN,focusText);
    tmp.htmlText = "test text";
    tmp.autoSize = "left";
    tmp.selectable = true;
    tmp.type = "input";
    tmp.border = true;
    tmp.x = 50;
    tmp.y = 50;
    addChild(tmp);
    function focusText(_fevt:FocusEvent):void{
    trace(_fevt.target.text);
    var tf:TextField = TextField(_fevt.target);
    tf.setSelection(0,tf.length);
    }

    This doesn't work. Such a shame.

    Anyway, Todd Fraser over here at Organic gave me one of those, "wait, MouseEvent.CLICK didn't work?" with one eyebrow raised. And although I had to admit I hadn't even bothered with MouseEvent.CLICK because I assumed FocusEvent.FOCUS_IN should work. Don't discount what you might consider "ol' timey" ways of doing things.

    var tmp:TextField = new TextField();
    tmp.addEventListener(MouseEvent.CLICK,focusText);
    tmp.htmlText = "test text";
    tmp.autoSize = "left";
    tmp.selectable = true;
    tmp.type = "input";
    tmp.border = true;
    tmp.x = 50;
    tmp.y = 50;
    addChild(tmp);
    function focusText(_fevt:MouseEvent):void{
    trace(_fevt.target.text);
    var tf:TextField = TextField(_fevt.target);
    tf.setSelection(0,tf.length);
    }

    Shoot, dawg.

    Labels: , ,

    Monday, September 22, 2008

    Fee Education Wins an Award

    I generally don't notice when something I worked on wins awards. It's not that I don't care, but if I didn't enter them I wouldn't know they were submitted. I digress.

    Turns out Fee & Processes Explained, a site I worked on last year for Organic, won a WebAward for Best Financial Services Website.

    Yay me. Yay Organic.

    Labels: ,

    Thursday, September 11, 2008

    MainImporter Class

    This is the second custom class used in the Bullet Class, MainImporter.

    During the same project that prompted TextFormatter it dawned on me I had no real useful Load this class. There are a lot of nice phat loaders around, BulkLoader is a great example. However, it's kind of overkill for what I wanted.

    So I put together MainImporter. It handles Bitmaps, SWFs and XML nicely and I've used it extensively for pretty much every project since.

    package com.utils{
    import com.events.LoaderEvent;
    import flash.display.Loader;
    import flash.events.Event;
    import flash.events.EventDispatcher;
    import flash.events.IOErrorEvent;
    import flash.events.ProgressEvent;
    import flash.net.URLLoader;
    import flash.net.URLRequest;
    public class MainImporter extends EventDispatcher{
    public static const ITEMLOADED:String = "item loaded";
    private var itemURL:String;
    public var loader:Loader;
    public var loaderXML:URLLoader;
    private var fileEnder:String;
    public var loadedCurrent:Number;
    public var loadedTotal:Number;
    public function MainImporter(_url:String){
    itemURL = _url;
    var tmpArray:Array = itemURL.split(".");
    fileEnder = tmpArray[tmpArray.length-1];
    loadItem();
    }
    private function loadItem():void{
    var urlRequest: URLRequest = new URLRequest(itemURL);
    if(fileEnder == "xml"){
    loaderXML = new URLLoader();
    loaderXML.addEventListener(IOErrorEvent.IO_ERROR,loadError);
    loaderXML.addEventListener(ProgressEvent.PROGRESS,progressListener);
    loaderXML.addEventListener(Event.COMPLETE,completeLoad);
    loaderXML.addEventListener(Event.INIT,initListener);
    loaderXML.load(urlRequest);
    }else{
    loader = new Loader();
    loader.contentLoaderInfo.addEventListener(IOErrorEvent.IO_ERROR,loadError);
    loader.contentLoaderInfo.addEventListener(ProgressEvent.PROGRESS,progressListener);
    loader.contentLoaderInfo.addEventListener(Event.COMPLETE,completeLoad);
    loader.contentLoaderInfo.addEventListener(Event.INIT,initListener);
    loader.load(urlRequest);
    }
    }
    private function initListener(evt:Event):void{
    //trace("init");
    }
    private function progressListener(evt:ProgressEvent):void{
    loadedCurrent = Math.floor(evt.bytesLoaded/1024);
    loadedTotal = Math.floor(evt.bytesTotal/1024);
    dispatchEvent(new LoaderEvent(LoaderEvent.UPDATELOADER,loadedCurrent,loadedTotal,true));
    }
    private function loadError(evt:IOErrorEvent):void{
    trace("IOErrorEvent : " + evt);
    }
    private function completeLoad(evt:Event):void{
    dispatchEvent(new Event(MainImporter.ITEMLOADED));
    }
    }
    }


    This is a work in progress, so do what you want with it.
    MainImporter.as

    Labels: , , ,

    TextFormatter Class

    I just posted on BulletBuilder. I realized there are two other classes I set up a while ago for another project that I use regularly that could use some explanation.

    First is TextFormatter. We'd started a project and needed a quick way to implement some basic textfields across the project that could react to some supplied variables; font, color, size, leading

    To circumvent some massive discussion about Stylesheets or whatever, I set up TextFormatter and it's done the job pretty adequately and I've used it since for anything non-complex in a textfield.

    To use TextFormatter, just import the class and create a textfield then instantiate TextFormatter. Of course, also import the TextField class. You'll want to set the width of the textfield as well.
    var tf:TextField = new TextField;
    tf.width = 300;
    new TextFormatter(tf,0x000000,12,"Flash ain't so bad","Arial");
    addChild(tf);

    Now in TextFormatter all the pseudo-heavy lifting can begin.
    package com.utils {
    import flash.text.TextField;
    import flash.text.TextFieldAutoSize;
    import flash.text.TextFormat;
    import flash.text.AntiAliasType;
    public class TextFormatter {
    public function TextFormatter(src:TextField,fcolor:uint,fsize:Number,str:String,ffont:String="FranklinGothicEF-Demi", leading:Number=0)
    {
    src.autoSize = TextFieldAutoSize.LEFT;
    src.background = false;
    src.border = false;
    src.embedFonts = true;
    src.selectable = false;
    src.antiAliasType = AntiAliasType.ADVANCED;
    var format:TextFormat = new TextFormat;
    format.font = ffont;
    format.color = fcolor;
    format.size = fsize;
    format.leading = leading;
    src.defaultTextFormat = format;
    src.htmlText = str;
    }
    }
    }


    TextFormatter.as

    Labels: , , ,

    Bullet Class

    A little while ago, I was working a little project that had several lists of bullets. I couldn't find any suitable solutions that gave the designer what he craved; a list of bullets with well-wrapped text.

    Sample xml;
    <SAMPLE_TEXT>• Bullet item one.
    • Bullet item two. Long enough to wrap because I've typed a little bit too much and it definitely is too long to fit in one line.
    • Bullet item three. There's nothing like seeing text wrapping to make you realize that bullets are the bane of your existence. Nothing, I say.
    • Bullet item four.</SAMPLE_TEXT>


    Here's what you get when you just set up a normal textfield and do what you normally do.

    var tf:TextField = new TextField;
    tf.width = 300;
    tf.multiline = true;
    tf.wordWrap = true;
    tf.text = SAMPLE_TEXT;
    addChild(tf);




    As you can see, the text wraps under the bullet because flash only sees it as a block of text.

    I realized that the best solution, for me anyway, was to separate the bullet and the line, make two textfields and line them up. This way the copy aligns as it should and doesn't wrap under the bullet. So I set up a little class to take care of it for me.

    The XML had to change to accomodate TextFormatter, but only a little;
    <SAMPLE_TEXT bulletString="•" ffont="Arial" fsize="18" fcolor="0x000000">• Bullet item one.
    • Bullet item two. Long enough to wrap because I've typed a little bit too much and it definitely is too long to fit in one line.
    • Bullet item three. There's nothing like seeing text wrapping to make you realize that bullets are the bane of your existence. Nothing, I say.
    • Bullet item four.</SAMPLE_TEXT>

    package com.display
    {
    import flash.display.Sprite;
    import com.utils.TextFormatter;
    import flash.text.TextField;
    public class BulletBuilder extends Sprite
    {
    private var content:Sprite;
    private var bulletCharacter:String;
    private var bulletArr:Array;
    private var contentArray:Array;
    private var bullet:TextField;
    private var copy:TextField;
    private var bulletHeight:Number = 0;
    private var fieldWidth:Number;
    /*====================
    provide the constructor with;
    the xml node
    what character to look for
    the width of the end field
    sample;
    var bulletBuilder:BulletBuilder = new BulletBuilder(sampleNode,"•",415);
    addChild(bulletBuilder);
    =====================*/
    public function BulletBuilder(_copy:XML,_bulletCharacter:String,_fieldWidth:Number)
    {
    content = new Sprite;
    bulletCharacter = _bulletCharacter;
    fieldWidth = _fieldWidth;
    bulletArr = _copy.toString().split(bulletCharacter+" ");
    setBulletFields(_copy);
    }
    /*=====================
    setBulletFields separates the copy
    into an array based on the provided bullet character.
    it then uses two textfields; one for the bullet character, one for the copy.
    places the copy at the same y position as the bullet
    and moving it to the right of the bullet
    it then adds the two fields to the sprite and updates the y position for the next bullet
    finally, the function adds the content sprite
    ========================*/
    private function setBulletFields(_copy:XML):void{
    contentArray = []
    for(var i:int = 1;i<bulletArr.length;i++){
    contentArray[i] = new Sprite;
    bullet = new TextField;
    copy = new TextField;
    copy.width = fieldWidth;
    copy.multiline = true;
    copy.wordWrap = true;
    new TextFormatter(bullet,_copy.@fcolor,_copy.@fsize,bulletCharacter,_copy.@ffont);
    new TextFormatter(copy,_copy.@fcolor,_copy.@fsize,bulletArr[i],_copy.@ffont);
    copy.x = bullet.width;
    contentArray[i].addChild(bullet);
    contentArray[i].addChild(copy);
    contentArray[i].y = bulletHeight;
    bulletHeight +=contentArray[i].height;
    content.addChild(contentArray[i]);
    }
    addChild(content);
    }
    }
    }



    Here's sample with the package(s)

    Labels: , , ,

    Friday, August 15, 2008

    FlashForward San Fransisco

    FlashForward is on next week and I'm about as excited as a fat kid looking at a bowl of smarties.

    Not only do I finally get to see the Organic offices in SF, but Libs managed to wrangle a couple of days off and will be joining me for her first trip there ever.

    I look forward to seeing all my friends, tipping a glass and toasting to everyone's health.

    Labels: , ,

    Monday, June 02, 2008

    Happy June

    Things are busy as usual and that means not posting. That's not to say I'm not doing anything and just to prove it...

    I ran into a problem in a recent project where I had a series of buttons and I wanted to one to be active right off the bat. ie, like a gallery where the first image is the triggered from the first thumbnail.

    There are two ways I found;

    1. When your button isn't actually sending any information along with it you can change your callback function to accept a null parameter.

    ex.
    button.addEventListener(MouseEvent.CLICK, onClick);

    private function onClick(mevt:MouseEvent=null):void
    {
    //do whatever here
    }

    now I can just call the onClick function like any regular ol' function

    onClick();

    However, if you want to actually click the button because you need to know something that button has;

    //using the same code as above

    button.dispatchEvent(new MouseEvent(MouseEvent.CLICK));

    TADA!

    Now tell me I haven't been doing anything.

    Labels: , ,

    Friday, November 30, 2007

    New Project Launched

    After I returned from Brighton and Flash on the Beach I was immediately booked on a job. To be honest, all I wanted to do was lie down for a week, but that wasn't meant to be.

    Luckily, it was an interesting job and one I haven't done before. A snow globe. I got to do a few things I've wanted to use in a project; copy images via BitmapData so I only need to load them once, and I adapted Seb Lee-Delisle's AS3 particle system for the snowflakes.

    Wish you were cheer

    Ran into a couple of bugaboos; namely SharedObject issues. Somewhere along the line we thought a downloaded globe could access a SharedObject created by a website. I think I knew this already, but I was hoping I was wrong. So we had to go with writing a text file on the fly, grabbing the exe and zipping them both up for download.

    For the embed code, it was a fairly simple matter of copying basic object and embed code and using FlashVars in the code for the blog aspect. One thing I didn't know and had to join MySpace to discover, MySpace rewrites that code on the fly and it does away with whatever it is I had that the globe recognizes for the globe. Any globe embedded on MySpace is blank. It still looks pretty sweet, and the snowflakes still work, but it's a bummer it's not your own globe. And FaceBook won't let the code work at all. If anyone knows anything about embedding swf's in FaceBook, enlighten me.


    Wish you were cheer

    However, if you have a blog, it works fine. See the post below this one.






    Wish you were cheer

    Labels: , , ,

    Tuesday, July 24, 2007

    Leap Years



    In investigating making an age of majority checker, I started thinking about leap years. I know of one person total that was born on February 29th. Statistically speaking, there are bound to be more.

    Anyway, here's a good little function that'll return true if you have a leap year. and false if you don't

    function checkYear(year) {
    return (((year % 4 == 0) && (year % 100 != 0)) || (year % 400 == 0)) ? 1 : 0;
    }

    Labels: , ,

    Friday, July 20, 2007

    gSkinner in PV3D

    Grant posted about some experimentation he's doing with Papervision3D.

    Nice work, G!

    Labels: ,

    Sunday, June 17, 2007

    Father's Day

    My first father's day. Most notable for the lack of Libs, who's in New York visiting her sister.

    It's been a lot of fun so far. Libs' mother took me out for brunch as a father's day gift. The real gift, in my opinion, was her staying with Declan and I this weekend while Libs is away. I am positive taking care of him alone would have been exhausting.

    Declan and I came back from the pool moments ago and he's just going down for a nap courtesy of Libs' mom. Good stuff, Josie!

    I had my first week at Organic. I'm their new Manager, Integrated Media. A little trepidacious about it but it's a whole new experience and I'm more excited than nervous.

    Labels: , ,

    Monday, June 11, 2007

    Flashbelt 07

    I had the good fortune to meet Dave Schroeder of Pilotvibe fame at this spring's FiTC.

    In a week's time, he is putting on Flashbelt 07 in Minneapolis. There's a tremendous lineup and I hope it's a great success. I only wish I could be there.

    Good luck, Dave!

    Labels: ,

    Wednesday, May 16, 2007

    Camgasm Update



    The fine folks at CustomWeather gave me access to their weather service a little while ago.

    After finally getting a chance to play with it again, I ran into problem after problem trying to connect.

    Well, it's been worked out and now camgasm.com has a cute little current weather reporting system for the time being.

    What am I doing with it?

    step 1. I get your IP address
    step 2. I send that IP to GeoBytes IPlocator.
    step 3. Now that I have the city, I query CustomWeather and get back the xml with your local weather.

    fun fun.

    Labels: , ,

    Thursday, April 26, 2007

    FiTC. Over for Another Year.

    My body nearly gave up on me this year. I missed the entire first day (nearly) due to exhaustion.

    Declan had some weird croupy cough Saturday night, so we brought him to emergency as a just in case. We were there from 10pm to 2 am. Now that's good, efficient healthcare.

    On to FiTC;
    - Craig had a nice dinner for some of us at the Korean Grill.
    - Grant and Bobi came over to meet Declan and for some BBQ.
    - I saw some pictures that looked suspiciously like Gmunk, Hoss, Marcos and Colin in a hot tub.
    - Watched the sun come up with Dale, Marcos, Simon and Shawn.
    - Someone made the mistake of saying "Hugh's more Scottish than you." To Hoss. HOSS! Seriously. I just kind of looked and thought, "That's not even close to true."
    - Tink's newly bald head makes me want to rub lotion on it. C'mere you silly bastard!
    - Shawn didn't make me pay for anything. Which is really nice.
    - Mario and Alexandra once again show themselves to be truly nice people. And honestly, Mario's sincere enthusiasm just gives you more energy.
    - Josh is one bad-ass poker player. So is Mario. Who knew? So I only won one game.
    - Had to watch Lordalex explain once more that, "yes, really, my name IS Lordalex." That's always fun.
    - Joshua gave me a nice print.
    - Shawn yelled at me. I might have deserved it.
    - John continues to rock. Even with short hair. Chris rocks, too, just not as hard or as well as John. It's not personal. It's a fact.
    - I finally remembered Phillip and Keith's name(s). For some reason, I continuously forget both of their names. So I feel better. And they too were good sports about my particular personal foible or forgetting some names.
    - No chance to wrestle Bradley, but give it time. And Chicago.
    - Met Aral and Niqui. Two very nice people. First I called Aral "Raul" (honestly, when he spelled it, i thought that's what he said). And I thought Niqui was Autralian. Turns out, South African. At least she was a good sport about it.
    - I DID forget more names than I remembered, but still it was great.

    Another year gone. Another boatload of braincells given their pink slips.

    Labels: , ,

    Tuesday, April 17, 2007

    UWindsor

    I recently finished up a project for the University of Windsor, hereinafter referred to as UWindsor. It was actually a very smooth project and I liked my team immensely.

    If you know of me as a Flash Developer (or have read previous posts of this blog), you'll know I love using XML as a way of handling content. Thanks to a heads up from Alex Davis, I've started using XPath in Flash. Jen deHaan has a nice little article here explaining it's usage. It really is a time saver. No more looping through childNodes yourself.

    Anyway, UWindsor wanted a site to pull in prospective students by showing them the university from the student's perspectives. Using testimonials from current students gave a voice to the site that would have been sorely lacking otherwise.


    You get to the site from an email from UWindsor, since they control the url, we added in their first name as a greeting using base64 encoding and decoding. In this example, aGFuZGJhbmFuYQ== becomes handbanana.




    The two guides, are equal on the main page. once you select either path "The School" or "The Scene" that guide increases in size, reinforcing the path you chose.





    It was apparent early on that users are used to picking what they want when they want it. So we provided users with a video gallery of all videos used in the site.





    This is what the photo asset looks like and it's xml node that triggers it.





    This is what the text asset looks like and it's xml node that triggers it.





    This is what the video asset looks like and it's xml node that triggers it.


    Labels: , , ,