Werdna has uploaded a new change for review.

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

Change subject: WIP: "Smoke test" at Special:OOUIDemo
......................................................................

WIP: "Smoke test" at Special:OOUIDemo

Includes support for calling OOUIPlayground from templates.

Change-Id: Ia4c101567d1adef5c6cdc89b2ec0ed884fed73e7
---
M OOUIPlayground.php
M autoload.php
M i18n/en.json
A includes/ContainerAccess.php
A includes/OOUILightNCandy.php
M includes/ParserHooks.php
A includes/SpecialOOUIDemo.php
M includes/WidgetInfo.php
M includes/container.php
A templates/demo.template
A templates/used_widgets.template
11 files changed, 295 insertions(+), 26 deletions(-)


  git pull ssh://gerrit.wikimedia.org:29418/mediawiki/extensions/OOUIPlayground 
refs/changes/66/190466/1

diff --git a/OOUIPlayground.php b/OOUIPlayground.php
index 13707ce..13aef20 100644
--- a/OOUIPlayground.php
+++ b/OOUIPlayground.php
@@ -43,6 +43,8 @@
 
 $wgMessagesDirs['OOUIPlayground'] = __DIR__ . '/i18n';
 
+$wgSpecialPages['OOUIDemo'] = 'SpecialOOUIDemo';
+
 $dir = dirname( __FILE__ );
 
 require_once __DIR__ . "/autoload.php";
diff --git a/autoload.php b/autoload.php
index 6ee40ca..ba471dd 100644
--- a/autoload.php
+++ b/autoload.php
@@ -1,5 +1,5 @@
 <?php
-// This file is generated by 
/Users/andrew/wm-dev/vagrant/mediawiki/extensions/OOUIPlayground, do not adjust 
manually
+// This file is generated by /vagrant/mediawiki/extensions/OOUIPlayground, do 
not adjust manually
 
 global $wgAutoloadClasses;
 
@@ -7,6 +7,7 @@
        'OOUIPlayground\\ArgumentFilterGroup' => __DIR__ . 
'/includes/argument-filters/ArgumentFilter.php',
        'OOUIPlayground\\ArgumentFilterInterface' => __DIR__ . 
'/includes/argument-filters/ArgumentFilter.php',
        'OOUIPlayground\\ConfiguredCodeRenderer' => __DIR__ . 
'/includes/CodeRenderer.php',
+       'OOUIPlayground\\Container' => __DIR__ . 
'/includes/ContainerAccess.php',
        'OOUIPlayground\\GeSHICodeRenderer' => __DIR__ . 
'/includes/CodeRenderer.php',
        'OOUIPlayground\\GroupElementFilter' => __DIR__ . 
'/includes/argument-filters/GroupElementFilter.php',
        'OOUIPlayground\\ICodeRenderer' => __DIR__ . 
'/includes/CodeRenderer.php',
@@ -18,6 +19,8 @@
        'OOUIPlayground\\NoSuchWidgetException' => __DIR__ . 
'/includes/WidgetInfo.php',
        'OOUIPlayground\\NoTypeGiven' => __DIR__ . 
'/includes/WidgetFactory.php',
        'OOUIPlayground\\NullCodeRenderer' => __DIR__ . 
'/includes/CodeRenderer.php',
+       'OOUIPlayground\\OOUILightNCandy' => __DIR__ . 
'/includes/OOUILightNCandy.php',
+       'OOUIPlayground\\OOUIStatic' => __DIR__ . 
'/includes/OOUILightNCandy.php',
        'OOUIPlayground\\ParserHooks' => __DIR__ . '/includes/ParserHooks.php',
        'OOUIPlayground\\PreCodeRenderer' => __DIR__ . 
'/includes/CodeRenderer.php',
        'OOUIPlayground\\WidgetDocumenter' => __DIR__ . 
'/includes/WidgetDocumenter.php',
@@ -27,4 +30,5 @@
        'OOUI\\DeferredWidget' => __DIR__ . '/includes/DeferredWidget.php',
        'OOUI\\MockGroupWidget' => __DIR__ . 
'/tests/phpunit/mocks/MockWidget.php',
        'OOUI\\MockWidget' => __DIR__ . '/tests/phpunit/mocks/MockWidget.php',
+       'SpecialOOUIDemo' => __DIR__ . '/includes/SpecialOOUIDemo.php',
 );
diff --git a/i18n/en.json b/i18n/en.json
index 86b239f..8c0c34e 100644
--- a/i18n/en.json
+++ b/i18n/en.json
@@ -5,5 +5,6 @@
        "ooui-playground-language-php" : "PHP",
        "ooui-playground-language-javascript" : "JavaScript",
        "ooui-playground-error-no-type" : "You must specify a type",
-       "ooui-playground-error-bad-type" : "There is no type called '$1'"
+       "ooui-playground-error-bad-type" : "There is no type called '$1'",
+       "oouidemo" : "OOJS-UI Demo"
 }
\ No newline at end of file
diff --git a/includes/ContainerAccess.php b/includes/ContainerAccess.php
new file mode 100644
index 0000000..24fd8d8
--- /dev/null
+++ b/includes/ContainerAccess.php
@@ -0,0 +1,20 @@
+<?php
+
+namespace OOUIPlayground;
+
+class Container {
+       protected static $container;
+
+       /**
+        * Gets an object from the container.
+        * @param  string $obj The object to get
+        * @return mixed|null   That section in config.php, or null if it does 
not exist.
+        */
+       public static function get( $obj ) {
+               if ( self::$container === null ) {
+                       self::$container = require __DIR__ . '/container.php';
+               }
+
+               return self::$container[$obj];
+       }
+}
\ No newline at end of file
diff --git a/includes/OOUILightNCandy.php b/includes/OOUILightNCandy.php
new file mode 100644
index 0000000..db30d35
--- /dev/null
+++ b/includes/OOUILightNCandy.php
@@ -0,0 +1,138 @@
+<?php
+
+namespace OOUIPlayground;
+
+use FormatJson;
+use LightnCandy;
+use OOUI\MediaWikiTheme;
+use OOUI\Theme;
+use SimpleLightNCandy;
+
+class OOUILightNCandy extends SimpleLightNCandy {
+       protected $widgetRepo;
+       protected $widgetFactory;
+
+       function __construct( WidgetRepository $repo = null, WidgetFactory 
$factory = null, $dir ) {
+               parent::__construct( $dir );
+               $this->widgetRepo = $repo;
+               $this->widgetFactory = $factory;
+
+               $this->setupHelpers();
+       }
+
+       public function renderTemplate( $templateName, array $input ) {
+               Theme::setSingleton( new MediaWikiTheme );
+
+               OOUIStatic::overrideFactory( $this->widgetFactory );
+               OOUIStatic::overrideRepository( $this->widgetRepo );
+               $output = parent::renderTemplate( $templateName, $input );
+               OOUIStatic::clearOverrides();
+               return $output;
+       }
+
+       protected function setupHelpers() {
+               $this->addHBHelper( 'ooui',
+                       function( $context, array $options ) {
+                               return OOUIPlayground\OOUIStatic::oouiHelper( 
$context, $options );
+                       }
+               );
+       }
+
+       protected function getCompileOptions() {
+               $options = parent::getCompileOptions();
+
+               $options['flags'] ^= LightnCandy::FLAG_MUSTACHE;
+               $options['flags'] |= LightnCandy::FLAG_HANDLEBARSJS;
+
+               return $options;
+       }
+}
+
+/**
+ * It's not possible to pass the WidgetRepo or WidgetFactory into a 
LightNCandy template,
+ * by design. So this is a hack we're using to get things working. It's 
probably the wrong
+ * way to approach the problem but it works for now.
+ */
+abstract class OOUIStatic {
+       protected static $overrideRepo = null;
+       protected static $overrideFactory = null;
+
+       public static function oouiHelper( $context, array $options ) {
+               $widgetName = $context;
+
+               $widgetInfo = self::getRepo()->getInfo( $widgetName );
+               $params = self::getParams( $widgetInfo, $options );
+               if ( isset( $params['render'] ) && $params['render'] === 'json' 
) {
+                       unset( $params['render'] );
+                       $params['type'] = $widgetInfo->getType();
+                       return array( FormatJson::encode( $params ) . ',', 
'raw' );
+               } else {
+                       $widget = self::getFactory()->getWidget( $widgetInfo, 
$params );
+
+                       return array( $widget->__toString(), 'raw' );
+               }
+       }
+
+       public static function getParams( WidgetInfo $widgetInfo, array 
$options ) {
+               $params = array();
+
+               foreach( $options['hash'] as $key => $value ) {
+                       if ( substr( $key, -strlen( '_json' ) ) === '_json' ) {
+                               $params[substr( $key, 0, -strlen( '_json' ) )] 
= FormatJson::encode( $value );
+                       } elseif ( substr( $key, -strlen( '_list' ) ) === 
'_list' ) {
+                               $params[substr( $key, 0, -strlen( '_list' ) )] 
= explode( ' ', $value );
+                       } else {
+                               $params[$key] = $value;
+                       }
+               }
+
+               // Handle contents if relevant
+               if ( isset( $options['fn'] ) ) {
+                       $contentMode = $widgetInfo->getContentMode();
+                       $contentVar = $widgetInfo->getContentVar();
+
+                       if ( $contentMode === 'var' ) {
+                               $params[$contentVar] = $options['fn']( array() 
);
+                       } elseif ( $contentMode === 'group' ) {
+                               $input = $options['fn']( array( '_ooui_mode' => 
'groupelement' ) );
+                               $input = trim( $input );
+                               $input = rtrim( $input, ',' );
+                               $input = "[$input]";
+                               $input = FormatJson::decode( $input, true );
+
+                               $params[$contentVar] = $input;
+                       }
+               }
+
+               return $params;
+       }
+
+       public static function overrideRepository( WidgetRepository $repo = 
null ) {
+               self::$overrideRepo = $repo;
+       }
+
+       public static function overrideFactory( WidgetFactory $factory = null ) 
{
+               self::$overrideFactory = $factory;
+       }
+
+       public static function clearOverrides() {
+               self::overrideRepository( null );
+               self::overrideFactory( null );
+       }
+
+       protected static function getRepo() {
+               if ( self::$overrideRepo !== null ) {
+                       return self::$overrideRepo;
+               } else {
+                       return Container::get( 'widgetRepository' );
+               }
+       }
+
+       protected static function getFactory() {
+               if ( self::$overrideFactory !== null ) {
+                       return self::$overrideFactory;
+               } else {
+                       return Container::get( 'widgetFactory' );
+               }
+       }
+}
diff --git a/includes/ParserHooks.php b/includes/ParserHooks.php
index 79d3916..3ef509f 100755
--- a/includes/ParserHooks.php
+++ b/includes/ParserHooks.php
@@ -13,8 +13,6 @@
 use Status;
 
 class ParserHooks {
-       protected static $container = null;
-
        /**
         * Handler for ParserFirstCallInit hook
         * @param  Parser $parser Parser to initialise
@@ -28,19 +26,6 @@
        }
 
        /**
-        * Gets an object from the container.
-        * @param  string $obj The object to get
-        * @return mixed|null   That section in config.php, or null if it does 
not exist.
-        */
-       protected static function getContainer( $obj ) {
-               if ( self::$container === null ) {
-                       self::$container = require __DIR__ . '/container.php';
-               }
-
-               return self::$container[$obj];
-       }
-
-       /**
         * Does any initialisation necessary to get OOUI to work.
         */
        protected static function setupOOUI() {
@@ -51,6 +36,15 @@
                }
        }
 
+       /**
+        * Gets an object from the container.
+        * @param  string $obj The object to get
+        * @return mixed|null   That section in config.php, or null if it does 
not exist.
+        */
+       protected static function getContainer( $obj ) {
+               return Container::get( $obj );
+       }
+
        public static function renderDoc( $input, array $args, Parser $parser, 
PPFrame $frame ) {
                $classStatus = self::getWidgetFromAttributes( $args );
 
diff --git a/includes/SpecialOOUIDemo.php b/includes/SpecialOOUIDemo.php
new file mode 100644
index 0000000..5fe1350
--- /dev/null
+++ b/includes/SpecialOOUIDemo.php
@@ -0,0 +1,70 @@
+<?php
+
+use OOUI\Widget;
+use OOUIPlayground\Container;
+use OOUIPlayground\GroupElementFilter;
+use OOUIPlayground\OOUILightNCandy;
+use OOUIPlayground\WidgetFactory;
+use OOUIPlayground\WidgetInfo;
+
+class SpecialOOUIDemo extends SpecialPage {
+       function __construct() {
+               parent::__construct( 'OOUIDemo' );
+       }
+
+       function execute( $par ) {
+               $this->setHeaders();
+
+               $this->getOutput()->addModules( array( 'oojs-ui' ) );
+               $this->getOutput()->addModuleStyles( array( 'oojs-ui.styles' ) 
);
+
+               $widgetRepository = Container::get( 'widgetRepository' );
+               $widgetFactory = new RecordingWidgetFactory( $widgetRepository 
);
+               $widgetFactory->addFilter( new GroupElementFilter( 
$widgetFactory ) );
+               $templating = new OOUILightNCandy( null /* default repo */, 
$widgetFactory, __DIR__ . "/../templates" );
+
+               $output = $this->getContext()->getOutput();
+
+               $output->addHTML( $templating->renderTemplate( 'demo', 
array('foo' => 'bar') ) );
+               $output->addHTML(
+                       $templating->renderTemplate(
+                               'used_widgets',
+                               array( 'used' => 
$widgetFactory->getUsedWidgets() )
+                       )
+               );
+       }
+}
+
+/** @todo Would be nice to be a Decorator instead of a whole new subclass */
+class RecordingWidgetFactory extends WidgetFactory {
+       protected $createdWidgets = array();
+
+       public function getWidget( WidgetInfo $info, array $args ) {
+               $output = parent::getWidget( $info, $args );
+
+               $this->recordWidget( $info, $output );
+
+               return $output;
+       }
+
+       public function getUsedWidgets() {
+               return array_keys( array_filter( $this->createdWidgets ) );
+       }
+
+       protected function recordWidget( WidgetInfo $info, Widget $widget ) {
+               $typesCreated = array( $info->getFullClassName() );
+
+               $reflection = $info->getReflection()->getParentClass();
+               while( $reflection ) {
+                       $typesCreated[] = $reflection->getName();
+                       $reflection = $reflection->getParentClass();
+               }
+
+               $typesCreated = array_merge( $typesCreated, $info->getMixins() 
);
+
+               $this->createdWidgets = array_merge(
+                       $this->createdWidgets,
+                       array_fill_keys( $typesCreated, true )
+               );
+       }
+}
\ No newline at end of file
diff --git a/includes/WidgetInfo.php b/includes/WidgetInfo.php
index efc1f15..e764aef 100644
--- a/includes/WidgetInfo.php
+++ b/includes/WidgetInfo.php
@@ -21,13 +21,7 @@
         * (cannot be used with new because it's in the wrong namespace)
         */
        public function getClassName( $type ) {
-               $type = strtolower( $type );
-
-               if ( ! isset( $this->classMap[$type] ) ) {
-                       throw new NoSuchWidgetException( $type );
-               } else {
-                       return $this->classMap[$type]['class'];
-               }
+               return $this->getInfo( $type )['className'];
        }
 
        /**
@@ -37,10 +31,12 @@
         * @return WidgetInfo
         */
        public function getInfo( $type ) {
-               $className = $this->getClassName( $type );
+               $type = strtolower( $type );
 
-               if ( $className ) {
+               if ( isset( $this->classMap[$type] ) ) {
                        return new WidgetInfo( $type, $this->classMap[$type] );
+               } else {
+                       throw new NoSuchWidgetException( $type );
                }
        }
 }
@@ -128,6 +124,18 @@
                return 'OOUI\\' . $this->className;
        }
 
+       public function getContentMode() {
+               return $this->getAttribute( 'contentMode' ) ?: 'var';
+       }
+
+       public function getContentVar() {
+               return $this->getAttribute( 'contentVar' ) ?: 'content';
+       }
+
+       protected function getAttribute( $name ) {
+               return isset( $this->classInfo[$name] ) ? 
$this->classInfo[$name] : null;
+       }
+
        /**
         * Get an instance of the OOUI-PHP class
         * Only for internal use, outside this class
diff --git a/includes/container.php b/includes/container.php
index 462fec9..be6abcf 100644
--- a/includes/container.php
+++ b/includes/container.php
@@ -11,12 +11,16 @@
 $container['classMap'] = array(
        'buttongroup' => array(
                'class' => 'ButtonGroupWidget',
+               'contentMode' => 'group',
+               'contentVar' => 'items',
        ),
        'buttoninput' => array(
                'class' => 'ButtonInputWidget',
+               'contentVar' => 'label',
        ),
        'button' => array(
                'class' => 'ButtonWidget',
+               'contentVar' => 'label',
        ),
        'checkboxinput' => array(
                'class' => 'CheckboxInputWidget',
@@ -32,6 +36,7 @@
        ),
        'label' => array(
                'class' => 'LabelWidget',
+               'contentVar' => 'label',
        ),
        'radioinput' => array(
                'class' => 'RadioInputWidget',
diff --git a/templates/demo.template b/templates/demo.template
new file mode 100644
index 0000000..ef3408a
--- /dev/null
+++ b/templates/demo.template
@@ -0,0 +1,21 @@
+{{#with "testctx"}}
+<h3>Labels</h3>
+<p>Normal labels:<br/>
+{{#ooui "label"}}
+This is my test template.
+{{/ooui}}
+</p>
+
+<p>Labels with icons:<br/>
+{{ooui "icon" iconTitle="Add" icon="add"}} {{#ooui "label"}}Add{{/ooui}}
+</p>
+
+<h3>Buttons</h3>
+
+{{#ooui "buttongroup"}}
+{{#ooui "button" render="json"}}Test button{{/ooui}}
+{{#ooui "button" flags_list="progressive primary" render="json"}}Progressive 
primary{{/ooui}}
+{{#ooui "button" flags_list="destructive primary" render="json"}}Destructive 
primary{{/ooui}}
+{{#ooui "button" flags_list="constructive" render="json"}}Constructive{{/ooui}}
+{{/ooui}}
+{{/with}}
diff --git a/templates/used_widgets.template b/templates/used_widgets.template
new file mode 100644
index 0000000..a6b1183
--- /dev/null
+++ b/templates/used_widgets.template
@@ -0,0 +1,6 @@
+<p>The following widgets were used in generating this demo:</p>
+<ul>
+{{#each used}}
+       <li>{{.}}</li>
+{{/each}}
+</ul>
\ No newline at end of file

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

Gerrit-MessageType: newchange
Gerrit-Change-Id: Ia4c101567d1adef5c6cdc89b2ec0ed884fed73e7
Gerrit-PatchSet: 1
Gerrit-Project: mediawiki/extensions/OOUIPlayground
Gerrit-Branch: master
Gerrit-Owner: Werdna <agarr...@wikimedia.org>

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

Reply via email to