Files
Million/Million Hunter/HunterMainForm.cs
2022-10-18 16:23:43 +09:00

494 lines
20 KiB
C#

using DevExpress.XtraEditors;
using DevExpress.XtraTreeList;
using Million;
using Million.IndicatorConditionSetup;
using Million.HunterSubForm;
using Million.HunterSubForm.IndicatorSetupForm;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
using Million.Data;
using Million.DbManagement;
using Million.FileDBManagement;
using Million.Manager;
using Million.SaveData;
using Microsoft.CodeAnalysis.CSharp.Scripting;
using System.Threading.Tasks;
using DevExpress.Data.Helpers;
using System.Drawing;
namespace Million
{
public partial class MainForm : Form
{
// 계산 저정 할/ 계산 저장 된 데이터 Class
public SavedResultData _saveResultData;
// 현재 선택된 Indicator 폼
private CommonIndicatorSetupUserForm _curruentIndicatorform;
// 현재 수정/삭제 대기중인 클래스의 초기화
private IndicatorCoditionSetup _curIndicatorSetup = null;
private int _indexOfList = 0;
// 마지막 사용된 Index
private int _lastIndexString;
public MainForm()
{
InitializeComponent();
InitForm();
}
private void InitForm()
{
// 기간 선택
dateEdit_StartDateTime.DateTime = DateTime.Now;
dateEdit_EndDateTime.DateTime = DateTime.Now;
// 버튼 태그 값 설정
simpleButton_TobuyList.Tag = "Buy";
simpleButton_ToSellList.Tag = "Sell";
// 지표 ComboBox 초기화
comboBoxEdit_IndicatorSelection.Properties.Items.Clear();
object[] indicatorTypeList = Enum.GetNames(enumType: typeof(CommonProperty.IndicatorType));
comboBoxEdit_IndicatorSelection.Properties.Items.AddRange(indicatorTypeList);
// 저장 할 계산 데이터 클래스 생성
_saveResultData = new SavedResultData();
// 트리리스트 와 클래스 리스트 연결
treeList_BuySetupList.DataSource = _saveResultData.BuySetupList = new List<object>();
treeList_SellSetupList.DataSource = _saveResultData.SellSetupList = new List<object>();
// 지표 새로 추가 시 수정/삭제 버튼 Visible 처리
simpleButton_SetupEdit.Visible = false;
simpleButton_SetupDelete.Visible = false;
simpleButton_TobuyList.Visible = true;
simpleButton_ToSellList.Visible = true;
DbServiceFunctions.GetMarketTable_FromDB("Upbit", "KRW");
// Result Data DB에 생성
Million.DbManagement.DBConnection.QueryUpdateExcuter
(CommonProperty.DbConnectionResultData, DbServiceFunctions.CreateSavedAnalysisDataTableQuery());
Million.DbManagement.DBConnection.QueryUpdateExcuter
(CommonProperty.DbConnectionResultData, DbServiceFunctions.CreateSavedResultDataTableQuery());
Million.DbManagement.DBConnection.QueryUpdateExcuter
(CommonProperty.DbConnectionResultData, DbServiceFunctions.CreateRealTimeIndicatorTableQuery());
}
// 지표 콤보박스 클릭 시 이벤트
private void comboBoxEdit_IndicatorSelection_SelectedIndexChanged(object sender, EventArgs e)
{
var comboboxEdit = sender as ComboBoxEdit;
if (comboboxEdit == null) return;
if (comboboxEdit.SelectedIndex < 0) return;
Enum.TryParse(comboBoxEdit_IndicatorSelection.SelectedItem.ToString(),
out CommonProperty.IndicatorType indicatorType);
// 지표 조건 설정 폼 생성하기
CreateIndicatorForm(indicatorType);
// 지표 새로 추가 시 수정/삭제 버튼 Hidden 처리
simpleButton_SetupEdit.Visible = false;
simpleButton_SetupDelete.Visible = false;
simpleButton_TobuyList.Visible = true;
simpleButton_ToSellList.Visible = true;
// 현재 수정/삭제 대기중인 클래스의 초기화
_curIndicatorSetup = null;
}
// 지표 조건 설정 폼 생성하기
public void CreateIndicatorForm(CommonProperty.IndicatorType indicatorType, object setupData = null)
{
// 조건 설정 창 초기화
panelControl_IndicatorSetup.Controls.Clear();
// 공통 Indicator 폼 생성
_curruentIndicatorform = new CommonIndicatorSetupUserForm(indicatorType, setupData);
// 패널에 Indicator 폼 추가
if (_curruentIndicatorform != null) panelControl_IndicatorSetup.Controls.Add(_curruentIndicatorform);
}
// 구매/판매에 추가 버튼 클릭 시 이벤트 처리
private void simpleButton_BuySellButton_Click(object sender, EventArgs e)
{
var button = sender as SimpleButton;
// 예외처리
if (_curruentIndicatorform == null || comboBoxEdit_IndicatorSelection.SelectedItem == null) return;
// 선택된 콤보박스로 부터 Indicator type 가져오기
Enum.TryParse(comboBoxEdit_IndicatorSelection.SelectedItem.ToString(),
out CommonProperty.IndicatorType indicatorType);
// Buy Sell 구분
Enum.TryParse(button.Tag.ToString(), out CommonProperty.BuySellType buySelltype);
_curIndicatorSetup = (IndicatorCoditionSetup)_curruentIndicatorform.SaveIndicatorSetup(true);
_curIndicatorSetup.ByBuySellType = buySelltype;
_curIndicatorSetup.IndexString = _lastIndexString.ToString();
switch (buySelltype)
{
case CommonProperty.BuySellType.Buy:
_saveResultData.BuySetupList.Add(_curIndicatorSetup);
treeList_BuySetupList.RefreshDataSource();
break;
case CommonProperty.BuySellType.Sell:
_saveResultData.SellSetupList.Add(_curIndicatorSetup);
treeList_SellSetupList.RefreshDataSource();
break;
}
_lastIndexString++;
// 현재 수정/삭제 대기중인 클래스의 초기화
_curIndicatorSetup = null;
}
// 구매/판매 트리 리스트 더블 클릭 시 이벤트 처리
private void treeList_BuySetupList_MouseDoubleClick(object sender, MouseEventArgs e)
{
var treeList = sender as TreeList;
if (treeList == null) return;
var hitInfo = treeList.CalcHitInfo(e.Location);
if (hitInfo.HitInfoType != HitInfoType.Cell) return;
var indicatorType = (CommonProperty.IndicatorType)hitInfo.Node["IndicatorType"];
var indicatorSetupClassData = treeList.GetDataRecordByNode(hitInfo.Node);
// 현재 수정/삭제 대기중인 클래스 저장
_curIndicatorSetup = (IndicatorCoditionSetup)indicatorSetupClassData;
_indexOfList = treeList.Nodes.IndexOf(hitInfo.Node);
// 지표 조건 설정 폼 생성하기
CreateIndicatorForm(indicatorType, indicatorSetupClassData);
// 지표 새로 추가 시 수정/삭제 버튼 Visible 처리
simpleButton_SetupEdit.Visible = true;
simpleButton_SetupDelete.Visible = true;
simpleButton_TobuyList.Visible = false;
simpleButton_ToSellList.Visible = false;
// 조건 설정 창 초기화
comboBoxEdit_IndicatorSelection.Text = "";
}
// 조건 수정 버튼 클릭
private void simpleButton_SetupEdit_Click(object sender, EventArgs e)
{
if (_curIndicatorSetup == null) return;
#pragma warning disable CS0219 // 변수가 할당되었지만 해당 값이 사용되지 않았습니다.
object classData = null;
#pragma warning restore CS0219 // 변수가 할당되었지만 해당 값이 사용되지 않았습니다.
var type = _curIndicatorSetup.GetType();
_curruentIndicatorform.SaveIndicatorSetup();
// 해당 List안에 있는 Class를 수정
if (_saveResultData.BuySetupList.Contains(_curIndicatorSetup))
treeList_BuySetupList.RefreshDataSource();
else
treeList_SellSetupList.RefreshDataSource();
}
// 조건 삭제 버튼 클릭
private void simpleButton_SetupDelete_Click(object sender, EventArgs e)
{
if (_curIndicatorSetup == null) return;
// 해당 List안에 있는 Class를 삭제
if (_curIndicatorSetup.ByBuySellType == CommonProperty.BuySellType.Buy)
{
_saveResultData.BuySetupList.RemoveAt(_indexOfList);
treeList_BuySetupList.RefreshDataSource();
}
else
{
_saveResultData.SellSetupList.RemoveAt(_indexOfList);
treeList_SellSetupList.RefreshDataSource();
}
// 조건 설정 창 초기화
_curruentIndicatorform = null;
panelControl_IndicatorSetup.Controls.Clear();
comboBoxEdit_IndicatorSelection.Text = "";
// 지표 새로 추가 시 수정/삭제 버튼 Visible 처리
simpleButton_SetupEdit.Visible = false;
simpleButton_SetupDelete.Visible = false;
simpleButton_TobuyList.Visible = true;
simpleButton_ToSellList.Visible = true;
}
//지표 Refresh
private void simpleButton_SetupRefresh_Click(object sender, EventArgs e)
{
// 선택된 지표가 있는 경우, 해당 지표를 새로 생성함
if (comboBoxEdit_IndicatorSelection.SelectedIndex <= 0) return;
Enum.TryParse(comboBoxEdit_IndicatorSelection.SelectedItem.ToString(),
out CommonProperty.IndicatorType indicatorType);
// 지표 조건 설정 폼 생성하기
CreateIndicatorForm(indicatorType);
// 지표 새로 추가 시 수정/삭제 버튼 Hidden 처리
simpleButton_SetupEdit.Visible = false;
simpleButton_SetupDelete.Visible = false;
simpleButton_TobuyList.Visible = true;
simpleButton_ToSellList.Visible = true;
// 현재 수정/삭제 대기중인 클래스의 초기화
_curIndicatorSetup = null;
}
// 계산하기 버튼 클릭 시 이벤트 처리
// 조건 검색을 반영하여 데이터 계산
private void simpleButton_CalcurateData_Click(object sender, EventArgs e)
{
// 계산 결과 데이터 관련 클래스에 값 채우기
_saveResultData.StartDateTime = dateEdit_StartDateTime.DateTime;
_saveResultData.EndDateTime = dateEdit_EndDateTime.DateTime;
_saveResultData.SavedDateTime = DateTime.Now;
_saveResultData.SearchResultList = new List<SearchResult>();
_saveResultData.BuyRegularExpression = textEdit_BuyRegularExpression.Text;
_saveResultData.SellRegularExpression = textEdit_SellRegularExpression.Text;
// 예외 처리
var buyIndicatorList = IndicatorSetupManager.InitDataSetup(_saveResultData.BuySetupList);
var sellIndicatorList = IndicatorSetupManager.InitDataSetup(_saveResultData.SellSetupList);
var totalIndicator = new List<IndicatorCoditionSetup>();
totalIndicator.AddRange(buyIndicatorList);
totalIndicator.AddRange(sellIndicatorList);
var tableList = CommonProperty.selectedMarketOfPlaceList;
var totalResultList = new List<SearchResult>();
var startDate = _saveResultData.StartDateTime;
var endDate = _saveResultData.EndDateTime;
//TODO 이전 조건보다 현재 조건이 더 높아야 한다는 조건 걸기
var upperMainIndicatorFlag = cb_UpperMainIndi.Checked;
Parallel.For(0, tableList.Count, i =>
{
//임시로 하나만
// for (var i = 0; i < tableList.Count; i++)
//{
var selectTable = tableList[i];
//data setting
var distinctIndicator = IndicatorSetupManager.Distinct(totalIndicator);
// 총 데이터
var dic = DataManager.GetStandardData(totalIndicator, startDate, endDate, selectTable, distinctIndicator, true);
// buy, sell 계산
var lossIndicator = new List<IndicatorCoditionSetup>();
// 1분봉 데이터 Setting
var resultCandleDataList = dic[CommonProperty.MCandleTimeType.M1];
resultCandleDataList = resultCandleDataList.Where(t => startDate <= t.DateTime && t.DateTime < endDate).ToList();
// Sub Indicator string list 반환
var subIndStringiList = DataManager.GetSubIndicatorStringList(totalIndicator);
// Sub Indicator Class
var subIndicator = totalIndicator.Where(t => subIndStringiList.Any(u => u == t.IndexString)).ToList();
// 선처리
CalculateManager.GetCalculateIndicator(totalIndicator, subIndStringiList, lossIndicator, startDate,
endDate, resultCandleDataList, subIndicator, dic, upperMainIndicatorFlag);
var totalIndi = totalIndicator.Select(t => t.IndexString).ToList();
// 중복계산 방지
foreach (var item in subIndStringiList)
totalIndi.Remove(item);
// 후처리
CalculateManager.GetCalculateIndicator(totalIndicator, totalIndi, lossIndicator, startDate,
endDate, resultCandleDataList, subIndicator, dic, upperMainIndicatorFlag);
// 계산 로직
var resultLsit = ResultLogicManager.GetSearchResultList(resultCandleDataList, lossIndicator,
_saveResultData.BuyRegularExpression, _saveResultData.SellRegularExpression, selectTable, totalIndicator);
totalResultList.AddRange(resultLsit);
//}
});
//수익 률 계산 로직 -> 이거는 추후 빼도 될듯
double totalVal = 0;
double win = 0;
double lose = 0;
double firstProfitRate = 0;
double firstWin = 0;
//승률, 수익률 계산
foreach (var item in totalResultList)
{
if (item.FirstWinFlag) firstWin++;
firstProfitRate += item.FirstEarningRate;
win += item.WinCount;
lose += item.LoseCount;
totalVal += item.TotalEarningRate;
}
var winRate = 0.0;
if (win == 0)
{
winRate = 0;
}
else if (lose == 0)
{
winRate = 100;
}
else
{
winRate = (win * 100 / (win + lose));
}
double tt = 0;
double t1 = 0;
foreach (var item in totalResultList)
{
var buy = item.BuyList.CandleDataLists_Im[0];
var sell = item.SellData;
tt += ((sell.SellValue - buy.BuyValue) / buy.BuyValue) * 100;
if (buy.BuyValue < sell.SellValue) t1++;
}
_saveResultData.EndDateTime = DateTime.Now;
_saveResultData.SavedDateTime = DateTime.Now;
tt /= totalResultList.Count;
_saveResultData.ResultDataCount = totalResultList.Count;
_saveResultData.FirstWinRate = (firstWin * 100) / totalResultList.Count;
_saveResultData.FirstProfitRate = firstProfitRate;
_saveResultData.WinRate = winRate;
_saveResultData.ProfitRate = totalVal / totalResultList.Count;
_saveResultData.SearchResultList = totalResultList;
_saveResultData.Name = _saveResultData.SavedDateTime.ToString("yyyy-MM-dd HH:mm:ss") + " Hunter Result";
_saveResultData.Type = "Data";
_saveResultData.SaveResultType = "Hunter";
_saveResultData.ExchangePlace = "Upbit";
// 3. 자동으로 저장하기
if (DBConnection.QueryInsertExcuter_SavedResultData(_saveResultData))
MessageBox.Show("데이터 저장 성공");
else
MessageBox.Show("데이터 저장 실패");
// 데이터가 있는 경우 버튼 색 변경
if (_saveResultData.SearchResultList != null)
{
simpleButton_ViewResultData.Appearance.BackColor = Color.FromArgb(128, 128, 255);
}
}
// 결과 보기 버튼 클릭 시 이벤트 처리
private void simpleButton_ViewResultData_Click(object sender, EventArgs e)
{
// 예외 처리
if (_saveResultData.SearchResultList == null || _saveResultData.SearchResultList.Count <= 0)
{
MessageBox.Show("계산 처리된 데이터가 없습니다.");
return;
}
var resultViewerForm = new ResultViewerForm(_saveResultData) { StartPosition = FormStartPosition.CenterScreen };
resultViewerForm.ShowDialog();
}
// 저장된 결과 데이터 폼 불러오기
private void simpleButton_SavedResultViewer_Click(object sender, EventArgs e)
{
var savedResultViewerForm = new SavedResultViewerForm(this) { StartPosition = FormStartPosition.CenterScreen };
if (savedResultViewerForm.ShowDialog() != DialogResult.OK) return;
// 시간 데이터 추가
dateEdit_StartDateTime.DateTime = _saveResultData.StartDateTime.Date;
dateEdit_EndDateTime.DateTime = _saveResultData.EndDateTime.Date;
textEdit_BuyRegularExpression.Text = _saveResultData.BuyRegularExpression;
textEdit_SellRegularExpression.Text = _saveResultData.SellRegularExpression;
// Buy/Sell 리스트에 데이터 추가
treeList_BuySetupList.DataSource = _saveResultData.BuySetupList;
treeList_SellSetupList.DataSource = _saveResultData.SellSetupList;
treeList_BuySetupList.RefreshDataSource();
treeList_SellSetupList.RefreshDataSource();
}
/// <summary>
/// 테스트 용
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void simpleButton1_Click(object sender, EventArgs e)
{
#pragma warning disable CS0219 // 변수가 할당되었지만 해당 값이 사용되지 않았습니다.
var a = "a";
#pragma warning restore CS0219 // 변수가 할당되었지만 해당 값이 사용되지 않았습니다.
}
// 임시 저장 버튼
private void simpleButton_SaveTest_Click(object sender, EventArgs e)
{
// 계산 결과 데이터 관련 클래스에 값 채우기
_saveResultData.StartDateTime = dateEdit_StartDateTime.DateTime;
_saveResultData.EndDateTime = dateEdit_EndDateTime.DateTime;
_saveResultData.SavedDateTime = DateTime.Now;
if (_saveResultData == null)
_saveResultData.SearchResultList = new List<SearchResult>();
_saveResultData.BuyRegularExpression = textEdit_BuyRegularExpression.Text;
_saveResultData.SellRegularExpression = textEdit_SellRegularExpression.Text;
if (DBConnection.QueryInsertExcuter_SavedResultData(_saveResultData))
MessageBox.Show("데이터 저장 성공");
else
MessageBox.Show("데이터 저장 실패");
}
/// <summary>
/// Buyer 정규식에 추가
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
private void bt_InsertBuyerIndicator_Click(object sender, EventArgs e)
{
var name = tb_BuyerIndicatorName.Text;
if (DBConnection.QueryInsertExcuter_RealTimeIndicator(_saveResultData, name))
MessageBox.Show("데이터 저장 성공");
else
MessageBox.Show("데이터 저장 실패");
}
}
}