View source
<?php
define('PM_ICON_SET_DEFAULT_BEHAVIOUR', 'default');
define('PM_ICON_SET_FONTAWESOME', 'fontawesome');
define('PM_ICON_SET_STORM', 'storm');
define('PM_ICON_SET_NO_ICON', 'none');
define('PM_CONTEXTUAL_LINK_PSEUDO_FIELD', 'pm_contextual_link');
define('PM_FONTAWESOME_DISABLED', 0x0);
define('PM_FONTAWESOME_LIBRARY_ENABLED', 0x1);
define('PM_FONTAWESOME_MODULE_ENABLED', 0x2);
define('PM_FONTAWESOME_ENABLED', PM_FONTAWESOME_LIBRARY_ENABLED | PM_FONTAWESOME_MODULE_ENABLED);
module_load_include('inc', 'pm', 'includes/pm.permission');
function pm_help($path, $arg) {
$output = '';
switch ($path) {
case "admin/help#pm":
$output = '<p>' . t("Provides a complete project management environment") . '</p>';
break;
case 'admin/help#pm-permission':
return '<p>' . t('PM Permission allows you to grant access to content based on interactions with Drupal PM.') . '</p>';
}
return $output;
}
function pm_permission() {
$permissions = array(
'administer pm permission' => array(
'title' => t('Administer Project Management Permission'),
'restrict access' => TRUE,
),
);
foreach (pm_permission_get_enabled_types() as $bundle_name) {
$permissions += pm_permission_permission_per_bundle($bundle_name);
}
$permissions += array(
'Project Management: access dashboard' => array(
'title' => t('Access Dashboard'),
'description' => t('Allows the user to access the Project Management dashboard. The items included on the dashboard are set through permissions on the individual modules that provide those links.'),
),
'Project Management: access administration pages' => array(
'title' => t('Administer Project Management'),
'description' => t('Allow the user to perform administrative tasks on Project Management modules, such as altering configuration.'),
),
);
return $permissions;
}
function pm_menu() {
$items = array();
$items['pm'] = array(
'title' => 'Project Management',
'description' => 'Access various components of <em>Project Management</em>',
'page callback' => 'pm_page_front',
'access arguments' => array(
'Project Management: access dashboard',
),
'type' => MENU_NORMAL_ITEM,
'file' => 'includes/pm.pages.inc',
);
$items['admin/config/pm'] = array(
'title' => 'Project Management',
'description' => 'Project Management settings',
'page callback' => 'system_admin_menu_block_page',
'access arguments' => array(
'Project Management: access administration pages',
),
'file' => 'system.admin.inc',
'file path' => drupal_get_path('module', 'system'),
);
$items['admin/config/pm/pm'] = array(
'title' => 'General Settings',
'description' => 'Configure <em>Project Management</em> behaviour across components.',
'page callback' => 'drupal_get_form',
'page arguments' => array(
'pm_admin_settings',
),
'access arguments' => array(
'Project Management: access administration pages',
),
'weight' => -100,
'file' => 'pm.settings.inc',
'file path' => drupal_get_path('module', 'pm') . '/includes',
);
$items['admin/config/pm/pm/basic'] = array(
'title' => 'Basic Settings',
'type' => MENU_DEFAULT_LOCAL_TASK,
);
$items['admin/config/pm/pm/permissions'] = array(
'title' => 'Permissions',
'description' => 'Configure access controls based on PM fields.',
'type' => MENU_LOCAL_TASK,
'page callback' => 'drupal_get_form',
'page arguments' => array(
'pm_permission_admin',
),
'access arguments' => array(
'administer pm permission',
),
'file' => 'pm.permission.inc',
'file path' => drupal_get_path('module', 'pm') . '/includes',
);
$items['admin/config/pm/pm/menu'] = array(
'title' => 'Menu',
'description' => 'Manage menu exposed in block and on dashboard.',
'type' => MENU_LOCAL_TASK,
'page callback' => 'drupal_get_form',
'page arguments' => array(
'pm_menu_list',
),
'access arguments' => array(
'administer pm permission',
),
'file' => 'pm.menu.inc',
'file path' => drupal_get_path('module', 'pm') . '/includes',
);
$items['admin/config/pm/pm/menu/%'] = array(
'title' => 'Menu Settings',
'title callback' => 'pm_menu_admin_title_callback',
'title arguments' => array(
5,
),
'description' => 'Manage Dashboard Menu.',
'page callback' => 'drupal_get_form',
'page arguments' => array(
'pm_menu_admin',
5,
),
'access arguments' => array(
'administer pm permission',
),
'file' => 'pm.menu.inc',
'file path' => drupal_get_path('module', 'pm') . '/includes',
);
return $items;
}
function pm_theme() {
return array(
'pm_dashboard' => array(
'file' => 'pm.theme.inc',
'variables' => array(
'links' => array(),
),
),
'pm_dashboard_block' => array(
'file' => 'pm.theme.inc',
'variables' => array(
'links' => array(),
),
),
'pm_dashboard_link' => array(
'file' => 'pm.theme.inc',
'variables' => array(
'link_blocks' => array(),
),
'template' => 'templates/pm.menu.link',
),
'pm_icon_none' => array(
'file' => 'pm.theme.inc',
'variables' => array(
'title' => '',
),
'template' => 'templates/pm.icon.none',
),
'pm_icon' => array(
'file' => 'pm.theme.inc',
'variables' => array(
'title' => '',
'icon' => '',
),
'template' => 'templates/pm.icon',
),
'pm_list_default' => array(
'file' => 'pm.theme.inc',
'template' => 'pm-list-default',
'variables' => array(
'value' => NULL,
'key' => NULL,
'field_name' => NULL,
),
),
'pm_parent_breadcrumb' => array(
'file' => 'pm.theme.inc',
'variables' => array(
'data' => array(),
),
),
'pm_menu_entry_table' => array(
'file' => 'pm.theme.inc',
'render element' => 'element',
),
);
}
function pm_field_extra_fields() {
$default = array(
'node:pmorganization' => 'node:pmorganization',
'node:pmproject' => 'node:pmproject',
'node:pmissue' => 'node:pmissue',
'node:pmtask' => 'node:pmtask',
'node:pmticket' => 'node:pmticket',
'node:pmtimetracking' => 'node:pmtimetracking',
'node:pmteam' => 'node:pmteam',
'node:pmnote' => 'node:pmnote',
'node:pmexpense' => 'node:pmexpense',
'user:user' => 'user:user',
);
$enabled_content_types = variable_get('pm_contextual_links_enabled_content_types', $default);
foreach ($enabled_content_types as $info) {
if ($info) {
$info = explode(':', $info);
$entity_type = $info[0];
$bundle = $info[1];
$extra[$entity_type][$bundle]['display'][PM_CONTEXTUAL_LINK_PSEUDO_FIELD] = array(
'label' => t('Drupal PM contextual links.'),
'description' => t('Add a contextual link exposing various Drupal PM related tasks on Drupal Entities.'),
'weight' => 50,
);
}
}
return $extra;
}
function pm_entity_view($entity, $type, $view_mode, $langcode) {
list($id, $vid, $bundle) = entity_extract_ids($type, $entity);
$extrafields = field_extra_fields_get_display($type, $bundle, $view_mode);
if (isset($extrafields[PM_CONTEXTUAL_LINK_PSEUDO_FIELD]) && isset($extrafields[PM_CONTEXTUAL_LINK_PSEUDO_FIELD]['visible']) && $extrafields[PM_CONTEXTUAL_LINK_PSEUDO_FIELD]['visible']) {
$links = module_invoke_all('pm_contextual_links', $entity, $type, $view_mode, $langcode);
ksort($links);
if (!empty($links)) {
$entity->content[PM_CONTEXTUAL_LINK_PSEUDO_FIELD] = array(
'#theme' => 'links__ctools_dropbutton',
'#links' => $links,
);
}
else {
$entity->content[PM_CONTEXTUAL_LINK_PSEUDO_FIELD] = '';
}
}
}
function pm_dashboard_get_links($check_active = TRUE, $type = 'page') {
module_load_include('inc', 'pm', 'includes/pm.menu');
$links = pm_menu_get_links($type, $check_active);
return $links;
}
function _pm_dashboard_sort_links(array $a, array $b) {
if (intval($a['weight']) == intval($b['weight'])) {
return 0;
}
elseif (intval($a['weight']) < intval($b['weight'])) {
return -1;
}
else {
return 1;
}
}
function pm_pm_dashboard_links($type) {
$links = array();
if ($type == 'page' || $type == 'block') {
$links[] = array(
'title' => t('Configuration'),
'icon' => 'pmconfiguration',
'path' => 'admin/config/pm',
'params' => array(),
'node_type' => '',
'add_type' => '',
'map' => array(),
'weight' => 15,
);
}
return $links;
}
function pm_block_info() {
$blocks['pm_menu'] = array(
'info' => t('Project Management Menu'),
);
return $blocks;
}
function pm_block_view($delta = '') {
$block = array();
switch ($delta) {
case 'pm_menu':
$block = array(
'subject' => 'Project Management Menu',
'content' => array(
'quick_links' => array(
'#theme' => 'pm_dashboard_block',
'#links' => pm_dashboard_get_links(TRUE, 'block'),
'#attached' => array(
'css' => array(
drupal_get_path('module', 'pm') . '/pm-dashboard.css',
),
),
),
),
);
break;
}
return $block;
}
function pm_preprocess_html(&$vars) {
$pm_icon = variable_get('pm_icon', PM_ICON_SET_DEFAULT_BEHAVIOUR);
switch ($pm_icon) {
case PM_ICON_SET_DEFAULT_BEHAVIOUR:
$fontawesome_status = _pm_get_fontawesome_status();
$vars['classes_array'][] = $fontawesome_status == PM_FONTAWESOME_ENABLED ? "pm-use-fa-icons" : "pm-use-storm-icons";
break;
case PM_ICON_SET_FONTAWESOME:
$vars['classes_array'][] = "pm-use-fa-icons";
break;
case PM_ICON_SET_STORM:
$vars['classes_array'][] = "pm-use-storm-icons";
break;
}
}
function pm_get_parent($node, $type = 'pmorganization', $iteration = 10) {
try {
$wrapper = entity_metadata_wrapper('node', $node);
while ($iteration) {
$iteration--;
$bundle = $wrapper
->getBundle();
if ($bundle == $type) {
return $wrapper
->getIdentifier();
}
if ($wrapper
->__isset($bundle . '_parent')) {
$parent_field = $bundle . '_parent';
}
elseif ($wrapper
->__isset('field_' . $bundle . '_parent')) {
$parent_field = 'field_' . $bundle . '_parent';
}
else {
return FALSE;
}
$wrapper = $wrapper->{$parent_field};
}
} catch (EntityMetadataWrapperException $exc) {
watchdog('pm', 'See ' . __FUNCTION__ . '() <pre>' . $exc
->getTraceAsString() . '</pre>', NULL, WATCHDOG_ERROR);
}
}
function pm_views_api() {
return array(
'api' => 3.0,
'path' => drupal_get_path('module', 'pm') . '/includes/views',
);
}
function pm_field_formatter_info() {
return array(
'pm_list_default' => array(
'label' => t('Project Management Icons'),
'field types' => array(
'list_integer',
'list_float',
'list_text',
'list_boolean',
),
),
'pm_parent_breadcrumb' => array(
'label' => t('Project Management Parent Breadcrumb'),
'field types' => array(
'entityreference',
),
),
);
}
function pm_field_formatter_view($entity_type, $entity, $field, $instance, $langcode, $items, $display) {
$element = array();
switch ($display['type']) {
case 'pm_list_default':
$allowed_values = list_allowed_values($field, $instance, $entity_type, $entity);
foreach ($items as $delta => $item) {
$value = '';
if (isset($allowed_values[$item['value']])) {
$value = field_filter_xss($allowed_values[$item['value']]);
}
else {
$value = field_filter_xss($item['value']);
}
$key = $item['value'];
$output = theme('pm_list_default', array(
'value' => $value,
'key' => $key,
'field_name' => $instance['field_name'],
));
$element[$delta] = array(
'#markup' => $output,
);
}
break;
case 'pm_parent_breadcrumb':
foreach ($items as $delta => $item) {
$element[$delta] = array(
'#data' => pm_get_parents($entity_type, $entity, $field, $delta),
'#theme' => 'pm_parent_breadcrumb',
);
}
break;
}
return $element;
}
function pm_get_parents($entity_type, $entity, $field, $delta) {
$iteration = 10;
$field_name = $field['field_name'];
$parents = array();
try {
$e = entity_metadata_wrapper('node', $entity);
if ($field['cardinality'] == '1') {
if (isset($e->{$field_name})) {
$wrapper = $e->{$field_name};
}
}
else {
if (isset($e->{$field_name})) {
$wrapper = $e->{$field_name}[$delta];
}
}
while ($iteration and $wrapper) {
$iteration--;
$bundle = $wrapper
->getBundle();
if ($wrapper
->getIdentifier()) {
$parents[$wrapper
->getIdentifier()] = pm_get_parent_label('node', $wrapper);
}
if ($wrapper
->__isset($bundle . '_parent')) {
$parent_field = $bundle . '_parent';
}
elseif ($wrapper
->__isset('field_' . $bundle . '_parent')) {
$parent_field = 'field_' . $bundle . '_parent';
}
else {
break;
}
if ($bundle == 'pmorganization') {
break;
}
$wrapper = $wrapper->{$parent_field};
}
} catch (EntityMetadataWrapperException $exc) {
watchdog('pm', 'See ' . __FUNCTION__ . '() <pre>' . $exc
->getTraceAsString() . '</pre>', NULL, WATCHDOG_ERROR);
}
return array_reverse($parents);
}
function pm_get_parent_label($entity_type, $wrapper) {
$label = $wrapper
->label();
$id = $wrapper
->getIdentifier();
$path = $entity_type . '/' . $id;
return drupal_valid_path($path) ? l($label, $path) : $label;
}
function pm_node_access_records($node) {
if (empty($node->status)) {
return array();
}
$bundle_name = is_string($node) ? $node : $node->type;
$grants = array();
if (!variable_get('node_permissions_' . $bundle_name, 1)) {
$default_grants = _pm_permission_grants_default($node, $bundle_name);
$grants = array_merge($grants, $default_grants);
}
if (module_exists('pmorganization')) {
if ($bundle_name == 'pmorganization' or _pm_permission_get_field_name($bundle_name, 'parent')) {
$belonged_grants = _pm_permission_grants_belonged($node, $bundle_name, 'Organization');
if ($belonged_grants) {
$grants = array_merge($grants, $belonged_grants);
}
}
}
if (module_exists('pmproject')) {
if (_pm_permission_get_field_name($bundle_name, 'pm')) {
$assigned_grants_pm = _pm_permission_grants_assigned($node, $bundle_name, 'Project Manager');
if ($assigned_grants_pm) {
$grants = array_merge($grants, $assigned_grants_pm);
}
}
}
if (_pm_permission_get_field_name($bundle_name, 'assigned')) {
$assigned_grants_assigned = _pm_permission_grants_assigned($node, $bundle_name, 'Assigned');
if ($assigned_grants_assigned) {
$grants = array_merge($grants, $assigned_grants_assigned);
}
}
return $grants;
}
function pm_node_grants($account, $op) {
$grants = array();
foreach (pm_permission_get_enabled_types() as $type) {
$grant_per_type = pm_permission_grants_list($account, $op, $type);
if ($grant_per_type) {
$grants += $grant_per_type;
}
}
return $grants;
}
function pm_node_access($node, $op, $account) {
$type = is_string($node) ? $node : $node->type;
if (variable_get("pm_permission_node_{$type}_enabled", FALSE) && $op == 'create') {
if (user_access("PM permission {$type}: create", $account)) {
return NODE_ACCESS_ALLOW;
}
}
return NODE_ACCESS_IGNORE;
}
function pm_node_update($node) {
$enabled = pm_permission_get_enabled_types();
$type = $node->type;
if (in_array($type, $enabled)) {
if (pm_permission_check_if_child_permission_needs_update($node)) {
pm_permission_hunt_and_update_all_child_permission($node);
}
}
}
function pm_set_breadcrumb(array $links, $pm_root = TRUE) {
$breadcrumb = array();
if ($pm_root && drupal_valid_path('pm')) {
$breadcrumb = array(
l(t('Project Management'), 'pm'),
);
}
foreach ($links as $link) {
$text = $link['text'];
$path = $link['path'];
$options = isset($link['options']) ? $link['options'] : array();
if (drupal_valid_path($path)) {
$breadcrumb[] = l($text, $path, $options);
}
}
if (!empty($breadcrumb)) {
drupal_set_breadcrumb($breadcrumb);
}
}
function _pm_get_fontawesome_status() {
$status =& drupal_static(__FUNCTION__);
if (!isset($status)) {
$status = PM_FONTAWESOME_DISABLED;
$status |= module_exists('fontawesome') ? PM_FONTAWESOME_MODULE_ENABLED : 0x0;
if (module_exists('libraries')) {
$library_info = libraries_detect('fontawesome');
if (isset($library_info['installed']) and $library_info['installed'] == TRUE) {
$status |= PM_FONTAWESOME_LIBRARY_ENABLED;
}
}
}
return $status;
}