I have a wp-network installed with users that can create pages in each site.
Each of those pages get a place in the primary menu, and only one user have permission to create all this menu.
I want to create a user only to be able to edit the content of the pages, but not the title.
How can I disable the title of the page to be edited from the admin menu for a specific user, or (far better) for a capability?
I thought only a possibility, that's editing admin css to hide the title textbox, but I have two problems:
I don't like to css-hide things.
I don't know where is the admin css.
I know php, but don't know how to add a css hide to an element for a capability.
You should definitely use CSS to hide the div#titlediv. You'll want the title to show in the markup so the form submission, validation, etc continues to operate smoothly.
Some elements you'll need to know to implement this solution:
current_user_can() is a boolean function that tests if the current logged in user has a capability or role.
You can add style in line via the admin_head action, or using wp_enqueue_style if you'd like to store it in a separate CSS file.
Here is a code snippet that will do the job, place it where you find fit, functions.php in your theme works. I'd put it inside a network activated plugin if you're using different themes in your network:
<?php
add_action('admin_head', 'maybe_modify_admin_css');
function maybe_modify_admin_css() {
if (current_user_can('specific_capability')) {
?>
<style>
div#titlediv {
display: none;
}
</style>
<?php
}
}
?>
I resolved the problem, just if someone comes here using a search engine, I post the solution.
Doing some research, I found the part of the code where the title textbox gets inserted, and I found a function to know if a user has a certain capability.
The file where the title textbox gets added is /wp-admin/edit-form-advanced.php. This is the line before the textbox
if ( post_type_supports($post_type, 'title') )
I changed it to this
if ( post_type_supports($post_type, 'title') and current_user_can('edit_title') )
That way, the textbox is only added when the user has the capability called "edit_title"
When this IF block ends few lines after, I added:
else echo "<h2>".esc_attr( htmlspecialchars( $post->post_title ) )."</h2>";
To see the page title but not to edit it, when the user hasn't got "edit_title" capability.
Then I had already installed a plugin to edit user capabilities and roles, wich help me to create a new capability (edit_title) and assign it to the role I want.
Related
I know there are 357,982 other posts about this BUT they all kinda lack something ie. an actual example that works for those of us who don't write 4,594,334 line of code every day.
SO - As it stands the scenerio is:
A plugin that registers a custom post type
A sub-menu you want to hide
What next?
The best solution I have found is actually pretty easy and requires a bit of inspection of the source and a good understanding of what to look for.
In this example woocommerce is registering the custom post type 'product' with a sub-menu that appears as 'Product Options'. We want to hide this for non-admin users.
Doing an inspection of the menu items we find that the hyperlink for the parent menu is 'edit.php?post_type=event_ticket' - looking a little further we see that the hyperlink for the sub-menu is 'https://websitename.com/wp-admin/edit.php?post_type=product&page=product_attributes'
We will use the 'add_action' hook as shown below. Please note that we are using the url for the parent menu however we are ONLY using the page parameter for the child.
add_action('admin_menu', 'remove_menu_pages', 999);
function remove_menu_pages()
{
if (current_user_can('manage_options') == false)
{
//1st parameter is parent URL | second is the 'page' parameter from the child url
remove_submenu_page('edit.php?post_type=product', 'product_attributes');
}
}
Add this to your functions.php and then login as a non-admin user and the submenu should now be hidden.
I am trying to hide certain page sections based on user role in Visual Composer by adding Custom Content Shortcode in two text blocks. The first text block is at the top of the content I want to hide to all but admins and contains:
[is role=administrator]
The second text block, at the bottom of the content I want to hide, contains the closing tag,
[/is]
This is doing what it's supposed to and hiding the content, however, Visual Composer doesn't seem to like it, and VC shortcode winds up getting outputted to the page for admins, i.e. [/vc_column]. I can't get it to not display the VC shortcode. It's strange too that it only outputs the shortcode for admins.
If there is a different or better way to do what I'm trying to accomplish, I'm open to any solutions! I just want certain page sections to only be visible to admins.
You could use the header function to use Jquery to remove the elements via css class for each user.
Below is not a tested solution but can be a way to achieve what you wanted but not sure how to remove completely the output source code only hide it.
This can be added to the function file or built into a plugin.
function insert_header()
{
// Check what user role
global $current_user;
$user_roles = $current_user->roles;
$user_role = array_shift($user_roles);
//return $user_role;
// Check if the user has role
if($user_role == "editor")
{
// inject jQuery or css to remove the elements by class
}
}
add_action('wp_head','insert_header');
I'm doing some work on an existing site that is based on the Wordpress theme, but uses about 15 plugins (Including Buddypress). One in particular is the WP Sliding Login|Dashboard plugin, which has a link to the user's activity feed. I found the code that creates that link in the wp-sliding-login-dashboard.php file:
<?php
if ( is_user_logged_in() ) {
global $current_user;
$username = $current_user->user_login;
echo ' <li>Activity Feed</li>';
}
?>
I want to use this code to send the user to the same location, but using the a link at the top of the home page. Unfortunately, the home page links are all created using Wordpress menus, which as far as I can tell, only allow for the use of static links attached to existing pages.
Do I create a dummy page to link to that exits only to execute the above code? Is that even possible? Picture a five-year-old trying to read Shakespeare, and you have an idea of my ability as a coder, so feel free to engage me as such - i.e. if you say, "oh just create a scoping function instead of creating a global function", i would stare at you drooling and confused.
Images for clarity: The sliding login menu (WP-Sliding Login|Dashboard Plugin), showing the target URL in the status bar as www.ferrignofit.com/members/FerrignoFit/activity/ (the current logged in user is FerrignoFit):
http://i.imgur.com/NPvmCXU.jpg
The main page Wordpress-based menu, which i want to go to the above URL, but is currently going to www.ferrignofit.com/activity/, a different page:
http://i.imgur.com/dIiFpDC.jpg
So here's a jQuery solution for this specific issue. From seeing the images you have, what you want to do is target a specific anchor in your dynamic WordPress menu.
As you may be aware, you can create custom links for the WordPress menu function... it simply lets you set a label and a URL. You should create such item and just give it a hash for the URL for now.
Now set a class for that specific menu item so you can have a nice handle for jQuery to target it (otherwise you can use the dynamic class that WordPress creates for each specific menu-item).
One you have a class set or you know what you need to target then you can add this block of code before your menu.
<?php if (is_user_logged_in()){ ?>
<script>
$(document).ready(function(e) {
var targetNav = $('li.customClassName a');
var userName = '<?php $current_user = wp_get_current_user(); echo $current_user->display_name;?>';
var userUrl = 'http://www.mywebsitename.com/members/'+ userName +'/activity/';
targetNav.attr('href',userUrl);
});
</script>
<?php } else { ?>
<script>
$(document).ready(function(e) {
var targetNav = $('li.customClassName a');
targetNav.attr('href','http://www.stackoverflow.com');
});
</script>
<?php } ?>
Please not that I am using PHP to get the current username in WordPress, after I get the username and I store it in the userName variable I use it in the userUrl to set it with the path that I want.
On another note, I'm using is_user_logged_in() so you have the option of making the link something else if the user is in fact not logged in. So with this if statement one of the two blocks of code will be output by PHP.
As soon as my two variables are set, I simply target my menu item with jQuery and modify the href attribute to replace the hash with the path and dynamic username.
Though this is not very good practice to mix JS and PHP, I'd like to learn myself here what other solutions someone can suggest so I'm posting this as a solution for your very specific issue.
I tested this code with my own WordPress site and it works, just remember that this code NEEDS to be in a PHP file otherwise the PHP used in the <script> tags won't mean anything to the server if it's in a .js file.
I don't use the Drupal Tabs because they interfere with my CSS but I need the functionality of the Edit tab to be on that screen so that a user can edit the node after reviewing it.
Any ideas on how to do this? Functions? tpl placement? Thanks!
You can do this in a custom module as follows.
In yourcustommodule.module you implement hook_preprocess_node(). In there you check if the user has permissions to edit the node and you set the edit link.
function yourcustommodule_preprocess_node(&$vars) {
if (node_access("update", $vars['node']) === TRUE) {
$vars['edit_link']['#markup'] = l(t('Edit'), 'node/' . $vars['nid'] . '/edit');
}
}
In the node.tpl.php template in the theme you print the edit link if it is available.
<?php if (isset($edit_link)) : ?>
<p><?php print render($edit_link); ?></p>
<?php endif; ?>
If you do not have a node.tpl.php template in your theme folder than copy the one from modules/node.
If you're using the Views Format "Fields", one of the fields that you can add is "Edit Link." It's pretty flexible; it will tell you what text to display in the link. That's probably the preferred option.
If you're not using the "Fields" format, it gets trickier, especially since you're already interfering with some basic drupal styling. I'd need more information about your View and your skill set to recommend a method that doesn't cause more problems.
As a sidenote: I learned Drupal theming from the outside in, and used to use CSS that would interfere with the underlying drupal mechanics like tabs and contextual links. I've moved away from that; I find very few cases where I need to interfere with native styling-- and for those I can use custom .tpl's to get around.
EDIT: Ah. If you're not using views, a custom page .tpl is probably the best way to go. If you're not familiar, the structure for any node edit link is '/node/<NID>/edit' (for clean URL's) or '/?q=node/<NID>/edit' for old-style URL's. Depending on how your path aliases are set up, '/<url-alias>/edit' may work as well but the previous ones are more reliable.
This link on drupal.org gives a few options.
I think u can write a theme file(.tpl) for u specific case and theme page in whichever way u want
I'm trying to remove the title of a page node on Drupal. I have this page:
And I want it to look like this:
As you can see, I want the title to be removed, but only for taxonomy terms. If I try to erase it using CSS, I erase al page-titles, so I wanted to use this module, that allows administrators to auto-generate node titles and hide it.
I go to structure -> type content -> my type content, and edit it. I activate the module, and I want to auto-generate titles depending on the node category. I think it should look like this, but it doesn't work...
Any ideas why?
EDIT: Sorry, I forgot to say: yes, when I activate the module, use it, and select the category as the auto-generated title, it works. But it doesn't hide the title...
It also launches this mistake:
Use Exclude Node Title module.
https://drupal.org/project/exclude_node_title
Setting for this module:
Click on Module->Exclude node title->configure
Home » Administration » Configuration » Content authoring
Select All nodes from Basic Page
Check Full Content for hide title from all cms page except home page
Check Teaser for hide title from home page.
If you want to remove the title, you should look into overriding the page and node templates.
page.tpl.php and node.tpl.php
All you need to do is click "View Source" on both of those and copy them to your theme folder. From there you can modify both as required.
From what I can gather, you'll want to remove the print $title from your node.tpl.php.
Have the similar issue before, as far as I remember, I just added some if statement to the code:
<?php if (blah-blah-blah): ?>
<h2> <?php echo $title; ?> </h2>
<?php endif; ?>
Hope, it'll give you a clue.
Some other thoughts: you can make an if statement or rewrite it not only in page.tpl.php but create some specific page-node-type.tpl.php file and overwrite only its $title, or you can try to customize page's output via Views/Panels modules as well.
Also, could you please make more clear, what title do you want to remove? Page title or node title? And it should be removed only when you are looking nodes associated with some taxonomy term (in other words, when you are on /taxonomy/term/n page), am I right?
By using the Context module, you can add classes to the body so you can target just the taxonomy pages in CSS.
Using Context module to set body classes
Sorry guys, it was as easy as hide title tag on "manage presentation"...
You are all right on your responses, but they were not exactly what I needed... thanks!
Use Exclude Node Title module.
https://drupal.org/project/exclude_node_title
another nice solution for specific nodes, is to use the standard $title_prefix/suffix vars, which should be implemented by every theme. using the standard class element-invisible in page preprocess ..
like:
/**
* Implements hook_preprocess_page().
*/
function YOUR_THEME_preprocess_page(&$variables) {
if (isset($variables['node']) && $variables['node']->nid == 1) {
$variables['title_prefix'] = array('#markup' => '<div class="element-invisible">');
$variables['title_suffix'] = array('#markup' => '</div>');
}
}
Every page should contain a heading.
You should always maintain a structured hierarchy of headings within any web page. You should never have a blank heading or even hide it with display:none;. Hiding any content which isn’t viewable by your visitors but is by search engines is against Google’s guidelines as your intention is to only manipulate search engine results by including it. Restyle a H1 so it fits into your design is the best option.
If you still have to hide it then a better option would be to either create a template for that node, content type or page and simply not print the heading.
Or if you want to use CSS then use position:absolute so the heading doesn’t use any space where it is located in the page and text-indent:-9999px; so the text is moved off the screen and no longer visible but at least can be read by screen readers and search engines.
This is how I did it, Switch statement
// Get the name of node
$node_name = node_type_get_name($node);
// Then just add the content types you wish to exclude by overwriting the // $title object with an empty string
switch ($node_name) {
case 'Home page':
$title = '' ;
break;
case 'Event':
$title = '';
break;
case 'Offer':
$title = '';
break;
}