Forums  

Go Back   Forums > Talk > General FPP Discussion

Reply
 
Thread Tools Display Modes
  #1  
Old 10-21-2007, 08:57 AM
Jason Villmer Jason Villmer is offline
Banned
 
Join Date: Oct 2007
Posts: 28
Downloads: 0
Uploads: 0
Smile I hope this helps some people..

Like many of you I think, I've often found myself somewhat frustrated while trying to find answers to things I would consider 'fundamental' or 'simple'. Denis has really gone out of his way to assist me on all occasions when I've had questions but, despite his personal help, I still find myself staring at actionscript or .xml trying to find the right combinations. Although I usually find the answers to what I'm looking for, either by raw trial-and-error, through suggestions by Denis or by someone on this forum, I know that there are a lot of you out there who are going through the same thing, so when I find an answer to something I know others are looking for I try to post it.

The most recent thing I've found was how to script (actionscript) buttons in Flash to control other elements of the FPP application, such as loading a new panorama, controlling other hotspots or changing and tweening parameters.

So, I've decided to share it with everyone who hasn't yet found this information. I have heard that there are other methods of doing this. Some of it is documented in the tutorials and some isn't.

Here you go:

Lets say you want to create flash buttons (using actionscript version 3) that, when clicked, will control something in the main FPP. First you will need to add a 'spot' or 'box' hotspot in your .xml document such as this:

<spot id="map" url="map.swf" static="1" alignX="00" alignY="-0.48" depth="10" scale="0.65" salign="LM"/>

This map.swf file contains 4 buttons that, when clicked, will load different panoramas.
In the Flash .fla file the 4 buttons are labeled as follows: b_piazza, b_plebiscito, b_viaroma and b_umberto
In a layer, above all visual elements I have added actionscript in one frame. Here it is:

// Use the same name in spots.xml: <global controller="lc_test">
// Better use different controller names for different panorama applications
var controllerName:String = "lc_test";

// Master slot name:
var masterSlot:String;
// Slave slot name:
var slaveSlot:String;

// Begin of connection code (better use it as is).
var dumpSlot = controllerName+"_dump_"+Math.random();
var _lc:LocalConnection = new LocalConnection();
_lc.allowDomain("*");
_lc.connect(dumpSlot);
_lc.addEventListener(StatusEvent.STATUS, onStatus);
_lc.client = this;
function onStatus(info) {
if (info.level == "error") {
trace("No master connection detected.");
_lc.close();
_lc = null;
}
};
function setSlot(slot) {
masterSlot = controllerName+"_master_"+slot;
slaveSlot = controllerName+"_slave_"+slot+"_"+Math.random();
_lc.close();
_lc.connect(slaveSlot);
trace("set slave: "+slaveSlot);
startWatch();
};
_lc.send(controllerName+"_master_0", "getSlot", dumpSlot);
// end of connecion code

var panoName:String; // current pano name
var panoBusy:Boolean; // true if panorama is loading or a transition effect is in process
var timer:Timer; // timer

// start watching parameters "panoName" and "panoBusy":
function startWatch () {
timer = new Timer(500);
timer.addEventListener(TimerEvent.TIMER, sendQuery);
timer.start();
}
// send query:
function sendQuery (event:Event) {
// 3rd argument is array of askable parameters, 4th and 5th are connection name to callback
_lc.send(masterSlot, "getParams", ["pano.panoName","pano2.panoName"], slaveSlot, "callback");
}

// REMOVE EVERYTHING BELOW AND REPLACE IT WITH YOUR OWN INFORMATION

b_piazza.addEventListener(MouseEvent.CLICK, transfer);
b_plebiscito.addEventListener(MouseEvent.CLICK, transfer2);
b_umberto.addEventListener(MouseEvent.CLICK, transfer3);
b_viaroma.addEventListener(MouseEvent.CLICK, transfer4);


function transfer (e:Event) {
if (masterSlot != null) {
_lc.send(masterSlot, "execute", "loadPano(piazza,,none)");
}
}

function transfer2 (e:Event) {
if (masterSlot != null) {
_lc.send(masterSlot, "execute", "loadPano(plebiscito,,none)");
}
}

function transfer3 (e:Event) {
if (masterSlot != null) {
_lc.send(masterSlot, "execute", "loadPano(umberto,,none)");
}
}

function transfer4 (e:Event) {
if (masterSlot != null) {
_lc.send(masterSlot, "execute", "loadPano(viaroma,,none)");
}
}

-----------------------------------------------

Don't be afraid of all of this code, just copy it and place it into a single frame above your content.
So, very simply here's the deal. For each labeled button such as 'b_plebiscito' you will create code that will 'listen' for mouse events (such as mouse clicks etc..)

The example above would be: b_piazza.addEventListener(MouseEvent.CLICK, transfer);
Now, the 'transfer' at the end of this line refers to a function I've made that will provide specific instructions on what to do when the b_piazza button is clicked.

I've then created the 'transfer' function:

function transfer (e:Event) {
if (masterSlot != null) {
_lc.send(masterSlot, "execute", "loadPano(piazza,,none)");
}
}

Now, what is important is what comes after the 'execute' statement. In my case I've put "loadPano(piazza,1000, fade)". That means that when it is clicked it will tell the main panorama to load the pano (equirectangular) named piazza. (with a 1000 delay using the fade transition). If, for example you wanted to tell another hotspot named 'myhotspot' to change its saturation to 2, you would simple replace the "loadPano(piazza,,none)" statement with this "myhotspot.saturation=2". Thats it. Good Luck.

You can see this at: http://www.villmer.com/napoli

Last edited by Jason Villmer; 10-21-2007 at 09:09 AM.
Reply With Quote
  #2  
Old 10-21-2007, 03:12 PM
zleifr's Avatar
zleifr zleifr is offline
Senior Member
 
Join Date: May 2007
Posts: 609
Downloads: 0
Uploads: 0
Default

Hey, thanks for sharing that code, we need lots more of this!

Zephyr
Reply With Quote
  #3  
Old 10-25-2007, 01:05 PM
davcom davcom is offline
Junior Member
 
Join Date: Aug 2007
Posts: 15
Downloads: 0
Uploads: 0
Default

Hey, nice one, BUT, how do you populate the masterSlot variable? It always remains = null on mine... And looks like you never call setSlot() neither...
Reply With Quote
  #4  
Old 10-25-2007, 07:43 PM
viking0 viking0 is offline
Junior Member
 
Join Date: Oct 2007
Posts: 24
Downloads: 0
Uploads: 0
Default

Jason as you can controll panotrough controller.swf is that possible to control EmbedPano.fla?
thank you.
Reply With Quote
  #5  
Old 10-25-2007, 09:39 PM
zleifr's Avatar
zleifr zleifr is offline
Senior Member
 
Join Date: May 2007
Posts: 609
Downloads: 0
Uploads: 0
Default

davcomm: the line that defines masterSlot got clipped. get it from controller.fla The setSlot function is not called by anything in that script. It is called by fpp (hotspots.swf I believe) in response to the lc.send with getSlot in the arguments.

viking: yes it is possible to use that same script in an embedPano setting. The only modification that I know of which you need to make is to establish a connection to the pano object (Glassmeter.fla has an example of this) and set up a timer watching for pano.parsed to be true BEFORE you start the localConnection. Otherwise the localConnection fails because the pano hasn't loaded fully enough to be able to respond.
Reply With Quote
  #6  
Old 10-31-2007, 01:15 PM
marktold marktold is offline
Junior Member
 
Join Date: Oct 2007
Posts: 18
Downloads: 0
Uploads: 0
Question

@zleifr

I have the same problem as davcom. setSlot(slot) does not seem to be called and masterSlot is therefore empty.

I tested it like this

function transfer (event:Event=null) {
if (masterSlot != null) {
_lc.send(masterSlot, "execute", "loadPano(movies/falcon2000_big,,none)");
}
else
{
myNaviStrip.myButton1.visible = false;
}
}

My button disaspears so masterSlot seems to be null.

Any idea.

Regards Markus
Reply With Quote
  #7  
Old 10-31-2007, 05:18 PM
zleifr's Avatar
zleifr zleifr is offline
Senior Member
 
Join Date: May 2007
Posts: 609
Downloads: 0
Uploads: 0
Default

Sorry, you're right. masterSlot and slaveSlot are set by the setSlot function. If setSlot is never being called, my guess is that the code is being loaded to soon because you are trying to use the localConnection in a plugin, as opposed to an swf loaded in a hotspot (swf's loaded in hotspots don't have this problem as hotspots.swf is obviously already loaded before the code in the individual spots starts running, while your plugin loads in parallel with hotspots.swf). IF you are not running this as a plugin, disregard the entire rest of this post, and I don't know what the problem is (install the flash debug player and check the log and watch for the error messages).

What I have done before is to check if the panorama is parsed, which is probably not the perfect thing to be checking for, but it worked (ideally you'd probably check the hotspots object: externals.hotspots.hotspots_obj or something like that....) Below is basically the code I used, but note that I just put this together now, as I can't find the code I used then, so there is possibly an error or two in there, but all this code is copied and pasted from the controller and glassMeter.

var pano:Object=null;
var dumpSlot = controllerName+"_dump_"+Math.random();
var _lc:LocalConnection = new LocalConnection();
var controllerName:String = "lc_test";

// Master slot name:
var masterSlot:String;
// Slave slot name:
var slaveSlot:String;

//this function is called when a new pano is loaded
function newPano (link:Object) {
pano = link;
if (pano.loadersState!=null) {
timer = new Timer(500);
timer.addEventListener(TimerEvent.TIMER, checkPanoParsed);
timer.start();
}
}

function checkPanoParsed (e:Event) {
if ( pano.parsed ) {
startLocalConnection();
}
}

function onStatus(info) {
if (info.level == "error") {
trace("No master connection detected.");
_lc.close();
_lc = null;
}
};
function setSlot(slot) {
masterSlot = controllerName+"_master_"+slot;
slaveSlot = controllerName+"_slave_"+slot+"_"+Math.random();
_lc.close();
_lc.connect(slaveSlot);
trace("set slave: "+slaveSlot);
startWatch();
};

startLocalConnection () {
_lc.allowDomain("*");
_lc.connect(dumpSlot);
_lc.addEventListener(StatusEvent.STATUS, onStatus);
_lc.client = this;
_lc.send(controllerName+"_master_0", "getSlot", dumpSlot);
}
Reply With Quote
  #8  
Old 10-31-2007, 06:46 PM
Nate Nate is offline
Senior Member
 
Join Date: Sep 2007
Posts: 112
Downloads: 0
Uploads: 0
Default

code works for me, but how do I load specific parameters into the new pano? Thanks for the help!
Reply With Quote
  #9  
Old 10-31-2007, 06:58 PM
zleifr's Avatar
zleifr zleifr is offline
Senior Member
 
Join Date: May 2007
Posts: 609
Downloads: 0
Uploads: 0
Default

change the xml file or put the parameters in the loadPano command:

loadPano(panoName=panoramas/nature&xml_file=nature.xml) (loads panorama with a new parameters file)

loadPano(panoName=nature&pan=100&tilt=-10) (loads panorama with initial pan=100 and tilt=-10)
Reply With Quote
  #10  
Old 10-31-2007, 07:28 PM
Nate Nate is offline
Senior Member
 
Join Date: Sep 2007
Posts: 112
Downloads: 0
Uploads: 0
Default

missed the "panoName" part. Thanks so much. Now I can get the panos to change, but the loading fail. So much to learn still!
Reply With Quote
Reply

Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Forum Jump


All times are GMT. The time now is 01:05 AM.


Powered by vBulletin® Version 3.7.1
Copyright ©2000 - 2017, Jelsoft Enterprises Ltd.