2026-03-30 17:09:29 +09:00

330 lines
12 KiB
C#

using Aurora.Api;
using Aurora;
using Aurora.View;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using VisionCommon;
using VisionUI;
using VisionUI.Camera;
using AuroraIO;
using AuroraCAS;
using Matrox.MatroxImagingLibrary;
using MilCommon;
using MilUI;
using WeldingCommon.Sequences;
using System.Windows.Input;
using System.Windows.Threading;
using System.Windows.Controls;
using System.Net;
using Aurora.Api.Devices;
using MilPattern;
using WeldingCommon.Settings;
namespace WeldingCommon.Views.Manual
{
public class UCManualModelFinderViewModel : NotifyPropertyChangedBase
{
private readonly Logger Log = new Logger("ManualModelFinder");
private readonly IAuroraEnvironment _auroraEnv;
private readonly DispatcherTimer _MonitorTimer;
#region 비전 관련
private PatternResult _patternResult;
private PatternAgentBase _patternAgent;
private ProcPatternInfo _procPatternInfo;
private PatternInfo _procPattern;
private PatternInfo _patternInfo;
private PatternInfo _testPatternInfo;
private ICameraDisplay _cameraDisplay;
private CameraAgentBase _cameraAgent;
private ImageManager _imageManager;
private CamConfig _camConfig;
private MIL_ID displayMilId = MIL.M_NULL;
private object _grabImage;
#endregion
private SequenceSetting _sequenceSetting;
public ICommand CMD_VisibleChanged { get; }
public ICommand CMD_LoadPreviousPage { get; }
public ICommand CMD_LoadNextImage { get; }
public ICommand CMD_FindPattern { get; }
public ICommand CMD_FindTestPattern { get; }
public ICommand CMD_GrabFind { get; }
public ICommand CMD_GrabFindTest { get; }
public ObservableCollection<FileSystemItem> FileSystemItems { get; set; }
private ModelFinderRunParam _currentParam;
public ModelFinderRunParam CurrentParam {
get { return _currentParam; }
set { SetProperty(ref _currentParam, value); }
}
private ModelFinderRunParam _testParam;
public ModelFinderRunParam TestParam {
get { return _testParam; }
set { SetProperty(ref _testParam, value); }
}
private ImagePoint _testLeftTopPoint;
public ImagePoint TestLeftTopPoint {
get { return _testLeftTopPoint; }
set { SetProperty(ref _testLeftTopPoint, value); }
}
private object _selectedItem;
public object SelectedItem {
get { return _selectedItem; }
set { SetProperty(ref _selectedItem, value); }
}
public UCManualModelFinderViewModel(IAuroraEnvironment aurora)
{
_auroraEnv = aurora;
CMD_VisibleChanged = new DelegateCommand(VisibleChanged);
CMD_LoadPreviousPage = new DelegateCommand(LoadPreviousPage);
CMD_LoadNextImage = new DelegateCommand(LoadNextPage);
CMD_FindPattern = new DelegateCommand(FindPattern);
CMD_FindTestPattern = new DelegateCommand(FindTestPattern);
CMD_GrabFind = new DelegateCommand(GrabFind);
CMD_GrabFindTest = new DelegateCommand(GrabFindTest);
_MonitorTimer = new DispatcherTimer();
_MonitorTimer.Tick += OnMonitoring;
_MonitorTimer.Interval = TimeSpan.FromMilliseconds(100);
_imageManager = new ImageManager();
_camConfig = VisionEnv.AuroraEnv.DeviceManager.GetDeviceConfig("CAM1") as CamConfig;
FileSystemItems = new ObservableCollection<FileSystemItem>();
_auroraEnv.EventObservable.AsObservable("LoadImageRequest")
.Subscribe(x => {
if (x.Param != null && x.Param is string path) {
if (displayMilId != MIL.M_NULL) { MIL.MbufFree(displayMilId); }
MIL_ID image = (MIL_ID)_imageManager.LoadImage(path, _camConfig.CamConnConfig.BoardType, _camConfig.CamConnConfig.BoardSlotPos);
_cameraDisplay.SetImage(image);
_cameraDisplay.ClearMeasureGraphics();
displayMilId = image;
}
});
}
private List<PatternInfo> mainPatterns = new List<PatternInfo>();
private void VisibleChanged(object obj)
{
bool visible = (bool)obj;
if (visible) {
_sequenceSetting = _auroraEnv.SettingEntry[CommonSettingIds.Sequence] as SequenceSetting;
LoadRootItems(_sequenceSetting.VisionFolderName);
_imageManager = new ImageManager();
// InitializeCameraDevice
FovInfo _fovInfo = VisionRecipeManager.GetFovInfos().FirstOrDefault();
//FovInfo는 UI 생성자를 통해 전달된 Params의 FovInfo를 사용한다.
_patternAgent = FovPatternAgentManager.GetAgent(_fovInfo.ToSubSysInfo());
List<PatternInfo> patterns = _patternAgent.GetMainPatterns(_fovInfo);
_patternInfo = patterns[0];
var pattern = _patternAgent.GetPattern(_patternInfo);
CurrentParam = pattern.GetRunParam() as ModelFinderRunParam;
// 테스트할 패턴은 Clone한 것에서 특정 좌표들만 바꾸어줌.
_testPatternInfo = patterns[0].Clone() as PatternInfo;
var testPattern = _patternAgent.GetPattern(_testPatternInfo);
TestParam = _patternAgent.GetPattern(_testPatternInfo).GetRunParam() as ModelFinderRunParam;
//TestLeftTopPoint = TestParam.MmfParamExt.FindROI.LeftTop;
//카메라 디스플레이 가져오기
_cameraDisplay = CameraDisplayManager.GetDisplay(_fovInfo, eDisplayType.Pattern);
//카메라 에이전트 가져오기
_cameraAgent = CameraAgentManager.GetCameraAgent(_fovInfo);
_grabImage = _cameraAgent.CloneImageBuffer();
_MonitorTimer.Start();
} else {
FileSystemItems?.Clear();
if (displayMilId != MIL.M_NULL) { MIL.MbufFree(displayMilId); }
_MonitorTimer.Stop();
}
}
private void OnMonitoring(object sender, EventArgs e)
{
}
private void LoadRootItems(string str)
{
var rootPath = str;
FileSystemItems.Add(new FileSystemItem(rootPath));
}
private void LoadPreviousPage(object obj)
{
int dir = -1;
ChangeSelectedItem(FileSystemItems[0], dir);
}
private void LoadNextPage(object obj)
{
int dir = +1;
ChangeSelectedItem(FileSystemItems[0], dir);
}
private void FindPattern(object obj)
{
_cameraDisplay.ClearMeasureGraphics();
_patternResult = _patternAgent.Find(_patternInfo, displayMilId, _cameraDisplay);
if (_patternResult.Status == eFoundStatus.FoundOK) _patternAgent.Draw(_patternInfo, _patternResult, _cameraDisplay);
}
private void FindTestPattern(object obj)
{
_cameraDisplay.ClearMeasureGraphics();
double left = TestLeftTopPoint.X;
double top = TestLeftTopPoint.Y;
double width = TestParam.GetFindRoi().Width;
double height = TestParam.GetFindRoi().Height;
Angle angle = TestParam.GetFindRoi().Angle;
TestParam.SetFindROI(new ROI(left + (double)(width / 2), top + (double)(height / 2), width, height, angle));
_patternAgent.GetPattern(_testPatternInfo).SetRunParam(TestParam);
var pattern = _patternAgent.GetPattern(_testPatternInfo);
_patternResult = _patternAgent.Find(_testPatternInfo, displayMilId, _cameraDisplay);
if (_patternResult.Status == eFoundStatus.FoundOK) _patternAgent.Draw(_testPatternInfo, _patternResult, _cameraDisplay);
}
private void GrabFind(object obj)
{
// Camera Grab할 경우
_cameraDisplay.ClearMeasureGraphics();
object image = _grabImage;
_cameraAgent.GrabSync(_cameraDisplay, ref image);
_grabImage = image;
_patternResult = _patternAgent.Find(_patternInfo, image, _cameraDisplay);
if (_patternResult.Status == eFoundStatus.FoundOK) _patternAgent.Draw(_patternInfo, _patternResult, _cameraDisplay);
}
private void GrabFindTest(object obj)
{
_cameraDisplay.ClearMeasureGraphics();
double left = TestLeftTopPoint.X;
double top = TestLeftTopPoint.Y;
double width = TestParam.GetFindRoi().Width;
double height = TestParam.GetFindRoi().Height;
Angle angle = TestParam.GetFindRoi().Angle;
TestParam.SetFindROI(new ROI(left + (double)(width / 2), top + (double)(height / 2), width, height, angle));
_patternAgent.GetPattern(_testPatternInfo).SetRunParam(TestParam);
object image = _grabImage;
_cameraAgent.GrabSync(_cameraDisplay, ref image);
_grabImage = image;
_patternResult = _patternAgent.Find(_testPatternInfo, image, _cameraDisplay);
if (_patternResult.Status == eFoundStatus.FoundOK) _patternAgent.Draw(_testPatternInfo, _patternResult, _cameraDisplay);
}
private bool ChangeSelectedItem(FileSystemItem a, int dir)
{
if (SelectedItem == null) {
return false;
}
if (a == SelectedItem) {
return true;
}
if (a.Children.Count == 0) {
return false;
}
foreach (var child in a.Children) {
if (ChangeSelectedItem(child, dir) && !child.IsFolder) {
int index = a.Children.IndexOf(child);
if (index > 0) // 인덱스가 0보다 클 때만 이전 항목을 선택
{
SelectedItem = a.Children[index + dir];
a.Children[index + dir].IsSelected = true;
child.IsSelected = false;
}
return true;
}
}
return false;
}
}
public class FileSystemItem : NotifyPropertyChangedBase
{
public FileSystemItem(string path)
{
this.FullPath = Path.GetFullPath(path);
this.Name = Path.GetFileName(path);
this.IsFolder = Directory.Exists(path);
this.Children?.Clear();
this.Children = new ObservableCollection<FileSystemItem>();
if (IsFolder) {
LoadChildren(path);
}
}
private void LoadChildren(string path)
{
try {
foreach (var directory in Directory.GetDirectories(path)) {
Children.Add(new FileSystemItem(directory));
}
foreach (var file in Directory.GetFiles(path)) {
Children.Add(new FileSystemItem(file));
}
} catch {
// 예외 처리 (예: 접근 권한 없음)
}
}
public string FullPath { get; set; }
public string Name { get; set; }
public bool IsFolder { get; set; }
public ObservableCollection<FileSystemItem> Children { get; set; }
private bool _isSelected;
public bool IsSelected {
get { return _isSelected; }
set {
SetProperty(ref _isSelected, value);
if (value == true) LoadImage(FullPath);
}
}
private bool _isExpanded;
public bool IsExpanded {
get { return _isExpanded; }
set { SetProperty(ref _isExpanded, value); }
}
private void LoadImage(string path)
{
// 파일 포맷 확인하기
string fileExtension = Path.GetExtension(path);
if (fileExtension != ".jpg" && fileExtension != ".JPG" && fileExtension != ".jpeg" && fileExtension != ".JPEG"
&& fileExtension != ".bmp" && fileExtension != ".BMP" && fileExtension != ".png" && fileExtension != ".PNG") return;
System.Windows.Application.Current.AuroraEnv().EventPublisher.Publish(new EventMessage("UCModelFinderViewModel", "LoadImageRequest", path));
}
}
}