diff --git a/h5p.classes.php b/h5p.classes.php index b003a27..90026b4 100644 --- a/h5p.classes.php +++ b/h5p.classes.php @@ -558,6 +558,16 @@ interface H5PFrameworkInterface { * Will trigger after the export file is created. */ public function afterExportCreated(); + + /** + * Check if user has permissions to an action + * + * @method hasPermission + * @param [H5PPermission] $permission Permission type, ref H5PPermission + * @param [int] $id Id need by platform to determine permission + * @return boolean + */ + public function hasPermission($permission, $id = NULL); } /** @@ -1669,6 +1679,20 @@ Class H5PExport { } } +abstract class H5PPermission { + const DOWNLOAD_H5P = 0; + const EMBED_H5P = 1; +} + +abstract class H5PDisplayOptionBehaviour { + const NEVER_SHOW = 0; + const CONTROLLED_BY_AUTHOR_DEFAULT_ON = 1; + const CONTROLLED_BY_AUTHOR_DEFAULT_OFF = 2; + const ALWAYS_SHOW = 3; + const CONTROLLED_BY_PERMISSIONS = 4; +} + + /** * Functions and storage shared by the other H5P classes */ @@ -1690,7 +1714,8 @@ class H5PCore { 'js/h5p-x-api-event.js', 'js/h5p-x-api.js', 'js/h5p-content-type.js', - 'js/h5p-confirmation-dialog.js' + 'js/h5p-confirmation-dialog.js', + 'js/h5p-action-bar.js' ); public static $adminScripts = array( 'js/jquery.js', @@ -1713,12 +1738,18 @@ class H5PCore { const DISABLE_COPYRIGHT = 8; const DISABLE_ABOUT = 16; + const DISPLAY_OPTION_FRAME = 'frame'; + const DISPLAY_OPTION_DOWNLOAD = 'export'; + const DISPLAY_OPTION_EMBED = 'embed'; + const DISPLAY_OPTION_COPYRIGHT = 'copyright'; + const DISPLAY_OPTION_ABOUT = 'icon'; + // Map flags to string public static $disable = array( - self::DISABLE_FRAME => 'frame', - self::DISABLE_DOWNLOAD => 'download', - self::DISABLE_EMBED => 'embed', - self::DISABLE_COPYRIGHT => 'copyright' + self::DISABLE_FRAME => self::DISPLAY_OPTION_FRAME, + self::DISABLE_DOWNLOAD => self::DISPLAY_OPTION_DOWNLOAD, + self::DISABLE_EMBED => self::DISPLAY_OPTION_EMBED, + self::DISABLE_COPYRIGHT => self::DISPLAY_OPTION_COPYRIGHT ); /** @@ -2442,54 +2473,152 @@ class H5PCore { } /** - * - */ - public function getGlobalDisable() { - $disable = self::DISABLE_NONE; - - // Allow global settings to override and disable options - if (!$this->h5pF->getOption('frame', TRUE)) { - $disable |= self::DISABLE_FRAME; - } - else { - if (!$this->h5pF->getOption('export', TRUE)) { - $disable |= self::DISABLE_DOWNLOAD; - } - if (!$this->h5pF->getOption('embed', TRUE)) { - $disable |= self::DISABLE_EMBED; - } - if (!$this->h5pF->getOption('copyright', TRUE)) { - $disable |= self::DISABLE_COPYRIGHT; - } - if (!$this->h5pF->getOption('icon', TRUE)) { - $disable |= self::DISABLE_ABOUT; - } - } - - return $disable; - } - - /** - * Determine disable state from sources. + * Create representation of display options as int * * @param array $sources * @param int $current * @return int */ - public function getDisable(&$sources, $current) { + public function getStorableDisplayOptions(&$sources, $current) { + // Download - force setting it if always on or always off + $download = $this->h5pF->getOption(self::DISPLAY_OPTION_DOWNLOAD, H5PDisplayOptionBehaviour::ALWAYS_SHOW); + if ($download == H5PDisplayOptionBehaviour::ALWAYS_SHOW || + $download == H5PDisplayOptionBehaviour::NEVER_SHOW) { + $sources[self::DISPLAY_OPTION_DOWNLOAD] = ($download == H5PDisplayOptionBehaviour::ALWAYS_SHOW); + } + + // Embed - force setting it if always on or always off + $embed = $this->h5pF->getOption(self::DISPLAY_OPTION_EMBED, H5PDisplayOptionBehaviour::ALWAYS_SHOW); + if ($embed == H5PDisplayOptionBehaviour::ALWAYS_SHOW || + $embed == H5PDisplayOptionBehaviour::NEVER_SHOW) { + $sources[self::DISPLAY_OPTION_EMBED] = ($embed == H5PDisplayOptionBehaviour::ALWAYS_SHOW); + } + foreach (H5PCore::$disable as $bit => $option) { - if ($this->h5pF->getOption(($bit & H5PCore::DISABLE_DOWNLOAD ? 'export' : $option), TRUE)) { - if (!isset($sources[$option]) || !$sources[$option]) { - $current |= $bit; // Disable - } - else { - $current &= ~$bit; // Enable - } + if (!isset($sources[$option]) || !$sources[$option]) { + $current |= $bit; // Disable + } + else { + $current &= ~$bit; // Enable } } return $current; } + /** + * Determine display options visibility and value on edit + * + * @param int $disable + * @return array + */ + public function getDisplayOptionsForEdit($disable = NULL) { + $display_options = []; + + $current_display_options = $disable === NULL ? [] : $this->getDisplayOptionsAsArray($disable); + + if ($this->h5pF->getOption(self::DISPLAY_OPTION_FRAME, TRUE)) { + $display_options[self::DISPLAY_OPTION_FRAME] = + isset($current_display_options[self::DISPLAY_OPTION_FRAME]) ? + $current_display_options[self::DISPLAY_OPTION_FRAME] : + TRUE; + + // Download + $export = $this->h5pF->getOption(self::DISPLAY_OPTION_DOWNLOAD, H5PDisplayOptionBehaviour::ALWAYS_SHOW); + if ($export == H5PDisplayOptionBehaviour::CONTROLLED_BY_AUTHOR_DEFAULT_ON || + $export == H5PDisplayOptionBehaviour::CONTROLLED_BY_AUTHOR_DEFAULT_OFF) { + $display_options[self::DISPLAY_OPTION_DOWNLOAD] = + isset($current_display_options[self::DISPLAY_OPTION_DOWNLOAD]) ? + $current_display_options[self::DISPLAY_OPTION_DOWNLOAD] : + ($export == H5PDisplayOptionBehaviour::CONTROLLED_BY_AUTHOR_DEFAULT_ON); + } + + // Embed + $embed = $this->h5pF->getOption(self::DISPLAY_OPTION_EMBED, H5PDisplayOptionBehaviour::ALWAYS_SHOW); + if ($embed == H5PDisplayOptionBehaviour::CONTROLLED_BY_AUTHOR_DEFAULT_ON || + $embed == H5PDisplayOptionBehaviour::CONTROLLED_BY_AUTHOR_DEFAULT_OFF) { + $display_options[self::DISPLAY_OPTION_EMBED] = + isset($current_display_options[self::DISPLAY_OPTION_EMBED]) ? + $current_display_options[self::DISPLAY_OPTION_EMBED] : + ($embed == H5PDisplayOptionBehaviour::CONTROLLED_BY_AUTHOR_DEFAULT_ON); + } + + // Copyright + if ($this->h5pF->getOption(self::DISPLAY_OPTION_COPYRIGHT, TRUE)) { + $display_options[self::DISPLAY_OPTION_COPYRIGHT] = + isset($current_display_options[self::DISPLAY_OPTION_COPYRIGHT]) ? + $current_display_options[self::DISPLAY_OPTION_COPYRIGHT] : + TRUE; + } + } + + return $display_options; + } + + /** + * Helper function used to figure out embed & download behaviour + * + * @param string $option_name + * @param H5PPermission $permission + * @param int $id + * @param bool &$value + */ + private function setDisplayOptionOverrides($option_name, $permission, $id, &$value) { + $behaviour = $this->h5pF->getOption($option_name, H5PDisplayOptionBehaviour::ALWAYS_SHOW); + // If never show globally, force hide + if ($behaviour == H5PDisplayOptionBehaviour::NEVER_SHOW) { + $value = false; + } + elseif ($behaviour == H5PDisplayOptionBehaviour::ALWAYS_SHOW) { + // If always show or permissions say so, force show + $value = true; + } + elseif ($behaviour == H5PDisplayOptionBehaviour::CONTROLLED_BY_PERMISSIONS) { + $value = $this->h5pF->hasPermission($permission, $id); + } + } + + /** + * Determine display option visibility when viewing H5P + * + * @param int $display_options + * @param int $id Might be content id or user id. + * Depends on what the platform needs to be able to determine permissions. + * @return array + */ + public function getDisplayOptionsForView($disable, $id) { + $display_options = $this->getDisplayOptionsAsArray($disable); + + if ($this->h5pF->getOption(self::DISPLAY_OPTION_FRAME, TRUE) == FALSE) { + $display_options[self::DISPLAY_OPTION_FRAME] = false; + } + else { + $this->setDisplayOptionOverrides(self::DISPLAY_OPTION_DOWNLOAD, H5PPermission::DOWNLOAD_H5P, $id, $display_options[self::DISPLAY_OPTION_DOWNLOAD]); + $this->setDisplayOptionOverrides(self::DISPLAY_OPTION_EMBED, H5PPermission::EMBED_H5P, $id, $display_options[self::DISPLAY_OPTION_EMBED]); + + if ($this->h5pF->getOption(self::DISPLAY_OPTION_COPYRIGHT, TRUE) == FALSE) { + $display_options[self::DISPLAY_OPTION_COPYRIGHT] = false; + } + } + + return $display_options; + } + + /** + * Convert display options as single byte to array + * + * @param int $disable + * @return array + */ + private function getDisplayOptionsAsArray($disable) { + return array( + self::DISPLAY_OPTION_FRAME => !($disable & H5PCore::DISABLE_FRAME), + self::DISPLAY_OPTION_DOWNLOAD => !($disable & H5PCore::DISABLE_DOWNLOAD), + self::DISPLAY_OPTION_EMBED => !($disable & H5PCore::DISABLE_EMBED), + self::DISPLAY_OPTION_COPYRIGHT => !($disable & H5PCore::DISABLE_COPYRIGHT), + self::DISPLAY_OPTION_ABOUT => $this->h5pF->getOption(self::DISPLAY_OPTION_ABOUT, TRUE), + ); + } + /** * Small helper for getting the library's ID. * @@ -3151,7 +3280,6 @@ class H5PContentValidator { break; } } - // Using a library in content that is not present at all in semantics if ($message === NULL) { $message = $this->h5pF->t('The H5P library %library used in the content is not valid', array( diff --git a/js/disable.js b/js/disable.js deleted file mode 100644 index 0bfbb07..0000000 --- a/js/disable.js +++ /dev/null @@ -1,19 +0,0 @@ -(function ($) { - $(document).ready(function () { - var $inputs = $('.h5p-action-bar-settings input'); - var $frame = $inputs.filter('input[name="frame"], input[name="h5p_frame"]'); - var $others = $inputs.filter(':not(input[name="frame"], input[name="h5p_frame"])'); - - var toggle = function () { - if ($frame.is(':checked')) { - $others.attr('disabled', false); - } - else { - $others.attr('disabled', true); - } - }; - - $frame.change(toggle); - toggle(); - }); -})(H5P.jQuery); diff --git a/js/h5p-action-bar.js b/js/h5p-action-bar.js new file mode 100644 index 0000000..8e34eb7 --- /dev/null +++ b/js/h5p-action-bar.js @@ -0,0 +1,89 @@ +H5P.ActionBar = (function ($, EventDispatcher) { + "use strict"; + + function ActionBar(displayOptions) { + EventDispatcher.call(this); + + var self = this; + + var hasActions = false; + + // Create action bar + var $actions = H5P.jQuery('