348 lines
14 KiB
C#
348 lines
14 KiB
C#
using MilCommon;
|
|
using VisionCommon;
|
|
using Hermes;
|
|
using Matrox.MatroxImagingLibrary;
|
|
using System;
|
|
|
|
namespace MilPattern {
|
|
public class ImageModelFinderTrainParam : ImageTrainParam, ICloneable {
|
|
public object Clone() {
|
|
return new ImageModelFinderTrainParam() {
|
|
TrainImage = TrainImage,
|
|
TrainRoi = TrainRoi.Clone() as ROI,
|
|
TrainOrigin = TrainOrigin.Clone() as Cross,
|
|
TrainOriginInModel = TrainOriginInModel.Clone() as Cross
|
|
};
|
|
}
|
|
}
|
|
|
|
internal static class MmfImage {
|
|
public static ITrainParam GetTrainParam(MIL_ID contextId) {
|
|
var trainParam = new ImageModelFinderTrainParam();
|
|
if (MmfCommon.HasModel(contextId)) {
|
|
trainParam.TrainRoi = GetTrainROI(contextId);
|
|
trainParam.TrainOrigin = GetFixtureOrigin(contextId);
|
|
trainParam.TrainOriginInModel = GetTrainOriginInModel(contextId);
|
|
}
|
|
|
|
return trainParam;
|
|
}
|
|
|
|
public static ROI GetTrainROI(MIL_ID contextId) {
|
|
if (MmfCommon.HasModel(contextId)) {
|
|
MIL_INT x = MIL.MmodInquire(contextId, MIL.M_DEFAULT, MIL.M_ALLOC_OFFSET_X, MIL.M_NULL);
|
|
MIL_INT y = MIL.MmodInquire(contextId, MIL.M_DEFAULT, MIL.M_ALLOC_OFFSET_Y, MIL.M_NULL);
|
|
MIL_INT width = MIL.MmodInquire(contextId, MIL.M_DEFAULT, MIL.M_ALLOC_SIZE_X, MIL.M_NULL);
|
|
MIL_INT height = MIL.MmodInquire(contextId, MIL.M_DEFAULT, MIL.M_ALLOC_SIZE_Y, MIL.M_NULL);
|
|
|
|
return new ROI(
|
|
x + ((int)width * 0.5),
|
|
y + ((int)height * 0.5),
|
|
(int)width, (int)height, new Angle());
|
|
}
|
|
|
|
return new ROI();
|
|
}
|
|
|
|
public static Cross GetFixtureOrigin(MIL_ID contextId) {
|
|
if (MmfCommon.HasModel(contextId)) {
|
|
double originalX = 0;
|
|
MIL.MmodInquire(contextId, MIL.M_DEFAULT, MIL.M_ORIGINAL_X, ref originalX);
|
|
double originalY = 0;
|
|
MIL.MmodInquire(contextId, MIL.M_DEFAULT, MIL.M_ORIGINAL_Y, ref originalY);
|
|
|
|
return new Cross(new ImagePoint(originalX, originalY));
|
|
}
|
|
|
|
return new Cross(new ImagePoint());
|
|
}
|
|
|
|
public static Cross GetTrainOriginInModel(MIL_ID contextId) {
|
|
if (MmfCommon.HasModel(contextId)) {
|
|
double trainOriginInModelX = 0;
|
|
MIL.MmodInquire(contextId, MIL.M_DEFAULT, MIL.M_REFERENCE_X, ref trainOriginInModelX);
|
|
double trainOriginInModelY = 0;
|
|
MIL.MmodInquire(contextId, MIL.M_DEFAULT, MIL.M_REFERENCE_Y, ref trainOriginInModelY);
|
|
|
|
return new Cross(new ImagePoint(trainOriginInModelX, trainOriginInModelY));
|
|
}
|
|
|
|
return new Cross(new ImagePoint());
|
|
}
|
|
|
|
public static int Train(MIL_ID contextId, ITrainParam trainParam) {
|
|
MmfCommon.DeleteAllModels(contextId);
|
|
|
|
if (trainParam is ImageModelFinderTrainParam) {
|
|
var param = trainParam as ImageModelFinderTrainParam;
|
|
var result = DefineModel(contextId, param);
|
|
|
|
if (result == E1.OK) {
|
|
SetDefaultMask(contextId);
|
|
return result;
|
|
}
|
|
}
|
|
|
|
return E1.GENERIC;
|
|
}
|
|
|
|
private static void SetDefaultMask(MIL_ID contextId) {
|
|
MIL_ID grayMaskImageId = MIL.M_NULL;
|
|
MIL_ID grayEdgeImageId = MIL.M_NULL;
|
|
|
|
try {
|
|
grayMaskImageId = GetGrayMaskImage(contextId);
|
|
if (grayMaskImageId != MIL.M_NULL) {
|
|
MIL.MbufClear(grayMaskImageId, 255);
|
|
|
|
grayEdgeImageId = MilEnvironment.GetCompatibleGrayImageBuffer(grayMaskImageId);
|
|
MIL.MmodDraw(MIL.M_DEFAULT, contextId, grayEdgeImageId, MIL.M_DRAW_EDGES, MIL.M_DEFAULT, MIL.M_DEFAULT);
|
|
MIL.MimDilate(grayEdgeImageId, grayEdgeImageId, 2, MIL.M_GRAYSCALE);
|
|
|
|
MIL.MbufClearCond(grayMaskImageId,
|
|
MIL.M_RGB888_R(0),
|
|
MIL.M_RGB888_G(0),
|
|
MIL.M_RGB888_B(0),
|
|
grayEdgeImageId, MIL.M_EQUAL, 255);
|
|
|
|
SetMaskImage(contextId, grayMaskImageId);
|
|
}
|
|
}
|
|
catch (Exception e) {
|
|
}
|
|
finally {
|
|
MilEnvironment.FreeImage(grayMaskImageId);
|
|
MilEnvironment.FreeImage(grayEdgeImageId);
|
|
}
|
|
}
|
|
|
|
private static int DefineModel(MIL_ID contextId, ImageModelFinderTrainParam param) {
|
|
if ((MIL_ID)param.TrainImage == MIL.M_NULL) {
|
|
return E1.ARGUMENT;
|
|
}
|
|
|
|
if (param.TrainRoi is null && param.TrainOrigin is null) {
|
|
return Train(contextId, (MIL_ID)param.TrainImage);
|
|
}
|
|
else if (param.TrainRoi is null) {
|
|
return Train(contextId, (MIL_ID)param.TrainImage, param.TrainOrigin);
|
|
}
|
|
else if (param.TrainOrigin is null) {
|
|
return Train(contextId, (MIL_ID)param.TrainImage, param.TrainRoi);
|
|
}
|
|
|
|
return Train(contextId, (MIL_ID)param.TrainImage, param.TrainRoi, param.TrainOrigin);
|
|
}
|
|
|
|
public static int Train(MIL_ID contextId, MIL_ID trainImage) {
|
|
var imageCenter = MilEnvironment.GetImageCenter(trainImage);
|
|
return Train(contextId, trainImage, new Cross(imageCenter));
|
|
}
|
|
|
|
public static int Train(MIL_ID contextId, MIL_ID trainImage, Cross trainOrigin) {
|
|
var imageCenter = MilEnvironment.GetImageCenter(trainImage);
|
|
var imageSize = MilEnvironment.GetImageSize(trainImage);
|
|
|
|
return Train(
|
|
contextId,
|
|
trainImage,
|
|
new ROI(imageCenter, imageSize.Width, imageSize.Height),
|
|
trainOrigin);
|
|
}
|
|
|
|
public static int Train(MIL_ID contextId, MIL_ID trainImage, ROI trainRoi) {
|
|
return Train(
|
|
contextId,
|
|
trainImage,
|
|
trainRoi,
|
|
new Cross(trainRoi.Center));
|
|
}
|
|
|
|
public static int Train(MIL_ID contextId, MIL_ID trainImage, ROI trainRoi, Cross trainOrigin) {
|
|
var originInTrainRoi = new Cross(new ImagePoint(
|
|
trainOrigin.Origin.X - trainRoi.Left,
|
|
trainOrigin.Origin.Y - trainRoi.Top));
|
|
|
|
return TrainImpl(
|
|
contextId,
|
|
trainImage,
|
|
trainRoi,
|
|
originInTrainRoi);
|
|
}
|
|
|
|
private static int TrainImpl(MIL_ID contextId, MIL_ID trainImage, ROI trainRoi, Cross originInTrainRoi) {
|
|
if (MilEnvironment.IsColorImage(trainImage)) {
|
|
var grayTrainImage = MilEnvironment.ConvertToGray(trainImage);
|
|
var result = TrainWithGrayImage(contextId, grayTrainImage, trainRoi, originInTrainRoi);
|
|
MIL.MbufFree(grayTrainImage);
|
|
return result;
|
|
}
|
|
|
|
return TrainWithGrayImage(contextId, trainImage, trainRoi, originInTrainRoi);
|
|
}
|
|
|
|
private static int TrainWithGrayImage(MIL_ID contextId, MIL_ID grayTrainImage, ROI trainRoi, Cross originInTrainRoi) {
|
|
MmfCommon.DeleteAllModels(contextId);
|
|
TrainWholeImageWithGraphicTrainROI(contextId, grayTrainImage, trainRoi);
|
|
|
|
return SetTrainOrigin(contextId, originInTrainRoi);
|
|
}
|
|
|
|
public static int SetTrainOrigin(MIL_ID contextId, Cross originInTrainRoi) {
|
|
if (MmfCommon.HasModel(contextId)) {
|
|
MIL.MmodControl(contextId, MIL.M_ALL, MIL.M_REFERENCE_X, originInTrainRoi.Origin.X);
|
|
MIL.MmodControl(contextId, MIL.M_ALL, MIL.M_REFERENCE_Y, originInTrainRoi.Origin.Y);
|
|
}
|
|
|
|
MIL.MmodPreprocess(contextId, MIL.M_DEFAULT);
|
|
|
|
if (!MmfCommon.IsPreprocessed(contextId)) {
|
|
return E1.GENERIC;
|
|
}
|
|
|
|
return E1.OK;
|
|
}
|
|
|
|
private static void TrainWholeImageWithTrainROI(MIL_ID contextId, MIL_ID grayTrainImage, ROI trainRoi) {
|
|
MIL.MmodDefine(
|
|
contextId, MIL.M_IMAGE, grayTrainImage,
|
|
trainRoi.Left, trainRoi.Top, trainRoi.Width, trainRoi.Height);
|
|
}
|
|
|
|
private static void TrainWholeImageWithGraphicTrainROI(MIL_ID contextId, MIL_ID grayTrainImage, ROI trainRoi) {
|
|
// 1. Alloc graphic context
|
|
MIL_ID graphicList = MIL.M_NULL;
|
|
MIL_ID graphicsContext = MIL.M_NULL;
|
|
MIL_ID systemId = MmfCommon.GetSystemOfContext(contextId);
|
|
MIL.MgraAllocList(systemId, MIL.M_DEFAULT, ref graphicList);
|
|
MIL.MgraAlloc(systemId, ref graphicsContext);
|
|
|
|
// 2. Set graphic ROI to train image
|
|
MIL.MgraRectAngle(
|
|
graphicsContext,
|
|
graphicList,
|
|
trainRoi.CenterX,
|
|
trainRoi.CenterY,
|
|
trainRoi.Width,
|
|
trainRoi.Height,
|
|
trainRoi.Angle.Degree,
|
|
MIL.M_CENTER_AND_DIMENSION);
|
|
MIL.MbufSetRegion(grayTrainImage, graphicList, MIL.M_DEFAULT, MIL.M_RASTERIZE + MIL.M_FILL_REGION, MIL.M_DEFAULT);
|
|
|
|
// 3. Train
|
|
MIL.MmodDefine(
|
|
contextId, MIL.M_IMAGE, grayTrainImage,
|
|
MIL.M_DEFAULT, MIL.M_DEFAULT, MIL.M_DEFAULT, MIL.M_DEFAULT);
|
|
|
|
// 4. Delete graphic ROI
|
|
MIL.MbufSetRegion(grayTrainImage, MIL.M_NULL, MIL.M_DEFAULT, MIL.M_DELETE, MIL.M_DEFAULT);
|
|
|
|
// 5. Free graphic
|
|
MIL.MgraFree(graphicsContext);
|
|
MIL.MgraFree(graphicList);
|
|
}
|
|
|
|
public static MIL_ID GetGrayModelImage(MIL_ID contextId) {
|
|
if (MmfCommon.HasModel(contextId)) {
|
|
return GetModelImageFromContext(contextId, 1);
|
|
}
|
|
return MIL.M_NULL;
|
|
}
|
|
|
|
public static MIL_ID GetColorModelEdgeImage(MIL_ID contextId) {
|
|
if (MmfCommon.HasModel(contextId)) {
|
|
var modelImageId = GetModelImageFromContext(contextId, 3);
|
|
DrawTrainEdge(contextId, modelImageId);
|
|
|
|
return modelImageId;
|
|
}
|
|
return MIL.M_NULL;
|
|
}
|
|
|
|
public static MIL_ID GetColorModelImage(MIL_ID contextId) {
|
|
if (MmfCommon.HasModel(contextId)) {
|
|
return GetModelImageFromContext(contextId, 3);
|
|
}
|
|
return MIL.M_NULL;
|
|
}
|
|
|
|
private static MIL_ID GetModelImageFromContext(MIL_ID contextId, int channel) {
|
|
MIL_INT sizeX = MIL.MmodInquire(contextId, 0, MIL.M_BOX_SIZE_X, MIL.M_NULL);
|
|
MIL_INT sizeY = MIL.MmodInquire(contextId, 0, MIL.M_BOX_SIZE_Y, MIL.M_NULL);
|
|
|
|
MIL_ID systemId = MmfCommon.GetSystemOfContext(contextId);
|
|
MIL_ID colorModelImageId = MIL.MbufAllocColor(
|
|
systemId, channel, sizeX, sizeY,
|
|
8 + MIL.M_UNSIGNED,
|
|
MIL.M_IMAGE + MIL.M_GRAB + MIL.M_PROC + MIL.M_DISP,
|
|
MIL.M_NULL);
|
|
|
|
MIL.MmodDraw(MIL.M_DEFAULT, contextId, colorModelImageId, MIL.M_DRAW_IMAGE, MIL.M_DEFAULT, MIL.M_DEFAULT);
|
|
|
|
return colorModelImageId;
|
|
}
|
|
|
|
private static void DrawTrainEdge(MIL_ID modContextId, MIL_ID colorModelImage) {
|
|
MIL_ID COLOR_TRAIN_EDGE = MIL.M_COLOR_DARK_GREEN;
|
|
MIL_ID edgeGrayImage = MilEnvironment.GetCompatibleGrayImageBuffer(colorModelImage);
|
|
MIL.MmodDraw(MIL.M_DEFAULT, modContextId, edgeGrayImage, MIL.M_DRAW_EDGES, MIL.M_DEFAULT, MIL.M_DEFAULT);
|
|
|
|
MIL.MbufClearCond(colorModelImage,
|
|
MIL.M_RGB888_R((int)COLOR_TRAIN_EDGE),
|
|
MIL.M_RGB888_G((int)COLOR_TRAIN_EDGE),
|
|
MIL.M_RGB888_B((int)COLOR_TRAIN_EDGE),
|
|
edgeGrayImage, MIL.M_EQUAL, 255);
|
|
|
|
MilEnvironment.ClearImage(edgeGrayImage);
|
|
}
|
|
|
|
public static MIL_ID GetMaskImage(MIL_ID contextId) {
|
|
return GetGrayMaskImage(contextId);
|
|
}
|
|
|
|
public static void DrawMaskImage(MIL_ID contextId, MIL_ID overalyId) {
|
|
MIL_ID grayMaskImageId = GetGrayMaskImage(contextId);
|
|
if (grayMaskImageId != MIL.M_NULL) {
|
|
ConvertMaskGrayToColorImage(grayMaskImageId, overalyId);
|
|
}
|
|
}
|
|
|
|
private static MIL_ID GetGrayMaskImage(MIL_ID contextId) {
|
|
MIL_ID grayMaskImageId = MIL.M_NULL;
|
|
|
|
if (MmfCommon.HasModel(contextId)) {
|
|
MIL_INT sizeX = MIL.MmodInquire(contextId, 0, MIL.M_BOX_SIZE_X, MIL.M_NULL);
|
|
MIL_INT sizeY = MIL.MmodInquire(contextId, 0, MIL.M_BOX_SIZE_Y, MIL.M_NULL);
|
|
int channel = 1;
|
|
|
|
MIL_ID systemId = MmfCommon.GetSystemOfContext(contextId);
|
|
grayMaskImageId = MIL.MbufAllocColor(
|
|
systemId, channel, sizeX, sizeY,
|
|
8 + MIL.M_UNSIGNED,
|
|
MIL.M_IMAGE + MIL.M_GRAB + MIL.M_PROC + MIL.M_DISP,
|
|
MIL.M_NULL);
|
|
MIL.MbufClear(grayMaskImageId, 0);
|
|
|
|
MIL.MmodDraw(MIL.M_DEFAULT, contextId, grayMaskImageId, MIL.M_DRAW_DONT_CARE, MIL.M_DEFAULT, MIL.M_DEFAULT);
|
|
}
|
|
return grayMaskImageId;
|
|
}
|
|
|
|
private static void ConvertMaskGrayToColorImage(MIL_ID grayMaskImage, MIL_ID colorMaskImage) {
|
|
MIL_ID COLOR_MASK = MIL.M_COLOR_DARK_MAGENTA;
|
|
|
|
MIL.MbufClearCond(colorMaskImage,
|
|
MIL.M_RGB888_R((int)COLOR_MASK),
|
|
MIL.M_RGB888_G((int)COLOR_MASK),
|
|
MIL.M_RGB888_B((int)COLOR_MASK),
|
|
grayMaskImage, MIL.M_EQUAL, 255);
|
|
}
|
|
|
|
public static int SetMaskImage(MIL_ID contextId, MIL_ID maskImage) {
|
|
MIL.MmodMask(contextId, 0, maskImage, MIL.M_DONT_CARE, MIL.M_DEFAULT);
|
|
|
|
return E1.OK;
|
|
}
|
|
}
|
|
}
|