[ 
https://issues.apache.org/jira/browse/FLEX-35370?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel
 ]

Hugo Ferreira updated FLEX-35370:
---------------------------------
    Description: 
TLF is a powerful framework however have a gap on a good image support or it's 
incompleted.

The developer can set a Sprite with bitmap data but when try to export the 
image source is exported as [Sprite object] and of course can't be restored by 
import.

I fixed this issue on my side, patching the original TLF export and import and 
I want to donate my patch to Apache Flex community.

In the method exportImage of the class TextLayoutExporter, replace:

{code:java}
if (image.source != null)
   output.@source = image.source;
{code}

By:

{code:java}
if (image.source != null)
{
        if (image.source is Sprite)
        {
                var sprite:Sprite = image.source as Sprite;
                var bitmapData:BitmapData = new BitmapData(image.measuredWidth, 
image.measuredHeight, true, 0x00FFFFFF);
                bitmapData.draw(sprite);

                var pngEncoder:PNGEncoder = new PNGEncoder();
                var base64Encoder:Base64Encoder = new Base64Encoder();
                base64Encoder.encodeBytes(pngEncoder.encode(bitmapData));
                output.@source = "data:image/png;base64," + 
base64Encoder.toString();
        }
        else
        {
                output.@source = image.source;
        }
}
{code}

And in the method createInlineGraphicFromXML of the class TextLayoutImporter, 
replace by this version:

{code:java}
public function createInlineGraphicFromXML(xmlToParse:XML):InlineGraphicElement
{                               
        var imgElem:InlineGraphicElement = new InlineGraphicElement();
        
        
parseStandardFlowElementAttributes(imgElem,xmlToParse,_ilgElementFormatImporters);
        
        if (_ilgFormatImporter.result)
        {
                var source:String = _ilgFormatImporter.result["source"];
                if (source != null && source.substr(0, 
"data:image/png;base64,".length) == "data:image/png;base64,")
                {
                        var base64Decoder:Base64Decoder = new Base64Decoder();
                        
base64Decoder.decode(source.substr("data:image/png;base64,".length));

                        var bitmapData:BitmapData = new 
PNGDecoder().decode(base64Decoder.toByteArray());

                        var image:Sprite = new Sprite();
                        image.graphics.beginBitmapFill(bitmapData, null, true, 
true);
                        image.graphics.drawRect(0, 0, bitmapData.width, 
bitmapData.height);
                        image.graphics.endFill();
                        imgElem.source = image;
                }
                else
                {
                        imgElem.source = _imageSourceResolveFunction != null ? 
_imageSourceResolveFunction(source) : source;
                }

                // if not defined then let InlineGraphic set its own default
                imgElem.height = _ilgFormatImporter.result["height"];
                imgElem.width  = _ilgFormatImporter.result["width"];
                /*      We don't support rotation yet because of bugs in the 
player. */         
                // imgElem.rotation  = 
InlineGraphicElement.heightPropertyDefinition.setHelper(imgElem.rotation,_ilgFormatImporter.result["rotation"]);
                imgElem.float = _ilgFormatImporter.result["float"];
        }

        return imgElem;
}
{code}

The only issue about this solution is that this import method relies on the 
third party PNGDecoder from this source: 
https://forum.starling-framework.org/topic/how-to-load-a-png-file-as-texture-with-a-sync-way
 because I needed to load the image synchronously, so the Apache Flex have 
several options: 1. use the case as it is, if possible; 2. create their own 
version; 3. adapt the code, so that can be compatible with async way.

  was:
TLF is a powerful framework however have a gap on a good image support or it's 
incompleted.

The developer can set a Sprite with bitmap data but when try to export the 
image source is exported as [Sprite object] and of course can't be restored by 
import.

I fixed this issue on my side, patching the original TLF export and import and 
I want to donate my patch to Apache Flex community.

In the method exportImage of the class TextLayoutExporter, replace:

{code:java}
if (image.source != null)
   output.@source = image.source;
{code}

By:

{code:java}
if (image.source != null)
{
        if (image.source is Sprite)
        {
                var sprite:Sprite = image.source as Sprite;
                var bitmapData:BitmapData = new BitmapData(sprite.width, 
sprite.height, true, 0x00FFFFFF);
                bitmapData.draw(sprite);

                var pngEncoder:PNGEncoder = new PNGEncoder();
                var base64Encoder:Base64Encoder = new Base64Encoder();
                base64Encoder.encodeBytes(pngEncoder.encode(bitmapData));
                output.@source = "data:image/png;base64," + 
base64Encoder.toString();
        }
        else
        {
                output.@source = image.source;
        }
}
{code}

And in the method createInlineGraphicFromXML of the class TextLayoutImporter, 
replace by this version:

{code:java}
public function createInlineGraphicFromXML(xmlToParse:XML):InlineGraphicElement
{                               
        var imgElem:InlineGraphicElement = new InlineGraphicElement();
        
        
parseStandardFlowElementAttributes(imgElem,xmlToParse,_ilgElementFormatImporters);
        
        if (_ilgFormatImporter.result)
        {
                var source:String = _ilgFormatImporter.result["source"];
                if (source != null && source.substr(0, 
"data:image/png;base64,".length) == "data:image/png;base64,")
                {
                        var base64Decoder:Base64Decoder = new Base64Decoder();
                        
base64Decoder.decode(source.substr("data:image/png;base64,".length));

                        var bitmapData:BitmapData = new 
PNGDecoder().decode(base64Decoder.toByteArray());

                        var image:Sprite = new Sprite();
                        image.graphics.beginBitmapFill(bitmapData, null, true, 
true);
                        image.graphics.drawRect(0, 0, bitmapData.width, 
bitmapData.height);
                        image.graphics.endFill();
                        imgElem.source = image;
                }
                else
                {
                        imgElem.source = _imageSourceResolveFunction != null ? 
_imageSourceResolveFunction(source) : source;
                }

                // if not defined then let InlineGraphic set its own default
                imgElem.height = _ilgFormatImporter.result["height"];
                imgElem.width  = _ilgFormatImporter.result["width"];
                /*      We don't support rotation yet because of bugs in the 
player. */         
                // imgElem.rotation  = 
InlineGraphicElement.heightPropertyDefinition.setHelper(imgElem.rotation,_ilgFormatImporter.result["rotation"]);
                imgElem.float = _ilgFormatImporter.result["float"];
        }

        return imgElem;
}
{code}

The only issue about this solution is that this import method relies on the 
third party PNGDecoder from this source: 
https://forum.starling-framework.org/topic/how-to-load-a-png-file-as-texture-with-a-sync-way
 because I needed to load the image synchronously, so the Apache Flex have 
several options: 1. use the case as it is, if possible; 2. create their own 
version; 3. adapt the code, so that can be compatible with async way.


> TLF - Import and export base64 string image
> -------------------------------------------
>
>                 Key: FLEX-35370
>                 URL: https://issues.apache.org/jira/browse/FLEX-35370
>             Project: Apache Flex
>          Issue Type: New Feature
>          Components: TLF
>    Affects Versions: Apache Flex 4.16.0
>         Environment: Flex + AIR + Text Layout Framework
>            Reporter: Hugo Ferreira
>
> TLF is a powerful framework however have a gap on a good image support or 
> it's incompleted.
> The developer can set a Sprite with bitmap data but when try to export the 
> image source is exported as [Sprite object] and of course can't be restored 
> by import.
> I fixed this issue on my side, patching the original TLF export and import 
> and I want to donate my patch to Apache Flex community.
> In the method exportImage of the class TextLayoutExporter, replace:
> {code:java}
> if (image.source != null)
>    output.@source = image.source;
> {code}
> By:
> {code:java}
> if (image.source != null)
> {
>       if (image.source is Sprite)
>       {
>               var sprite:Sprite = image.source as Sprite;
>               var bitmapData:BitmapData = new BitmapData(image.measuredWidth, 
> image.measuredHeight, true, 0x00FFFFFF);
>               bitmapData.draw(sprite);
>               var pngEncoder:PNGEncoder = new PNGEncoder();
>               var base64Encoder:Base64Encoder = new Base64Encoder();
>               base64Encoder.encodeBytes(pngEncoder.encode(bitmapData));
>               output.@source = "data:image/png;base64," + 
> base64Encoder.toString();
>       }
>       else
>       {
>               output.@source = image.source;
>       }
> }
> {code}
> And in the method createInlineGraphicFromXML of the class TextLayoutImporter, 
> replace by this version:
> {code:java}
> public function 
> createInlineGraphicFromXML(xmlToParse:XML):InlineGraphicElement
> {                             
>       var imgElem:InlineGraphicElement = new InlineGraphicElement();
>       
>       
> parseStandardFlowElementAttributes(imgElem,xmlToParse,_ilgElementFormatImporters);
>       
>       if (_ilgFormatImporter.result)
>       {
>               var source:String = _ilgFormatImporter.result["source"];
>               if (source != null && source.substr(0, 
> "data:image/png;base64,".length) == "data:image/png;base64,")
>               {
>                       var base64Decoder:Base64Decoder = new Base64Decoder();
>                       
> base64Decoder.decode(source.substr("data:image/png;base64,".length));
>                       var bitmapData:BitmapData = new 
> PNGDecoder().decode(base64Decoder.toByteArray());
>                       var image:Sprite = new Sprite();
>                       image.graphics.beginBitmapFill(bitmapData, null, true, 
> true);
>                       image.graphics.drawRect(0, 0, bitmapData.width, 
> bitmapData.height);
>                       image.graphics.endFill();
>                       imgElem.source = image;
>               }
>               else
>               {
>                       imgElem.source = _imageSourceResolveFunction != null ? 
> _imageSourceResolveFunction(source) : source;
>               }
>               // if not defined then let InlineGraphic set its own default
>               imgElem.height = _ilgFormatImporter.result["height"];
>               imgElem.width  = _ilgFormatImporter.result["width"];
>               /*      We don't support rotation yet because of bugs in the 
> player. */         
>               // imgElem.rotation  = 
> InlineGraphicElement.heightPropertyDefinition.setHelper(imgElem.rotation,_ilgFormatImporter.result["rotation"]);
>               imgElem.float = _ilgFormatImporter.result["float"];
>       }
>       return imgElem;
> }
> {code}
> The only issue about this solution is that this import method relies on the 
> third party PNGDecoder from this source: 
> https://forum.starling-framework.org/topic/how-to-load-a-png-file-as-texture-with-a-sync-way
>  because I needed to load the image synchronously, so the Apache Flex have 
> several options: 1. use the case as it is, if possible; 2. create their own 
> version; 3. adapt the code, so that can be compatible with async way.



--
This message was sent by Atlassian JIRA
(v6.4.14#64029)

Reply via email to