Thanks to FireFox's buggy implementation of ActiveX components (it really should take an image of them when printing) Flex components (in our case charts) don't print in FX.
They print fine in IE7, even IE6.
We need these charts to print, but they also have dynamic content. I don't really want to draw them again as images when the user prints - the Flex component should do it.
We've found a potential workaround, but unfortunately it doesn't work in FireFox3 (in FireFox2 it sort-of works, but not well enough).
Anyone know a workaround?
Using the ACPrintManager I was able to get firefox 3 to print perfectly!
The one thing I had to add to the example was to check if stage was null, and callLater if the stage was null.
private function initPrint():void {
//if we don't have a stage, wait until the next frame and try again
if ( stage == null ) {
callLater(initPrint);
return;
}
PrintManager.init(stage);
var data:BitmapData = new BitmapData(stage.stageWidth, stage.stageHeight);
data.draw(myDataGrid);
PrintManager.setPrintableContent(data);
}
Thanks. A load of callLater-s added to our custom chart code seems to have done it.
Related
I'm trying to solve a view placement bug that has arisen as of iOS 9. I am instantiating a view controller from a xib file (non-autolayout) and then pushing this onto my UINavigationController.
The problem is that when the view controller's viewWillAppear method is called, its frame has not yet been adjusted to the navigation controller's size and is still what was set in the xib file. It doesn't get set properly now until viewDidAppear.
This is completely screwing up my code. Does anyone know precisely what has changed that is causing this and what is the best way to handle it? I don't want to wait until viewDidAppear because this will look bad and make for a poor user experience.
I am also looking for the best fix.
My temporary one is to call the code that was in "viewDidAppear" in "viewDidLayoutSubviews". That way, my code will get called as soon as the frames are set.
But, make sure to add a boolean or something so that your code doesn't get called every time viewDidLayoutSubviews is called
-(void)viewDidLayoutSubviews{
if (didLayoutSubviews == NO){
didLayoutSubviews = YES;
// perform code that was in viewWillAppear
}
}
I occurred this issue too,
try to uncheck option "Resize View From NIB" from storyboard
Try moving the layout code from viewWillAppear to viewWillLayoutSubviews.
A little bit updated NickProvost's answer:
private var loadViewToken: dispatch_once_t = 0
override func viewDidLayoutSubviews() {
super.viewDidLayoutSubviews()
dispatch_once(&loadViewToken) { [weak self] in
if let wSelf = self {
wSelf.setupView()
}
}
}
I have a website which is built totally in flex.
I want to make a button, on the click of which the browser becomes fullscreen. I am not talking about a flex fullscreen, by which i mean "Application.application.stage.displayState = StageDisplayState.FULL_SCREEN;" I dont want to use this.
The reason, I dont want to use it is, that flash does not supports keyboard on flex-fullscreen. But if i can make the browser fullscreen, it will solve my purpose.
Also i am hoping the same method will be good for all browsers on PC and Mac both.
Use ExternalInterface to call a javascript function for it. Sorry this solution is half-baked so I'm not 100% sure it works..
//In ActionScript
public function fullScreen():void
{
if (ExternalInterface.available)
{
ExternalInterface.call("fullScreen");
}
else
{
//Error
}
}
//In JavaScript
function fullScreen()
{
if (parseInt(navigator.appVersion)>3) {
moveTo(0,0);
resizeTo(screen.availWidth,screen.availHeight);
}
//on older browsers just leave it alone
}
i did the same work using thw solution for which you r saying no, u r saying the keyboard doesn't work, but it's working in ma case
here is the button code :
<mx:Button id="fullscreen" styleName="fullscreen" click="toggleFullScreen();"/>
and here is the function which gets called :-
private function toggleFullScreen():void
{
if(Application.application.stage.displayState == StageDisplayState.NORMAL)
Application.application.stage.displayState = StageDisplayState.FULL_SCREEN;
else if(Application.application.stage.displayState == StageDisplayState.FULL_SCREEN)
Application.application.stage.displayState = StageDisplayState.NORMAL;
}
also there are some files , that u need to copy in the html-template folder:-
i'll send u those files, mail me ankursharma85#in.com, i'll reply u
and yes, when u r in full screen mode, u can press "esc" key to get to the normal mode, and if u want to use keyboard to make fullscreen, then u keyboard events, thats a different story
i hope this helps
tc hav a gr8 time
I'm developing a grid with excel-like functionality using the telerik controls. For example users can click on a cell and the cell turns into an input control for editing. Users can tab to move onto the next cell or use arrow keys for up/down to get the cell above or below. I've found the standard telerik grid is good but I've had to extend it with custom javascript to achieve what I need.
My problem is performance in the IE browser. While Firefox, Chrome, Safari are all fine, IE is a real pain. IE8 is considerably better than IE7 however moving around with the cursor keys is a bit unnatural, and nothing like as smooth as Chrome or FF.
I can't really post sample code due to the complexity of what the grid is doing, but generally I'm displaying the standard telerik grid and using the telerik javascript API to fill and bind in the browser. When a cell is clicked a javascript function moves a previously hidden input control into the cell from a hidden collection and gives it focus. When you tab away the cell value is cleared and the server is updated using ajax pagemethods and the next cell is selected in a similar manner.
The grid has approx 40 columns and 20 rows, i.e. 800 extra controls are hidden on the page and only activated by clicking a cell or through navigating with the keyboard. I originally had just one hidden control for each column but moving up and down with the cursor keys became problematic in IE.
Any advice for things to check that might speed up IE8 would be greatly appreciated.
//selects a cell and sets the value
this.select = function(value) {
this.moveFromTo(this._hiddenCell, this._gridCell);
this._bIsSelected = true;
this.set_inputValue(value);
this._focus();
}
//clears inner content for a cell
this.removeChildrenFromNode = function(node) {
if (node == undefined || node == null) {
return;
}
var len = node.childNodes.length;
while (node.hasChildNodes()) {
node.removeChild(node.firstChild);
}
}
//move back or forwards between hidden or active cell
this.moveFromTo = function(from, to) {
var currChild = null;
this.removeChildrenFromNode(to);
var i = 0;
if (from.childNodes != null) {
while (i < from.childNodes.length) {
currChild = from.childNodes[i];
if (to != null) to.appendChild(currChild);
i += 1;
}
}
this.removeChildrenFromNode(from);
}
Load up your page in IE8, open the developer toolbar F12 and turn on the profiling:
Profiler (tab) > Start Profiling
Use your grid for a bit as normal, and let IE profile your code.
When done, click Stop Profiling, and verify which function calls are chewing up the memory or taking the most time.
They may be ones that are beyond your control (e.g. in Telerik's code) but if anything you've added is the bottleneck post the function(s) back here on SO to ask for advise on how to optimize.
It sounds as though most if not all of your controls related to the grid are created from within JavaScript?
If so there are a couple of things to keep in mind:
IE hates string concatenation: there are numerous posts about it's poor performance
Ensure your clearing your events when switching controls and not just overwriting them
memory leaks are not your friend
IE hates adding controls as much as you do - so reuse them when possible
IE is faster if the controls are created via HTML (why oh why?)
IE hates it when you add lots of dynamic images and CSS with on-the-fly HTML controls
IE prefers innerHTML to addChild() (seems counter intuitive to string issue above)
etc
etc
There's many more, but with IE you also have to implement almost every single JavaScript performance suggestion you can find:
short variable names
ensure variables are properly scoped (otherwise the runtime will jump up scopes until nothing is left to search)
iterators from frameworks like prototype and jQuery are often slower than traditional for and while loops (VERY VERY sad but quite true)
etc
etc
When a cell is clicked a javascript
function moves a previously hidden
input control into the cell from a
hidden collection and gives it focus.
You have to explain the quote above in more detail. How exactly do you move the previously hidden control into the cell? Check the site below for a benchmark that uses different methods to generate a dynamic table. Moving the control using the W3C DOM methods or table methods could slow down IE while working fine in other browsers.
http://www.quirksmode.org/dom/innerhtml.html
Edit: Try this to check if it's faster(not as a final solution):
this.moveFromTo = function(from, to) {
to.innerHTML = from.innerHTML; }
Here are some useful links
Understanding and Solving Internet Explorer Leak Patterns
IE Sieve, Memory Leak detector for Internet Explorer
JavaScript Profiling
Try Google Frame. It pushes the performance on IE8 ;)
Test you code with jslint.com
Can I add a ProgressEvent listener to the stage?
I don't see it in any of the auto-complete options when I am typing in Flex.
What do people normally do to get a progress readout of the entire main runner's loading progress?
I try the following, which is where I would expect to see the ProgressEvent options pop up:
stage.addEventListener(
Thanks...
Try adding it to loaderInfo.
something like:
this.loaderInfo.addEventListener(ProgressEvent.PROGRESS, progressHandler);
Also , if you're using the framework, you should probably extend the DownloadProgressBar.
I remember this old tutorial, but surely there must be plenty online.
I have a new problem:
I use the following code to show the progress of the download of my site content:
public function mainProgress(e:ProgressEvent):void
{
var w:Number = e.bytesLoaded / e.bytesTotal;
_mainprog.graphics.clear();
_mainprog.graphics.beginFill(0x000000);
_mainprog.graphics.drawRect(0, 0, w * stage.stageWidth, 50);
_mainprog.graphics.endFill();
}
But it doesn't seem to work.
What happens is that the loaderInfo object thinks that the site has loaded before I am actually ready to display anything. So what ends up happening (I think) is the site loads, the loader progress disappears before the initial page's graphics have fully loaded, and then there is a delay between when the completion of the loaderInfo object happens and the actual graphics appearing.
Has anyone else had this problem before?
Thanks...
First and foremost, I apologize for any vagueness in this question. At this point, I'm simply trying to get some new ideas of things to try in order to diagnose this bug.
Anyway, the problem I'm having is with an application that's using a custom moduleloader. That moduleloader has been compiled into an swc and the moduleloader is being instantiated via its namespace. This all works perfectly fine. The problem I'm encountering is specific to mx:button controls used within modules. For whatever reason, their labels are being truncated so, for example, Sign In is showing up with an ellipsis, as Sign ...
After quite a bit of fooling around I have been able to establish the following:
This problem only seems to occur within modules. If a button control is used in the main mxml, the label does not get truncated.
The button control whose label is being truncated does not have a width specified (setting its width to 100% or a specific pixel width doesn't fix the issue)
The button control is using the default padding (messing with the padding by setting left and right to 5 or any other value doesn't help matters either).
We are not using any embedded fonts so I've ruled that out as a possibility as well.
mx:CheckBox and mx:LinkButton are equally impacted by this problem although mx:CheckBox also seems to not want to show its checkbox, it just shows the truncated label.
A potential side affect of this is that attaching a dataprovider to mx:ComboBox causes the combobox control to throw a drawing error but I'm not entirely certain that it's related to the above problem.
One interesting thing I did find while perusing the net for an answer was a mention of fontContext and its relationship to IFlexModuleFactory. There's no specification for fontContext within our implementation of moduleloader so I'm not entirely certain if this could be the issue. In any case, if anyone has any ideas, it would be hugely appreciated. On the other hand, if you know exactly what ails me and can provide me with an answer, I might just wet myself with excitement. It's late. I'm tired. I NEED my Flex app to play nice.
Thanks in advance,
--Anne
Edit: To clarify what I'm looking for with this question, I really just need to know the following:
Could this issue be caused by a namespace conflict?
What else can potentially override the default behavior of labels if no CSS has been implemented?
Has anyone encountered a problem with inheritance being lost while using a custom implementation of moduleloader?
Has anyone encountered this problem or a similar problem with or without using moduleloader?
I'm not sharing any code with this question simply because I'd have to share the entire application and, unfortunately, I can't do that. Again, I'm not looking for the end all, be all solution, just some suggestions of things to look out for if anyone has any ideas.
I've been dealing with this issue myself, off and on and in various forms, for a year, and while I haven't figured out just what's causing it yet, there's clearly a mismeasurement happening somewhere along the line.
What I have been able to to, though, is work around it, essentially by subclassing button-type controls (in my case, Button, LinkButton, PopUpButton, et. al.) and assigning their textField members instances of a UITextField extension whose truncateToFit element simply returns false in all cases:
public class NonTruncatingUITextField extends UITextField
{
public function NonTruncatingUITextField ()
{
super();
}
override public function truncateToFit(s:String = null):Boolean
{
return false;
}
}
The custom component just extends Button (or whatever other button-type control is the culprit -- I've created a half-dozen or so of these myself, one for each type of control), but uses a NonTruncatingTextField as its label, where specified by the component user:
public class NonTruncatingButton extends Button
{
private var _truncateLabel:Boolean;
public function NonTruncatingButton()
{
super();
this._truncateLabel = true;
}
override protected function createChildren():void
{
if (!textField)
{
if (!_truncateLabel)
textField = new NonTruncatingUITextField();
else
textField = new UITextField();
textField.styleName = this;
addChild(DisplayObject(textField));
}
super.createChildren();
}
[Inspectable]
public function get truncateLabel():Boolean
{
return this._truncateLabel;
}
public function set truncateLabel(value:Boolean):void
{
this._truncateLabel = value;
}
}
... so then finally, in your MXML code, you'd reference the custom component thusly (in this case, I'm telling the control never to truncate its labels):
<components:NonTruncatingButton id="btn" label="Click This" truncateLabel="false" />
I agree it feels like a workaround, that the component architecture ought to handle all this more gracefully, and that it's probably something we're both overlooking, but it works; hopefully it'll solve your problem as you search for a more definitive solution. (Although personally, I'm using it as-is, and I've moved on to other things -- time's better spent elsewhere!)
Good luck -- let me know how it works out.
I've used the custom button and link button class solutions and still ran into problems - but found a workaround that's worked every time for me.
Create a css style that includes the font you'd like to use for you label. Be sure to check 'embed this font' right under the text selection dropdown. Go back and apply the style to your button (or your custom button, depending on how long you've been bashing your hear against this particular wall), and voila!
Or should be voila...
I just came across this issue and solve it this way:
<mx:LinkButton label="Some label"
updateComplete="event.target.mx_internal::getTextField().text = event.target.label"
/>;
I've had some success preventing Flex's erroneous button-label truncation by setting labelPlacement to "bottom", as in:
theButton.labelPlacement = ButtonLabelPlacement.BOTTOM;
Setting the label placement doesn't seem to help prevent truncation in some wider button sizes, but for many cases it works for me.
In cases where you can't use a bottom-aligned button label (such as when your button has a horizontally aligned icon), janusz's approach also seems to work. here's a version of janusz's .text reassignment technique in ActionScript rather than MXML:
theButton.addEventListener(FlexEvent.UPDATE_COMPLETE, function (e:FlexEvent):void {
e.target.mx_internal::getTextField().text = e.target.label;
});
The preceding code requires you to import mx_internal and FlexEvent first, as follows:
import mx.events.FlexEvent;
import mx.core.mx_internal;
And here are the results…
Before (note truncation despite ample horizontal space):
After:
The only downside to this approach is you lose the ellipsis, but in my case I considered that a welcome feature.