Archive for the ‘text layout framework’ Category

Mouse interactions on Text Layout Framework InlineGraphicElements in EditMode

Thursday, March 26th, 2009

One slightly frustrating (but totally logical) feature of using editmode in TLF is that inserted InlineGraphicElements lose their "interactivity". Instead, they are treated the same as text characters, that is, the user can select them as if they were selecting text:

There was a comment In my previous entry about the possibility of mouse interaction with inserted graphics.

I have a way to do this, a bit hackish, but it does the job. Every added graphic needs to be stored in an array. When a user clicks, the code loops through all the graphics and checks if one of them happens to be under the mouse. This is achieved using the trusty old localToGlobal() method:

Actionscript:
  1. protected function handleMouseDown(e:MouseEvent):void{
  2.     var hitrect:Rectangle;
  3.     var bm:Bitmap;
  4.     for(var i:uint=0;i<_images.length;i++){
  5.         bm=Bitmap(_images[i]);
  6.         var ltg:Point=bm.localToGlobal(new Point(0,0));
  7.         hitrect=new Rectangle(ltg.x,ltg.y,bm.width,bm.height);
  8.         if(hitrect.contains(mouseX,mouseY)){
  9.             mx.controls.Alert.show("so, I see you have clicked on an image eh?");
  10.             break;
  11.         }
  12.     }
  13. }

This is very useful if you want to edit the graphic somehow, for instance, in the RTE that I'm currently working on I use this for "table support". In the TextFlow, my tables are represented as bitmaps, when clicked, the actual DataGrid is opened and ready to edit. When finished, a new BitmapData is grabbed and the InlineGraphic in the TextFlow is updated.

I have found one "bug" (or a feature?!), if an image is taller than (somewhere around 1000 pixels), the image is no longer properly "wrapped", and actually starts to cover some text.

It's also possible to listen to MouseMove, and set some rollover/out states to the graphics. You can see a demo here and download the source mxml file here.

Insert image from File System into text using the Text Layout Framework

Monday, March 23rd, 2009

For the past few weeks I've been building a Rich Text Editor using the TLF. It's been a great opportunity to dig into it, and I have to say it's mostly been a pleasure. One of the features was to insert images, which turned out to be easy. So dead easy, that I found it cool enough to warrant a blog post.

Click the image for a demo:

Once you've created a TextFlow and activated an EditManager (Making the text editable), it takes just 4 steps:

1) Open an OS Dialogue box, wait for the user to select an image file:

Actionscript:
  1. public function addImage(e:MouseEvent):void {
  2.   _file_ref = new FileReference();
  3.   _file_ref.addEventListener( Event.SELECT, handleFileSelect,false,0,true );
  4.    var filter:FileFilter = new FileFilter("Images", "*.jpg;*.gif;*.png");
  5.   _file_ref.browse([filter]);
  6. }

2) Load the selected file:

Actionscript:
  1. protected function handleFileSelect(e:Event):void {
  2.   _file_ref.removeEventListener( Event.SELECT, handleFileSelect );
  3.   _file_ref.addEventListener(Event.COMPLETE, handleFileOpen,false,0,true );
  4.   _file_ref.load();
  5. }

3) The file is now in the form of a ByteArray. Use a Loader, to loadBytes() and wait for a COMPLETE event.

Actionscript:
  1. protected function handleFileOpen(e:Event):void {
  2.   _file_ref.removeEventListener(Event.COMPLETE, handleFileOpen );
  3.   var data:ByteArray = _file_ref.data as ByteArray;
  4.   _img_loader=new Loader();
  5.   _img_loader.loadBytes(data);
  6.   _img_loader.contentLoaderInfo.addEventListener(Event.COMPLETE,imageLoadComplete,false,0,true);
  7. }

4) Then "copy" the BitmapData into a new Bitmap. This might seem a bit cryptic, a good explanation can be found in this thead Finally, the "one liner" or the "punchline" of this blog post: use EditManager.insertInlineGraphic() to plug it into the textFlow.

Actionscript:
  1. protected function imageLoadComplete(e:Event):void{
  2.   _img_loader.contentLoaderInfo.removeEventListener(Event.COMPLETE,imageLoadComplete);
  3.   var bmd:BitmapData=Bitmap(_img_loader.content).bitmapData;
  4.   var bm:Bitmap=new Bitmap(bmd);
  5.   EditManager(_flow.interactionManager).insertInlineGraphic(bm,bm.width,bm.height);
  6.   _flow.flowComposer.updateAllContainers();
  7. }

That is all... Well, for this to be useful, the image will have to be stored somewhere, if the document being created is to be saved or sent somewhere.

download the source (just one zipped mxml file)

For further reading, here's a couple useful links concerning the TLF:

How to use the TLF tutorial
TLF online forum
online TLF documentation