Título: Problema con evento KeyDown. Publicado por: Charlie BoT en 21 Agosto 2019, 01:37 am Saludos, les comento que estoy con ganas de hacer un juego simple con gdi+ en mis ratos libres y me dispuse a armar los controles, todo iba sobre ruedas hasta que me encontré con el problema de que si desplazo mi personaje por la pantalla de lado a lado va todo mas que bien. El problema viene al intentar simular un salto usando dos rutinas una para ascender y otra para descender que funcionan muy bien pero uso la barra de espacio para saltar y las flechas derecha e izquierda para moverme.
me muevo a los lados y si salto el evento keydown cancela la tecla sostenida y da lugar a la nueva pulsada, eso lo comprendo pero no se como emular una solución, si alguien me puede tirar alguna idea me seria de gran ayuda! Dejo lo que tengo por ahora... Código Código: Public Class Form1 Dim jumpLimit As Short = 100 Dim charGround As Short = 200 Private charSize As New Size(30, 30) Private charPos As New Point(200, charGround) Private character As Rectangle Private WithEvents tmrRefresh As New Timer Private GameRefresh As Short = 60 ' ms. Private counterTimer As Short = 0 Private _jumpAction As Byte = 0 Public Property JumpAction() As Byte Get Return _jumpAction End Get Set(ByVal value As Byte) _jumpAction = value Select Case value Case Is = 0 ' De pie. ' ***** Case Is = 1 ' Ascendiendo. Call JumpUp() Case Is = 2 ' Descendiendo. Call JumpDown() End Select End Set End Property Public Sub New() ' Llamada necesaria para el diseñador. InitializeComponent() ' Agregue cualquier inicialización después de la llamada a InitializeComponent(). Me.SetStyle(ControlStyles.UserPaint, True) Me.SetStyle(ControlStyles.AllPaintingInWmPaint, True) Me.SetStyle(ControlStyles.OptimizedDoubleBuffer, True) Me.DoubleBuffered = True tmrRefresh.Interval = GameRefresh tmrRefresh.Start() End Sub Private Sub Form1_KeyDown(sender As Object, e As KeyEventArgs) Handles Me.KeyDown Select Case e.KeyCode Case Is = Keys.Left charPos.X -= 2 Case Is = Keys.Right charPos.X += 2 Case Is = Keys.Space JumpAction = 1 End Select End Sub Private Sub JumpUp() If charPos.Y = jumpLimit Then JumpAction = 2 : Exit Sub If charPos.Y > jumpLimit And JumpAction = 1 Then charPos.Y -= 5 End If End Sub Private Sub JumpDown() If charPos.Y = charGround Then JumpAction = 0 : Exit Sub charPos.Y += 5 End Sub Private Sub tmrRefresh_Tick(sender As Object, e As EventArgs) Handles tmrRefresh.Tick ' Contador de tiempo. If counterTimer < 99 Then counterTimer += 1 : Else : counterTimer = 0 End If If JumpAction = 1 Then JumpUp() If JumpAction = 2 Then JumpDown() Me.Refresh() End Sub Private Sub draw(e As PaintEventArgs) character = New Rectangle(charPos, charSize) e.Graphics.FillRectangle(Brushes.Red, character) End Sub Protected Overrides Sub OnPaint(e As PaintEventArgs) MyBase.OnPaint(e) Call draw(e) End Sub End Class Título: Re: Problema con evento KeyDown. Publicado por: Eleкtro en 22 Agosto 2019, 00:17 am me muevo a los lados y si salto el evento keydown cancela la tecla sostenida y da lugar a la nueva pulsada, eso lo comprendo pero no se como emular una solución, si alguien me puede tirar alguna idea me seria de gran ayuda! La solución es muy simple: ignorar la repetición de tecla generada en el evento KeyDown hasta que la correspondiente tecla sea procesada posteriormente en el evento KeyUp. Para ello, simplemente añade una condición adicional para comprobar si el personaje ya está saltando... Un ejemplo: Código
Saludos. Título: Re: Problema con evento KeyDown. Publicado por: Charlie BoT en 22 Agosto 2019, 01:42 am Bueno primero que nada te agradezco la ayuda elektro...
Probé tu sugerencia y no soluciona el problema, porque mi personaje pierde su movimiento hacia los lados. Lo que yo pretendo es que si yo voy avanzado hacia la derecha y sin soltar la tecla de avance presiono la de salto (SPACE) que el personaje no cancele el avance y ejecute su salto sino que si voy avanzando y se ejecuta el salto, el salto sea hacia arriba y siga avanzando porque no he soltado la tecla direccional. Esto es lo mas necesario en un juego dado a que nadie va poder jugar bien a un juego donde la dirección se suelta y esperar a que salte para comenzar a direccionar el salto, es algo que en los juegos se hace en simultaneo.. Se que no es imposible de hace, pero en este momento no se me ocurre una solución :-\ Título: Re: Problema con evento KeyDown. Publicado por: Eleкtro en 22 Agosto 2019, 11:11 am Lo que yo pretendo es que si yo voy avanzado hacia la derecha y sin soltar la tecla de avance presiono la de salto (SPACE) que el personaje no cancele el avance y ejecute su salto sino que si voy avanzando y se ejecuta el salto, el salto sea hacia arriba y siga avanzando porque no he soltado la tecla direccional. Pensé que el problema principal que describiste era que el salto se repetía por mantener presionada la tecla de salto. De todas formas creo que tu programa debería determinar si el personaje se está moviendo para evitar que se cancele el desplazamiento a izquierda o derecha cuando se presiona la tecla de salto, entonces podrías empezar por declarar una variable con nombre "isMoving" para ello, e intentando adaptar el código del ejemplo de arriba a tus necesidades... No me atrevo a sugerir más ideas ni realizar modificaciones al código que mostraste por si en lugar de ayudar consigo lo contrario, ya que la programación orientada al gaming no es lo mio, y, aunque con el suficiente tiempo examinando el código que mostraste + ensayo y error podría encontrarte una solución, seguro que no sería la solución más óptima o estandarizada para este tipo de situaciones en programación de video juegos. es algo que en los juegos se hace en simultaneo.. Se que no es imposible de hace, pero en este momento no se me ocurre una solución :-\ Ya, bueno, imposible no es, pero no es lo mismo hacer todos los cálculos y operaciones necesarias a pelo (con el lenguaje que sea), que utilizar un framework para abstraer cierta complejidad... (ej. Unity: https://forum.unity.com/threads/how-to-make-a-jump-in-c.40411/ ) Se que no es de mucha ayuda lo que te dije, pero de todas formas aquí deberías encontrar alguna solución:
Fíjate que en los códigos que encontrarás suele haber ciertos factores definidos de forma arbiraria como velocidad y gravedad, y con ello se consigue hacer el salto en movimiento, por lo que quizás esto pueda ser un indicativo de que el planteamiento de tu código sencillamente no sea el más adecuado para llevar a cabo el control de movimiento y salto del "personaje". Creo que deberías examinar algunos ejemplos de los resultados de Google, a ver si sacas algo más en claro. PD: ¿donde está el usuario Abderramah cuando se le necesita?. jeje. Saludos. |