|
1
|
|
|
<?php |
|
|
|
|
|
|
2
|
|
|
/** |
|
3
|
|
|
* GravityView Admin notices |
|
4
|
|
|
* |
|
5
|
|
|
* @package GravityView |
|
6
|
|
|
* @license GPL2+ |
|
7
|
|
|
* @author Katz Web Services, Inc. |
|
8
|
|
|
* @link http://gravityview.co |
|
9
|
|
|
* @copyright Copyright 2015, Katz Web Services, Inc. |
|
10
|
|
|
* |
|
11
|
|
|
* @since 1.12 |
|
12
|
|
|
*/ |
|
13
|
|
|
|
|
14
|
|
|
/** |
|
15
|
|
|
* When the plugin is activated, flush dismissed notices |
|
16
|
|
|
* @since 1.15.1 |
|
17
|
|
|
*/ |
|
18
|
|
|
register_activation_hook( GRAVITYVIEW_FILE, array( 'GravityView_Admin_Notices', 'flush_dismissed_notices' ) ); |
|
19
|
|
|
|
|
20
|
|
|
/** |
|
21
|
|
|
* Handle displaying and storing of admin notices for GravityView |
|
22
|
|
|
* @since 1.12 |
|
23
|
|
|
*/ |
|
24
|
|
|
class GravityView_Admin_Notices { |
|
25
|
|
|
|
|
26
|
|
|
/** |
|
27
|
|
|
* @var array |
|
28
|
|
|
*/ |
|
29
|
|
|
static private $admin_notices = array(); |
|
30
|
|
|
|
|
31
|
|
|
static private $dismissed_notices = array(); |
|
32
|
|
|
|
|
33
|
|
|
function __construct() { |
|
|
|
|
|
|
34
|
|
|
|
|
35
|
|
|
$this->add_hooks(); |
|
36
|
|
|
} |
|
37
|
|
|
|
|
38
|
|
|
function add_hooks() { |
|
|
|
|
|
|
39
|
|
|
add_action( 'network_admin_notices', array( $this, 'dismiss_notice' ), 50 ); |
|
40
|
|
|
add_action( 'admin_notices', array( $this, 'dismiss_notice' ), 50 ); |
|
41
|
|
|
add_action( 'admin_notices', array( $this, 'admin_notice' ), 100 ); |
|
42
|
|
|
add_action( 'network_admin_notices', array( $this, 'admin_notice' ), 100 ); |
|
43
|
|
|
} |
|
44
|
|
|
|
|
45
|
|
|
/** |
|
46
|
|
|
* Clear out the dismissed notices when the plugin gets activated |
|
47
|
|
|
* @see register_activation_hook |
|
48
|
|
|
* @since 1.15.1 |
|
49
|
|
|
* @return void |
|
50
|
|
|
*/ |
|
51
|
|
|
static public function flush_dismissed_notices() { |
|
|
|
|
|
|
52
|
|
|
delete_transient( 'gravityview_dismissed_notices' ); |
|
53
|
|
|
} |
|
54
|
|
|
|
|
55
|
|
|
/** |
|
56
|
|
|
* Dismiss a GravityView notice - stores the dismissed notices for 16 weeks |
|
57
|
|
|
* @since 1.12 |
|
58
|
|
|
* @return void |
|
59
|
|
|
*/ |
|
60
|
|
|
public function dismiss_notice() { |
|
61
|
|
|
|
|
62
|
|
|
// No dismiss sent |
|
63
|
|
|
if( empty( $_GET['gv-dismiss'] ) ) { |
|
|
|
|
|
|
64
|
|
|
return; |
|
65
|
|
|
} |
|
66
|
|
|
|
|
67
|
|
|
// Invalid nonce |
|
68
|
|
|
if( !wp_verify_nonce( $_GET['gv-dismiss'], 'dismiss' ) ) { |
|
|
|
|
|
|
69
|
|
|
return; |
|
70
|
|
|
} |
|
71
|
|
|
|
|
72
|
|
|
$notice_id = esc_attr( $_GET['notice'] ); |
|
|
|
|
|
|
73
|
|
|
|
|
74
|
|
|
//don't display a message if use has dismissed the message for this version |
|
75
|
|
|
$dismissed_notices = (array)get_transient( 'gravityview_dismissed_notices' ); |
|
|
|
|
|
|
76
|
|
|
|
|
77
|
|
|
$dismissed_notices[] = $notice_id; |
|
78
|
|
|
|
|
79
|
|
|
$dismissed_notices = array_unique( $dismissed_notices ); |
|
80
|
|
|
|
|
81
|
|
|
// Remind users every week |
|
82
|
|
|
set_transient( 'gravityview_dismissed_notices', $dismissed_notices, WEEK_IN_SECONDS ); |
|
83
|
|
|
|
|
84
|
|
|
} |
|
85
|
|
|
|
|
86
|
|
|
/** |
|
87
|
|
|
* Has the notice been dismissed already in the admin? |
|
88
|
|
|
* |
|
89
|
|
|
* If the passed notice array has a `dismiss` key, the notice is dismissable. If it's dismissable, |
|
90
|
|
|
* we check against other notices that have already been dismissed. |
|
91
|
|
|
* @since 1.12 |
|
92
|
|
|
* @see GravityView_Admin_Notices::dismiss_notice() |
|
93
|
|
|
* @see GravityView_Admin_Notices::add_notice() |
|
94
|
|
|
* @param string $notice Notice array, set using `add_notice()`. |
|
95
|
|
|
* @return boolean True: show notice; False: hide notice |
|
96
|
|
|
*/ |
|
97
|
|
|
private function is_notice_dismissed( $notice ) { |
|
98
|
|
|
|
|
99
|
|
|
// There are no dismissed notices. |
|
100
|
|
|
if( empty( self::$dismissed_notices ) ) { |
|
101
|
|
|
return false; |
|
102
|
|
|
} |
|
103
|
|
|
|
|
104
|
|
|
// Has the |
|
105
|
|
|
$is_dismissed = !empty( $notice['dismiss'] ) && in_array( $notice['dismiss'], self::$dismissed_notices ); |
|
|
|
|
|
|
106
|
|
|
|
|
107
|
|
|
return $is_dismissed ? true : false; |
|
108
|
|
|
} |
|
109
|
|
|
|
|
110
|
|
|
/** |
|
111
|
|
|
* Get admin notices |
|
112
|
|
|
* @since 1.12 |
|
113
|
|
|
* @return array |
|
114
|
|
|
*/ |
|
115
|
|
|
public static function get_notices() { |
|
116
|
|
|
return self::$admin_notices; |
|
117
|
|
|
} |
|
118
|
|
|
|
|
119
|
|
|
/** |
|
120
|
|
|
* Handle whether to display notices in Multisite based on plugin activation status |
|
121
|
|
|
* |
|
122
|
|
|
* @uses \GV\Plugin::is_network_activated |
|
123
|
|
|
* |
|
124
|
|
|
* @since 1.12 |
|
125
|
|
|
* |
|
126
|
|
|
* @return bool True: show the notices; false: don't show |
|
127
|
|
|
*/ |
|
128
|
|
|
private function check_show_multisite_notices() { |
|
129
|
|
|
|
|
130
|
|
|
if( ! is_multisite() ) { |
|
131
|
|
|
return true; |
|
132
|
|
|
} |
|
133
|
|
|
|
|
134
|
|
|
// It's network activated but the user can't manage network plugins; they can't do anything about it. |
|
135
|
|
|
if ( gravityview()->plugin->is_network_activated() && ! is_main_site() ) { |
|
136
|
|
|
return false; |
|
137
|
|
|
} |
|
138
|
|
|
|
|
139
|
|
|
// or they don't have admin capabilities |
|
140
|
|
|
if( ! is_super_admin() ) { |
|
141
|
|
|
return false; |
|
142
|
|
|
} |
|
143
|
|
|
|
|
144
|
|
|
return true; |
|
145
|
|
|
} |
|
146
|
|
|
|
|
147
|
|
|
/** |
|
148
|
|
|
* Outputs the admin notices generated by the plugin |
|
149
|
|
|
* |
|
150
|
|
|
* @uses GVCommon::has_cap() |
|
151
|
|
|
* @since 1.12 |
|
152
|
|
|
* |
|
153
|
|
|
* @return void |
|
154
|
|
|
*/ |
|
155
|
|
|
public function admin_notice() { |
|
156
|
|
|
|
|
157
|
|
|
/** |
|
158
|
|
|
* @filter `gravityview/admin/notices` Modify the notices displayed in the admin |
|
159
|
|
|
* @since 1.12 |
|
160
|
|
|
*/ |
|
161
|
|
|
$notices = apply_filters( 'gravityview/admin/notices', self::$admin_notices ); |
|
162
|
|
|
|
|
163
|
|
|
if( empty( $notices ) || ! $this->check_show_multisite_notices() ) { |
|
164
|
|
|
return; |
|
165
|
|
|
} |
|
166
|
|
|
|
|
167
|
|
|
//don't display a message if use has dismissed the message for this version |
|
168
|
|
|
// TODO: Use get_user_meta instead of get_transient |
|
169
|
|
|
self::$dismissed_notices = isset( $_GET['show-dismissed-notices'] ) ? array() : (array)get_transient( 'gravityview_dismissed_notices' ); |
|
|
|
|
|
|
170
|
|
|
|
|
171
|
|
|
$output = ''; |
|
172
|
|
|
|
|
173
|
|
|
foreach( $notices as $notice ) { |
|
174
|
|
|
|
|
175
|
|
|
// If the user doesn't have the capability to see the warning |
|
176
|
|
|
if( isset( $notice['cap'] ) && false === GVCommon::has_cap( $notice['cap'] ) ) { |
|
177
|
|
|
gravityview()->log->debug( 'Notice not shown because user does not have the capability to view it.', array( 'data' => $notice ) ); |
|
178
|
|
|
continue; |
|
179
|
|
|
} |
|
180
|
|
|
|
|
181
|
|
|
if( true === $this->is_notice_dismissed( $notice ) ) { |
|
182
|
|
|
gravityview()->log->debug( 'Notice not shown because the notice has already been dismissed.', array( 'data' => $notice ) ); |
|
183
|
|
|
continue; |
|
184
|
|
|
} |
|
185
|
|
|
|
|
186
|
|
|
$output .= '<div id="message" style="position:relative" class="notice '. gravityview_sanitize_html_class( $notice['class'] ).'">'; |
|
187
|
|
|
|
|
188
|
|
|
// Too cute to leave out. |
|
189
|
|
|
$output .= gravityview_get_floaty(); |
|
190
|
|
|
|
|
191
|
|
|
if( !empty( $notice['title'] ) ) { |
|
|
|
|
|
|
192
|
|
|
$output .= '<h3>'.esc_html( $notice['title'] ) .'</h3>'; |
|
193
|
|
|
} |
|
194
|
|
|
|
|
195
|
|
|
$message = isset( $notice['message'] ) ? $notice['message'] : ''; |
|
196
|
|
|
|
|
197
|
|
|
if( !empty( $notice['dismiss'] ) ) { |
|
|
|
|
|
|
198
|
|
|
|
|
199
|
|
|
$dismiss = esc_attr($notice['dismiss']); |
|
|
|
|
|
|
200
|
|
|
|
|
201
|
|
|
$url = esc_url( add_query_arg( array( 'gv-dismiss' => wp_create_nonce( 'dismiss' ), 'notice' => $dismiss ) ) ); |
|
202
|
|
|
|
|
203
|
|
|
$align = is_rtl() ? 'alignleft' : 'alignright'; |
|
204
|
|
|
$message .= '<a href="'.$url.'" data-notice="'.$dismiss.'" class="' . $align . ' button button-link">'.esc_html__('Dismiss', 'gravityview' ).'</a></p>'; |
|
|
|
|
|
|
205
|
|
|
} |
|
206
|
|
|
|
|
207
|
|
|
$output .= wpautop( $message ); |
|
208
|
|
|
|
|
209
|
|
|
$output .= '<div class="clear"></div>'; |
|
210
|
|
|
$output .= '</div>'; |
|
211
|
|
|
|
|
212
|
|
|
} |
|
213
|
|
|
|
|
214
|
|
|
echo $output; |
|
|
|
|
|
|
215
|
|
|
|
|
216
|
|
|
unset( $output, $align, $message, $notices ); |
|
217
|
|
|
|
|
218
|
|
|
//reset the notices handler |
|
219
|
|
|
self::$admin_notices = array(); |
|
220
|
|
|
} |
|
221
|
|
|
|
|
222
|
|
|
/** |
|
223
|
|
|
* Add a notice to be displayed in the admin. |
|
224
|
|
|
* @since 1.12 Moved from {@see GravityView_Admin::add_notice() } |
|
225
|
|
|
* @since 1.15.1 Allows for `cap` key, passing capability required to show the message |
|
226
|
|
|
* @param array $notice { |
|
227
|
|
|
* @type string $class HTML class to be used for the notice. Default: 'error' |
|
228
|
|
|
* @type string $message Notice message, not escaped. Allows HTML. |
|
229
|
|
|
* @type string $dismiss Unique key used to determine whether the notice has been dismissed. Set to false if not dismissable. |
|
230
|
|
|
* @type string|array $cap The capability or caps required for an user to see the notice |
|
231
|
|
|
* } |
|
232
|
|
|
* @return void |
|
233
|
|
|
*/ |
|
234
|
|
|
public static function add_notice( $notice = array() ) { |
|
235
|
|
|
|
|
236
|
|
|
if( !isset( $notice['message'] ) ) { |
|
|
|
|
|
|
237
|
|
|
gravityview()->log->error( 'Notice not set', array( 'data' => $notice ) ); |
|
238
|
|
|
return; |
|
239
|
|
|
} |
|
240
|
|
|
|
|
241
|
|
|
$notice['class'] = empty( $notice['class'] ) ? 'error' : $notice['class']; |
|
242
|
|
|
|
|
243
|
|
|
self::$admin_notices[] = $notice; |
|
244
|
|
|
} |
|
245
|
|
|
} |
|
246
|
|
|
|
|
247
|
|
|
new GravityView_Admin_Notices; |
|
248
|
|
|
|
The PSR-1: Basic Coding Standard recommends that a file should either introduce new symbols, that is classes, functions, constants or similar, or have side effects. Side effects are anything that executes logic, like for example printing output, changing ini settings or writing to a file.
The idea behind this recommendation is that merely auto-loading a class should not change the state of an application. It also promotes a cleaner style of programming and makes your code less prone to errors, because the logic is not spread out all over the place.
To learn more about the PSR-1, please see the PHP-FIG site on the PSR-1.