How to play a MovieClip x times - movieclip

The MovieClip class in the EaselJS module has a loop property which can be set to true or false, causing the movie clip to play infinitely or only once. http://www.createjs.com/docs/easeljs/classes/MovieClip.html
I need to play a movie clip (banner ad) three times. How can that be done?
This is the init function:
<script>
var canvas, stage, exportRoot;
function init() {
// --- write your JS code here ---
canvas = document.getElementById("canvas");
images = images||{};
var loader = new createjs.LoadQueue(false);
loader.addEventListener("fileload", handleFileLoad);
loader.addEventListener("complete", handleComplete);
loader.loadManifest(lib.properties.manifest);
}
function handleFileLoad(evt) {
if (evt.item.type == "image") { images[evt.item.id] = evt.result; }
}
function handleComplete(evt) {
exportRoot = new lib.banner_728x90();
stage = new createjs.Stage(canvas);
stage.addChild(exportRoot);
stage.update();
stage.enableMouseOver();
createjs.Ticker.setFPS(lib.properties.fps);
createjs.Ticker.addEventListener("tick", stage);
}
</script>

There is currently no loop count support, nor any events from MovieClip indicating when an animation finishes. The latter isn't a bad idea, feel free to log a bug in GitHub.
One solution you could use would be to dispatch some custom events from a timeline script in Animate:
this.dispatchEvent("walkend");
Then you can listen for the event, and handle it yourself.
var loopCount = 0;
exportRoot.myClip.on("walkend", function(event) {
loopCount++;
if (loopCount > 2) {
doSomething();
event.remove(); // No longer get this event.
}
});
Hope that helps.

Related

How to execute some code whenever the user interacts with the map?

I have an OpenLayers 3.9.0 map. I also have a pair of LonLat coordinates that I am tracking from an external source and updating onto the map. I am continuously re-centering the map on these coordinates:
function gets_called_when_I_have_updated_coords() {
map.getView.setCenter(coords);
}
What I want is to disable this auto-centering whenever the user interacts with the map. In other words, I want this:
var auto_center = true;
function gets_called_when_I_have_updated_coords() {
if (auto_center) {
map.getView.setCenter(coords);
}
}
function user_started_interacting() {
auto_center = false;
}
// But where should this function be attached to?
// where.on('what?', user_started_interacting);
I don't know how to detect a user interaction.
I expected that the default interactions had some kind of event, so that when the user starts dragging/rotating/zooming the map, an event would be triggered and my code would run. I could not find such event.
Here, the user is dragging:
map.on('pointermove', function(evt){
if(evt.dragging){
//user interacting
console.info('dragging');
}
});
Here, the user is changing resolution:
map.getView().on('change:resolution', function(evt){
console.info(evt);
});
UPDATE
Some options to detect keyboard interaction:
//unofficial && undocumented
map.on('key', function(evt){
console.info(evt);
console.info(evt.originalEvent.keyIdentifier);
});
//DOM listener
map.getTargetElement().addEventListener('keydown', function(evt){
console.info(evt);
console.info(evt.keyIdentifier);
});
A fiddle to test.
An other approach could be to listen to the pointerdown and pointerup events occurring on the map and while the down is in action, disable your auto-center feature.
map.on('pointerdown', function() {
auto_center = false;
}, this);
map.on('pointerup', function() {
auto_center = true;
}, this);
This approach may need more work, but it would be a start. Thoughts ?
As an workaround, I can attach an event to a change in the view:
map.getView().on('change:center', function(ev){…});
But I must take extra steps to distinguish from code-initiated changes from user-initiated ones. The complete code looks somewhat like this:
var auto_center = true;
var ignore_change_events = false;
function gets_called_when_I_have_updated_coords() {
if (auto_center) {
ignore_change_events = true;
map.getView.setCenter(coords);
ignore_change_events = false;
}
}
map.getView().on('change:center', function() {
if (ignore_change_events) {
return;
}
auto_center = false;
});
Note that this approach breaks if any animation is used (and there is no callback or event for when an animation finishes).
Depending on your project, you may want to try either this solution or Jonatas Walker's solution.

How to set currentTime in video.js in Safari for iOS

Other is ok, but the setting of currentTime:
I tried some ways like:
videojs("example_video_1", {}, function() {
this.currentTime(200);
this.play();
});
And this is not working.
videojs("example_video_1").ready(function(){
this.currentTime(200);
});
This also doesn't work.
var dom = document.getElementById('example_video_1');
dom.addEventListener("loadedmetadata", function() {
dom.currentTime = 100;
}, false); // ok for no video.js
videojs(dom);
Not working. Even reverse the line of addEventListener and init videojs.
And I tried the videojs event.
var player = videojs("example_video_1");
alert(player.addEvent);
alert(player.addEventListener);
these API all not exists, so how do I bind Event in videojs?
This is how I got the video playback on a defined position at startup (it removes the problem that the video first started and only afterwards jumped to a video position):
$(document).ready(function()
{
var timecode = 120;
var initdone = false;
// wait for video metadata to load, then set time
video.on("loadedmetadata", function(){
video.currentTime(timecode);
});
// iPhone/iPad need to play first, then set the time
// events: https://www.w3.org/TR/html5/embedded-content-0.html#mediaevents
video.on("canplaythrough", function(){
if(!initdone)
{
video.currentTime(timecode);
initdone = true;
}
});
}); // END ready
Oh, by lucky, i found an example in https://github.com/videojs/video.js
var dom = document.getElementById('example_video_1');
videojs(dom, {}, function(){
this.on('loadedmetadata', function(){
this.currentTime(500);
});
});
this is work, the API to bind event is player.on('event', fn);
videojs is cool~

ajaxStart() on forge.request.ajax

For showing a loading screen, we listen to the jQuery ajaxStart() event the following way:
$(document).ajaxStart(function() {
//show loading screen
});
However, this event doesn't get fired sending forge.reques.ajax() requests (at least is seems so).
Is there already a solution like that for forge or do I have to write that event by hand?
This doesn't currently exist in forge, but its pretty easy to implement:
var onAjaxStart = function () {
// show loading screen
}
var onAjaxEnd = function () {
// hide loading screen
}
var myAjax = function (params) {
onAjaxStart();
var success = params.success;
params.success = function () {
onAjaxEnd();
success && success();
};
forge.request.ajax(params);
}
Then us myAjax(...) instead of forge.request.ajax(...).

Disable eventlistener temporarily till animation completes

I'm working on a basic flash fight game. I'm not a developer so i'm new to actionscript except that i have some background knowledge about coding from my course.
The problem is-
There are about 6 fighting moves and i want to disable all 6 key_down events till the animation completes. And all 6 animations have different time frames. Can some1 just help me out with this?
stage.addEventListener(KeyboardEvent.KEY_DOWN, enterKeyHandler);
function enterKeyHandler(event:KeyboardEvent):void {
if (event.keyCode == Keyboard.B) {
gotoAndPlay(252);}
if (event.keyCode == Keyboard.V) {
gotoAndPlay(259);}
I have put down only 2 of them but there 6 in total.
I would use a public static flag , ex:
keyboardDisabled:Boolean = false;
While you play your animations you could set this to true, and inside the function which listens to keyboard events just check if keyboard is disabled and return right away.
Some code would look like
public static var keyboardDisabled:Boolean = false;
stage.addEventListener(KeyboardEvent.KEY_DOWN, enterKeyHandler);
function enterKeyHandler(event:KeyboardEvent):void {
if ( keyboardDisabled )
return;
if (event.keyCode == Keyboard.B) {
gotoAndPlay(252);}
if (event.keyCode == Keyboard.V) {
gotoAndPlay(259);
}
Then in the frame where your animation begin
keyboardDisabled = true;
And on animation end
keyboardDisabled = false;

xpcom/jetpack observe all document loads

I write a Mozilla Jetpack based add-on that has to run whenever a document is loaded. For "toplevel documents" this mostly works using this code (OserverService = require('observer-service')):
this.endDocumentLoadCallback = function (subject, data) {
console.log('loaded: '+subject.location);
try {
server.onEndDocumentLoad(subject);
}
catch (e) {
console.error(formatTraceback(e));
}
};
ObserverService.add("EndDocumentLoad", this.endDocumentLoadCallback);
But the callback doesn't get called when the user opens a new tab using middle click or (more importantly!) for frames. And even this topic I only got through reading the source of another extension and not through the documentation.
So how do I register a callback that really gets called every time a document is loaded?
Edit: This seems to do what I want:
function callback (event) {
// this is the content document of the loaded page.
var doc = event.originalTarget;
if (doc instanceof Ci.nsIDOMNSHTMLDocument) {
// is this an inner frame?
if (doc.defaultView.frameElement) {
// Frame within a tab was loaded.
console.log('!!! loaded frame:',doc.location.href);
}
else {
console.log('!!! loaded top level document:',doc.location.href);
}
}
}
var wm = Cc["#mozilla.org/appshell/window-mediator;1"].getService(Ci.nsIWindowMediator);
var mainWindow = wm.getMostRecentWindow("navigator:browser");
mainWindow.gBrowser.addEventListener("load", callback, true);
Got it partially from here: https://developer.mozilla.org/en/XUL_School/Intercepting_Page_Loads
#kizzx2 you are better served with #jetpack
To the original question: why don't you use tab-browser module. Something like this:
var browser = require("tab-browser");
exports.main = function main(options, callbacks) {
initialize(function (config) {
browser.whenContentLoaded(
function(window) {
// something to do with the window
// e.g., if (window.locations.href === "something")
}
);
});
Much cleaner than what you do IMHO and (until we have official pageMods module) the supported way how to do this.
As of Addon SDK 1.0, the proper way to do this is to use the page-mod module.
(Under the hood it's implemented using the document-element-inserted observer service notification, you can use it in a regular extension or if page-mod doesn't suit you.)

Resources