Aller au contenu

Matrices de bayer


Greg34

Messages recommandés

Pardonnes moi, je ne suis pas connaisseur mais juste curieux, si j'ai bien compris, le but est de déléguer une tache exécutée par le CPU au GPU pour alléger le logiciel ? J'ai bon ?

 

Si c'est ça, c'est super ! J'ai toujours trouvé regrettable d'avoir un GPU fortiche en traitement parallèle inexploité avec un CPU qui pédale dans la semoule à côté... :D

Lien vers le commentaire
Partager sur d’autres sites

Salut,

 

Désolé pour la réponse tardive, je suis plus souvent à l'étranger qu'à la maison ces derniers temps avec mon taff.

 

Pour résumer, tout ce que font les logiciels via des librairies ou autre qui pèsent un âne mort en plus :p , je le fais avec moins de 2mo d’exécutable et toute l’amélioration qui va avec.

Wavelet en live preview ainsi que le dématricage (debayer) du capteur cmos.

Zoom avec interpolation et quelques bricoles tout cela dans le but d'éviter d'utiliser le cpu.

 

Sinon la cam au passage c'était une plb-cx revendue pour incompatibilité avec mon nouveau portable.

Rachat d'une gpcam...(rien à voir avec la plb-cx-> la toupcam est une belle mer..).

Du coup, je rame un peu pour continuer vu la daube que j'ai en ma possession.

Elle marche mais niveau fps elle craint :confused:

Vu que je reprend tout avec cette cam, je me suis amusé à faire un wrapper pour reprendre le projet à temps perdu.

Ci-dessous le code pour les curieux (traduit du c vers delphi):

unit ToupcamUnit;

interface

uses windows,classes,sysutils;

type enump=^integer;
type SN= array [0..31] of ansichar;
type PTOUPCAM_EVENT_CALLBACK= procedure (nEvent:cardinal;pCallbackContext:pointer);  stdcall;

const SDK = 'toupcam.dll';

{Options}
const TOUPCAM_OPTION_NOFRAME_TIMEOUT      =$01;// iValue: 1 = enable; 0 = disable. default: enable
const TOUPCAM_OPTION_THREAD_PRIORITY      =$02;// set the priority of the internal thread which grab data from the usb device. iValue: 0 = THREAD_PRIORITY_NORMAL; 1 = THREAD_PRIORITY_ABOVE_NORMAL; 2 = THREAD_PRIORITY_HIGHEST; default: 0; see: msdn SetThreadPriority
const TOUPCAM_OPTION_PROCESSMODE          =$03;//  0 = better image quality, more cpu usage. this is the default value
                                              //  1 = lower image quality, less cpu usage
const TOUPCAM_OPTION_RAW                  =$04;// raw mode, read the sensor data. This can be set only BEFORE Toupcam_StartXXX()
const TOUPCAM_OPTION_HISTOGRAM            =$05;// 0 = only one, 1 = continue mode
const TOUPCAM_OPTION_BITDEPTH             =$06;// 0 = 8bits mode, 1 = 16bits mode
const TOUPCAM_OPTION_FAN                  =$07;// 0 = turn off the cooling fan, 1 = turn on the cooling fan
const TOUPCAM_OPTION_COOLER               =$08;// 0 = turn off cooler, 1 = turn on cooler
const TOUPCAM_OPTION_LINEAR               =$09;// 0 = turn off tone linear, 1 = turn on tone linear
const TOUPCAM_OPTION_CURVE                =$0a;// 0 = turn off tone curve, 1 = turn on tone curve
const TOUPCAM_OPTION_TRIGGER              =$0b;// 0 = continuous mode, 1 = trigger mode, default value =  0
const TOUPCAM_OPTION_RGB48                =$0c;// enable RGB48 format when bitdepth > 8

const TOUPCAM_PROCESSMODE_FULL            =$00;// better image quality, more cpu usage. this is the default value
const TOUPCAM_PROCESSMODE_FAST            =$01;// lower image quality, less cpu usage

const TOUPCAM_EVENT_EXPOSURE              =$01;// exposure time changed */
const TOUPCAM_EVENT_TEMPTINT              =$02;// white balance changed, Temp/Tint mode */
const TOUPCAM_EVENT_CHROME                =$03;// reversed, do not use it */
const TOUPCAM_EVENT_IMAGE                 =$04;// live image arrived, use Toupcam_PullImage to get this image */
const TOUPCAM_EVENT_STILLIMAGE            =$05;// snap (still) frame arrived, use Toupcam_PullStillImage to get this frame */
const TOUPCAM_EVENT_WBGAIN                =$06;// white balance changed, RGB Gain mode */
const TOUPCAM_EVENT_ERROR                 =$80;// something error happens */
const TOUPCAM_EVENT_DISCONNECTED          =$81;// camera disconnected */

const S_OK          =$00;      //Operation successful
const S_FALSE       =$01;      //Operation successful
const E_FAIL        =$80004005;//Unspecified failure
const E_INVALIDARG  =$80070057;//One or more arguments are not valid
const E_NOTIMPL     =$80004001;//Not supported or not implemented
const E_POINTER     =$80004003;//Pointer that is not valid
const E_UNEXPECTED  =$8000FFFF;//Unexpected failure

procedure Toupcam_Close(c_Handle:THandle);stdcall; external SDK name 'Toupcam_Close';  //ok
function Toupcam_Version:pwchar ;stdcall; external SDK name 'Toupcam_Version';  //ok
function Toupcam_Enum(n:enump ):integer ;stdcall; external SDK name 'Toupcam_Enum';//ok
function Toupcam_Open(const id:pwchar):THandle ;stdcall; external SDK name 'Toupcam_Open'; //ok
function Toupcam_get_MaxSpeed(c_Handle:THandle):integer ;stdcall; external SDK name 'Toupcam_get_MaxSpeed'; //ok
function Toupcam_get_ExpoAGain(c_Handle:THandle; var _gain:integer ):integer ;stdcall; external SDK name 'Toupcam_get_ExpoAGain';//ok
function Toupcam_put_ExpoAGain(c_Handle:THandle; _gain:integer ):integer ;stdcall; external SDK name 'Toupcam_put_ExpoAGain';//ok
function Toupcam_get_ExpoTime(c_Handle:THandle; var _Time:integer ):integer ;stdcall; external SDK name 'Toupcam_get_ExpoTime';//ok
function Toupcam_put_ExpoTime(c_Handle:THandle; _Time:integer ):integer ;stdcall; external SDK name 'Toupcam_put_ExpoTime';//ok
function Toupcam_get_SerialNumber(c_Handle:THandle;var _SN:SN ):integer ;stdcall; external SDK name 'Toupcam_get_SerialNumber';//ok
function Toupcam_get_HwVersion(c_Handle:THandle;var _SN:SN ):integer ;stdcall; external SDK name 'Toupcam_get_HwVersion';//ok
function Toupcam_get_ProductionDate(c_Handle:THandle;var _SN:SN ):integer ;stdcall; external SDK name 'Toupcam_get_ProductionDate';//ok
function Toupcam_put_Option(c_Handle:THandle;_Option:integer; _Value:integer ):integer ;stdcall; external SDK name 'Toupcam_put_Option';  //ok
function Toupcam_get_Option(c_Handle:THandle;_Option:integer; _Value:integer ):integer ;stdcall; external SDK name 'Toupcam_get_Option';  //ok
function Toupcam_put_LEDState(c_Handle:THandle;_iLed:short; _iState:short; _iPeriod:short ):integer ;stdcall; external SDK name 'Toupcam_put_LEDState';  //marche pas cette merde
function Toupcam_put_Size(c_Handle:THandle; _Width:integer; _Height:integer):integer ;stdcall; external SDK name 'Toupcam_put_Size';
function Toupcam_get_Size(c_Handle:THandle;var _Width:integer;var _Height:integer):integer ;stdcall; external SDK name 'Toupcam_get_Size';
function Toupcam_get_ResolutionNumber(c_Handle:THandle):integer ;stdcall; external SDK name 'Toupcam_get_ResolutionNumber';
function Toupcam_get_MaxBitDepth(c_Handle:THandle):integer ;stdcall; external SDK name 'Toupcam_get_MaxBitDepth';
function Toupcam_get_Temperature(c_Handle:THandle):SmallInt ;stdcall; external SDK name 'Toupcam_get_Temperature';
function Toupcam_get_RawFormat(c_Handle:THandle;var _FourCC:integer;var _bitdepth:integer):integer ;stdcall; external SDK name 'Toupcam_get_RawFormat';
function Toupcam_get_HZ(c_Handle:THandle):byte ;stdcall; external SDK name 'Toupcam_get_HZ';
function Toupcam_get_Speed(c_Handle:THandle):byte ;stdcall; external SDK name 'Toupcam_get_Speed';
function Toupcam_put_Speed(c_Handle:THandle):byte ;stdcall; external SDK name 'Toupcam_put_Speed';
function Toupcam_put_eSize(c_Handle:THandle;nResolutionIndex:byte):integer ;stdcall; external SDK name 'Toupcam_put_eSize';
function Toupcam_put_Mode(c_Handle:THandle;bSkip:byte):integer ;stdcall; external SDK name 'Toupcam_put_Mode';


function Toupcam_StartPullModeWithCallback(c_Handle:THandle;pEventCallback:PTOUPCAM_EVENT_CALLBACK; var pCallbackCtx:pointer):Integer; stdcall;external SDK name 'Toupcam_StartPullModeWithCallback';

function Toupcam_PullImage(c_Handle:THandle;pImageData:pbyte;_bitdepth:byte ;var pnWidth:enump;var pnHeight:enump):cardinal ;stdcall; external SDK name 'Toupcam_PullImage';

implementation

end.

Lien vers le commentaire
Partager sur d’autres sites

  • 2 mois plus tard...

Salut,

 

Pour ceux qui ont une gmpcam color, ils peuvent tester la release ci-dessous.

Attention, elle pèse lourd :be:

Pas mal de bugs encore et beaucoup de trucs à finir mais doucement/surement.

 

http://dl.free.fr/q9n4I9ZaB

 

 

26125-1467659933.jpg

 

Edit:Brancher la cam en premier, le soft lance directement le visu.Si la gpcam est pas connectée, ça plante (j'ai oublié une sécurité :p)

Modifié par Greg34
Lien vers le commentaire
Partager sur d’autres sites

  • 3 semaines plus tard...

J'ai recompilé avec altaircam.dll cette fois-ci (vu la date de la version,ça devrait prendre en charge la IMX224 ?).

Ca pas été compliqué, les fonctions sont apparemment les mêmes (à part une fonction d'auto exposition qui était active par défaut et qui faisait ramer la cam...).

Après j'ai pas la V2 de cette cam, faudrait tester plusieurs versions histoire de voir si elle est reconnue.

Au pire, j'ai une version beta de la dll sur mon pc que je regarderai demain.

J'ai pas activé toutes les fonctions pour le moment, vu que c'était une transition d'un autre sdk (plb-cx) à la base.

 

http://dl.free.fr/iuTtSD0UD

Modifié par Greg34
Lien vers le commentaire
Partager sur d’autres sites

C'est déjà un bon début ^^

Pour le reste, ça suivra doucement.

J'essaye déjà de faire la même chose sous linux sans trop surcharger le code.

Pour les rvb, tu as un curseur pour tout bouger en même temps.

Molette souris pour zoomer, +/- pour changer l'angle et "z/q/s/d" pour se déplacer dans l'image en mode zoom.

Enfin bon, 800ko pour l'exe contre 25mo (constructeur) sans librairies externes ;)

Reste encore du taf...circle buffer,enregistrement des vidéos/images...ajout d'un thread pour récupérer le flux de la cam...

De quoi combler des weekends bien pourris au niveau du temps :be:

Lien vers le commentaire
Partager sur d’autres sites

  • 1 année plus tard...

Hello !

 

Un an après, je bosse encore dessus mais cette fois-ci, j'ai tenté l'expérience avec l'ASI224.

J'ai fait pas mal de modif pour exploiter les trames de la cam et j'ai pu la faire tourner aussi sous Delphi sans opencv :)

 

Toujours sur le même principe:

Caméra->capture raw->debayering GPU->filtre GPU->rendu écran.

 

Récupération des trames de la cam dans un thread pour pas ralentir l'affichage et le thread principal du programme.

 

A défaut de filmer la lune (toujours un temps de m.... ici), j'ai filmé ma main avec l'objectif fourni avec la cam.

 

Pour info, j'ai pas une main bizarre :be: c'est l'objo qui est sphérique !

 

Sur la vidéo de démo, je monte/diminue progressivement le filtre afin de montrer le changement apporté au rendu.

 

Bien sur, au début de la vidéo le filtre est désactivé et montre progressivement la montée en détails.

 



"iZuEdKw0qSs" via YouTube
ERROR: Si vous lisez ce texte, YouTube est hors-ligne ou vous n'avez pas installe Flash

 

Non non...ce n'est pas la nouvelle saison de walking dead xD

 

Bonne journée.

Modifié par Greg34
Lien vers le commentaire
Partager sur d’autres sites

Super job !

Par curiosite, c'est opensource ?

Je pose la question car je suis entrain de me lancer dans un projet qui ressemble un peu (pas completement), et je cherche un moyen robuste de savoir a quel filtre appartient quel pixel, quelqu'un sait comment faire ? (Je n'ai pas encore zieute dans Siril)

Lien vers le commentaire
Partager sur d’autres sites

Salut dolguldur,

 

Merci pour ton retour (le seul d'ailleurs).

Non c'est pas Open (pour le moment).

 

je cherche un moyen robuste de savoir a quel filtre appartient quel pixel

Pas trop compris ce que tu voulais faire là ? :)

Dans ce contexte, tu parles d'un filtre mécanique ou logiciel ?

Lien vers le commentaire
Partager sur d’autres sites

opencv, c'était pour quelle étape?

 

C'est une lib utilisée pour gérer la matrice et profiter aussi du plein potentiel de la caméra de part ses traitements GPU :)

Seul reproche à cette lib, c'est que c'est une usine à gaz qui pèse relativement lourd et de plus, j'ai toujours aimé faire des applications les plus petites possible et optimisée.

Du coup, j'essaye de pas l'utiliser.

 

Ah ben après la main de King Kong, tu joue à Walking Dead... on progresse je vois lol

 

J'te cause plus :be: !

Lien vers le commentaire
Partager sur d’autres sites

Salut dolguldur,

 

Merci pour ton retour (le seul d'ailleurs).

Non c'est pas Open (pour le moment).

 

 

Pas trop compris ce que tu voulais faire là ? :)

Dans ce contexte, tu parles d'un filtre mécanique ou logiciel ?

 

Oups, desole, mon message etait loin d'etre clair !

Je parle en fait rarement de filtres pour les ondelettes, pour differentes raisons. Ici je pensais a filtre physiques ou microlentilles qui sont devant les pixels de l'imageur.

 

En gros, ma question est la suivante, est-ce que pour connaitre la couleur d'un pixel (x,y) dans mon buffer image, je peux faire un truc du genre:

 

if(x%2==0 &&y%2==0) {

color = blue;

} else if (x%2!=0 && y%2!=0) {

color = red;

} else {

color = green;

}

 

Ou y a t'il plus de subtilite selon les capteurs ? J'imagine que oui, au vu de l'article suivant: https://en.wikipedia.org/wiki/Bayer_filter

 

Sinon, question subsidiaire, par curiosite, comment as-tu code la transforme en ondelettes en GPU ? Je connais quelques implem opensource, mais j'etais curieux de savoir si tu avais fais ca from scratch ou depuis des exemples (openCL, cuda ?), je n'ai meme pas verifie, peut etre meme qu'openCV fourni cela ?

 

En tout cas, encore bravo pour ce travail !

Lien vers le commentaire
Partager sur d’autres sites

Okey, mais ducoup, il y a une info dans les exif, ou dans une metadonnee quelconque quelque part ?

En gros mon projet est de faire la debayerisation moi meme, mais je trouve assez peu de doc pratique sur le sujet (pas sur la theorie de la debayerisation).

Dans l'ideal je trouve un fichier d'include qui me donne toutes les infos que je cherche... Peut etre quelque part dans libgphoto... je vais regarder ca plus en detail d'ici quelques semaines.

Lien vers le commentaire
Partager sur d’autres sites

En fait, le souci c'est qu'il n'y a pas qu'un seul algo pour le dématriçage et comme disait Fred_76, tu as aussi différentes séquences en fonction du capteur choisi.

 

 

Un bon lien qui justement décrit la matrice : https://fr.wikipedia.org/wiki/D%C3%A9matri%C3%A7age mais bon ça relève encore de la théorie.

 

OpenCV peut concrétiser directement le dématriçage mais je trouve que ça devient moins intéressant que de le faire soi-même.

 

Ici, tu as un code ainsi qu'une bonne doc qui associe la théorie à la pratique:

http://www.ipol.im/pub/art/2011/bcms-ssdd/

Lien vers le commentaire
Partager sur d’autres sites

  • 1 mois plus tard...

Je pense pouvoir proposer une version beta surement pleine de bugs avec des trucs qui marchent pas bientot :be:

Juste pour essayer et avoir des retours ou pas ...

C'est un petit soft sans prétentions (sous windows) qui ne fonctionne pour le moment qu'avec les caméras ZWO car à chaque fois que j'ai eu une caméra dans les mains, j'ai toujours joué avec le SDK de la cam en cours.

 

Ci dessous, un shoot extérieur avec le même temps d'expo, gain etc ... sur la petite lunette guide Orion 50mm en 8bit (le 12bit me pose un problème pour le moment).

 

Exemple avec le filtre qui permet de comparer en live via un curseur l'amélioration de l'image:

astrogpu.gif

 

L'image débayérisée avec le rendu GPU:

2.jpg

 

Rendu GPU + filtre convolution + unsharp en live (le tout peut être réglé via une matrice->là j'ai peut être un peu forcé sur les curseurs);

1.jpg

 

Merci aux curieux de se manifester histoire de savoir si je continu à alimenter ce fil ou pas :)

Lien vers le commentaire
Partager sur d’autres sites

Superbe !

Franchement c'est pas mal, le seul truc qui me chagrine un peu c'est que je suis reste sur ma faim au niveau du "comment".

J'ai juste commence a jeter un coup d'oeil a l'article IPOL, mais j'avoue que je m'attendais a un truc plus "pratique" (j'ai deja quelques notions sur les problemes inverses).

La question que je me pose c'est comment toi tu as obtenu l'equation qui permet de mapper une coordonnee 2D a un canal couleur, c'est code en dur ? tu as utilise un header du sdk zwo ?

Question subsidiaire pour la curiosite cette fois ci, quel type d'ondelette utilise tu ? peux tu faire varier la taille de ton image d'entree (tailles impaires) et profondeur de la decomposition ?

Lien vers le commentaire
Partager sur d’autres sites

En fait, c'est pas compliqué pour le debayering (et là je vais faire un heureux) je suis parti sur cette thèse: https://www.researchgate.net/publication/220494111_Efficient_High-Quality_Bayer_Demosaic_Filtering_on_GPUs

 

Pour le reste, c'est de l'opengl mais tu peux aussi le faire sous directx,opencv et j'en passe ...

 

Le SDK de l'asi ne sert que pour connecter la cam (avec les réglages etc ...) et récupérer le pointeur donné par la fonction "ASIGetVideoData" en mode raw8 ou raw16 (qui est du raw12 pour la 224).

 

A partir de là, tu as tout ce qu'il faut pour débayeriser ton image.

Forcement avec un shader tu vas pouvoir récupérer les coordonnées dans ton vertex et appliquer diverses opérations dans ton fragment (merci aux jeux vidéos xD) comme les ondelettes etc ...

http://www.fil.univ-lille1.fr/~aubert/p3d/Cours08.pdf

 

Pour ce qui est du reste, j'écris mes shaders à la volée et me basant sur des formules de reconstructions d'images liées à la photographie avec détection et affichage des pixels saturés en live.

Là ou photoshop ou Registrax met quelques secondes pour améliorer l'image, avec ce procédé c'est instantané et en live.

Lien vers le commentaire
Partager sur d’autres sites

Lol je crois qu'on a vraiment beaucoup de mal a se comprendre.

Je ne suis pas interesse par la facon de coder l'algorithme de debayerisation (enfin si, mais plus tard), ce qui m'interesse vraiment c'est, de maniere extremement pratique, dans du CODE informatique, comment tu recupere le mapping de coordonnes2d -> canal couleur.

En effet ce mapping peut etre different pour differentes camera, et j'aurai besoin d'une librairie qui puisse me fournir cette info a la compilation.

 

L'ideal serait donc un header, ainsi qu'un document qui me permette d'ecrire mon code dans le genre:

 

switch (bayer)

case Bayer::RGGB {...}

//Dans ce cas je sais que le pixel (0,0)->R (0,1)->G (1,0)->G (1,1)->B et ainsi de suite

 

case Bayer::RGBGBGRBR {...}

//Dans ce cas on a un autre mapping un peu plus complexe, disponible dans une doc quelconque

etc...

 

EDIT: dans l'article de McGuire, en fait il considere (en dur dans le code) que :

/** Pixel position of the first red pixel in the Bayer pattern. [{0,1}, {0, 1}] **/

 

Je comprends pas trop ce qu'il veut dire dans ce commentaire, c'est pas 0,0 ? pourquoi il donne deux paires de nombres, est ce que cela change d'un capteur a l'autre ?

Modifié par dolguldur
Lien vers le commentaire
Partager sur d’autres sites

comment tu recupere le mapping de coordonnes2d -> canal couleur.

 

Ben si je t'ai répondu :be:

Shaders & opengl !

 

Là, on bosse avec le GPU, tu peux oublier les scanline ou les tableaux de pixels...ça se rapproche mais la syntaxe est différente.

 

Pourquoi un header avec :

 

switch (bayer)

case Bayer::GRBG) {...}

case Bayer::RGBGBGRBR) {...}

 

Alors que dans l'exemple fourni pour haut on peut écrire directement dans le code à l’exécution du shader dans la routine d'affichage d'opengl:

 

case bayer_index of

0: glUniform2f(firstRed, 0, 0); //BGGR

1: glUniform2f(firstRed, 0, 1); //GRBG

2: glUniform2f(firstRed, 1, 0); //GBRG

3: glUniform2f(firstRed, 1, 1); //RGGB

end;

 

ou bayer_index correspond à l'index d'un combobox par exemple ...

 

Bon encore mieux ^^ ->https://github.com/motmot/libcamiface/tree/master/demo

 

C'est pas dans mon langage de prédilection mais ça devrait pouvoir répondre à 90% de tes attentes sachant que là, tu as du code source :)

Lien vers le commentaire
Partager sur d’autres sites

Rejoignez la conversation !

Vous pouvez répondre maintenant et vous inscrire plus tard. Si vous avez un compte, connectez-vous pour poster avec votre compte.

Invité
Répondre à ce sujet…

×   Collé en tant que texte enrichi.   Coller en tant que texte brut à la place

  Seulement 75 émoticônes maximum sont autorisées.

×   Votre lien a été automatiquement intégré.   Afficher plutôt comme un lien

×   Votre contenu précédent a été rétabli.   Vider l’éditeur

×   Vous ne pouvez pas directement coller des images. Envoyez-les depuis votre ordinateur ou insérez-les depuis une URL.

  • En ligne récemment   0 membre est en ligne

    • Aucun utilisateur enregistré regarde cette page.
×
×
  • Créer...

Information importante

Nous avons placé des cookies sur votre appareil pour aider à améliorer ce site. Vous pouvez choisir d’ajuster vos paramètres de cookie, sinon nous supposerons que vous êtes d’accord pour continuer.