# ArDrone can not takeoff if Publisher is call within a Class

**URL:** <https://get-help.theconstruct.ai/t/ardrone-can-not-takeoff-if-publisher-is-call-within-a-class/5026>\
**Category:** ROS Basics In 5 Days (Python)\
**Tags:** error, rospy\
**Created:** [August 29, 2020, 6:24pm UTC](https://get-help.theconstruct.ai/t/ardrone-can-not-takeoff-if-publisher-is-call-within-a-class/5026 "2020-08-29T18:24:51Z")\
**Posts on this page:** 8\
**Page:** 1

<div class="post-metadata">

**Author:** ![qhuy.phm](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/qhuy.phm/32/1396_2.png) [@qhuy.phm](https://get-help.theconstruct.ai/u/qhuy.phm)\
**Post date:** [August 29, 2020, 6:24pm UTC](https://get-help.theconstruct.ai/t/ardrone-can-not-takeoff-if-publisher-is-call-within-a-class/5026/1 "2020-08-29T18:24:51Z")

</div>

Hello everyone,

I got an error in Unit 5: Actions

I tried to create a Class that covers all Ardrone behavior like Takeoff, Land, TakePicture. The problem is that if I call the takeoff() function of the class, the ARDrone does nothings. It only takeoff when the publish command is executed directly in the main function.

Here is my code for reference:

```
#!/usr/bin/env python

import rospy as ros
import actionlib as alib 
from geometry_msgs.msg import Twist 
from ardrone_as.msg import (
    ArdroneAction, 
    ArdroneResult, 
    ArdroneGoal,
    ArdroneFeedback)

from std_msgs.msg import Empty

import time  

class ArdroneController():

    def __init__ (self):
        self.velController = ros.Publisher('/cmd_vel', Twist, queue_size = 1)
        self.velCommand = Twist()   
        self.rate = ros.Rate(1)
        self.is_airbone = False # 0: Landing 1:Airbone
        self.camera = alib.SimpleActionClient('/ardrone_action_server', ArdroneAction)
        self.camera.wait_for_server()
        ros.on_shutdown(self._shutdownhook)
        self.camera_timer = ArdroneGoal()
        
    def _shutdownhook(self):
        ros.loginfo('Terminate Drone operation')
        if self.is_airbone:
            self.land()

    def investigate(self):
        if not self.is_airbone:
            self.takeoff()
        self.camera_timer.nseconds = 10.
        self.camera.send_goal(self.camera_timer, feedback_cb = self._camera_callback) 

    def _camera_callback(self, feedback):
        pass
        # velMess.linear.x = 2.0 
        # velMess.angular.x = 0.1 
        # velMess.angular.z = 0.2

        # velPubl.publish(velMess)

    def takeoff(self):
        message = Empty()
        publisher = ros.Publisher('/drone/takeoff', Empty, queue_size = 1)
        ros.loginfo("Taking Off ...")
        i = 0
        while not i == 3:
            publisher.publish(message)
            time.sleep(1.)
            i +=1
        self.is_airbone = True
            
        # del publisher, message
        ros.loginfo('Taken-Off !') 
                
    def land(self):
        message = Empty()
        publisher = ros.Publisher('/drone/land', Empty, queue_size = 1)
        while self.is_airbone:
            ros.loginfo('Landing ...')
            connections = publisher.get_num_connections()
            if connections > 0:
                publisher.publish(message)
                self.is_airbone = False
                break
        # del publisher, message
        ros.loginfo('Landed !') 

if __name__ == " __main__":
    ros.init_node('ardrone_client_node')
    controller = ArdroneController()
    try:
        controller.takeoff()
    except ros.ROSInterruptException:
        pass

    time.sleep(5)
    # controller.land()

    # message = Empty()
    # publisher = ros.Publisher('/drone/takeoff', Empty, queue_size = 1)
        
    # ros.loginfo("Taking Off ...")
    # for i in range(3):
        
    # publisher.publish(message)
    # time.sleep(1.)
        
    # # del publisher, message
    # ros.loginfo('Taken-Off !')
```

---

<div class="post-metadata">

**Author:** ![simon.steinmann91](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/simon.steinmann91/32/324_2.png) [@simon.steinmann91](https://get-help.theconstruct.ai/u/simon.steinmann91)\
**Post date:** [August 30, 2020, 2:01pm UTC](https://get-help.theconstruct.ai/t/ardrone-can-not-takeoff-if-publisher-is-call-within-a-class/5026/2 "2020-08-30T14:01:47Z")

</div>

Hi @qhuy.phm,  
welcome to the community 🙂 The code you posted is just the action CLIENT, is your action SERVER running in a seperate terminal? If yes, and it doesnt work, please post your server code

---

<div class="post-metadata">

**Author:** ![qhuy.phm](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/qhuy.phm/32/1396_2.png) [@qhuy.phm](https://get-help.theconstruct.ai/u/qhuy.phm)\
**Post date:** [August 30, 2020, 5:55pm UTC](https://get-help.theconstruct.ai/t/ardrone-can-not-takeoff-if-publisher-is-call-within-a-class/5026/3 "2020-08-30T17:55:51Z")

</div>

Hi @simon.steinmann91,

I’m sorry to confuse you. In my code, there are only Publisher and Subscriber implemented, I haven’t touch the Action part yet.  
In order to take-off, I publish an Empty message to the topic /drone/takeoff. It works nicely when executed in the main program (below if **name** == “ **main** ”), but hads no effect when call within class ( ArdroneController.takeoff() )

---

<div class="post-metadata">

**Author:** ![simon.steinmann91](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/simon.steinmann91/32/324_2.png) [@simon.steinmann91](https://get-help.theconstruct.ai/u/simon.steinmann91)\
**Post date:** [August 30, 2020, 6:04pm UTC](https://get-help.theconstruct.ai/t/ardrone-can-not-takeoff-if-publisher-is-call-within-a-class/5026/4 "2020-08-30T18:04:55Z")

</div>

Do you get this in your terminal?

```auto
ros.loginfo("Taking Off ...")

```

meaning, is the function called or not? Perhaps you wanna add a print() to you exception below, or not use Try at all.

---

<div class="post-metadata">

**Author:** ![qhuy.phm](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/qhuy.phm/32/1396_2.png) [@qhuy.phm](https://get-help.theconstruct.ai/u/qhuy.phm)\
**Post date:** [August 30, 2020, 7:02pm UTC](https://get-help.theconstruct.ai/t/ardrone-can-not-takeoff-if-publisher-is-call-within-a-class/5026/5 "2020-08-30T19:02:50Z")

</div>

> [@simon.steinmann91](#):
>
> meaning, is the function called or not? Perhaps you wanna ad

I even got the “Taken-Off” notification. But the drone did not move an inch 🤯

---

<div class="post-metadata">

**Author:** ![simon.steinmann91](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/simon.steinmann91/32/324_2.png) [@simon.steinmann91](https://get-help.theconstruct.ai/u/simon.steinmann91)\
**Post date:** [August 30, 2020, 7:06pm UTC](https://get-help.theconstruct.ai/t/ardrone-can-not-takeoff-if-publisher-is-call-within-a-class/5026/6 "2020-08-30T19:06:31Z")

</div>

You could try a publish loop like this for the takeoff message as well. It ensures that it is really sent. Also check with `rostopic echo /drone/takeoff` whether the message gets sent

> [@qhuy.phm](#):
>
> ```auto
> while self.is_airbone:
> ros.loginfo('Landing ...')
> connections = publisher.get_num_connections()
> if connections > 0:
> publisher.publish(message)
> self.is_airbone = False
> break
> 
> ```

---

<div class="post-metadata">

**Author:** ![eblady](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/eblady/32/6980_2.png) [@eblady](https://get-help.theconstruct.ai/u/eblady)\
**Post date:** [June 3, 2021, 1:31pm UTC](https://get-help.theconstruct.ai/t/ardrone-can-not-takeoff-if-publisher-is-call-within-a-class/5026/7 "2021-06-03T13:31:54Z")

</div>

Hi Simon,

I did that, but the Ardrone is not taking off, even it is not moving at all and the /cmd\_vel, /takeoff and /landtopics are active. But using the command line it works.

Any ideas please?

thanks for your time.

---

<div class="post-metadata">

**Author:** ![hskramer](https://get-help.theconstruct.ai/user_avatar/get-help.theconstruct.ai/hskramer/32/3225_2.png) [@hskramer](https://get-help.theconstruct.ai/u/hskramer)\
**Post date:** [June 13, 2021, 12:08am UTC](https://get-help.theconstruct.ai/t/ardrone-can-not-takeoff-if-publisher-is-call-within-a-class/5026/8 "2021-06-13T00:08:41Z")

</div>

When using a class you need to remember that once you create a object of the class as you do in the line `controller = ArdroneController()` and call a method from the class it must refer back to the object that is why you have the `self` keyword this refers back to the instance/object of the class. So your methods (just a term used to refer to a function that is part of a class) need to have keyword `self` so for the drone to takeoff try:

```
           def takeoff(self): 
                 self.message = Empty()
                 self.publisher = ros.Publisher('/drone/takeoff', Empty, queue_size = 1)
                 ros.loginfo("Taking Off ...")
                 i = 0
                 while not i == 3:
                       self.publisher.publish(self.message)
                       time.sleep(1.)
                       i +=1

```

The use of `self` is required in other parts of your code too. Use this example to fix the rest of your code if you have trouble post again.
