¿Navegar entre SWFs?
5 seguidores
Tengo un SWF (A) desde el cual quiero navegar a un SWF (B). No necesito conservar absolutamente nada del anterior (variables, estados, etc.) En AS2 bastaba con root.loadMovie("movie2.swf") para reemplazar todo.
Segun entiendo si lo hago en AS3 sin borrar todas las variable y objetos se me va a ir saturando la memoria.
¿Alguien sabe como puedo hacer esto en AS3 fácil?
Algo asi como navigateToURL(new URLRequest("b.swf"), this)
oskitar
Para que un objecto pueda ser elegido para el garbage collection tienes que desactivarlo, esto incluye:
* eliminar los métodos de los eventos
* parar los timers
* detener la película a eliminar si es un movieclip
* desactivar también los objetos que contenga
Create un método en la película que quieres eliminar que haga todo esto, elimínalo del displayList y asigna el objeto a null.
Una buena práctica siempre que se haga una suscripión a Timers y eventos para un objeto es proveer un método para desuscribirse de esos eventos y Timers, yo suelo pasar la suscripción de eventos a una función propia y a continuación escribir la función que los elimina.
Para más referencias puedes mirar el capítulo 14 del Essential actionscript de O'Reilly
Usuario desconocido
Pensé que existía algún truco sencillo como destruir el Stage o el loader de toda la movie, pero por lo visto no es tan sencillo. Gracias por la respuestas voy a leer el libro que me recomiendas.
tpmmds
Hola:
Añadir a lo comentado que también hay que "cerrar todos los canales abiertos", por así decir: Sonidos, enlace a al cámara web, localconnection, socket... TODO. Especialmente si se tienen sonidos reproduciéndose hay que detenerlos, y si este swf cargado también carga recursos con Loader.
Tambien es conveniente, cuando se registra el detector con addEventListener, hacer la referencia débil, pasándole el 5º parámetro como "true". O sea cuando se registra el detector escribir todo este rollo :
boton.addEventListener(MouseEvent.MOUSE_DOWN, onMouseDownHander, false, 0, true)
Y otra cosa que también ayuda: cruzar los dedos cuando estés probando si se libera la memoria ;-)
A mí esta filosofía de Flash, de que TODO esté a la vista de TODOS me desconcierta bastante. Es cierto que ayuda al principio y puede facilitar las cosa. Es muy cómodo cargar un swf y poder controlarlo desde la aplicación que lo carga prácticamente sin limitaciones; pero claro, después tienes todos estos problemas. Yo preferiría que el swf cargado fuese POR DEFECTO opaco en todos los sentidos a la aplicación que lo carga, y que fueses tú, cuando estimes oportuno, el que dejes visibles las cosas que te interesan.
Aparte de los sonidos, hay otra cosa que suele dar muchos problemas: las fuentes incrustada. Esa, a priori, ventaja de las fuentes, que una vez cargadas, están disponibles para cualquier swf que se cargue con posterioridad, puede ser una fuente de problemas cuando el proyecto cambia de manos. Me explico: imaginemos una aplicación que hace una persona, y decide incrustar todas las fuentes que va a utilizar en un swf llamado Recursos.swf que carga al principio de todo. Una vez cargado dicho swf, las fuentes ya están disponibles y cualquier swf cargado con posterioridad pude utilizarlas. Este proyecto cambia de manos, y si no está documentado, o el nuevo desarrollador no se lee esa parte, le va a parecer casi mágico uqe en la tercera sección, "Clientes internacionales" aparezca texto en chino, si no ve las fuentes incrustadas por ningún sitio ;-)
Vaya rollo que he soltao'
Un saludo.
Ventd'Aval
En flashplayer 10 tienes el metodo Loader.unloadAndStop que, en principio, se dedica recursivamente a cerrar, parar, y borrar todo lo que haya de un swf cargado... por lo que, a menos que hayas creado alguna referencia externa (desde el swf al "exterior" o desde el padre a algun elemento dentro del swf) debiera quedar elegible para el GC.
Yo coincido con tpmmds en que veo todo este tema un poco mal estructurado de raiz por adobe, la posibilidad de encapsular completamente un swf (que se puede con workarounds de subdominios y tal, pero es un rollo) o de explicitamente borrar algo de memoria me parece fundamental para una plataforma como flash. ¿No os parece mas lógico que en vez de desenlazar un objeto y rezar para q lo quite el GC y no se nos haya olvidado ninguna referencia, podamos simplemente hacer un "delete objeto;", y que cualquier referencia activa cante error porque ya no existe el objeto?
tpmmds
Hola, Ventd'Aval:
Claro. Y es que además, Flash es tremendamente asimétrico: es muy fácil "crear" cosas y bastante complicado "deshacerse" de ellas. Me viene a la cabeza la gente que utiliza templates en los que cada sección de la aplicación es un swf que se va cargando y descargando, algo que incluso puede pasar desapercibido para el que lo está "customizando" y le aparece el típico problema de música que sigue sonando, o que cada vez la aplicación va más lenta y maaaaas leeeenta... Lo que comentas de Loader.unloadAndStop no lo conocía, voy disparado a probarlo :-)
Un saludo.
tpmmds
Hola, de nuevo:
Lo estoy viendo ahora mismo en la API de FP10, y parece que Adobe ha oído nuestras súplicas
Un saludo
tpmmds
Hooola de nuevo:
Parece que funciona... salvo con la clase Bitmap/BitmapData. He estado cargando/descargando swf's con audio, loaders, animaciones y demás, y parece que todo bien; pero cuando he probado con alguno que llevaba algún efecto/filtro, no libera la memoria. Bueno, nadie es perfecto, pero al menos ha solucionado el engorroso tema del audio. Más de uno suspirará aliviado ;-)
Un saludo.
Usuario desconocido
Wow!! Al parecer me funciona perfecto el método "Loader.unloadAndStop"! Muchas gracias!!
Aun así coincido con que adobe debería crear "Ambiente Independiente" si asi uno lo desea, a la hora de cargar un swf externo.
dourado
BuenAS :)
mmm.... duda chicos(no me maten por esto :) ) .. y es posible saber que pasa con el GC... o sea hacer un "trace" o algo similar para saber lo que realmente está borrando y que cantidad real de memoría se está liberando, al final sería monotorizar que ocurre. ¿Se puede?
Salud++
tpmmds
Hola:
En Flex tienes la posibilidad de hacer un profile de la aplicación (un análisis del consumo de memoria, número de instancias de cada clase, disparar el garbage collector, etc.) y en este sentido es muy práctico. En Windows tienes la posibilidad de abrirte el administrador de tareas (Ctrl+Alt+Sup) e ir viendo si se va liberando memoria; es un poco más "casero". Imagino que debe existir alguna aplicación que monitorice la memoria, pero no conozco ninguna. También tienes la clase System.totalMemory que te muestra la cantidad de memoria que en cada momento ocupa Flash Player, deberías hacerle un trace cuando te interese, o mostrar su valor en un textField. Estas opciones no las utilizo mucho, ya que como digo empleo la herramienta profile de Flex.
Un saludo.
P.D.: Si alguien coge el hilo en este punto, recordar que esto es válido SÓLO para Flash Player 10 (Flash CS4)
dourado
BuenAS Tpmmds,
Ya me imaginaba que flex lo podría hacer, desconocía System.totalMemory :)
El metodo casero en mi caso uso el Activity Monitor del OS´x.. pero lo veo chungo que la IDE de flash lo hayan metido nada en ese sentido.
GraciAS
Ventd'Aval
Con Flash se suele usar algun medidor de fps/memoria... yo me hice el mio en su momento, lo puedes bajar aqui:
http://www.ventdaval.com/upload/archivos/cl.rar
Se pone simplemente asi:
import cl.cay.utils.*;
addChild(new FPSCounter());
En swfs medianamente complejos, suele haber un pico de fps cada vez que pasa el GC, y con suerte un bajon en memoria ^^
dourado
Buenas Vent!
Tengo algo muy similar con la diferencia de que no tenía la parte de la memoria.
Me va muy bien, gracias ;)