Index: bp-templates/bp-legacy/buddypress-functions.php
===================================================================
--- bp-templates/bp-legacy/buddypress-functions.php	(revision 7200)
+++ bp-templates/bp-legacy/buddypress-functions.php	(working copy)
@@ -195,26 +195,15 @@
 	public function enqueue_styles() {
 
 		// LTR or RTL
-		$file = is_rtl() ? 'css/buddypress-rtl.css' : 'css/buddypress.css';
+		$file = is_rtl() ? 'buddypress-rtl.css' : 'buddypress.css';
 
-		// Check child theme
-		if ( file_exists( trailingslashit( get_stylesheet_directory() ) . $file ) ) {
-			$location = trailingslashit( get_stylesheet_directory_uri() );
-			$handle   = 'bp-child-css';
+		// Locate the BP stylesheet
+		$asset = $this->locate_asset_in_stack( $file, 'css' );
 
-		// Check parent theme
-		} elseif ( file_exists( trailingslashit( get_template_directory() ) . $file ) ) {
-			$location = trailingslashit( get_template_directory_uri() );
-			$handle   = 'bp-parent-css';
-
-		// BuddyPress Theme Compatibility
-		} else {
-			$location = trailingslashit( $this->url );
-			$handle   = 'bp-legacy-css';
+		// Enqueue BuddyPress-specific styling, if found
+		if ( isset( $asset['location'], $asset['handle'] ) ) {
+			wp_enqueue_style( $asset['handle'], $asset['location'], array(), $this->version, 'screen' );
 		}
-
-		// Enqueue the BuddyPress styling
-		wp_enqueue_style( $handle, $location . $file, array(), $this->version, 'screen' );
 	}
 
 	/**
@@ -224,28 +213,17 @@
 	 */
 	public function enqueue_scripts() {
 
-		// LTR or RTL
-		$file = 'js/buddypress.js';
+		$file = 'buddypress.js';
 
-		// Check child theme
-		if ( file_exists( trailingslashit( get_stylesheet_directory() ) . $file ) ) {
-			$location = trailingslashit( get_stylesheet_directory_uri() );
-			$handle   = 'bp-child-js';
+		// Locate the BP JS file
+		$asset = $this->locate_asset_in_stack( $file, 'js' );
 
-		// Check parent theme
-		} elseif ( file_exists( trailingslashit( get_template_directory() ) . $file ) ) {
-			$location = trailingslashit( get_template_directory_uri() );
-			$handle   = 'bp-parent-js';
-
-		// BuddyPress Theme Compatibility
-		} else {
-			$location = trailingslashit( $this->url );
-			$handle   = 'bp-legacy-js';
+		// Enqueue the global JS, if found - AJAX will not work
+		// without it
+		if ( isset( $asset['location'], $asset['handle'] ) ) {
+			wp_enqueue_script( $asset['handle'], $asset['location'], array( 'jquery' ), $this->version );
 		}
 
-		// Enqueue the global JS - Ajax will not work without it
-		wp_enqueue_script( $handle, $location . $file, array( 'jquery' ), $this->version );
-
 		// Add words that we need to use in JS to the end of the page so they can be translated and still used.
 		$params = array(
 			'my_favs'           => __( 'My Favorites', 'buddypress' ),
@@ -261,7 +239,7 @@
 			'remove_fav'	    => __( 'Remove Favorite', 'buddypress' ),
 			'unsaved_changes'   => __( 'Your profile has unsaved changes. If you leave the page, the changes will be lost.', 'buddypress' ),
 		);
-		wp_localize_script( $handle, 'BP_DTheme', $params );
+		wp_localize_script( $asset['handle'], 'BP_DTheme', $params );
 
 		// Maybe enqueue comment reply JS
 		if ( is_singular() && bp_is_blog_page() && get_option( 'thread_comments' ) ) {
@@ -270,6 +248,75 @@
 	}
 
 	/**
+	 * Get the URL and handle of a web-accessible CSS or JS asset
+	 *
+	 * We provide two levels of customizability with respect to where CSS
+	 * and JS files can be stored: (1) the child theme/parent theme/theme
+	 * compat hierarchy, and (2) the "template stack" of /buddypress/css/,
+	 * /community/css/, and /css/. In this way, CSS and JS assets can be
+	 * overloaded, and default versions provided, in exactly the same way
+	 * as corresponding PHP templates.
+	 *
+	 * We are duplicating some of the logic that is currently found in
+	 * bp_locate_template() and the _template_stack() functions. Those
+	 * functions were built with PHP templates in mind, and will require
+	 * refactoring in order to provide "stack" functionality for assets
+	 * that must be accessible both using file_exists() (the file path)
+	 * and at a public URI.
+	 *
+	 * This method is marked private, with the understanding that the
+	 * implementation is subject to change or removal in an upcoming
+	 * release, in favor of a unified _template_stack() system. Plugin
+	 * and theme authors should not attempt to use what follows.
+	 *
+	 * @since BuddyPress (1.8)
+	 * @access private
+	 * @param string $file A filename like buddypress.cs
+	 * @param string $type css|js
+	 * @return array An array of data for the wp_enqueue_* function:
+	 *   'handle' (eg 'bp-child-css') and a 'location' (the URI of the
+	 *   asset)
+	 */
+	private function locate_asset_in_stack( $file, $type = 'css' ) {
+		// Child, parent, theme compat
+		$locations = array(
+			'bp-child' => array(
+				'dir' => get_stylesheet_directory(),
+				'uri' => get_stylesheet_directory_uri(),
+			),
+			'bp-parent' => array(
+				'dir' => get_template_directory(),
+				'uri' => get_template_directory_uri(),
+			),
+			'bp-legacy' => array(
+				'dir' => bp_get_theme_compat_dir(),
+				'uri' => bp_get_theme_compat_url(),
+			),
+		);
+
+		// Subdirectories within the top-level $locations directories
+		$subdirs = array(
+			'buddypress/' . $type,
+			'community/' . $type,
+			$type,
+		);
+
+		$retval = array();
+
+		foreach ( $locations as $location_type => $location ) {
+			foreach ( $subdirs as $subdir ) {
+				if ( file_exists( trailingslashit( $location['dir'] ) . trailingslashit( $subdir ) . $file ) ) {
+					$retval['location'] = trailingslashit( $location['uri'] ) . trailingslashit( $subdir ) . $file;
+					$retval['handle']   = $location_type . '-' . $type;
+					break 2;
+				}
+			}
+		}
+
+		return $retval;
+	}
+
+	/**
 	 * Put some scripts in the header, like AJAX url for wp-lists
 	 *
 	 * @since BuddyPress (1.7)
