Isarra has uploaded a new change for review.

  https://gerrit.wikimedia.org/r/311603

Change subject: I don't actually remember what all I was doing.
......................................................................

I don't actually remember what all I was doing.

Made a ToC class; partially implemented.
Made an icon class, partially used.

bug: T140170
Change-Id: I3126a963c603c2bd4ca38b0552eb52e14697eaa2
---
M extension.json
M i18n/en.json
M i18n/qqq.json
M includes/content/CollaborationHubContent.php
A includes/content/CollaborationHubTOC.php
A includes/content/CollaborationKitIcon.php
M modules/ext.CollaborationKit.hub.styles.less
7 files changed, 409 insertions(+), 152 deletions(-)


  git pull 
ssh://gerrit.wikimedia.org:29418/mediawiki/extensions/CollaborationKit 
refs/changes/03/311603/1

diff --git a/extension.json b/extension.json
index 2fd2145..21a2faa 100644
--- a/extension.json
+++ b/extension.json
@@ -20,6 +20,8 @@
                "CollaborationKitHooks": "includes/CollaborationKit.php",
                "CollaborationHubContent": 
"includes/content/CollaborationHubContent.php",
                "CollaborationHubContentHandler": 
"includes/content/CollaborationHubContentHandler.php",
+               "CollaborationHubTOC": 
"includes/content/CollaborationHubTOC.php",
+               "CollaborationKitIcon": 
"includes/content/CollaborationKitIcon.php",
                "CollaborationListContent": 
"includes/content/CollaborationListContent.php",
                "CollaborationListContentHandler": 
"includes/content/CollaborationListContentHandler.php",
                "SpecialCreateCollaborationHub": 
"includes/SpecialCreateCollaborationHub.php",
diff --git a/i18n/en.json b/i18n/en.json
index f7501e5..8f9951b 100644
--- a/i18n/en.json
+++ b/i18n/en.json
@@ -49,5 +49,6 @@
        "collaborationkit-hub-subpage-view": "View",
        "collaborationkit-hub-subpage-remove": "Remove feature",
        "collaborationkit-hub-edit-apierror": "API edit error: $1",
-       "collaborationkit-hub-edit-tojsonerror": "Error converting to JSON"
+       "collaborationkit-hub-edit-tojsonerror": "Error converting to JSON",
+       "collaborationkit-hub-toc-label": "Project contents"
 }
diff --git a/i18n/qqq.json b/i18n/qqq.json
index 3d02923..a830742 100644
--- a/i18n/qqq.json
+++ b/i18n/qqq.json
@@ -49,5 +49,6 @@
        "collaborationkit-hub-subpage-view": "View link label for subpages on 
Collaboration Hub mainpages",
        "collaborationkit-hub-subpage-remove": "Remove link label for subpages 
on Collaboration Hub mainpages",
        "collaborationkit-hub-edit-apierror": "Error message for API edit 
error",
-       "collaborationkit-hub-edit-tojsonerror": "Error message when something 
went wrong converting to JSON"
+       "collaborationkit-hub-edit-tojsonerror": "Error message when something 
went wrong converting to JSON",
+       "collaborationkit-hub-toc-label": "Label for the toc on a Collaboration 
Hub mainpage"
 }
diff --git a/includes/content/CollaborationHubContent.php 
b/includes/content/CollaborationHubContent.php
index f72f9e2..a28c41a 100644
--- a/includes/content/CollaborationHubContent.php
+++ b/includes/content/CollaborationHubContent.php
@@ -252,7 +252,7 @@
                        'div',
                        [ 'class' => 'wp-header-image' ],
                        // TODO move all image stuff to ToC class (what is that 
class even going to be, anyway?)
-                       $this->getParsedImage( $this->getImage(), 200 )
+                       $this->getParsedImage( $title, $this->getImage(), 200 )
                );
                // get members list
                $html .= Html::rawElement(
@@ -270,7 +270,7 @@
                $html .= Html::rawElement(
                        'div',
                        [ 'class' => 'wp-toc' ],
-                       $this->getTableofContents( $title, $options )
+                       $this->getTableOfContents( $title, $options )
                );
                // get transcluded content
                $html .= Html::rawElement(
@@ -443,7 +443,7 @@
                                        $text = Html::rawElement(
                                                'div',
                                                [ 'class' => 'wp-header-image' 
],
-                                               $spContent->getParsedImage( 
$spContent->getImage(), 100 )
+                                               $spContent->getParsedImage( 
$spTitle, $spContent->getImage(), 100 )
                                        );
                                        $text .= 
$spContent->getParsedIntroduction( $spTitle, $options );
                                } elseif ( $spContentModel == 
'CollaborationListContent' ) {
@@ -636,98 +636,10 @@
         * @param ParserOptions $options
         * @return string
         */
-       protected function getTableofContents( Title $title, ParserOptions 
$options ) {
-               // This is going to be moved into its own class, and cleaning 
it up here is too much effort right now.
-               // Restoring placeholder.
-               $html = '<div>TOC APPEARS HERE (PENDING T140170)</div>';
+       protected function getTableOfContents( Title $title, ParserOptions 
$options ) {
+               $toc = new CollaborationHubTOC();
 
-               return $html;
-       }
-
-       /**
-        * Generates html for canned icons
-        * @param string $icon data: either an icon id or anything to use as a 
seed
-        * @return string
-        */
-       protected function makeIcon( $icon ) {
-               // Keep this synced with the icons listed in the module in 
extension.json
-               $iconsPreset = [
-                       // Randomly selectable items
-                       'book',
-                       'circlestar',
-                       'clock',
-                       'community',
-                       'contents',
-                       'die',
-                       'edit',
-                       'eye',
-                       'flag',
-                       'funnel',
-                       'gear',
-                       'heart',
-                       'journal',
-                       'key',
-                       'link',
-                       'map',
-                       'menu',
-                       'newspaper',
-                       'ol',
-                       'page',
-                       'paperclip',
-                       'puzzlepiece',
-                       'ribbon',
-                       'rocket',
-                       'star',
-                       'sun',
-                       'ul',
-
-                       'addimage',
-                       'addmapmarker',
-                       'addquote',
-                       'bell',
-                       'circleline',
-                       'circletriangle',
-                       'circlex',
-                       'discussion',
-                       'download',
-                       'editprotected',
-                       'gallery',
-                       'image',
-                       'lock',
-                       'mail',
-                       'mapmarker',
-                       'message',
-                       'messagenew',
-                       'messagescary',
-                       'move',
-                       'nowiki',
-                       'pagechecked',
-                       'pageribbon',
-                       'pagesearch',
-                       'print',
-                       'quotes',
-                       'search',
-                       'starmenu',
-                       'translate',
-                       'trash',
-                       'user'
-               ];
-               // if preset or other logical class name, just set class; we 
allow non-preset ones for on-wiki flexibility?
-               if ( $icon !== null && in_array( $icon, $iconsPreset ) ) {
-                       $class = Sanitizer::escapeClass( $icon );
-               } else {
-                       // Choose random class name using $icon value as seed
-                       $class = $iconsPreset[ hexdec( sha1( $icon )[0] ) % 27];
-               }
-
-               $colour = $this->getThemeColour();
-               if ( $colour == 'black' ) {
-                       $colorSuffix = '';
-               } else {
-                       $colorSuffix = '-' . $colour;
-               }
-
-               return Html::element( 'div', [ 'class' => 'mw-ckicon 
mw-ckicon-' . $class .  $colorSuffix ] );
+               return $toc->renderTOC( $this->content, $this->themeColour );
        }
 
        /**
@@ -737,34 +649,7 @@
         * @param string $seed fallback seed for explicitly something 
somethinged ones
         * @return string
         */
-       public function getParsedImage( $fallback = 'none', $size = 50, $seed = 
'' ) {
-               if ( $seed === '' ) {
-                       $image = $this->getImage();
-
-                       if ( $image == '' || $image == '-' ) {
-                               if ( $fallback == 'none' ) {
-                                       return '';
-                               } elseif ( $fallback == 'random' ) {
-                                       return $this->makeIcon( 
$this->getDisplayName() );
-                               } else {
-                                       // Maybe they want a specific one?
-                                       return $this->makeIcon( $fallback );
-                               }
-                       }
-                       if ( wfFindFile( $image ) ) {
-                               return Html::rawElement(
-                                       'div',
-                                       [ 'class' => 'file-image' ],
-                                       wfFindFile( $image )->transform( [ 
'width' => $size ] )->toHtml()
-                               );
-                       } else {
-                               return $this->makeIcon( $image );
-                       }
-               } else {
-                       // No image data etc; use seed
-                       return $this->makeIcon( $seed );
-               }
-
-               // TODO make it handle/return error/do something besides just 
selecting a random one when file doesn't exist/image key not found?
+       public function getParsedImage( $title, $image, $size = 200 ) {
+               return CollaborationKitIcon::makeIconOrImage ( 
$this->getImage(), $size, 'puzzlepiece' );
        }
 }
diff --git a/includes/content/CollaborationHubTOC.php 
b/includes/content/CollaborationHubTOC.php
new file mode 100644
index 0000000..8fb2ce6
--- /dev/null
+++ b/includes/content/CollaborationHubTOC.php
@@ -0,0 +1,221 @@
+<?php
+
+class CollaborationHubTOC {
+
+       /** @var $tocLinks array ids/links for ToC items that have been used 
already */
+       protected $tocLinks;
+
+       /**
+        * Get unique id for ToC Link/header
+        * @param $header
+        * @return string
+        */
+       public function getToCLinkID( $header ) {
+               $link = Sanitizer::escapeId( htmlspecialchars( $header ) );
+               $link2 = $link;
+               $linkCounter = 1;
+               while ( in_array( $link2, $this->tocLinks ) ) {
+                       $link2 = $link . '_' . $linkCounter;
+                       $spPageLinkCounter++;
+               }
+               $this->tocLinks[] = $link2;
+               return $link2;
+       }
+
+       public function resetToCLinks() {
+               $this->tocLinks = [];
+       }
+
+       public function __construct () {
+               $this->resetToCLinks();
+       }
+
+       /**
+        * ToC rendering for hub
+        * @param array $content block from collaborationhub
+        * @param string $colour variable from collaborationhub content
+        * @return string html
+        */
+       public function renderToC( $content, $colour ) {
+               global $wgParser;
+               $linkRenderer = $wgParser->getLinkRenderer();
+
+               $html = Html::openElement( 'div', [ 'class' => 
'wp-toc-container' ] );
+               $html .= Html::rawElement(
+                       'div',
+                       [ 'class' => 'toc-label' ],
+                       wfMessage( 'collaborationkit-hub-toc-label' 
)->inContentLanguage()->text()
+               );
+               $html .= Html::openElement( 'ul' );
+
+               foreach ( $content as $item ) {
+                       $title = Title::newFromText( $item['title'] );
+                       $rev = Revision::newFromTitle( $title );
+
+                       // TODO sanitise?
+                       if ( isset( $item['display_title'] ) ) {
+                               $displayTitle = $item['display_title'];
+                       } else {
+                               $displayTitle = $title->getSubpageText();
+                       }
+
+                       if ( isset( $item['image'] ) ) {
+                               $displayIcon = 
CollaborationKitIcon::makeIconOrImage( $item['image'], 50, $colour );
+                       } else {
+                               $displayIcon = 
CollaborationKitIcon::makeIconOrImage( $displayTitle, 50, $colour );
+                       }
+
+                       $linkTarget = Title::newFromText( '#' . 
$this->getToCLinkID( $displayTitle ) );
+                       $linkDisplay = new HtmlArmor( Html::rawElement(
+                               'div',
+                               [],
+                               $displayIcon . Html::element( 'span', [ 'class' 
=> 'item-label' ], $displayTitle )
+                       ) );
+                       $link = $linkRenderer->makeLink( $linkTarget, 
$linkDisplay );
+
+                       $html .= Html::rawElement(
+                               'li',
+                               [ 'class' => 'wp-toc-item' ],
+                               $link
+                       );
+               }
+
+               $html .= Html::closeElement( 'ul' );
+               $html .= Html::closeElement( 'div' );
+               return $html;
+       }
+
+       /**
+        * ToC rendering for non-hubs
+        * @param Title $title of hub the ToC is generated off
+        *
+        *
+        * @return string html
+        */
+       public function renderSubpageToC( $title ) {
+
+       }
+
+
+
+       // TOC stuff as was. This is going away.
+
+       /**
+        * Helper function for fillParserOutput; return HTML for a ToC.
+        * @param Title $title for target
+        * @param string $type: main or flat or stuff (used as css class)
+        * @return string|null
+        */
+       protected function generateToC( Title $title, ParserOutput &$output, 
$type = 'main' ) {
+               // TODO use correct version of text; support PREVIEWS as well 
as just pulling the content revision
+               $rev = Revision::newFromTitle( $title );
+               if ( isset( $rev ) ) {
+                       $sourceContent = $rev->getContent();
+                       $html = '';
+
+                       if ( $rev->getContentModel() == 
'CollaborationHubContent' ) {
+                               $ToCItems = [];
+
+                               // Add project mainpage to toc for subpages
+                               if ( $type != 'main' ) {
+
+                                       $display = Html::element(
+                                               'span',
+                                               [],
+                                               $sourceContent->getPageName()
+                                       );
+                                       $display = $sourceContent->getImage( 
'puzzlepiece', 40 ) . $display;
+
+                                       
$ToCItems[$sourceContent->getPageName()] = [
+                                               Html::rawElement(
+                                                       'span',
+                                                       [ 'class' => 
'wp-toc-projectlabel' ],
+                                                       wfMessage( 
'collaborationhub-toc-partof' )->inContentLanguage()->text()
+                                               ) . Linker::Link( $title, 
$display ),
+                                               'toc-mainpage'
+                                       ];
+                               }
+
+                               foreach ( $sourceContent->getContent() as $item 
) {
+                                       $spTitle = Title::newFromText( 
$item['item'] );
+                                       $spRev = Revision::newFromTitle( 
$spTitle );
+
+                                       if ( isset( $spRev ) ) {
+                                               $spContent = 
$spRev->getContent();
+                                               $spContentModel = 
$spRev->getContentModel();
+
+                                               $output->addTemplate( $spTitle, 
$spTitle->getArticleId(), $spRev->getId() );
+                                       } else {
+                                               $spContentModel = 'none';
+
+                                               $output->addTemplate( $spTitle, 
$spTitle->getArticleId(), null );
+                                       }
+
+                                       // Display name and #id
+                                       $item = $spContentModel == 
'CollaborationHubContent' ?
+                                               $spContent->getPageName() : 
$spTitle->getSubpageText();
+                                       $display = Html::element( 'span', [ 
'class' => 'item-label' ], $item );
+                                       while ( isset( $ToCItems[$item] ) ) {
+                                               // Already exists, add a 1 to 
the end to avoid duplicates
+                                               $item = $item . '1';
+                                       }
+
+                                       // Link
+                                       if ( $type != 'main' ) {
+                                               // TODO add 'selected' class if 
already on it
+                                               $link = $spTitle;
+                                       } else {
+                                               $link = Title::newFromText( '#' 
. htmlspecialchars( $item ) );
+                                       }
+
+                                       // Icon
+                                       if ( $spContentModel == 
'CollaborationHubContent' /* && image is set in $spContent */ ) {
+                                               $display = 
$spContent->getImage( 'random', 50 ) . $display;
+                                       } else {
+                                               // Use this one as a surrogate 
because it's not a real hub page; $link can act as seed
+                                               $display = $this->getImage( 
'random', 50, $item ) . $display;
+                                       }
+
+                                       $ToCItems[$item] = [ Linker::Link( 
$link, $display ), Sanitizer::escapeId( 'toc-' . $spTitle->getSubpageText() ) ];
+                               }
+                               $html .= Html::openElement( 'div', [ 'class' => 
'wp-toc' ] );
+
+                               if ( $type == 'main' ) {
+                                       $html .= Html::rawElement(
+                                               'div',
+                                               [ 'class' => 'toc-label' ],
+                                               wfMessage( 
'collaborationkit-toc-label' )->inContentLanguage()->text()
+                                       );
+                               }
+
+                               $html .= Html::openElement( 'ul' );
+
+                               foreach ( $ToCItems as $item => $linkJunk ) {
+                                       $html .= Html::rawElement(
+                                               'li',
+                                               [
+                                                       'class' => 'wp-toc-item 
' . $linkJunk[1] // id info
+                                               ],
+                                               $linkJunk[0] // link html string
+                                       );
+                               }
+                               $html .= Html::closeElement( 'ul' );
+                               $html .= '<div class="visualClear"></div>';
+                               $html .= Html::closeElement( 'div' );
+
+                               $html = Html::rawElement(
+                                       'div',
+                                       [ 'class' => 'wp-toc-container' ],
+                                       $html
+                               );
+                       } else {
+                               $html = 'Page not found, ToC not possible';
+                       }
+               } else {
+                       $html = '';
+               }
+
+               return $html;
+       }
+
+}
diff --git a/includes/content/CollaborationKitIcon.php 
b/includes/content/CollaborationKitIcon.php
new file mode 100644
index 0000000..85684d6
--- /dev/null
+++ b/includes/content/CollaborationKitIcon.php
@@ -0,0 +1,154 @@
+<?php
+
+class CollaborationKitIcon {
+
+       /**
+        * Generate an in icon based on an on-wiki file or a canned CK icon
+        * @param string $icon icon id, filename, or random seed
+        * @param int $size intended height/width for rendered icon in px
+        * @param string $fallback what to do for no icon; allowed values are 
'random', 'none', or a valid icon id
+        * @return string html
+        */
+       public static function makeIconOrImage( $icon, $size = 50, $colour = 
'black', $fallback = 'random' ) {
+               // We were going to only find files with file name extensions, 
but that's hard to parse, and there's no way to really handle ones that aren't 
uploaded, so we'll just look and see if they're uploaded and be done with it.
+               if ( wfFindFile( $icon ) ) {
+                       // TODO also find if prefixed with 'file:', 'image:', 
etc
+                       return CollaborationKitIcon::makeImage( $icon, $size );
+               } elseif ( $fallback == 'none' ) {
+                       return '';
+               } else {
+                       // canned icons time
+
+                       $iconsPreset = CollaborationKitIcon::getCannedIcons();
+
+                       if ( !in_array( $icon, $iconsPreset ) && in_array( 
$fallback, $iconsPreset ) ) {
+                               return CollaborationKitIcon::makeIcon( 
$fallback, $size, 'grey2', '#eee' );
+                       } else {
+                               // makeicon falls back to making a random icon 
anyway, and we've ruled out all the other fallbacks at this point
+                               return CollaborationKitIcon::makeIcon( $icon, 
$size, $colour );
+                       }
+               }
+       }
+
+       /**
+        * Generate an in icon using a canned CK icon
+        * @param string $icon icon id or random seed
+        * @param int $size intended height/width for rendered icon in px
+        * @param string $fallback what to do for no icon; allowed values are 
'random', 'none', or a valid icon id
+        * @return string html
+        */
+       public static function makeIcon(  $icon, $size = 50, $colour = 'black', 
$background = 'transparent' ) {
+               $iconsPreset = CollaborationKitIcon::getCannedIcons();
+
+               if ( in_array( $icon, $iconsPreset ) ) {
+                       $iconClass = Sanitizer::escapeClass( $icon );
+               } else {
+                       // Random time
+                       // Choose class name using $icon value as seed
+                       $iconClass = $iconsPreset[ hexdec( sha1( $icon )[0] ) % 
27];
+               }
+
+               if ( $colour == 'black' ) {
+                       $colorSuffix = '';
+               } else {
+                       $colorSuffix = '-' . $colour;
+               }
+               return Html::element(
+                       'div',
+                       [
+                               'class' => [
+                                       'mw-ckicon',
+                                       'mw-ckicon-' . $iconClass .  
$colorSuffix
+                               ],
+                               'css' => "height: {$size}px; width: {$size}px; 
background-color: $background;"
+                       ]
+               );
+       }
+
+       /**
+        * Make an image from a file onwiki
+        * Assumes the file exists, and this was already checked. Doesn't work 
if it doesn't.
+        * @param string $file filename
+        * @param int $size width, height in px
+        * @param string $background colour for optional css backgroundstuff
+        * @return string html
+        */
+       public static function makeImage( $file, $size = 50, $background = 
'transparent' ) {
+               return Html::rawElement(
+                       'div',
+                       [
+                               'class' => 'file-image',
+                               'css' => "max-height: {$size}px; 
background-color: $background;"
+                       ],
+                       wfFindFile( $file )->transform( [ 'width' => $size ] 
)->toHtml()
+               );
+       }
+
+       /**
+        * @return array of stupidly many icons
+        */
+       public static function getCannedIcons() {
+               // Keep this synced with the icons listed in the module in 
extension.json
+               return $iconsPreset = [
+                       // Randomly selectable items
+                       'book',
+                       'circlestar',
+                       'clock',
+                       'community',
+                       'contents',
+                       'die',
+                       'edit',
+                       'eye',
+                       'flag',
+                       'funnel',
+                       'gear',
+                       'heart',
+                       'journal',
+                       'key',
+                       'link',
+                       'map',
+                       'menu',
+                       'newspaper',
+                       'ol',
+                       'page',
+                       'paperclip',
+                       'puzzlepiece',
+                       'ribbon',
+                       'rocket',
+                       'star',
+                       'sun',
+                       'ul',
+
+                       'addimage',
+                       'addmapmarker',
+                       'addquote',
+                       'bell',
+                       'circleline',
+                       'circletriangle',
+                       'circlex',
+                       'discussion',
+                       'download',
+                       'editprotected',
+                       'gallery',
+                       'image',
+                       'lock',
+                       'mail',
+                       'mapmarker',
+                       'message',
+                       'messagenew',
+                       'messagescary',
+                       'move',
+                       'nowiki',
+                       'pagechecked',
+                       'pageribbon',
+                       'pagesearch',
+                       'print',
+                       'quotes',
+                       'search',
+                       'starmenu',
+                       'translate',
+                       'trash',
+                       'user'
+               ];
+       }
+}
diff --git a/modules/ext.CollaborationKit.hub.styles.less 
b/modules/ext.CollaborationKit.hub.styles.less
index cb3e99f..79dbb4b 100644
--- a/modules/ext.CollaborationKit.hub.styles.less
+++ b/modules/ext.CollaborationKit.hub.styles.less
@@ -5,14 +5,16 @@
 // ARGH
 .wp-toc {
        clear: both;
-       margin: 1em 0;
+       margin: 1em 0 2em;
 
        ul {
                padding: 0;
                margin: 0;
-               list-style: none;
        }
        li {
+               max-width: 7.5em;
+               text-align: center;
+               list-style: none;
                float: left;
                margin: .5em 1.25em .5em 0;
                word-wrap: break-word;
@@ -24,13 +26,28 @@
        }
 
        .file-image {
-               height: 40px;
+               height: 50px;
                overflow: hidden;
 
                img {
                        vertical-align: middle;
                }
        }
+       .toc-label {
+               font-weight: bold;
+               margin: 0 0 1em;
+               border-bottom: 3px solid;
+               width: 33%;
+       }
+       .mw-ckicon {
+               height: 50px;
+               width: 50px;
+       }
+}
+.mw-content-rtl .wp-toc ul,
+.mw-content-ltr .wp-toc ul {
+       margin: 0;
+       padding: 0;
 }
 
 // Mainpage hub layout (.mw-body included because vector has excessively 
specific rules)
@@ -86,30 +103,6 @@
        font-size: 115%;
 }
 
-.wp-toc {
-       ul {
-               list-style: none;
-       }
-       li {
-               max-width: 6em;
-               text-align: center;
-       }
-       .toc-label {
-               font-weight: bold;
-               margin: 0 0 1em;
-               border-bottom: 3px solid;
-               width: 33%;
-       }
-       .mw-ckicon {
-               height: 50px;
-               width: 50px;
-       }
-}
-.mw-content-rtl .wp-toc ul,
-.mw-content-ltr .wp-toc ul {
-       margin: 0;
-       padding: 0;
-}
 
 // Themes
 .mw-body .wp-mainpage {

-- 
To view, visit https://gerrit.wikimedia.org/r/311603
To unsubscribe, visit https://gerrit.wikimedia.org/r/settings

Gerrit-MessageType: newchange
Gerrit-Change-Id: I3126a963c603c2bd4ca38b0552eb52e14697eaa2
Gerrit-PatchSet: 1
Gerrit-Project: mediawiki/extensions/CollaborationKit
Gerrit-Branch: master
Gerrit-Owner: Isarra <zhoris...@gmail.com>

_______________________________________________
MediaWiki-commits mailing list
MediaWiki-commits@lists.wikimedia.org
https://lists.wikimedia.org/mailman/listinfo/mediawiki-commits

Reply via email to