Archive > July 2012

Reviving Upscreen – A Screenshot Utility

» 19 July 2012 » In C#, Open-Source, Programming, Releases » 2 Comments

Not so long ago, I started Upscreen for Min.us API. I used C++ with minimal 3rd party libraries, and got it working for few weeks. But then it became unstable and I didn’t have the time to update it (my apologies). So now, I revived the project and used imgur API instead. It was smooth, and I’m considering adding an option to upload to min.us (I love them too!).

The hotkey I originally used was Win + PrntScrn, but for some reason, I cannot register the hotkey on Windows 8. So to be safe, Ctrl + Shift + PrntScrn was used.

The good thing about using C# is, I didn’t have to go with the trouble of accessing the clipboard within the Win32 API. It can be done via Clipboard class.

if (Clipboard.ContainsImage())
{
    Image img = Clipboard.GetImage();
    img.Save(tmpName);
    PostToImgur(tmpName);
}

Upscreen is mainly built for uploading screenshots, but it can be used on any other image. Just place the image in the clipboard, then hit the hotkey.

Code is available at GitHub.

Continue reading...

Tags: , , , , ,

Committing Sensitive Data

» 18 July 2012 » In C#, Git, Open-Source, Programming, Security » 2 Comments

I spent the whole night trying to figure out how to revert commits, and remove my sensitive information from my public repositories. This helped me realized how important it is to learn and practice git.

I mostly do open source projects on C#, and I always put to-change data like API keys in app.config. At first, I thought I was on the safe road, while making git ignore changes from my app.config file.

git update-index --assume-unchanged app.config

But then I was wrong. I am actually partially on the safe road.

Several hours ago, while working on a project, I noticed that Settings.settings and Settings.Designer.cs updates whenever I change something in my settings variables. Upon looking at the contents of the files, panic filled my soul and I just realized that it’s not just app.config that I should be untracking.

I furiously searched for a way to resolve this issue, and thinking that I have to go over one commit at a time, I started to think that I made a very huge mistake. I have a database connection string and my personal phone number in two separate projects in GitHub.

Luckily I found this article. Without further munching, I applied the commands to every repository I have, wherein I used app.config to store sensitive data.

Afterwards, I ran the command I used with app.config on Settings.settings and Settings.Designer.cs. Now I am both ashamed to be in such situation, and happy to learn something new.

Continue reading...

Tags: , , , , , ,

Extending SMS Capabilities

» 16 July 2012 » In C#, Life, Open-Source, Programming » 3 Comments

I live in a place where wireless access points are few, mobile internet is expensive, but SMS is unlimited. Of course, I use SMS for communicating with my friends, family, girlfriend, colleagues, and for business. Then, one day it came to my mind, why not communicate with my personal computer?

My father brought home a USB dongle (Huawei E220), I unlocked it, and tried a sim card, and it worked! Now this, is what my computer will be using as a receiver. At first, it’s very frustrating to install the drivers for this dongle. Modern ones are just smooth on PnP (Plug ‘n Play) features. It took me a while to find out that I need to reconfigure the driver Windows installed by default.

Setting Up

Now it’s connected. But I need a way to make it receive SMS, and save it somehow. Then I stumbled upon Gammu luckily, it supports E220(see all supported devices). The configuration file is given, and pretty elementary.

[gammu]
port = COM6
connection = at19200
model = at

You just need to replace COM6 with the COM port you have in your device manager.

Device Manager

COM Port used by the USB Dongle

And then, I intend to install gammu as a service. Luckily an SMS daemon is included, and using the previous gammu configuration:

[smsd]
logfile=C:\smsd\smsd.log
service=files
inboxpath=C:\SMSData\data\


[gammu]
port = COM6
connection = at19200
model = at

[include_numbers]
+000000000000

You can change the paths as you wish, but make sure your number is included in the [include_numbers] section. This is a nice feature that will block unwanted texts from other numbers.

Not that it’s all set, run the daemon and make it install itself as a service, then start the service.

gammu-smsd -i -c C:\smsd\gammu-smsdrc

It will now run automatically with windows. Your USB dongle must be connected all the time to your computer.

Processing Received Messages

Now here’s a tricky but fun part. How will you process the incoming messages? Notice that I used the Files mode instead of using DBMS to receive SMS message. This is because, I need to constantly check if there’s a new message, and checking the database tables every now and then for 24/7 is painful. So in files, we’re gonna use a Timer? No! Of course, we’re not using methods that will cause heavy CPU load.

Using the FileSystemWatcher class, we can check, in real-time, if there’s a new file created in a given directory. This is perfect, because gammu’s SMS daemon creates a new text file, with the message in it, in the specified directory we included in the configuration file.

if (!fpath.Equals(""))
    watcher.Path = fpath + @"\";

watcher.Filter = "*.txt";
watcher.NotifyFilter = NotifyFilters.LastWrite | NotifyFilters.FileName;
watcher.Created += new FileSystemEventHandler(OnChanged);
watcher.EnableRaisingEvents = listenToolStripMenuItem.Checked;

Whenever a file is created inside the specified directory, it will execute the code inside the OnChanged() method. From this, we can process the content of each file and read them.

But not so fast. Sadly(although this seems like a right way), gammu splits the messages by 67 characters. Meaning, if your message exceeds 67 characters, it will be split into several files. For instance:

IN20120716_121927_00_+000000000000_00.txt
IN20120716_121927_00_+000000000000_00.txt
IN20120716_121930_00_+000000000000_01.txt

These are files the dongle received at one point in time. But they really are just 2 separate messages. How? If you look into the last two digits on the filename, it will tell you the sequence of the messages. 00 means the beginning of the message, if followed by another 00, it’s a new message. But if it’s followed by 01, it’s to be appended, and must be read as part two of the first one.

It took me sometime to figure out how to combine them into one. I can only receive one at a time, but the parts came both together with a very tiny interval. By this, I came up with a solution that will use a Timer.

timer.Enabled = false;
timer.Interval = 1000;
timer.Tick += new EventHandler(timer_Tick);

I allotted two seconds to wait for upcoming possible parts, then process them and verify if they really are parts of a long message.

private void OnChanged(object sender, FileSystemEventArgs e)
{
    if (timer.Enabled)
    {
        tmp.Add(e.FullPath);
    }
    else
    {
        tmp = new List<string>();
        this.Invoke(new MethodInvoker(delegate
        {
            timer.Enabled = true;
            timer.Start();
        }));
        tmp.Add(e.FullPath);
    }            
}

private void timer_Tick(object sender, EventArgs e)
{
    secs++;
    if (secs >= 2)
    {
        timer.Enabled = false;
        secs = 0;
        procList(tmp);
    }
}

private void procList(List<string> lst)
{
    List<string> data = new List<string>();
    string xdata = "";
    bool app = true;
    int prev = -1;
    foreach (string fp in lst)
    {
        if (Regex.IsMatch(fp, @"_(d{2})\.txt$"))
        {
            Match m = Regex.Match(fp, @"_(d{2})\.txt$");
            int x = Int32.Parse(m.Groups[1].Value);
            if (x - prev != 1)
            {
                app = false;
                prev = -1;
            }
            else
            {
                prev = x;
            }
        }
        string datum = readContent(fp);
        if (app)
        {
            xdata += datum;
        }
        else
        {
            data.Add(xdata);
            xdata = datum;
        }
    }
    data.Add(xdata);
    foreach (string d in data)
    {
        processData(d);
    }
            
}

It’s a pretty long process, and it took me hours to figure out what to do. But after that, it’s time to add some modules to boost its functionality.

Making Things Functional

As for now, I only have the twitter module working.

private void processData(string data)
{
    Command cmd = parseString(data);

    switch (cmd.id)
    {
        case "tweet":
            tServ.SendTweet(cmd.arg);
            break;
        case "google":
            // Google processing here
            break;
    }
}

private Command parseString(string str)
{
    Command cmd = new Command();
    if (str.Contains(' '))
    {
        cmd.id = str.Split(' ').FirstOrDefault();
        cmd.arg = str.Remove(0, cmd.id.Length + 1);
    }
    return cmd;
}
// ... 
class Command
{
    public string id;
    public string arg;
}

I have plenty of ideas in mind. I am currently working on a google module, then a file-search module for my computer, and many more. In the mean time, you can watch the development process and add your own modules as well. Fork it in GitHub.

I will update if I have something new. Cheers!

I named this project after Parker, my favorite Leverage character.

Continue reading...

Tags: , , , , , ,

ADown: Back in Action!

» 10 July 2012 » In C#, Open-Source, Programming, Releases » 2 Comments

After so many months of being still, I didn’t know ADown(Facebook Album Downloader) is not quite working. Today, I updated the code and the binary. It’s now usable again!

ADown - Facebook Album Downloader

Facebook Album Downloader

So what exactly happened?

Mainly, there has been an issue with the function ParseAlbumUrl. If you want to see the actual differentiation, you can head over here. Meanwhile, the new code looks like this:

/// <summary>
/// Parses the album URL.
/// </summary>
/// <param name="url">The URL.</param>
/// <returns>A string list containing the short album ID, user ID and the validity</returns>
private List<string> ParseAlbumUrl(string url)
{
    List<string> details = new List<string>();
    Match m;

    // Check if the URL has the user id and the album id parameter
    // And store it in the list
    if (Regex.IsMatch(url, @"a\.[0-9]+\.[0-9]+\.[0-9]+(&.+)?$"))
    {
        m = Regex.Match(url, @"a\.([0-9]+)\.[0-9]+\.([0-9]+)(&.+)?$");
        details.Add(m.Groups[2].Value);
        details.Add(m.Groups[1].Value);
        details.Add("valid");
    }
    else
    {
        // If it's not, clear the list and add null, and invalid.
        details.Clear();
        details.AddRange(new string[] { "null", "null", "invalid" });
    }

    return details;
}

And of course, there’s a new feature. I added a parent directory for each album. The directory of the album owner’s name is first created. This will eliminate confusion and album merge from different owners.

Download it here.

Continue reading...

Tags: , , , , ,

Mouse Prank in C++

» 07 July 2012 » In C/C++, Programming » 3 Comments

Hooray for the new post. This post was actually a draft way back 2011. But hopefully, i’ll be motivated and keep on posting. I have many tricks to share!

Several years ago, me and my mates were having fun writing prank codes. I can barely remember them all, but here’s one.

One of the main reason why to code is fun. Of course, we all do want to have some fun. I’ll show and explain how to write a simple C++ program that will add weight to the cursor, making it difficult to use. Here’s the function that does the trick:

void heavyCursor(int weight) {
	POINT cPos;

	while (1) {
		GetCursorPos (&cPos);
		int x = cPos.x;
		int y = cPos.y;

		y += weight;

		SetCursorPos(x,y);
		Sleep(5);
	}
}

To clarify, yes it is an endless loop. This code will continually add points in the y axis and resets the cursor position in the screen. This will be fun, but very hard to stop. Sometimes it’s fun watching your friend struggle on reaching Task Manager just to stop this little program.

Continue reading...

Tags: , , ,