These two with's are to put the class initializer statements lexically in the
scope of the class's instance and class vars. We should file an improvement to
use Don's analysis to eliminate these two with statements by finding the free
references in the initializer and rewriting them.
The big descriptor objects are because we don't have descriptors for the LFC
node classes, so each user class has to replicate these descriptors, event if
they don't add any new attributes.
There's a couple of improvements that can be filed here:
1) We could hand-create these descriptors in the LFC. This is the least
desirable solution, but it would work as a stop-gap.
2) We could rewrite the LFC node classes in LZX and teach the LFC compiler to
tag-compile them and extract this kind of information directly.
3) We could use Don's analysis tools to build these descriptors in the script
compiler and insert them into the LFC node classes when they are compiled.
On 2011-03-17, at 12:00, Max Carlson wrote:
> I thought I'd try this out - and the performance boost is amazing! I was
> wondering why the generated app code was slightly larger. For example,
> components/demos/house.lzx?lzt=object&lzr=dhtml has tons declarations like
> this:
>
> (function($0){
> with($0)with($0.prototype){
> {
> LzNode.mergeAttributes({$CSSDescriptor:{},$attributeDescriptor:{types:{aaactive:"boolean",aadescription:"string",aaname:"string",aasilent:"boolean",aatabindex:"number",align:"string",backgroundrepeat:"string",bgcolor:"color",cachebitmap:"boolean",capabilities:"string",classroot:"string",clickable:"boolean",clickregion:"string",clip:"boolean",cloneManager:"string",contextmenu:"string",cornerradius:"string",cursor:"token",datapath:"string",defaultplacement:"string",fgcolor:"color",focusable:"boolean",focustrap:"boolean",font:"string",fontsize:"size",fontstyle:"string",frame:"numberExpression",framesloadratio:"number",hasdirectionallayout:"boolean",hassetheight:"boolean",hassetwidth:"boolean",height:"size",id:"ID",ignoreplacement:"boolean",immediateparent:"string",inited:"boolean",initstage:"string",isinited:"boolean",layout:"css",loadratio:"number",mask:"string",name:"token",nodeLevel:"number",opacity:"number",options:"css",parent:"string",pixellock:"boolean",placement:"stri!
ng"
> ,playing:"boolean",resource:"string",resourceheight:"number",resourcewidth:"number",rotation:"numberExpression",selected:"boolean",shadowangle:"number",shadowblurradius:"number",shadowcolor:"color",shadowdistance:"number",showhandcursor:"boolean",source:"string",stretches:"string",styleclass:"string",subnodes:"string",subviews:"string",tintcolor:"string",totalframes:"number",transition:"string",unstretchedheight:"number",unstretchedwidth:"number",usegetbounds:"boolean",valign:"string",visibility:"string",visible:"boolean",width:"size","with":"string",x:"numberExpression",xoffset:"numberExpression",xscale:"numberExpression",y:"numberExpression",yoffset:"numberExpression",yscale:"numberExpression"}},onselected:LzDeclaredEvent,selected:false,selectionmanager:null},$lzc$class__m2f.attributes)
> }}})($lzc$class__m2f)
> };
>
> It seems like the with($0) shouldn't be there. Awesome work so far!
>
> On 3/16/11 2:06 PM, Donald Anderson wrote:
>> Change dda-20110301-0dx by [email protected]
>> <mailto:[email protected]> on 2011-03-01 14:23:55 EST
>> in /Users/dda/laszlo/src/svn/openlaszlo/trunk-c/WEB-INF/lps/schema
>> for http://svn.openlaszlo.org/openlaszlo/trunk/WEB-INF/lps/schema
>>
>> Summary: Eliminate the need for with(this) from most typical cases
>>
>> New Features:
>>
>> Bugs Fixed: LPP-8751 Eliminate the use of `with(this)`
>>
>> Technical Reviewer: ptw (pending)
>> QA Reviewer: henry (pending)
>> Doc Reviewer: (pending)
>>
>> Documentation:
>>
>> Release Notes:
>>
>> Overview:
>> [Mar 16 review - updated review comments indicated in [] brackets below]
>>
>> with(this) can be eliminated from a function only when either of these
>> conditions occur:
>> - we have an complete knowledge of the class heirarchy.
>> - there are no free references in the function
>> and when this condition does not occur:
>> - another 'with(varname)' appears in the function.
>> We address the first condition via changes to the js2doc as it
>> generates the lfc schema, the tag compiler as it generates extra
>> 'reference' JS classes that contain attributes and methods with
>> empty implementations, and the script compiler, as it uses the
>> reference classes to create a (usually) complete picture of the class
>> heirarchy for most cases.There's nothing we can do about the
>> second condition [a change from previously].As for the third
>> condition, there are ways of mitigating it, but we don't bother for now
>> on the assumption that a function coded containing 'with(varname)' is not
>> a function that is coded for speed.
>>
>> There may be some future work that may require a complete set of
>> reference classes, or method args, etc..These are mentioned in
>> comments below as 'FUTURE WORK'.For most of these, preliminary
>> explorations were done, and abandoned for expediency.
>>
>> Details:
>> [these 3 files changed since last review: added more tests]
>> test/lztest/lztest-class-impl.lzx:
>> test/smoke/smokecheck.lzx:
>> test/smoke/compiler.lzl:
>> Added some simple tests that illustrate how with(this) is inserted
>> in certain cases (before this change).By inspecting JS, used to
>> verify that 'this.' insertion and 'with(this)' removal is working.
>> Added more tests in response to Andre's testing, and suggestions by
>> Tucker [new]
>> Added tests using classes that inherit from LzURL, since it won't
>> be 'completely known', so will require with(this). [new]
>>
>> WEB-INF/lps/schema/lfc-undeclared.lzx: [changed since last review, added
>> ondestroy, from LzEventable]
>> Added attribute: isinited, marked as private in doc, which is used
>> by old components, and cannot be marked as public.
>> Added method: setAttribute, which actually lives in LzEventable, and is
>> used quite often.We don't current emit reference classes for
>> any classes that are not associated with a tag (it was too hard
>> to get a non-tag class into the tag compiler - FUTURE WORK).
>> Added method: ondestroy, an event that really lives in LzEventable,
>> for the same reason as above. [new]
>>
>> WEB-INF/lps/lfc/core/LzNode.lzs:
>> Added devnote about isinited.
>>
>> WEB-INF/lps/lfc/compiler/Class.lzs:
>> Minor error message improvement that I found helpful once. (optional)
>>
>> WEB-INF/lps/server/src/org/openlaszlo/js2doc/SchemaBuilder.java:
>> - jsname (the javascript name) for a class as well as jsextends
>> (the javascript class it extends) are put into the schema, though
>> not currently used - FUTURE WORK).
>> - omit event names not already defined as attributes
>> - method parameters are now collected and inserted into the schema,
>> but no typing is currently preserved (FUTURE WORK).
>>
>> WEB-INF/lps/server/src/org/openlaszlo/compiler/ClassCompiler.java:
>> Ignore classes in the schema that has no associated tag name (FUTURE WORK).
>> Small change to the protocol of compiling a ClassModel.
>>
>> WEB-INF/lps/server/src/org/openlaszlo/compiler/NodeModel.java:
>> Ignore the jsname, jsextends parts of the schema (FUTURE WORK).
>> Small change to the protocol of compiling a ClassModel.
>>
>> WEB-INF/lps/server/src/org/openlaszlo/compiler/ClassModel.java: [changed
>> since last review: fixed parenthesization, emit reference classes
>> without regard to runtime type]
>> - Changed isCompiled() to be true to its name.
>> - reworked compile() to handle emiting reference classes as needed.
>> - reworked emitClassDeclaration() to work with reference classes.
>>
>> WEB-INF/lps/server/src/org/openlaszlo/sc/ScriptClass.java: [changed
>> since last review: elide, rather than rename, names that are reserved]
>> Changed generation of a class so it won't create attributes named 'with'
>> classes named 'class', etc.Needed when generating all classes for
>> the full schema (possibly optional now, but needed for FUTURE WORK).
>>
>> WEB-INF/lps/server/src/org/openlaszlo/sc/CommonGenerator.java: [changed
>> since last review: renamed predefinedGlobals->globalProperties, added
>> "canvas", "escape", "unescape", removed "prototype"]
>> - rearrange globals and debugGlobals into separate sets, enumerate
>> the members of JS 'Object' class.
>> - ClassDescriptor.getInstanceProperties() modified to return an
>> 'incomplete' set,
>> rather than null.ClassDescriptor.complete is set and needs to be checked
>> by the caller.
>> - ClassDescriptor.incompleteSet() added for informational messages.
>> - ClassDescriptor.toString() for development/debugging.
>> - process reference classes minimally when needed at all.
>>
>> WEB-INF/lps/server/src/org/openlaszlo/sc/JavascriptGenerator.java:
>> [changed since last review: renamed predefinedGlobals->globalProperties,
>> new algorithm for determining if withThis is needed]
>> - create set of forwardGlobals by doing a shallow walk of the AST.
>> - manage the 'possibleInstance' set to try to reduce it and move
>> as many items as appropriate/possible to the 'bindthis' set,
>> which is the set of variables we will actively bind to 'this'.
>> - issue warning if 'warnWithThis' or 'warnUnknownGlobals' is on.
>>
>> WEB-INF/lps/server/src/org/openlaszlo/sc/SWF9Generator.java: [changed
>> since last review - fixed code to ignore reference classes]
>> Make sure reference classes are ignored in this generator.
>>
>> WEB-INF/lps/server/src/org/openlaszlo/sc/DHTMLCompiler.java:
>> set option so that reference classes are accepted.
>>
>> WEB-INF/lps/server/src/org/openlaszlo/sc/Compiler.java: [changed since
>> last review: added "warnUnknownGlobals"]
>> define 'referenceClass' pragma issued by tag compiler.
>> define 'registerReferenceClasses', an option only set by the DHTMLCompiler.
>> define 'warnWithThis', a new debugging option that will warn
>> when with(this) is used, and give the reason behind it, e.g.:
>> 'with(this) added in foobar: unknown parts of class hierarchy:
>> [LzTestManagerClass->LzEventable] and unaccounted refs: [LzHTTPLoader,
>> escape]'
>> define 'warnUnknownGlobals', a new debugging option that will warn
>> when we know the inheritance chain, yet there are free references
>> that we cannot identify.
>>
>> WEB-INF/lps/server/src/org/openlaszlo/sc/CodeGenerator.java:
>> Abide by new ClassDescriptor protocol
>>
>> WEB-INF/lps/server/src/org/openlaszlo/sc/GenericVariableAnalyzer.java:
>> WEB-INF/lps/server/src/org/openlaszlo/sc/VariableAnalyzer.java:
>> WEB-INF/lps/server/src/org/openlaszlo/sc/WithThisAnalyzer.java:
>> Refactored VariableAnalyzer so essential parts could be shared
>> with a new 'WithThisAnalyzer'.The new analyzer walks the tree
>> and applies identifier --> this.identifier transformation for
>> any free variables found in a set.It also tracks if any
>> 'with' constructs are found, which is a spoiler for with(this) removal.
>>
>> WEB-INF/lps/server/sc/src/org/openlaszlo/sc/parser/SimpleNode.java:
>> Added indexOf() - a convenience function, helpful in the 'this binding'.
>>
>> Tests:
>> - Ran smoketest (DHTML,SWF10) lztest, runlzunit (includes new tests)
>> - For lztest, spot checked to ensure that 'this.'
>> was inserted, specifically in the 'WithThis' tests
>> (in test/lztest/lztest-class-impl.lzx)
>> -Of the occurrences in lztest that require with(this), we know why they
>> occur: 1) LzTestManagerClass inherits
>> from LzEventable, not a class associated with a tag.This will not happen for
>> pure lzx programs. 2) they often refer to use class names in the LFC:
>> LzHTTPLoader, LzTimeKernel.3) they refer to identifiers 'canvas', 'escape'.
>>
>>
>>
>> Files:
>> Mtest/lztest/lztest-class-impl.lzx
>> Mtest/smoke/smokecheck.lzx
>> Mtest/smoke/compiler.lzl
>> MWEB-INF/lps/schema/lfc-undeclared.lzx
>> MWEB-INF/lps/lfc/core/LzNode.lzs
>> MWEB-INF/lps/lfc/compiler/Class.lzs
>> MWEB-INF/lps/server/src/org/openlaszlo/js2doc/SchemaBuilder.java
>> AWEB-INF/lps/server/src/org/openlaszlo/sc/WithThisAnalyzer.java
>> MWEB-INF/lps/server/src/org/openlaszlo/sc/JavascriptGenerator.java
>> AWEB-INF/lps/server/src/org/openlaszlo/sc/GenericVariableAnalyzer.java
>> MWEB-INF/lps/server/src/org/openlaszlo/sc/VariableAnalyzer.java
>> MWEB-INF/lps/server/src/org/openlaszlo/sc/CommonGenerator.java
>> MWEB-INF/lps/server/src/org/openlaszlo/sc/SWF9Generator.java
>> MWEB-INF/lps/server/src/org/openlaszlo/sc/DHTMLCompiler.java
>> MWEB-INF/lps/server/src/org/openlaszlo/sc/Compiler.java
>> MWEB-INF/lps/server/src/org/openlaszlo/sc/CodeGenerator.java
>> MWEB-INF/lps/server/src/org/openlaszlo/sc/ScriptClass.java
>> MWEB-INF/lps/server/src/org/openlaszlo/compiler/ClassCompiler.java
>> MWEB-INF/lps/server/src/org/openlaszlo/compiler/NodeModel.java
>> MWEB-INF/lps/server/src/org/openlaszlo/compiler/ClassModel.java
>> MWEB-INF/lps/server/sc/src/org/openlaszlo/sc/parser/SimpleNode.java
>>
>> Changeset: http://svn.openlaszlo.org/openlaszlo/patches/dda-20110301-0dx.tar
>>
>>
>>
>> --
>>
>> Don Anderson
>> Java/C/C++, Berkeley DB, systems consultant
>>
>> voice: 617-306-2057
>> email: [email protected] <mailto:[email protected]>
>> www: http://www.ddanderson.com <http://www.ddanderson.com/>
>> blog: http://libdb.wordpress.com
>>
>>
>>
>>
>>