2010-07-21 9 views
5

Tengo una imagen muy grande y solo quiero mostrar una sección del tamaño de la pantalla (sin escala), y la sección debe ser el centro de la imagen. Como la imagen es muy grande, no puedo leer toda la imagen en la memoria y luego recortarla. Esto es lo que tengo hasta ahora pero dará OutOfMemory para imágenes grandes. Además, no creo que se aplique inSampleSize porque quiero recortar la imagen, no reducir la resolución.Recortar mapa de bits sin leer todo el mapa de bits primero

Uri data = getIntent().getData(); 
InputStream is = getContentResolver().openInputStream(data); 
Bitmap bitmap = BitmapFactory.decodeStream(is, null, null); 

¿Alguna ayuda sería genial?

+0

¿En qué formato está tu imagen? – finnw

+2

jpeg. Grr - el comentario tiene que ser más largo ... – timothyjc

Respuesta

1

Estoy de acuerdo en que la manera más fácil es dividir la imagen en muchas imágenes de mosaico más pequeñas y simplemente cargar las apropiadas para hacer la imagen que está buscando.

Sin embargo, si no desea hacerlo, puede verse obligado a buscar en la codificación del propio jpeg.

Lo que podría hacer es algo así como copiar el encabezado del archivo en un nuevo archivo, y luego extraer solo los píxeles que desea para crear un nuevo archivo. Luego, volver a cargar el nuevo archivo le permitirá tener solo el subconjunto de la imagen con la que desea trabajar, y todas las clases y funcionalidades regulares de Java estarán igualmente disponibles para su uso.

Sé que no es necesariamente una solución elegante o simple, sin embargo, garantiza que podrá utilizar la funcionalidad java original que espera poder utilizar.

+0

Parece que es demasiado difícil para mis habilidades de pirateo. Tuve que renunciar a ese proyecto para otras limitaciones técnicas de todos modos :( – timothyjc

0

Creo que está abordando el problema desde la dirección incorrecta.

Si el mapa de bits ya es tan grande que no se puede cargar como una sola imagen continua, ¿por qué almacenarlo como una sola imagen? Reúnala en los azulejos, luego cargue los azulejos/baldosas centrales y actúe sobre ellos.

+0

Sí. No quiero leer toda la imagen en la memoria, solo el mosaico central como lo pones. ¿Tienes algún código para esto? – timothyjc

+0

@timothyjc: ¿Cortarlo en rebanadas? Puede usar algo como Imagemagick para hacer eso fuera de su aplicación. http://superuser.com/questions/35832/split-a-image-into-tiles –

1

Usted puede hacer esto en 2 pasos:

  1. obtener el tamaño del mapa de bits, mediante el uso de inJustDecodeBounds = true.

  2. utilice BitmapRegionDecoder para decodificar solo la parte que desea.

¿El inconveniente? solo funciona desde la API 10 (pero ya es la mayoría ...).

+0

esto es una buena idea, pero el problema es que tal vez la imagen recortada sería demasiado grande y OOM puede ocurrir –

+1

Si el mapa de bits no se puede guardar dentro del montón, causará OOM. Puedes verificar cuánto tomará y evitar OOM, si lo deseas. Además, si tienes un mapa de bits grande y necesitas recortarlo y evitar OOM, puedes usar JNI como he hecho aquí: https: // github.com/AndroidDeveloperLB/AndroidJniBitmapOperations –

+0

Voy a probar su biblioteca. thanls –

Cuestiones relacionadas