Truyền đối số cho một menu gọi lại trang quản trị?


14

Tình huống: Tôi đang làm việc trên một plugin và tôi đang phát triển nó như một lớp, mọi thứ đều hoạt động tốt cho đến khi tôi gặp phải tình huống này. Tôi muốn làm cho mọi thứ sạch sẽ hơn một chút và thử điều này ..

class MyPlugin {
    function __construct() {
        add_action('admin_menu', array(&$this, 'myplugin_create_menus');
    }        

    //I don't want to write a function for every options page I create
    //so I prefer to just load the content from an external file.        
    function load_view($filename) {
        $view = require(dirname(__FILE__).'/views/'.$filename.'.php');
        return $view;
    }

    //Here is where the problem comes
    function myplugin_create_menus() {
        add_menu_page( 'Plugin name',
                       'Plugin name',
                       'manage_options',
                       'my-plugin-settings',
                       array(&$this, 'load_view') // Where do I specify the value of $filename??
                     );
    }

}#end of class

Tôi đã thử một loạt các tùy chọn khác nhau nhưng không có gì hoạt động, có thể tôi đang ở phía trước nhưng tôi không thể thấy nó.

Tất nhiên đây là một sáng tạo lại, tôi đã đặt trước tất cả các chức năng của mình và chúng không chính xác như tôi đã viết ở đây nhưng tôi hy vọng bạn có ý tưởng về việc tôi đang yêu cầu.

Cảm ơn trước.

PD: Nếu bạn muốn xem mã nguồn gốc, tôi sẽ vui lòng dán nó và cung cấp cho bạn liên kết.

Câu trả lời:


8

Bạn không thể truyền đối số cho hàm gọi lại. add_menu_page()thêm nó như một trình xử lý hành độngadmin.phpkích hoạt hành động mà không có bất kỳ đối số nào.

Tôi thấy hai giải pháp đơn giản cho vấn đề này. Một là lưu trữ tất cả tên tệp trong một mảng trong lớp của bạn, được lập chỉ mục theo tên hook. Sau đó, bạn có thể sử dụng điều này để tra cứu tập tin nào bạn cần tải (bạn cũng có thể lưu trữ dữ liệu bổ sung trong mảng này).

class WPSE16415_Plugin
{
    protected $views = array();

    function load_view() {
        // current_filter() also returns the current action
        $current_views = $this->views[current_filter()];
        include(dirname(__FILE__).'/views/'.$current_views.'.php');
    }

    function myplugin_create_menus() {
        $view_hook_name = add_menu_page( 'Plugin name',
            'Plugin name',
            'manage_options',
            'my-plugin-settings',
            array(&$this, 'load_view'),
        );
        $this->views[$view_hook_name] = 'options';
    }
}

Cách khác là bỏ qua đối số gọi lại, vì vậy WordPress sẽ bao gồm tệp được chỉ định bởi chính tên sên, như Brady gợi ý trong câu trả lời của mình.


ah-ha tại sao tôi không nghĩ làm theo cách đó :(
Brady

YEAH !! bạn đã lưu hàng chục chú mèo con ngày hôm nay .. chưa bao giờ nghe thấy chức năng đó mặc dù 'current_filter'. Giải pháp rất thông minh. Cảm ơn rất nhiều vì sự giúp đỡ của bạn @Brady @Jan Fabry
Luis

4

Bạn luôn có thể sử dụng một chức năng ẩn danh (hoặc đóng cửa). Một cái gì đó ảnh hưởng đến:

add_menu_page( $page, $menu, $capability, $slug, function() { print_my_admin_page($with_args); }, $icon, $position);

1
Điều này không làm việc cho tôi. Tôi đang sử dụng WordPress 4.1 (và tính đến hôm nay 4.1.1)
Jeff Vdovjak

Tài giỏi! Và nó hoạt động. Đây là một ví dụ đầy đủ hơn: hastebin.com/segibugice sẽ tạo một URL như example.com/wp-admin/admin.php?page=my-slug
Quinn Comendant

Tôi nên đã đề cập khi chuyển các biến vào phạm vi của một hàm ẩn danh, bạn phải sử dụng từ khóa "sử dụng". function() use ($my_var) { // now you can use $my_var }
dùng35752

0

Hàm load_view sẽ như thế này?:

function load_view($filename) {
    include(dirname(__FILE__).'/views/'.$filename.'.php');
}

và trong tệp đính kèm của bạn, nó sẽ lặp lại bất kỳ nội dung nào cho trang đang được hiển thị.

BIÊN TẬP:

Đây là những gì codex nói về vấn đề này:

$menu_slug (string) (required)Tên sên để chỉ menu này bởi (nên là duy nhất cho menu này). Trước phiên bản 3.0, nó được gọi là tham số tệp (hoặc xử lý). Nếu tham số chức năng bị bỏ qua, menu_slug sẽ là tệp PHP xử lý việc hiển thị nội dung trang menu. Mặc định: Không có

$function Chức năng hiển thị nội dung trang cho trang menu. Về mặt kỹ thuật, tham số chức năng là tùy chọn, nhưng nếu nó không được cung cấp, thì về cơ bản, WordPress sẽ cho rằng bao gồm tệp PHP sẽ tạo ra màn hình quản trị, mà không gọi hàm. Hầu hết các tác giả plugin chọn đặt mã tạo trang vào một hàm trong tệp plugin chính của họ. Trong trường hợp tham số hàm được chỉ định, có thể sử dụng bất kỳ chuỗi nào cho tham số tệp. Điều này cho phép sử dụng các trang như? Page = my_super_plugin_page thay vì? Page = my-super-plugin / admin-Options.php.

Vì vậy, những gì tôi có thể thu thập từ điều này là nếu bạn để trống chức năng, nó sẽ cố gắng bao gồm một tệp php dựa trên những gì bạn đã đặt menu_slug.

CHỈNH SỬA 2

function load_view() {
    include(dirname(__FILE__).'/views/'.$this->filename.'.php');
}

function myplugin_create_menus() {
    $this->filename = "something";
    add_menu_page( 'Plugin name',
                   'Plugin name',
                   'manage_options',
                   'my-plugin-settings',
                   array(&$this, 'load_view')
                 );
    $this->filename = "somethingelse";
    add_menu_page( 'Plugin name',
                   'Plugin name',
                   'manage_options',
                   'my-plugin-settings',
                   array(&$this, 'load_view')
                 );
}

@Brady Tôi biết điều đó và chức năng "load_view" đang hoạt động tốt và xuất nội dung chính xác khi sử dụng giá trị tĩnh. Ví dụ: incl .... / lượt xem / my-panel.php ');
Luis

@Luis - Vậy thì vấn đề là gì?
Brady

Mảng @Brady (& $ this, 'load_view') // Tôi chỉ định giá trị của tên tệp $ ở đâu ??. Tôi không thể làm một cái gì đó như mảng (& $ this, 'load_view ("my-value")') Tôi muốn tìm cách truyền tham số cho hàm tôi đang gọi
Luis

Oh tôi hiểu rồi Bạn muốn truyền một hàm lớp nhưng với một tham số. Vâng Ive đã nhìn và nhìn và không thể tìm thấy cách bạn làm điều đó. Nhưng vì bạn đang vượt qua lớp nên bạn không thể làm những gì tôi đã đưa vào EDIT 2?
Brady

@Brady: Chỉnh sửa thứ hai của bạn sẽ không giúp được gì nhiều, bạn chỉ cần ghi đè lên filenamebiến để nó luôn như vậy "somethingelse". Chỉnh sửa đầu tiên của bạn có thể là mẹo ở đây: nếu load_viewkhông làm gì ngoại trừ bao gồm tệp, bạn thực sự không nên vượt qua chức năng gọi lại và WordPress sẽ cố tải trang bạn đã chuyển qua dưới dạng sên.
Jan Fabry

0

Tôi đã giải quyết vấn đề này bằng cách chỉ thêm ID (hoặc bất kỳ dữ liệu nào bạn cần) vào sên menu.

Ví dụ:

 add_menu_page( 'Plugin name',
                       'Plugin name',
                       'manage_options',
                       'my-plugin-settings-' . $identifier,
                       'setting-function-callback'
                     );

Điều này sau đó sẽ tạo một URL với 'my-plugin-settings-filename' (làm ví dụ) và tôi chỉ có thể phân tích phần đó của URL (với $ _GET hoặc filter_input).


Bạn cũng có thể sử dụng một tham số URL, nhưng bạn phải tạo một mục menu (và sau đó bạn có thể ẩn nó nếu muốn).
Jeff Vdovjak

Cảm ơn vì đã đặt mã của tôi vào một mã toscho. Khi tôi hỏi một câu hỏi có một nút cho nó, nhưng tôi không quen với việc đánh dấu để trả lời.
Jeff Vdovjak

0

Dựa trên câu trả lời của người dùng35752 , bạn thậm chí có thể sử dụng một phương thức đối tượng với tham số là gọi lại.

$args = [ [new Foo(), 'bar'], [$param1, $param2, ...] ];

$callback = function () use ($args){
                call_user_func_array($args[0], $args[1]);
            };
add_menu_page( $page, $menu, $capability, $slug, $callback , $icon, $position)
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.