This commit is contained in:
2026-02-05 14:26:02 +09:00
parent e0e328ea97
commit 3f209dcd4d
9 changed files with 194 additions and 107 deletions
-1
View File
@@ -159,7 +159,6 @@ fun DashboardScreen() {
// 3. 실시간 체결 통보 핸들러 (주문번호 중심)
wsManager.onExecutionReceived = {code, qty, price,orderNo, isBuy ->
scope.launch {
println("$orderNo, $code, $price, $qty, $isBuy")
val exec = ExecutionData(orderNo, code, price, qty, isBuy)
executionCache[orderNo] = exec
syncAndExecute(orderNo)
+26 -18
View File
@@ -82,12 +82,12 @@ fun IntegratedOrderSection(
// 계산용 변수
val curPriceNum = currentPrice.replace(",", "").toDoubleOrNull() ?: 0.0
val basePrice = (if (orderPrice.isEmpty()) curPriceNum else orderPrice.toDoubleOrNull() ?: 0.0)
val inputQty = orderQty.replace(",", "").toIntOrNull() ?: 0
fun excuteTrade(willEnableAutoSell: Boolean, orderQty: String, profitRate1: Double?) {
fun excuteTrade(willEnableAutoSell: Boolean, orderQty: String, profitRate1: Double?,confidence : Boolean = false) {
scope.launch {
val tickSize = MarketUtil.getTickSize(basePrice)
val oneTickLowerPrice = basePrice - tickSize
val oneTickLowerPrice = basePrice - (tickSize * if (confidence) { 1} else {2})
// 2. 주문 가격 설정 (직접 입력값이 없으면 한 틱 낮은 가격 사용)
val finalPrice = if (orderPrice.isBlank()) {
@@ -114,7 +114,7 @@ fun IntegratedOrderSection(
// 4. 보정된 수익률을 적용하여 목표가 계산
val calculatedTarget = MarketUtil.roundToTickSize(basePrice * (1 + effectiveProfitRate / 100.0))
val calculatedStop = MarketUtil.roundToTickSize(basePrice * (1 + sRate / 100.0))
val inputQty = orderQty.replace(",", "").toIntOrNull() ?: 0
// 5. DB 저장 (effectiveProfitRate를 저장하여 분석 시 실제 목표치를 확인 가능하게 함)
DatabaseFactory.saveAutoTrade(AutoTradeItem(
orderNo = realOrderNo,
@@ -146,13 +146,7 @@ fun IntegratedOrderSection(
completeTradingDecision.stockCode.equals(stockCode)) {
fun resultCheck(completeTradingDecision :TradingDecision) {
println("""
corpName : ${completeTradingDecision.corpName}
confidence : ${completeTradingDecision.confidence + append}
shortPossible : ${completeTradingDecision.shortPossible() + append}
profitPossible : ${completeTradingDecision.profitPossible()+ append}
safePossible : ${completeTradingDecision.safePossible()+ append}
""".trimIndent())
val weights = mapOf(
"short" to 0.3, // 초단기 점수가 낮아도 전체에 미치는 영향 감소
@@ -169,8 +163,15 @@ fun IntegratedOrderSection(
// 3. 매수 결정 문턱값 (예: 70점 이상이면 매수 가능)
val MIN_PURCHASE_SCORE = 68.0
val HIGH_QUALITY_SCORE = 85.0 // 강력 추천 기준
if (totalScore >= MIN_PURCHASE_SCORE && completeTradingDecision.confidence > MIN_CONFIDENCE) {
println("""
corpName : ${completeTradingDecision.corpName}
confidence : ${completeTradingDecision.confidence + append}
shortPossible : ${completeTradingDecision.shortPossible() + append}
profitPossible : ${completeTradingDecision.profitPossible()+ append}
safePossible : ${completeTradingDecision.safePossible()+ append}
totalScore : ${totalScore}
""".trimIndent())
if (totalScore >= MIN_PURCHASE_SCORE && completeTradingDecision.confidence >= MIN_CONFIDENCE) {
// 4. 점수에 따른 가변 마진 적용
// 토탈 스코어가 85점 이상이면 마진을 3.0으로 고정하거나 추가 가산(append) 적용
@@ -182,16 +183,23 @@ fun IntegratedOrderSection(
}
println("🚀 [매수 진행] 토탈 스코어: ${String.format("%.1f", totalScore)} -> 종목: ${completeTradingDecision.stockCode}")
val MAX_BUDGET = 25000.0
// basePrice(현재가 혹은 지정가)를 기준으로 매수 가능 수량 산출 (최소 1주 보장)
val calculatedQty = if (basePrice > 0) {
(MAX_BUDGET / basePrice).toInt().coerceAtLeast(1)
} else {
1
}
// 5. 매수 실행 (계산된 finalMargin 전달)
excuteTrade(
willEnableAutoSell = true,
orderQty = "1",
profitRate1 = finalMargin
orderQty = calculatedQty.toString(),
profitRate1 = finalMargin,
confidence = totalScore >= HIGH_QUALITY_SCORE
)
} else {
println("✋ [관망] 토탈 스코어(${String.format("%.1f", totalScore)})가 기준치($MIN_PURCHASE_SCORE) 미달")
println("✋ [관망] 토탈 스코어(${String.format("%.1f", totalScore)})가 기준치($MIN_PURCHASE_SCORE) 미달 또는 신뢰도 ${completeTradingDecision.confidence}가 기준치 ${MIN_CONFIDENCE} 미달")
}
}
when (completeTradingDecision?.decision) {
@@ -228,7 +236,7 @@ fun IntegratedOrderSection(
modifier = Modifier.weight(1f)
)
}
val inputQty = orderQty.replace(",", "").toIntOrNull() ?: 0
// 수익률 시뮬레이션 표
if (basePrice > 0 && inputQty > 0) {
SimulationCard(basePrice, inputQty.toDouble())