Showing posts with label Quicktips. Show all posts
Showing posts with label Quicktips. Show all posts

Creating a simple WYSIWYG editor with HTML and JavaScript


An updated and better version of this post with a new and better demo can be found here: http://www.kinderas.com/technology/2014/2/18/a-simple-rich-text-editor

Wouldn't it be nice to provide the users of your website with a WYSIWYG rich text editor instead of boring forms and a bunch of textfields? Enter «contenteditable». This is a simple property which can be set on any DOM element, like divs, sections and so on. What it does it making the element writable for the user, directly inline with all your predefines styles and content.
contenteditable="true"
To get set up, set the «contenteditable» property of your selected element to "true". In my demo I'm using a «section» element, but as noted above, you can use any DOM element. And that is it actually. You now have a working rich text editor running on you web-page. You can use the keyboard shortcuts like «cmd+b» to make selected text bold and so on. But wait, there's more.
document.execCommand('bold',false,null);
This simple JavaScript command will allow you to programmatically make text bold and thats not all, there are a dozen of built in commands which can be executed on the selected text, for an overview take a look at the WHATWG specification.

When combining «contenteditable» with the HTML 5 storage APIs you can pretty easily make a powerful rich text editor for your users. Take a look at my simple demo to see how you can accomplish this. As a side note, iOS 5 brings support for «contenteditable» on mobile platforms as well.

Quicktip: Skewing an image with JavaScript and CSS3

Have you ever found yourself in a situation where you needed to skew a rabbit? If you haven't, you'll probably enter this place soon, so here I am to prepare you. The task is to skew an image on a HTML page using CSS and JavaScript. This could be attached to for instance a button click event. This is a one liner..
document.getElementById('myImage').style.transform = "skew(-15deg)"
The «skew» property of the «transform» CSS method takes degrees of skew as an input. Negative numbers will skew the image top right, bottom left and positive numbers..the other way around.
Note that in order for this to actually work, you will need to use vendor prefixes as the time of writing this post. For Safari (desktop and iOS) and Chrome (and Android) you would use «webkitTransform» for FireFox «mozTransform» and so on.

Quicktip: Flipping an image with JavaScript


Let's say you wanted to flip an image in you web-app horizontally or vertically. By using a tiny bit of JavaScript and CSS 3 this is really easy.

//Get the image
var img = document.getElementById('myimage');
//Flip it horizontally
img.style.webkitTransform = 'scaleX(-1)';


And you're done! Note that this will only work in webkit browsers. The equivalent for Mozilla browsers would be «img.style.MozTransform». To flip the image vertically you could use: «scaleY(-1)». And to flip both horizontally and vertically at the same time: «scale(-1,-1)».

[edit 17.03.2011]
You can of course do this in other browsers besides Gecko or WebKit based browsers, as pointed out in the comments. Safari will actually support both the «webkit» and the «Moz» prefix, but this will most likely go away soon. So what you'll need to use is feature detection. This will still not work in ALL browsers, but the usable ones will most likely support it.
if(img.style.webkitTransform){
  img.style.webkitTransform = 'scaleX(-1)';
}else if(img.style.MozTransform){
  img.style.MozTransform = 'scaleX(-1)';
}else if(img.style.OTransform){
   img.style.OTransform = 'scaleX(-1)';
}else if(img.style.msTransform){
   img.style.msTransform = 'scaleX(-1)';
}else{
   img.style.transform = 'scaleX(-1)';
}

Quicktip: Searching an ArrayCollection fast and easy

Let's say your Flex project needs to maintain a large amount of data, like all the userdata from you big ass site. You can use several datastructures in Flex to store complex userdata, from XML to linked lists. However, perhaps the most useful and easiest structure is the Flex native ArrayCollection. This structure gives you a lot for free, for instance.. searching for stuff.

Let's say you have all of your users in "usersCollection" which is an ArrayCollection. A user object may contain things like "firstNamename","lastName", "email", "address" and so on. Now, what if you need to find a specific user like "John Rambo". Then you'll need to search both the first and last name fields. You could of course traverse the entire collection using a loop, checking every iteration. Hang on, there is a faster way using a cursor (it's kinda lika a struct pointer if you're a C person).

First you need to sort the collection
var mySort:Sort = new Sort();
mySort.fields = [new SortField('lastname')];
usersCollection.sort = mySort;
usersCollection.refresh();

Then we create the cursor, pointing to the first item in the collection at init.
var cursor:iViewCursor = usersCollection.createCursor;

Now, we need to search both first and last name, so we create a searchobject.
var sObj:Object = {firstname:"John",lastname:"Rambo"};

We are now ready to do the actual search by using the findAny method of the cursor.
if(cursor.findAny(sObj)){
//We found him
}else{
//John Rambo is lost again
}

In order to get to the user we found we utilize the current property of the cursor.
var foundUser:Object = cursor.current;

Do keep in mind that the cursor is now pointing to the user found, so if we want the next user in the list we can simply go "cursor.moveNext()"

Why should you use this method? It's more flexible, it's faster and uses less resources than the traditional iterative loop approach.

Generating a thumbnail and saving it to disk

This quicktip will show you how to load an image from wherever and how to generate a thumbnail from that image and save it to the disk. In fact, you can use this method to generate screen dumps from any visual component from within Flex.
There are some considerations, first the actual scaling of an image can be done in several ways, the most used trough a scale Matrix. However, in this example I'll be utilizing the Flex library in order to scale the image using smoothing, thereby accomplishing a better result than with simply a Matrix.

Let's say I have loaded an image into a Flex Image component(myImg) and wish to generate a widescreen(16/9) thumbnail for it.
Load the image
myImg.source = "http://graphics8.nytimes.com/images/2006/12/28/business/28dog.xlarge1.jpg";

When the image is finished loading(Event.COMPLETE) we generate the thumb at a size of 200x112
var orgBitmap:BitmapData = new BitmapData(myImg.contentWidth,myImg.contentHeight);
var thumb:BitmapData = new BitmapData(200,112);
orgBitmap.draw(myImg);//Get the orginal image

var scaleImg:Image = new Image();
scaleImg.load(new Bitmap(orgBitmap,"auto",true));//Set smoothing to true
scaleImg.content.width = 200;
scaleImg.content.height = 112;

thumb.draw(scaleImg);//Here we have the scaled image data

Now we have scaled the image using the Image component in Flex which actually does smoothing on the image when scaled. Now we need to convert the bitmapdata into valid JPEG format.
var myjpeg:JPEGEncoder = new JPEGEncoder(80);//Set quality to 80
var thumbdata:ByteArray = myjepeg.encode(thumb);

Now we need to save it to disk(to desktop)
var fl:File = File.desktopDirectory.resolvePath("myimage.jpg");
var fls:FileStream = new FileStream();
fls.open(fl,FileMode.WRITE);
fls.writeBytes(thumbdata);
fls.close();

There you have a smoothed thumbnail waiting for you on the desktop.

QuickTip: MOUSE_OVER vs ROLL_OVER

So, what is the difference between the MouseEvents, MOUSE_OVER and ROLL_OVER? The short answer is that MOUSE_OUT triggers when mousing over a child of the listener object, ROLL_OUT only triggers when leaving the listener objects bounding box. Consider the following code:

var sp:Sprite = new Sprite();
sp.graphics.beginFill(0xFF0000);
sp.graphics.drawRect(0,0,200,200);
sp.graphics.endFill();

var inner:Sprite = new Sprite();
inner.graphics.beginFill(0x00FF00);
inner.graphics.drawRect(0,0,50,50);
inner.x = 75;
inner.y = 75;
sp.addChild(inner);
addChild(sp);

sp.addEventListener(MouseEvent.MOUSE_OVER, report);
sp.addEventListener(MouseEvent.MOUSE_OUT, report);
sp.addEventListener(MouseEvent.ROLL_OVER, report);
sp.addEventListener(MouseEvent.ROLL_OUT, report);

function report(evt:MouseEvent):void{
trace(evt.type);
}


The sprite "inner" is a child of "sp". When rolling over "sp", both the MOUSE_OVER and the ROLL_OVER will trigger. However, when rolling over "inner", MOUSE_OUT will trigger, succeeded by MOUSE_OVER again. ROLL_OUT will not trigger when rolling over "inner". Test it out and it will all become clear!

Quicktip:Event handling

I've been seeing a lot of this(image) following the launch of ActionScript 3. For me, having the debugger version of Flash Player installed it manifests as an error dialog box telling me that loading did never complete. If you don't have the debugger version of the Flash Player this will only result in the application stopping without any message.

What puzzles me a bit is how often I see this error and the share number of professionally build Flash sites where this occurs. Now, this is completely avoidable. It's just a question of handling your events.

Basically there are 6 event you handle when loading stuff over http(s). You don't actually need to do anything upon the occurrence of an event(however it is smart to do so), you simply need to handle it in order to avoid FP throwing an error shown above. Do this and your app will feel so much more well made to the end user.

Quicktip: Skewing an image using ActionScript 3


So you want to skew an image, or a MovieClip or perhaps any other DisplayObject. You could do this manually in the Flash editor of course, but what if you need to do it dynamically, or in Flex.. Here is how.
//If you prefer to draw one visually, skip down
/*var target:MovieClip = new MovieClip();
target.graphics.beginFill(0x000000);
target.graphics.lineTo(100,0);
target.graphics.lineTo(100,100);
target.graphics.lineTo(0,100);
target.graphics.lineTo(0,0);
target.graphics.endFill();
//center it on the stage
target.x = stage.stageWidth *.5-50;
target.y = stage.stageHeight *.5-50;
//add the mc to the stage
addChild(target);*/
/*****/
//Set the skewing angle
var degX:Number = 15;
var degY:Number = 15;

//Get the transform matrix for the object to skew
var m:Matrix = target.transform.matrix;
m.b = Math.tan(degY *(Math.PI/180));
m.c = Math.tan(degX +(Math.PI/180));

//Apply the matrix to the transform object
var t:Transform = new Transform(target);
t.matrix = m;

//Apply the skew
target.transform = t;

Looks like a lot of code, but remember that the first 10 lines of code(not counting comments) are just to draw a MovieClip onto the center of the stage. The actual skew is achieved in just 8 lines of code.
When applying this to a movieclip it will look something like the image in the top of the post.

Quicktip: Ducking local security in FlashPlayer

Ever needed to test a swf containing networking residing on your local hard drive? Sure, you can choose to export for only network from the publish menu in Adobe Flash. But what if you need to load some movies locally and then make a connection to your remote server at the same time? Well, out of the box, you can't. But wait, there is a simple solution to allow flash player to do both when playing locally. Only tree easy steps..

1. Open your favorite texteditor(BBEdit, Coda, Textmate..) and create a new textfile. At the first line, type the path of the folder where your project resides, e.g./Users/username/myproject

2. Save the file with a .cfg extension to: /Library/Application Support/Macromedia/FlashPlayerTrust/

3. There is no step 3

Note: You can do this for your entire user account, but I strongly recommend not to do so, cos this will allow not trusted files to run both networking and local command on your computer if you download them. You don't want that.

Quicktip: Avoiding popup blockers in AS3

Adobe/Macromedia did change a couple of things as the release of ActionScript 3 became a reality.
For once, it's not as easy as it once was to open an external browser window. There are many solutions to this floating around, many of them involve using the "wmode" parameter in the HTML embed code for the swf. In my opinion this is not a good idea cos it will bring a bunch of new problems with it, like handling textfields and so on. I've written a possible solution for this problem which works using standard embed code in the HTML. It simply tries to use the ExternalInterface, if that fails, it falls back to navigateToURL. Hey, remember to import ExternalInterface, URLRequest and NavigateToURL in order for it to compile properly.

private function openURL(url:String, window:String = "_blank") : void {
var WINDOW_OPEN_FUNCTION:String = "window.open";
if(!ExternalInterface.call(WINDOW_OPEN_FUNCTION, url, window)){
navigateToURL(new URLRequest(url),window);
}
}

Quicktip: Changing the font in Flex 3 editor

Have you ever wanted to turn enlarge that font size in the code editor in Flex builder 2/3, but have thrown in the towel after several hours poking around to find this setting? Since Flex is build on Eclipse, this part of the editor is actually identical to the Eclipse interface. To change the font, choose Window -> Preferences -> General -> Appearance -> Colors and fonts.
In that small list of folders, choose Basic -> Text font and hit the change button. Tada! Kinda a lot of effort, but it will be worth it in assisting your eyes from squinting all day long.

And hey, while we're at it. If you are starting to type something in the code editor, but can't quite remember the whole variable name or whatever... hit ctrl+ spacebar. Flex will then make a suggestion. This is a very handy feature as well..

Quicktip: Actionscript 3 and number bases

"Oh my God, he's writing about numbers, how boooring!".. I bet you're thinking something like that right now, but hang on, this isn't really about numbers, it's about colors and all the cool things you can make em do.
So what does number bases has to do with colors? Well, in this exact moment you are looking at several colors, and at least two color models. The most commonly used on webpages, hexadecimal colors, like #FFFFFF or 0xffffff (in Flash/flex). In fact, hexadecimal means 16 based, as opposed to decimal or 10 based like we're used to (0-9). This is kinda good to know, because.. let's say you want your flash app to sample some colors from a picture and present the colors to a web-designer in a hexadecimal format.. how would you go about converting the premultiplied color value Flash gives you into an usable hex color?

Let's say you sample the color white, Flash gives you 16777215, completeley useless for a designer. Let's transform that value into a hex color in one line:
var myWhiteColor:uint = 16777215;
trace(myWhiteColor.toString(16));
And there you go, Flash spits out "ffffff". This happes because the toString method takes the radix or number base as a parameter and converts the passed number. To reverse the conversion you'd use parseInt("0xffffff"), that would give you the original premultiplied color value.

Quicktip: Getting the GET params in ActionScript

So, you want to get the content of a GET variable, like «http://nytimes.com/?id=dork» the id from the URL of that web page. Using a server side script like PHP in conjunction with ActionScript you can use $_GET['id'] and print that to a FlashVars on the page in which the swf file is embedded. That sounds like a tedious solution, and what if you can't control the server side scripting? Well, good news, using the spanking new ExternalInterface api for ActionScript 3 we can get the id value passing a bit of JavaScript.

var myStr:String = ExternalInterface.call("window.location.search.substring", 1);

Note that this will accually give you the entire string "id=dork", so you will have to split it on the equal sign.

var myParams:Array = myStr.split("=");
var param:String = myParams[1];

There you have it.. no server side scripting, only ActionScript and javaScript, all from within the one swf file.

Quicktip: Flipping an image in Actionscript

Ever needed to flip a dynamically loaded image in Flash or Flex? Like for making mirror effects and so on..
There is no property in ActionScript 3 called "flipImage", but there is one easy way to do it.

In AS3, to flip an image horizontally, go like so:

var flipper:MovieClip = new MovieClip();
//Load your image into the flipper MC
flipper.scaleX = -1;

This works because you're actually resizing the image beyond zero, literately turning it inside out.
PS: This will not work with components, like the UILoader.