Wikia code/includes/Skin.php

--- D:\Programming\SVN\mediawiki\branches\REL1_16\phase3\includes\Skin.php	2011-07-18 22:31:28.318359400 +0100
+++ D:\Programming\SVN\wikia\trunk\includes\Skin.php	2011-08-17 15:28:46.652343700 +0100
@@ -101,6 +101,15 @@
 			return $key;
 		}
 
+		// Wikia: normalize using $wgSkinTheme array
+		global $wgSkinTheme;
+		if ( strpos($key, '-') !== false ) {
+			list($skin, $theme) = explode('-', $key);
+			if ( isset($wgSkinTheme[$skin]) && in_array($theme, $wgSkinTheme[$skin]) ) {
+				return $key;
+			}
+		}
+
 		// Older versions of the software used a numeric setting
 		// in the user preferences.
 		$fallback = array(
@@ -115,8 +124,10 @@
 
 		if( isset( $skinNames[$key] ) ) {
 			return $key;
+		} elseif( isset( $skinNames[$wgDefaultSkin] ) ) {
+			return $wgDefaultSkin;
 		} else {
-			return 'monobook';
+			return 'oasis';
 		}
 	}
 
@@ -126,7 +137,7 @@
 	 * @return Skin
 	 */
 	static function &newFromKey( $key ) {
-		global $wgStyleDirectory;
+		global $wgStyleDirectory, $wgCityId, $wgUseMonaco2;
 
 		$key = Skin::normalizeKey( $key );
 
@@ -134,6 +145,10 @@
 		$skinName = $skinNames[$key];
 		$className = 'Skin' . ucfirst( $key );
 
+		if($skinName == 'Monaco' && empty($wgUseMonaco2)) {
+			$skinName = 'Monaco_old';
+		}
+
 		# Grab the skin class and initialise it.
 		if ( !class_exists( $className ) ) {
 			// Preload base classes to work around APC/PHP5 bug
@@ -150,8 +165,8 @@
 				# except by SQL manipulation if a previously valid skin name
 				# is no longer valid.
 				wfDebug( "Skin class does not exist: $className\n" );
-				$className = 'SkinMonobook';
-				require_once( "{$wgStyleDirectory}/MonoBook.php" );
+				$className = 'SkinMonaco';
+				require_once( "{$wgStyleDirectory}/Monaco.php" );
 			}
 		}
 		$skin = new $className;
@@ -192,7 +207,7 @@
 		}
 
 		if( false !== $wgFavicon ) {
-			$out->addLink( array( 'rel' => 'shortcut icon', 'href' => $wgFavicon ) );
+			$out->addLink( array( 'rel' => 'shortcut icon', 'href' => str_replace('images.wikia.com', 'images1.wikia.nocookie.net', $wgFavicon) ) );
 		}
 
 		# OpenSearch description link
@@ -506,30 +521,45 @@
 	 * @return string
 	 */
 	public function generateUserJs( $skinName = null ) {
-		global $wgStylePath;
+		global $wgStylePath, $wgUseSiteJs;
+		
+		/* Wikia change begin - @author: macbre */
+		/* Don't return generated JS when per-site JS is disabled (BugId:9961) */
+		if (empty($wgUseSiteJs)) {
+			return '/* generated javascript is disabled */';
+		}
+		/* Wikia change end */
 
 		wfProfileIn( __METHOD__ );
 		if( !$skinName ) {
 			$skinName = $this->getSkinName();
 		}
 
+		// Wikia change for new skin project
+		$jsFileName = $this->getSkinName();
+		if($jsFileName == 'oasis') {
+			$jsFileName = 'wikia';
+		}
+
 		$s = "/* generated javascript */\n";
 		$s .= "var skin = '" . Xml::escapeJsString( $skinName ) . "';\n";
 		$s .= "var stylepath = '" . Xml::escapeJsString( $wgStylePath ) . "';";
 		$s .= "\n\n/* MediaWiki:Common.js */\n";
+		$s .= "try{\n";
 		$commonJs = wfMsgExt( 'common.js', 'content' );
 		if ( !wfEmptyMsg( 'common.js', $commonJs ) ) {
-			$s .= $commonJs;
+			$s .= $commonJs . "\n";
 		}
 
 		$s .= "\n\n/* MediaWiki:" . ucfirst( $skinName ) . ".js */\n";
 		// avoid inclusion of non defined user JavaScript (with custom skins only)
 		// by checking for default message content
-		$msgKey = ucfirst( $skinName ) . '.js';
+		$msgKey = ucfirst( $jsFileName ) . '.js';
 		$userJS = wfMsgExt( $msgKey, 'content' );
 		if ( !wfEmptyMsg( $msgKey, $userJS ) ) {
-			$s .= $userJS;
+			$s .= $userJS . "\n";
 		}
+		$s .=  "\n } catch(err) {\n window._customJSerror = err;\n } ";
 
 		wfProfileOut( __METHOD__ );
 		return $s;
@@ -597,6 +627,9 @@
 		global $wgRequest, $wgContLang, $wgUser;
 		global $wgAllowUserCss, $wgUseSiteCss, $wgSquidMaxage, $wgStylePath;
 
+		// FIXME: override this method in Oasis skin?
+		global $wgOasisLastCssScripts;
+
 		wfProfileIn( __METHOD__ );
 
 		$this->setupSkinUserCss( $out );
@@ -620,13 +653,21 @@
 				'ctype' => 'text/css',
 				'smaxage' => $wgSquidMaxage
 			) + $siteargs );
+
 			# Site settings must override extension css! (bug 15025)
-			$out->addStyle( self::makeNSUrl( 'Common.css', $query, NS_MEDIAWIKI ) );
 			$out->addStyle( self::makeNSUrl( 'Print.css', $query, NS_MEDIAWIKI ), 'print' );
 			if( $wgHandheldStyle ) {
 				$out->addStyle( self::makeNSUrl( 'Handheld.css', $query, NS_MEDIAWIKI ), 'handheld' );
 			}
-			$out->addStyle( self::makeNSUrl( $this->getSkinName() . '.css', $query, NS_MEDIAWIKI ) );
+
+			// Wikia
+			if( empty($this->themename) || $this->themename == 'custom' || $this->themename == 'oasis' ) {
+				$skinname = $this->getSkinName();
+				if($skinname != 'oasis') {
+					$out->addStyle( self::makeNSUrl( 'Common.css', $query, NS_MEDIAWIKI ) );
+					$out->addStyle( self::makeNSUrl( $skinname . '.css', $query, NS_MEDIAWIKI ) );
+				}
+			}
 		}
 
 		if( $wgUser->isLoggedIn() ) {
@@ -640,7 +681,12 @@
 		if( ( $us = $wgRequest->getVal( 'useskin', '' ) ) !== '' ) {
 			$siteargs['useskin'] = $us;
 		}
+		// Wikia change - start (Sean)
+		$skinname = $this->getSkinName();
+		if($skinname != 'oasis'){
 		$out->addStyle( self::makeUrl( '-', wfArrayToCGI( $siteargs ) ) );
+		}
+		// Wikia change - end (Sean)
 
 		// Per-user custom style pages
 		if( $wgAllowUserCss && $wgUser->isLoggedIn() ) {
@@ -650,10 +696,33 @@
 				// @FIXME: properly escape the cdata!
 				$out->addInlineStyle( $wgRequest->getText( 'wpTextbox1' ) );
 			} else {
-				$out->addStyle( self::makeUrl(
-					$this->userpage . '/' . $this->getSkinName() . '.css',
-					'action=raw&ctype=text/css' )
-				);
+				wfProfileIn(__METHOD__ . '::checkForEmptyUserCSS');
+
+				// macbre: check for empty User:foo/skins.css
+				$skinname = $this->getSkinName();
+				if($skinname == 'oasis') {
+					$userCSS = $this->userpage . '/wikia.css';
+				} else {
+					$userCSS = $this->userpage . '/' . $skinname .'.css';
+				}
+
+				$userCSStitle = Title::newFromText($userCSS);
+				if ($userCSStitle->exists()) {
+					$rev = Revision::newFromTitle($userCSStitle, $userCSStitle->getLatestRevID());
+					if (!empty($rev) && $rev->getText() != '') {
+						$userCSSurl = self::makeUrl($userCSS, 'action=raw&ctype=text/css');
+
+						if ($skinname == 'oasis') {
+							// RT #68514 - load in specific order
+							$wgOasisLastCssScripts[] = $userCSSurl;
+						}
+						else {
+							$out->addStyle( $userCSSurl );
+						}
+					}
+				}
+
+				wfProfileOut(__METHOD__ . '::checkForEmptyUserCSS');
 			}
 		}
 
@@ -681,7 +750,14 @@
 			$type = 'ns-subject';
 		}
 		$name = Sanitizer::escapeClass( 'page-' . $title->getPrefixedText() );
-		return "$numeric $type $name";
+
+		$classes = "$numeric $type $name";
+
+		// macbre@wikia: allow extensions to change body tag attributes
+		// refs RT #14017
+		wfRunHooks( 'SkinGetPageClasses', array( &$classes ) );
+
+		return $classes;
 	}
 
 	/**
@@ -768,6 +844,9 @@
 		global $wgOut, $wgUseCategoryBrowser;
 		global $wgContLang, $wgUser;
 
+		if( !wfRunHooks( 'Skin::getCategoryLinks::begin', array( &$alternativeCategoryLinks ) ) )
+			return $alternativeCategoryLinks;
+
 		if( count( $wgOut->mCategoryLinks ) == 0 ) {
 			return '';
 		}
@@ -788,8 +867,13 @@
 			$t = $embed . implode( "{$pop} {$sep} {$embed}" , $allCats['normal'] ) . $pop;
 
 			$msg = wfMsgExt( 'pagecategories', array( 'parsemag', 'escapenoentities' ), count( $allCats['normal'] ) );
+			$attribs = array();
+			global $wgWikiaUseNoFollow;
+			if( !empty( $wgWikiaUseNoFollow ) ) {
+				$attribs['rel'] = 'nofollow';
+			}
 			$s .= '<div id="mw-normal-catlinks">' .
-				$this->link( Title::newFromText( wfMsgForContent( 'pagecategorieslink' ) ), $msg )
+				$this->link( Title::newFromText( wfMsgForContent( 'pagecategorieslink' ) ), $msg, $attribs )
 				. $colon . $t . '</div>';
 		}
 
@@ -825,6 +909,8 @@
 			$s .= implode( "<br />\n", $tempout );
 		}
 
+		wfRunHooks( 'Skin::getCategoryLinks::end', array( &$s ) );
+
 		return $s;
 	}
 
@@ -1017,7 +1103,7 @@
 				$name = $this->mTitle->getDBkey();
 				$image = wfFindFile( $this->mTitle );
 				if( $image ) {
-					$link = htmlspecialchars( $image->getURL() );
+					$link = htmlspecialchars( wfReplaceImageServer( $image->getURL(), $image->getTimestamp() ) );
 					$style = $this->getInternalLinkAttributes( $link, $name );
 					$s[] = "<a href=\"{$link}\"{$style}>{$name}</a>";
 				}
@@ -1158,6 +1244,7 @@
 					$growinglink .= $link;
 					$display .= $link;
 					$linkObj = Title::newFromText( $growinglink );
+					wfRunHooks( 'SkinSubPageSubtitleAfterTitle', array( $linkObj, &$display ) );
 					if( is_object( $linkObj ) && $linkObj->exists() ) {
 						$getlink = $this->link(
 							$linkObj,
@@ -1221,7 +1309,7 @@
 				: 'login';
 			$ret .= "\n<br />" . $this->link(
 				SpecialPage::getTitleFor( 'Userlogin' ),
-				wfMsg( $loginlink ), array(), $query
+				wfMsg( $loginlink ), array( 'rel' => 'nofollow' ), $query
 			);
 		} else {
 			$returnTo = $this->mTitle->getPrefixedDBkey();
@@ -1260,7 +1348,7 @@
 	}
 
 	function searchForm() {
-		global $wgRequest, $wgUseTwoButtonsSearchForm;
+		global $wgRequest, $wgUseTwoButtonsSearchForm, $wgSearchDefaultFulltext;;
 		$search = $wgRequest->getText( 'search' );
 
 		$s = '<form id="searchform' . $this->searchboxes . '" name="search" class="inline" method="post" action="'
@@ -1496,7 +1584,12 @@
 			$title = Title::newFromText( $wgRightsPage );
 			$link = $this->linkKnown( $title, $wgRightsText );
 		} elseif( $wgRightsUrl ) {
+			global $wgWikiaUseNoFollow;
+			if( !empty( $wgWikiaUseNoFollow ) ) {
+				$link = $this->makeExternalLink( $wgRightsUrl, $wgRightsText, true, '', array('rel' => 'nofollow') );
+			} else {
 			$link = $this->makeExternalLink( $wgRightsUrl, $wgRightsText );
+			}
 		} elseif( $wgRightsText ) {
 			$link = $wgRightsText;
 		} else {
@@ -1509,6 +1602,11 @@
 		}
 
 		$out .= wfMsgForContent( $msg, $link );
+
+		// Return just a (WF-driven) link; omit MediaWiki:Copyright msg.
+		// getCopyright is used only in the footer so this hack should be fairly safe.
+		$out = $link;
+
 		return $out;
 	}
 
@@ -1543,6 +1641,29 @@
 		return $img;
 	}
 
+	function deliciousLink() {
+		global $wgDelicious, $wgGraphicalDelicious, $wgStylePath;
+		$delicious = ($wgGraphicalDelicious)
+			? Xml::element( "img", array( "src" => "$wgStylePath/common/images/OPmydel.gif",  "alt" => "del.icio.us" ) )
+			: wfMsgForContent('deliciouslink');
+		return ( $wgDelicious ) ? "<a href=\"http://del.icio.us/post\" onclick=\"location.href='https://api.del.icio.us/v1/posts/add?description='+encodeURIComponent(document.title)+'&amp;url='+encodeURIComponent(location.href); return false;\">".$delicious."</a>" : '';
+	}
+
+	function diggsLink() {
+		global $wgDigg, $wgGraphicalDigg;
+		$digg = ($wgGraphicalDigg) ? '<script type="text/javascript">
+		//<!--
+			document.write(\'<\'+\'img src="http://images.wikia.com/common/skins/common/images/91x17-digg-button.png?js=1" width="91" height="17" alt="Digg!" border="0"\'+\' />\');
+		 // -->
+		 </script><noscript><div><img src="http://images.wikia.com/common/skins/common/images/91x17-digg-button.png?js=0" width="91" height="17" alt="Digg!" /></div></noscript>' : wfMsgForContent('digglink');
+		return ( $wgDigg ) ? "<a href=\"http://digg.com/submit\"  onclick=\"location.href='http://digg.com/submit?phase=2&amp;url='+encodeURIComponent(location.href)+'&amp;title='+encodeURIComponent(document.title); return false;\">".$digg."</a>" : '';
+	}
+
+	function getHostedBy() {
+		$url = "http://www.wikicities.com/images/e/e1/Hosted_by_wikicities.png" ;
+		return '<a href="http://www.wikicities.com/"><img src="'.$url.'" alt="MediaWiki" /></a>';
+	}
+
 	function lastModified() {
 		global $wgLang, $wgArticle;
 		if( $this->mRevisionId && $this->mRevisionId != $wgArticle->getLatest() ) {
@@ -2081,6 +2202,7 @@
 			}
 		}
 
+        $heading = "";
 		$bar = array();
 		$this->addToSidebar( $bar, 'sidebar' );