I've created a number of skins for various components recently. Some of these were for Spark components and the default behavior of Flash Builder is to take the source code of the original skin and copy into your skin as a starting point.
Normally, I am 90% ok with the original skin, I just want to tweak or add one little thing. It seems to me that duplicating 3 pages of source code to do this is a bad idea. What do I do when I upgrade Flex SDKs? Do I have to go back through the source of all these original skins and (re)compare? This sounds like a disaster.
Is there a way I can create a new skin in MXML that inherits from the old skin? Can I do this via ActionScript?
If you upgrade your Flex SDK I don't think there should be any modification in the skinParts of components. Anyway if there were, you would have a compilation error if one of your implemented skinparts is not of the right type or if you miss a required skinPart. So I wouldn't worry if I were you :)
Another tip would be to use as much as possible CSS styling to avoid this kind of problems.
And no, I don't think you can inherit from a skin and modify its elements (but I'd be glad to be proved wrong).
Related
So, I was just wondering if anyone could give me a succinct answer on why exactly it's better to code mostly in an AS3 file as opposed to most on the timeline?
I've heard a lot of people answer questions with a cop-out "don't put so much code in your timeline". I've tried both ways and found some pros and cons on each, but it just seems silly to me for so many people to parrot the general good coding practice techniques.
Another thing about that is that a lot of times I'll be searching for help on coding, and people will give such complicated responses, and half the time I'll use little snippets of code as well as incorporate a small portion into my projects. Also, the AS3 API site also gives waaaay overcomplicated coding examples. Why do people do this? I could figure out some of my issues much more quickly if people just simplified the code examples.
Three good reasons not to put it on the timeline:
Your code will be stuck inside a binary file, not allowing you to use version control nor review changes to it.
You're going to hide code behind menus, making it hard to review in an instance. When it's all in one place you can easily refactor it, and change it.
By putting code on your timeline, you're making your code be dependent on the Animate compiler. (Animate is going to take your code and inject it into your document class using the undocumented function addFrameScript to make things work). The code isn't easy to migrate in this form, if you ever feel the need to re-code in another language.
Please use an IDE when coding. It will help prevent mistakes and even suggest ways to make your code simpler. (To name a few IDEs: FlashDevelop, VSCode, IntelliJ Idea Ultimate (paid).)
To clear up any confusion, writing code in an AS3 file instead of the timeline doesn't mean make things less organized or put code where it doesn't make sense to put it.
What you should be doing is creating a new AS3 file for every MovieClip that you need scripted, then going into the Symbol Properties of your movieclip and selecting Export for ActionScript and set the class name to your AS3 file. The runtime will automatically declare the instances in your file at compile time. What you can do is actually declare them yourself in the file, to have full completion capability in your IDE.
What I like doing is first setting the movieclip to export for actionscript, publishing my project, then opening the compiled swf using Free Flash Decompiler, and copy paste the generated class into a new AS3 file. (You'll want to only copy paste the class and generated instance variables.) Then you can code in your AS3 file with all the symbols contained within the MovieClip already referenced.
I am making a project in AS3, but I have come to a point, where I need to branch out, because I want it to publish to 2 places, which each require a bit of different additional code to function properly. So is it possible to achieve that I do not need to make 2 projects and maintain 2 similar projects?
I hope I wrote it clear enough.
Thanks for your responses.
You can do several things, depending on whether you're working in the Flash IDE, Flash Builder, or one of the other tools like IntelliJ.
If you are working in the Flash IDE and/or have a Flash Professional project set up in Flash Builder, you can go into the ActionScript Properties panel and set up a source path that points anywhere (I usually try to keep it relative, but it's up to you).
If you're working without a fla/xfl, then you probably need to look at setting up a library project.
This is a big reaseon for OOP! Write Base Classes and extend them for your Projects as needed.
Also check out Conditional Compilation
I love skins in Flex 4 - they offer a really nice separation between logic and styling.
I was wondering how people use binding in skins. The easiest way is to just bind in the skin:
label="{ hostComponent.model.buttonLabel }"
you can also use 2 way bindings:
selectedItem="#{ hostComponent.model.selectedItem }"
but you could argue that this is logic so it should really be handled in the component. You don't really want to re-create all the bindings each time you create a new skin. That seems fragile and prone to creating bugs.
So what are the alternatives? Creating a bucket load of event listeners I suppose. The adobe observe and observeValues tags could be useful as well I suppose.
How do others handle this?
I think it's a good and interesting question. There are a couple of alternatives. I suppose you could inject the model into the skin and bind directly, but that seems wrong because I think the skin should be intimately connected with the component - if the component changes its reference to the model, it automatically changes in the skins. And anyway it only exaggerates the problem you mentioned.
You can create ids in the skin and operate on them from the model. For example
SKIN: label id="infoLabel"
COMPONENT: [SkinPart] var infoLabel:Label
creationComplete {
BindingUtils.bindProperty(this, 'infoLabel', model, 'infoLabel');
}
This solves your problem. No repetitive maintenance between skins of the same component. However using BindingUtils comes at a cost. Firstly it's not as evident what is bound to what - using the {} way is just so much more obvious. Secondly (I suppose this is actually just part of the first point) you might confuse less-able developers that have to read your code and figure out what's going on.
EDIT: This assumes your component is in AS3. If your component is in MXML, I guess you can just bind as you normally would in MXML.
I've been writing in actionscript 3 using flex builder 3 for a couple of weeks now and never encountered the need to use anything like MXML. I code all layout and design in pure actionscript.
I am not sure why, but many people immediately expect me to have written a lot of MXML when I say that I'm using flex builder.
Is MXML really recommended? If so, why did I never encounter the need for it yet?
As MXML is compiled to ActionScript while building, there may be no need for MXML - everything can be coded in AS3.
However, I find that MXML is quicker to use in some scenarios - for example, composite components of the UI in an application.
If a composite component is a library-type component (a new type of generic widget - whether based on an existing control or completely custom), I use AS3 as I get finer control. The code for such controls will not change much over time, once a stable release is made.
If a composite component is a part of an application's UI which is more likely to change over time due to user-driven changes to the UI (e.g. application configuration panels) then MXML allows faster iterative development. This is the kind of change where you have to move controls around, change styling etc. in response to user or marketing feedback, or business-driven changes over time.
Is the source code available somewhere just to make a few small fixes to textfield class?
As mentioned, the sources for the internal flash.* classes are not available. To modify or add behavior you'll need to subclass TextField.
You should extend the Textfield class. Override what you want to change.
Flex is an open-source SDK built on top of Flash, so it shouldn't be a problem to find the relevant source file in the SDK and apply your fix.
But it might be simpler to either:
Apply the fix externally. e.g. by deriving from the class and overriding.
Open a bug with the SDK people and ask them to fix it (that is, if it's not an urgent critical bug).
If you do end up fixing it in the SDK, consider releasing your fix back to the community.