2026-01-26 18:56:53 +09:00

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;
}
}
}