Página 6 de 7 PrimerPrimer 1234567 ÚltimoÚltimo
Resultados 251 al 300 de 307

Tema: Desarrollo de un GUI (Interface Gráfica) para DCRAW


  1. #251
    Nino no ha iniciado sesión Habitual
    Fecha de ingreso
    28 ene, 05
    Ubicación
    Ávila
    Mensajes
    270
    Cita Iniciado por ManuelLlorens Ver mensaje
    Para Nino y Carcamal.

    He subido el mismo test de antes, pero compilando la DLL con MinGW en vez de VC++ a ver si con eso se soluciona el fallo. Si podéis probar Nino y Carcamal en este
    enlace os lo agradezco:

    http://www.ojodigital.com/prawpblender/Test4b.rar

    Si esto os funciona tendremos que seguir mirando a ver qué pasa cuando se compila con VC++. Si no os funciona tendremos un problema un poco mayor.

    Un saludo:
    Siento haber taraddo tanto en responder, pero ya funciona perfectamente.
    Un saludo.

  2. #252
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    Manuel:
    el algoritmo de marcado que proponía GUI sería algo así:
    Código:
     
    inline void PixelFrom16to8(PX8 *data8,PX16 *data16, int flash)
    {
      if(flash){
        if( data16[0]== 65535 ) data8[0]=128;
        else data8[0]= data16[0]>>8;
        if( data16[1]== 65535 ) data8[1]=128;
        else data8[1]= data16[1]>>8;
        if( data16[2]== 65535 ) data8[2]=128;
        else data8[2]= data16[2]>>8;
      } else  {
        data8[0]= data16[0]>>8;
        data8[1]= data16[1]>>8;
        data8[2]= data16[2]>>8;
      }
    }
    Como ves, no he comprobado si flash es > 0, pues con lo propuesto por GUI no hay tres estados posibles, sólo dos: o dejar la imagen con su valor de pixels inalterado (en uno de los ticks del reloj) o marcar el quemado (en otro tick).
    El comparar si es distinto de cero es ligeramente más rápido que comparar si es positivo.

    Se podría ahorrar un poquito más (aunque sería marginal) evitando la comprobación de la variable flash por cada pixel recorrido, separando las rutinas FastDraw en dos: una implenmentando el marcado de pixels con la primera parte del if y otra sin el marcado de pixels con la parte del else en su lugar.

    Otra mejora estaría en comprobar no si es igual a 65535 sino hacer un xor (o exclusivo) bit a bit con 0xFFFF que es más rápido.
    Esto dará distinto de cero si no es igual y sólo dara 0 (0x0000) si el valor es igual a 0xFFFF.

    Esto sí creo que pueda merecer la pena cambiarlo porque en vez de hacer una resta en cada operación para ver si le sale nulo, es suficiente con un xor que es mucho más rápido. Aunque es posible que un compilador moderno haga esa optimización del código él solito.

    Código:
        if( data16[0] ^ 0xFFFF ) data8[0] = data16[0]>>8;
        else data8[0]= =128;
    Un incremento de velocidad marginal serí utilizar operadores de desplasamiento de punteros ++data, aunque quedará mucho menos legible.
    Además seguramente con los compiladores actuales y sus optimizaciones esta optimización ya la haga el compilador.
    Quedaría algo así (edito: lo corrijo porque estaba mal escrito):
    Código:
    inline void PixelFrom16to8(PX8 *data8,PX16 *data16, int flash)
    {
      if(flash){
        if( (*data16) ^ 0xFFFF ) *(data8++) = (*(data16++))>>8;
        else *(data8++) =128;
        if( (*data16) ^ 0xFFFF ) *(data8++) = (*(data16++))>>8;
        else *(data8++) =128;
        if( (*data16) ^ 0xFFFF ) *(data8++) = (*(data16++))>>8;
        else *(data8++) =128;
      } else  { 
        *(data8++) =128;
        *(data8++) =128;
        *(data8++) =128;
      }
    }
    Creo no haberme equivodado al poner la lógica de punteros. Habrá que comprobarlo.
    Última edición por ariznaf; 19/05/2008 a las 18:37 Razón: Corrección de errores en el código del último ejemplo.

  3. #253
    cacharruco no ha iniciado sesión Vivo en los foros
    Fecha de ingreso
    14 oct, 05
    Ubicación
    JARAIZ DE LA VERA (Cáceres)
    Mensajes
    5,573
    ¿Debería funcionar en Windows Vista?
    Saludos, Angel
    Tengo mi propia del versión del optimismo.
    Si no puedo cruzar una puerta, cruzaré otra o haré otra puerta.
    Algo maravilloso vendrá, no importa lo oscuro que esté el presente.


  4. #254
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    En Vista sí, en Vista 64 no (aunque esperábamos que funcionara no ha sido así, aunque estamos en ello e intentaremos que así sea, por la cuenta que me tiene, que yo uso Vista 64).

  5. #255
    cacharruco no ha iniciado sesión Vivo en los foros
    Fecha de ingreso
    14 oct, 05
    Ubicación
    JARAIZ DE LA VERA (Cáceres)
    Mensajes
    5,573
    Cita Iniciado por ariznaf Ver mensaje
    En Vista sí, en Vista 64 no (aunque esperábamos que funcionara no ha sido así, aunque estamos en ello e intentaremos que así sea, por la cuenta que me tiene, que yo uso Vista 64).
    Yo tambien uso el 64. Estaré atento. Gracias
    Saludos, Angel
    Tengo mi propia del versión del optimismo.
    Si no puedo cruzar una puerta, cruzaré otra o haré otra puerta.
    Algo maravilloso vendrá, no importa lo oscuro que esté el presente.


  6. #256
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    En el 64 te funcionarán los test que puso Manuel del entorno con el jpeg del salón, pero no el test de revelado.
    El problema está en que la dll de dcraw no funciona en Vista 64.
    Estamos en ello, pero hay otras prioridades (aunque en el momento que esto avance un poco y se integre revelador y entorno, yo voy a necesitar hacer algo, porque dejará de funcionarme la aplicación)

  7. #257
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Cita Iniciado por ariznaf Ver mensaje
    el algoritmo de marcado que proponía GUI sería algo así. El comparar si es distinto de cero es ligeramente más rápido que comparar si es positivo.
    Sí, hay varias optimizaciones que pensaba hacer sobre el código final, pero iré poniéndolas todas ahora.

    Cita Iniciado por ariznaf Ver mensaje
    Se podría ahorrar un poquito más (aunque sería marginal) evitando la comprobación de la variable flash por cada pixel recorrido, separando las rutinas FastDraw en dos: una implenmentando el marcado de pixels con la primera parte del if y otra sin el marcado de pixels con la parte del else en su lugar.
    Eso lo pierdes en facilidad de mantenimiento del código, creo que no merecerá la pena, pero lo estudiaré.

    Cita Iniciado por ariznaf Ver mensaje
    Otra mejora estaría en comprobar no si es igual a 65535 sino hacer un xor (o exclusivo) bit a bit con 0xFFFF que es más rápido.
    ¿Tenemos claro que saturado significa exactamente igual a 0xFFFF? ¿No vamos a querer definir un umbral más abierto? Si es así lo optimizaremos como tú dices, claro. Y lo mismo en 0.

    Cita Iniciado por ariznaf Ver mensaje
    Un incremento de velocidad marginal serí utilizar operadores de desplasamiento de punteros ++data, aunque quedará mucho menos legible.
    Eso efectivamente ya lo optimiza el compilador. *(data+5) y data[5] se convierte en lo mismo una vez en ensamblador.

    Voy a subir la prueba a 16 bits, esta noche te pasaré el código para que lo cambies en tu clase vista.

    Un saludo:
    _________________________________
    Aquí va la prueba del GUI a 16 bits con el diseño de ariznaf. Parpadean los blancos a negro y los negros a blanco. Las dos vistas van a 16 bits. El rar pesa mucho más porque lleva dentro un TIFF de 16 bits, claro. Además tarda al arrancar porque .NET tarda un montón en cargar un TIFF y porque hace un cálculo de gamma sRGB cutre en código 100% .NET, cuando tire del revelado no tendrá ese retardo en arrancar.

    He arreglado el botón 2 para que podáis comparar velocidades. (Le quedan al FTP 10 minutos para terminar de subirlo, tened paciencia).

    http://www.ojodigital.com/prawpblender/GUI16.rar

    Un saludo:
    Última edición por ManuelLlorens; 19/05/2008 a las 18:20 Razón: Fusión automática de mensajes para prevenir autosubir post
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  8. #258
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    ¿Tenemos claro que saturado significa exactamente igual a 0xFFFF? ¿No vamos a querer definir un umbral más abierto? Si es así lo optimizaremos como tú dices, claro. Y lo mismo en 0.
    Bueno, eso lo planteó GUI en este mismo hilo y yo creo que tiene razón: quemados son quemados, con el valor más alto posible. Con un umbral no serían quemados sino "altos", pero recuperables con ajustes de exposición. Sólo querríamos marcar los "irrecuperables".
    Eso efectivamente ya lo optimiza el compilador. *(data+5) y data[5] se convierte en lo mismo una vez en ensamblador.
    Si pero si hay tres instrucciones seguidas como:
    data[0]= xxx;
    data[1]= xxx;
    data[2]=xxx;
    no sé si el compilador detecta que los índices son seguidos o lo convierte en:
    *(data)=xxx;
    *(data+1)=xxx;
    *(data+2)=xxx;

    En vez de en:
    *(data++)=xxx;
    *(data++)=xxx;
    *(data++)=xxx;

    Los procesadore tienen operaciones especiales de incremento en uno de un puntero más rápidas y sin acceso a memoria (en un solo ciclo) que llevará menos que el sumar una constante de desplazamiento (que requiere hacer la suma y cargar el valor a sumar, lo que es más de un ciclo).

    Por cierto que en el ejemplo anterior estaba mal puesto y había puest ++(*data) que lo que haría sería incrementar en uno el valor almacenado y no el puntero.
    Lo corregiré.
    _________________________________
    MMMM a ver Manuel: más compacto todavía usando el operador ternario (que dicen que está optimizado por el compilador y hace menos saltos que el if ... else.
    Código:
    inline void PixelFrom16to8(PX8 *data8,PX16 *data16, int flash)
    {
      if(flash){
        *(data8++)= ( (*data16) ^ 0xFFFF ) ? (*(data16++))>>8 : 128;
        *(data8++)= ( (*data16) ^ 0xFFFF ) ? (*(data16++))>>8 : 128;
        *(data8++)= ( (*data16) ^ 0xFFFF ) ? (*(data16++))>>8 : 128;
      } else  { 
        *(data8++) =128;
        *(data8++) =128;
        *(data8++) =128;
      }
    }
    Es posible que haya algún error pero compilar compila
    _________________________________
    Por cierto, Manuel:

    ya que a mi no me funciona el revelador en Vista 64 y hasta que esto se arregle, ¿podrías seguir haciendo las pruebas con el test y cargando un tiff de 16 bits en vez de un jpeg de 8?

    De esta manera podríamos seguir avanzando con el tema de la interface gráfica, prescindiendo temporalmente del problema del revelador dcraw.
    Última edición por ariznaf; 19/05/2008 a las 18:58 Razón: Fusión automática de mensajes para prevenir autosubir post

  9. #259
    Guillermo Luijk no ha iniciado sesión RAW RAW la botella de RAW
    Fecha de ingreso
    07 mar, 06
    Ubicación
    Madrid (a ratos Alicante)
    Mensajes
    8,602
    Cita Iniciado por ariznaf Ver mensaje
    Manuel:
    el algoritmo de marcado que proponía GUI sería algo así:
    Código:
     
    inline void PixelFrom16to8(PX8 *data8,PX16 *data16, int flash)
    {
      if(flash){
        if( data16[0]== 65535 ) data8[0]=128;
        else data8[0]= data16[0]>>8;
        if( data16[1]== 65535 ) data8[1]=128;
        else data8[1]= data16[1]>>8;
        if( data16[2]== 65535 ) data8[2]=128;
        else data8[2]= data16[2]>>8;
      } else  {
        data8[0]= data16[0]>>8;
        data8[1]= data16[1]>>8;
        data8[2]= data16[2]>>8;
      }
    }

    A ver que esto no es lo que decía, sino:

    Código:
    if(flash){  // Imagen parpadeo
        if( data16[0]== 65535 or data16[1]== 65535 or data16[2]== 65535 )
        // El píxel tiene algún canal quemado
        {
        if( data16[0]== 65535 ) data8[0]=128; else data8[0]= 0;
        if( data16[1]== 65535 ) data8[1]=128; else data8[1]= 0;
        if( data16[2]== 65535 ) data8[2]=128; else data8[2]= 0;
        if data8[0]=128 and data8[1]=128 and data8[2]=128 {
          data8[0]=0; data8[1]=0; data8[2]=0;
          }
        } else {  // El píxel no tiene ningún canal quemado
        data8[0]= data16[0]>>8;
        data8[1]= data16[1]>>8;
        data8[2]= data16[2]>>8;
        }
      } else  {  // Imagen normal
        data8[0]= data16[0]>>8;
        data8[1]= data16[1]>>8;
        data8[2]= data16[2]>>8;
      }
    No sé si estáis creandos dos bitmaps que se alternan según el reloj del parpadeo, pero la idea es ésta: cuando parpadean las zonas quemadas, en los píxels quemados no aparece NADA que tenga que ver con la imagen original, sale sólo un color que nos informa acerca de los canales que están quemados. Y cuando no parpadean aparece la imagen original (con sus quemados sin los tiene claro).

    Respecto a poner umbrales, quizá si que es mejor poder poner un umbral, es decir, que quemado sea mayor de 65536-50 por ejemplo, porque a veces ocurre que el punto de saturación de las cámaras oscila y da lugar a saturaciones en valores algo por debajo de 65536.
    "En ocasiones veo halos."

    http://www.guillermoluijk.com para suscribirte haz clic aquí
    Último contenido: PARA QUÉ SIRVE EL RANGO DINÁMICO?

  10. #260
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    No, no se están creando dos bitmap, sino uno sólo, por eso en los no quemados copio el valor del pixel original.
    Lo que tú propones sería un método de máscara: marcar en otro buffer los pixels quemados con algo distinto de 0.
    Para eso sobraría la parte del else que establece los valores en 0, pues el buffer se inicializaría todo el a 0 con un memset de una sola vez (más rápido).

    En el parpadeo se vuelve a hacer el reescalado y demás de cada vez: una con pixels quemados y otra sin ellos.
    Por ahora funciona bastante rápido y bien. Si esto lo ralentiza, habría que utilizar la técnica de double buffer, pero yo siempre prepararía una imagen definitiva, sino habría que montar la máscara de pixels quemados sobre la imagen al final y eso en GDI+ es lent o según en comparación con el algoritmo de manuel (las operaciones con bitmaps en GDI son lentas por las pruebas que hizo al principio Manuel).

    Si se quieren poner umbrales habrá que volver a lo de la comparación con un valor mínimo:

    *(data8++)= ( (*data16) >= umbral ) ? (*(data16++))>>8 : 128;

    en vez de:
    *(data8++)= ( (*data16) ^ 0xFFFF ) ? (*(data16++))>>8 : 128;

    El umbral debería de dejarse como un valor configurable que se pase a la función o una variable global de la dll para poder ajustarlo (aunque esto será más lento que utilizar un valor constante, pues requiere un acceso a memoria más).
    Si no se piensa que el usuario vaya a andar cambiándolo, se puede definir con un const en la dll de fastdraw.


    editado para probar superpoderes
    Última edición por Guillermo Luijk; 20/05/2008 a las 00:42

  11. #261
    Guillermo Luijk no ha iniciado sesión RAW RAW la botella de RAW
    Fecha de ingreso
    07 mar, 06
    Ubicación
    Madrid (a ratos Alicante)
    Mensajes
    8,602
    Cita Iniciado por ariznaf Ver mensaje
    No, no se están creando dos bitmap, sino uno sólo, por eso en los no quemados copio el valor del pixel original.
    Lo que tú propones sería un método de máscara: marcar en otro buffer los pixels quemados con algo distinto de 0.

    A ver, o yo estoy entendiendo mal esto:

    Código:
    if( data16[0]== 65535 ) data8[0]=128;
        else data8[0]= data16[0]>>8;
    if( data16[1]== 65535 ) data8[1]=128;
        else data8[1]= data16[1]>>8;
    if( data16[2]== 65535 ) data8[2]=128;
        else data8[2]= data16[2]>>8;
    o tú lo que haces es: si un canal está quemado, lo pones a 128, y si no está quemado, lo dejas como era en origen. Si eso es así, está mal. Eso va a formar en las zonas parcialmenet quemadas un color que no se sabrá lo que es, porque vendrá dado por una mezcla de canales quemados a 128, y canales de la imagen original, no?

    Por eso te decía que en la imagen que se ha de mostrar cuando estén parpadeando las luces quemadas, se haga:

    Código:
    if( data16[0]== 65535 ) data8[0]=128; else data8[0]= 0;
    if( data16[1]== 65535 ) data8[1]=128; else data8[1]= 0;
    if( data16[2]== 65535 ) data8[2]=128; else data8[2]= 0;
    if data8[0]=128 and data8[1]=128 and data8[2]=128 then {
        data8[0]=0; data8[1]=0; data8[2]=0}
    Así si se quema solo el canal rojo, verde o azul, parpadeará en dicho color. Si se quema R+G parpadeará en amarillo (B=0), si se quema R+B parpadeará en magenta (G=0), si se queman los 3, los ponemos a 0 (negro) para que se distinga mejor aún.

    Se trata de construir los colores para lograr estos chivatos (los de la izq.) en las 7 posibles combinaciones de saturaciones:

    Última edición por Guillermo Luijk; 19/05/2008 a las 20:32
    "En ocasiones veo halos."

    http://www.guillermoluijk.com para suscribirte haz clic aquí
    Último contenido: PARA QUÉ SIRVE EL RANGO DINÁMICO?

  12. #262
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Cita Iniciado por ariznaf Ver mensaje
    Bueno, eso lo planteó GUI en este mismo hilo y yo creo que tiene razón: quemados son quemados, con el valor más alto posible. Con un umbral no serían quemados sino "altos", pero recuperables con ajustes de exposición. Sólo querríamos marcar los "irrecuperables".
    Vale, no lo había leído bien... entonces OK.

    Cita Iniciado por ariznaf Ver mensaje
    Si pero si hay tres instrucciones seguidas como:
    data[0]= xxx;
    data[1]= xxx;
    data[2]=xxx;
    no sé si el compilador detecta que los índices son seguidos o lo convierte en:
    *(data)=xxx;
    *(data+1)=xxx;
    *(data+2)=xxx;

    En vez de en:
    *(data++)=xxx;
    *(data++)=xxx;
    *(data++)=xxx;
    Es que no son lo mismo. Tu segundo ejemplo modifica el puntero, el primero es una operación de búsqueda en tabla que no modifica el puntero, no es lo mismo: data++ es lo mismo que data=data+1, no que data+1 a secas.
    _________________________________
    Cita Iniciado por ariznaf Ver mensaje
    MMMM a ver Manuel: más compacto todavía usando el operador ternario (que dicen que está optimizado por el compilador y hace menos saltos que el if ... else.
    Código:
    inline void PixelFrom16to8(PX8 *data8,PX16 *data16, int flash)
    {
      if(flash){
        *(data8++)= ( (*data16) ^ 0xFFFF ) ? (*(data16++))>>8 : 128;
        *(data8++)= ( (*data16) ^ 0xFFFF ) ? (*(data16++))>>8 : 128;
        *(data8++)= ( (*data16) ^ 0xFFFF ) ? (*(data16++))>>8 : 128;
      } else  { 
        *(data8++) =128;
        *(data8++) =128;
        *(data8++) =128;
      }
    }
    Es posible que haya algún error pero compilar compila
    Te veo emocionado con el C ... no te preocupes que lo optimizaremos bien. Había pensado en evitar el if utilizando un puntero a la función, pero entonces no podríamos usar el inline. Creo que meteré el if dentro de la función que la llama para optimizar y a la vez mantener el código lo mejor posible.
    _________________________________
    Cita Iniciado por ariznaf Ver mensaje
    Por cierto, Manuel:
    ya que a mi no me funciona el revelador en Vista 64 y hasta que esto se arregle, ¿podrías seguir haciendo las pruebas con el test y cargando un tiff de 16 bits en vez de un jpeg de 8?
    Eso hago en el ejemplo que acabo de subir. Si subo ejemplos subsiguientes no volverá a subir el tiff para no cargar el download. En cuanto retoque un poco el código te lo paso para que lo juntes con el tuyo.

    Un saludo:
    _________________________________
    Bueno, no os preocupéis demasiado por el código del parpadeo. Yo me encargo de que funcione como quiere _GUI_ y tan optimizado como se posible para contentar a ariznaf. Esta noche subo el ejemplo. Por cierto, en el código que he subido fuerzo la imagen para que se queme y parpadee. Buscaré una nueva imagen con más "paleta de colores", a ver si consigo una que tenga realmente quemados píxeles de diversos canales.
    Última edición por ManuelLlorens; 19/05/2008 a las 20:40 Razón: Fusión automática de mensajes para prevenir autosubir post
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  13. #263
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    Manuel:

    Es que no son lo mismo. Tu segundo ejemplo modifica el puntero, el primero es una operación de búsqueda en tabla que no modifica el puntero, no es lo mismo: data++ es lo mismo que data=data+1, no que data+1 a secas.

    Hombre claro, ahí está la gracia no... precisamente lo que hace es obtener el valor de la posición actual del puntero y después mover el puntero a la siguiente posición, quedando apuntanto a donde tenemos almacenado el siguiente canal de color.
    Luego vuelve a repetir lo mismo con el siguiente canal. Al final el puntero queda apuntando al primer canal del siguiente pixel.

    Esa es precisamente la gracia.
    Sólo se puede hacer esto cuando no necesitamos volver a acceder a la posición antigua (sólo se accede una vez) y cuando los valores a acceder son seguidos como en este caso.

    GUI:

    A ver, o yo estoy entendiendo mal esto:


    Código:

    .............. eliminado .........

    o tú lo que haces es: si un canal está quemado, lo pones a 128, y si no está quemado, lo dejas como era en origen. Si eso es así, está mal. Eso va a formar en las zonas parcialmenet quemadas un color que no se sabrá lo que es, porque vendrá dado por una mezcla de canales quemados a 128, y canales de la imagen original, no?

    Por eso te decía que en la imagen que se ha de mostrar cuando estén parpadeando las luces quemadas, se haga:


    Código:
    ........... eliminado .........
    Así si se quema solo el canal rojo, verde o azul, parpadeará en dicho color. Si se quema R+G parpadeará en amarillo (B=0), si se quema R+B parpadeará en magenta (G=0), si se queman los 3, los ponemos a 0 (negro) para que se distinga mejor aún.
    Ahora el que no entiende nada soy yo.

    El parpadeo no se hace con dos buffers, sino creando en una ocasión la imagen tal cuál sin marcar pixels quemados y en la siguiente marcándolos.

    En el código que tú pones lo que haces es poner a 128 los canales quemados y a 0 los que no lo están. Pero entonces obtendremos una imagen con todo en negro menos los pixels con los canales quemados.

    Si te endiendo bien lo que pretendes es que en vez de dejar los otros canales como estaban, los pongamos con valor 0, de forma que el color sea un rojo neutro si se quema el color rojo, etc.

    Pero el código entonces sería así:

    Código:
     
    //copiar primero los valores del pixel convertidos a 8 bits.
    data8[0] = data16[0] >> 8;
    data8[0] = data16[0] >> 8;
    data8[0] = data16[0] >> 8;
     
    //Si está quemado el canal rojo, poner un rojo medio
    if( data16[0]== 65535 ) {
       data8[0]=128;
       data8[1]=0;
       data8[2]=0;
    } else data8[0]= 0;
     
    //Si está quemado el verde, un verde medio.
    if( data16[1]== 65535 ) {
       data8[0]=0;
       data8[1]=128;
       data8[2]=0;
    } else data8[1]= 0;
     
    //Si está quemado el azul, un azul medio.
    if( data16[2]== 65535 ) {
       data8[0]=0;
       data8[1]=0;
       data8[2]=128;
    }
    Tampoco es exactamente eso, pues tal y como está sólo contempla el que se queme un canal, no dos o tres.

    Ya pensaré algo para ver cómo resolver las posibles combinaciones de que se queme más de un canal (evitando poner muchos ifs) y lo pongo.
    Última edición por ariznaf; 19/05/2008 a las 21:16

  14. #264
    Guillermo Luijk no ha iniciado sesión RAW RAW la botella de RAW
    Fecha de ingreso
    07 mar, 06
    Ubicación
    Madrid (a ratos Alicante)
    Mensajes
    8,602
    A ver, que te estás liando con los dedos de los pies , y es sencillísimo, ya lo había puesto antes. A ver:

    Código:
    if(flash){  // Imagen parpadeo
       if( data16[0]== 65535 or data16[1]== 65535 or data16[2]== 65535 )
        // El píxel tiene algún canal quemado
        {
        if( data16[0]== 65535 ) data8[0]=128; else data8[0]= 0;
        if( data16[1]== 65535 ) data8[1]=128; else data8[1]= 0;
        if( data16[2]== 65535 ) data8[2]=128; else data8[2]= 0;
        if data8[0]=128 and data8[1]=128 and data8[2]=128 {
          data8[0]=0; data8[1]=0; data8[2]=0;
          }
        } else {  // El píxel no tiene ningún canal quemado
        data8[0]= data16[0]>>8;
        data8[1]= data16[1]>>8;
        data8[2]= data16[2]>>8;
        }
      } else  {  // Imagen normal
        data8[0]= data16[0]>>8;
        data8[1]= data16[1]>>8;
        data8[2]= data16[2]>>8;
      }

    Si no flash dejamos la imagen original tal cual en todos los pixels.

    Si flash, generamos la imagen parpadeo:
    • Si el píxel tiene algún canal quemado, se generan las 7 combinaciones de color posibles (donde no interviene para nada el valor de los canales no quemados del píxel).
    • Si el píxel no tiene ningún canal quemado, se dejan los canales originales.


    Yo no sé muy bien si la implementación la hacéis con 2 buffers o uno solo que se reescribe, pero la idea es ésta. Por cierto, pensáis que es óptimo (tiempo de procesado) estar recalculando a cada parpadeo toda la imagen en lugar de tener 2 buffers de 8 bits?
    Última edición por Guillermo Luijk; 19/05/2008 a las 21:28
    "En ocasiones veo halos."

    http://www.guillermoluijk.com para suscribirte haz clic aquí
    Último contenido: PARA QUÉ SIRVE EL RANGO DINÁMICO?

  15. #265
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    A ver creo que ya lo tengo:
    La siguiente tabla con las posibles combinaciones de valores quemados y los colores que se quieren asignar:

    Código:
    Indice | Rojo | Verde | Azul | Color a asignar
    0          0       0          0       El original del pixel.
    1          0       0          1       RGB=(0,0,128)
    2          0       1          0       RGB=(0,128,0)
    3          0       1          1       RGB=(0,128,128)
    4          1       0          0       RGB=(128,0,0)
    5          1       0          1       RGB=(128,0,128)
    6          1       1          0       RGB=(128,128,0)
    7          1       1          1       RGB=(128,128,128)
    Obsérvese que la representación binaria del índice de entrada de la tabla coincide con los canales quemados (entendiendo por 1 canal correspondiente quemado y 0 no quemado)

    Por consiguiente sólo haría falta generar el índice comprobando qué canal está quemado con operaciones lógicas y de desplazamiento de bits y luego entrar en la tabla para obtener el valor a asignar.
    Con ello se ahorran comprobaciones u operaciones aritméticas.

    El código quedaría algo así:
    Código:
    typedef unsigned char PX8;
    typedef unsigned short PX16;
    const PX16 umbral =65500;
    const PX8 tablaR[8]= {0,0,0,0,128,128,128,128};
    const PX8 tablaG[8]= {0,0,128,128,0,0,128,128};
    const PX8 tablaB[8]= {0,128,0,128,0,128,0,128};
    inline void PixelFrom16to8(PX8 *data8,PX16 *data16, int flash)
    {
           int indice;
           if(flash) {
                 //construir el indice de entrada en la tabla a partir de los canales quemados
                 indice = (data16[0]>=umbral);
                 indice <<=1;
                 indice |= (data16[1]>=umbral);
                 indice <<=1;
                 indice= (data16[2]>=umbral);
                 if( indice ) { 
                     //indice != 0 significa canales quemados. Cambiar el color por los de la tabla
                     data8[0]= tablaR[indice];
                     data8[1]= tablaR[indice];
                     data8[2]= tablaR[indice];
                     return;
                 }
           }
           //Si hemos llegado hasta aquí o no se marcan los canales quemados (flash =0)
           // o no hay ninguno quemado.
           data8[0]= data16[0]>>8;
           data8[1]= data16[1]>>8;
           data8[2]= data16[2]>>8;
    }
    Si como dices quieres que cuando los tres canales estén quemados en vez de un gris RGB=(128,128,128) sea un negro RGB=(0,0,0) es suficiente con cambiar las entradas de la tabla, poniendo en el último valor de cada color un 0 en vez de un 128.
    En realidad con esa tabla se podría asignar los colores que quisiéramos a cada combinación de canales quemados.

  16. #266
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    Vaya, nos hemos cruzado.
    Bien ahora que repaso el código completo lo entiendo.

    Sí que había entendido bien lo que querías hacer (ahora que antes creí que los otros canales no quemados había que dejarlos como estaban).

    Lo que pasa que en la última vez que lo pusiste no habías puesto todo el código (faltaba el if del principio).

    Mi alternativa es similar sólo que sin todas las comparaciones. Únicamente tres y algunos desplazamientos de bits, por lo que creo que será más rápida.
    Será cuestión de probar.

  17. #267
    Guillermo Luijk no ha iniciado sesión RAW RAW la botella de RAW
    Fecha de ingreso
    07 mar, 06
    Ubicación
    Madrid (a ratos Alicante)
    Mensajes
    8,602
    Cita Iniciado por ariznaf Ver mensaje
    Vaya, nos hemos cruzado.
    Bien ahora que repaso el código completo lo entiendo.

    Sí que había entendido bien lo que querías hacer (ahora que antes creí que los otros canales no quemados había que dejarlos como estaban).
    jeje ya te digo que yo transmito solo ideas. tómate lo que pongo al 100% como pseudocódigo, a implementar y optimizar como consideréis mejor.

    Lo del umbral está bien porque muchas veces (en general por fallo del punto de saturación de DCRAW) hay RAWs que saturan a 65534 o unos pocos niveles menos. Son saturaciones con todas las de la ley, pero por culpa del punto de saturación no llegan a 65535. De hecho no vería mal un slider para controlar dicho umbral.
    "En ocasiones veo halos."

    http://www.guillermoluijk.com para suscribirte haz clic aquí
    Último contenido: PARA QUÉ SIRVE EL RANGO DINÁMICO?

  18. #268
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Vaya, ariznaf, estamos haciendo los dos lo mismo:

    Código:
     mask=(data16[0]<=uH)+(data16[1]<=uH)<<1+(data16[2]<=uH)<<2+(data16[0]>=uL)<<3+(data16[1]>=uL)<<4+(data16[2]>=uL)<<5;   
       if(mask!=0){
          data8[0]=ColorMask[mask][0];          
          data8[1]=ColorMask[mask][1];
          data8[2]=ColorMask[mask][2];
       }else{
          data8[0]=(data16[0]>>8);
          data8[1]=(data16[1]>>8);
          data8[2]=(data16[2]>>8);    
       }
    Un saludo:
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  19. #269
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Cita Iniciado por _GUI_ Ver mensaje
    De hecho no vería mal un slider para controlar dicho umbral.
    Tomo nota.
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  20. #270
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883

    Control de exposición

    He implementado el control de exposición en esta función, que es prácticamente el código puesto por _GUI_:

    Código:
    void exposure_correction(void){
        int i;
        float Y, Yp, exposure2, K1, K2;
        
        if(verbose) printf("Exposure correction ");
        if((exposure_mode==0)||(exposure<1.0)){
           // Exposure correction without highlight preservation
           if(verbose) printf("without highlight preservation\n");
           for(i=0;i<height*width;i++){
             image[i][0]=CLIP((float)image[i][0]*exposure); // R
             image[i][1]=CLIP((float)image[i][1]*exposure); // G (mixed)
             image[i][2]=CLIP((float)image[i][2]*exposure); // B
           }
        }else{
           // Exposure correction with highlight preservation
           if(verbose) printf("with highlight preservation\n");
           K1=32768/exposure;
           K2=65535-K1;
           for(i=0;i<height*width;i++){
             Y=0.299*(float)image[i][0]+0.587*(float)image[i][1]+0.114*(float)image[i][2]; // CIE luminosity
             if(Y<K1){
                image[i][0]=CLIP((float)image[i][0]*exposure); // R
                image[i][1]=CLIP((float)image[i][1]*exposure); // G (mixed)
                image[i][2]=CLIP((float)image[i][2]*exposure); // B
             }else{
                Yp=32767*(Y-65535)/K2+65535;
                exposure2=Yp/Y;
                image[i][0]=CLIP((float)image[i][0]*exposure2); // R
                image[i][1]=CLIP((float)image[i][1]*exposure2); // G (mixed)
                image[i][2]=CLIP((float)image[i][2]*exposure2); // B
             }
           }
        }        
    }
    Entiendo que el modo de preservación de luces sólo tiene sentido para valores de f>1.0, ¿verdad _GUI_? Por eso he añadido una condición en ese sentido en el if inicial.

    He actualizado el revelador para que puedas probarlo. Utiliza una gamma lenta por lo que es un poco rollazo de probar (no sé porqué, pero mi LUT en MinGW es bastante lenta, si hubiese puesto una LUT superrápida como la que pienso poner todo el proceso duraría menos de un segundo ), pero vale para que veas el efecto del control de exposición que has propuesto. No hay slider, pero sí un control up/down que va de 0,25 en 0,25. Más adelante podemos poner uno tipo cámara: 0,3 - 0,7 - 1... de momento para probar vale así. También hay un checkbox para seleccionar la preservación de luces altas.

    A mí personalmente me parece bastante correcto, incluso espectacular preservando luces altas.

    Enlace al nuevo revelador (aún no funcionará en Vista 64 y he machacado la prueba del revelador anterior).
    ¡OJO! para que funcione esta prueba debe existir el archivo c:\test\1_a.dng (y ser un DNG válido, obviamente). Al mediodía de hoy subiré una versión sin esa limitación. Disculpad.

    Un saludo:
    Última edición por ManuelLlorens; 20/05/2008 a las 11:07
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  21. #271
    Guillermo Luijk no ha iniciado sesión RAW RAW la botella de RAW
    Fecha de ingreso
    07 mar, 06
    Ubicación
    Madrid (a ratos Alicante)
    Mensajes
    8,602
    Cita Iniciado por ManuelLlorens Ver mensaje
    Entiendo que el modo de preservación de luces sólo tiene sentido para valores de f>1.0, ¿verdad _GUI_?
    No tiu, con f<1.0 también es interesante tener preservación de altas luces (a elección del usuario siempre eh?), explico porqué:
    - Si una imagen no tiene nada quemado, entonces sí, es tontería aplicar esta preservación (que luego cuento en qué consiste), lo correcto y lo que se habría obtenido con la cámara caso de exponer menos es: R'=R*f...
    - Pero si una imagen tiene altas luces quemadas, típicamente a tope (R=G=B=255) o sea blancos, aplicar una exposición a la baja implica convertirlos en grises, cuando lo más lógico es pensar que esas altas luces estaban bastantes diafragmas por encima (es decir, no eran áreas que resultaron en un valor 65535, sino que habrían obtenido un valor mucho mayor, solo que saturaron a 65535), y por lo tanto es bueno que sigan siendo altas luces blancas para emular mejor el resultado que habríamos obtenido en la cámara caso de exponer menos.

    Éste es precisamente el motivo por el que no suelo corregir la exposición (tanto al alza como a la baja) de los revelados procedentes de DCRAW con curvas en lineal (PS no admite curvas a tramos rectos como éstas), sino que aplico gamma y uso curvas normales; pero éstas ya alteran tono y saturación, no son verdaderos controles de exposición como el de la cámara.

    Por eso planteé la curva azul: lo que está en negrita es una recta que pasa por (32768, 32768*f) y (65535, 65535), que se implementa con:

    Código:
    else { // f<1
    // Aplicar a toda la imagen bucle:
    Y = 0.299R + 0.587*G + 0.114*B // Calculamos luminosidad CIE
    if Y <= 32768 {
    R' = clipf(R * f)
    G' = clipf(G * f)
    B' = clipf(B * f)
    } else {
    Y' = (65535 - 32768*f) * (Y - 65535) / 32767 + 65535
    f2 = Y' / Y
    R' = clipf(R * f2)
    G' = clipf(G * f2)
    B' = clipf(B * f2)
    }
    }
    Por cierto, clip no redondea a enteros? por qué no haces clipf en este punto? es para ganar velocidad mientras se prueba?


    Esa curva tiene además una propiedad que no tiene la curva roja, y es que al ser f<1 sí que se va a garantizar la igualdad de tono en absolutamente todos los casos(estás trabajando en lineal no?). Prueba ese algoritmo con alguna imagen lineal con zonas de altas luces quemadas, y compara el aspecto de éstas cuando bajas la exposición comparado con el modo normal.

    No me funciona (Vista 32 bits) el último Perfect RAW.exe, pero bueno da igual centraos en seguir adelante. Me siento aquí un poco como un ogro dandoos instrucciones de lo que hacer, pero es que estoy a años luz de vosotros, no soy capaz de hacer funcional el entorno de programación así que creo que ayudo más así.

    jeje, os habéis dado cuenta de que podemos editarnos los posts entre nosotros? o sea, aunque no sean nuestros.
    Última edición por Guillermo Luijk; 20/05/2008 a las 02:50
    "En ocasiones veo halos."

    http://www.guillermoluijk.com para suscribirte haz clic aquí
    Último contenido: PARA QUÉ SIRVE EL RANGO DINÁMICO?

  22. #272
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883

    Exclamation ¡¡¡mensaje Importante!!!

    Cita Iniciado por _GUI_ Ver mensaje
    No tiu, con f<1.0 también es interesante tener preservación de altas luces (a elección del usuario siempre eh?), explico porqué:
    Es verdad, es que hice pruebas con una imagen y no vi diferencia, aunque intuía algo... debí seguir mi intuición y probar con una imagen más quemada. Lo cambio este mediodia. Miraré también lo del CLIP/CLIPF.

    Cita Iniciado por _GUI_ Ver mensaje
    Me siento aquí un poco como un ogro dandoos instrucciones de lo que hacer, pero es que estoy a años luz de vosotros, no soy capaz de hacer funcional el entorno de programación así que creo que ayudo más así.
    Estoy de acuerdo en que no te instales el entorno de programación, creo que no te merece la pena. Creo que ahora estamos funcionando bien, tú pones pseudocódigo (aunque cada vez es más C, la verdad) y ariznaf y yo lo implementamos. Luego colgamos un ejecutable para que lo pruebes y ponemos en el foro el código que hemos implementado para que lo revises, ¿_GUI_, ariznaf, os parece correcta esta forma de trabajo?


    <_GUI_>: a mí sí, aunque sigo sin poder ejecutar nada. En el PC del curro (XP Pro) me pide que instale el .NET Framework. Pero vamos que da igual, con que me funcione al final de todo...

    (por ariznaf)
    Me parece bien, pero lo que no sé es si daré a basto para hacer mis cosas. GUI y tú sois una máquina de generar ideas.
    Yo luego soy más bien lentito (sobre todo por que hace mucho que no programo y el .NET ha cambiado bastante).

    Cita Iniciado por _GUI_ Ver mensaje
    jeje, os habéis dado cuenta de que podemos editarnos los posts entre nosotros? o sea, aunque no sean nuestros.
    Eso puede ser el caos . Supongo que los duendes que nos protegen van haciendo de las suyas. Se nota también en los subforos que han aparecido por arte de magia.

    (por ariznaf)
    Como expliqué más abajo lo he pedido yo. No todos pueden editar los mensajes sólo los que somos moderadores, que no nos dedicaremos a hacer el burro o jugar con lo de los demás ¿verdad?
    ___________________________________

    He pensado en un nuevo reparto de tareas.

    Os rogaría a los implicados que comentárais y/o confirmárais que el reparto es el adecuado. Por supuesto, no quiero imponer nada a nadie, sólo organizar un poco el tema para que no nos pisemos unos a otros. Dado que podemos editarnos los mensajes unos a otros. Sería bueno que en vez de contestar los que podáis editéis esta parte del mensaje y así queda algo definitivo.
    • _GUI_ se pone a definir el balance de blancos: relación temperatura de color -> multiplicadores (te pasé algunos enlaces que ya tenías, pero me molesté en sacarte el código fuente para que no tengas que descargarte, por ejemplo, el SDK del DNG).
    • He traspasado a ariznaf todo la maqueta del GUI. Así irá creciendo su clase de vistas con todo lo que llevamos hecho. Es mejor que un solo programador se encargue de esa tarea y ariznaf tiene las ideas muy claras al respecto. (por ariznaf) de acuerdo lo iré implementando según pueda. Una manita no vendría mal... para implementar alguna cosa concreta y separada de lo que yo pueda estar haciendo.
    • Yo me sigo encargando del revelador, empezando por la dll de dcraw, terminaré (algún día) de arreglar sus bugs (sólo queda uno y lo tengo acorralado, es cuestión de horas que se entrege con las manos en alto, cuando salga le cortaré la cabeza y sólo quedará un imortal, que seré yo... lo siento, se me ha ido la pinza ). Revisaré el control de exposición como pongo arriba. Prepararé la dll para perfectBLEND. Iré integrando la clase de vistas de ariznaf (tirando de lo que suba a SVN) con el revelador y poniendo los controles que faltan (es decir, todos ).
    • Otros temas (disculpad que ponga al burro delante):
      • Yo empezaré a bucear en el SDK del DNG, al menos a ver si consigo aclararme de cuánto código hace falta para escribir un DNG sencillo y si podemos prescindir del SDK o al menos encapsularlo en una clase C#. Creo que conseguiré escribir un DNG partiendo de cero, que es lo verdaderamente importante para perfectBLEND. (por ariznaf) venga a ver si lo consigues. Estaría muy bien.
      • Yo también revisaré cuando tenga dcraw.dll terminada si consigo hacerla funcionar con VC++.
      • Y por último yo empezaré a diseñar controles personalizados con la esperanza de traspasárselos a ariznaf cuando él termine lo que está haciendo ahora.
      • ariznaf seguirá con las pruebas en Vista 64. La pista de truji de los manifiestos es buena y hay que avanzar por ahí. Además él es el primer interesado . (por ariznaf) A ver si se consigue. El problema está principalmente en dcrawDLL que es un hueso duro de roer. Lo que programemos nosotros no creo que haya mayor problema (incluso para pasarlo a 64 bits), sólo es cuestión de tener un poco de cuidado y ya lo hemos tenido encuenta declarando tipos como PX8 y PX16.
      • _GUI_ seguirá pensando en perfectBLEND y también estaría bien que fuera definiendo los histogramas de perfectRAW.

        <_GUI_>: necesito que me digáis el nombre de las variables con que se acceden a los 3 canales de la imagen, y el formato en que están, e implemento los histogramas lineal y logarítmico. Sería casi imprescindible que la ventana final dedicada al histograma tenga un ancho potencia de 2 (512 píxels vendría fenomanal).
        Lo de Perfect BLEND las ideas las tengo clarísimas, es un programa muy sencillo y si encima no habrá que hacer balance de blancos más fácil aún. Lo duro va a ser lo del DNG.


        De momento crearé un histograma con un int[65535] a lo bruto y otro con int[512] para visualizar rápido, que obviamente calcularé a partir del anterior. Creo que integrar la funcionalidad completa, en otra ventana, de histogrammar sería una buena idea, daría un fondo técnico al revelador que no hay en otros reveladores. Por cierto, tanto nuestro revelador como dcraw internamente usan int para los índices sobre el array de la imagen, así que el día que nuestras cámaras den imágenes de 65536x65536 píxeles el programa nos dejará de funcionar .
      • vertex y perroverd seguirán haciendo pruebas en linux y mantiendo el SVN a punto.
      • Los demás seguís probando lo que subamos (es decir, haciendo el prealfa-testing ).
    Sería bueno que apareciera dsamper, creo que nos ayudaría mucho.

    Y creo que no me dejo nada.
    ___________________________________

    Posibilidad de vernos las caras

    Hablamos ariznaf y yo este fin de semana de vernos las caras el próximo lunes 16 de junio a las 18:00-19:00 horas en algún sitio donde podamos hablar y tomar algo. Tiene que ser en esa fechar porque él vendrá de Oviedo a Madrid y, como es listo, no lo hace habitualmente.
    <Manuel>: ¿Cambiamos la hora de 19:30 a 22:00 y que se vaya uniendo el que pueda?
    (por ariznaf) está bien ir de vez en cuando pero es como el vino: en grandes cantidades no sienta bien.

    <_GUI_>: Yo los lunes a esas horas estoy currando en Pozuelo, un poco jodido lo tengo. Un finde podría ir a tu casa Manuel, y me enseñas a compilar (puedo probar el sillón relax?)
    <Manuel>: es de cartón piedra, como los tanques de los iraquíes... si cuidas a los niños mientras yo programo luego te dejo darte un masaje.

    Evidentemente podemos hacer otras quedadas parciales en las que no esté él e ir a esta todos los que podamos. Yo iré seguro a tomarme algo con ariznaf y el que se apunte.

    Con franqueza me gustaría que pudiérais estar al menos los que aparecéis en el reparto de tareas de arriba y cualquier otro que se apunte, aunque algunos no seáis de Madrid y es un día laborable con lo que, salvo la casualidad, sé que será muy difícil. (Yo antes viajaba a Barcelona de vez en cuando, ahora no viajo nada, pero a lo mejor ariznaf, _GUI_ o algún otro van por allí de vez en cuando).

    No sé si resultará una reunión productiva, pero al menos nos vemos y nos tomamos algo. Hay algunos detalles que no es bueno discutir tan públicamente (como el nombre del dominio y otras cosas que se me ocurren).
    (por ariznaf) completamente de acuerdo. Además siempre hay curiosidad de ver la cara al interlocutor.

    ¿Opiniones? ¿Ideas? ¿Problemas?

    Un saludo:
    Última edición por ManuelLlorens; 20/05/2008 a las 14:28
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  23. #273
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    jeje, os habéis dado cuenta de que podemos editarnos los posts entre nosotros? o sea, aunque no sean nuestros.
    Lo has detectado antes de que lo pudiera comentar.
    Al objeto de poder organizar mejor los mensajes y facilitar la lectura de los mismos cuando buscamos sobre temas concretos, he pedido a Ojodigital dos cosas:
    -Que nos permitan ser moderadores de este foro. Así cuando un bug se da por arreglado por ejemplo, podremos cerrar el hilo (lo consideraremos como una incidencia resuelta9. Si luego aparecen nuevos problemas, se ha de abrir otro hilo (incidencia).
    Es por eso por lo que puedes modificar los posts, porque eres moderador. Pero ojito, que las modificaciones realizadas quedan marcadas y registradas, de forma que todo el mundo verá que has editado el post

    -Que nos crearan algún subforo nuevo. No he pedido muchos, sólo los más básicos, para separar lo relacionado con la programación, el "reporte" de bugs y la solicitud de nuevas funcionalidades.

    Así en vez de un hilo sobre bugs en el que meterlos todos (que luego se hace muy difícil de seguir en qué punto está la resolución de uno de los bugs o la implementación de una característica) se puede abrir un post para cada uno de ellos y ver en todo momento en qué estado está.

    Con esto pretendo facilitar el desarrollo y el mantenimiento de la aplicación (sobre todo cara al futuro inmediato, cuando habrá un montón de frentes abiertos... bueno ya los hay).

    Bueno, ahora a ver si somos nosotros mismos un poco organizaditos (yo me lanzo muchas veces a tratar temas sin pensar muy bien si el hilo es el adecuado).

    Voy a mover lo hilos existentes que corresponden claramente a los nuevos subforos.

    ¿Os parece bien?

    Saludines....
    Última edición por ariznaf; 20/05/2008 a las 10:13

  24. #274
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    No estaría de más que alguien que no estuviera en lo de la programación pero que tuviera interés en este proyecto y algo de experiencia con lo de los foros se apuntara a moderar este foro.

    Se encargaría de poner un poco de orden (tampoco se trata de tener un policía y normas superestrictas, sólo de contestar las preguntas evidentes de los nuevos que puedan llegar, mover algún hilo claramente fuera de sitio y ese tipo de cosas).

    (por Manuel): su nombre aparecería en los créditos de la aplicación, es lo poco que podemos ofrecer. Por cierto, aprovecho para proponer que en los créditos de la aplicación aparezca todo el que haya tenido algo que ver con ella en orden alfabético, así no nos peleamos. O eso o definimos claramente cómo aparecerá cada uno.
    Última edición por ManuelLlorens; 20/05/2008 a las 11:13

  25. #275
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    No me funciona en XP el programa puesto en Enlace al nuevo revelador

    Cuando lo lanzo me da una excepción de AccessViolation. Primero aparece un cuadro de diálogo explicando que no se deben hacer dos revelados seguidos.

    ¿Tiene la misma interface que tenía con un botón para seleccionar imagen o es que estás intentando abrir una imagen raw directamente que yo no tengo en el equipo?

  26. #276
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Cita Iniciado por ariznaf Ver mensaje
    No me funciona en XP el programa puesto en Enlace al nuevo revelador

    Cuando lo lanzo me da una excepción de AccessViolation. Primero aparece un cuadro de diálogo explicando que no se deben hacer dos revelados seguidos.

    ¿Tiene la misma interface que tenía con un botón para seleccionar imagen o es que estás intentando abrir una imagen raw directamente que yo no tengo en el equipo?
    ¡Ah! claro... eso es. Es que he cambiado el modo de inicializar la DLL para sortear el casque que aún tiene y al hacerlo me lo he cargado más. Ya te dije anoche que me tenía que ir a la cama. A ver si recupero un poco de energía, programo más concentrado y cometo menos errores.

    Bueno es fácil de arreglar, aunque un poco chapuza, hasta que lo suba de nuevo. Tenéis que aseguraros de que existe c:\test\1_a.dng y ya está. Podéis ir cambiando la imagen pero tendréis que cerrar y abrir la aplicación. Al mediodía lo subo arreglado para los más pacientes. De paso meteré excepciones para tratar los casos más evidentes y si me da tiempo meto la LUT sRGB rápida y la salida a 16 bits en el revelador.

    Un saludo:
    Última edición por ManuelLlorens; 20/05/2008 a las 11:10
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  27. #277
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Cita Iniciado por ariznaf Ver mensaje
    Voy a mover lo hilos existentes que corresponden claramente a los nuevos subforos. ¿Os parece bien?
    Es perfecto.
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  28. #278
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    Bien ya está hecho. Se mantendrán durante diez días enlaces en el foro raíz a los temas movidos.

    Manuel: a veces he visto que hay lío y confusión cuando alguien comunica un problema con uno de los test, pues están comentando problemas sobre un test viejo, que ya fueron corregidos en test posteriores.
    No es de extrañar que en un hilo tan largo como este pueda pasar desapercibido un mensaje en el que subas un nuevo programa de prueba (salvo para los más asiduos, claro)

    Por ello te propongo el siguiente sencillo esquema de funcionamiento para cualquier programa de prueba que se quiera poner a disposición de los demás.

    Crear un anuncio en el post principal que nitifique su creación identificando claramente la versión del programa de prueba. Este hilo se ha de crear como cerrado (para que no se respondan mensajes en él con problemas y demás y tener un único sitio de notificación de problemas).
    Algo asÍ:
    Nueva versión YY de prueba del programa XXXX

    He subido a (enlace a donde sea) una nueva versión del programa XXX qu hace esto y aquello....

    Para notificar errores en el funcionamiento del programa o comentarios sobre su forma de funcionar, házlo en el hilo (enlace al hilo del foro bugs)
    Crear también un nuevo hilo "Notificación de problemas de XXXXX versión YY".

    A ver qué os parece esa forma de funcionar y si es ágil y funcional.

  29. #279
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    Y dicho con la boca pequeña y sin que nadie se enfade....
    Creo que ha llegado el momento de cerrar este hilo ...
    Vamos ya por 14 páginas y para alguien que llegue de nuevas o no lo haya leido en algún tiempo, se hace interminable.
    Además mezclamos en él infinidad de temas y se hace imposible localizar una respuesta concreata (ya sé que existe el buscador, pero ...)
    Además se hace casi imposible poner un enlace a una respuesta concreat en otro hilo.

    Sé que al principio nos costará un poquito, pues estamos acostumbrados a venir aquí y contestar directamente a lo último que ponemos.
    Pero en un par de días, en cuanto se empiezen a separar los distintos temas lo tendremos más organizado y será todo mucho más fácil de leer.

    Bueno no me pongo más pesado con esto que parezco la mamá rezongona.

  30. #280
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Yo creo que debemos mover a otros foros los mensajes que traten de temas concretos, pero un foro general siempre debe haberlo. Habrá cosas inclasificables, otras como organizarnos para quedar un día y vernos las caras, etc. que no encajarán en otros foros. Digo yo.

    Un saludo:
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  31. #281
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Vale, ya he arreglado el control de exposición. No había leído todo el texto de _GUI_ antes de ponerme a implementar, de ahí mi error anterior.

    Podéis probarlo en este enlace, que machaca al anterior. He vuelto a actualizarlo a las 18:30 con la gamma sRGB rápida en vez de usar la de dcraw, es considerablemente más rápido. Y una vez más a las 20:00 con un botón para grabar el resultado en JPEG (8 bits, calidad 96, gamma sRGB, sin perfil de color incrustado).

    El código:
    Código:
    void exposure_correction(void){
        int i;
        float Y, Yp, exposure2, K1, K2;
        
        if(verbose) printf("Exposure correction ");
        if(exposure_mode==0){
           // Exposure correction without highlight preservation
           if(verbose) printf("without highlight preservation\n");
           for(i=0;i<height*width;i++){
             image[i][0]=CLIPF((float)image[i][0]*exposure); // R
             image[i][1]=CLIPF((float)image[i][1]*exposure); // G (mixed)
             image[i][2]=CLIPF((float)image[i][2]*exposure); // B
           }
        }else{
           // Exposure correction with highlight preservation
           if(verbose) printf("with highlight preservation\n");
           if(exposure>1){
               K1=32768/exposure;
               K2=65535-K1;
               for(i=0;i<height*width;i++){
                 Y=0.299*(float)image[i][0]+0.587*(float)image[i][1]+0.114*(float)image[i][2]; // CIE luminosity
                 if(Y<K1){
                    image[i][0]=CLIPF((float)image[i][0]*exposure); // R
                    image[i][1]=CLIPF((float)image[i][1]*exposure); // G (mixed)
                    image[i][2]=CLIPF((float)image[i][2]*exposure); // B
                 }else{
                    Yp=32767*(Y-65535)/K2+65535;
                    exposure2=Yp/Y;
                    image[i][0]=CLIPF((float)image[i][0]*exposure2); // R
                    image[i][1]=CLIPF((float)image[i][1]*exposure2); // G (mixed)
                    image[i][2]=CLIPF((float)image[i][2]*exposure2); // B
                 }
               }
           }else{
               K1=32768*exposure;
               K2=65535-K1;           
               for(i=0;i<height*width;i++){
                 Y=0.299*(float)image[i][0]+0.587*(float)image[i][1]+0.114*(float)image[i][2]; // CIE luminosity
                 if(Y<32768){
                    image[i][0]=CLIPF((float)image[i][0]*exposure); // R
                    image[i][1]=CLIPF((float)image[i][1]*exposure); // G (mixed)
                    image[i][2]=CLIPF((float)image[i][2]*exposure); // B
                 }else{
                    Yp=K2*(Y-65535)/32767+65535;
                    exposure2=Yp/Y;
                    image[i][0]=CLIPF((float)image[i][0]*exposure2); // R
                    image[i][1]=CLIPF((float)image[i][1]*exposure2); // G (mixed)
                    image[i][2]=CLIPF((float)image[i][2]*exposure2); // B
                 }
               }             
           }
        }        
    }
    El algoritmo de exposición de _GUI_ funciona, de eso no hay ninguna duda. Supongo que está asumido que el usar la preservación de luces altas afecta ligeramente al contraste de la imagen de modo que si f<1.0 se aumenta y si f>1.0 disminuye, ¿verdad _GUI_? De hecho, en algunas imágenes según dónde caiga la zona de transición entre cada tramo de la curva de corrección de exposición, puede quedar más natural o más raro, especialmente en retratos y transiciones suaves. Imagino que el control de exposición con preservación de luces altas, especialmente al disminuir la exposición, habrá que usarlo con cuidado y evaluar su efecto en cada imagen. He revelado un ejemplo (mola, porque es el primer ejemplo que ponemos que se ha revelado con perfectRAW, la interpolación del ejemplo es una caca):

    El primero con control de exposición -2.0 y CON preservación de luces altas.
    El segundo con control de exposición -1.0 y CON preservación de luces altas.
    El tercero con control de exposición -1.0 y SIN preservación de luces altas.



    Un saludo:
    Última edición por ManuelLlorens; 20/05/2008 a las 20:17
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  32. #282
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    Bueno lo he probado en un ordenador con XP SP2 y me funcionó bien.

    Eso sí como el ordenador es una patata (Pentium 4 2GHz y 2GB) de RAM me he eternizado un poquito mientras revelaba la imagen estandar.
    Ha tardado 30 segundos pero lo ha revelado (con ajuste de exposición y preservación de altas luces).

  33. #283
    Eduardo Cañadas no ha iniciado sesión Lleva poco por aquí
    Fecha de ingreso
    27 ago, 07
    Ubicación
    Barcelona
    Mensajes
    34
    Lo he probado nuevamente con Vista 64 y me vuelve loco, porque hay veces que funciona tres ocuatro veces y luego no vuelve a funcionar, no es un tema de la foto, ya que la misma foto va a veces si a veces no.

    Las veces que funciona, funciona correctamente el control de expocicion y la preservacion de luces.

  34. #284
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    ¿Alguien que pruebe con la recuperación de altas luces de PerfectRaw sobre la foto puesta en el tema Recuperación altas luces distintos reveladores RAW por GUI y ponga os resultados?

    La foto es la que está en esta dirección: http://users.uoi.gr/gianstam/test/_3160973.ORF


    No se podrá guardar pero se puede hacer un corta y pega de la pantalla para comparar con los otros resultados de ese hilo.
    Yo no lo puedo hacer porque en este ordenador no tengo ningún programa para poder pegar la imagen y exportarla a jpeg (en casa en Vista 64 no me pita).

  35. #285
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    Lo he probado nuevamente con Vista 64 y me vuelve loco, porque hay veces que funciona tres ocuatro veces y luego no vuelve a funcionar, no es un tema de la foto, ya que la misma foto va a veces si a veces no.

    Las veces que funciona, funciona correctamente el control de expocicion y la preservacion de luces.
    ¿Con Vista 64? Juraría que no funcionaba... daba el error nada más hacer el GetInfo de la imagen.
    Esta noche lo probaré.

  36. #286
    Eduardo Cañadas no ha iniciado sesión Lleva poco por aquí
    Fecha de ingreso
    27 ago, 07
    Ubicación
    Barcelona
    Mensajes
    34
    Cita Iniciado por ariznaf Ver mensaje
    ¿Con Vista 64? Juraría que no funcionaba... daba el error nada más hacer el GetInfo de la imagen.
    Esta noche lo probaré.
    Efectivamente ese es el error que da cuando falla, per o hay veces que funciona, lo cual despista aun mas

  37. #287
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Cita Iniciado por ariznaf Ver mensaje
    ¿Alguien que pruebe con la recuperación de altas luces de PerfectRaw sobre la foto puesta en el tema Recuperación altas luces distintos reveladores RAW por GUI y ponga os resultados?
    El control de exposición de _GUI_ no recupera luces altas, sólo las preserva, no existe una recuperación de luces de prefectRAW. De preservarlas se sigue encargando el algoritmo de dcraw y ese no ha cambiado. La gracia es poder controlar la exposición de la imagen en 32 bits y sin estropear las luces altas bien porque se quemen cosas que antes no se quemaban, bien porque se conviertan en un empasto gris.

    Aquí tienes la imagen de ejemplo con exposure: 0.5 (viene a ser -1.0), preservación de luces altas y recuperación máxima de luces (-h 9):


    y de nuevo la misma imagen con con exposure: 2 (viene a ser +1.0), preservación de luces altas y recuperación máxima de luces (-h 9):


    Un saludo:
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  38. #288
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Cita Iniciado por Eduardo Cañadas Ver mensaje
    Efectivamente ese es el error que da cuando falla, per o hay veces que funciona, lo cual despista aun mas
    Tendréis que esperar a que arregle el bug que tengo localizado en dcraw.dll a ver si influye. Es posible que sí. Haré otro intento de compilar dcraw con VC++ para ver si ariznaf puede depurarlo en su Vista 64 cuando casque.

    He subido una nueva prueba de perfectRAW con un botón que graba un jpeg a calidad 96 en la misma carpeta y con el mismo nombre que el archivo revelado (+".jpg"). La idea es hacer más fácil subir pruebas al foro. La imagen NO incluye el perfil de color sRGB, pero sí está corregida con gamma sRGB, al abrirla en PS tendréis que asignarle el perfil sRGB.

    Un saludo:
    Última edición por ManuelLlorens; 20/05/2008 a las 20:10
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  39. #289
    dgmaga no ha iniciado sesión Vivo en los foros
    Fecha de ingreso
    10 abr, 05
    Ubicación
    n.c.
    Mensajes
    2,041
    Joer, ¡qué bien va la cosa!

    A ver si luego puedo bajármelo y probarlo pero avanza a pasos de gigante! :-)

    Daniel

  40. #290
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    El primero con control de exposición -2.0 y CON preservación de luces altas.
    El segundo con control de exposición -1.0 y CON preservación de luces altas.
    El tercero con control de exposición -1.0 y SIN preservación de luces altas.

    ¿Está ampliada o algo así esta imagen?

    Se aprecia un extraño efecto en el pelo y los ojos.
    Parece como un aliasing. Lo digo por si es algún efecto del demosaicing (un fallo) aunque creo que la interpolación la hace dcraw ¿no?

  41. #291
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    Pues a mi no me funciona el programa en Vista 64 que decepción.

    Tendréis que esperar a que arregle el bug que tengo localizado en dcraw.dll a ver si influye. Es posible que sí. Haré otro intento de compilar dcraw con VC++ para ver si ariznaf puede depurarlo en su Vista 64 cuando casque.
    A ver a ver... si consigues que compile y se pueda ejecutar, aunque se la pegue luego será un gran avance, pues podremos ver qué le ocurre a ver si nos hacemos una idea.

  42. #292
    Guillermo Luijk no ha iniciado sesión RAW RAW la botella de RAW
    Fecha de ingreso
    07 mar, 06
    Ubicación
    Madrid (a ratos Alicante)
    Mensajes
    8,602
    La preservación de luces al reducir la exposición (f<1.0) es demasiado agresiva, ese codo tan abrupto (mirar la gráfica de la derecha arriba) da lugar a que se manifieste la transición del penúltimo al último diafragma, el brillito de la nariz de la niña ha quedado literalmente aislado del resto de la imagen. De todos modos la imagen de la niña (es tu hija?) no tiene zonas quemadas así que ahí no estaría justificado su uso.

    No queda más remedio que acudir a una curva no lineal, te paso el pseudocódigo esta noche. El cambio sería pasar de las curvas de arriba (izq. lineal vs lineal, der. log vs lineal), a las de abajo, mucho más progresivas. Implica usar una potencia (f2 = 2^(-Exp*(Y-1)/0,5) donde Exp es la subexposición en EV, p.ej. Exp=-2EV e Y>0.5 el valor lineal normalizado 0..1 de la luminosidad), pero esto ya lo tienes muy optimizado no?



    Creo que debería funcionar bien; en log-log también es muy progresiva:



    El contraste solo se altera en el último diafragma, donde lo aumentamos para poder preservar las altas luces. En todos los restantes diafragmas de luminosidad la corrección de exposición es lineal y por tanto no hay alteración de contraste. El tono no se altera en ningún caso.

    Podéis probar el ajuste de exposición al alza con una imagen normal? no la del barco, que tiene las altas luces recuperadas y de partida presenta tonos extraños.
    Cualquier RAW a punto de quemar, se revela y se le sube la exp. +1, +2, +3, con y sin preservación de altas luces, a ver qué tal va la curva recta para aumentar la exposición, o si también hay que corregirla.
    Última edición por Guillermo Luijk; 20/05/2008 a las 21:06
    "En ocasiones veo halos."

    http://www.guillermoluijk.com para suscribirte haz clic aquí
    Último contenido: PARA QUÉ SIRVE EL RANGO DINÁMICO?

  43. #293
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Cita Iniciado por ariznaf Ver mensaje
    ¿Está ampliada o algo así esta imagen? Se aprecia un extraño efecto en el pelo y los ojos. Parece como un aliasing. Lo digo por si es algún efecto del demosaicing (un fallo) aunque creo que la interpolación la hace dcraw ¿no?
    El demosaicing de dcraw está en el más rápido, es eso junto con la caca de interpolación que hace GDI+. Es una captura de pantalla pasada a PS y ampliada en PS con NN. Por eso he puesto el botón de grabar JPEG porque el método de capturar pantalla para pruebas al 100% o más es un asco.

    Un saludo:
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  44. #294
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Cita Iniciado por ariznaf Ver mensaje
    A ver a ver... si consigues que compile y se pueda ejecutar, aunque se la pegue luego será un gran avance, pues podremos ver qué le ocurre a ver si nos hacemos una idea.
    En cuanto tenga un rato te llamo al Messenger y hablamos del tema. Tengo algunas ideas que comentar contigo sobre el Vista 64 y cómo debemos proceder para arreglarlo de una vez por todas.

    Un saludo:
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  45. #295
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    Te subo un ejemplo como pedías... aunque tú puedes ejecutar el programa en casa sin problema, ya arreglé todo lo que fallaba en la prueba de anoche.

    Exp: 0


    Exp: +1 sin y con preservación:



    Exp: +2 sin y con preservación:



    Exp: +3 sin y con preservación:



    Exp: -1 sin y con preservación:



    Un saludo:
    Última edición por ManuelLlorens; 20/05/2008 a las 22:11
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  46. #296
    Guillermo Luijk no ha iniciado sesión RAW RAW la botella de RAW
    Fecha de ingreso
    07 mar, 06
    Ubicación
    Madrid (a ratos Alicante)
    Mensajes
    8,602
    hostia pues el aumento con preservación va de coxones, verdad? cómo lo veis? se pierde contraste (como no puede ser de otro modo), pero el tono se mantiene y la textura también. en las hojas la saturación parcial del canal verde llega pronto y se nota.
    la reducción ahora pongo el código nuevo menos agresivo, pero ésa solo será útil en fotos con zonas quemadas.

    Bueno el código corregido para f<1 sería:

    Código:
    void exposure_correction(void){
        int i;
        float Y, Yp, exposure2, K1, K2, EV;
        
        if(verbose) printf("Exposure correction ");
        if(exposure_mode==0){
           // Exposure correction without highlight preservation
           if(verbose) printf("without highlight preservation\n");
           for(i=0;i<height*width;i++){
             image[i][0]=CLIPF((float)image[i][0]*exposure); // R
             image[i][1]=CLIPF((float)image[i][1]*exposure); // G (mixed)
             image[i][2]=CLIPF((float)image[i][2]*exposure); // B
           }
        }else{
           // Exposure correction with highlight preservation
           if(verbose) printf("with highlight preservation\n");
           if(exposure>1){
               K1=32768/exposure;
               K2=65535-K1;
               for(i=0;i<height*width;i++){
                 Y=0.299*(float)image[i][0]+0.587*(float)image[i][1]+0.114*(float)image[i][2]; // CIE luminosity
                 if(Y<K1){
                    image[i][0]=CLIPF((float)image[i][0]*exposure); // R
                    image[i][1]=CLIPF((float)image[i][1]*exposure); // G (mixed)
                    image[i][2]=CLIPF((float)image[i][2]*exposure); // B
                 }else{
                    Yp=32767*(Y-65535)/K2+65535;
                    exposure2=Yp/Y;
                    image[i][0]=CLIPF((float)image[i][0]*exposure2); // R
                    image[i][1]=CLIPF((float)image[i][1]*exposure2); // G (mixed)
                    image[i][2]=CLIPF((float)image[i][2]*exposure2); // B
                 }
               }
           }else{             
               EV=log(exposure)/log(2)                              // Convertimos exp. lineal a EV           
               for(i=0;i<height*width;i++){
                 Y=0.299*(float)image[i][0]+0.587*(float)image[i][1]+0.114*(float)image[i][2]; // CIE luminosity
                 if(Y<32768){
                    image[i][0]=CLIPF((float)image[i][0]*exposure); // R
                    image[i][1]=CLIPF((float)image[i][1]*exposure); // G (mixed)
                    image[i][2]=CLIPF((float)image[i][2]*exposure); // B
                 }else{
                    exposure2=pow(2,-EV*(Y/65535-1)/0,5);
                    image[i][0]=CLIPF((float)image[i][0]*exposure2); // R
                    image[i][1]=CLIPF((float)image[i][1]*exposure2); // G (mixed)
                    image[i][2]=CLIPF((float)image[i][2]*exposure2); // B
                 }
               }             
           }
        }        
    }
    quizá una versión similar para cuando aumentamos la exposición mejore los resultados vistos. Una curva más suave no descontrastará tanto las altas luces a costa de descontrastar más aún las muy altas luces. Te paso el código cuando lo tenga.

    Por cierto si f=1 esta función realizar el procesado como cuando f<1, te has asegurado de que nunca sea llamada si f=1?
    Última edición por Guillermo Luijk; 20/05/2008 a las 23:13
    "En ocasiones veo halos."

    http://www.guillermoluijk.com para suscribirte haz clic aquí
    Último contenido: PARA QUÉ SIRVE EL RANGO DINÁMICO?

  47. #297
    ManuelLlorens no ha iniciado sesión Enganchad@ a los foros
    Fecha de ingreso
    30 abr, 08
    Ubicación
    Madrid
    Mensajes
    883
    [quote=_GUI_;2153357]hostia pues el aumento con preservación va de coxones, verdad? cómo lo veis?[/code]
    A mí me gusta.

    Cita Iniciado por _GUI_ Ver mensaje
    quizá una versión similar para cuando aumentamos la exposición mejore los resultados vistos. Una curva más suave no descontrastará tanto las altas luces a costa de descontrastar más aún las muy altas luces. Te paso el código cuando lo tenga.
    ¿Mantengo lo anterior como una opción?

    Cita Iniciado por _GUI_ Ver mensaje
    Por cierto si f=1 esta función realizar el procesado como cuando f<1, te has asegurado de que nunca sea llamada si f=1?
    Código:
    if (exposure!=1.0) exposure_correction();
    Un saludo:
    Manuel Llorens

    Olympus E-P1, E-510, E-300
    www.rawness.es

  48. #298
    Guillermo Luijk no ha iniciado sesión RAW RAW la botella de RAW
    Fecha de ingreso
    07 mar, 06
    Ubicación
    Madrid (a ratos Alicante)
    Mensajes
    8,602
    Cita Iniciado por ManuelLlorens Ver mensaje
    ¿Mantengo lo anterior como una opción?
    De hecho mantelo como la única opción cuando f>1, va a ser lo mejor. Forzando que el descenso de sobreexposición baje a 0EV en lineal (abajo-der.), se obtienen sobreexposiciones que saturan la luminosidad (abajo-izq.). Además cualquier esquema que supusiera una curva por encima de las rectas de la gráfica sup.-izq. implicaría más facilidad de saturación parcial así que ya que el esquema actual no crea extraños lo dejamos así.



    Para f<1 sí por favor prueba lo que he propuesto, creo que mejorará. Si es así el esquema final de curvas quedaría:



    Otro esquema que puede dar resultados muy interesantes, o como poco curiosos, es el de usar las curvas que ya tenemos definidas pero con una definición diferente de la luminosidad como el máximo de los canales: Y=max(R,G,B), tal como se hace en el modelo de color HSV.

    Según ese esquema los colores más saturados tendrán mayor luminosidad y se sobre/subexpondrán menos. El resultado puede ser curioso; lo cierto es que por mucha sobreexposición que se aplique, nunca se va a alterar el tono de un solo píxel porque no habrá saturaciones parciales. Esto deberá respetar el verde de tus hojas al subir la exposición, si bien las puede dejar estancadas en una determinada luminosidad cuando su entorno menos saturado sigue ganando brillo.
    Última edición por Guillermo Luijk; 21/05/2008 a las 01:27
    "En ocasiones veo halos."

    http://www.guillermoluijk.com para suscribirte haz clic aquí
    Último contenido: PARA QUÉ SIRVE EL RANGO DINÁMICO?

  49. #299
    ariznaf está en línea Eterno aprendiz...
    Fecha de ingreso
    22 mar, 08
    Ubicación
    Oviedo
    Mensajes
    8,302
    Pues los resultados son espectaculares, la verda... Se puede subir la luminosidad general pero sin que se queme la imagen.
    El reducirla, por lo que veo lo que hace es mantener las zonas brillantes mientras oscurece el resto pero de manera progresiva.... (esto lo veo menos interesante, aunque el efecto está muy consiguido).
    Si señor ha quedado bien.

    Dos cositas:
    ¿Se podría hacer el efecto contrario? Es decir mantener las zonas oscuras.
    Quiero decir, que si la imagen tiene zonas brillantes que queremos reducir puede ser interesante que las zonas no pasen a negro.
    De hecho es algo parecido a lo que hace el LightRoom con las curvas cuando modificamos las sombras o las luces altas. El lo separa en sombras, zonas oscuras, medias, altas y muy altas o algo así. Cada una se puede corregir por separado afectando algo a las vecinas.
    Sólo que GUI lo hace con curvas lineales ¿no?

    Creo que también sería interesante poder controlar el punto de transición, donde la curva prograsiva pasa a tener un valor constante de sub o sobre exposición

    Creo que lo ideal sería poder tener una curva con dos puntos configurables. A la derecha e izda de esos puntos la exposición sería progresiva y en medio constante.
    Así se podría controlar que zona de luminosidad de la imagen queremos afectar mayormente por la exposición, siendo fuera de esa franja progresiva.

    Y ya puestos en una versión futura, poner un editor de la curva de transición en lineal.
    Última edición por ariznaf; 21/05/2008 a las 01:32

  50. #300
    Guillermo Luijk no ha iniciado sesión RAW RAW la botella de RAW
    Fecha de ingreso
    07 mar, 06
    Ubicación
    Madrid (a ratos Alicante)
    Mensajes
    8,602
    Cita Iniciado por ariznaf Ver mensaje
    Pues los resultados son espectaculares, la verda... Se puede subir la luminosidad general pero sin que se queme la imagen.
    El reducirla, por lo que veo lo que hace es mantener las zonas brillantes mientras oscurece el resto pero de manera progresiva.... (esto lo veo menos interesante, aunque el efecto está muy consiguido).
    Es que aún no lo habéis probado con una imagen con amplias zonas quemadas, que es donde cobra sentido; para que las luces no se vayan a gris. Estos seguro de que con la última mejora y un RAW quemado se notará la utilidad.


    Cita Iniciado por ariznaf Ver mensaje
    Creo que también sería interesante poder controlar el punto de transición, donde la curva prograsiva pasa a tener un valor constante de sub o sobre exposición

    Creo que lo ideal sería poder tener una curva con dos puntos configurables. A la derecha e izda de esos puntos la exposición sería progresiva y en medio constante.
    Así se podría controlar que zona de luminosidad de la imagen queremos afectar mayormente por la exposición, siendo fuera de esa franja progresiva.
    Esto puede ser interesante, porque no todas las imágenes tienen igual porción de información en el último diafragma (que es el que he tomado yo como punto de cambio de comportamiento). Además es muy sencillo, basta un parámetro que afecte a las fórmulas. Lo peor es que el GUI se nos va llenando de cositas.

    Respecto a la preservacción de sombras, poderse se puede hacer (como estamos en lineal preservar el tono es trivial, es lo fantástico de la edición lineal), pero se nos trastocaría el contraste de toda la imagen no solo de las altas luces.
    Esto creo que ya entraría más en la filosofía de edición que de revelado y ajuste. Si esto sale bien no estaría nada mal atrevernos con un editor de curvas lineal; se podrían hacer virguerías.
    "En ocasiones veo halos."

    http://www.guillermoluijk.com para suscribirte haz clic aquí
    Último contenido: PARA QUÉ SIRVE EL RANGO DINÁMICO?

Página 6 de 7 PrimerPrimer 1234567 ÚltimoÚltimo

Permisos de publicación

  • No puedes crear nuevos temas
  • No puedes responder temas
  • No puedes subir archivos adjuntos
  • No puedes editar tus mensajes
  •  
<<<<<<<< Your Customized Value <<<<<<<<