¿Deshacer / rehacer rápidamente con el patrón del memento / comando?
Estoy escribiendo una aplicación Java de pintura / gráficos para un teléfono móvil (por lo que la memoria es limitada). El estado de aplicación es esencialmente tres mapas de bits de 1000×500 (es decir, capas de una pintura). La carga de tres mapas de bits toma alrededor de 2 ó 3 segundos.
Estoy tratando de escribir un motor de deshacer, pero no puedo encontrar una buena manera de hacerlo. Los enfoques típicos son:
- Ajustes de optimización de Proguard: Habilitar la combinación de clases, los modelos y el campo / * en versiones modernas de API y Proguard
- Bucle eficiente a través de la lista de Java
- Simple particle system en Android usando OpenGL ES 1.0
- ¿Por qué proguard procesa AndroidManifest.xml?
- Prueba NEON-optimizado cv :: threshold () en el dispositivo móvil
-
Utilice el patrón de comando: Al deshacer, vuelve a cargar el estado del archivo inicial y luego reproduce todos los comandos procesados hasta ahora, excepto el último. Hacer esto ingenuamente significa que espera 2 o 3 segundos para cargar el estado inicial que es demasiado lento. No hay memoria suficiente para almacenar el estado inicial en memoria tampoco.
-
Utilice el patrón de recuerdo: Al deshacer, reemplaza la parte del estado actual que se cambió con el estado antiguo. Esto significa que cada acción necesita guardar bitmaps del antiguo estado en disco porque no hay suficiente memoria en un dispositivo móvil para almacenar esto en la memoria. Como guardar mapas de bits toma tiempo, ¿cómo puedo hacer frente si el usuario decide, por ejemplo, pintar muchos pinceladas en rápida sucesión? No puedo hacerlos esperar.
Todas mis soluciones implican híbridos complejos de los patrones anteriores.
¿Alguien puede sugerir una solución que me permita tener razonablemente rápido deshacer / rehacer para mi aplicación?
- Cómo optimizar las aplicaciones de Android para varios núcleos
- Autocompletar super rápido usando la búsqueda binaria en el archivo clasificado (300000 líneas)
- Demasiadas actividades en Android?
- ¿Cómo puedo activar adecuadamente ACTION_REQUEST_IGNORE_BATTERY_OPTIMIZATIONS?
- Evitar que Proguard elimine elementos estirables específicos
- Optimización: Acceso a campos y métodos
- Optimización de SQLite para aplicaciones de Android
- ¿Canvas.getClipBounds asigna un objeto Rect?
Hay un tercer método común de manejo deshacer. Esto es para almacenar las diferencias entre los dos estados dentro del objeto Deshacer. Puede hacer esto como diferencias reales (es decir, como qué píxeles han cambiado y lo que cambió a), pero que es probablemente casi tan inútil de memoria como almacenar el mapa de bits en cada etapa.
Alternativamente, puede utilizar el enfoque de patrón de comando, pero en lugar de volver a ejecutar los comandos cuando se deshace, se almacena la inversa de la orden – es decir, si el usuario aumentó el valor rojo por diez, entonces el comando deshacer es disminuirla por diez . Para deshacer simplemente ejecuta el comando inverso. Algunos comandos son difíciles de encontrar una inversa para, como "convertir a blanco y negro", pero mediante la mezcla de un mapa de bits subyacente con una serie de filtros que se activan o desactivan por el comando que probablemente pueda hacerlo.
Como otra sugerencia, use el método de comando que mencionó pero mantenga un mapa de bits para el paso anterior. Cuando el usuario hace el deshacer inmediatamente mostrar el mapa de bits en caché desde el paso anterior (n-1) y luego comenzar a calcular el mapa de bits para n-2 para que esté listo para cuando se presiona deshacer de nuevo.
Acerca de Use el punto de patrón de comando : A partir del estado inicial y de nuevo la ejecución de comandos no son necesarios en absoluto. Cada clase Command debe representar una acción de usuario pequeña y debe tener mecanismo para deshacer lo que hace en su método execute (), si se desea soportar la operación undo. Mantenemos una pila de *** objetos de comando. Cuando el usuario deshace algo, se dispara un objeto Command de la pila y se llama a su método undo ().
No veo ninguna motivación para usar el patrón de recuerdo en su caso ya que las acciones de deshacer serán en orden FIFO. El usuario no puede deshacer las acciones a su antojo, supongo.
- ¿Cómo hacer clic en un clickablespan utilizando espresso?
- Comprender los conceptos de Android a través de la perspectiva de desarrollo de escritorio