A Flash Developer Resource Site

Results 1 to 18 of 18

Thread: Swf Exports Image of Itself... Can PHP Save It on the Site?

  1. #1
    Musical chair sumwungye's Avatar
    Join Date
    Jan 2008
    Location
    Planet Earth, third planet from the Sun
    Posts
    287

    Question Swf Exports Image of Itself... Can PHP Save It on the Site?

    Hello all,

    So I recently found this article with some interesting code that does what I once thought was impossible. Basically, it creates a jpeg version of the swf with actionscript (And then sends it to PHP, pixel by pixel).

    (The Article)

    Of course, the image will only stay on the page as long as the POST data exists.

    However, there's one thing I'm not sure of how to do, that'd definitely be useful. I want the PHP file with the jpeg to save the jpeg as an automatically controlled (with variables) name ( with a .jpg at the end, of course). And rather than saving to the user's computer, is it possible to save it directly to the site directory?

    So basically, save it to the site's files' folder with a name I can control automatically.

    Thanks a lot to whoever can help!
    --SumWunGye

  2. #2
    Senior Member
    Join Date
    Apr 2004
    Location
    LA
    Posts
    349
    if you've got your actionscript talking to the PHP server, try using file_put_contents to write the contents of your $_POST var to a file on your server.

    The web server (which is 'apache' on some machines, 'nobody' on some, 'www-data' on others, etc.) will need write permission for the directory where you want to write the file.

    Once you write the file, try viewing it in a browser or something.
    Write multiplayer games with FlashMOG 0.3.1
    Try the MyPlan Salary Calculator

  3. #3
    Developing For Dunkets mneil's Avatar
    Join Date
    Mar 2007
    Location
    Lincoln City
    Posts
    2,156
    I believe fileReference can save a png from the flash stage in AS3 directly. Maybe it isn't the fileReference class (I just read this here on the forum a few days ago) but as3 can save a screenshot on it's own; no php needed. Sephiroths way gets to be very slow as the stage size increases..... but it is cool. Sephiroths example outputs it, but you can change it to save it to the server as well, or use php headers to output the type as an image for download.

    Okay, fileReference wasn't it. I couldn't give you such a vague answer, chickity check this out:
    http://stackoverflow.com/questions/9...nshot-of-stage.
    It's still sending to php but is likely faster than sephiroths since AS3 is faster and jpgencode is also quicker than the old F8 method.
    http://code.mneilsworld.com/
    Text Effects | Bubbles | Dynamic Resize
    4 weeks , 20 papers ... thats 2 dollars .....Caassshhh!

  4. #4
    Musical chair sumwungye's Avatar
    Join Date
    Jan 2008
    Location
    Planet Earth, third planet from the Sun
    Posts
    287
    Hi Sneakyimp and Mneil and thanks for the responses

    file_put_contents looks like something that may work, though I'll have to test it. (And before I test it, I need to consolidate all the code into one swf without actionscript files externally...because I swear, I have ocd.)

    And actionscript 3 won't work, because I'm trying to send the screenshots from a swf I made already in as2, so I'd rather keep it in as2 than having to rewrite it in as3.

    Thanks again to both of you!
    --SumWunGye

  5. #5
    Musical chair sumwungye's Avatar
    Join Date
    Jan 2008
    Location
    Planet Earth, third planet from the Sun
    Posts
    287
    Hello again

    So I've been working on getting getPixel to save the color information into arrays inside my Flash project. (Meaning, I still haven't made it to the PHP part yet.) Right now, my problem is doing so efficiently.

    In order, this is basically what happens:
    >use a do-while loop to put the first row of colors into an array, column-by-column.
    >gotoAndPlay an actionless frame (to give Flash time to think, and so it doesn't freeze, having to output tens of thousands of pixels of color).
    >go back and repeat with the next row.

    Even though I give Flash time to process the heavy information being thrown at it with the actionless frames, it's still outputting at about 1 row per second, all the while making Flash mostly unresponsive, and slowing down my computer, and with 228 rows and multiple frames, that just won't do.

    In the article I posted earlier, (Here it is again,) they use a component loading bar (I think?) and likely code it completely differently. Problem is, I can't seem to find the location of the code in the example that I can use as a foundation for making my code more efficient.

    So I ask you, how could I change what "basically happens" to make the code run quickly like in that article?
    --SumWunGye

  6. #6
    Senior Member
    Join Date
    Apr 2004
    Location
    LA
    Posts
    349
    One row per second sounds impossibly slow. I think when he refers to using setInterval to avoid stressing flash, he's not talking about making his code more efficient, but rather breaking up the entire chore of capturing the movie so that he doesn't get the 'script running too long' error.

    Looks to me like what he's doing is using setInterval to repeatedly call a function that renders a single row. After it renders that row, it checks to see if all the rows have been completed.

    He's not using a do/while loop, he's using a for loop.
    Write multiplayer games with FlashMOG 0.3.1
    Try the MyPlan Salary Calculator

  7. #7
    Musical chair sumwungye's Avatar
    Join Date
    Jan 2008
    Location
    Planet Earth, third planet from the Sun
    Posts
    287
    PHP Code:
    import flash.display.*;
    var 
    bmp:BitmapData = new BitmapData(228348false);
    bmp.draw(_root); 
    I realized what was making it so slow!

    After adding setInterval into the mix of code to capture pixels, it probably sped up by about 2x. Still, this was impossibly slow. After a lot of experimentation, I discovered that the code at the top of this post was what made it so slow: not the fact that it was in there to begin with, but the fact that I was looping it in the do/while loop (I wrote the code differently than Sephiroth's, so I changed it around a bit) along with the actual capturing code. All I really needed to do was take these 3 lines of code and use them once, THEN go with the rest of the code looped and such.

    Thanks a lot to everyone, especially to sneakyimp, for it should be smooth sailing from here. I'll let you know if that changes, hah.
    --SumWunGye

  8. #8
    Musical chair sumwungye's Avatar
    Join Date
    Jan 2008
    Location
    Planet Earth, third planet from the Sun
    Posts
    287
    Okay, here's a strange thing that's been happening as I prepare to send the pixels through to PHP.

    Code:
    variables = new Array();
    variables[0] = "You";
    variables[1] = "Test";
    This code, in Flash, creates an array with two items. Then, it sends it to PHP via POST, and then PHP loads it and echoes it. Or at least, that's what you'd think'd happen...

    PHP Code:
    echo $_POST['variables'][0];
    echo 
    $_POST['variables'][1]; 
    Expecting it to output "You" and "Test" respectively, I was surprised to see it output "Y" and "o" respectively. It's as if the array changed into a string, only keeping the first item. (When I echo $_POST['variables']; it does not show the "Test" part of it.)

    Am I missing something? Thanks!
    --SumWunGye

  9. #9
    Senior Member
    Join Date
    Apr 2004
    Location
    LA
    Posts
    349
    Sending an array to PHP from flash via POST might be a bit more involved than you'd like. It sounds like you have only sent 'You' to PHP. Show us your Actionscript code that does the POST.
    Write multiplayer games with FlashMOG 0.3.1
    Try the MyPlan Salary Calculator

  10. #10
    Musical chair sumwungye's Avatar
    Join Date
    Jan 2008
    Location
    Planet Earth, third planet from the Sun
    Posts
    287
    Code:
    getURL("makeacard.php", "_self", "POST");
    stop();
    makeacard.php is also the page where the flash is embedded, so the getURL takes you to the same page, just with the POST data.

    If there is a way to have arrays sent via PHP or if I'm just missing something...yeah. If worse comes to worse, I can just put the array's content into one variable, then explode it when it gets to PHP.
    --SumWunGye

  11. #11
    Senior Member
    Join Date
    Apr 2004
    Location
    LA
    Posts
    349
    As I understand it, using getURL to send variables will try to send all of your root-level vars to the url you specify. Looks to me like this is not working properly as it is only sending the first element of your array or perhaps it's sending a comma-separated list or something. In either case, it doesn't appear to work properly.

    You might try this in makeacard.php instead:
    PHP Code:
    <?
    print_r($_POST);
    ?>
    That will give you a better idea of what exactly is defined in your $_POST var as it will recursively output the whole thing.

    I would recommend using a LoadVars object. Or better yet, use sephiroth's AS3 serializer.
    Write multiplayer games with FlashMOG 0.3.1
    Try the MyPlan Salary Calculator

  12. #12
    Musical chair sumwungye's Avatar
    Join Date
    Jan 2008
    Location
    Planet Earth, third planet from the Sun
    Posts
    287
    Okay, so I managed to fix the sending of the array "variables" (as it was the only array PHP was not fully receiving). I don't quite know how I did, but I did.

    Though, as it seems, PHP still doesn't receive arrays inside of arrays (or arrays inside of arrays inside of arrays, in my case). With print_r(), arrays appear as...

    [variablename] => item,item2

    ...while an array with only arrays inside appear as...

    [variablename] =>

    It may have to do with the fact that inside the first array are 348 different arrays, each with 228 different arrays inside, each with one hex number inside. (Too much info to send? Maybe...)

    Anyways, I'll probably need to switch the arrays-inside-arrays-inside-arrays to really long, explodable variables.

    Thanks again for the help
    --SumWunGye

  13. #13
    Senior Member
    Join Date
    Apr 2004
    Location
    LA
    Posts
    349
    Sounds to me like you could really use the ByteArray object in AS3. You might want to consider creating a string from bitwise operations or something? It's possible to send nested arrays intact, but the overhead is going to be substantial!
    Write multiplayer games with FlashMOG 0.3.1
    Try the MyPlan Salary Calculator

  14. #14
    Musical chair sumwungye's Avatar
    Join Date
    Jan 2008
    Location
    Planet Earth, third planet from the Sun
    Posts
    287
    Oh wow, board.flashkit.com went down after I loaded this page, but right before I posted my response -_- Ohhhhhboy.

    So can I use this AS3 ByteArray object with this project (which I made in AS2)?

    If so, I'll probably need to understand better what it does. From what I think I understand, it takes arrays and arrays inside of arrays and encodes them? Then, when loaded into PHP, they can be decoded and used in their original form?

    Thanks!
    --SumWunGye

  15. #15
    Senior Member
    Join Date
    Apr 2004
    Location
    LA
    Posts
    349
    The ByteArray object only exists as of Actionscript 3 so you won't be able to use it in your AS2 project. A ByteArray is not useful for sending arrays of arrays, it is useful for sending raw binary data. It's literally an array of bytes, nothing more.

    Without the ByteArray object, you must perform exactly the type of thing you are doing, which is sending an array of ints or something. I linked sephiroth's serializer class, which can easily send nested arrays and I'm guessing you didn't look at it.

    Sending a bitmap image this way will mean a lot of overhead. You'll probably send a at least twice as much data as is contained in the raw bitmap image.
    Write multiplayer games with FlashMOG 0.3.1
    Try the MyPlan Salary Calculator

  16. #16
    Musical chair sumwungye's Avatar
    Join Date
    Jan 2008
    Location
    Planet Earth, third planet from the Sun
    Posts
    287
    Well, I did read the description, and I guess I was sort of right about the encoding/decoding part (into/from binary).

    I would try it out, but I've already started rearranging my code to take the arrays out of the arrays out of the arrays and make a whole lot of uniquely-named explodable strings.

    Thanks again so much for the help Though, looking ahead, file_put_contents (according to php.net) can only put arrays or variables into a file, but I don't know how it'll work with the image.
    --SumWunGye

  17. #17
    Senior Member
    Join Date
    Apr 2004
    Location
    LA
    Posts
    349
    You should absolutely, definitely, give the serializer class a try. It will save you so much time in the future because you can create complex arrays of data in either php or flash and send it back and forth--intact--very easily. I think learning this class would be a better use of your time then refactoring your code.

    Download the latest AS2 version of the serializer class and extract the archive. there's a folder named 'it' among the unzipped files. Put that folder in the directory where you have your FLA file.

    From there it's really very simple:
    code:

    // import the class
    // relative path to file should be it/sephiroth/Serializer.as
    import it.sephiroth.Serializer

    // create an instance of the class:
    var serial:Serializer = new Serializer();

    // let's assume all your data is in an array var called "myArray"
    var myArray:Array = new Array();
    myArray[0] = "hello there";
    myArray[1] = "hello again";
    myArray[2] = new Array();
    myArray[2][0] = 'nested array item 1';
    myArray[2][1] = 'nested array item 2';
    myArray[2][2] = 'nested array item 3';
    myArray[2][3] = new Array(); // a doubly-nested one!
    myArray[2][3][0] = 'omg what madness is this?';
    myArray[2][3][1] = 'stop i am going to be sick';
    myArray[2][3][2] = '<Puking>RAAALLLLFFF</Puking>';



    var lvSend:LoadVars = new LoadVars();
    // "bitmapData" will be the associative index of our data in $_POST
    // on the php side
    lvSend.bitmapData = serial.serialize(myArray);
    var lvRecv:LoadVars = new LoadVars();
    lvRecv.onLoad=function(success) {
    if(success){
    trace(lvRecv);
    var incomingData = serial.unserialize(lvRecv.responseData);
    if (incomingData['success']) {
    trace('success!');
    trace(incomingData['message1']);
    } else {
    trace('failure to unserialize on the server');
    trace(incomingData['message1']);
    }
    }
    }
    lvSend.sendAndLoad("makeacard.php", lvRecv, "POST");



    Then in your PHP file, you could do something like this:
    PHP Code:
    <?php
    function myErrorHandler($errno$errstr$errfile$errline){
        
    file_put_contents('error.txt''#' $errno ':' $errstr "\nFILE: " $errfile "LINE: " $errlineFILE_APPEND);
        return 
    true;
    }
    $old_error_handler set_error_handler("myErrorHandler");


    $serialized_data $_POST['bitmapData'];
    $bitmap_data unserialize($serialized_data);

    if (!
    $bitmap_data) {
      
    $success FALSE;
    } else {
      
    $success TRUE;
    }

    // === do all kinds of stuff with your data here ===

    // generate a reponse to send back to flash so you can
    // let your flash movie know if it was successful or not
    $response = array();
    $response['message1'] = 'Here is one message';
    $response['message2'] = 'Here is some other message';
    $response['output_file'] = 'This might contain the location of the output file';
    $response['success'] = $success;
    // "responseData" will be the property of lvRecv containing your data
    // in your flash movie
    echo "responseData=" urlencode(utf8_encode(serialize($response)));
    ?>
    IMPORTANT: magic_quotes_gpc need to be disabled on the server or this won't work. If you can't disable magic_quotes_gpc then you'll have to call strip_slashes on $_POST['bitmapData'].

    As for the php code to turn this complex data into an image file, that will depend on the structure of the data coming from your flash movie. I have no idea what this data looks like. getPixel apparently returns a number, right?
    Write multiplayer games with FlashMOG 0.3.1
    Try the MyPlan Salary Calculator

  18. #18
    Senior Member
    Join Date
    Apr 2004
    Location
    LA
    Posts
    349
    You'll probably end up using imagecolorallocate on each incoming pixel to create a color value and then imagefilledrectangle to fill a one-pixel rectangle for that pixel.
    Write multiplayer games with FlashMOG 0.3.1
    Try the MyPlan Salary Calculator

Tags for this Thread

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  




Click Here to Expand Forum to Full Width

HTML5 Development Center