추세검색 수정

This commit is contained in:
Macbook
2026-05-27 00:28:09 +09:00
parent fe812389cc
commit c1bcf88c6c
10 changed files with 631 additions and 287 deletions
+62 -46
View File
@@ -17,6 +17,7 @@ import {
type TrendSearchRequest,
type TrendSearchResultDto,
} from '../utils/trendSearchApi';
import { sortTrendSearchByStrength } from '../utils/trendSearchMetrics';
import '../styles/trendSearchDashboard.css';
import '../styles/virtualTradingDashboard.css';
@@ -59,7 +60,7 @@ const TrendSearchPage: React.FC<Props> = ({
if (!opts?.silent) setSearching(true);
try {
const list = await scanTrendSearch(filtersRef.current);
setResults(list);
setResults(sortTrendSearchByStrength(list));
setLastUpdatedAt(Date.now());
setSelectedMarket(prev => {
if (prev && list.some(r => r.market === prev)) return prev;
@@ -94,57 +95,72 @@ const TrendSearchPage: React.FC<Props> = ({
try {
const detail = await fetchTrendSearchDetail(row.market, filters.timeframe);
if (detail) {
setResults(prev => prev.map(r => (r.market === detail.market ? detail : r)));
setResults(prev => sortTrendSearchByStrength(
prev.map(r => (r.market === detail.market ? detail : r)),
));
}
} catch { /* keep row */ }
}, [filters.timeframe]);
return (
<BuilderPageShell
theme={theme}
title="추세검색"
subtitle="Golden Analysis · Trend Search"
pageClassName="bps-page--tsd bps-page--vtd"
headerActions={(
<TrendSearchViewHeaderControls
displayMode={displayMode}
onDisplayModeChange={setDisplayMode}
autoRefresh={autoRefresh}
onAutoRefreshChange={setAutoRefresh}
searching={searching}
onRefresh={() => void runSearch()}
resultCount={results.length}
/>
<>
<BuilderPageShell
theme={theme}
title="추세검색"
subtitle="Golden Analysis · Trend Search"
pageClassName="bps-page--tsd bps-page--vtd"
headerActions={(
<TrendSearchViewHeaderControls
displayMode={displayMode}
onDisplayModeChange={setDisplayMode}
autoRefresh={autoRefresh}
onAutoRefreshChange={setAutoRefresh}
searching={searching}
onRefresh={() => void runSearch()}
resultCount={results.length}
/>
)}
leftStorageKey="tsd-left-width"
leftDefaultWidth={320}
leftCollapsedStorageKey="tsd-left-open"
collapsiblePanels
left={(
<TrendSearchFilterPanel
filters={filters}
onChange={setFilters}
onSearch={() => void runSearch()}
searching={searching}
/>
)}
center={(
<TrendSearchResultsCardGrid
results={results}
timeframe={filters.timeframe}
displayMode={displayMode}
selectedMarket={selectedMarket}
onSelect={row => void handleSelect(row)}
flashMarkets={flashMarkets}
theme={theme}
chartRealtimeSource={chartRealtimeSource}
chartSeriesPriceLabels={chartSeriesPriceLabels}
tickers={tickers}
lastUpdatedAt={lastUpdatedAt}
/>
)}
/>
{searching && (
<div className="tsd-search-overlay" role="status" aria-live="polite" aria-busy="true">
<div className="tsd-search-overlay-card">
<div className="loading-spinner tsd-search-spinner" />
<p className="tsd-search-overlay-text"> </p>
<div className="tsd-search-progress" aria-hidden="true">
<div className="tsd-search-progress-indeterminate" />
</div>
</div>
</div>
)}
leftStorageKey="tsd-left-width"
leftDefaultWidth={320}
leftCollapsedStorageKey="tsd-left-open"
collapsiblePanels
left={(
<TrendSearchFilterPanel
filters={filters}
onChange={setFilters}
onSearch={() => void runSearch()}
searching={searching}
/>
)}
center={(
<TrendSearchResultsCardGrid
results={results}
timeframe={filters.timeframe}
displayMode={displayMode}
loading={searching}
selectedMarket={selectedMarket}
onSelect={row => void handleSelect(row)}
flashMarkets={flashMarkets}
theme={theme}
chartRealtimeSource={chartRealtimeSource}
chartSeriesPriceLabels={chartSeriesPriceLabels}
tickers={tickers}
lastUpdatedAt={lastUpdatedAt}
/>
)}
/>
</>
);
};