pointer to target

HEllo,

I wish to have a visual pointer on the border of the screen to indicates in which direction the target is.

Does someone has already done something like this? Or can give me idea on how to solve this?

Do you rather mean something like a pointer in a fixed place that simply points towards a target (like in some driving games) or something that moves along the screen edge (sometimes seen in FPSs)?

something seen in spatial fps(?). there is a arrow moving along the screen edge to knows where target is, when it is no more on the screen. (I think in Xwing we got this, and in Eve online, and Black Prophecy of course).

Try this:

from direct.showbase.ShowBase import ShowBase


def isInView(obj, camnode=None, cam=None):
    if camnode is None:
        camnode = base.camNode
    if cam is None:
        cam =  base.cam
    return camnode.isInView(obj.getPos(cam))


def sign(number):
    return number / abs(number) if number != 0 else 0


class Follower(object):
    """Onscreen indicator for relationship of a node relative to the camera.
    Shows an indicator at the edge of the screen if target is not in view."""
    def __init__(self, target):
        """Arguments:
        target -- nodepath to follow
        """
        self.target = target
        self.pointer = loader.loadModel("smiley")
        self.pointer.setScale(0.1)
        self.pointer.setColor(1, 0, 0, 1)
        self.pointer.reparentTo(base.aspect2d)
        self.pointer.hide()
        
        self.task = taskMgr.add(self.track, "onscreen follower")
        self.active = True

    def track(self, task):

        if isInView(self.target):
            self.pointer.hide()
        else:
            self.pointer.show()
            x, y, z = self.target.getPos(base.cam)
            # y is unimportant for now
            if abs(x) > abs(z):
                z /= abs(x) if x != 0 else 1
                x = sign(x)
            else:
                x /= abs(z) if z != 0 else 1
                z = sign(z)
            x *= base.getAspectRatio()
            self.pointer.setPos(x, 1, z)
        return task.cont

    def toggle(self):
        if self.active:
            self.pointer.hide()
            taskMgr.remove(self.task)
            self.active = False
        else:
            self.task = taskMgr.add(self.track, "onscreen follower")
            self.active = True
            
    def destroy(self):
        taskMgr.remove(self.task)
        self.pointer.removeNode()


class App(ShowBase):
    def __init__(self):
        ShowBase.__init__(self)
        target = loader.loadModel("smiley")
        target.reparentTo(render)
        target.setY(10)
        f = Follower(target)
        base.accept("space", f.toggle)

App().run()

After starting, move around as you would in pview. If you move the smiley out of the view, a small red sphere will pop up and indicate its direction.

Press space to toggle it.

Nothing to say. It is exactly what I wish to do.
I was not hoping directly the code, but it is perfect.

I will adapt to what I am doing.

Thanks a lot!