Mittwoch, 8. Mai 2013

C++: improved string tokenizer

Using templates the old string tokenzier can be further improved:

template  void tokenize(const std::string &str,
              T &tokens,
              const std::string &delimiters = " ") {
  string::size_type lastPos = str.find_first_not_of(delimiters, 0);
  string::size_type pos = str.find_first_of(delimiters, lastPos);

  while (std::string::npos != pos || std::string::npos != lastPos) {
    tokens.push_back(str.substr(lastPos, pos - lastPos));
    lastPos = str.find_first_not_of(delimiters, pos);
    pos = str.find_first_of(delimiters, lastPos);
  }
}

This allows any container with a push_back() method to receive the extracted tokens.

std::list tokens;
tokenize("I want to tokenize this!", tokens);

tokenize("2012-02-20", tokens, "-");

or

std::vector tokens;
tokenize("I want to tokenize this!", tokens);

tokenize("2012-02-20", tokens, "-");

Freitag, 21. September 2012

Web: Placeholder.it

I found this very useful site on the internet a few days ago. Placeholder.it provides a very simple service. You can request an image from them specifying a width and height and they will provide a grey image at your requested size.

If you are lazy like me, you can use these images to quickly build spacers or blind images to layout your site.

This will generate an image with 350x150 pixels.

http://www.placehold.it/350x150

Mittwoch, 22. August 2012

C++: String startsWith function

This function checks if the supplied string starts with the specified prefix.

bool string_startsWith(const std::string &str, const std::string &prefix) {
  return std::equal(prefix.begin(), prefix.end(), str.begin());
}

Freitag, 17. August 2012

ActionScript: Distance between line and a point

/**
 * Computes the difference vector between two vectors.
 * @param p1 First vector (from (0,0).
 * @param p2 Second vector (from (0,0).
 * @return  The difference vector between p1 and p2.
 */
public static function differenceVector(p1 : Point, p2 : Point) : Point {
 return new Point(p2.x - p1.x, p2.y - p1.y);
}
  
/**
 * Projects a point onto a line. Returns the projected point or null if
 * the projection does not fall within the segment. 
 * 
 * @param lineStart First point of the line.
 * @param lineEnd Second point of the line.
 * @param p Point that should be projected onto the line given by 
 *              lineStart and lineEnd.
 * @return      The projected point on the line or null if the projection line
 *              falls not between lineStart and lineEnd.
 */
public static function projectPointOntoLine(lineStart : Point, 
                                            lineEnd : Point, 
                                            p : Point) : Point {
 // Difference vector is the line.
 var l : Point = differenceVector(lineEnd, lineStart);
   
 // Determine determinant and divide it by the length of the line.
 var u : Number = (((p.x - lineStart.x) * (lineEnd.x - lineStart.x)) + 
                          ((p.y - lineStart.y) * (lineEnd.y - lineStart.y))) / 
                         (l.length * l.length);
   
 // Check whether the projection lies between lineStart and lineEnd.
 if ((u < 0) || (u > 1)) {
  return null;
 }
   
 // Compute projection point.
 var pp : Point = new Point(lineStart.x + u * (lineEnd.x - lineStart.x),
                                   lineStart.y + u * (lineEnd.y - lineStart.y));
   
 return pp;
}
  
/**
 * Computes the shortest distance between a line and a point. If the 
 * point cannot be projected onto the line segment specified by
 * lineStart and lineEnd, the function will return -1.
 * 
 * @param lineStart First point of the line.
 * @param lineEnd Second point of the line.
 * @param p Point that should be projected onto the line given by
 *              lineStart and lineEnd.
 * @return      The distance between p and the line or -1 if p cannot be
 *              projected onto the line.
 */
public static function distanceLinePoint(lineStart : Point, 
                                         lineEnd : Point, 
                                         p : Point) : Number {
 var projection : Point = projectPointOntoLine(lineStart, lineEnd, p);
 if (projection != null) {
  return differenceVector(p, projection).length;
 } else {
  return -1;
 }
}

Donnerstag, 16. August 2012

FlashDevelop: CamelCase cursor hopping

As a keyboard person I really like to navigate text fast. I use CRTL-Left and CRTL-Right in any text editor to jump between words. Eclipse added another feature onto the word hopping. It recognizes the CamelCase nature of code. So if I have

myLayoutManager

it will position the cursor at the beginning of my on the first press, on the L of Layout on the second press and on the M of Manager on the thrid press, before jumping to the next word or character. For editing code this is simply great. Saves so much time and single curor movement.

Because I have not found an official name for this behavior I will call it CamelCase cursor hopping (CCCH).

FlashDevelop does not support CCCH, but you can install plugins. Mørkeulv wrote the Wordshifter plugin that enables it in FlashDevelop. Just download the binary from his blog and install it. He even provides the source code for the plugin.

You can customize the jumping behavior by providing your own regular expression and which keys should be used to hop around the code. This way you can reenable the old word jumping and have CCCH along each other.

Thanks for the addon!

Links:



Mittwoch, 15. August 2012

Android: Install USB drivers for HP Touchpad

If you have a HP Touchpad running CyanogenMod Android, you can use it to develop and test applications on the native device. But before you can use the tools from the Android SDK on a Windows PC, you have to install the USB drivers.

The Android SDK provides USB drivers for Windows in <sdk-directory>/extras/google/usb-drivers. But those drivers don't include the needed information to identifiy a CyanogenMod Android. CyanogenMod has a patched android_winusb.inf file and the instructions on how to install it available in their wiki.

The patched driver information file does not contain information for the HP Touchpad. You have to patch the patched INF file again for the Touchpad.

So here are the steps needed to connect the Touchpad to a Windows PC to start developing/debugging:


1. Turn on MTP, which is disabled by default, on the Touchpad.
Go to Settings -> Storage -> click on the three small squares in the upper right corner -> USB computer connection -> enable Media Device (MTP)
2. Add HP Touchpad Vendor and Product IDs to the INF file
Edit the android_winusb.inf either from the CyanodgenMod wiki or the original file from the Android SDK. Add these lines at the end of the sections for [Google.NTx86] and [Google.NTamd64].

; HP TouchPad
%SingleAdbInterface%    = USB_Install, USB\VID_0BB4&PID_6860&REV_0227&MI_01
%CompositeAdbInterface% = USB_Install, USB\VID_0BB4&PID_6860&MI_01


3. Update driver in Windows Device Manager
Open the Device Manager in Windows, selection the unknown USB device and update drivers. Select the android_winusb.inf file you just modified.

Dienstag, 14. August 2012

FlashDevelop: Curly braces and CodeFormatter

I have been using FlashDevelop lately. It is a great IDE for ActionScript development. But coming from an Eclipse background I had to relearn a lot of keyboard shortcuts. One feature I really like in an IDE is using a code formatter. FlashDevelop contains such a feature and it can be accessed by right clicking in the editor and selecting Refactor->Code Formatter or by using the keyboard shortcut CRTL-Shift-2.

But as always every programmer hates it when the automatic code formatter destroys lovingly crafted indentation. The default behavior of the FlashDevelop formatter is to put the curly braces on a new line. I have struggled a long time with myself over whether to put them on a new line or keep them on the same line. The later option won. And now it just feels awkward to see them on a line of their own.

Of course FlashDevelop provides a solution - a little bit hidden. Go to

Tools -> Program Settings -> CodeFormatter -> BraceStyle

and change it to "OnLine".