3 +--------------------------------------------------------------------+
4 | CiviCRM version 4.6 |
5 +--------------------------------------------------------------------+
6 | Copyright CiviCRM LLC (c) 2004-2014 |
7 +--------------------------------------------------------------------+
8 | This file is a part of CiviCRM. |
10 | CiviCRM is free software; you can copy, modify, and distribute it |
11 | under the terms of the GNU Affero General Public License |
12 | Version 3, 19 November 2007 and the CiviCRM Licensing Exception. |
14 | CiviCRM is distributed in the hope that it will be useful, but |
15 | WITHOUT ANY WARRANTY; without even the implied warranty of |
16 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. |
17 | See the GNU Affero General Public License for more details. |
19 | You should have received a copy of the GNU Affero General Public |
20 | License and the CiviCRM Licensing Exception along |
21 | with this program; if not, contact CiviCRM LLC |
22 | at info[AT]civicrm[DOT]org. If you have questions about the |
23 | GNU Affero General Public License or the licensing of CiviCRM, |
24 | see the CiviCRM license FAQ at http://civicrm.org/licensing |
25 +--------------------------------------------------------------------+
29 * The core concept of the system is an action performed on an object. Typically this will be a "data model" object
30 * as specified in the API specs. We attempt to keep the number and type of actions consistent
31 * and similar across all objects (thus providing both reuse and standards)
34 * @copyright CiviCRM LLC (c) 2004-2014
38 class CRM_Core_Action
{
41 * Different possible actions are defined here. Keep in sync with the
42 * constant from CRM_Core_Form for various modes.
71 //make sure MAX_ACTION = 2^n - 1 ( n = total number of actions )
74 * Map the action names to the relevant constant. We perform
75 * bit manipulation operations so we can perform multiple
76 * actions on the same object if needed
78 * @var array $_names type of variable name to action constant
83 static $_names = array(
85 'update' => self
::UPDATE
,
87 'delete' => self
::DELETE
,
88 'browse' => self
::BROWSE
,
89 'enable' => self
::ENABLE
,
90 'disable' => self
::DISABLE
,
91 'export' => self
::EXPORT
,
92 'preview' => self
::PREVIEW
,
95 'profile' => self
::PROFILE
,
96 'renew' => self
::RENEW
,
97 'detach' => self
::DETACH
,
98 'revert' => self
::REVERT
,
99 'close' => self
::CLOSE
,
100 'reopen' => self
::REOPEN
,
104 * The flipped version of the names array, initialized when used
109 static $_description;
112 * Called by the request object to translate a string into a mask
114 * @param string $str the action to be resolved
116 * @return int the action mask corresponding to the input string
119 public static function resolve($str) {
122 $items = explode('|', $str);
123 $action = self
::map($items);
129 * Given a string or an array of strings, determine the bitmask
130 * for this set of actions
132 * @param mixed $item either a single string or an array of strings
134 * @return int the action mask corresponding to the input args
138 public static function map($item) {
141 if (is_array($item)) {
142 foreach ($item as $it) {
143 $mask |
= self
::mapItem($it);
148 return self
::mapItem($item);
153 * Given a string determine the bitmask for this specific string
155 * @param string $item the input action to process
157 * @return int the action mask corresponding to the input string
161 public static function mapItem($item) {
162 $mask = CRM_Utils_Array
::value(trim($item), self
::$_names);
163 return $mask ?
$mask : 0;
168 * Given an action mask, find the corresponding description
170 * @param int $mask the action mask
172 * @return string the corresponding action description
176 public static function description($mask) {
177 if (!isset($_description)) {
178 self
::$_description = array_flip(self
::$_names);
181 return CRM_Utils_Array
::value($mask, self
::$_description, 'NO DESCRIPTION SET');
185 * Given a set of links and a mask, return the html action string for
186 * the links associated with the mask
188 * @param array $links the set of link items
189 * @param int $mask the mask to be used. a null mask means all items
190 * @param array $values the array of values for parameter substitution in the link items
191 * @param string $extraULName enclosed extra links in this UL.
192 * @param boolean $enclosedAllInSingleUL force to enclosed all links in single UL.
195 * @param null $objectName
196 * @param int $objectId
198 * @return string the html string
201 static function formLink($links,
204 $extraULName = 'more',
205 $enclosedAllInSingleUL = FALSE,
210 $config = CRM_Core_Config
::singleton();
215 // make links indexed sequentially instead of by bitmask
216 // otherwise it's next to impossible to reliably add new ones
218 foreach ($links as $bit => $link) {
223 if ($op && $objectName && $objectId) {
224 CRM_Utils_Hook
::links($op, $objectName, $objectId, $seqLinks, $mask, $values);
229 foreach ($seqLinks as $i => $link) {
230 if (!$mask ||
!array_key_exists('bit', $link) ||
($mask & $link['bit'])) {
231 $extra = isset($link['extra']) ? self
::replace($link['extra'], $values) : NULL;
233 $frontend = (isset($link['fe'])) ?
TRUE : FALSE;
235 if (isset($link['qs']) && !CRM_Utils_System
::isNull($link['qs'])) {
236 $urlPath = CRM_Utils_System
::url(self
::replace($link['url'], $values),
237 self
::replace($link['qs'], $values), TRUE, NULL, TRUE, $frontend
241 $urlPath = CRM_Utils_Array
::value('url', $link, '#');
244 $classes = 'action-item crm-hover-button';
245 if (isset($link['ref'])) {
246 $classes .= ' ' . strtolower($link['ref']);
249 //get the user specified classes in.
250 if (isset($link['class'])) {
251 $className = is_array($link['class']) ?
implode(' ', $link['class']) : $link['class'];
252 $classes .= ' ' . strtolower($className);
255 if ($urlPath !== '#' && $frontend) {
256 $extra .= ' target="_blank"';
258 // Hack to make delete dialogs smaller
259 if (strpos($urlPath, '/delete') ||
strpos($urlPath, 'action=delete')) {
260 $classes .= " small-popup";
262 $url[] = sprintf('<a href="%s" class="%s" %s' . $extra . '>%s</a>',
265 !empty($link['title']) ?
"title='{$link['title']}' " : '',
273 if ($enclosedAllInSingleUL) {
275 CRM_Utils_String
::append($allLinks, '</li><li>', $mainLinks);
276 $allLinks = "{$extraULName}<ul class='panel'><li>{$allLinks}</li></ul>";
277 $result = "<span class='btn-slide crm-hover-button'>{$allLinks}</span>";
281 $extraLinks = array_splice($url, 2);
282 if (count($extraLinks) > 1) {
283 $mainLinks = array_slice($url, 0, 2);
284 CRM_Utils_String
::append($extra, '</li><li>', $extraLinks);
285 $extra = "{$extraULName}<ul class='panel'><li>{$extra}</li></ul>";
288 CRM_Utils_String
::append($resultLinks, '', $mainLinks);
290 $result = "<span>{$resultLinks}</span><span class='btn-slide crm-hover-button'>{$extra}</span>";
293 $result = "<span>{$resultLinks}</span>";
301 * Given a string and an array of values, substitute the real values
302 * in the placeholder in the str in the CiviCRM format
304 * @param string $str the string to be replaced
305 * @param array $values the array of values for parameter substitution in the str
307 * @return string the substituted string
310 public static function &replace(&$str, &$values) {
311 foreach ($values as $n => $v) {
312 $str = str_replace("%%$n%%", $v, $str);
318 * Get the mask for a permission (view, edit or null)
320 * @param string the permission
322 * @return int the mask for the above permission
325 public static function mask($permissions) {
327 if (!is_array($permissions) || CRM_Utils_System
::isNull($permissions)) {
330 //changed structure since we are handling delete separately - CRM-4418
331 if (in_array(CRM_Core_Permission
::VIEW
, $permissions)) {
332 $mask |
= self
::VIEW | self
::EXPORT | self
::BASIC | self
::ADVANCED | self
::BROWSE | self
::MAP | self
::PROFILE
;
334 if (in_array(CRM_Core_Permission
::DELETE
, $permissions)) {
335 $mask |
= self
::DELETE
;
337 if (in_array(CRM_Core_Permission
::EDIT
, $permissions)) {
338 //make sure we make self::MAX_ACTION = 2^n - 1
339 //if we add more actions; ( n = total number of actions )
340 $mask |
= (self
::MAX_ACTION
& ~self
::DELETE
);