【问题标题】:Why does using $this inside a class in a Wordpress plugin throw a fatal error?为什么在 Wordpress 插件的类中使用 $this 会引发致命错误?
【发布时间】:2011-02-18 11:29:14
【问题描述】:

我正在编写一个 Wordpress 插件,它在管理区域创建一个页面,并执行一些前端代码。

下面的代码抛出了一个很好的Fatal error: Using $this when not in object context 错误。这是相当神秘的,因为变量是在类中调用的。

也许我没有遵循函数和类的预期 Wordpress 插件结构,但下面的概念代码是使用 Wordpress Codex 中插件开发的相关条目创建的。

有人可以解释为什么会触发错误,因为当我在 Wordpress 代码库之外创建类的实例时,一切都很好。

if (!class_exists("MyClass")) {
  class MyClass {
    var $test = 'Test variable';

    public function index() {
      //Index code
    }

    public function add() {
      echo $this->test;
    }
  }
}

add_action('admin_menu', 'my_plugin_menu');

function my_plugin_menu() {
  add_menu_page('My Plugin', 'My Plugin', 'manage_options', 'my-plugin', array('MyClass', 'index'));
  add_submenu_page('my-plugin', 'Add New Thing', 'Add New', 'manage_options', 'my-plugin-add', array('MyClass', 'add'));
}

【问题讨论】:

    标签: php class wordpress


    【解决方案1】:

    所以,我似乎已经解决了这个问题,回到基础并向 Google 提出了一个不起眼的问题:“在 Wordpress 插件中使用类”。

    Jay Fortner 的文章和dConstructing.com 上的一篇文章都很有帮助。

    基本上,我现在在类中调用 add_menu_page 和 add_submenu_page。我的印象是这些函数以某种方式创建了一个对象,但显然它们没有。

    我的代码现在看起来像这样,我可以毫无错误地调用声明的类变量:

    if (!class_exists("MyClass")) {
      class MyClass {
        var $test = 'Test variable';
    
        function __construct() {
          add_action('admin_menu', 'my_plugin_menu');
        }
    
        function my_plugin_menu() {
          add_menu_page('My Plugin', 'My Plugin', 'manage_options', 'my-plugin', array(&$this, 'index'));
          add_submenu_page('my-plugin', 'Add New Thing', 'Add New', 'manage_options', 'my-plugin-add', array(&$this, 'add'));
        }
    
        public function index() {
          //Index code
        }
    
        public function add() {
          echo $this->test;
        }
      }
      new MyClass;
    }
    

    【讨论】:

    • 嘿...,代码对我不起作用。所以,我把这个add_action('admin_menu', 'my_plugin_menu'); 函数改成这个add_action('admin_menu', array($this, 'my_plugin_menu'));
    【解决方案2】:

    这不再是真的。

    别忘了,如果你通过了这门课,你可能想通过它 参考,你甚至可以使用 &$this 传递一个类自己的函数 在类内部并继续修改同一个实例,这有助于 不必每次调用不同的部分时都重新创建一个类 插件但同一个类。

    发件人:https://codex.wordpress.org/Function_Reference/do_action_ref_array

    从 PHP 5.4 开始,数组不再通过引用传递,尽管 函数的名称。您甚至不能使用参考符号“&”,因为 通过引用传递调用时间现在会引发错误。你能做的是 将引用指针作为数组元素传递。这样做确实需要 添加到操作的所有回调都需要一个引用指针。这 不是您将在 WordPress 操作中看到的内容。这种技术是 仅供参考。

    $Class = new MyClass();
     add_menu_page(
           'My Plugin',
            'My Plugin',
            'manage_options',
            'my-plugin',
            array(&$Class, 'index')
    

    或者

    $myClass= new MyClass ;
    
    add_action('admin_menu', array( $myClass, 'admin_menu' ) );
    
    class MyClass 
    {
        public function admin_menu()
        {   
            add_menu_page('MyMenu', 'MyMenu', 'read', 'mymenu', array( $this, 'action' ));  
        }
        public function action()
        {   
            //Do something here
        }
    }
    

    【讨论】:

    • 内部操作我添加了表单标签。那么我应该在行动中传递什么以及我在哪里可以获得后价值?提前致谢。
    • 检查 $_POST 数组的 post 值。
    【解决方案3】:

    你应该做的是:

    function my_plugin_menu()
    {
    add_menu_page('My Plugin', 'My Plugin', 'manage_options', 'my-plugin', array(new MyClass, 'index'));
    add_submenu_page('my-plugin', 'Add New Thing', 'Add New', 'manage_options', 'my-plugin-add', array('MyClass', 'add'));
    }
    

    使用array('MyClass', 'index') 会导致 php 将方法作为静态方法执行,但将实际对象作为第一个参数传递将通过对象调用方法。

    function my_plugin_menu()
    {
        $Class = new MyClass();
        add_menu_page(
            'My Plugin',
            'My Plugin',
            'manage_options',
            'my-plugin',
            array($Class, 'index')
        );
    }
    

    如果您想重复使用该对象,也可以使用。

    【讨论】:

      【解决方案4】:

      取决于类的调用方式,静态 Class::method() 会抛出错误。如果是这种情况,我认为您需要使用 self::$test;但可能是错误的。

      【讨论】:

      • 我不确定 Wordpress 是如何调用该类的,但恐怕使用 self::test 而不是 $this->test 并不能解决错误。
      猜你喜欢
      • 2019-04-29
      • 1970-01-01
      • 1970-01-01
      • 2013-12-10
      • 2019-04-27
      • 1970-01-01
      • 2016-12-06
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多