오늘 스트림릿을 정식적으로 쓰면서 나의 코드를 강화해나갈 생각이다.
그런데 배경화면을 설정하고 싶다는 생각이 들어서 코드를 검색해보니 이렇게 나왔다.
import streamlit as st
# HTML과 CSS로 배경 이미지 설정
st.markdown(
"""
<style>
.stApp {
background-image: url('https://example.com/your-image.jpg');
background-size: cover;
background-position: center;
background-repeat: no-repeat;
}
</style>
""",
unsafe_allow_html=True
)
st.write("전체 애플리케이션의 배경이 설정되었습니다.")
대충 스타일이 이렇다고 하니, 하나하나 알아봅시다.
먼저, st.markdown()을 사용하면 HTML과 CSS를 포함하여 다양한 스타일을 적용할 수 있습니다. 하지만 주의해야 할 점은 Streamlit이 기본적으로 HTML을 허용하고 있지만, CSS와 JavaScript를 삽입할 때는 unsafe_allow_html=True를 설정해줘야 한다는 점입니다.
마크다운 자체는 기본적으로 스타일링을 지원하지 않지만, HTML을 삽입하는 방식으로 배경 이미지나 다른 스타일을 적용할 수 있습니다.
그것이 바로 <style>입니다
<style> 태그는 HTML 내에서 CSS 스타일을 삽입하는 데 사용되는 태그입니다. CSS는 웹 페이지의 디자인과 레이아웃을 정의하는 언어이며, <style> 태그 안에 작성된 CSS 코드는 페이지의 요소에 적용됩니다.
Streamlit에서는 st.markdown()을 사용하여 HTML 코드와 CSS 스타일을 삽입할 수 있습니다. 이때, <style> 태그를 사용하여 배경 이미지, 글꼴, 색상 등 다양한 스타일을 지정할 수 있습니다.
Streamlit에서는 st.markdown()을 사용하여 마크다운과 HTML을 혼합하여 사용할 수 있습니다. 마크다운은 주로 텍스트를 구조화하고 간단하게 꾸미는 데 사용되며, HTML은 더 복잡한 스타일링과 레이아웃 변경을 지원합니다. 따라서 st.markdown()으로 HTML을 삽입할 수 있습니다.
두번째로 .stApp입니다
stApp은 Streamlit 애플리케이션의 최상위 DOM 요소에 해당하는 클래스입니다. 즉, Streamlit의 전체 애플리케이션을 감싸고 있는 HTML 요소의 클래스를 의미합니다. 이 클래스를 사용하여 애플리케이션의 배경, 크기, 레이아웃 등을 CSS로 스타일링할 수 있습니다.
stApp 클래스를 사용하는 이유
전체 애플리케이션 스타일링: stApp을 사용하면 페이지 전체의 스타일을 한 번에 설정할 수 있습니다. 예를 들어, 배경 이미지나 색상, 폰트 스타일 등을 설정할 때 유용합니다.
페이지의 기본 레이아웃을 변경: 예를 들어, stApp에 height, width, margin 등을 설정해서 애플리케이션의 기본 레이아웃을 변경할 수 있습니다.
하지만 stApp은 반드시 필요한 것은 아닙니다. stApp은 Streamlit 애플리케이션의 전체 레이아웃을 대상으로 스타일을 적용할 때 사용하는 클래스이므로, stApp 없이도 <style>을 사용하여 특정 요소에 스타일을 적용할 수 있습니다.
주요 Streamlit CSS 클래스 및 요소들
1. stApp
전체 애플리케이션의 스타일을 정의할 때 사용됩니다.
페이지 전체의 배경색, 이미지, 여백 등을 설정할 수 있습니다.
2. .stText
기본적으로 텍스트와 관련된 스타일을 정의할 때 사용됩니다.
st.write(), st.markdown(), st.text() 등으로 표시되는 텍스트에 적용됩니다.
3. .stSidebar
Streamlit 사이드바의 스타일을 제어하는 클래스입니다.
사이드바의 배경색, 여백, 텍스트 등을 변경할 때 사용됩니다.
4. .stButton
버튼을 스타일링할 때 사용됩니다.
st.button() 함수로 생성된 버튼에 적용됩니다.
5. .stMarkdown
마크다운 텍스트에 적용되는 클래스입니다.
st.markdown() 함수로 표시되는 마크다운 내용에 스타일을 지정할 때 사용됩니다.
6. .stSelectbox, .stMultiselect
st.selectbox()와 st.multiselect()에서 생성된 드롭다운 메뉴나 다중 선택 박스를 스타일링할 때 사용됩니다.
7. .stSlider
슬라이더 위젯에 관련된 스타일을 정의할 때 사용됩니다.
st.slider()로 생성된 슬라이더에 적용됩니다.
8. .stTable
테이블을 스타일링하는 클래스입니다.
st.write()나 st.dataframe()에서 데이터 테이블을 렌더링할 때 사용됩니다.
9. .stProgress
진행 상태 표시줄에 스타일을 적용할 때 사용됩니다.
st.progress()로 생성된 진행 표시줄에 스타일을 적용할 수 있습니다.
10. .stTextInput, .stTextArea
텍스트 입력 필드나 텍스트 영역을 스타일링할 때 사용됩니다.
st.text_input()이나 st.text_area()로 생성된 입력 필드에 적용됩니다.
Streamlit 내부적으로 사용되는 주요 CSS 클래스
11. .stAlert: 알림창과 관련된 스타일입니다. (예: st.warning(), st.success() 등)
12. .stFileUploader: 파일 업로더와 관련된 스타일입니다. (예: st.file_uploader() 위젯)
13. .stRadio: 라디오 버튼 스타일입니다. (예: st.radio() 위젯)
14. .stCheckbox: 체크박스 스타일입니다. (예: st.checkbox() 위젯)
15. .stTextArea: 텍스트 영역의 스타일입니다. (예: st.text_area() 위젯)
16. .stMetric: 메트릭 카드 스타일입니다. (예: st.metric() 위젯)
17. .stExpander: 확장 가능한 요소 스타일입니다. (예: st.expander() 위젯)
전체적으로 예제를 봅시다.
1. .stApp: 전체 애플리케이션 스타일링
설명: stApp은 전체 애플리케이션 영역에 대한 스타일을 제어합니다.
적용 가능한 스타일:
배경색, 배경 이미지, 여백, 패딩, 글꼴 스타일 등
import streamlit as st # stApp 클래스에 스타일 적용 st.markdown( """ <style> .stApp { background-image: url('https://example.com/your-image.jpg'); /* 배경 이미지 URL */ background-size: cover; /* 이미지 크기를 화면에 맞춤 */ background-position: center; /* 배경 이미지 위치 */ background-repeat: no-repeat; /* 이미지 반복 방지 */ background-attachment: fixed; /* 스크롤 시 이미지 고정 */ color: white; /* 기본 텍스트 색상 */ font-family: Arial, sans-serif; /* 기본 글꼴 */ padding: 20px; /* 전체 여백 */ } </style> """, unsafe_allow_html=True ) # 애플리케이션 내용 st.write("배경 이미지가 적용된 Streamlit 애플리케이션입니다!")
2. .stText: 텍스트 스타일링
설명: 텍스트 구성 요소(st.write, st.text, st.markdown)의 스타일을 제어합니다.
적용 가능한 스타일:
텍스트 색상, 크기, 글꼴, 간격 등
import streamlit as st # stText 클래스에 스타일 적용 st.markdown( """ <style> .stText { color: #FF4500; /* 텍스트 색상 */ font-size: 24px; /* 글꼴 크기 */ font-weight: bold; /* 글씨 굵기 */ text-align: center; /* 텍스트 정렬 */ text-shadow: 2px 2px 4px rgba(0,0,0,0.3); /* 텍스트 그림자 */ } </style> """, unsafe_allow_html=True ) # 텍스트 출력 st.write("🎉 Streamlit 텍스트 스타일링 예제 🎉")
3. .stSidebar: 사이드바 스타일링
설명: 사이드바 영역의 스타일을 제어합니다.
적용 가능한 스타일:
배경색, 여백, 글꼴 색상, 글꼴 크기 등
예제:
import streamlit as st # stSidebar 클래스에 스타일 적용 st.markdown( """ <style> .stSidebar { background-color: #F0F0F0; /* 사이드바 배경색 */ padding: 20px; /* 내부 여백 */ font-size: 18px; /* 글꼴 크기 */ color: #333; /* 기본 텍스트 색상 */ } </style> """, unsafe_allow_html=True ) # 사이드바 내용 st.sidebar.write("이 스타일은 사이드바에 적용됩니다.") st.sidebar.button("Click Me!")
4. .stButton: 버튼 스타일링
설명: 버튼 요소(st.button)의 스타일을 제어합니다.
적용 가능한 스타일:
배경색, 텍스트 색상, 크기, 여백 등
예제:import streamlit as st # stButton 클래스에 스타일 적용 st.markdown( """ <style> .stButton>button { background-color: #4CAF50; /* 버튼 배경색 */ color: white; /* 버튼 텍스트 색상 */ border: none; /* 테두리 제거 */ padding: 15px 32px; /* 버튼 내부 여백 */ text-align: center; /* 텍스트 정렬 */ font-size: 16px; /* 글꼴 크기 */ cursor: pointer; /* 커서 스타일 */ border-radius: 5px; /* 둥근 모서리 */ } </style> """, unsafe_allow_html=True ) # 버튼 생성 st.button("클릭하세요!")
5. .stMarkdown: 마크다운 텍스트 스타일링
설명: st.markdown으로 렌더링된 텍스트의 스타일을 제어합니다.
적용 가능한 스타일:
텍스트 색상, 글꼴, 간격, 테두리 등
예제:
import streamlit as st # stMarkdown 클래스에 스타일 적용 st.markdown( """ <style> .stMarkdown h1 { color: #FF6347; /* 헤더 색상 */ font-family: Georgia, serif; /* 글꼴 */ border-bottom: 2px solid #333; /* 아래쪽 테두리 */ } .stMarkdown p { color: #666; /* 일반 텍스트 색상 */ font-size: 18px; /* 일반 텍스트 크기 */ } </style> """, unsafe_allow_html=True ) # 마크다운 내용 st.markdown("# 마크다운 헤더\n이것은 일반 텍스트입니다.")
6. .stSelectbox: 셀렉트박스 스타일링
설명: 드롭다운 셀렉트박스(st.selectbox)의 스타일을 제어합니다.
적용 가능한 스타일:
드롭다운 메뉴 색상, 글꼴 크기, 테두리 등
예제:import streamlit as st # stSelectbox 클래스에 스타일 적용 st.markdown( """ <style> .stSelectbox>div>div>div { background-color: #FFF; /* 드롭다운 배경색 */ color: #333; /* 텍스트 색상 */ border: 2px solid #4CAF50; /* 테두리 */ padding: 10px; /* 내부 여백 */ border-radius: 5px; /* 둥근 모서리 */ } </style> """, unsafe_allow_html=True ) # 셀렉트박스 생성 option = st.selectbox("옵션을 선택하세요:", ["옵션 1", "옵션 2", "옵션 3"]) st.write(f"선택된 옵션: {option}")
6.1 .stMultiselect: 멀티 셀렉트 스타일
설명: 멀티 셀렉트 위젯(st.multiselect())의 스타일을 제어합니다. 여러 개의 옵션을 선택할 수 있는 드롭다운 형태의 위젯입니다.
적용 가능한 스타일:
배경색, 선택된 항목의 색상, 드롭다운 화살표 색상 등
예제:import streamlit as st # stMultiselect 클래스에 스타일 적용 st.markdown( """ <style> .stMultiselect > div { background-color: #E3F2FD; /* 위젯 배경색 */ border: 2px solid #2196F3; /* 테두리 색상 */ border-radius: 8px; /* 둥근 모서리 */ color: #0D47A1; /* 텍스트 색상 */ font-size: 16px; /* 텍스트 크기 */ padding: 5px; /* 내부 여백 */ } .stMultiselect div[data-baseweb="select"] > div { background-color: #BBDEFB; /* 드롭다운 배경색 */ color: #0D47A1; /* 드롭다운 텍스트 색상 */ } .stMultiselect div[data-baseweb="select"]:hover { border-color: #1976D2; /* 호버 시 테두리 색상 */ } </style> """, unsafe_allow_html=True ) # 멀티 셀렉트 생성 options = ["Python", "JavaScript", "Java", "C++", "Go"] selected = st.multiselect("좋아하는 프로그래밍 언어를 선택하세요:", options) # 선택된 옵션 출력 if selected: st.write("선택한 언어:", selected)
7. .stSlider: 슬라이더 스타일링
설명: st.slider와 관련된 슬라이더의 스타일을 제어합니다.
적용 가능한 스타일:
슬라이더 색상, 높이, 손잡이 스타일 등
예제:import streamlit as st # stSlider 클래스에 스타일 적용 st.markdown( """ <style> .stSlider>div>div { background-color: #ddd; /* 슬라이더 배경 */ height: 8px; /* 슬라이더 높이 */ } .stSlider>div>div>div { background-color: #4CAF50; /* 활성 슬라이더 색상 */ } </style> """, unsafe_allow_html=True ) # 슬라이더 생성 st.slider("슬라이더를 움직여보세요", 0, 100, 50)
8. .stTable: 테이블 스타일링
설명: st.write 또는 st.dataframe에서 생성된 테이블의 스타일을 제어합니다.
적용 가능한 스타일:
테이블 테두리, 배경색, 텍스트 색상 등
예제:import pandas as pd import streamlit as st # stTable 클래스에 스타일 적용 st.markdown( """ <style> .stTable { border: 1px solid #ddd; /* 테이블 테두리 */ border-radius: 5px; /* 둥근 테두리 */ background-color: #f9f9f9; /* 테이블 배경색 */ font-size: 16px; /* 텍스트 크기 */ } </style> """, unsafe_allow_html=True ) # 테이블 데이터 출력 data = pd.DataFrame({ "Name": ["Alice", "Bob", "Charlie"], "Age": [25, 30, 35], "City": ["New York", "San Francisco", "Los Angeles"] }) st.write(data)
9. .stProgress: 프로그래스바 스타일링
설명: 진행 상태를 표시하는 프로그래스바(st.progress)의 스타일을 제어합니다.
적용 가능한 스타일:
진행 색상, 높이 등
예제:import time import streamlit as st # stProgress 클래스에 스타일 적용 st.markdown( """ <style> .stProgress>div>div>div { background-color: #4CAF50; /* 진행 상태 색상 */ height: 20px; /* 진행 바 높이 */ } </style> """, unsafe_allow_html=True ) # 프로그래스바 생성 progress = st.progress(0) for i in range(101): time.sleep(0.05) progress.progress(i)
9.1. .stImage: 이미지 스타일링
설명: 이미지 요소(st.image)에 대한 스타일을 제어합니다.
적용 가능한 스타일:
이미지 크기, 정렬, 테두리, 그림자 등
예제:import streamlit as st # stImage 클래스에 스타일 적용 st.markdown( """ <style> .stImage img { border-radius: 15px; /* 둥근 모서리 */ border: 2px solid #4CAF50; /* 테두리 */ box-shadow: 5px 5px 15px rgba(0,0,0,0.3); /* 그림자 효과 */ max-width: 80%; /* 최대 너비 제한 */ margin: auto; /* 이미지 중앙 정렬 */ display: block; /* 블록 요소로 변환 */ } </style> """, unsafe_allow_html=True ) # 이미지 출력 st.image( "https://via.placeholder.com/400", caption="이것은 예제 이미지입니다." ) 여기서 box-shadow: offset-x offset-y blur-radius spread-radius color; offset-x (5px): 그림자의 수평 오프셋입니다. 예를 들어, 5px는 그림자가 요소의 오른쪽으로 5픽셀 이동하게 합니다. offset-y (5px): 그림자의 수직 오프셋입니다. 예를 들어, 5px는 그림자가 요소의 아래로 5픽셀 이동하게 합니다. blur-radius (15px): 그림자의 흐림 정도를 설정합니다. 예를 들어, 15px는 그림자가 비교적 부드럽게 흐려지도록 만듭니다. spread-radius (0px in the example, but if included): 그림자의 확산 정도입니다. 예를 들어, -5px는 그림자가 작아지게 만들고, 5px는 그림자가 커지게 만듭니다. color (rgba(0,0,0,0.5)): 그림자의 색상을 지정합니다. rgba(0,0,0,0.5)는 반투명한 검은색을 의미합니다. (검정색이고 투명도가 50%인 색상) rgba에서 (0, 0, 0)은 RGB 색상 값 (검정색)이며, 0.5는 투명도를 나타냅니다. (1은 불투명, 0은 완전히 투명)
9. .stInput: 입력 상자 스타일링
설명: 텍스트 입력 필드(st.text_input, st.text_area)의 스타일을 제어합니다.
적용 가능한 스타일:
입력 상자의 배경색, 테두리, 글꼴 스타일 등
예제:import streamlit as st # stInput 클래스에 스타일 적용 st.markdown( """ <style> .stTextInput>div>input { background-color: #F9F9F9; /* 배경색 */ color: #333; /* 텍스트 색상 */ border: 2px solid #4CAF50; /* 테두리 */ padding: 10px; /* 내부 여백 */ border-radius: 5px; /* 둥근 모서리 */ font-size: 16px; /* 글꼴 크기 */ } </style> """, unsafe_allow_html=True ) # 텍스트 입력 생성 user_input = st.text_input("당신의 이름은 무엇인가요?") if user_input: st.write(f"안녕하세요, {user_input}님!")
10. .stTextInput: 텍스트 입력 필드 스타일
설명: 텍스트 입력 위젯(st.text_input())의 스타일을 제어합니다.
적용 가능한 스타일:
입력 필드 배경색, 테두리, 글꼴 크기, 텍스트 색상 등
예제:import streamlit as st # stTextInput 클래스에 스타일 적용 st.markdown( """ <style> .stTextInput > div > div > input { background-color: #E8F5E9; /* 입력 필드 배경색 */ border: 2px solid #4CAF50; /* 테두리 색상 */ border-radius: 8px; /* 둥근 모서리 */ font-size: 16px; /* 글꼴 크기 */ color: #1B5E20; /* 텍스트 색상 */ padding: 10px; /* 내부 여백 */ } </style> """, unsafe_allow_html=True ) # 텍스트 입력 필드 생성 user_text = st.text_input("이름을 입력하세요:") if user_text: st.write(f"안녕하세요, {user_text}님!")
10.1 .stTextArea: 텍스트 영역 스타일
설명: 텍스트 영역 위젯(st.text_area())의 스타일을 제어하는 클래스입니다. 텍스트 입력 필드와 유사하지만, 여러 줄 입력이 가능합니다.
적용 가능한 스타일:
배경색, 테두리, 글꼴 크기, 내부 여백 등
예제:import streamlit as st # stTextArea 클래스에 스타일 적용 st.markdown( """ <style> .stTextArea textarea { background-color: #FFEBEE; /* 텍스트 영역 배경색 */ border: 2px solid #F44336; /* 테두리 색상 */ border-radius: 8px; /* 둥근 모서리 */ font-size: 16px; /* 텍스트 크기 */ color: #D32F2F; /* 텍스트 색상 */ padding: 10px; /* 내부 여백 */ line-height: 1.5; /* 줄 간격 */ } </style> """, unsafe_allow_html=True ) # 텍스트 영역 생성 user_text = st.text_area("의견을 입력하세요:", height=150) if user_text: st.write("입력된 의견:") st.write(user_text)
11. .stAlert: 경고 메시지 스타일링
설명: 경고 메시지(st.warning, st.error, st.info, st.success)의 스타일을 제어합니다.
적용 가능한 스타일:
메시지 색상, 글꼴 크기, 테두리 등
예제:import streamlit as st # stAlert 클래스에 스타일 적용 st.markdown( """ <style> .stAlert { background-color: #FFEBE6; /* 경고 메시지 배경색 */ border-left: 5px solid #FF4500; /* 왼쪽 테두리 강조 */ padding: 10px; /* 내부 여백 */ font-size: 18px; /* 글꼴 크기 */ } </style> """, unsafe_allow_html=True ) # 경고 메시지 출력 st.warning("이것은 경고 메시지입니다!")
12. .stFileUploader: 파일 업로더와 관련된 스타일
설명: 파일 업로드 위젯(st.file_uploader())의 스타일을 제어합니다.
적용 가능한 스타일:
배경색, 테두리, 글꼴 크기, 업로드 버튼 디자인 등
예제:import streamlit as st # stFileUploader 클래스에 스타일 적용 st.markdown( """ <style> .stFileUploader { background-color: #f5f5f5; /* 배경색 */ border: 2px dashed #4CAF50; /* 점선 테두리 */ padding: 15px; /* 내부 여백 */ border-radius: 10px; /* 둥근 모서리 */ text-align: center; /* 텍스트 중앙 정렬 */ } </style> """, unsafe_allow_html=True ) # 파일 업로드 위젯 생성 uploaded_file = st.file_uploader("파일을 업로드하세요") if uploaded_file is not None: st.write(f"업로드된 파일 이름: {uploaded_file.name}")
13. .stRadio: 라디오 버튼 스타일링
설명: 라디오 버튼 요소(st.radio)의 스타일을 제어합니다.
적용 가능한 스타일:
버튼 크기, 색상, 간격 등
예제:import streamlit as st # stRadio 클래스에 스타일 적용 st.markdown( """ <style> .stRadio>div { font-size: 16px; /* 텍스트 크기 */ color: #4CAF50; /* 텍스트 색상 */ margin-bottom: 15px; /* 하단 여백 */ } .stRadio>div>div>div { background-color: #FFF; /* 버튼 배경색 */ border: 2px solid #4CAF50; /* 버튼 테두리 */ border-radius: 5px; /* 둥근 모서리 */ } </style> """, unsafe_allow_html=True ) # 라디오 버튼 생성 choice = st.radio("하나를 선택하세요:", ["옵션 A", "옵션 B", "옵션 C"]) st.write(f"선택된 옵션: {choice}")
14. .stCheckbox: 체크박스 스타일링
설명: 체크박스 요소(st.checkbox)의 스타일을 제어합니다.
적용 가능한 스타일:
체크박스 크기, 간격, 색상 등
예제:import streamlit as st # stCheckbox 클래스에 스타일 적용 st.markdown( """ <style> .stCheckbox>div { font-size: 18px; /* 체크박스 텍스트 크기 */ color: #4CAF50; /* 텍스트 색상 */ margin-top: 10px; /* 상단 여백 */ } </style> """, unsafe_allow_html=True ) # 체크박스 생성 agree = st.checkbox("동의하시겠습니까?") if agree: st.write("감사합니다! 동의하셨습니다.")
15. .stTextArea: 텍스트 영역 스타일
설명: 텍스트 영역 위젯(st.text_area())의 스타일을 제어합니다.
적용 가능한 스타일:
배경색, 테두리, 글꼴 크기 등
예제:import streamlit as st # stTextArea 클래스에 스타일 적용 st.markdown( """ <style> .stTextArea textarea { background-color: #FFF3E0; /* 배경색 */ border: 1px solid #FF5722; /* 테두리 색상 */ border-radius: 5px; /* 둥근 모서리 */ font-size: 16px; /* 텍스트 크기 */ padding: 10px; /* 내부 여백 */ color: #333; /* 텍스트 색상 */ } </style> """, unsafe_allow_html=True ) # 텍스트 영역 생성 user_input = st.text_area("자유롭게 텍스트를 입력하세요:") st.write(f"입력된 텍스트: {user_input}")
16. .stMetric: 메트릭 카드 스타일
설명: 메트릭 카드 위젯(st.metric())의 스타일을 제어합니다.
적용 가능한 스타일:
배경색, 글꼴 크기, 값의 색상 강조 등
예제:import streamlit as st # stMetric 클래스에 스타일 적용 st.markdown( """ <style> .stMetric { background-color: #E3F2FD; /* 배경색 */ border: 1px solid #2196F3; /* 테두리 */ border-radius: 5px; /* 둥근 모서리 */ padding: 10px; /* 내부 여백 */ color: #1A237E; /* 텍스트 색상 */ font-size: 18px; /* 글꼴 크기 */ } </style> """, unsafe_allow_html=True ) # 메트릭 카드 생성 st.metric(label="매출", value="$10,000", delta="+5%")
17. .stExpander: 확장 가능한 요소 스타일
설명: 확장 가능한 요소 위젯(st.expander())의 스타일을 제어합니다.
적용 가능한 스타일:
확장 상태의 배경색, 테두리, 글꼴 크기 등
예제:import streamlit as st # stExpander 클래스에 스타일 적용 st.markdown( """ <style> .stExpander>div>div { background-color: #FFEBEE; /* 확장 요소 배경색 */ border: 1px solid #F44336; /* 테두리 */ border-radius: 5px; /* 둥근 모서리 */ color: #880E4F; /* 텍스트 색상 */ font-size: 16px; /* 텍스트 크기 */ } </style> """, unsafe_allow_html=True ) # 확장 가능한 요소 생성 with st.expander("자세히 보기"): st.write("이것은 확장 가능한 콘텐츠입니다.")
그런데 여기서 > div란 개념이 나옵니다. 하나가 아니라 여러개로....
저게 뭘까요?
> div 같은 CSS 선택자는 HTML 구조의 계층을 따라 정확히 특정 요소를 타겟팅하기 위해 사용됩니다. Streamlit 위젯은 여러 중첩된 <div> 태그를 사용하여 위젯을 렌더링하기 때문에, CSS 선택자에서 계층 구조를 따라야 원하는 요소에 스타일을 적용할 수 있습니다.
여기서 CSS 선택자라는 개념을 확실히 밟고 가야합니다.
CSS의 > 선택자란?
>는 직접적인 자식 요소만을 선택할 때 사용됩니다.
예:
.parent > .child { color: red; }
위 코드는 .parent의 바로 아래 자식 요소 중 클래스가 .child인 것만 스타일링합니다.
Streamlit에서 > div가 왜 여러 단계로 필요한가?
Streamlit 위젯들은 HTML DOM(Document Object Model) 구조에서 여러 계층으로 중첩된 <div> 요소를 포함합니다. 예를 들어, st.multiselect 위젯의 구조를 보면:<div class="stMultiselect"> <div> <div data-baseweb="select"> <div>...드롭다운 내용...</div> </div> </div> </div>
여기서:
.stMultiselect: 최상위 컨테이너.
.stMultiselect > div: 첫 번째 자식 요소.
.stMultiselect > div > div[data-baseweb="select"]: 두 번째 레벨의 특정 자식 요소.
.stMultiselect > div > div[data-baseweb="select"] > div: 세 번째 레벨의 자식 요소로, 드롭다운 내부를 가리킴.
왜 여러 계층을 따라야 하나요?
HTML 구조에서 모든 요소에 동일한 클래스명이 부여되지 않기 때문입니다. 특정 스타일을 적용하려면 중첩된 요소를 정확히 찾아야 합니다.
예시: Streamlit의 멀티 셀렉트 구조<div class="stMultiselect"> <div> <div data-baseweb="select"> <div>옵션 1</div> <div>옵션 2</div> </div> </div> </div>
CSS 적용
.stMultiselect: 최상위 컨테이너에 스타일 적용.
.stMultiselect > div: 첫 번째 자식 컨테이너 스타일.
.stMultiselect > div > div[data-baseweb="select"]: 드롭다운 부분의 스타일.
.stMultiselect > div > div[data-baseweb="select"] > div: 개별 옵션의 스타일.
결론
> div가 필요한 이유: Streamlit 위젯의 구조가 중첩되어 있어 특정 요소를 타겟팅하려면 계층을 따라야 함.
CSS 선택자 사용법:
최상위 클래스를 기준으로 스타일 적용.
내부 계층 요소를 따라가며 특정 부분에 세부 스타일 적용.
실전 팁:
Streamlit 앱을 실행한 후 브라우저의 **개발자 도구(F12)**를 사용해 DOM 구조를 확인하면, 필요한 CSS 경로를 쉽게 찾을 수 있습니다.
혹시 어렵다고 느끼시면 더 쉽게 설명해보겠습니다.
CSS 선택자는 HTML에서 "어떤 걸 꾸밀지"를 골라주는 도구이며. 마치 방 안에 있는 장난감들 중에 "어떤 장난감만 꾸밀지" 정하는 것과 비슷합니다.
HTML 구조를 집안으로 비유하기
집 안 구조
우리가 꾸미려는 HTML은 마치 방과 방이 이어져 있는 집 같습니다.
예를 들어, 이런 집이 있다고 해보면:집 (div1) ├ 거실 (div2) │ ├ 소파 (div3) │ ├ TV (div4) ├ 부엌 (div5) ├ 냉장고 (div6)
여기서 집(div1) 안에 거실(div2)과 부엌(div5)이 있고, 그리고 거실 안에는 소파(div3)와 TV(div4)가 있고, 부엌 안에는 냉장고(div6)가 있습니다.
CSS에서 > 선택자가 하는 일
> 선택자는 "바로 옆방에 있는 아이만 꾸며"라는 명령이며,
예를 들어, 이렇게 생긴 코드가 있다고 해보면:<div class="집"> <div class="거실"> <div class="소파">소파</div> <div class="TV">TV</div> </div> <div class="부엌"> <div class="냉장고">냉장고</div> </div> </div>
만약 꾸민다고 하면,
1. 모두 꾸미기 (아무런 제한 없이).집 div { background-color: yellow; /* 집 안의 모든 방 배경을 노란색으로 */ }
결과: 거실, 소파, TV, 부엌, 냉장고 모두 노란색으로 칠해짐.
2. 직접 자식만 꾸미기 (>).집 > div { background-color: yellow; /* 바로 집 밑에 있는 방(거실, 부엌)만 */ }
결과: 거실과 부엌만 노란색이 되고, 소파, TV, 냉장고는 영향을 받지 않음.
Streamlit에서 왜 이렇게 복잡할까?
Streamlit에서 사용하는 HTML은 우리가 만드는 모든 위젯을 각각 방처럼 여러 계층으로 나눠서 저장하기 때문입니다.
예를 들어, 멀티 셀렉트 위젯의 HTML 구조는 다음과 같이 생겼습니다:<div class="stMultiselect"> <div> <!-- 부모 방 --> <div data-baseweb="select"> <!-- 자식 방 --> <div>옵션 1</div> <div>옵션 2</div> </div> </div> </div>
예제: 멀티 셀렉트 위젯 꾸미기.stMultiselect > div { background-color: lightblue; /* 바로 아래 부모 방만 */ } .stMultiselect > div > div[data-baseweb="select"] { background-color: lightgreen; /* 드롭다운(자식 방) */ } .stMultiselect > div > div[data-baseweb="select"] > div { color: red; /* 드롭다운 안의 옵션들 */ }
.stMultiselect: 이건 "집" 전체입니다.
.stMultiselect > div: 집 안에 바로 있는 "거실과 부엌" 같은 방을 꾸밉니다.
.stMultiselect > div > div[data-baseweb="select"]: 방 안에 있는 "TV" 같은 물건을 꾸밉니다.
.stMultiselect > div > div[data-baseweb="select"] > div: TV 화면 속에 나오는 "그림" 같은 세부적인 부분을 꾸밉니다.
왜 이렇게 나눠서 쓰는 걸까?
다른 부분에 영향을 주지 않기 위해: 소파만 꾸미고 싶을 때, 거실 전체를 꾸미면 안될때.
세밀하게 꾸밀 수 있도록: TV도 꾸미고, TV 화면 속 그림도 따로 꾸밀 수 있어야 하기때문.
하지만 이건 뭘까요?
[data-baseweb="select"]
CSS에서 [data-baseweb="select"] 같은 속성 선택자를 쓰는 이유는 특정 HTML 요소를 더 정확히 타겟팅하기 위해서입니다. div만 쓰면 너무 포괄적이거나 원하는 요소와 다른 요소들까지 영향을 받을 수 있기 때문입니다.
들어가기전 드롭다운이 뭔지 살짝 예시로 알려드리겠습니다.
드롭다운(dropdown)은 웹 페이지에서 자주 사용되는 UI 요소 중 하나로, 선택 가능한 여러 항목을 숨기고, 사용자가 클릭하거나 터치하면 항목들이 나타나는 메뉴입니다.
[영어 ▼] - 영어 - 한국어 - 일본어 - 스페인어 영어를 누르면 그 안 항복들이 보이게 됩니다!
왜 속성 선택자를 쓰는 걸까?
HTML 구조가 복잡해서 특정 요소만 골라야 할 때
Streamlit에서 모든 위젯은 여러 겹으로 중첩된 <div>로 만들어져 있습니다.
예를 들어, 이런 구조가 있다고 해보겠습니다:
여기서 data-baseweb="select"는 "이 드롭다운은 Select 컴포넌트다"라는 정보를 나타내요. 만약 우리가 단순히 div만 선택한다면:<div class="stMultiselect"> <div> <div data-baseweb="select"> <!-- 드롭다운 컨테이너 --> <div>옵션 1</div> <div>옵션 2</div> </div> </div> </div>
.stMultiselect div { background-color: yellow; }
결과: 모든 div가 노란색이 됩니다.
문제: 드롭다운뿐만 아니라 옵션(옵션 1, 옵션 2)까지 영향을 받죠.
중요! 필터링해서 정확히 타겟팅하기 위해속성 선택자를 쓰면 특정 요소만 정확히 골라낼 수 있어요:
.stMultiselect div[data-baseweb="select"] { background-color: yellow; /* 드롭다운만 노란색으로 */ }
결과: 드롭다운 컨테이너만 영향을 받습니다.
속성 선택자의 역할
1. 특정 속성을 가진 요소만 선택[속성명="값"] { 스타일; }
[data-baseweb="select"]: data-baseweb이라는 속성값이 "select"인 요소만 선택.
2. 다른 요소와 혼동을 방지
div만 쓰면 모든 div가 영향을 받을 수 있어요.
속성 선택자를 추가하면 특정 속성을 가진 div만 타겟팅할 수 있죠.
참고로 select 요소가 여러 개 있을 때, 부모 요소를 기준으로 스타일을 지정할 수 있습니다. 예를 들어, 하나의 select 요소는 div 안에 있고, 다른 하나는 form 안에 있을 때, 부모 요소를 기준으로 선택자를 작성할 수 있습니다.<div class="select-group"> <div data-baseweb="select">Select 1</div> </div> <form> <div data-baseweb="select">Select 2</div> </form>
/* .select-group 안에 있는 data-baseweb="select" 선택 */ .select-group div[data-baseweb="select"] { background-color: lightblue; } /* form 안에 있는 data-baseweb="select" 선택 */ form div[data-baseweb="select"] { background-color: lightgreen; }
하지만 속성 선택자는 data-baseweb 외에도 다양한 속성들을 사용할 수 있습니다! 기본적으로 속성 선택자는 HTML 요소의 특정 속성(attribute)을 기준으로 해당 요소를 선택하는 방법입니다. data-baseweb은 Streamlit 같은 UI 프레임워크에서 사용하는 속성 중 하나일 뿐이며, HTML 요소에는 다양한 속성들이 존재합니다.
일단 스트림릿에는 data-baseweb을 주로 쓰며 이것만 알면 됩니다!
일단! 오늘은 여기까지...코드 적으러 가야지....