I'm trying to update Annotorious (https://annotorious.github.io/#) to the latest version of Closure / Javascript.
When I compile it with "SIMPLE" optimizations, dot-syntax functions seem to disappear when goog.events.listen callbacks are invoked. Here's an example:
Here's the "main":
goog.provide('annotorious.Annotorious');
...
/**
* The main entrypoint to the application. The Annotorious class is instantiated exactly once,
* and added to the global window object as 'window.anno'. It exposes the external JavaScript API
* and internally manages the 'modules'. (Each module is responsible for one particular media
* type - image, OpenLayers, etc.)
* @constructor
*/
annotorious.Annotorious = function() {
/** @private **/
this._isInitialized = false;
/** @private **/
this._modules = [ new annotorious.mediatypes.image.ImageModule() ];
...
In another file (they're all compiled together), we have this:
goog.provide('annotorious.Annotation');
goog.require('annotorious.shape');
/**
* A 'domain class' implementation of the external annotation interface.
* @param {string} src the source URL of the annotated object
* @param {string} text the annotation text
* @param {annotorious.shape.Shape} shape the annotated fragment shape
* @constructor
*/
annotorious.Annotation = function(src, text, shape) {
this.src = src;
this.text = text;
this.shapes = [ shape ];
this['context'] = document.URL; // Prevents dead code removal
}
So we start up the code, and at some point we end in the editor for the annotation, listening for a "Save" button:
goog.provide('annotorious.Editor');
....
/**
* Annotation edit form.
* @param {Object} annotator reference to the annotator
* @constructor
*/
annotorious.Editor = function(annotator) {
this.element = goog.soy.renderAsElement(annotorious.templates.editform);
....
/** @private **/
//this._btnSave = goog.dom.query('.annotorious-editor-button-save', this.element)[0];
this._btnSave = this.element.querySelector('.annotorious-editor-button-save');
...
goog.events.listen(this._btnSave, goog.events.EventType.CLICK, function(event) {
event.preventDefault();
var annotation = self.getAnnotation();
annotator.addAnnotation(annotation);
annotator.stopSelection();
if (self._original_annotation)
annotator.fireEvent(annotorious.events.EventType.ANNOTATION_UPDATED, annotation, annotator.getItem());
else
annotator.fireEvent(annotorious.events.EventType.ANNOTATION_CREATED, annotation, annotator.getItem());
self.close();
});
If I put a breakpoint at "goog.events.listen(this._btnSave...", and type "annotorious.Annotation", I get what I expect:
In fact, it has all kinds of methods:
Then I let the code go, and break in the listener (event.preventDefault();, etc, above):
Now, all the dot-syntax methods are gone.
This of course causes crashes later on.
All of these files are compiled together.
This happens for all callbacks - 'load' events, other ux callbacks, etc.
This must have worked in prior versions of Closure / JS.
What could be causing this?
Thanks!
Ok, I was able to resolve the problem by adding "--assume_function_wrapper" to the closure compiler command line.
Previously, I was compiling the package using Plovr. However, since Plovr hasn't been updated in a long time, I switched to using the closure compiler natively.
Apparently either Plovr provided '--assume_function_wrapper' internally or the version of the compiler Plovr used didn't break the functions as described.
As @john suggests above I'll bet '--assume_function_wrapper' keeps goog.provide from "destroying" namespaces by re-declaring them.