import pandas as pd import difflib from sklearn.feature_extraction.text import TfidfVectorizer from sklearn.metrics.pairwise import cosine_similarity import gradio as gr import numpy as np # Load the data - when deploying, adjust the path to where your dataset will be stored def load_data(): try: # For Hugging Face Spaces deployment, you might need to adjust this path data = pd.read_csv('games_march2025_cleaned.csv', nrows=20000, on_bad_lines='skip', engine='python') return data except Exception as e: print(f"Error loading data: {e}") return None # Prepare the feature vectors for similarity calculation def prepare_features(data): selected_features = ['genres', 'price', 'average_playtime_2weeks', 'tags'] for feature in selected_features: data[feature] = data[feature].fillna('') combined_features = ( data['genres'] + ' ' + data['price'].astype(str) + ' ' + data['average_playtime_2weeks'].astype(str) + ' ' + data['tags'].astype(str) ) vectorizer = TfidfVectorizer() feature_vectors = vectorizer.fit_transform(combined_features) return feature_vectors # Function to get game recommendations def get_recommendations(game_name, data, feature_vectors): list_of_all_titles = data['name'].tolist() find_close_match = difflib.get_close_matches(game_name, list_of_all_titles) if not find_close_match: return "No match found for the game name. Please try another title." closest_match = find_close_match[0] index_of_the_game = data.loc[data['name'] == closest_match].index[0] game_similarity = cosine_similarity(feature_vectors) similarity_scores = list(enumerate(game_similarity[index_of_the_game])) sorted_similar_games = sorted(similarity_scores, key=lambda x: x[1], reverse=True) result_html = "" for i, game in enumerate(sorted_similar_games[1:10], 1): index = game[0] name = data.loc[index, 'name'] about = data.loc[index, 'short_description'] or "No description available" image_url = data.loc[index, 'header_image'] or "" platforms = [] if data.loc[index, 'windows'] == 1: platforms.append("Windows") if data.loc[index, 'mac'] == 1: platforms.append("Mac") if data.loc[index, 'linux'] == 1: platforms.append("Linux") platforms_str = ", ".join(platforms) or "Unknown" metacritic = data.loc[index, 'metacritic_score'] price = data.loc[index, 'price'] pos = data.loc[index, 'positive'] neg = data.loc[index, 'negative'] total_reviews = pos + neg pos_ratio = f"{(pos / total_reviews * 100):.1f}%" if total_reviews > 0 else "N/A" # Combine into HTML result_html += f"""

{i}. {name}

Platforms: {platforms_str}

Price: ${price}

Metacritic Score: {metacritic if pd.notnull(metacritic) else "N/A"}

Positive Reviews: {pos_ratio}

{about}


""" return result_html # Gradio interface function def recommend_games(game_name, max_age, max_price, min_metacritic): data = load_data() if data is None: return "Failed to load data. Please check the data file." # Apply filters BEFORE feature preparation data = data[ (data['required_age'] <= max_age) & (data['price'] <= max_price) & ((data['metacritic_score'].fillna(0) >= min_metacritic) | data['metacritic_score'].isna()) ].reset_index(drop=True) if data.empty: return "No games found matching your filter criteria." feature_vectors = prepare_features(data) recommendations_html = get_recommendations(game_name, data, feature_vectors) return recommendations_html # Create the Gradio interface with gr.Blocks(title="Steam Game Recommender") as demo: gr.Markdown("Steam Game Recommender") gr.Markdown("Enter a game you like and customize filters to get similar suggestions.") with gr.Row(): input_text = gr.Textbox(label="Favorite Game") with gr.Row(): max_age_slider = gr.Slider(0, 21, value=17, label="Max Age Rating (Avoid Adult Games)") max_price_slider = gr.Slider(0.0, 100.0, value=60.0, step=0.5, label="Maximum Price ($)") min_metacritic_slider = gr.Slider(0, 100, value=50, step=1, label="Minimum Metacritic Score") with gr.Row(): submit_btn = gr.Button("Get Recommendations") with gr.Row(): output_text = gr.Markdown(label="Recommendations") submit_btn.click( fn=recommend_games, inputs=[input_text, max_age_slider, max_price_slider, min_metacritic_slider], outputs=output_text ) # Launch the app if __name__ == "__main__": demo.launch()