display-name and/or key=>array(display-name, choice1, choice2, ...)
* key: an option name for the key (this name will be given a prefix when stored in
* the database to ensure it does not conflict with other plugin options)
* value: can be one of two things:
* (1) string display name for displaying the name of the option to the user on a web page
* (2) array where the first element is a display name (as above) and the rest of
* the elements are choices of values that the user can select
* e.g.
* array(
* 'item' => 'Item:', // key => display-name
* 'rating' => array( // key => array ( display-name, choice1, choice2, ...)
* 'CanDoOperationX' => array('Can do Operation X', 'Administrator', 'Editor', 'Author', 'Contributor', 'Subscriber'),
* 'Rating:', 'Excellent', 'Good', 'Fair', 'Poor')
*/
public function get_option_meta_data() {
return array();
}
/**
* Get main data
*
* @return array
*/
public function get_main_data() {
return array();
}
/**
* Get plugin options
*
* @return array
*/
public function get_plugin_meta_data() {
return array();
}
/**
* Get option names
*
* @return array of string name of options
*/
public function get_option_names() {
return array_keys( $this->get_option_meta_data() );
}
/**
* Override this method to initialize options to default values and save to the database with add_option
*
* @return void
*/
protected function init_options() {
}
/**
* Cleanup: remove all options from the DB
*
* @return void
*/
protected function delete_saved_options() {
$option_meta_data = $this->get_option_meta_data();
if ( is_array( $option_meta_data ) ) {
foreach ( $option_meta_data as $a_option_key => $a_option_meta ) {
$prefixed_option_name = $this->prefix( $a_option_key ); // how it is stored in DB.
delete_option( $prefixed_option_name );
}
}
}
/**
* Get plugin name
*
* @return string display name of the plugin to show as a name/title in HTML.
* Just returns the class name. Override this method to return something more readable
*/
public function get_plugin_display_name() {
return get_class( $this );
}
/**
* Get the prefixed version input $name suitable for storing in WP options
* Idempotent: if $optionName is already prefixed, it is not prefixed again, it is returned without change
*
* @param string $name option name to prefix. Defined in settings.php and set as keys of $this->optionMetaData.
* @return string
*/
public function prefix( $name ) {
$option_name_prefix = $this->get_option_name_prefix();
if ( strpos( $name, $option_name_prefix ) === 0 ) { // 0 but not false
return $name; // already prefixed.
}
return $option_name_prefix . $name;
}
/**
* Remove the prefix from the input $name.
* Idempotent: If no prefix found, just returns what was input.
*
* @param string $name option name.
* @return string $optionName without the prefix.
*/
public function &un_prefix( $name ) {
$option_name_prefix = $this->get_option_name_prefix();
if ( strpos( $name, $option_name_prefix ) === 0 ) {
return substr( $name, strlen( $option_name_prefix ) );
}
return $name;
}
/**
* A wrapper function delegating to WP get_option() but it prefixes the input $optionName
* to enforce "scoping" the options in the WP options table thereby avoiding name conflicts
*
* @param string $option_name defined in settings.php and set as keys of $this->optionMetaData.
* @param string $default default value to return if the option is not set.
* @return string the value from delegated call to get_option(), or optional default value
* if option is not set.
*/
public function get_option( $option_name, $default = null ) {
$prefixed_option_name = $this->prefix( $option_name ); // how it is stored in DB.
$ret_val = get_option( $prefixed_option_name );
if ( ! $ret_val && $default ) {
$ret_val = $default;
}
return $ret_val;
}
/**
* Get plugin option value
*
* @param string $option_name name of plugin option.
* @param null $default default value tu return if not found.
* @return null
*/
public function get_plugin_option( $option_name, $default = null ) {
global $wpdb;
$ret_val = null;
$table_name = $wpdb->prefix . Adtechmedia_Config::get( 'plugin_table_name' );
// @codingStandardsIgnoreStart
$row = $wpdb->get_row(
$wpdb->prepare(
"SELECT option_value FROM `$table_name` WHERE option_name = %s LIMIT 1",
$option_name
)
);
// @codingStandardsIgnoreEnd
if ( is_object( $row ) ) {
$ret_val = $row->option_value;
}
if ( ! $ret_val && $default ) {
$ret_val = $default;
}
return $ret_val;
}
/**
* A wrapper function delegating to WP delete_option() but it prefixes the input $optionName
* to enforce "scoping" the options in the WP options table thereby avoiding name conflicts
*
* @param string $option_name defined in settings.php and set as keys of $this->optionMetaData.
* @return bool from delegated call to delete_option()
*/
public function delete_option( $option_name ) {
$prefixed_option_name = $this->prefix( $option_name ); // how it is stored in DB.
return delete_option( $prefixed_option_name );
}
/**
* Delete plugin option
*
* @param string $option_name name of option.
* @return bool
*/
public function delete_plugin_option( $option_name ) {
global $wpdb;
$table_name = $wpdb->prefix . Adtechmedia_Config::get( 'plugin_table_name' );
// @codingStandardsIgnoreStart
$result = $wpdb->delete( $table_name, array( 'option_name' => $option_name ) );
// @codingStandardsIgnoreEnd
if ( ! $result ) {
return false;
}
return true;
}
/**
* A wrapper function delegating to WP add_option() but it prefixes the input $optionName
* to enforce "scoping" the options in the WP options table thereby avoiding name conflicts
*
* @param string $option_mame defined in settings.php and set as keys of $this->optionMetaData.
* @param mixed $value the new value.
* @return null from delegated call to delete_option()
*/
public function add_option( $option_mame, $value ) {
$prefixed_option_name = $this->prefix( $option_mame ); // how it is stored in DB.
return add_option( $prefixed_option_name, $value );
}
/**
* Add new option to plugin
*
* @param string $option_name name of option.
* @param string $value value of option.
* @return bool
*/
public function add_plugin_option( $option_name, $value ) {
global $wpdb;
$table_name = $wpdb->prefix . Adtechmedia_Config::get( 'plugin_table_name' );
// @codingStandardsIgnoreStart
$result = $wpdb->query(
$wpdb->prepare(
"INSERT INTO `$table_name` (`option_name`, `option_value`) VALUES (%s, %s) ON DUPLICATE KEY UPDATE `option_name` = VALUES(`option_name`), `option_value` = VALUES(`option_value`)",
$option_name,
$value
)
);
// @codingStandardsIgnoreEnd
if ( ! $result ) {
return false;
}
return true;
}
/**
* A wrapper function delegating to WP add_option() but it prefixes the input $optionName
* to enforce "scoping" the options in the WP options table thereby avoiding name conflicts
*
* @param string $option_name defined in settings.php and set as keys of $this->option_meta_data.
* @param mixed $value the new value.
* @return null from delegated call to delete_option()
*/
public function update_option( $option_name, $value ) {
$prefixed_option_name = $this->prefix( $option_name ); // how it is stored in DB.
return update_option( $prefixed_option_name, $value );
}
/**
* Update plugin option
*
* @param string $option_name name of option.
* @param string $value value of option.
* @return bool
*/
public function update_plugin_option( $option_name, $value ) {
global $wpdb;
$table_name = $wpdb->prefix . Adtechmedia_Config::get( 'plugin_table_name' );
// @codingStandardsIgnoreStart
$result = $wpdb->update( $table_name, [ 'option_value' => $value ], array( 'option_name' => $option_name ) );
// @codingStandardsIgnoreEnd
if ( ! $result ) {
return false;
}
return true;
}
/**
* A Role Option is an option defined in getOptionMetaData() as a choice of WP standard roles, e.g.
* 'CanDoOperationX' => array('Can do Operation X', 'Administrator', 'Editor', 'Author', 'Contributor', 'Subscriber')
* The idea is use an option to indicate what role level a user must minimally have in order to do some operation.
* So if a Role Option 'CanDoOperationX' is set to 'Editor' then users which role 'Editor' or above should be
* able to do Operation X.
* Also see: canUserDoRoleOption()
*
* @param string $option_name name of option.
* @return string role name
*/
public function get_role_option( $option_name ) {
$role_allowed = $this->get_option( $option_name );
if ( ! $role_allowed || '' == $role_allowed ) {
$role_allowed = 'Administrator';
}
return $role_allowed;
}
/**
* Given a WP role name, return a WP capability which only that role and roles above it have
* http://codex.wordpress.org/Roles_and_Capabilities
*
* @param string $role_name name of role.
* @return string a WP capability or '' if unknown input role
*/
protected function role_to_capability( $role_name ) {
switch ( $role_name ) {
case 'Super Admin':
return 'manage_options';
case 'Administrator':
return 'manage_options';
case 'Editor':
return 'publish_pages';
case 'Author':
return 'publish_posts';
case 'Contributor':
return 'edit_posts';
case 'Subscriber':
return 'read';
case 'Anyone':
return 'read';
}
return '';
}
/**
* Check user role
*
* @param string $role_name a standard WP role name like 'Administrator'.
* @return bool
*/
public function is_user_role_equal_or_better_than( $role_name ) {
if ( 'Anyone' == $role_name ) {
return true;
}
$capability = $this->role_to_capability( $role_name );
return current_user_can( $capability );
}
/**
* Check user role
*
* @param string $option_name name of a Role option (see comments in getRoleOption()).
* @return bool indicates if the user has adequate permissions
*/
public function can_user_do_role_option( $option_name ) {
$role_allowed = $this->get_role_option( $option_name );
if ( 'Anyone' == $role_allowed ) {
return true;
}
return $this->is_user_role_equal_or_better_than( $role_allowed );
}
/**
* See: http://codex.wordpress.org/Creating_Options_Pages
*
* @return void
*/
public function create_settings_menu() {
$plugin_name = $this->get_plugin_display_name();
// create new top-level menu.
add_menu_page(
$plugin_name . ' Plugin Settings',
$plugin_name,
'administrator',
get_class( $this ),
array( &$this, 'settings_page' )
); // if you call 'plugins_url; be sure to "require_once" it.
// call register settings function.
add_action( 'admin_init', array( &$this, 'register_settings' ) );
}
/**
* Register settings
*/
public function register_settings() {
$settings_group = get_class( $this ) . '-settings-group';
$option_meta_data = $this->get_option_meta_data();
foreach ( $option_meta_data as $a_option_key => $a_option_meta ) {
register_setting( $settings_group, $a_option_meta );
}
}
/**
* Update property
*/
public function update_prop() {
$plugin_dir = plugin_dir_path( __FILE__ );
$file = $plugin_dir . '/js/atm.min.js';
// @codingStandardsIgnoreStart
@unlink( $file );
// @codingStandardsIgnoreEnd
Adtechmedia_Request::property_update_config(
$this->get_plugin_option( 'id' ),
$this->get_plugin_option( 'container' ),
$this->get_plugin_option( 'selector' ),
$this->get_plugin_option( 'price' ),
$this->get_plugin_option( 'ads_video' ),
$this->get_plugin_option( 'key' ),
$this->get_plugin_option( 'content_offset' ),
$this->get_plugin_option( 'content_lock' ),
$this->get_plugin_option( 'revenue_method' ),
$this->get_plugin_option( 'payment_pledged' ),
$this->get_plugin_option( 'content_offset_type' ),
$this->get_plugin_option( 'price_currency' ),
$this->get_plugin_option( 'content_paywall' ),
$this->get_target_cb_js( json_decode( stripslashes( $this->get_plugin_option( 'template_position' ) ), true ) ),
$this->get_toggle_cb_js( json_decode( stripslashes( $this->get_plugin_option( 'template_position' ) ), true ) )
);
Adtechmedia_ContentManager::clear_all_content();
}
/**
* Get JS to targetCb function
*
* @param array $position array of position properties.
* @return string
*/
public function get_target_cb_js( $position ) {
$width = ! empty( $position['width'] ) ? $position['width'] : '600px';
$offset_top = ! empty( $position['offset_top'] ) ? $position['offset_top'] : '0px';
$offset_left = ! empty( $position['offset_left'] ) ? $position['offset_left'] : '0px';
$content = '';
if ( ! empty( $position['sticky'] ) ) {
$content .= "mainModal.rootNode.style.position = 'fixed';\n";
$content .= "mainModal.rootNode.style.top = '$offset_top';\n";
$content .= "mainModal.rootNode.style.width = '$width';\n";
$offset_left = trim( $offset_left );
if ( '-' == $offset_left[0] ) {
$offset_left[0] = ' ';
$content .= "mainModal.rootNode.style.left = 'calc(50% - $offset_left)';\n";
} else {
$content .= "mainModal.rootNode.style.left = 'calc(50% + $offset_left)';\n";
}
$content .= "mainModal.rootNode.style.transform = 'translateX(-50%)';\n";
} else {
$content .= "mainModal.rootNode.style.width = '100%';\n";
}
return "function(modalNode, cb) {
var mainModal=modalNode;
mainModal.mount(document.querySelector('#content-for-atm-modal'), mainModal.constructor.MOUNT_APPEND);
mainModal.rootNode.classList.add('atm-targeted-container');
$content
cb();
}";
}
/**
* Get JS to toggleCb function
*
* @param array $position array of position properties.
* @return string
*/
public function get_toggle_cb_js( $position ) {
$scrolling_offset_top = ! empty( $position['scrolling_offset_top'] ) ? (int) $position['scrolling_offset_top'] : 0;
if ( empty( $position['sticky'] ) ) {
$scrolling_offset_top = -10;
}
return "function(cb) {
var adjustMarginTop = function (e) {
var modalOffset = (window.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop || 0) >= $scrolling_offset_top;
if (modalOffset) {
cb(true);
} else {
cb(false);
}
};
document.addEventListener('scroll', adjustMarginTop);
adjustMarginTop(null);}";
}
/**
* Creates HTML for the Administration page to set options for this plugin.
* Override this method to create a customized page.
*
* @return void
*/
public function settings_page() {
if ( ! current_user_can( 'manage_options' ) ) {
wp_die( esc_html__( 'You do not have sufficient permissions to access this page.', 'adtechmedia' ) );
}
$main_data = $this->get_main_data();
$plugin_meta_data = $this->get_plugin_meta_data();
$main_data_class = get_class( $this ) . '-main-settings-group';
$plugin_meta_data_class = get_class( $this ) . '-data-settings-group';
// Save Posted Options.
if ( isset( $_POST['option_page'] )
&& isset( $_POST['_wpnonce'] )
&& wp_verify_nonce( sanitize_text_field( wp_unslash( $_POST['_wpnonce'] ) ), $main_data_class . '-options' )
&& sanitize_text_field( wp_unslash( $_POST['option_page'] ) ) == $main_data_class
) {
$this->try_to_save_post( $main_data, $_POST );
Adtechmedia_Request::property_update(
$this->get_plugin_option( 'id' ),
$this->get_plugin_option( 'support_email' ),
$this->get_plugin_option( 'country' ),
$this->get_plugin_option( 'key' )
);
$this->update_prop();
} elseif ( isset( $_POST['option_page'] )
&& isset( $_POST['_wpnonce'] )
&& wp_verify_nonce( sanitize_text_field( wp_unslash( $_POST['_wpnonce'] ) ), $plugin_meta_data_class . '-options' )
&& sanitize_text_field( wp_unslash( $_POST['option_page'] ) ) == $plugin_meta_data_class
) {
$this->try_to_save_post( $plugin_meta_data, $_POST );
$this->update_prop();
}
require_once 'views/admin.php';
}
/**
* Try to save data from request
*
* @param array $options request data.
* @param array $post request data.
*/
public function try_to_save_post( $options, $post ) {
if ( null != $options ) {
foreach ( $options as $a_option_key => $a_option_meta ) {
if ( isset( $post[ $a_option_key ] ) ) {
$this->update_plugin_option( $a_option_key, $post[ $a_option_key ] );
}
}
}
}
/**
* Helper-function outputs the correct form element (input tag, select tag) for the given item
*
* @param string $a_option_key name of the option (un-prefixed).
* @param mixed $a_option_meta meta-data for $aOptionKey (either a string display-name or an array(display-name, option1, option2, ...).
* @param string $saved_option_value current value for $a_option_key.
* @param string $placeholder placeholder to field.
* @return void
*/
protected function create_form_control( $a_option_key, $a_option_meta, $saved_option_value, $placeholder = '' ) {
if ( is_array( $a_option_meta ) && count( $a_option_meta ) >= 2 ) { // Drop-down list.
$choices = array_slice( $a_option_meta, 1 );
?>
get_results( 'select version() as mysqlversion' );
// @codingStandardsIgnoreEnd
if ( ! empty( $rows ) ) {
return $rows[0]->mysqlversion;
}
return false;
}
/**
* If you want to generate an email address like "no-reply@your-site.com" then
* you can use this to get the domain name part.
* E.g. 'no-reply@' . $this->getEmailDomain();
* This code was stolen from the wp_mail function, where it generates a default
* from "wordpress@your-site.com"
*
* @return string domain name
*/
public function get_email_domain() {
// Get the site domain and get rid of www.
if ( ! isset( $_SERVER['SERVER_NAME'] ) ) {
return '';
}
$sitename = strtolower( sanitize_text_field( wp_unslash( $_SERVER['SERVER_NAME'] ) ) );
if ( substr( $sitename, 0, 4 ) == 'www.' ) {
$sitename = substr( $sitename, 4 );
}
return $sitename;
}
}