QuantumLearner commited on
Commit
340e882
·
verified ·
1 Parent(s): c94f7a3

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +29 -32
app.py CHANGED
@@ -1,6 +1,6 @@
1
  import numpy as np
2
- import pandas as pd
3
  import yfinance as yf
 
4
  import plotly.graph_objects as go
5
  import streamlit as st
6
  from datetime import datetime, timedelta
@@ -9,6 +9,7 @@ from sklearn.cluster import KMeans
9
  import matplotlib.pyplot as plt
10
 
11
  # Streamlit app
 
12
  st.set_page_config(page_title="Identifying Key Support and Resistance In Price Levels", layout="wide")
13
  st.title('Key Support and Resistance In Price Levels')
14
 
@@ -38,14 +39,12 @@ with st.sidebar.expander("How to use:", expanded=False):
38
  4. **Run Analysis**: Click 'Run' to generate results.
39
  """)
40
 
41
- # Expander for ticker and date settings
42
  with st.sidebar.expander("Ticker and Date Settings", expanded=True):
43
  st.write("Specify the ticker and date range for analysis.")
44
  ticker = st.text_input('Stock Ticker or Crypto Pair', 'AAPL', help="Enter stock ticker (e.g., AAPL) or crypto pair (e.g., BTC-USD).")
45
  start_date = st.date_input('Start Date', pd.to_datetime('2023-01-01'))
46
  end_date = st.date_input('End Date', datetime.now() + timedelta(days=1))
47
 
48
- # Expander for methodology-specific parameters
49
  with st.sidebar.expander("Pivot Points and Levels", expanded=True):
50
  window_period = st.slider('Window Period for Pivot Points and Levels', min_value=10, max_value=60, value=30, help="Set the window period for calculating pivot points and support/resistance levels.")
51
 
@@ -58,12 +57,11 @@ with st.sidebar.expander("Volume Profile and KMeans", expanded=True):
58
 
59
  # Define functions for different analyses
60
  def calculate_pivot_points(df, window):
61
- # Ensure calculations are Series-based to avoid multi-column issues
62
  df['Pivot'] = df['Close'].rolling(window=window).mean()
63
- df['R1'] = (2 * df['Pivot']) - df['Low'].rolling(window=window).min().reindex(df.index, method='ffill')
64
- df['S1'] = (2 * df['Pivot']) - df['High'].rolling(window=window).max().reindex(df.index, method='ffill')
65
- df['R2'] = df['Pivot'] + (df['High'].rolling(window=window).max().reindex(df.index, method='ffill') - df['Low'].rolling(window=window).min().reindex(df.index, method='ffill'))
66
- df['S2'] = df['Pivot'] - (df['High'].rolling(window=window).max().reindex(df.index, method='ffill') - df['Low'].rolling(window=window).min().reindex(df.index, method='ffill'))
67
  return df
68
 
69
  def find_levels(data, window):
@@ -76,9 +74,20 @@ def check_significant_break(data, support, resistance):
76
  breaks_below_support = (data['Close'] < support.shift(1)) & (data['Volume'] > data['Volume'].rolling(window=30).mean())
77
  return breaks_above_resistance, breaks_below_support
78
 
 
79
  def prepare_data_for_trendlines(data, lookback_period):
80
- data['Swing_High'] = data['High'][argrelextrema(data['High'].values, np.greater_equal, order=lookback_period)[0]]
81
- data['Swing_Low'] = data['Low'][argrelextrema(data['Low'].values, np.less_equal, order=lookback_period)[0]]
 
 
 
 
 
 
 
 
 
 
82
  return data
83
 
84
  def calculate_fibonacci_levels(data, lookback_period):
@@ -107,8 +116,7 @@ def calculate_kmeans_clusters(data, n_days, num_clusters):
107
 
108
  # Run the analysis
109
  if st.sidebar.button('Run Analysis'):
110
- # Explicitly set auto_adjust=False to avoid yfinance default changes
111
- data = yf.download(ticker, start=start_date, end=end_date, auto_adjust=False)
112
 
113
  if not data.empty:
114
  # Calculate Pivot Points
@@ -134,11 +142,11 @@ if st.sidebar.button('Run Analysis'):
134
  # Plot Pivot Points
135
  st.write("### Pivot Points")
136
  st.markdown("""
137
- **Pivot Points** are short-term trend indicators used to determine potential support and resistance levels. The central pivot point, as well as derived support and resistance levels, are calculated using the high, low, and close prices of a previous period (usually the previous day for day trading).
138
  - **Pivot Point (P)**: The average of the high, low, and close of the previous trading period.
139
  - **First Resistance (R1)**: Calculated by doubling the pivot point and then subtracting the previous low.
140
  - **First Support (S1)**: Derived by doubling the pivot point and then subtracting the previous high.
141
- - **Second Resistance (R2)**: Obtained by adding the difference of high and low (the range) to the pivot point.
142
  - **Second Support (S2)**: Found by subtracting the range from the pivot point.
143
  """)
144
 
@@ -162,10 +170,7 @@ if st.sidebar.button('Run Analysis'):
162
  # Plot Support and Resistance Levels using Rolling Midpoint Range
163
  st.write("### Rolling Midpoint Range")
164
  st.markdown("""
165
- **Support and Resistance Levels** This method uses a rolling window to identify these levels. This provides a dynamic approach to pinpointing key price levels.
166
- - **Support Level**: Calculated as the rolling minimum price over the specified window period. It acts as a floor where buying interest is strong enough to prevent further price declines.
167
- - **Resistance Level**: Calculated as the rolling maximum price over the specified window period. It acts as a ceiling where selling interest prevents the price from rising further.
168
- In this analysis, the support and resistance levels are determined using a rolling window approach. Significant breaks above resistance and below support are highlighted, especially when accompanied by higher-than-average trading volumes, which could indicate potential breakout or breakdown scenarios.
169
  """)
170
 
171
  fig2 = go.Figure()
@@ -209,8 +214,7 @@ if st.sidebar.button('Run Analysis'):
209
  # Plot Fibonacci Retracement Levels
210
  st.write("### Fibonacci Retracement Levels")
211
  st.markdown("""
212
- **Fibonacci Retracement Levels** are horizontal lines that indicate where support and resistance are likely to occur. They are based on Fibonacci numbers and are used to predict the future movement of asset prices.
213
- - **Levels**: 23.6%, 38.2%, 50%, 61.8%, and 78.6% represent key points where the price could potentially reverse.
214
  """)
215
 
216
  fig4 = go.Figure()
@@ -231,12 +235,7 @@ if st.sidebar.button('Run Analysis'):
231
  # Plot Trendlines
232
  st.write("### Trendlines with Regression Analysis")
233
  st.markdown("""
234
- **Trendlines** are straight lines drawn on a price chart to connect two or more price points. They help identify the direction of the market trend and potential areas of support and resistance. In this analysis, trendlines are determined using regression analysis to fit the lines through swing highs and lows.
235
- - **Upper Trendline**: Connects higher highs using linear regression to fit a line through these points. This line acts as a resistance level.
236
- - **Lower Trendline**: Connects lower lows using linear regression to fit a line through these points. This line acts as a support level.
237
- 1. **Swing Highs and Lows Identification**: First, local maxima (swing highs) and minima (swing lows) are identified using a specified lookback period.
238
- 2. **Linear Regression**: A linear regression is then applied to the swing highs to form the upper trendline and to the swing lows to form the lower trendline.
239
- 3. **Visualization**: The trendlines are plotted along with the stock's closing prices to represent of potential resistance and support levels.
240
  """)
241
 
242
  fig5 = go.Figure()
@@ -266,8 +265,7 @@ if st.sidebar.button('Run Analysis'):
266
  # Plot Volume Profile
267
  st.write("### Volume Profile")
268
  st.markdown("""
269
- **Volume Profile** is a charting tool that shows the amount of volume traded at different price levels over a specified period. It helps identify areas of high trading activity, which can act as support or resistance.
270
- - **High Volume Areas**: Indicate significant trading activity and can act as strong support or resistance levels.
271
  """)
272
 
273
  fig6, (ax1, ax2) = plt.subplots(nrows=1, ncols=2, figsize=(20, 5), gridspec_kw={'width_ratios': [3, 1]})
@@ -293,13 +291,12 @@ if st.sidebar.button('Run Analysis'):
293
  ax1.set_title(f'{ticker} Price Data')
294
  ax2.barh(price_bins[:-1], volume_profile, height=(price_bins[1] - price_bins[0]), color='blue', edgecolor='none')
295
  ax2.set_title('Volume Profile')
296
- st.pyplot(fig6, use_container_width=True)
297
 
298
  # Plot KMeans Clusters
299
  st.write("### KMeans Clusters")
300
  st.markdown("""
301
- **KMeans Clustering** is a machine learning algorithm used to partition a dataset into clusters. In the context of stock prices, it helps identify patterns and group similar price movements together.
302
- - **Clusters**: Represent different regimes or phases in the stock price movements.
303
  """)
304
 
305
  fig7 = go.Figure()
@@ -328,4 +325,4 @@ hide_streamlit_style = """
328
  footer {visibility: hidden;}
329
  </style>
330
  """
331
- st.markdown(hide_streamlit_style, unsafe_allow_html=True)
 
1
  import numpy as np
 
2
  import yfinance as yf
3
+ import pandas as pd
4
  import plotly.graph_objects as go
5
  import streamlit as st
6
  from datetime import datetime, timedelta
 
9
  import matplotlib.pyplot as plt
10
 
11
  # Streamlit app
12
+
13
  st.set_page_config(page_title="Identifying Key Support and Resistance In Price Levels", layout="wide")
14
  st.title('Key Support and Resistance In Price Levels')
15
 
 
39
  4. **Run Analysis**: Click 'Run' to generate results.
40
  """)
41
 
 
42
  with st.sidebar.expander("Ticker and Date Settings", expanded=True):
43
  st.write("Specify the ticker and date range for analysis.")
44
  ticker = st.text_input('Stock Ticker or Crypto Pair', 'AAPL', help="Enter stock ticker (e.g., AAPL) or crypto pair (e.g., BTC-USD).")
45
  start_date = st.date_input('Start Date', pd.to_datetime('2023-01-01'))
46
  end_date = st.date_input('End Date', datetime.now() + timedelta(days=1))
47
 
 
48
  with st.sidebar.expander("Pivot Points and Levels", expanded=True):
49
  window_period = st.slider('Window Period for Pivot Points and Levels', min_value=10, max_value=60, value=30, help="Set the window period for calculating pivot points and support/resistance levels.")
50
 
 
57
 
58
  # Define functions for different analyses
59
  def calculate_pivot_points(df, window):
 
60
  df['Pivot'] = df['Close'].rolling(window=window).mean()
61
+ df['R1'] = 2 * df['Pivot'] - df['Low'].rolling(window=window).min()
62
+ df['S1'] = 2 * df['Pivot'] - df['High'].rolling(window=window).max()
63
+ df['R2'] = df['Pivot'] + (df['High'].rolling(window=window).max() - df['Low'].rolling(window=window).min())
64
+ df['S2'] = df['Pivot'] - (df['High'].rolling(window=window).max() - df['Low'].rolling(window=window).min())
65
  return df
66
 
67
  def find_levels(data, window):
 
74
  breaks_below_support = (data['Close'] < support.shift(1)) & (data['Volume'] > data['Volume'].rolling(window=30).mean())
75
  return breaks_above_resistance, breaks_below_support
76
 
77
+ # Updated function to use positional indexing via .iloc and .values
78
  def prepare_data_for_trendlines(data, lookback_period):
79
+ swing_highs = pd.Series(index=data.index, dtype=float)
80
+ swing_lows = pd.Series(index=data.index, dtype=float)
81
+
82
+ high_positions = argrelextrema(data['High'].values, np.greater_equal, order=lookback_period)[0]
83
+ low_positions = argrelextrema(data['Low'].values, np.less_equal, order=lookback_period)[0]
84
+
85
+ # Use .iloc with .values to ensure scalar assignments
86
+ swing_highs.iloc[high_positions] = data['High'].iloc[high_positions].values
87
+ swing_lows.iloc[low_positions] = data['Low'].iloc[low_positions].values
88
+
89
+ data['Swing_High'] = swing_highs
90
+ data['Swing_Low'] = swing_lows
91
  return data
92
 
93
  def calculate_fibonacci_levels(data, lookback_period):
 
116
 
117
  # Run the analysis
118
  if st.sidebar.button('Run Analysis'):
119
+ data = yf.download(ticker, start=start_date, end=end_date)
 
120
 
121
  if not data.empty:
122
  # Calculate Pivot Points
 
142
  # Plot Pivot Points
143
  st.write("### Pivot Points")
144
  st.markdown("""
145
+ **Pivot Points** are short-term trend indicators used to determine potential support and resistance levels based on the high, low, and close prices of previous periods.
146
  - **Pivot Point (P)**: The average of the high, low, and close of the previous trading period.
147
  - **First Resistance (R1)**: Calculated by doubling the pivot point and then subtracting the previous low.
148
  - **First Support (S1)**: Derived by doubling the pivot point and then subtracting the previous high.
149
+ - **Second Resistance (R2)**: Obtained by adding the range (High - Low) to the pivot point.
150
  - **Second Support (S2)**: Found by subtracting the range from the pivot point.
151
  """)
152
 
 
170
  # Plot Support and Resistance Levels using Rolling Midpoint Range
171
  st.write("### Rolling Midpoint Range")
172
  st.markdown("""
173
+ **Support and Resistance Levels** are determined using a rolling window approach to calculate the dynamic minimum (support) and maximum (resistance) prices over a given period.
 
 
 
174
  """)
175
 
176
  fig2 = go.Figure()
 
214
  # Plot Fibonacci Retracement Levels
215
  st.write("### Fibonacci Retracement Levels")
216
  st.markdown("""
217
+ **Fibonacci Retracement Levels** are horizontal lines indicating potential support and resistance based on Fibonacci ratios.
 
218
  """)
219
 
220
  fig4 = go.Figure()
 
235
  # Plot Trendlines
236
  st.write("### Trendlines with Regression Analysis")
237
  st.markdown("""
238
+ **Trendlines** are drawn using regression on swing highs and lows to indicate potential support and resistance.
 
 
 
 
 
239
  """)
240
 
241
  fig5 = go.Figure()
 
265
  # Plot Volume Profile
266
  st.write("### Volume Profile")
267
  st.markdown("""
268
+ **Volume Profile** is a charting tool that shows the amount of volume traded at different price levels over a specified period.
 
269
  """)
270
 
271
  fig6, (ax1, ax2) = plt.subplots(nrows=1, ncols=2, figsize=(20, 5), gridspec_kw={'width_ratios': [3, 1]})
 
291
  ax1.set_title(f'{ticker} Price Data')
292
  ax2.barh(price_bins[:-1], volume_profile, height=(price_bins[1] - price_bins[0]), color='blue', edgecolor='none')
293
  ax2.set_title('Volume Profile')
294
+ st.pyplot(fig6, use_container_width=True)
295
 
296
  # Plot KMeans Clusters
297
  st.write("### KMeans Clusters")
298
  st.markdown("""
299
+ **KMeans Clustering** partitions the price data into clusters to identify significant price levels.
 
300
  """)
301
 
302
  fig7 = go.Figure()
 
325
  footer {visibility: hidden;}
326
  </style>
327
  """
328
+ st.markdown(hide_streamlit_style, unsafe_allow_html=True)