Algorithmus Schwierigkeit



  • Hallo,

    ich muss von meiner Uni aus ein Trapez zu einem Rechteck transformieren. So das hab ich jetzt gemacht und zwar mit diesem Algorithmus wir er in diesem Dokument auf Seite 13 beschrieben ist. Das ganze nennt sich wohl auch Perspective Warping.
    http://www.gm.fh-koeln.de/~konen/WPF-BV/BV08.PDF

    Jedenfalls scheint bei mir noch etwas falsch zu sein und ich weiss nicht was. Bin für jede Hilfe dankbar.

    //Koordinaten Paare Bild 
                float[,] src = { { 53, 136 }, { 392, 137 }, { 29, 285 }, { 422, 290 } }; 
                float[,] dst = { { 33, 0 }, { 412, 0 }, { 33, 300 }, { 412, 300 } }; 
    
                //float[,] src = { { coordImage[0, 0], coordImage[0, 1] }, { coordImage[1, 0], coordImage[1, 1] }, 
                //                 { coordImage[2, 0], coordImage[2, 1] }, { coordImage[3, 0], coordImage[3, 1] } }; 
    
                //float[,] dst = { { coordImage[2, 0], coordImage[0, 1] }, { coordImage[3, 0], coordImage[1, 1] }, 
                //                 { coordImage[2, 0], coordImage[2, 1] }, { coordImage[3, 0],coordImage[3, 1]  } }; 
    
                Sparse2DMatrix<int, int, double> mat = new Sparse2DMatrix<int, int, double>();//{{3,2 ,-1},{2,-2, 4},{-1,0.5,-1} }; 
                SparseArray<int, double> bVector = new SparseArray<int, double>(); 
                SparseArray<int, double> xVector = new SparseArray<int, double>(); 
    
                const int numberEquations = 8; 
                double xCoord=0; 
                double yCoord = 0; 
                double homCoord = 0; 
    
                //Stelle Gleichungssystem auf 
                for (int i = 0; i < 4; i++) 
                { 
                    mat[i, 0] = src[i, 0]; 
                    mat[i, 1] = src[i, 1]; 
                    mat[i, 2] = 1; 
                    mat[i, 3] = mat[i, 4] = mat[i, 5] = 0; 
                    mat[i, 6] = -src[i, 0] * dst[i, 0]; 
                    mat[i, 7] = -dst[i, 0] * src[i, 1]; 
                    //mat[i, 8] = dst[i, 0]; 
    
                    mat[i + 4, 0] = mat[i + 4, 1] = mat[i + 4, 2] = 0; 
                    mat[i + 4, 3] = src[i, 0]; 
                    mat[i + 4, 4] = src[i, 1]; 
                    mat[i + 4, 5] = 1; 
                    mat[i + 4, 6] = -dst[i, 1] * src[i, 0]; 
                    mat[i + 4, 7] = -dst[i, 1] * src[i, 1]; 
    
                    bVector[i] = dst[i,0] ; 
                    bVector[i + 4] = dst[i, 1]; 
                } 
                //Löse Gleichungssystem 
                LinearEquationSolver.Solve(numberEquations, mat, bVector, xVector); 
    
                int width  = originalImage.Width; 
                int height = originalImage.Height; 
    
                newImage = new Bitmap(width, height); 
                Color col = new Color(); 
    
                //Baue 3x3 Matrix auf 
                CSML.Matrix mat1 = new CSML.Matrix(3,3); 
                mat1[1, 1] = new CSML.Complex(xVector[0]); 
                mat1[1, 2] = new CSML.Complex(xVector[1]); 
                mat1[1, 3] = new CSML.Complex(xVector[2]); 
    
                mat1[2, 1] = new CSML.Complex(xVector[3]); 
                mat1[2, 2] = new CSML.Complex(xVector[4]); 
                mat1[2, 3] = new CSML.Complex(xVector[5]); 
    
                mat1[3, 1] = new CSML.Complex(xVector[6]); 
                mat1[3, 2] = new CSML.Complex(xVector[7]); 
                mat1[3, 3] = new CSML.Complex(xVector[8]); 
    
                //Berechne Inverse der Matrix 
                CSML.Matrix matInv = mat1.Inverse(); 
    
                //Multipliziere mit inverser Matrix und erhalte ursprüngliche Pixel zurück 
                for (int i = 0; i < width; i++) 
                { 
                    for (int j = 0 ; j < height; j++) 
                    { 
                        col = originalImage.GetPixel(i, j); 
                        //Matrix Multiplication 
                        homCoord = (matInv[3, 1].Re * i + matInv[3, 2].Re * j + matInv[3,3].Re * 1); 
                        xCoord = ((matInv[1, 1].Re * i + matInv[1, 2].Re * j + matInv[1, 3].Re * 1) / homCoord); 
                        yCoord = ((matInv[2, 1].Re * i + matInv[2, 2].Re * j + matInv[2, 3].Re * 1) / homCoord); 
    
                        if (homCoord != 0) 
                        { 
                            xCoord = xCoord / -homCoord; 
                            yCoord = yCoord / -homCoord; 
                        } 
                        if(xCoord>0 && yCoord < height) 
                        newImage.SetPixel((int)xCoord,(int) yCoord, col); 
                    } 
                } 
                //Weise PictureBox neues Bild zu 
                pictureBox2.Image = newImage;
    


  • Reicht ein Thread zu dem Thema nicht? 🙄

    Btw, wenn der Code kompilieren würde, würde ich ihn mir sogar mal anschaun. Wenn ich alle Abhängigkeiten erst selber machen muss bin ich aber ganz ehrlich zu faul. :p



  • Zum Lösen des Gleichungssystems verwende ich halt Bibliotheken. Das sind ca 5 Dateien. Aber der Algorithmus ist ja eigentlich nicht schwierig. Ich dachte das sollte selbsterklärend sein.



  • Das ganze ist auch in OpenCV implementiert http://docs.opencv.org/modules/imgproc/doc/geometric_transformations.html

    dort sind es die Funktionen
    getPerspectiveTransform und warpPerspective

    Bitte überfliegt mal jemand meinen Code und prüft was falsch sein könnte. Es scheint nicht offensichtlich. Denn ich hab das schon mehrmals gepostet



  • kennst sich einer mit der C Sharp Implementierung von OpenCV aus. Hab mir jetzt den Ordner runtergeladen aber finde folgende Funktionen nicht. cvGetPerspectiveTransform und cvWarpPerspective . Wo sind die denn mit drin ?

    http://sourceforge.net/projects/emgucv/



  • LonelyOcean schrieb:

    kennst sich einer mit der C Sharp Implementierung von OpenCV aus. Hab mir jetzt den Ordner runtergeladen aber finde folgende Funktionen nicht. cvGetPerspectiveTransform und cvWarpPerspective . Wo sind die denn mit drin ?

    http://sourceforge.net/projects/emgucv/

    Weiß nicht ob wir das selbe meinen, aber OpenCV hat keine "C#-Implementierung", es gibt nur einen C#-Wrapper namens Emgu



  • HelplessInTheOcean schrieb:

    ...

    Das solltest du vielleicht lesen.



  • Das heisst ich brauch mir den C# Source Code gar nicht anschauen weil das eh nur Aufrufe zur C++ Library sind ??



  • HelplessInTheOcean schrieb:

    Das heisst ich brauch mir den C# Source Code gar nicht anschauen weil das eh nur Aufrufe zur C++ Library sind ??

    ja



  • das ist irgendwie so einfache Mathematik,
    warum rechnest du nicht für die Eck-Punkte des Bildes das mal per Hand und Taschenrechner nach und vegleichst dann im Debugger die Werte?

    Dann siehst du doch genau die Zeile im Quelltext, ab der die Werte der Variablen von deiner Erwartung abweichen...


Anmelden zum Antworten