Accessing the parent class in OOP in the right way

I just started OOP programming, and I ran into a domain problem. In the next project, I have a masterClass called App. The application class has screens: the screen class and the navigation class, like children. From the navigation class, I want to control which screens will be displayed. I do not know how to do that...

Please check the code to fully understand my intentions.

Your help is greatly appreciated, I would really like to learn programming, and not just a dirty solution :), but all suggestions are welcome!

// Main Class // public class App extends Sprite { private var screens:Array; private var screen1:Screen; private var screen2:Screen; private var screen3:Screen; private var screen4:Screen; public var currentScreen:String; // private var navigation:Navigation; public function App() { init(); } private function init():void { buildScreens(); buildNavigation(); } private function buildScreens():void { screen1 = new Screen(); screen1.name = 'startScreen'; currentScreen = screen1.name; addChild(screen1); screen2 = new Screen(); screen2.name = 'irrelevantA'; screen3 = new Screen(); screen3.name = 'irrelevantB'; screen4 = new Screen(); screen4.name = 'irrelevantC'; screens = new Array(screen1, screen2, screen3, screen4); } private function buildNavigation():void { navigation = new Navigation(screens); } } // Screen Class // public class Screen extends Sprite { public function Screen() { // creates a new screen } } // Navigation Class // public class Navigation extends Sprite { private var buttons:Array; public function Navigation(screens:Array) { addButtons(screens); } private function addButtons(screens:Array):void { buttons = new Array(); for each(var screen:Screen in screens) { var button:Button = new Button(); button.link = screen.name; button.addEventListener(MouseEvent.MOUSE_DOWN, mouseDown); buttons.push(button); } } private function mouseDown(e:MouseEvent):void { // THIS IS WHAT MY QUESTION IS ABOUT: How should I talk to the parent class in an OOP correct way? // and how can I add and remove a screen in the App class from here? // Here some of my tries // I don't think using parent to get there is a good way because next time it might be; parent.parent.parent trace(e.target.parent.parent.currentScreen); this.parent.currentScreen; stage.App.currentScreen; App.currentScreen; //--------------------------------- } } // Button Class // public class Button extends Sprite { public var link:String; public function Button() { // creates a new button } } 
+4
source share
2 answers

If you directly access parent classes from child objects, you create a strong connection - this is exactly what you do not want in a well-built system. It’s better not to access the application object directly, but to use event listeners and custom events to facilitate change, for example. navigation.

Here is an example. First create a custom event:

 public class MyCustomEvent extends Event { public static const MENU_ITEM_SELECTED : String = "MENU_ITEM_SELECTED"; public var selectedItem:String; } 

Then send the navigation when the button is clicked:

 public class Navigation extends Sprite () { // ... private function onButtonClicked(ev:Event) : void { ev.stopPropagation(); var custEvent:MyCustomEvent = new MyCustomEvent(MyCustomEvent.MENU_ITEM_SELECTED); custEvent.selectedItem = ev.target.name; this.dispatchEvent (custEvent); } // ... } 

Finally, let the application handle the custom event and display a different screen:

 public class App { // ... public function createNavigation () : void { navigation = new Navigation (); navigation.addEventListener (MyCustomEvent.MENU_ITEM_SELECTED, onMenuItemSelected); // ... more stuff happening } // ... private function onMenuItemSelected (ev:MyCustomEvent) : void { switchToScreen (ev.selectedItem); } private function switchToScreen (name:String) : void { // choose screen by name, etc. } } 

For all this, neither the screen nor navigation should know anything about any other involved objects, so you can easily replace each one without disturbing the rest of the system.

+7
source

Basically you want to communicate down (from parent to child), passing references as arguments (as you do with an array of screens) and up (from child to parent), calling public functions.

So, in your case, something like this:

Application Class:

 private function buildNavigation():void { navigation = new Navigation(this, screens); } //etc public function changeScreen(newScreen:int):void{ //Your logic for adding/removing screens goes here } 

Navigation class:

  private var app:App public function Navigation(app:App, screens:Array) { this.app = app addButtons(screens); } private function addButtons(screens:Array):void { buttons = new Array(); for each(var screen:Screen in screens) { var button:Button = new Button(); button.link = screen.name; button.addEventListener(MouseEvent.MOUSE_DOWN, mouseDown); buttons.push(button); } } private function mouseDown(e:MouseEvent):void { app.changeScreens(2); } } 

Obviously, change the implementation to suit your needs (for example, now that you have a link to the application class, consider whether you need to pass a separate link to an array of screens or not) - this is just an example of how you can communicate.

0
source

Source: https://habr.com/ru/post/1400848/


All Articles