Wordpress: Accessing A Plugin's Function From A Theme - plugins

I'm trying to add some functionality from a plugin I have made into a Wordpress theme but I am having little joy. The documentation doesn't really help me solve the problem so perhaps someone here can help.
I have a plugin in Wordpress that is activated and working fine. The class for this plugin has a function called generateHtml which I would like to access from a Wordpress Theme. But whatever I try, I cannot seem to access my plugin's code.
Can either give me a summary of what I need to do to get a theme accessing code from a plugin and/or point out there I am going wrong in my code:
Plugin:
<?php
/** Usual comments here **/
if (!class_exists("ImageRotator")) {
class ImageRotator {
private $uploadPath = '';
private $pluginPath = '';
private $options;
function __construct() {
$this->uploadPath = dirname(__file__).'\\uploads\\';
// add_shortcode('imagerotator', array(&$this, 'generateHtml'));
}
// Various functions for plugin
function generateHtml() {
echo '<p>Hello World</p>';
}
}
}
/**
* Create instance of image rotator
*/
$imageRotator = new ImageRotator();
/**
* Create actions & filters for Wordpress
*/
if (isset($imageRotator)) {
// Actions
add_action('admin_menu', array(&$imageRotator, 'createMenu'));
add_action('admin_init', array(&$imageRotator, 'registerSettings'));
add_action('imagerotator_show', array(&$imageRotator, 'generateHtml'));
}
Portion from theme header page:
<?php if (isset($imageRotator)) {
$imageRotator->generateHtml();
} else if (isset($ImageRotator)) {
print_r($ImageRotator);
} else {
echo '<p>Nope!</p>';
}
if (function_exists("imagerotator_show")) {
echo 'Function found';
} else {
echo 'Function NOT found';
}
?>
Currently all I ever see is "Nope" and "Function NOT found". Thanks for any input.
Lee,

For starters, "imagerotator_show" is not a function; it's the name of a type of action. When you use the add_action() function, Wordpress just adds your method to the list of functions/methods to call when a particular action is triggered. Thus your second test will always respond with 'Function NOT found'.
The most likely cause of the first problem is failing to declare the method you want to call as a public method. You're also making the code harder than it needs to be.
The best practice I've seen for declaring methods and registering hooks from a class looks something like this:
if ( ! class_exists( 'Foo' ) ):
class Foo {
function __construct() {
add_action( 'hook_name', array( &$this, 'my_hook_implementation' ) );
}
function my_hook_implementation() {
// does something
}
public function my_special_method() {
// does something else
}
}
if ( class_exists( 'Foo' ) ):
$MyFoo = new Foo();
This allows your class to keep all of its implementation details private. When you need to call my_special_method(), you do it as follows:
$MyFoo->my_special_method();

#andrew since I can't comment I thought I would answer your ancillary question. See:
http://net.tutsplus.com/tutorials/wordpress/create-wordpress-plugins-with-oop-techniques/
Where it is explained that when defining a callback function from an object you have to use the array function. It's basically saying get the function 'my_hook_implementation' from the object $this and use it as the callback parameter to the add action hook. It is because you defined the function within the scope of the object and you have to define the scope in order for PHP to know what function you are talking about. The scope being the object referred to by the variable $this.

You just need to use do_action() function, inside your theme.
If you want the function generateHtml to appears inside your header.php you just need to open the header.php file and paste <?php do_action('imagerotator_show'); ?> where you want and then your function will be called there.

Related

SugarCRM: how to use preDisplay function in ViewQuickcreate?

I'm trying to customize the quick create view to add a default value of a field in Sugar Community Edition 6.5.24
Similar code works fine for ViewEdit, but it seems never called in subpanels.
Current file is
custom/modules/Opportunities/views/view.quickcreate.php
Unfortunately the constructor is not invoked.
Any help very appreciated.
<?php
require_once('include/MVC/View/views/view.quickcreate.php');
class OpportunitiesViewQuickcreate extends ViewQuickcreate {
function OpportunitiesViewQuickcreate(){
parent::ViewQuickcreate();
}
function preDisplay() {
parent::preDisplay();
$_REQUEST['custom_field_c'] = "a value for this field";
}
}
After tens of trying, I've found solution.
The right way is to extend SubpanelQuickCreate in the file custom/modules/Opportunities/views/view.subpanelquickcreate
require_once('include/EditView/SubpanelQuickCreate.php');
class OpportunitiesSubpanelQuickcreate extends SubpanelQuickCreate {
function OpportunitiesSubpanelQuickcreate() {
$_REQUEST['custom_field_c'] = "a value for this field";
parent::SubpanelQuickCreate("Opportunities");
}
}
Going from memory, so I may be wrong, but try adding $this->useForSubpanel = true; in your constructor.

Wordpress Plugins / Custom Class / get_option() / shortcode

I'm having an issue displaying information returned from a custom class defined within a plugin's files, when using a shortcode. I'll write up some mock files that showcase my issue.
/wp-content/plugins/my-plugin/classes/my_class.php
<?php
class People {
public $api_url = "https://www.external-service.com/api";
private $api_key;
function __construct($key = null) {
if $(key) {
$this->api_key = $key;
}
function get_response() {
$path = $this->api_url . "?my_api_token=" . $this->api_key;
}
}
?>
/wp-content/plugins/my-plugin/my-plugin.php
<?php
/**
* all of the wordpress plugin comments
* ...
*/
require "myplg_options.php";
require "myplg_shortcodes.php";
The options page and menu is generated from myplg_options; it is functioning correctly (including using get_option to retrieve the saved option (in this case, the api key).
/wp-content/plugins/my-plugin/myplg_shortcodes.php
<?php
require "classes/my_class.php";
$options = get_option('myplg_settings');
$myplg = new People($options['myplg_api_key']);
$response = $myplg->get_response();
function myplg_list_result(){
echo "the shortcode is working!";
var_dump($options, $myplg, $respnose);
}
add_shortcode('myplg_list', 'myplg_list_result');
?>
Testing externally from wordpress, the class works and everything is fine and dandy. The plugin's option page sets and retains the single option perfectly; the shortcode actually registers and is usable from within a WordPress page/portfolio/etc.
The issue I'm having is that using var_dump, all three of those variables are dumped as NULL.
After doing some homework, I was able to determine that moving the three variable declarations inside the shortcode makes it work. It would seem to me, however, that doing that is not the best workflow, as I'd need to re-grab the option, instantiate a new class, and call the class' function for every shortcode.
Is there a way around this?
As mentioned in the comment it's because variables are function scoped. You may be better off using a Closure.
<?php
require "classes/my_class.php";
$options = get_option('myplg_settings');
$myplg = new People($options['myplg_api_key']);
$response = $myplg->get_response();
add_shortcode('myplg_list', function() use ($options, $response, $myplg) {
echo "the shortcode is working!";
var_dump($options, $myplg, $respnose);
});

silverstripe permissions - prevent dataobject from being edited

at the moment I´m checking out the canEdit and canDelete Functions of Dataobject. As far as I can see I have to call that functions always manually in the template or other php code... Is there a way to prevent editing/deleting in general for a certain Dataobject? When I saw the canEdit function the first time I expected it to be checked by silverstripe automatically before writing the DataObject.
So I just want ADMINS to be allowed to write this DataObject:
public function canEdit($member = null){
return(
Permission::checkMember($member = Member::currentUser(), 'ADMIN')
);
}
Regards,
Florian
public function canEdit($member){
if (Permission::check('ADMIN')){
return true;
}else{
// do something here if applicable
}
}
Reference Link 1
Reference Link 2
Reference Link 3

Calling a javascript function defined in KRL from outside a KRL closure

I'm defining a Javascript function in my KRL global block that I want to call when the user clicks a link. Here are the relevant parts of the ruleset:
global {
emit <|
function clear_hold() {
app = KOBJ.get_application("a421x26");
app.raiseEvent("clear_hold");
}
|>;
}
rule add_link_to_clear_hold {
select when pageview ".*"
pre {
clear_div = << <div id="clear_hold">
Clear Hold
</div> >>;
}
{
append("body", clear_div);
}
rule clear_the_hold {
select when web clear_hold
{
replace_html("#clear_link", "<div id='clear_link'>Not on hold</div>");
}
always {
clear ent:hold;
}
}
When I click the link I get an error message that clear_link is not defined.
What do I need to do to call my javascript function?
It is suggested to use the following name spacing method to attach JavaScript functions to the KOBJ object to avoid clashes with other apps the user might have running.
KOBJ.a60x33.clear_hold = function() {
KOBJ.log('...wohoo! You found me!');
}
The function can then be called with
KOBJ.a60x33.clear_hold();
The function is defined inside the KRL closure, but I was calling from outside the closure. To make it visible outside I added it to KOBJ after defining the function
KOBJ.clear_hold = clear_hold;
Then to call it from the link:
href="javascript:KOBJ.clear_hold()

Zend: Quick and succinct way of inserting custom HTML into a Zend_Form?

Is there some method that accepts inserting custom html without having to actually add form controls, even if they're hidden and making my html a decorator?
I'm looking for something like:
$this->addCustomElement( array(
'div',
'body' => '<p>inner text</p>'
) );
I need something short and quick, I don't want to create a new class or something overkill.
Well it's really as simple as this:
$note = new Zend_Form_Element('note');
$note->helper = 'formNote';
$note->setValue('<b>hi</b>');
$form->addElement($note);
But the problem is that when you submit the form, the form calls $note->isValid(), which overrides the value, so if there are errors with the form, the next time you display it, the custom HTML won't be shown. There are two easy ways to fix this, the first is to override isValid() in your Form class like this:
public function isValid($data)
{
$note = $this->note->getValue();
$valid = parent::isValid($data);
$this->note->setValue($note);
return $valid;
}
But personally I find this kinda hackish way, and prefer the second option. That is to write a very simple class (this should really be part of Zend itself, I have no idea why it isn't, since it includes a formNote view helper, but no element that uses it):
class My_Form_Element_Note extends Zend_Form_Element_Xhtml
{
public $helper = 'formNote';
public function isValid($value, $context = null) { return true; }
}
Then you just have to do:
$note = new My_Form_Element_Note('note');
$note->setValue('<b>hi</b>');
$form->addElement($note);
And everything will just work.
Other options include doing some black magic with decorators, but I really recommend you to not go down that path.
Also note the AnyMarkup Decorator.