Esmaeilkiani commited on
Commit
0d7fb21
·
verified ·
1 Parent(s): 357ab06

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +94 -163
app.py CHANGED
@@ -1,169 +1,100 @@
1
  import streamlit as st
2
  import pandas as pd
3
  import folium
4
- from streamlit_folium import folium_static
5
- import base64
6
- from folium.plugins import MarkerCluster
7
-
8
- # Set page title and layout
9
- st.set_page_config(page_title="Farm Monitoring Dashboard", layout="wide")
10
-
11
- # Add custom CSS for blinking effect
12
- st.markdown("""
13
- <style>
14
- @keyframes blink {
15
- 0% { opacity: 1; }
16
- 50% { opacity: 0.3; }
17
- 100% { opacity: 1; }
18
- }
19
- .blinking {
20
- animation: blink 1.5s infinite;
21
- }
22
- </style>
23
- """, unsafe_allow_html=True)
24
-
25
- # Function to load data
26
- @st.cache_data
27
- def load_data():
28
- #In a real app, you would load from actual CSV files
29
- representative_farms = pd.read_csv("مزارع نماینده راتون.csv")
30
- farm_coordinates = pd.read_csv("مختصات و مشخصات کامل مزارع (4).csv")
31
-
32
- # For this example, we'll create sample dataframes
33
- representative_farms = pd.DataFrame({
34
- "مزرعه نماینده": ["Farm A", "Farm A", "Farm B", "Farm B", "Farm C"],
35
- "زیر مجموعه": ["Subset A1", "Subset A2", "Subset B1", "Subset B2", "Subset C1"],
36
- "کانال": ["Channel 1", "Channel 1", "Channel 2", "Channel 2", "Channel 3"],
37
- "اداره": ["Dept 1", "Dept 1", "Dept 2", "Dept 2", "Dept 3"],
38
- "سن": [3, 3, 5, 5, 2],
39
- "واریته": ["Variety X", "Variety X", "Variety Y", "Variety Y", "Variety Z"],
40
- "تهیه قلمه": ["Method 1", "Method 1", "Method 2", "Method 2", "Method 3"],
41
- "مساحت کلی": [150, 120, 200, 180, 250]
42
- })
43
-
44
- farm_coordinates = pd.DataFrame({
45
- "مزرعه": ["Farm A", "Subset A1", "Subset A2", "Farm B", "Subset B1",
46
- "Subset B2", "Farm C", "Subset C1"],
47
- "طول جغرافیایی": [51.4, 51.41, 51.39, 51.5, 51.51, 51.49, 51.3, 51.31],
48
- "عرض جغرافیایی": [35.7, 35.71, 35.69, 35.8, 35.81, 35.79, 35.6, 35.61]
49
- })
50
-
51
- return representative_farms, farm_coordinates
52
-
53
- # Load data
54
- representative_farms, farm_coordinates = load_data()
55
-
56
- # Title
57
- st.title("Farm Monitoring Dashboard")
58
- st.markdown("---")
59
-
60
- # Sidebar for farm selection
61
- with st.sidebar:
62
- st.header("Farm Selection")
63
-
64
- # Get unique representative farms
65
- unique_farms = representative_farms["مزرعه نماینده"].unique()
66
-
67
- # Create dropdown for farm selection
68
- selected_farm = st.selectbox(
69
- "Select a representative farm:",
70
- options=unique_farms
71
- )
72
-
73
- # Get subsets for the selected farm
74
- if selected_farm:
75
- subsets = representative_farms[representative_farms["مزرعه نماینده"] == selected_farm]["زیر مجموعه"].tolist()
76
-
77
- st.subheader("Subsets:")
78
- for subset in subsets:
79
- st.markdown(f"- {subset}")
80
-
81
- # Display farm details
82
- st.subheader("Farm Details:")
83
- farm_details = representative_farms[representative_farms["مزرعه نماینده"] == selected_farm].iloc[0]
84
-
85
- st.markdown(f"**Age:** {farm_details['سن']} years")
86
- st.markdown(f"**Variety:** {farm_details['واریته']}")
87
- st.markdown(f"**Channel:** {farm_details['کانال']}")
88
- st.markdown(f"**Department:** {farm_details['اداره']}")
89
- st.markdown(f"**Cutting Method:** {farm_details['تهیه قلمه']}")
90
- st.markdown(f"**Total Area:** {farm_details['مساحت کلی']} hectares")
91
-
92
- # Main content - Map
93
- if selected_farm:
94
- # Get coordinates for the selected farm
95
- main_farm_coords = farm_coordinates[farm_coordinates["مزرعه"] == selected_farm]
96
-
97
- if not main_farm_coords.empty:
98
- main_lat = main_farm_coords.iloc[0]["عرض جغرافیایی"]
99
- main_lon = main_farm_coords.iloc[0]["طول جغرافیایی"]
100
-
101
- # Get coordinates for subsets
102
- subset_coords = farm_coordinates[farm_coordinates["مزرعه"].isin(subsets)]
103
-
104
- # Create map centered on the main farm
105
- m = folium.Map(location=[main_lat, main_lon], zoom_start=12,
106
- tiles="https://server.arcgisonline.com/ArcGIS/rest/services/World_Imagery/MapServer/tile/{z}/{y}/{x}",
107
- attr="Esri World Imagery")
108
-
109
- # Add layer control
110
- folium.TileLayer('OpenStreetMap').add_to(m)
111
- folium.TileLayer('Stamen Terrain').add_to(m)
112
- folium.LayerControl().add_to(m)
113
-
114
- # Add marker for the main farm
115
  folium.Marker(
116
- location=[main_lat, main_lon],
117
- popup=f"<b>{selected_farm}</b><br>Representative Farm",
118
- icon=folium.Icon(color="red", icon="star")
119
  ).add_to(m)
120
-
121
- # Add markers for subsets with blinking effect
122
- for _, row in subset_coords.iterrows():
123
- iframe = folium.IFrame(f"""
124
- <div>
125
- <h4>{row['مزرعه']}</h4>
126
- <p>Subset Farm</p>
127
- <p>Coordinates: {row['عرض جغرافیایی']:.6f}, {row['طول جغرافیایی']:.6f}</p>
128
- </div>
129
- """)
130
-
131
- popup = folium.Popup(iframe, min_width=200, max_width=300)
132
-
133
- # Create a custom icon with blinking class
134
- icon_html = """
135
- <div class="blinking">
136
- <i class="fa fa-map-marker fa-3x" style="color:green"></i>
137
- </div>
138
- """
139
-
140
- icon = folium.DivIcon(
141
- icon_size=(30, 30),
142
- icon_anchor=(15, 30),
143
- html=icon_html
144
- )
145
-
146
- folium.Marker(
147
- location=[row["عرض جغرافیایی"], row["طول جغرافیایی"]],
148
- popup=popup,
149
- icon=icon
150
- ).add_to(m)
151
-
152
- # Display the map
153
- st.subheader(f"Map for {selected_farm} and its Subsets")
154
- folium_static(m, width=1000, height=600)
155
-
 
 
 
 
 
 
 
 
 
 
 
 
 
 
156
  else:
157
- st.error("No coordinates found for the selected farm.")
158
- else:
159
- st.info("Please select a farm from the sidebar to view on the map.")
160
-
161
- # Add some information at the bottom
162
- st.markdown("---")
163
- st.markdown("### How to use this dashboard:")
164
- st.markdown("""
165
- 1. Select a representative farm from the dropdown in the sidebar
166
- 2. View the farm's subsets and details in the sidebar
167
- 3. Explore the farm and its subsets on the satellite map
168
- 4. The main farm is marked with a red star
169
- 5. Subset farms are marked with blinking green markers
 
1
  import streamlit as st
2
  import pandas as pd
3
  import folium
4
+ from streamlit_folium import st_folium
5
+ import ee
6
+ import geemap.foliumap as geemap
7
+
8
+ # احراز هویت GEE با فایل json
9
+ SERVICE_ACCOUNT = 'dehkhodamap-e9f0da4ce9f6514021@ee-esmaeilkiani13877.iam.gserviceaccount.com'
10
+ KEY_PATH = 'ee-esmaeilkiani13877-cfdea6eaf411.json'
11
+ ee.Initialize(ee.ServiceAccountCredentials(SERVICE_ACCOUNT, KEY_PATH))
12
+
13
+ st.set_page_config(page_title="داشبورد مزارع نماینده", layout="wide")
14
+ st.title("📡 داشبورد پایش مزارع نماینده نیشکر دهخدا")
15
+
16
+ # خواندن فایل‌��ا
17
+ df_links = pd.read_csv("مزارع نماینده راتون.csv", encoding='utf-8-sig')
18
+ df_coords = pd.read_csv("مختصات و مشخصات کامل مزارع (4).csv", encoding='utf-8-sig')
19
+
20
+ df_links.columns = df_links.columns.str.strip()
21
+ df_coords.columns = df_coords.columns.str.strip()
22
+ df_coords = df_coords.dropna(subset=["طول جغرافیایی", "عرض جغرافیایی"])
23
+
24
+ # انتخاب مزرعه نماینده
25
+ representatives = df_links["مزرعه نماینده"].dropna().unique()
26
+ selected_rep = st.selectbox("🔍 انتخاب مزرعه نماینده:", sorted(representatives), index=0)
27
+
28
+ if selected_rep:
29
+ subset_df = df_links[df_links["مزرعه نماینده"] == selected_rep]
30
+ sub_farms = subset_df["زیر مجموعه"].dropna().tolist()
31
+
32
+ rep_coords = df_coords[df_coords["مزرعه"] == selected_rep]
33
+ if not rep_coords.empty:
34
+ rep_lat = rep_coords["عرض جغرافیایی"].values[0]
35
+ rep_lon = rep_coords["طول جغرافیایی"].values[0]
36
+
37
+ m = folium.Map(
38
+ location=[rep_lat, rep_lon],
39
+ zoom_start=14,
40
+ tiles="https://mt1.google.com/vt/lyrs=s&x={x}&y={y}&z={z}",
41
+ attr="Google Satellite"
42
+ )
43
+
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
44
  folium.Marker(
45
+ location=[rep_lat, rep_lon],
46
+ tooltip=f"🌟 مزرعه نماینده: {selected_rep}",
47
+ icon=folium.Icon(color='blue', icon='star')
48
  ).add_to(m)
49
+
50
+ # نمایش زیرمزارعه‌ها روی نقشه
51
+ for i, row in subset_df.iterrows():
52
+ farm = row["زیر مجموعه"]
53
+ coords = df_coords[df_coords["مزرعه"] == farm]
54
+ if not coords.empty:
55
+ lat = coords["عرض جغرافیایی"].values[0]
56
+ lon = coords["طول جغرافیایی"].values[0]
57
+ folium.CircleMarker(
58
+ location=[lat, lon],
59
+ radius=8,
60
+ color="red",
61
+ fill=True,
62
+ fill_color="yellow",
63
+ fill_opacity=0.8,
64
+ tooltip=f"{farm} - سن: {row['سن']}، واریته: {row['واریته']}"
65
+ ).add_to(m)
66
+
67
+ st_folium(m, width=1000, height=600)
68
+
69
+ # نمایش جدول اطلاعات زیرمزارعه‌ها
70
+ st.subheader("📋 اطلاعات زیرمزارعه‌ها")
71
+ st.dataframe(subset_df[["زیر مجموعه", "سن", "واریته", "تهیه قلمه", "مساحت کلی"]])
72
+
73
+ # نمودار NDVI برای هر زیرمزرعه
74
+ st.subheader("📈 نمودار سری زمانی NDVI (S2)")
75
+ for farm in sub_farms:
76
+ coords = df_coords[df_coords["مزرعه"] == farm]
77
+ if not coords.empty:
78
+ lat = coords["عرض جغرافیایی"].values[0]
79
+ lon = coords["طول جغرافیایی"].values[0]
80
+ point = ee.Geometry.Point(float(lon), float(lat))
81
+ collection = ee.ImageCollection('COPERNICUS/S2_SR') \
82
+ .filterBounds(point) \
83
+ .filterDate('2024-01-01', '2024-12-31') \
84
+ .filter(ee.Filter.lt('CLOUDY_PIXEL_PERCENTAGE', 20)) \
85
+ .map(lambda img: img.addBands(img.normalizedDifference(['B8', 'B4']).rename('NDVI')))
86
+
87
+ ndvi_ts = collection.select('NDVI').getRegion(point, 30).getInfo()
88
+
89
+ if len(ndvi_ts) > 1:
90
+ df_ndvi = pd.DataFrame(ndvi_ts[1:], columns=ndvi_ts[0])
91
+ df_ndvi["datetime"] = pd.to_datetime(df_ndvi["time"], unit='ms')
92
+ df_ndvi = df_ndvi[["datetime", "NDVI"]].dropna()
93
+
94
+ st.line_chart(df_ndvi.set_index("datetime")["NDVI"], height=200, use_container_width=True)
95
+ st.markdown(f"📍 **{farm}**")
96
+ else:
97
+ st.warning(f"📍 داده‌ای برای NDVI مزرعه {farm} پیدا نشد.")
98
+
99
  else:
100
+ st.warning("مختصات مزرعه نماینده یافت نشد.")