Showing posts with label Emgu. Show all posts
Showing posts with label Emgu. Show all posts

Tuesday, January 28

Emgu.CV.CvInvoke invoke OpenCV function

cvInvoke simple tutorial

    เนื่องด้วยข้อเสียของ Emgu คือ เรื่องเอกสาร Tutorial หาอ่านยากมากๆ (ไม่นับรวม api class referrence) ในเว็บ wiki ของเขาเอง ก็ใช่ว่าจะมีตัวอย่างครบ นั่นอาจจะเป็นเพราะว่า Emgu เอง มันเองเป็น wrapper function ที่ครอบอยู่บน OpenCV อยู่ เลยทำให้ Developer เอง ไม่อยากจะทำ Tutorial ออกมา คงเข้าใจว่า ผู้นำ Emgu ไปใช้ คงมีความรู้พื้นฐานอยู่บ้าง และหากสงสัยใน Class ไหน ก็ให้หาอ่านเอาในเอกสารของ OpenCV หล่ะมั้ง (อันนี้ ผมคิดไปเองนะครับ)

ในเมื่อไม่มีทางเลือกที่จะต้องเรียกใช้ OpenCV Function ตรงๆ ใน .NET แล้ว ทาง Emgu ก็มี CvInvoke ที่จะทำให้เราสามารถเรียกใช้ OpenCV ได้โดยตรง และเมื่อเรียกใช้โดยตรงแล้ว ก็ให้อ้างอิงเอกสารของ OpenCV ได้เลย (ซึ่งมีตัวอย่างการใช้งาน และอื่นๆ ค่อนข้างครบ) เอาหล่ะ เรามาลองเขียน Emgu application โดยใช้ความสามารถของ CvInvoke กันดูครับ

สร้าง win application ขึ้นมา โดยทำตามขั้นตอนแรกๆ Getting started Emgu with Visual C# 2010 Express จากนั้นบนหน้าฟอร์มเปล่าๆ ก็สร้าง button ขึ้นมา 1 อัน แล้วก็เขียนไปบน Event double click ของมัน โดยดับเบิลคลิกที่ปุ่มบนฟอร์ม แล้วเขียนโค๊ดเหล่านี้ลงไป

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

using Emgu.CV;
using Emgu.Util;
using Emgu.CV.Structure;

namespace Emgu_cvInvoke
{
    public partial class Form1 : Form
    {
        MCvScalar color_text = new MCvScalar(255, 255, 255);
        MCvFont font = new MCvFont(Emgu.CV.CvEnum.FONT.CV_FONT_HERSHEY_SIMPLEX, 0.5, 0.5);
        IntPtr img = CvInvoke.cvCreateImage(new Size(200, 200), Emgu.CV.CvEnum.IPL_DEPTH.IPL_DEPTH_8U, 1);

        public Form1()
        {
            InitializeComponent();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            CvInvoke.cvPutText(img, "Hello Emgu", new Point(50, 50), ref font, color_text);
            CvInvoke.cvShowImage("Simple Emgu application", img);
        }

        private void Form1_FormClosing(object sender, FormClosingEventArgs e)
        {
            CvInvoke.cvDestroyWindow("Simple Emgu application");
            CvInvoke.cvReleaseImage(ref img);
        }
    }
}

จริงๆ แล้ว ตัวอย่างนี้ เราใช้่ cvCreatImage (Creates an image header and allocates the image data ) เป็นแค่การจองหน่วยความจำสำหรับเก็บข้อมูลรูปภาพ แล้วก็ใส่ตัวอักษร ด้วย cvPutText ไปบนพื้นที่ว่างบนรูปภาพ (คือพื้นสีดำว่างๆ นั่นแหละ) โดยกำหนดตำแหน่งข้อความและขนาดและสีของตัวอักษรเท่านั้นเอง 

ซึ่งหากจะเปรียบเทียบรูปแบบฟังก์ชั่นของ cvCreatImage และ cvPutText กับ cvShowImage แล้วจะพบว่า รูปแบบของการใส่ Parameter เข้าไปในฟังก์ชั่นก็ยังเหมือนเดิมในเอกสารของ OpenCV ถึงแม้ว่าเรากำลังเขียนอยู่บน Emgu Framework ก็ตาม เพีิยงแค่เรียก cvInvoke แล้วก็ตามด้วยฟังก์ชั่นบน OpenCV จากนั้นก็เติมพารามิเตอร์ให้ครบตามเอกสาร เท่านี้ เราก็เรียกใช้ OpenCV function ได้แล้วครับ

Emgu.CV.CvInvoke invoke OpenCV function

cvCreateImage

cvPutText

cvShowImage

แล้วทดสอบรันโปรแกรมดูครับ

image

งาน Image Processing บางอย่างเราอาจจะเจอวิธีแก้ไข ด้วย OpenCV Function ซึ่งถ้าหากเราต้องการนำมาใส่ใน Emgu Application ของเรา ก็เพียงเรียกใช้ cvInvoke เข้ามา แล้วก็ปรับแก้นิดหน่อยให้เป็นไปตาม .NET syntax เราก็อาจจะจบงานของเราได้เหมือนกัน ลองเอาไปประยุกต์ดูครับ

แล้วสนุกกับ Emgu นะครับ

ปล. และหากต้องการนำข้อมูลรูปภาพที่อยู่ใน pointer img กลับไปใส่ใน picturebox control ก็สามารถทำได้ ด้วยการใช้ CvInvoke.cvCopy Method โดยปลายทางของข้อมูล อาจจะเป็น bitmap แต่ size และ channel ต้องเท่ากันกับภาพต้นฉบับ และใช้ pointer properties ของตัวแปรปลายทางด้วย

private void button1_Click(object sender, EventArgs e)
{
      Image<Gray, byte> img2 = new Image<Gray, byte>(200,200);
      CvInvoke.cvPutText(img, "Hello Emgu", new Point(50, 50), ref font, color_text);           
      CvInvoke.cvShowImage("Simple Emgu application", img);
      CvInvoke.cvCopy(img, img2.Ptr, IntPtr.Zero);
      pictureBox1.Image = img2.ToBitmap();
   
}

how to create bitmap from image pointer IplImage

how to create bitmap from image pointer IplImage

อ่านเพิ่มเติม...

Wednesday, October 23

Emgu Convert Colour image to Gray,Binary Image

พอดีมีคนถามหาโค๊ด ซึ่งเป็นโค๊ดที่ผมเริ่มศึกษา Emgu ใหม่ๆ (ตอนนี้ ก็ยังใหม่อยู่เหมือนเดิม ;P ) ก็เลยเอามาอัพไว้ที่บล๊อกสักหน่อย

ไม่มีอะไรมากครับ เป็นการโหลด Image เข้ามา แล้วทำการแปลงเป็นภาพ Gray , Binary Image เฉยๆ

Emgu Convert Colour image to Gray,Binary Image

ไลบรารี่ที่ดึงเข้ามาใช้ในโปรเจค

Emgu Convert Colour image to Gray,Binary Image

อันนี้เป็นโค๊ด

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

using System.IO;
using Emgu.CV;
using Emgu.CV.Structure;


namespace CovertImage
{
    public partial class Form1 : Form
    {
        string imageFileName;
        Image<Bgr, Byte> imageCoverted;
        public Form1()
        {
            InitializeComponent();
        }

        private void button2_Click(object sender, EventArgs e)
        {
            string extension;
            OpenFileDialog openFile = new OpenFileDialog();
            openFile.Filter = "Image Files(*.BMP;*.JPG;*.GIF)|*.BMP;*.JPG;*.GIF|All files (*.*)|*.*";
            openFile.FilterIndex = 1;
            openFile.RestoreDirectory = true;
            if (openFile.ShowDialog() == DialogResult.OK)
            {
                extension = Path.GetExtension(openFile.FileName);
                if (extension == ".jpg" | extension == ".gif" | extension == ".bmp")
                {
                    imageFileName = openFile.FileName;
                    Image<Bgr, byte> img = new Image<Bgr, byte>(openFile.FileName);
                    imageCoverted = new Image<Bgr, Byte>(openFile.FileName);
                    pictureBox1.Image = img.ToBitmap(pictureBox1.Width, pictureBox1.Height);
                    pictureBox2.Image = null;
                }
                else
                {
                    pictureBox1.Image = null;
                    pictureBox2.Image = null;
                    MessageBox.Show("File does not supported");
                }

            }
        }

        private void button1_Click(object sender, EventArgs e)
        {
            processImage(imageCoverted, 0);
        }

        private void button4_Click(object sender, EventArgs e)
        {
            processImage(imageCoverted, 1);
        }

        private void processImage(Image<Bgr,byte> img,int Mode)
        {
            switch (Mode)
            {
                case 0:
                    label2.Text = "Gray";
                    pictureBox2.Image = img.Convert<Gray, byte>().ToBitmap(pictureBox2.Width, pictureBox2.Height);
                    break;
                case 1:
                    label2.Text = "Binary";
                    pictureBox2.Image = img.Convert<Gray, Byte>().ThresholdBinary(new Gray(127), new Gray(255)).ToBitmap(pictureBox2.Width, pictureBox2.Height);
                    break;
            }

        }

        private void toolStripStatusLabel1_Click(object sender, EventArgs e)
        {
            System.Diagnostics.Process.Start("http://vs-visual-studio.blogspot.com/");
        }
    }
}

ดาวน์โหลดซอร์สโค๊ดและโปรเจค https://dl.dropboxusercontent.com/u/65353188/CovertImage.zip

อ่านเพิ่มเติม...

Saturday, September 14

List video devices from PC by DirectShowLib

ในกรณีที่เราอยากทำให้ Application ของเราสามารถเลือกได้ว่าจะติดต่อกับกล้องตัวใน ถ้าเครื่องคอมพิวเตอร์ของเรามีมากกว่า 2 ตัว เราจะทำอย่างไร ถึงจะทำให้ application ที่เรากำลังสร้างนั้นมองเห็นกล้องทั้งหมดในเครื่องคอมพิวเตอร์เครื่องนั้นได้

วันนี้ผมจะแนะนำความสามารถของ Library ตัวหนึ่งชื่อ DirectShowLib ที่เอาไว้ดึงรายชื่อกล้องทั้งหมดที่ต่ออยู่ในเครื่องคอมพิวเตอร์ของเราออกมาเป็นตัวแปร array จากนั้นเราก็สามารถที่จะใช้ ComboBox ใช้แสดงรายชื่อกล้องทั้งหมด ไว้ให้ user เอาไว้เลือกต่อได้ ว่าจะติดต่อกับกล้องตัวไหน

อันดับแรก ก็ให้ไปดาวน์โหลด Library ตัวนี้ก่อนครับ อยู่ใน sourceforge ก็มี ดาวน์โหลดได้ที่นี่ http://sourceforge.net/projects/directshownet/files/ เมื่อดาวน์โหลดมาได้แล้ว เราต้องการไฟล์ DirectShowLib-2005.dll ที่อยู่ในโฟลเดอร์ \DirectShowLibV2-1\lib ของมัน

เรามาเริ่มสร้างโปรเจคกัน ในที่นี้ผมให้เป็น Windows Forms Application ที่เมนู Project เลือก Add reference หรือคลิกขวาที่ References ที่ ใต้ชื่อ Project เราที่ solution explorer ทำการ Browse หาไฟล์  DirectShowLib-2005.dll

image

สร้างหน้าต่าง form ตามรูป แล้วทำการเขียนโค๊ด (อันนี้ผมไม่บอกละเอียดแล้วนะ ถือว่า พอมีประสบการณ์กันบ้างหล่ะ)

image

เรามาดูที่โค๊ดกันครับ หัวใจของเรื่องนี้ ก็อยู่ตรงที่ เราสร้างตัวแปร object จาก Class DsDevice ที่อยู่ใน namespace ของ DirectShowLib (ฉะนั้นอย่าลืมที่ using DirectShowLib; ด้วยนะครับ)

ผมประกาศตัวแปร DsDevice[] videoDevices; ก่อน

จากนั้น ผมก็ทำการสร้างอินสแตนซ์จาก Class DsDevice แล้วก็เอามาวนลูปแสดงใน ComboBox


videoDevices = DsDevice.GetDevicesOfCat(FilterCategory.VideoInputDevice);
if (videoDevices.Length == 0)
{
     throw new Exception();
}

for (int i = 1, n = videoDevices.Length; i <= n; i++)
{
     string cameraName = i + " : " + videoDevices[i - 1].Name;
     cameraCombo.Items.Add(cameraName);
}
cameraCombo.SelectedIndex = 0;

ทีเหลือก็ไม่มีอะไรมาก เอา index ที่ได้จากการเลือก combobox สร้างอินสแตนซ์ Capture แล้วก็โยนให้ picturebox แสดงผล

ลองดูโค๊ดเต็มๆ

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

using Emgu.CV;
using Emgu.Util;
using Emgu.CV.Structure;

using DirectShowLib;

namespace AnyCameras
{
    public partial class Form1 : Form
    {
        DsDevice[] videoDevices;
        private Capture capture = null;

        public Form1()
        {
            InitializeComponent();
            timer.Interval = 100;

            // show device list
            try
            {
                videoDevices = DsDevice.GetDevicesOfCat(FilterCategory.VideoInputDevice);
                if (videoDevices.Length == 0)
                {
                    throw new Exception();
                }

                for (int i = 1, n = videoDevices.Length; i <= n; i++)
                {
                    string cameraName = i + " : " + videoDevices[i - 1].Name;
                    cameraCombo.Items.Add(cameraName);
                }
                cameraCombo.SelectedIndex = 0;
            }
            catch
            {
                cameraCombo.Items.Clear();
                cameraCombo.Items.Add("No cameras found");
                cameraCombo.SelectedIndex = 0;
                cameraCombo.Enabled = false;
            }       
       
        }

        private void StartCamera()
        {
            capture = new Capture(cameraCombo.SelectedIndex);
            timer.Start();
        }

        private void StopCamera()
        {
            timer.Stop();
            if (capture != null)
            {
                capture.Dispose();
            }
        }

        private void timer_Tick(object sender, EventArgs e)
        {
            Image<Bgr, Byte> frame = capture.QueryFrame();
            cameraPictureBox.Image = frame.ToBitmap();
        }

        private void startButton_Click(object sender, EventArgs e)
        {
            StartCamera();
            startButton.Enabled = false;
            stopButton.Enabled = true;
        }

        private void stopButton_Click(object sender, EventArgs e)
        {
            StopCamera();
            startButton.Enabled = true;
            stopButton.Enabled = false;
        }

        private void Form1_FormClosing(object sender, FormClosingEventArgs e)
        {
            timer.Stop();
            if (capture != null)
            {
                capture.Dispose();
            }
        }

        private void linkLabel1_LinkClicked(object sender, LinkLabelLinkClickedEventArgs e)
        {
            System.Diagnostics.Process.Start("http://vs-visual-studio.blogspot.com/");
        }

    }
}

 

ลองดาวน์โหลดโค๊ดไปเล่นกันครับ https://dl.dropboxusercontent.com/u/65353188/AnyCameras.zip

อ่านเพิ่มเติม...

Saturday, April 13

How to use ImageBox control

ImageBox คือ เครื่องมือในการสร้างพื้นที่การแสดงภาพ คล้ายๆ กับ PictureBox แต่ ต่างกันตรงที่ ImageBox นั้นมีฟังก์ชั่นเพิ่มเติมในการจัดการรูปภาพติดมาด้วย นอกจากนี้ เรายังสามารถกำหนดให้ ImageBox มีคุณสมบัติเทียบเท่า หรือมากกว่า PictureBox ได้เช่นกัน  ซึ่งนับว่ายืดหยุ่นกว่า PictureBox แบบเก่าๆ

แต่ ก่อนที่เราจะเรียกใช้ ImageBox ได้ เราจะต้องทำการเพิ่ม Control ตัวนี้เข้ามาในหน้าต่างของ Visual C# ซะก่อน ทำตามขั้นตอนดังนี้

คลิกขวา เลือก Choose Items.... ที่บริเวณพื้นที่ว่างของ หน้าต่าง Toolbox

Toolbox

ะปรากฏหน้าต่าง Choose Toolbox Items ให้ทำการคลิก Browse แล้วเลือกไฟล์ 'Emgu.CV.UI.dll' จาก C:\Emgu\emgucv-windows-x86-gpu 2.4.2.1777\bin หรือที่เราติดตั้ง emgu ไว้

จากนั้น เลื่อนหา ImageBox เมื่อเจอแล้ว ให้ทำการเช็คบอกซ์ แล้วกด OK

Choose Toolbox Items

กลับมาที่ Toolbox จะปรากฏ ImageBox control ขึ้นมา ให้ลากมาวางบนพื้นที่ว่างบนฟอร์ม ปรับแต่งขนาดให้เหมาะสม ทดสอบรันโปรแกรม

ImageBox control

นอกจากนี้ เราสามารถกำหนดคุณสมบัติของ ImageBox ได้ด้วย ในระหว่างการพัฒนา และการปล่อยซอร์ฟแวร์ให้ลูกค้าใช้ เราอาจะเปิดฟังก์ชั่นบางอย่างเท่านั้น  ด้วยการใช้ preprocessor กำหนดค่า เช่น

#if DEBUG
imageBox1.FunctionalMode = ImageBox.FunctionalModeOption.Everything;
#else
imageBox1.FunctionalMode = ImageBox.FunctionalModeOption.PanAndZoom;
#endif

ถ้าเราไม่ได้อยู่ในโหมด Debug ให้ ImageBox มีแค่ ฟังก์ชั่นการ ซูม เท่านั้น 

ลองนำไปประยุกต์กันดูนะัครับ ขอให้สนุกกับ Emgu

อ้างอิง http://www.emgu.com/wiki/index.php/ImageBox

อ่านเพิ่มเติม...

Saturday, March 30

Getting started Emgu with Visual C# 2010 Express

ถ้าหากเรามองว่า OpenCV คือ ไลบรารี่สำเร็จรูปที่ใช้สำหรับจัดการงานด้าน Computer Vision ซึ่งรองรับภาษา C/C++,JAVA,Python แล้วหล่ะก็ Emgu ก็คือฟังก์ชั่นที่ทำขึ้นมาครอบ OpenCV อีกชั้นหนึ่ง แต่ ทำขึ้นมาเพื่อรองรับภาษา Visual C# นั่นเอง  ซึ่งทำให้นักพัฒนาด้วยภาษา Visual C# สามารถก้าวเข้ามาเล่น Computer Vision ได้อย่างง่ายดาย

วันนี้ผมจะพาเพื่อนๆ มาติดตั้ง Emgu กันครับ เริ่มแรก เราต้องเตรียมซอร์ฟแวร์ที่จะติดตั้งกันก่อน โดยอ้างอิงจากที่ผมติดตั้งไว้แล้ว ดังนี้

ระบบปฏิบัติการ Windows7
Visual C# 2010 Express edition หากยังไม่มี ติดตั้งโปรแกรนี้ก่อน ได้จาก ที่นี่
ดาวน์โหลด Emgucv2.4.2 libemgucv-windows-x86-gpu-2.4.2.1777.exe ได้จาก ที่นี่
เมื่อได้ไฟล์ libemgucv-windows-x86-gpu-2.4.2.1777.exe ให้ทำการติดตั้งไว้ที่ Dirve C: เลยครับ

หรือจะไว้ที่ Drive ก็ได้ แล้วแต่สะดวก ในระหว่างการติดตั้ง ถ้ามีปัญหา เช่น

- Uninstall or Repair Microsoft C++ Redistributable ให้ตอบ Cancel
หรือ
- Visual Studio Debugger ถ้าเรายังไม่เคยติดตั้ง Emgu มาก่อน ใหคลิก Yes แต่ถ้าเคยติดตั้งมาแล้วให้คลิก No

Emgucv1Emgucv2Emgucv3Emgucv4Emgucv5

เมื่อเสร็จเรียบร้อยแล้ว เราต้ิองมาทำการ set path ให้ Windows มองหา Emgu ก่อน เพื่อป้องกันปัญหาต่างๆ ในการ Build solution โดยไปตั้งค่าที่

Control Panel->System->Advance system setting ที่แท๊บ Advanced คลิก

Environment Variables ที่ System Variables คลิกที่ Path แล้ว Edit..
ให้เอา path ที่เราติดตั้ง Emgu ไปใส่ต่อท้าย ในที่นี้ผมติดตั้งไว้ที่ C:\Emgu\emgucv-windows-x86-gpu2.4.2.1777\bin ผมก็ก๊อปปี้ไปต่อท้าย โดยคั่นด้วย ; ก่อน และหลัง path ที่ผมใส่เพิ่มเข้าไป จากนั้นกด OK เรื่อยๆ แล้วทำการรีสตาร์ทคอมพิวเตอร์ 1 ครั้ง

image

ต่อไป ให้ทำการ เปิด Visual C# ขึ้นมา แล้วทำการ New Project โดยเราจะสร้างโปรเจค แบบ  ตั้งชื่อโปรเคตามต้องการ จากนั้น สร้างหน้าตา form ดังรูป

image

กำหนดค่า text properties ให้ button1 และ button2 เป็น Image-1, Image-2 ตามลำดับ
กำหนดค่า text properties ให้ form1 เป็น  Hello Emgu
ส่วน PictureBox1 กำหนดให้มี Size เท่ากับ 400,300

Emgu Visual C# 2010 express

เสร็จแล้ว ที่หน้าต่าง Solution Explorer ทางขวามือ ที่ References ให้คลิกขวา แล้วทำการเลือก Add references..

ให้ทำการ add *.dll จากโฟวเดอร์ C:\Emgu\emgucv-windows-x86-gpu 2.4.2.1777\bin โดย

คลิก Ctrl ค้างไว้ แล้วคลิกที่ไฟล์ แต่ละไฟล์  แล้วกด OK

Add Reference_

จากนั้น กลับมาที่หน้า form design ของเรา ให้ดับเบิลคลิกที่ button1 เพื่อทำการเขียนโค๊ด โปรแกรมจะพาเราเข้ามาเขียนโค๊ดที่หน้า Form1.cs ให้เพิ่มโค๊ดเข้าไปดังรูป (เราทำการคลิกที่ button2 แล้วก็เพิ่มโค๊ดเข้าไปเช่นเดียวกัน กับครั้งแรก)

ก่อนที่เราจะรันโปรแกรมของเรา ให้เราทำการเตรียมภาพ ไว้ สองภาพ ในทีนี้ ผมได้เตรียมภาพที่ชื่อ linux.jpg และ windows.jpg เก็บไว้ที่ Drive E: ของผม (สังเกตจากในโค๊ด) โดยผมค้นหาภาพจาก อินเตอร์เนต โดยหาภาพที่มีขนาด 400x300 pixel ให้เท่ากับ size ของ picturebox ทีผมกำหนดไว้ตอนแรก

เมื่อเรียบร้อยแล้ว ให้กด F6 เพื่อ Build Solution หากไม่มีข้อความแสดง Error ใดๆ ให้กด F5 เพื่อ Start Debugging

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

using Emgu.CV;
using Emgu.CV.CvEnum;
using Emgu.CV.Structure;

namespace HelloEmgu
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            Image<Bgr, Byte> img = new Image<Bgr, byte>("E:\\linux.jpg");
            pictureBox1.Image = img.ToBitmap(pictureBox1.Width, pictureBox1.Height);
        }

        private void button2_Click(object sender, EventArgs e)
        {
            Image<Bgr, byte> img = new Image<Bgr, byte>("E:\\windows.jpg");
            pictureBox1.Image = img.ToBitmap(pictureBox1.Width, pictureBox1.Height);
        }
    }
}

HelloEmgu - Microsoft Visual C# 2010 Express

ทดลองกด Image-1 และ Image-2 ดูผลลัพธ์ครับ ถ้าโปรแกรมที่เราเขียนขึ้น แสดงภาพได้ตามต้องการ ก็แสดงความยินดีด้วยครับ และขอให้สนุกกับ Emgu นะครับ

 

----------------------------------------------------------------------------------------------------------------

แก้ปัญหา “The type initializer for 'Emgu.CV.CvInvoke' threw an exception.”

The type initializer for 'Emgu.CV.CvInvoke' threw an exception.

เนื่องจากเกิดปัญหาเครื่องผมถูกอัพเกรดให้เป็น WIndows7 64 บิต อย่างเต็มตัว ซึ่งก่อนหน้าถูกอัพเกรดโค๊ดเหล่านี้ยังทำงานได้เป็นปรกติ แต่พอมาเป็น WIndows7 64 บิต กลับพบว่า ไม่สามารถทำงานได้ ฉะนั้นจึงต้องมาการเปลี่ยนแปลงดังนี้

1. ใ้ห้ทำการติดตั้ง libemgucv-windows-x86-2.4.0.1717.exe ดาวน์โหลดจาก ที่นี่ ติดตั้งเหมือนเดิม แต่อาจไม่จำเป็นต้องเป็น Drive C: แล้ว เพราะเราจะใช้การก๊อปปี้ไฟล์ dll มาใส่ในโปรเจคเลย

2. ติดตั้งเสร็จแล้ว ให้ทำการแก้ไขโค๊ด โดยทำการ Add references ใหม่ (reference เก่าให้ delete ทิ้งไป) โดยให้ browse ไปที่ path ที่เราติดตั้ง Emgu เวอร์ชั่น 2.4.0 แทน ในที่นี้ผม browse ไำปที่ E:\Emgu\emgucv-windows-x86 2.4.0.1717\bin แล้วเลือกไฟล์ Emgu.CV.dll,Emgu.CV.GPU.dll, Emgu.CV.ML.dll, Emgu.CV.UI.dll, Emgu.Util.dll

3. ทำการ add file dll อื่นมาเลย ในที่นี้เราต้องทำการเลือก Add Existing items..  แล้วเลือกเอาไฟล์ dll เข้ามาในโปรเจค 2 ไฟล์ คือไฟล์ opencv_core240.dll, opencv_imgproc240.dll ซึ่งอยู่ใน E:\Emgu\emgucv-windows-x86 2.4.0.1717\bin\x86 ที่หน้าต่าง properties ช่อง Copy to output directory ให้เลือก copy always

แล้วลองกด F5 (Start debugging) อีกครั้ง

-----------------------------------------------------------------------

แก้ไข 18/07/2014

เจอปัญหาเก่าอีกครั้ง ตอนนี้เปลี่ยนเครื่องคอมพ์ กับ windows 7 64bit ไม่แน่ใจว่าเกิดอะไรขึ้นเหมือนกัน ปัญหาเยอะจริงๆ เวลาเปลี่ยนเวอร์ชั่นเนี้ย เท่าๆ ที่อ่านดูคล้ายๆ กับว่าตอนที่ make file มาให้เรา มีปัญหาเรื่อง dirver card vga ไม่รองรับกับเครื่องอื่นๆ ก็รอเขาแก้ปัญหากันต่อไป ตอนนี้ ก็โหลดเวอร์ชั่นเบต้า มาใช้ก่อน เป็นเวอร์ชั่นที่ใช้กับ driver card vga ได้ทุกรุ่น Download libemgucv-windows-universal-cuda-2.9.0.1922-beta.exe (214.0 MB) หลังจากติดตั้งแล้ว ให้ทำการแก้ไข path ใหม่ ใน

Control Panel->System->Advance system setting ที่แท๊บ Advanced คลิก

เพิ่ม path นี้เข้าไป (สำหรับ windows7 64 bit)

C:\Emgu\emgucv-windows-universal-cuda 2.9.0.1922\bin\x64

แล้วทำการ รีสตาร์ทเครื่องคอมพ์ หนึ่งครั้ง จากนั้นก็ทำการสร้างโปรเจคใน Visual C# เหมือนเดิม ทำการ add referrence เอาเฉาพะ EMGU.CV.dll, EMGU.CV.UI.dll, Emgu.Util.dll ซึ่งอยู่ใน

C:\Emgu\emgucv-windows-universal-cuda 2.9.0.1922\bin\

ที่เหลือไม่ต้องทำอะไรเหมือนคราวที่แล้ว เพราะเราได้กำหนด path ไว้แล้ว ทำการเขียนโค๊ดทดสอบ  อ่อ อย่าลืมเลือก solution platforms ให้เป็น x64 ด้วยหล่ะ ให้ตรงกับที่เราอ้าง path

"The type initializer for 'Emgu.CV.CvInvoke' threw an exception."

"The type initializer for 'Emgu.CV.CvInvoke' threw an exception."

เป็นวิธีแก้ปัญหาที่ง่ายดี ก็ได้หวังว่าผู้พัฒนา EMGU จะทำให้ง่ายกว่านี้ และ bug น้อยลงไปเรื่อยๆ นะครับ เอาหล่ะ ขอให้สนุกกับ EMGU กันต่อ

อ่านเพิ่มเติม...
 

แจกฟรี พื้นที่ฝากไฟล์ 2 GB

ads

ติดตามข่าวสารผ่าน Twitter

ติดตาม Blog นี้

Blog อื่นๆของฉัน

จำนวนการเยี่ยมชมบล๊อก