Geek Girl Blogs
GeekGirlBlogs

I recently had to solve these kind of requirements: some components execute actions and at some point in time need to notify other components that certain events happened, so the other components can execute code related to these events. For example, class A executes method ChangeStateOfObjectX, and needs to notify class B when X is changed; then B does a certain action (for example, increments a perf counter that illustrates the number of inner objects in X, or writes an event entry or plays a song) when it’s notified. Let’s call class A the Events Generator (because it generates events :)) and B the Events Consumer (because it takes actions in response to the events generated by A).

Let’s take a concrete example: the class ProjectProgressTracker keeps track of a project progress – this is the Events Generator; when a task is added, completed or blocked (all internal states that the user doesn’t have access to), it needs to let a monitor system know – the Events Consumer.

// generates events when a task is added, completed, blocked etc
class ProjectProgressTracker {
    static Random r = new Random((int)DateTime.Now.Ticks);
    List<Task> tasks;

    public ProjectProgressTracker(string[] initialTasks) {
        this.tasks = new List<Task>();
        if (initialTasks != null)
            foreach (string s in initialTasks)
                this.tasks.Add(new Task(s));
    }

    public void NextAction() {
        int randomNumber = r.Next(10);
        if (randomNumber < 3)
            // a new task was added
        else if (randomNumber > 6)
            // a task is blocked
        else
            // the task is done
    }

    class Task {
        string name;
        public Task(string name)
            this.name = name;
        // other properties & methods
    }
}

This monitor system – StatusUpdatePublisher, sends mails and updates calendars.

// the class that reacts to events generated by ProjectProgressTracker
class StatusUpdatePublisher {
    public void OnTaskAdded(string taskName) {
        this.UpdateCalendar(true);
        this.SendMail(taskName, "added");
    }
    public void OnTaskBlocked(string taskName) {
        this.SendMail(taskName, "blocked");
    }
    public void OnTaskCompleted(string taskName) {
        this.UpdateCalendar(false);
        this.SendMail(taskName, "completed");
    }

    void SendMail(string taskName, string action) {
        Console.WriteLine("Task {0} was {1}", taskName, action);
    }
    void UpdateCalendar(bool taskAdded) {
        Console.WriteLine("Task was {0}", taskAdded ? "added" : "removed");
    }
}

The 2 functionalities (generator / consumer) are completely separate.

1. One way to implement this is to pass an Events Consumer object when constructing the Events Generator; then the generator class simply uses the consumer instance to call the desired methods.

class ProjectProgressTracker {
    static Random r = new Random((int)DateTime.Now.Ticks);
    List<Task> tasks;
    readonly StatusUpdatePublisher publisher;
    
    public ProjectProgressTracker(string[] initialTasks, StatusUpdatePublisher publisher) {
        this.publisher = publisher;
        // other functionality, see above
    }

    public void NextAction() {
        // This should be replaced with the actual logic
        int randomNumber = r.Next(10);
        if (randomNumber < 3)
            publisher.OnTaskAdded(randomNumber.ToString());
        else if (randomNumber > 6)
            publisher.OnTaskBlocked(randomNumber.ToString());
        else
            publisher.OnTaskCompleted(randomNumber.ToString());
    }
    
    // other methods & classes
}

This works, but makes the events generator class tightly coupled with the events consumer. Consider now that we want to add another monitor system that generates documentation tasks. If we follow the style above, we should pass it too inside the events generator class so it can call the correct methods. Of course, this model doesn’t scale very well.

2. Another option is to raise some events at the correct time.

class TaskEventArgs : EventArgs {
    public TaskEventArgs(string taskName) {
        this.TaskName = taskName;
    }
    public string TaskName { get; private set; }
}

delegate void TaskEventHandler(object sender, TaskEventArgs e);

The events generator class has 3 events – for tasks added, completed and blocked.

class ProjectProgressTracker {
    public event TaskEventHandler OnTaskAdded;
    public event TaskEventHandler OnTaskCompleted;
    public event TaskEventHandler OnTaskBlocked;
  
    public void NextAction() {
        // This should be replaced with the actual logic
        int randomNumber = r.Next(10);
        TaskEventArgs eventArgs = new TaskEventArgs(randomNumber.ToString());
        if (randomNumber < 3)
            this.OnTaskAdded(this, eventArgs);
        else if (randomNumber > 6)
            this.OnTaskBlocked(this, eventArgs);
        else
            this.OnTaskCompleted(this, eventArgs);
    }

    // other methods & classes
}

Then the user of the class needs to hook up the events to the correct methods in the consumer class.

ProjectProgressTracker tracker = new ProjectProgressTracker(new string[] {"Gather requirements", "Prototype"});
tracker.OnTaskAdded += (object o, TaskEventArgs e) => publisher.OnTaskAdded(e.TaskName);
tracker.OnTaskCompleted += (object o, TaskEventArgs e) => publisher.OnTaskCompleted(e.TaskName);
tracker.OnTaskBlocked += (object o, TaskEventArgs e) => publisher.OnTaskBlocked(e.TaskName); 

The benefit of this approach is that the generator class is not modified, no matter how many consumer classes we want to add to it. The disadvantage is that the user class needs to hook up all events to the correct implementation in consumers.

3. Another solution is to use the Observable/Observer pattern. The Observer-Observable design pattern is a a very useful pattern for maintaining one-way communication between one object and a set of other objects. The observers receive communications from the Observable. Observers do not have a reference back to the Observable, so the communication is strictly from the Observable to the Observers. The observable is the object the Observers are "watching". The Observable maintains some sort of  list of references to Observers. That way, the Observable can send a message to all the Observers by calling each of their update methods.

This is a known pattern, but since it’s not implemented in .Net Framework 3.5, I am just going to define some interfaces that suit my needs.

Here, the class that generates events is the IObservable<T> and the class that consumes events in IObserver<T>:

interface IObservable<T> {
    void Subscribe(IObserver<T> observer);
    bool Unsubscribe(IObserver<T> observer);
}

interface IObserver<T> {
    void OnNext(T value);
}

In our case, T is a class that contains the state of the task – the name of the task and the action that was taken:

enum TaskAction { Added, Completed, Blocked }
class TaskState {
    public TaskState(string taskName, TaskAction taskAction) {
        this.TaskAction = taskAction;
        this.TaskName = taskName;
    }
    public string TaskName { get; private set; }
    public TaskAction TaskAction { get; private set; }
}

So our classes change accordingly: the ProjectProgressTracker implements the IObservable interface, and the status update class implements the IObserver interface.

class ProjectProgressTracker : IObservable<TaskState>
{
    List<IObserver<TaskState>> observers = new List<IObserver<TaskState>>();

    public void Subscribe(IObserver<TaskState> observer){
        this.observers.Add(observer);
    }
    public bool Unsubscribe(IObserver<TaskState> observer) {
        return this.observers.Remove(observer);
    }

    public void NextAction() {
        // This should be replaced with the actual logic
        int randomNumber = r.Next(10);
        TaskEventArgs eventArgs = new TaskEventArgs(randomNumber.ToString());
        if (randomNumber < 3)
            foreach (IObserver<TaskState> observer in this.observers)
                observer.OnNext(new TaskState(randomNumber.ToString(), TaskAction.Added));
        else if (randomNumber > 6)
            foreach (IObserver<TaskState> observer in this.observers)
                observer.OnNext(new TaskState(randomNumber.ToString(), TaskAction.Blocked));
        else
            foreach (IObserver<TaskState> observer in this.observers)
                observer.OnNext(new TaskState(randomNumber.ToString(), TaskAction.Completed));
    }

    // other methods & classes
}
class StatusUpdatePublisher : IObserver<TaskState> {
    public void OnNext(TaskState state) {
        switch (state.TaskAction) {
            case TaskAction.Added: 
                this.OnTaskAdded(state.TaskName);break;
                   case TaskAction.Blocked: 
                this.OnTaskBlocked(state.TaskName);break;
                   case TaskAction.Completed: 
                this.OnTaskCompleted(state.TaskName);break;
        }
    }

    // the other methods
}

Now the user just constructs the classes and registers the desired consumers:

StatusUpdatePublisher publisher = new StatusUpdatePublisher();
ProjectProgressTracker tracker = new ProjectProgressTracker(new string[] {"Gather requirements", "Prototype"});
tracker.Subscribe(publisher);

This pattern has a couple of advantages:

  • Multiple consumers can be added easily
  • The events generator doesn’t need to know anything about the consumers; no change in the generator is needed when one or more of the consumers is changed.

But we pay the penalty of wrapping the state in a class and then analyzing it in the Observer to see what concrete method to implement.

4. Another possible implementation is the IRegistrar pattern (Disclaimer: I’m not aware of a pattern with this name described. The name is something I came up with). This is somewhat similar with the IObservable pattern, but instead of a class that wraps the state when the event occurs, we specify an interface for the type of events.

interface IProjectEvents {
    void OnTaskAdded(string taskName);
    void OnTaskBlocked(string taskName);
    void OnTaskCompleted(string taskName);
}

interface IRegistrar<T> {
    void Subscribe(T consumer);
    bool Unsubscribe(T consumer);
}

The events consumers implement this interface:

class StatusUpdatePublisher : IProjectEvents {
    // the original methods
}

The generator class can register consumers that know to consume events of type T (IProjectEvents in our case).

class ProjectProgressTracker : IRegistrar<IProjectEvents> {
    List<IProjectEvents> consumers = new List<IProjectEvents>();

    public void Subscribe(IProjectEvents consumer) {
        this.consumers.Add(consumer);
    }
    public bool Unsubscribe(IProjectEvents consumer) {
        return this.consumers.Remove(consumer);
    }

    public void NextAction() {
        // This should be replaced with the actual logic
        int randomNumber = r.Next(10);
        TaskEventArgs eventArgs = new TaskEventArgs(randomNumber.ToString());
        if (randomNumber < 3)
            foreach (IProjectEvents consumer in this.consumers)
                consumer.OnTaskAdded(randomNumber.ToString());
        else if (randomNumber > 6)
            foreach (IProjectEvents consumer in this.consumers)
                consumer.OnTaskBlocked(randomNumber.ToString());
        else
            foreach (IProjectEvents consumer in this.consumers)
                consumer.OnTaskCompleted(randomNumber.ToString());
    }

    // other methods & classes
}

The usage is just as the one for the IObservable pattern.

In our case, it seems that this pattern works the best, because we get all the previous advantages plus strongly typing when calling consumer methods.

Depending on your project requirements, you may choose one of these solutions or look for a better one. Some requirements may be:

  • Loosely coupling between the events generator and the consumers
    • Changing the consumer doesn’t affect the generator
  • One or more consumers can be added
  • Producers can have inner producers and the consumers must be propagated
  • Etc… who knows?

Thu, 02 Jul 2009 17:57:00 PDT


RT @fmpickering: Make sure your marketing copy doesn’t break the law - new copy advice site from CAP - http://digg.com/u17FL0 # Have you noticed #hashtags are now hyperlinked? If you don’t understand hashtags then read Mashable’s hashtag guide http://digg.com/d1rTF8 # Have you noticed that #hashtag are now hyperlinked? This is a #useful way to # Moonfruit running [...]

Thu, 02 Jul 2009 18:39:45 PDT


twitter (feed #9) 5:04pm jokay posted a tweet on jokay@twitter.
Finally home..Yay! but swear upstairs neighbours have opened a rollerskating rink..rolling noises & im sure i heard someone singing xanadu!

Thu, 02 Jul 2009 16:59:59 PDT


I'm not surprised. Today, Federal Judge George Wu tentatively rejected the federal conviction of Lori Drew in the her infamous cyber bullying case. It's not surprising since the case hinged on a strange interpretation of the laws about terms of use policies for MySpace. Since the malicious messages were sent from a fake account, the creation of the fake account become the issue to be decided in the case. It is so normal for online users to simply click "Yes" or "Accept" and ignore, misread, or misunderstand those complex, legal documents called "User Agreements" or "Terms of Use Policies". There doesn't usually seem to be a penalty in doing so. To now claim that this behavior is actual evidence of hacking is a specious argument to most casual observers. Rather, it was a convenient prosecutor's effort to find a way to get justice for the Meier family for the tragic loss of their beloved Megan.

Thu, 02 Jul 2009 15:39:10 PDT


At Microsoft we like to drive special attention to people that do great work in the developer community, as you might know the MVP title is a recognition of this effort.

Since yesterday we have two new MVPs in Belgium, of which one in the developer space.

Therefore, I would like to congratulate Maarten Balliauw for being awarded MVP in the ASP/ASP.NET category.
Maarten has been working a lot around ASP.NET MVC lately, of which he also released the first book on the subject (as far as I know it was the first one at the time): ASP.NET MVC 1.0 Quickly.
Next to that, Maarten’s blog is a fantastic resource. He does depth posts around ASP.NET MVC, Azure, VSTS, PHP, OpenXML and much more. Congratulations Maarten!

Renewed MVPs

We would also like to congratulate the MVPs that have been re-awarded. You have been doing great work!

Hans  Le Roy -  Internet Explorer - http://hlrnet.com/technoblog/?tag=ie8
Loïc  Bar  -  Client App Dev - http://blogs.codes-sources.com/loicbar/default.aspx
Ludovic  Lefort  -  SharePoint Services - http://lefortludovic.blogspot.com/
Riemer  Grootjans -   XNA/DirectX - http://www.riemers.net/
Jan  Tielens  - SharePoint Server - http://weblogs.asp.net/jan/
Wilfried  Mestdagh - Windows Live Platform   
Bruno  van Dooren - Visual C++

Congratulations to all of you!


Thu, 02 Jul 2009 04:37:46 PDT


Don’t get ripped off by the BT Web Clicks service.  Why pay £460 every month for a year for a service that would only cost you £150? More importantly, why is BT claiming to generate “contacts” for your business, when indeed all it is doing is charging you for a “click” to your website .  Since [...]

Thu, 02 Jul 2009 14:39:01 PDT


Hidden banking fees won't be so hidden anymore thanks to a new Twitter service by ING Direct that's inviting people to tweet their fees.

The online institution that already created waves by eschewing bricks and mortar bank branches in favour of online saving and borrowing services is offering people an avenue to vent their fee stories and at the same time track the money they spend in banking fees.

While it's giving people a chance to vent their banking complaints, ING Direct isn't escaping the wrath of consumers who are also using tweeting their complaints about ING. You won't read them in the FeeTweeter Twitter stream but a search of Twitter shows ING Direct is feeling the sting of complaints as well.

Among the tweets so far at ING's Twitter account, @FeeTweeter:

  •  “I just got charged $12.50 to do a stop payment. I asked if I could do a stop payment on the fee. Surprisingly they said no.
  • “I was just charged $24.95 for Account Fees and I think big banks should eat shorts man.
  • “was just charged $3.50 for ABM Fees and I think this was unfair, considering it was a shady backalley abm decorated in gum
  • “I was just charged $4.99 for money order and I think this was "fair", since it was egyptian ink, & printed on gold paper
  • “I was just charged $16.00 for Account Fees and I think this was unfair. I have never received interest on this account!
  • “I was just charged $5.00 for ABM Fees and I think this was a slaaaam dunk on my poor, thin, frail wallet.

 Users who write about their banking fees, either as a direct message to @feetweeter or as a more public @ message that can be read by all their followers, can get a biweekly accounting of their total fees tweeted to date.

Tweet @FeeTweeter to share your 140-character banking fee stories and complaints. @FeeTweeter will RT (that is retweet) some of the tweets it gets but only ones that don't mention names of any financial institutions.

"If there was something with a bank reference, like ' I just paid $4 at RBC,'  we wouldn’t retweet that," Mark Nicholson, head of online in ING's marketing department told me in a phone interview. "It would be coming from us and we don’t want to bash banks directly.

"We don’t want to make it look like our brand is bashing the other banks. We are providing a channel for people to speak out against unfair fees."

Bashing ING also doesn't earn a RT. Among other tweets direct to @feetweeter were:

  •   @FeeTweeter Have u included ING's practice of taking out 2 monthly payments at once 4 Insurance & refusing to correct?
  • @FeeTweeterthinking about switching my mortgage from ING to @rbc

 Users can log into their Twitter account at on ING's fair fees web site to view the total of the bank fees they have tweeted.

Non-Twitter users can log in with a guest account here.

 


Thu, 02 Jul 2009 10:02:00 PDT


This picture was taken in the mountains of Norway, not too far from Flam and the nearby fjords with my digital camera. Peaceful. I've been observing people of all ages using technology durng my...

[[ This is a content summary only. Visit my website for full links, other content, and more! ]]

Thu, 02 Jul 2009 12:52:59 PDT


Autonomous, intelligent robots are great, but when they look like classic Transformers characters they’re even better.

Chris Davies, Chiara Robot with WiFi b/g, articulated claw & Pico-ITX brain [Video]

The handiwork of Mellon University’s Tekkotsu lab, the Chiara Robot has six independent legs, a claw arm with six degrees of freedom, and a combination of webcam and IR rangefinder for spotting objects and obstacles.  Even better, this is no simple lab project: the Chiara Robot will actually be manufactured and sold by RoPro Design.

I admit, Chiara is cool, but I don’t think it’s got the beat when it comes to looking like a classic Transformer character.  The WR-07, created by Nakamura san at Himeji Soft Works, is a robot that morphs from car to humanoid and back.


Thu, 02 Jul 2009 11:48:34 PDT


Today, Mark and I announced the winner of the 3rd Madgex Coding Challenge. This coding challenge was announced on the 3rd June and entries needed to be in on the 30th June. The email announcement said:
So, the challenge this time is all around compression.

Take a string, compress it into a byte[], record the size, decompress it.

You can use any algorithm you chose, but it must be coded by you and not included from an external library

I have defined an Interface ICompress as follows:

public interface ICompress
{
   /// <summary>
   /// Take a string and convert it into a byte[]
   /// </summary>
   /// <param name="source">The string to be converted</param>
   /// <returns>The converted byte[]</returns>
   byte[] Compress(string source);

   /// <summary>
   /// Take the bytearray produced by the call to Compress, and decompress it
   /// </summary>
   /// <param name="compressedData">The data to be decompressed</param>
   /// <returns>The string</returns>
   string DeCompress(byte[] compressedData);
}


I have provided a solution with the interface (Interface), a console app (CodingChallenge3) and an implementation of the interface (Compressor) (which just converts from string to byte[] and back again, no compression) on the development file share.

The source string is provided through the app.config file of the CodingChallenge3 project (the console app).

What do you need to submit?
- A Compressor project that I can plug in to the provided solution
- A couple of paragraphs explaining how your algorithm works


We had 4 solutions submitted, and they were all of a really high standard. I tested them with 6 different input scenarios:
- The original provided sample - the text for "Mary had a little lamb"
- An empty string - which caused a few exceptions to be raised
- A single space
- A string of numbers
- The contents of war and peace
- The contents of the 3 musketeers in French

Each sample was run through each person's solution, and the most compressed result won that round. In the end, one person won 2 rounds (having implemented their own algorithm) and one won 4 rounds (having implemented 3 different methods and selected the one with the highest compression).

This was based around Puzzle 16: Zip me up, Buttercup from the great resource Collection Of Puzzles For Programmers

Previous coding challenges have been based loosely on LTD Puzzle 4: Finding Prime Numbers (which was Madgex coding challenge 1) and LTD Puzzle 3: ASCII Art Shapes (Madgex coding challenge 2).

I'm delighted with how these are going, and the interest and general communication that they generate - lots of discussion, hints of secrecy, and comparisons between each other - and then lots of discussion once the results have been announced, and the code is available for scrutiny. So, I'm now busy thinking up ideas for Madgex Coding Challenge 4 - if anyone has any suggestions or resources for me to use, please pop them in the comments

Thu, 02 Jul 2009 10:27:22 PDT


Episode 122: “Where the hell is Carlos?”

Interesting short film about a happily married couple on the verge of realizing the American dream - Jessica is pregnant and Daniel finally gets the money to open a small diner. But when they hire Carlos, an illegal immigrant from Mexico, they find that they are targets of blackmail:

Turns out I can’t embed the video anymore (I could a couple of days ago, when I scheduled this post), so check it out at Vimeo.

Related posts:

  1. Video of The Day: A Tale of Two Bean Bags
  2. A Video A Day: Where The Hell Is Matt?
  3. A Video A Day: Torchwood Sweded


Thu, 02 Jul 2009 08:00:56 PDT


Would you like to offer a group of your users the ability to create their own file structure and upload massively large files? Look no further. Here is a DotNetNuke module by The Open Light Group, with source code that will do that.

If you have any problems installing it, please post to the forum at this link.

However, hold off on any feature requests because this is just a proof of concept for a Silverlight File Manager that will be in SilverlightDesktop.net.

Why we made this

The reason we broke this off into it's own app is we needed to work out a few challenges:

  • When you move files around in a web based file manager, the communication lag causes things to sometimes get "out of sync".
  • When you allow people to upload large files you simply cannot store all the files on a single server.

How to prevent Lag

The answer to the problem of:

  1. User drags 4 large files from one directory to another using the Silverlight File manager
  2. File manager uses web services to instruct the server to move the files
  3. The server starts to move the files
  4. The user changes their mind and moves the files somewhere else before the server has finished the first move

The answer? Don't move the files. Store the file structure (the folders) "virtually" in the database. So once a person uploads a file it doesn't move again unless it is deleted.

How to Store a Large amount of Files

The answer? Store them in a lot of places. We borrowed a feature we initially developed for ADefHelpDesk called "rolling repository".

It will allow you to set the upload folder, and if files are uploaded to one path and the path is changed for future files, the application will remember what location each file was uploaded to and will be able to retrieve all files. This will allow you to specify different directories at different times.

You can download the module here:

http://dnnsilverlight.adefwebserver.com/Silverlight20/PersonalFileUpload/tabid/77/Default.aspx


Sat, 27 Jun 2009 13:46:06 PDT


The July issue of the OSBR is now available in PDF and HTML formats. The editorial theme this month is Collaboration and the authors include:

Thu, 02 Jul 2009 02:47:46 PDT


Google intern Scott Suiter went to Times Square and asked 50 random people three simple questions:

“What is a browser?”

“Do you know the difference between a browser and a search engine?”

“What browser do you use?”

It wasn’t exactly JayWalking, but to read some of the comments as this Google video makes its way around the blogosphere, you might be tempted to think it was.

JayWalking, if you’re not a Tonight Show fan, was a popular man-on-the-street interview segment where former host Jay Leno would stop pedestrians and ask them questions about American history, current events and other things a fifth grader would probably know. The more stupid the answers, the funnier the segment.

It’s pretty clear just from this little micro-survey that people were confused about the difference between a browser and a search engine.

The question is, does it really matter?

I don’t type in “http://” anymore.  I rarely type in “www.”  What I do instead sets my husband’s teeth right on edge because it’s so lazy. You see, sometimes I’ll search right from my browser window.

If you’re still pulling up the Google home page to begin your search, try skipping that step.  Open IE or Firefox and in the browser toolbar where it says “address,” type in your query –

And then imagine a whole generation of kids growing up doing the same thing.  They don’t care if they’re using the right window or the right word.  Would you be embarrassed because you called a generic bathroom tissue a “Kleenex?”  Or feel stupid if you called the HP office machine that copies and collates a “Xerox machine” instead of a photocopier?  Nah.  And that’s about how important any of this stuff is going to be to the next generation.

The video ends by saying “Less than 8% of the people who were interviewed on this day knew what a browser was.”


Thu, 02 Jul 2009 05:59:17 PDT


Amelia: A look at the life of legendary American pilot Amelia Earhart (Hilary Swank), who disappeared while flying over the Pacific Ocean in 1937 in an attempt to make a flight around the world. I think this could put Swank as a contender again as Best Actress at the Oscars this year.Release Date: October 2009 (US), November 2009 (UK)


The Invention of Lying: A comedy set in a world where no one has ever lied, until a writer seizes the opportunity for personal gain. Starring Ricky Gervais, Jennifer Garner, Tina Fey, Rob Lowe, Jonah Hill.Release Date: September 2009 (US), October 2009 (UK)


Inglourious Basterds: There already have been a couple of trailers out for this Tarantino flick, but this French one has a completely different vibe to it. During World War II, a group of Jewish-American soldiers known as “the Basterds” are chosen to spread fear throughout the Third Reich by scalping and brutally killing Nazis. The Basterds soon cross paths with a young French girl named Shosanna who runs a movie theater in Paris that is frequented by soldiers. Release Date: August 2009 (US, UK)


Couples Retreat: A comedy about four couples who head to a tropical resort for a vacation. While one of them is there to work on their marriage, the others fail to realize that participation in the resort’s therapy is not optional. Release Date: October 2009 (US, UK)


The Informant: The government decides to go after an agri-business giant with a price-fixing accusation, based on the evidence submitted by their star witness, vice president turned informant Mark Whitacre (Matt Damon). Release Date: October 2009 (US), November 2009 (UK)


Planet 51: Because Ice Age is out in cinemas today, a couple more animation trailers have been released. This is the second trailer of Planet 51, where its inhabitants live in fear of alien invasion. Their paranoia is realized when an astronaut arrives from Earth. Befriended by a young resident, he has to avoid capture and recover his spaceship. Release Date: November 2009 (US), December 2009 (UK)


Cloudy With A Chance of Meatballs: Another animation trailer! This time it’s the second full length trailer for Cloudy With A Chance of Meatballs. Inspired by Judi and Ron Barrett’s children’s book, the film focuses on a town where food falls from the sky like rain. Release Date: September 2009 (US,UK)


Forbidden Reality (aka Smersh XXI, aka The Interceptor): Based on the novel by popular sci-fi writer Vasiliy Golovachev, the film is about an agent who is betrayed by his partner while transporting a new psychic weapon. Believed to be dead, he escapes and takes new identity so he can live in peace. But is later forced to return to Moscow to confront a secret organization. The trailer is completely in Russian (without subtitles) so it’s a bit difficult to follow what is happening, but the visuals look pretty cool. Release Date: unknown


Trailers courtesy of FirstShowing

Related posts:

  1. Trailerrific Thursday: Thirst, Last and Nobody
  2. Trailerrific: Where The Wild Things Are
  3. Trailerrific: Superheroes, Suicides and Poker


Thu, 02 Jul 2009 05:00:47 PDT


In a recent deployment, project owners can now use advertisements from The Lounge using a single click.

single click option to host ads from The Lounge

Project owner can see advertisements appear on the Home tab, the Downloads tab, the Discussions tab, and the Issue Tracker.

Displaying an ad from The Lounge

The CodePlex documentation has more information about displaying ads from The Lounge.


Thu, 02 Jul 2009 03:00:00 PDT


Support ActionAid Australia’s search for their next outreach blogger by adding one of these banners to your website or even sign yourself up here.

actionaid_200X200


Thu, 02 Jul 2009 01:42:46 PDT


Who’s visiting Excel blogs and websites? Chandoo, at Pointy Haired Dilbert, reported his stats for June 2009, and a few more people chimed in.

The Spreadsheet Page

Daily Dose of Excel

PTS Blog

And here are the stats for my Contextures website (blog not included)

200906_CtxSite

And this blog — I lost a couple of days of stats when I switched blog themes.

200906_CtxBlog

________________________

Share/Save/Bookmark


Wed, 01 Jul 2009 21:33:00 PDT


shelfariShelfari has been one of my favorite websites in the past few months. I’m so thankful that my friend Mike invited me. It’s another book social network, but what makes this one different is the amazing user interface. I absolutely love seeing the book covers on an actual shelf. Adding books, reviews, and discussions are quite easy as well. Join the community so we can recommend books to each other. ;)

Here are some IT-related books that I read/want to read:

Shelfari: Book reviews on your book blog

Share a book review on Shelfari, where this reader meets fellow readers.

I enjoy reading books with topics in sci-fi, fantasy, technology, social media, library 2.0, and scrapbooking. Come join me on Shelfari. I’m also on GoodReads and LibraryThing if you prefer those book social networks.


Wed, 01 Jul 2009 22:19:09 PDT


gdgt-logoThere’s one thing that you need to know about me if you don’t already — I LOVE GADGETS. I’m a total gadget geek and I’m sure a lot of you are as well. I had two friends call me “Mary Poppins” recently because I was pulling all sorts of random gadgets out of my purse. I’ll take it as a compliment since she’s quite a lovely lady. :)

So what can make me more happier than having a new shiny toy to play with? Joining a social network built around a community of shiny gadgets of course! I joined gdgt today and absolutely love the concept and community. The website is run by Ryan Block and Peter Rojas — two amazing gadget gurus, along with with the rest of the gdgt team!

So how does it work? My friend Veronica will tell you how!


So, what is gdgt? from gdgt on Vimeo.

As you can see, I’m quite addicted to it. Here’s my geeky gadget badge. You can see all the gadgets I own, wish for, and use to have. So what are you waiting for? Come join in on the fun — register for a gdgt account now.


Wed, 01 Jul 2009 20:47:40 PDT

Add Your Blog

Add your blog feed...

Enter the code shown above:
Submit
*Required
The Blog Roll
Copyright 2009 by SoulSolutions Pty Ltd   |  Terms Of Use  |  Privacy Statement