I create 3 TitleWindow:
PopUpManager.addPopUp( TitleWindow1, root, false);
PopUpManager.addPopUp( TitleWindow2, root, false);
PopUpManager.addPopUp( TitleWindow3, root, false );
And then I manage those position and depth using mouse. Now I want to delete them by depth.
In my TitleWindow add listener:
root.addEventListener( KeyboardEvent.KEY_DOWN, onKeyDown );
private function onKeyDown(event:KeyboardEvent = null):void {
if ( event.keyCode == Keyboard.ESCAPE && this. ) { //!!!! how to detect this window depth, that it at first plan??
event.preventDefault();
event.stopImmediatePropagation();
closeHandler();
}
}
}
How does me solve this issue?
Now, I can offer one idea, I use state inactive:
private function onKeyDown(event:KeyboardEvent = null):void {
if ( event.keyCode == Keyboard.ESCAPE
&& this.getCurrentSkinState() != "inactive" ) {
event.preventDefault();
event.stopImmediatePropagation();
closeHandler();
}
}
override protected function stateChanged (oldState:String, newState:String, recursive:Boolean) : void {
super.stateChanged( oldState, newState, recursive );
if ( oldState == "inactive" && newState == "normal" ) {
PopUpManager.bringToFront( this );
}
}
You'll need to keep track of this when you add the pop ups. Here is an example class that extends the pop up manager:
package
{
import flash.display.DisplayObject;
import mx.collections.ArrayCollection;
import mx.core.IFlexDisplayObject;
import mx.core.IFlexModuleFactory;
import mx.core.UIComponent;
import mx.managers.PopUpManager;
public class PopManagerDepth extends PopUpManager
{
public function PopManagerDepth() { super(); }
public static var popUpsByDepth :ArrayCollection = new ArrayCollection();
public static function addPopUpWithDepth(window:IFlexDisplayObject,
parent:DisplayObject,
modal:Boolean = false,
childList:String = null,
moduleFactory:IFlexModuleFactory = null):void
{
PopUpManager.addPopUp(window, parent, modal, childList, moduleFactory);
PopManagerDepth.popUpsByDepth.addItem( window );
}
public static function removeLastPopUp():void{
PopManagerDepth.removePopUpByIndex(PopManagerDepth.popUpsByDepth.length);
}
public static function removePopUpByIndex( idx :uint ):void{
if( PopManagerDepth.popUpsByDepth.length > idx){
PopUpManager.removePopUp( popUpsByDepth.getItemAt( idx ) as IFlexDisplayObject );
}
}
}
}
You'd use this class to add your popups, just like popupmanager but with this method:
PopManagerDepth.addPopUpWithDepth( .... );
The difference is there is a new method you'd use to remove them :
PopManagerDepth.removeLastPopUp();
or
PopManagerDepth.removePopUpByIndex();
Should do the trick, sorry I cant test it right now, but should work or close to it. I'll help ya debug if needed :)
By Windows depth do you mean the z-index ? If so you might want to try the getChildIndex and removeChildAt methods on the DisplayObject class. However, since PopUps exists in a different heirarchy than the rest of the general components, I am unsure if this will work but it is a start ?
Here's what I would do:
Create an Array to keep track of each TitleWindow instance you pop up. You can use the Array index as a z-index indicator.
In your closeHandler() method, iterate through each member of the Array and close that TitleWindow instance.
Related
when i use the following tree renderer class the the informtions in the tree gets chopped. Is there any solution to fix this bug. please help me.
The PLTree class is as follows:
import flash.events.Event;
import mx.events.ScrollEvent;
import mx.controls.Tree;
import mx.core.ScrollPolicy;
import mx.core.mx_internal;
import mx.events.TreeEvent;
public class PLTree extends Tree
{
private var _lastWidth:Number = 0;
private var _lastHeight:Number = 0;
public function PLTree() {
super();
horizontalScrollPolicy = ScrollPolicy.AUTO;
}
override public function get maxHorizontalScrollPosition():Number
{
return mx_internal::_maxHorizontalScrollPosition;
}
override public function set maxHorizontalScrollPosition(value:Number):void
{
mx_internal::_maxHorizontalScrollPosition = value;
dispatchEvent(new Event("maxHorizontalScrollPositionChanged"));
scrollAreaChanged = true;
invalidateDisplayList();
}
override protected function updateDisplayList(unscaledWidth:Number, unscaledHeight:Number):void
{
var diffWidth:Number = measureWidthOfItems(0,0) - (unscaledWidth - viewMetrics.left - viewMetrics.right);
if (diffWidth <= 0) {
maxHorizontalScrollPosition = 0;
horizontalScrollPolicy = ScrollPolicy.OFF;
} else {
maxHorizontalScrollPosition = diffWidth;
horizontalScrollPolicy = ScrollPolicy.ON;
}
super.updateDisplayList(unscaledWidth, unscaledHeight);
}
override protected function scrollHandler(event:Event):void
{
if (mx_internal::isOpening)
return;
// TextField.scroll bubbles so you might see it here
if (event is ScrollEvent){
super.scrollHandler(event);
invalidateDisplayList();
}
}
}
i am attaching the image file of how it looks when executed.
When surfing using google i found a suggesion to fix this bug is it the right way ?
(
Issue: Text getting chopped of at end.
Fix: change
maxHorizontalScrollPosition = diffWidth;
to
maxHorizontalScrollPosition = diffWidth + 10;
or what ever correction factor you need.
)
Kindly help me .Thanks a lot in advance.
Looking at your picture, I'd suspect the issue has nothing to do with the specific tree, and is only slightly related to the renderer. Instead, I think that when the container holding the Tree is created, it doesn't have a size, and when the Tree sizes its renderers, it gives them the wrong size. Since List-based controls don't set the actual width on renderers, choosing to set explicitWidth instead, the renderers aren't triggered into changing their size.
Check out http://www.developria.com/2009/12/handling-delayed-instantiation-1.html for more explicit details and fixes.
similar to the scroll handler in the above mentioned program. Use a mouse wheel scroll handler to handle that event as follows:
override protected function mouseWheelHandler(eventMouse:MouseEvent):void
{ if (mx_internal::isOpening)
return;
if (eventMouse is MouseEvent){
super.mouseWheelHandler(eventMouse);
invalidateDisplayList();
}
}
I have a button which I use for sending a message. When the message text is empty, it should not be possible to click the button.
This is all fine and not an issue. The only thing that is bugging me is the fact that I can disable the send button but the image does not get disabled (like I would expect).
Is there a way to do this elegantly because I don't want to provide a sendicon_disabled.png and change it myself (I don't think this should be my job).
You can use the following button for that:
package
{
import mx.controls.Button;
import mx.core.mx_internal;
use namespace mx_internal;
public class IconButton extends Button
{
private var enabledChanged:Boolean = false;
override public function set enabled(value:Boolean):void
{
if (super.enabled == value)
{
return;
}
super.enabled = value;
enabledChanged = true;
invalidateDisplayList();
}
override protected function updateDisplayList(unscaledWidth:Number,
unscaledHeight:Number):void
{
super.updateDisplayList(unscaledWidth, unscaledHeight);
if (enabledChanged)
{
if (!enabled && currentIcon)
{
currentIcon.alpha = 0.5;
}
enabledChanged = false;
}
}
}
}
You can use your custom alpha value or move it to separate style.
Is there any workaround to create submenu in a flex context menu other than stopping right click from javascript.
Regards,
Hi Frank,
Yes, I want to create submenus in a context menu. Can you help me here.
Regards,
Hi Frank,
I need the context menu for the application not for datagrid.
In my initial question the phrase "other than stopping right click from javascript" means
"catch the right click in html, call a javascript function and over js call a as function."
The project that you have specified does the above procedure. I don't want to use this
procedure. Is there any other way for achieving submenus in a flex context menu. Could you
please tell me if so..
Regards,
Arvind
Yes, there is.
I don't know, what you exactly mean with this:
other than stopping right click from
javascript.
But, if you want to create a entry in submenu, do this:
//Instance of my own class
private var myContext:myContextMenu = new myContextMenu();
application.contextMenu = myContext.myContextMenu;
//Here is the Class:
package com.my.components
{
/* ////////////////////////////////////////////
///// My Context MenĂ¼ /////////////////////
///////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////
//to use: //
// private var myContext:MyContextMenu = new MyContextMenu(); //
// init() in creationComplete //
// application.contextMenu = myContext.myContextMenu; //
////////////////////////////////////////////////////////////////////////////// */
import flash.display.Sprite;
import flash.events.ContextMenuEvent;
import flash.net.URLRequest;
import flash.net.navigateToURL;
import flash.text.TextField;
import flash.ui.ContextMenu;
import flash.ui.ContextMenuBuiltInItems;
import flash.ui.ContextMenuItem;
public class MyContextMenu extends Sprite
{
public var myContextMenu:ContextMenu;
private var menuLabel:String = String.fromCharCode(169)+" My Company GmbH";
public function MyContextMenu()
{
myContextMenu = new ContextMenu;
removeDefaultItems();
addCustomItems();
myContextMenu.addEventListener(ContextMenuEvent.MENU_SELECT, menuSelectHandler);
super();
}
private function removeDefaultItems():void
{
myContextMenu.hideBuiltInItems();
var defaultItems:ContextMenuBuiltInItems = myContextMenu.builtInItems;
defaultItems.print = true;
}
private function addCustomItems():void
{
var item:ContextMenuItem = new ContextMenuItem(menuLabel);
myContextMenu.customItems.push(item);
item.addEventListener(ContextMenuEvent.MENU_ITEM_SELECT,menuItemSelectHandler);
}
private function menuSelectHandler(event:ContextMenuEvent):void
{
}
private function menuItemSelectHandler(event:ContextMenuEvent):void
{
navigateToURL(new URLRequest('http://www.my-company.de'));
}
private function createLabel():TextField
{
var txtField:TextField = new TextField();
//txtField.text = textLabel;
txtField.text = "RightClickHere";
return txtField;
}
}
}
Have fun
EDIT:
There is an interesting project here. They catch the right click in html, call a javascript function and over js call a as function.
Unfortunately, the limitation of FP or NativeMenu APi allowed just on level contextmenu. Read here
Frank
I try to do preloder in Flex for my project written in Flash.
I make this with the help of this site
link text
My Flash project have next source in main class called Game
stage.addEventListener(KeyboardEvent.KEY_DOWN, keyDown);
stage.addEventListener(KeyboardEvent.KEY_UP, keyUp);
private function keyDown(event:KeyboardEvent) {
if (event.keyCode == 81 && q_was_push == false) q_was_push = true;
if (event.keyCode == 81) press_q = true;
if (event.keyCode == 65) press_a = true;
if (event.keyCode == 83) press_s = true;
if (event.keyCode == 32) press_space = true;
} ...
When I take new swf file maked by Flex, I have error
TypeError: Error #1009: Cannot access a property or method of a null object reference.
at Game()
if I comment
//stage.addEventListener(KeyboardEvent.KEY_DOWN, keyDown);
//stage.addEventListener(KeyboardEvent.KEY_UP, keyUp);
Flex application work but Flash application does not react to button presses
Please how I can make preloader and work buttons together
The stage property will be null until a display object is added to the display list. Listen to the addedToStage event and add the key listeners from there.
addEventListener(Event.ADDED_TO_STAGE, onAddedToStage);
function onAddedToStage(e:Event):void
{
stage.addEventListener(KeyboardEvent.KEY_DOWN, keyDown);
stage.addEventListener(KeyboardEvent.KEY_UP, keyUp);
}
Anytime you need access to the stage, have the Class listen for it/check for it in the constructor, and have your init function be the handler.
package
{
import flash.display.Sprite;
import flash.events.Event;
/**
* ...
* #author Brian Hodge
*/
public class SomeClass extends Sprite
{
public function SomeClass()
{
if (stage) _init();
else addEventListener(Event.ADDED_TO_STAGE, _init);
}
private function _init(e:Event = null):void
{
//You may now access the stage property of the DisplayObject.
stage.addEventListener(Event.RESIZE);
}
}
}
When I debug my code nothing appears on screen. I've rechecked the code and consulted with others yet nothing appears. My html template is fine.
package {
import flash.display.Sprite;
import flash.events.*;
public class asgnv2 extends Sprite
{
var lineY = 0;
public function asgnv2()
{
stage.addEventListener(Event.ENTER_FRAME, update);
graphics.lineStyle(1);
}
function update(e){
graphics.clear();
graphics.moveTo(0 ,lineY);
graphics.lineTo(100, lineY);
lineY+=0.5;
}
}
}
unless asgnv2 is Document class, it is not going to work, as you are registering ENTER_FRAME event on the stage inside the constructor of asgnv2. A DisplayObject can not access stage property until it is added to Stage Display List. So try the following. public function asgnv2(){
this.addEventListener(Event.ADDED_TO_STAGE, onAdded);
graphics.lineStyle(1);
}
private function onAdded(e:Event):void {
stage.addEventListener(Event.ENTER_FRAME, update);
this.removeEventListener(Event.ADDED_TO_STAGE, onAdded);
}
private function update(e:Event):void{
//do the stuff
}