Fandom

Touhou en Español

Danmakufu: Como Empezar

1.342páginas en
el wiki}}
Crear una página
Discusión0 Share

¡Interferencia de bloqueo de anuncios detectada!


Wikia es un sitio libre de uso que hace dinero de la publicidad. Contamos con una experiencia modificada para los visitantes que utilizan el bloqueo de anuncios

Wikia no es accesible si se han hecho aún más modificaciones. Si se quita el bloqueador de anuncios personalizado, la página cargará como se esperaba.


Marco BasicoEditar

Todos los lenguajes de programación (que yo sepa) requieren algún tipo de marco (o Framework) para que todo lo demás sea leido en Danmakufu. El siguiente es el marco para Danmakufu. Los animo a seguir adelante y crear una carpeta en el directorio script llamado "tutorial" y pegue el siguiente código en un nuevo archivo .txt para que tengas algo para experimentar con lo de seguir este tutorial. Si la secuencia de comandos le pasa algo que le impida funcionar y no tienes idea de cómo solucionarlo, solo copia-pega de nuevo.


#TouhouDanmakufu
#Title[Attack Name]
#Text[Attack Description]
#Image[.\img.png]
#BackGround[User(.\bg.png, 1, 1)]
#BGM[.\bgm.mp3]
#PlayLevel[Normal]
#Player[FREE]
#ScriptVersion[2]

script_enemy_main {
    @Initialize {
    }

    @MainLoop {
    }

    @DrawLoop {
    }

    @Finalize {
    }

    @BackGround {
    }
}

Si intenta ejecutar este script en Danmakufu, te darás cuenta que no hace absolutamente nada. De hecho, el jefe muere cuando empieza el juego porque no hay una función que fija su valor de vida. Por ahora, sin embargo, vamos a meterse con algunos de los valores en el marco de darle una idea de lo que realmente hacen.


#TouhouDanmakufu
Esto le dice Danmakufu que el este archivo es un script para Danmakufu. En concreto, se está diciendo Danmakufu que es un solo ataque de un jefe. Si elimina esta línea, verá que el programa ya no lo tiene en la lista como una secuencia de comandos ejecutables, incluso si es el ataque más impresionante en el mundo. Sin embargo, no todo lo que usted crea con este programa será un solo ataque. Con #TouhouDanmakufu[plural], le está diciendo Danmakufu que este script es un jefe con múltiples ataques. Con #TouhouDanmakufu [Stage], está diciendo que el script es una etapa. Y por el #TouhouDanmakufu[Player], está diciendo que el script es un personaje jugable. Por ahora, sólo se va a utilizar #TouhouDanmakufu


#Title
En pocas palabras basta, este ordena a Danmakufu lo que desea mostrar como un nombre para este script en particular cuando se está en la lista en el programa como un script ejecutable. Si pones #Title [Lol], entonces se mostrará como "Lol". Si pones #Title [Sanae is a good girl], se muestra como "Sanae is a good girl". Siga adelante y cambia el texto al lado de #Title, despues comprueba en el programa para ver de lo que estoy hablando. (Asegúrese de guardar el archivo .txt cada vez que desee ejecutar el script para que Danmakufu ejecuta la versión correcta. De lo contrario, se ejecutará la ultima version sin guardar y los cambios no habran aparecido.)


#Text
Esto es similar a #Title. En lugar de afectar el título, sin embargo, afecta a la descripción de la secuencia de comandos cuando el título se resalta. Asimismo, esta directiva es opcional. Puede eliminar esta línea y no hay ninguna descripción se mostrará.


#Image

Esto determina la vista preliminar que se muestra cuando el título resalta en Danmakufu. Se pueden emplear los tipos de imagenes más comunes, como por ejemplo JPG, GIF o PNG. Para elegir la imagen que deseas mostrar, solo has de saber donde se encuentra. De momento, nos limitaremos a copiar una pequeña imagen en la carpeta "tutorial" ya creada, (se supone) y renombrala como "image.jpg" (pero si deseas ponerle otro nombre no hay problema). Ahora, cuando pongas #Image[.\image.jpg](o el nombre que le hayas dado), guarda el script y la imagen deberá aparecer al seleccionar la secuencia de comandos en Danmakufu. Examinando el texto ".\Image.jpg" deberías de ser capaz de decir que el período en el comienzo señala el directorio en el que se encuentra el script actualmente. Si la imagen no está en la carpeta, pero está en otra llamada imágenes dentro de la carpeta "tutorial", necesitarás agregar ".\imágenes\image.jpg" en el apartado "#Image" del archivo .txt para poder encontrar la imagen. Si la imagen está en la carpeta donde se encuentra la carpeta "tutorial", deberás agregar ".\nombre de la carpeta\imágenes\image.jpg" para indicar el directorio donde el script se encuentra.

Esto también es opcional y se puede eliminar sin afectar la viabilidad del script.


#BackGround

Esto raramente es utilizado porque @Background es mucho más flexible, pero más adelante #Background se utiliza para generar un "tiled scrolling background" con una imagen que usted mismo proporciona o un fondo predeterminado integrado en el sistema. Para empezar, los fondos por defecto. Que yo sepa, solo hay dos, "Default" y "Ice Mountain". Si reemplazas el texto entre corchetes de esta directiva, podrás ver lo que aparece. Si lo que quieres es usar una imagen para crear un "tiled background", tendrás que utilizar User(imagedirectory, x, y). "Imagedirectory" es donde se ha de poner el directorio donde se encuentra la imagen como explicamos en la anterior sección, "x" en la velocidad a la que se despazará el fondo de izquierda a derecha e "y" es la velocidad a la que el fondo se desplazará de arriba a abajo. Vamos a usar la imagen que usamos para el apartado #Image, asumiendo que la imagen está justo al lado del archivo de comandos, el directorio es .\image.jpg. Vamos a poner el valor 1 a "x" e "y". Ahora, debería quedar algo como esto: #Background[User(.\image.jpg, 1, 1)]. Si se ha hecho correctamente, al ejecutar el script ahora, debería existir un "tile background" a partir de la imagen que se desplaza en diagonal. Puedes probar diferentes números con "x" e "y" para ver como afecta el desplazamiento del fondo, teniendo en cuenta que los negativos y los decimales son compatibles.

Esto también es opcional y se puede eliminar sin afectar la viabilidad del script.


#BGM

Esto le indica a Danmakufu la música que se ha de reproducir durante el juego. La música se selecciona igual que las imágenes, así que pondremos un archivo mp3 en la carpeta "tutorial". Comprueba que Danmakufu puede reproducir la música sin tener que indicarle exactamente que poner en los corchetes.

Esto es opcional y se puede eliminar sin afectar la viabilidad del script.


#PlayLevel

Esto agrega texto al lado derecho de la pantalla. Básicamente existe para identificar si el script mostrará "Lunatic" o "Easy" en el lado de la pantalla. Realmente, esto no es importante, así que la mayoría de personas no lo utilizan, pero, si de todas formas quieres diferentes dificultades en su script, puedes indicar un nivel de dificultad con esta función.


#Player

Esto le indica a Danmakufu que personajes pueden ser usados en el script. Para elegir que personajes se permiten, debes saber donde está el script de los personajes. En la mayoría de los casos, van a estar en la carpeta "player" de Danmakufu, como el personaje jugable "Rumia", que biene incluido con el programa. Para referite a este directorio, tendrás que utilizar "player\Rumia\Rumia.txt". Como ya debes saber, hay tambien cuatro personajes jugables ya integrados en Danmakufu: "ReimuA", "ReimuB", "MarisaA" y "MarisaB". Obviamente, no están almacenados en ningún diectorio. Debes referirte a ellos como REIMUA, REIMUB, MARISAA y MARISAB (las mayusculas son necesarias). Para matar dos pájaros de un tiro puedes referirte a ellos como REIMU (para añadir tanto a ReimuA y ReimuB en la lista de personajes jugables) y Marisa (igual que antes). Finalmente, eres libre de colocar todos los personajes en la carpeta "player", así como los cuatro ya nombrados, ya listos para su uso. He aquí un ejemplo donde los personajes "ReimuB", "MarisaA", "MarisaB" y "Rumia" están disponibles: #Player[REIMUB, MARISA, player\Rumia\Rumia.txt].

Esto es opcional, pero si es eliminado pasa automáticamente de forma predeterminada a libre.


#Script version

No sé muy bien que hace esto, pero siempre lo tengo y no lo cambio.


script_enemy_main

Esto indica el comienzo del script que dicta el comportamiento del enemigo. Antes de nada, debes declarar las variables y crear las funciones que se van a usar con más frecuencia. Te explicaré como hacerlo más adelante.


@Initialize

Aquí es donde debes poner las cosas que solo se mostrarán una vez en el comienzo del script, como la vida del jefe, la puntiación, el nombre de la "spell card", el contador de tiempo, etc. Te explicaré como hacerlo más adelante.


@ MainLoop

Aquí debes indicar como quieres que se comporte el enemigo. Puedes indicar cosas como su danmaku o su movimiento. Te enseñaré más adelante.


@DrawLoop

Aquí es donde debes poner cómo quieres dibujar las cosas. Por favor, diríjase a Nuclear Cheese's Danmakufu Drawing Tutorial para más información sobre como utilizarlo (siento que esté en inglés).


@Finalize

Aquí es donde debes poner cosas que sólo ocurran una vez al final, como la caída de "power ups" y puntos o eliminar el "sprite" del jefe.


@Background

Aquí es donde puedes controlar el comportamiento del fondo. Esto sustituye cualquier comando introducido en #Background si se dió el caso y todo lo dibujado en esto, se dibuja detrás de cualquier cosa dibujada en @DrawLoop (esta parte me lió un poco a la hora de traducir, lo siento). Al igual que antes, diríjase a Nuclear Cheese's Danmakufu Drawing Tutorial para más información.


Notas

Fíjate en todos esos corchetes (estas cosas "{" y "}"). Asegúrate de que siempre están ahí. Esto indica al Script cuando comienza y termina cada sección. Si tienes una cantidad desigual o si están colocados incorrectamente, Danmakufu generará un error.

De hecho, Danmakufu probablemente generará el error la mayoría de veces en las que estás intentando crear algo. Si no eres capaz que pequeño error hace funcionar mal a Danmakufu, es que definitivamente no estás preparado para aprender a usar Danmakufu. O cualquier otro lenguaje de programación.

Variables e Instrucciones de ControlEditar

Las variables y las instrucciones de control són herramientas imprescindibles para crear cualquier cosa en Danmakufu. Si no existiesen, el programa sería inútil.


VariablesEditar

Las variables almacenan información para un uso posterior. Se pueden utilizar para almacenar números (e.g. 14, 2398.37, -583), cadenas ("Hello, world!", "2957 is a number", ":V"), y booleanos

(true, false). Para crear una varible, todo lo que has de hacer es poner "let test;". "Test" es el nombre de la variable. Esto, básicamente se traduce por "Crea una variable llamada "test". Asegúrate de que el punto y coma (";") está ahí, porque significa el fianl de un comunicado. Al crear una variable, también se le puede dar un valor inmediato en la misma línea: let test = 500;. Esto, básicamente se traduce a "Crea una variable llamada "test" con una valor inicial de 500." Otra vez asegúrate de que el punto y coma está ahí, porque Danmakufu es muy exigente y generará un error si no sabe donde está el final de la instrucción. Asegúrate de que cuando crees variables, nunca le des a dos variables el mismo nombre o un error se generará y el script se dará por terminado cuando se ejecute.

Para cambiar el valor de una variable, todo lo que tienes que poner es test = 501;. Esto se traduce a "Establece una varible de nombre "test" a la igualdad de 501." También puedes ajustar el valor de una variable utilizando las matemáticas, como esto: test = 14*37-199/34+13;. También puedes ajuster el valor de una variable con sede fuera de su valor actual. Por ejemplo, si el valor actual de "test" es 20 y tu pones: test = test + 5;, el valor de "test" pasa a ser 25. Hay un camino más corto para escribir esto "test += 5;" significa lo mismo que "test = test + 5;". Del mismo modo que "test -= 5;" es lo mismo que test = test - 5;. Esto sirve tanto para la suma (+) como para la resta (-) al igual que con la multiplicación (*) y la división (/). Es cuestión de cambiar el signo.

También puedes usar otras variables cuando se cambia el valor de una variable diferente. Si hubiese otra variable llamada "test2", con un valor de 18, la línea sería así: test = test2 + 34;. causaría que "test" asumiese el valor 52 mientras que "test2" se quedaría en 18.

Las mareices (array) son otro tipo especial de variables capaces de almacenar diferentes valores con el mismo nombre. Se crean de la misma manera, pero se definen como "array" cuando se establezcan de manera específica después del signo igual. He aquí una linea para crear una matriz: let array = [4, 1, 6, 3, 5, 2];. Como puedes obsevar, ahora hay almacenados seis valores bajo el mismo nombre. Para llamar a un valor específico, escribe el nombre de la matriz, abre un paréntesis, inserta un número y cierra el paréntesis. Por ejemplo, si después de crear la matriz, yo tubiese que escribir en la línea let something = array[4];, la nueva varible "something" tendría un valor de 5 puesto que ese fué el cuato valor en la matriz (el valor 1 para nosotros, es 0 para la computadora). Cambiar el valor de una matriz también es similar. "array[0] = 1;" causará que ahora, la matriz sea [1, 1, 6, 3, 5, 2].

El tamaño de una matriz es constante, así que despues de hacer una, debe asegurarse de que nuncá pondrá algo que va más allá de su límite. Por ejemplo, "array[6] = 9;" haría que se produjese un error porque no hay un valor 6 en los cambios de la matriz que había creado. Hay pocas operaciones que trabajen con matrices.

Aritmética: el primer elemento es operado con el primer elemento, el segundo con el segundo, etc. Esto solo funciona si las matrices tienen la misma longitud.

[2, 4, 7] + [1, 5, 2] = [3, 9, 9]
[2, 4, 7] - [1, 5, 2] = [1, -1, 5]
[2, 4, 7] * [1, 5, 2] = [2, 20, 14]
[2, 4, 7] / [1, 5, 2] = [2, 0.8, 3.5]

También puedes combinar las matrices o agregar valores.

[2, 4, 7] ~ [1, 5, 2] = [2, 4, 7, 1, 5, 2]
[2, 4, 7] ~ [1, 5] = [2, 4, 7, 1, 5]
[2, 4, 7] ~ [1] = [2, 4, 7, 1]

O eliminar valores

erase([2, 4, 7], 0) = [4, 7]
erase([2, 4, 7], 1) = [2, 7]
erase([2, 4, 7], 2) = [2, 4]


Instrucciones de controlEditar

Las instrucciones de control dirijen el flujo del script. Esto determina cuando deben suceder las cosas como cuando deben lanzarse las balas, cuando ha de moverse el jefe, o cuando un efecto especial debe ser creado. Sin esto, todo sucedería unavez por "frame", o 60 veces por segundo, independientemente de cualquier condición.

Hay muchos tipos diferentes de instrucciones de control que te ayudan a dirigir el flujo, pero antes de hablar de ellos, primero tendrás que saber algunos operadores booleanos, o comparaciones:

==: Esto quiere decir "es igual a". 12==12 es verdad. 28==2 es falso. 8==14 es falso.
!=: Esto quiere decir "no es igual a". 12!=12 es falso. 28!=2 es verdad. 8!=14 es verdad.
>: Esto quiere decir "es mayor que". 12>12 es falso. 28>2 es verdad. 8>14 es falso.
<: Esto quiere decir "es menor que". 12<12 es falso. 28<2 es falso. 8<14 es verdad.
>=: Esto quiere decir "es mayor o igual a". 12>=12 es verdad. 28>=2 es verdad. 8>=14 es falso.
<=: Esto quiere decir "es menor o igual a". 12<=12 es verdad. 28<=2 es falso. 8<=14 es verdad.

&&: Esto quiere decir "y". Si dos enunciados verdaderos están unidos con && como un solo enunciado, esta afirmación es verdadera.
    De lo contrario, es falso.

||: Esto quiere decir "o". Si dos enunciado falsos se unen con || como un solo enunciado, esta afirmación es falsa. De lo contrario, es verdad.

Y ahora las sentencias de control reales. La más comun es el enunciado "si", puede ir seguido por más enunciados, aunque depende de lo que estés tratando de lograr. La instrucción "si" trabaja del mismo modo que en la vida real. Por ejemplo, la frase "si duermes, sueñas" significa que soñarás sólo mientras duermes. Del mismo modo, la instrucción en Danmakufu, if(PowerLevel > 9000){VegetaScreams = "It's over nine thousand!";} significa que la variable "VegetaScreams" almacenará la cadena "It's over nine thousand!" solamente si la variable "PowerLevel" es mayor que 9000.

Básicamente, la estructura de una instrucción "if" es: "if"(requerimientos){pasan cosas}. Sin embargo, es mucho mejor que la organices así:

if(requirements){
   something happens;
   something happens;
   something happens;
}

De esta manera, si múltiples cosas están ocurriendo como en este caso, es mucho más facil ver lo que está pasando. Ten en cuenta que si los requisitos no se cumplen, Danmakufu omitirá las cosas que suceden entre las llaves. Si pones {algo pasa} después de cerrar la llave de una instrucción "if", se saltará esa zona.

if(requirements){
   something happens;
   something happens;
   something happens;
}else{
   something else happens;
   something else happens;
   something else happens;
}

En este caso, si se cumplen los requisitos, algo ocurrirá en tres ocasiones. Si los requisitos no se cumplen, otra cosa ocurrirá en tres ocasiones. Ten en cuenta que esta configuración, algo y otra cosa, no pueden ocurrir al mismo tiempo. Es uno o el otro. Hay una variación de la instrucción "if" llamada "alternative". Se utiliza cuando hay más de dos resultados. He aquí un ejemplo:

alternative(variable)
case(1){
   x+=5;
}
case(2){
   x-=5;
}
case(3){
   x+=2;
}
others{
   x=0;
}

Lo que este fragmento de texto significa básicamente es "Mira la variable llamada "variable". Si es igual a 1, acontinuación añade 5 a la variable "x". Si es igual a 2, resta 5 a la variable "x". Si es igual a 3 añade 2 a la variable "x". Si se trata de otra cosa, haz que la variable "x" almacene el valor 0". Como puedes ver, "alternative" es una forma abreviada de escribir una larga instrucción "if"´.


Otra instrucción de control común es "loop". Esto es más facil de usar y entender que "if" y "else". Supongamos que quieres que algo ocurra múltiples veces, pero no quieres tener que escribir lo mismo una y otra vez. Aquí es donde la instruccióm "loop" entra en juego. La estructura de una instrucción "loop" es la siguiente:

loop(20){
   something happens;
}

El número entre paréntesis le indica a Danmakufu cuantas veces ha de ejecutar lo que está en los corchetes. En esta configuración, algo pasará 20 veces, "loop" también se conoce por tiempo. Si no pones un número dentro del paréntesis, crearás un bucle infinito y tendrás que finalizar la tarea Danmakufu a menos que uses "break". "Break" inmediatamente sale justo después del próximo corchete cerrado ("}").

while(variable<10){
    something happens;
}

En este ejemplo, algo continuará sucediendo hasta que la variable "variable" sea inferior a 10. Si es menos de 10, entonces algo no pasará cuando el programa llegue a esta parte del script. Ten en cuenta que el programa no pasará esta parte hasta que la variable sea inferior a 10, por lo tanto, en este caso se ha creado un bucle infinito. Para contrarrestar esto, puedes poner algo en las llaves que cambie el valor de la variable, de manera que. eventualmente, causará que se convierta en mayor o igaul a 10. "break" también se puede usar para salir del bucle infinito.

Por último, están el "ascent" y el "descent" como instrucciones de control, que son similares a "loop". La diferencia es, que implican una variable, que aumenta o disminuye en 1 cada bucle hasta alcancar el límite que decidas. La variable que se utiliza para esta instrucción no tiene que ser creada con "let" ("let" ya lo hemos visto antes, se supone).

ascent(i in 0..5) {
   array[i] = i;
}
descent(i in 0..5) {
   array[i] = i;
}

En estos dos casos, la variable utilizada es "i" y los números van del 0 al 5. Los dos frágmentos de código (arriba) vendrían a ser lo equivalentes a los siguientes dos fragmentos de código, respectivamente.

array[0] = 0;
array[1] = 1;
array[2] = 2;
array[3] = 3;
array[4] = 4;
array[4] = 4;
array[3] = 3;
array[2] = 2;
array[1] = 1;
array[0] = 0;

Notas: Cuando crees variables e instrucciones de control, algo pasa donde se encuentra la variable utilizada.

let variable1 = 0;
loop(5){
   let variable2 = variable1;
   variable2 += 10;
}
variable1 = variable2;

En este ejemplo, se creará un error. ¿Por qué? Tiene que ver con el ámbito en que las variables pueden ser utilizadas. En "loop" se llama "variable1", algo perfecto, pero una vez salido de "loop", es "variable2", algo que no está permitido. Esto es porque cada vez que Danmakufu llega al final de "loop", "variable2" deja de existir. Esto también explica porque 5 variables con el mismo nombre, al parecer pueden existir (aquí no se da el caso). Básicamente, a las variables en el interior no se puede acceder de forma externa, pero a las variables externas si se puede acceder desde el interior.


Iniciando Una Lucha Contra el JefeEditar

Ahora, finalmente llegamos a la parte donde se aprende a conseguir que el jefe haga algo. Bueno, más o menos. Aprenderás a configurar la vida de el jefe y cosas por el estilo. ¡Pero esto también es importante!

El siguiente script tiene un montón de cosas en @initialize, la mayoría de los cuales probablemente nunca estará realmente en el mismo tiempo del actual script y una cuantas variables para almacenar un par de valores para que sea más fácil seguirle la pista a la información. También tiene algunas cosas en @DrawLoop y se ha omitido por completo el apartado @Background (@Background es opcional) que debes aprender de Nuclear Cheese's Danmakufu Drawing Tutorial en un futuro (estoy pensando en traducirlo también cuando acabe mis objetivos, me he cansado de verlo todo en inglés).

#TouhouDanmakufu
#Title[Boss Initialize]
#Text[Boss Initialization with almost everything you could possibly need stuck in @Initialize]
#Player[FREE]
#ScriptVersion[2]

script_enemy_main {
    let BossImage = "script\img\ExRumia.png";
    let BossCutIn = "script\img\ExRumia.png";
    @Initialize {
        LoadGraphic(BossImage);
        SetLife(100);
        SetDamageRate(10, 10);
        SetTimer(50);
        SetInvincibility(30);
        CutIn(YOUNU, "Spellcard Name", BossCutIn, 0, 0, 200, 600);
        SetScore(500000);
        SetEnemyMarker(true);
        SetDurableSpellCard;
        LastSpell;
        Concentration01(60);
        Concentration02(60);
        MagicCircle(false);
        SetEffectForZeroLife(180, 100, 1);
    }

    @MainLoop {
    }

    @DrawLoop {
        SetTexture(BossImage);
        DrawGraphic(GetX, GetY);
       
    }

    @Finalize {
    }
}

De las cositas que hay en @Initialize, solo te mostraré las más comunes. Si de verdad quieres, también se puede hacer que el movimiento del jefe a un punto específico cuando se genera, dispara alguna balas o lásers o sacar familiares cuando se inicia. Por ahora vamos a seguir por donde me quedé.


LoadGraphic

Esta función carga la imagen que esté referida por la ruta de directorio entre paréntesis, estando lista para ser extraída en @DrawLoop. Otra vez, diríjete a Nuclear Cheese's Danmakufu Drawing Tutorial (esto se está convirtiendo en un día a día).


SetLife

La cosa guay de Danmakufu es que las funciones están muy bien nombradas. Si te fijas en el nombre de la función seguro que serías capaz, en general, de saber lo que hace (a menos que no tengas ni papa de idea en inglés). Es obvio que, SetLife, establece la vida del jefe. Todo lo que has de hacer es poner un valor numérico entre paréntesis. Cuanto mayor sea el número, más tiempo durará la vida de jefe. Si no estableces la vida en un ataque, el jefe muere de manera automática cuando se genera. Nunca pongas el valor entre paréntesis como una variable. El script funcionará, pero tendrás problemas más adelante a la hora de encadenar distintos ataques para hacer un jefe.


SetDamageRate

Esta función determina que porcentaje de la potencia de fuego del jugador hará daño. El primer número es el porcentaje de daño que hará un tiro mientra que el segundo número será el porcentaje de daño que hará una bomba (o spell card del jugador). Por ejemplo, como está ahora: "SetDamageRate(10, 10);", si el tiro del jugador, que normalmente un 10% de daño por golpe y la bomba que normalmente ocupa un 100% de daño, el disparo en realida daña un 1% al jefe y la bomba solo daña un 10%. Si esta función no se conoce, se mostrará como "SetDamageRate(100, 100);".


SetTimer

Otra función bastante obvia. SetTimer establece el temporizador en segundos para que se agote el ataque. Por si no lo sabes, el temporizador se encuentra en la esquina superior derecha, debajo de la barra de vida del jefe cuando se ejecuta el script. Si no estableces el temporizador, el tiempo por defecto será 99 y el ataque no se ejecutará hasta que la vida del jefe llegue a 0. También puedes ajustar el temporizador para que sea mayor a 99, pero el contador mostrará 99 hasta que consiga mostrar un número de dos dígitos.


SetInvincibility

Esta función determinará el tiempo de invencibilidad que tendrá el jefe en "frames" (1 segundo = 60 frames). Por lo general, se utiliza con el fin de evitar que las bombas que acaben con un ataque anterior dañen la siguiente barra de vida. Si no estableces esta función, el valor predeterminado es de 0 "frames" de invencibilidad.


CutIn

Esta función muestra el nombre del ataque, así como un "cut in" en el jefe que tienes que proporcionar. Esta es la función más complicada que has visto hasta el momento con 7 parámetros para llenar. Vayamos por orden. El primer parámetro es el estilo en que deseas que Danmakufu mostre el "cut in". YOUMU hace referencia a Touhou Youyoumu (Perfect Cherry Blossom), mientras que KOUMA hace refencia a Touhou Koumakyou (Embodiment of Scarlet Devil). En el momento de escribir este artículo, estas eran las únicas opciones disponibles para el primer parámetro. El segundo parámetro es el nombre de la spell card entre comillas. Algo como Power Sign "Chaotic Spin" o algo parecido. Sin embargo, puedes observa que si se intenta poner comillas dentro de las comillas, se confunde a Danmakufu (y por tanto se genera un error). Para confundirlo (y confundirte a ti mismo) escribe algo como esto: CutIn(YOUMU, "Power Sign "\""Chaotic Spin"\", BossCutIn, 0, 0, 200, 600);.


Los últimos 5 parámetros son lo que esta función realmente ha de ser (por lo general solo se utilizan para darle nombre a la spell card). El primero de los últimos 5 parámetros es el directorio de la imagen que quieras usar para el "cut in", en este caso, almacenado en la variable BossCutIn. A estas alturas ya deberias saber como funciona eso de los directorios para mostrar las imágenes correctas (si no lo sabes o no te acuerdas, sube la página hasta el apartado #Image). Los últimos 4 determinan los cuatro lados de la imagen (izquierda, arriba, derecha y abajo, en este orden) que se refieren al último parámetro. Generalmente, si tu imagen "cut-in" es sólo la imagen que deseas en lugar de una hoja de sprite, los primeros dos números (izquierda y arriba) serán 0, el tercer número (derecha) será el ancho de la imagen en píxeles, y el último (abajo) será la altura.


SetScore

Esta función establece el "spell card bonus" que se gana al derrotar una spell card sin usar bombas ni morir (lo que se dice capturarla, vamos). Si la función no se establece, el jugador no será recompensado con la bonificación por muy bien que lo haya hecho.


SetEnemyMaker

Esta función determina si el indicador rojo del jefe en la parte inferior de la pantalla se mostrará o no. Se mostrará solo si el valor del paréntesis es verdadero, y si es falso no se verá. Si esta función no se establece, el indicador del enemigo puede aparecer o no dependiendo si se habia establecido la función SetScore. Si SetScore se estableció el indicador se mostrará. De lo contrario, no lo hará.


SetDurableSpellCard

Esta función, se activará cuando se recoja la bonificación de la spell card, incluso si el temporizador se acabó o el jugador no agota la barra de vida del jefe. Si no se establece esta función, una spell card acabada no le dará bonus. Esto no tiene ningún efecto sobre el bono de spell card en lo que respecta a las muertes y las bombas.


LastSpell

Esta función, cuando se determina, desactiva el uso de bombas para un ataque en particular. Si no se determina, se permitirá usar bombas. Además, cuando el jugador es golpeado, el ataque acaba de inmediato y el jugador no pierde vidas.


Concentration01

Esta función crea un efecto especial que hace que, el jefe, parezca que se está cargando de energía. El valor entre paréntesis determina el tiempo en el que el jefe estará cargando energía.


Concentration02

Esta función actúa exactamente igual que la anterior, pero el efecto especial es el de la carga de energía de hielo (es decir, copos de nieve).


MagicCircle

Esta función determina si el círculo mágico alrededor del personaje aparece. Si es verdadero (true) aparece. Si es falso (false) no aparecerá. Si esta función se omite, la forma predeterminada será verdadero (true).


SetEffectForZeroLife

Esta función determina el efecto que se produce cuando la vida del jefe llega a 0. El primer parámetro determina cuantos fotogramas permanecerán el jefe y el efecto. El segundo, determina la intensidad del desenfoque de movimiento de todo lo elaborado con 225 de máxima intensidad. Y el último valor determinará cuanto disminuirá la velocidad cuando el jefe muera. Cuanto más alto sea el número, más lento será el efecto. Conel valor 0 la velocidad no disminuirá y 1 es la velocidad media. Si esta función no se determina, ningún efecto adicional se producirá.


Notas:

Espero que ahora, sepas como crear funciones que trabajen en Danamkufu. Ahí está el nombre de la función (que es este caso es sensible a las mayúsculas), por lo general se usan algunos paréntesis y algunos valores en los paréntesis que determinan los detalles específicos de la función. A estas altura seguramente ya puedas echar un ojo en Touhou Wiki's Danmakufu Section y entender más o menos el significado de la lista de funciones (de momento en inglés, y tal vez en un futuro no muy lejano en español...).

Disparos y Control de BalasEditar

Bien, ahora llega la parte del tutorial a la que seguramente querías haber llegado antes (o simplemente te has saltado todo lo que he traducido antes, táctica muy útil para ciertas cosas...). De todos modos, crea, para empezar un nuevo archivo .txt con el siguiente códogo en él:

#TouhouDanmakufu
#Title[how do I shot bullets?]
#Text[lol i dunno]
#Player[FREE]
#ScriptVersion[2]

script_enemy_main {
    let frame = 0;
    @Initialize {
        SetLife(1000);
        SetEnemyMarker(true);
    }

    @MainLoop {
        SetCollisionA(GetX, GetY, 32);
        SetCollisionB(GetX, GetY, 24);
        if(frame==60){
            CreateShot01(GetX, GetY, 3, GetAngleToPlayer, RED01, 10);
            frame = 0;
        }
        frame++;
    }

    @DrawLoop {       
    }

    @Finalize {
    }
}

Este es un script muy simple para que el jefe, que ahora cuenta con un "hitbox" al que golpear, dispare una bala roja estándar al jugador cada segundo. Vamos a examinar el flujo del programa a medida que lee el script.

En primer lugar crea una variable llamada "frame" y almacena el valor 0 en ella. Luego pasa a @Initialize, donde la vida del jefe se establece a 100 y el indicador del enemigo (la marquita roja abajo del todo donde se señala en que lugar se encuentra el jefe) está habilitado. Por último se dirige a @MainLoop que continuará funcionando una vez por "frame". Para los primeros 60 "throughs" de ejecución, no pasará nada excepto los comandos SetCollisionA(GetX, GetY, 32);, SetCollisionB(GetX, GetY, 24);, y frame++;. SetCollisionA establece la colisión del jefe para que las balas del jugador puedan dañarle. El primer parámetro es la coordenada "x" del centro del círculo de colisión, es segundo, la coordenada "y" y el tercero el radio del círculo de colisión. Te habrás percatado, GetX y GetY fueron utilizados en lugar de números para los dos primeros parámetros. Estas són funciones que encuentran las actuales coordenadas "x" e "y", respectivamente, del jefe. SetCollisonB se utiliza del mismo modo que SetCollisionA, pero el tipo de colisión que se detecta es la que manda el jefe al jugador, lo que causaría la perdida de una vida. Finalmente, frame++ es el equivalente a "frame=1" o "frame=frame+1". Como puedes ver, después de los 60 "throuhgs" de ejecución a través de la variable @MainLoop, "frame", finalmente será igual a 60 y el flujo del script entrará en la sentencia "if" por primera vez.

En la instrucción "if", la función CreateShot1 está habilitada, lo que significa que está listo para una bala roja apuntando directamente hacie el jugador. Este es el comando más básico para disparar una bala y que, junto con muchos otros, se explicará más adelante en esta sección. Después de realizar el disparo, la variable "frame" se establece a 0 de nuevo, haciendo que @MainLoop no haga básicamente nada en 60 "frames" antes de que el flujo de la instrucción "if" entre una vez más. Esto continuará indefinidamente hasta que el jugador agote la vida del jefe. Esperemos que, ahora que se supone que sabes como usar instrucciones de control y variables, puedas controlar lo que sucede y con qué frecuencia. Con solo este simple "set up", la sincronización de todas las balas que quieras disparar pueden ser controladas con la variable "frame" y una o más instrucciones de control.


Bullets Graphics

En la función CreateShot01 que se ha nombrado en el ejemplo anterior, el parámetro RED01 le dice a Danmakufu que dispare una bala roja. Una lista de todos los gráficos de bala están incorporadas en Danmakufu así como los gráficos (ejemplos) que se pueden encontrar aquí. Ve y experimenta con ellos, por ejemplo, sustituye RED01 por GREEN05 o WHITE22.


BulletControl

Danmakufu te da muchas maneras diferentes para disparar balas que varían en el control que tienes sobre la bala, así como la cantidad de potencia de procesamiento que requiere la bala. Vamos en orden, de lo más básico y más fácil de controlar a lo más complejo y difícil de controlar:


CreateShot01

Esta es la función más facil de usar. Los parámetros que pide, en orden, són la coordenada X de partida, la coordenada Y de partida, velocidad, ángulo, gráfico, y retraso. X/Y en el plano de coordenadas de Danmakufu (0,0), es la esquina izquierda. Cuanto más grande es la coordenada X, más a la derecha estará el punto, mientrás que cuanto más grande sea Y, más abajo estará el punto. La velocidad se mide en píxels por "frame" y puede ser tanto decimal como negativo. Para el ángulo, 0 recto hacia la derecha, mientras que 90 es recto hacia abajo. En el ejemplo anterior, se usa GetAngleToPlayer, una función que dirije el ángulo del jefe hacia el jugador. Ten en cuenta que esto no devuelve el ángulo al lugar del que salió la bala hacia el jugador, así que la bala solo tendrá como objetivo al jugador si esta se genera en la parte superior al jefe (y por tanto en el punto GetX y GetY). Los gráficos ya se han explicado en la sección anterior. Por último, relay (retraso) es la cantidad de tiempo (en frames) que la bala se retrasa antes de salir disparada. Antes de ser disparada, se mostrará un resplandor del mismo color en el punto desde el que va a ser lanzada. Para una mejor idea de lo que quiero decir, cambia el valor que hay en el script por uno mucho más grande o mucho más menor para comprobar el efecto.










Si quieres traducir y/o completar la sección, saca la información de aquí: Danmakufu Basics Tutorial

Spotlights de otros wikis

Wiki al azar