first commit

This commit is contained in:
2023-09-12 21:41:04 +02:00
commit 3361a7f053
13284 changed files with 2116755 additions and 0 deletions

View File

@@ -0,0 +1,147 @@
<?php
namespace JP\CC\Admin;
use JP\CC\Helpers;
use JP\CC\Options;
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
class Ajax {
public static function init() {
add_action( 'wp_ajax_jp_cc_object_search', array( __CLASS__, 'object_search' ) );
add_action( 'wp_ajax_jp_cc_options_autosave', array( __CLASS__, 'options_autosave' ) );
}
public static function options_autosave() {
// Make sure we have got the data we are expecting.
$nonce = isset( $_POST["nonce"] ) ? $_POST["nonce"] : "";
$option_key = isset( $_POST["key"] ) ? $_POST["key"] : false;
$option_value = isset( $_POST["value"] ) ? $_POST["value"] : null;
if ( wp_verify_nonce( $nonce, 'jp-cc-admin-nonce' ) && isset( $option_value ) ) {
if ( $option_key && ! empty( $option_key ) ) {
Options::update( $option_key, $option_value );
} else {
wp_send_json_error( "No option key was passed." );
}
} else {
// If the nonce was invalid or the comment was empty, send an error.
wp_send_json_error( "This came from the wrong place" );
}
wp_send_json_success( $option_value );
}
public static function object_search() {
$results = array(
'items' => array(),
'total_count' => 0,
);
$object_type = sanitize_text_field( $_REQUEST['object_type'] );
switch ( $object_type ) {
case 'post_type':
$post_type = ! empty( $_REQUEST['object_key'] ) ? sanitize_text_field( $_REQUEST['object_key'] ) : 'post';
$include = ! empty( $_REQUEST['include'] ) ? wp_parse_id_list( $_REQUEST['include'] ) : null;
$exclude = ! empty( $_REQUEST['exclude'] ) ? wp_parse_id_list( $_REQUEST['exclude'] ) : null;
if ( ! empty( $include ) && ! empty( $exclude ) ) {
$exclude = array_merge( $include, $exclude );
}
if ( $include ) {
$include_query = Helpers::post_type_selectlist_query( $post_type, array(
'post__in' => $include,
), true );
foreach ( $include_query['items'] as $id => $name ) {
$results['items'][ $id ] = array(
'id' => $id,
'text' => $name,
);
}
$results['total_count'] += $include_query['total_count'];
}
$query = Helpers::post_type_selectlist_query( $post_type, array(
's' => ! empty( $_REQUEST['s'] ) ? sanitize_text_field( $_REQUEST['s'] ) : null,
'paged' => ! empty( $_REQUEST['paged'] ) ? absint( $_REQUEST['paged'] ) : null,
'post__not_in' => $exclude,
'posts_per_page' => 10,
), true );
foreach ( $query['items'] as $id => $name ) {
$results['items'][ $id ] = array(
'id' => $id,
'text' => $name,
);
}
$results['total_count'] += $query['total_count'];
break;
case 'taxonomy':
$taxonomy = ! empty( $_REQUEST['object_key'] ) ? sanitize_text_field( $_REQUEST['object_key'] ) : 'category';
$include = ! empty( $_REQUEST['include'] ) ? wp_parse_id_list( $_REQUEST['include'] ) : null;
$exclude = ! empty( $_REQUEST['exclude'] ) ? wp_parse_id_list( $_REQUEST['exclude'] ) : null;
if ( ! empty( $include ) && ! empty( $exclude ) ) {
$exclude = array_merge( $include, $exclude );
}
if ( $include ) {
$include_query = Helpers::taxonomy_selectlist_query( $taxonomy, array(
'include' => $include,
), true );
foreach ( $include_query['items'] as $id => $name ) {
$results['items'][ $id ] = array(
'id' => $id,
'text' => $name,
);
}
$results['total_count'] += $include_query['total_count'];
}
$query = Helpers::taxonomy_selectlist_query( $taxonomy, array(
'search' => ! empty( $_REQUEST['s'] ) ? sanitize_text_field( $_REQUEST['s'] ) : null,
'paged' => ! empty( $_REQUEST['paged'] ) ? absint( $_REQUEST['paged'] ) : null,
'exclude' => $exclude,
'number' => 10,
), true );
foreach ( $query['items'] as $id => $name ) {
$results['items'][ $id ] = array(
'id' => $id,
'text' => $name,
);
}
$results['total_count'] += $query['total_count'];
break;
default:
// Do nothing if object is not post_type or taxonomy.
}
// Take out keys which were only used to deduplicate.
$results['items'] = array_values( $results['items'] );
echo json_encode( $results );
die();
}
}

View File

@@ -0,0 +1,151 @@
<?php
namespace JP\CC\Admin;
use JP_Content_Control;
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
class Assets {
public static function init() {
add_action( 'admin_enqueue_scripts', array( __CLASS__, 'scripts_styles' ) );
}
public static function scripts_styles( $hook ) {
global $post_type;
// Use minified libraries if SCRIPT_DEBUG is turned off
$suffix = ( defined( 'SCRIPT_DEBUG' ) && SCRIPT_DEBUG ) ? '' : '.min';
if ( $hook == 'widgets.php' ) {
wp_enqueue_style( 'jpcc-widget-editor', JP_Content_Control::$URL . 'assets/styles/widget-editor' . $suffix . '.css', null, JP_Content_Control::$VER, false );
wp_enqueue_script( 'jpcc-widget-editor', JP_Content_Control::$URL . 'assets/scripts/widget-editor' . $suffix . '.js', array( 'jquery' ), JP_Content_Control::$VER, true );
}
if ( $hook == 'settings_page_jp-cc-settings' ) {
if ( Settings::active_tab() == 'restrictions' ) {
add_action( 'admin_footer', array( __CLASS__, 'js_wp_editor' ) );
}
Footer_Templates::init();
wp_enqueue_style( 'jpcc-settings-page', JP_Content_Control::$URL . 'assets/styles/settings-page' . $suffix . '.css', array( 'editor-buttons' ), JP_Content_Control::$VER, false );
wp_enqueue_script( 'jpcc-settings-page', JP_Content_Control::$URL . 'assets/scripts/settings-page' . $suffix . '.js', array(
'jquery',
'underscore',
'wp-util',
'wplink',
'jquery-ui-sortable',
), JP_Content_Control::$VER, true );
wp_localize_script( 'jpcc-settings-page', 'jp_cc_vars', array(
'nonce' => wp_create_nonce( 'jp-cc-admin-nonce' ),
'I10n' => array(
'tabs' => array(
'general' => __( 'General', 'content-control' ),
'protection' => __( 'Protection', 'content-control' ),
'content' => __( 'Content', 'content-control' ),
),
'restrictions' => array(
'confirm_remove' => __( 'Are you sure you want to delete this restriction?', 'content-control' ),
),
'restriction_modal' => array(
'title' => __( 'Restriction Editor', 'content-control' ),
'description' => __( 'Use this to modify a restrictions settings.', 'content-control' ),
),
'conditions' => array(
'not_operand' => array(
'is' => __( 'Is', 'content-control' ),
'not' => __( 'Not', 'content-control' ),
),
),
'save' => __( 'Save', 'content-control' ),
'cancel' => __( 'Cancel', 'content-control' ),
'add' => __( 'Add', 'content-control' ),
'update' => __( 'Update', 'content-control' ),
),
) );
}
}
/*
* JavaScript Wordpress editor
* Author: Ante Primorac
* Author URI: http://anteprimorac.from.hr
* Version: 1.1
* License:
* Copyright (c) 2013 Ante Primorac
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
* Usage:
* server side(WP):
* js_wp_editor( $settings );
* client side(jQuery):
* $('textarea').wp_editor( options );
*/
public static function js_wp_editor( $settings = array() ) {
if ( ! class_exists( '\_WP_Editors' ) ) {
require( ABSPATH . WPINC . '/class-wp-editor.php' );
}
/*
ob_start();
wp_editor( '', 'jp_cc_id' );
ob_get_clean();
*/
$set = \_WP_Editors::parse_settings( 'jp_cc_id', $settings );
if ( ! current_user_can( 'upload_files' ) ) {
$set['media_buttons'] = false;
}
if ( $set['media_buttons'] ) {
wp_enqueue_style( 'buttons' );
wp_enqueue_script( 'thickbox' );
wp_enqueue_style( 'thickbox' );
wp_enqueue_script( 'media-upload' );
wp_enqueue_script( 'wp-embed' );
$post = get_post( 1 );
if ( ! $post && ! empty( $GLOBALS['post_ID'] ) ) {
$post = $GLOBALS['post_ID'];
}
wp_enqueue_media( array(
'post' => $post,
) );
}
\_WP_Editors::editor_settings( 'jp_cc_id', $set );
$jp_cc_vars = array(
'url' => get_home_url(),
'includes_url' => includes_url(),
);
wp_localize_script( 'jpcc-settings-page', 'jp_cc_wpeditor_vars', $jp_cc_vars );
}
}

View File

@@ -0,0 +1,515 @@
<?php
namespace JP\CC\Admin;
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
class Footer_Templates {
/**
*
*/
public static function init() {
if ( did_action( 'admin_footer' ) || doing_action( 'admin_footer' ) ) {
self::render();
} else {
add_action( 'admin_footer', array( __CLASS__, 'render' ) );
}
}
/**
*
*/
public static function render() {
self::general_fields();
self::html5_fields();
self::custom_fields();
self::misc_fields();
self::helpers();
self::conditions_editor();
self::restrictions();
}
/**
*
*/
public static function general_fields() {
?>
<script type="text/html" id="tmpl-jp-cc-field-text">
<input type="text" placeholder="{{data.placeholder}}" class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
</script>
<script type="text/html" id="tmpl-jp-cc-field-password">
<input type="password" placeholder="{{data.placeholder}}" class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
</script>
<script type="text/html" id="tmpl-jp-cc-field-select">
<select id="{{data.id}}" name="{{data.name}}" data-allow-clear="true" {{{data.meta}}}>
<# _.each(data.options, function(option, key) {
if (option.options !== undefined && option.options.length) { #>
<optgroup label="{{{option.label}}}">
<# _.each(option.options, function(option, key) { #>
<option value="{{option.value}}" {{{option.meta}}}>{{option.label}}</option>
<# }); #>
</optgroup>
<# } else { #>
<option value="{{option.value}}" {{{option.meta}}}>{{{option.label}}}</option>
<# }
}); #>
</select>
</script>
<script type="text/html" id="tmpl-jp-cc-field-radio">
<ul class="jp-cc-field-radio-list">
<# _.each(data.options, function(option, key) { #>
<li
<# print(option.value === data.value ? 'class="jp-cc-selected"' : ''); #>>
<input type="radio" id="{{data.id}}_{{key}}" name="{{data.name}}" value="{{option.value}}" {{{option.meta}}}/>
<label for="{{data.id}}_{{key}}">{{{option.label}}}</label>
</li>
<# }); #>
</ul>
</script>
<script type="text/html" id="tmpl-jp-cc-field-checkbox">
<input type="checkbox" id="{{data.id}}" name="{{data.name}}" value="1" {{{data.meta}}}/>
</script>
<script type="text/html" id="tmpl-jp-cc-field-multicheck">
<ul class="jp-cc-field-mulitcheck-list">
<# _.each(data.options, function(option, key) { #>
<li>
<input type="checkbox" id="{{data.id}}_{{key}}" name="{{data.name}}[{{option.value}}]" value="{{option.value}}" {{{option.meta}}}/>
<label for="{{data.id}}_{{key}}">{{option.label}}</label>
</li>
<# }); #>
</ul>
</script>
<script type="text/html" id="tmpl-jp-cc-field-textarea">
<textarea name="{{data.name}}" id="{{data.id}}" class="{{data.size}}-text" {{{data.meta}}}>{{data.value}}</textarea>
</script>
<script type="text/html" id="tmpl-jp-cc-field-hidden">
<input type="hidden" class="{{data.classes}}" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
</script>
<?php
}
/**
*
*/
public static function html5_fields() {
?>
<script type="text/html" id="tmpl-jp-cc-field-range">
<input type="range" placeholder="{{data.placeholder}}" class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
</script>
<script type="text/html" id="tmpl-jp-cc-field-search">
<input type="search" placeholder="{{data.placeholder}}" class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
</script>
<script type="text/html" id="tmpl-jp-cc-field-number">
<input type="number" placeholder="{{data.placeholder}}" class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
</script>
<script type="text/html" id="tmpl-jp-cc-field-email">
<input type="email" placeholder="{{data.placeholder}}" class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
</script>
<script type="text/html" id="tmpl-jp-cc-field-url">
<input type="url" placeholder="{{data.placeholder}}" class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
</script>
<script type="text/html" id="tmpl-jp-cc-field-tel">
<input type="tel" placeholder="{{data.placeholder}}" class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
</script>
<?php
}
/**
*
*/
public static function custom_fields() {
?>
<script type="text/html" id="tmpl-jp-cc-field-editor">
<textarea name="{{data.name}}" id="{{data.id}}" class="jp-cc-wpeditor {{data.size}}-text" {{{data.meta}}}>{{data.value}}</textarea>
</script>
<script type="text/html" id="tmpl-jp-cc-field-link">
<button type="button" class="dashicons dashicons-admin-generic button"></button>
<input type="text" placeholder="{{data.placeholder}}" class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
</script>
<script type="text/html" id="tmpl-jp-cc-field-rangeslider">
<input type="text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" class="jp-cc-range-manual" {{{data.meta}}}/>
<span class="jp-cc-range-value-unit regular-text">{{data.unit}}</span>
</script>
<script type="text/html" id="tmpl-jp-cc-field-color">
<input type="text" class="jp-cc-color-picker color-picker" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" data-default-color="{{data.std}}" {{{data.meta}}}/>
</script>
<script type="text/html" id="tmpl-jp-cc-field-measure">
<input type="number" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" size="5" {{{data.meta}}}/> <select id="{{data.id}}_unit" name="<# print(data.name.replace(data.id, data.id + '_unit')); #>">
<# _.each(data.units, function(option, key) { #>
<option value="{{option.value}}" {{{option.meta}}}>{{{option.label}}}</option>
<# }); #>
</select>
</script>
<script type="text/html" id="tmpl-jp-cc-field-license_key">
<input class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value.key}}" autocomplete="off" {{{data.meta}}}/>
<# if (data.value.key !== '') { #>
<?php wp_nonce_field( 'pum_license_activation', 'pum_license_activation_nonce' ); ?>
<# if (data.value.status === 'valid') { #>
<span class="jp-cc-license-status"><?php _e( 'Active', 'popup-maker' ); ?></span>
<input type="submit" class="button-secondary jp-cc-license-deactivate" id="{{data.id}}_deactivate" name="pum_license_deactivate[{{data.id}}]" value="<?php _e( 'Deactivate License', 'popup-maker' ); ?>"/>
<# } else { #>
<span class="jp-cc-license-status"><?php _e( 'Inactive', 'popup-maker' ); ?></span>
<input type="submit" class="button-secondary jp-cc-license-activate" id="{{data.id}}_activate" name="pum_license_activate[{{data.id}}]" value="<?php _e( 'Activate License', 'popup-maker' ); ?>"/>
<# } #>
<# } #>
<# if (data.value.messages && data.value.messages.length) { #>
<div class="jp-cc-license-messages">
<# for(var i=0; i < data.value.messages.length; i++) { #>
<p>{{{data.value.messages[i]}}}</p>
<# } #>
</div>
<# } #>
</script>
<script type="text/html" id="tmpl-jp-cc-field-datetime">
<div class="jp-cc-datetime">
<input placeholder="{{data.placeholder}}" data-input class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
<a class="input-button" data-toggle><i class="dashicons dashicons-calendar-alt"></i></a>
</div>
</script>
<script type="text/html" id="tmpl-jp-cc-field-datetimerange">
<div class="jp-cc-datetime-range">
<input placeholder="{{data.placeholder}}" data-input class="{{data.size}}-text" id="{{data.id}}" name="{{data.name}}" value="{{data.value}}" {{{data.meta}}}/>
<a class="input-button" data-toggle><i class="dashicons dashicons-calendar-alt"></i></a>
</div>
</script>
<script type="text/html" id="tmpl-jp-cc-field-ga_event_labels">
<# data.value = _.extend({
category:'',
action: '',
label: '',
value: 0,
}, data.value); #>
<table>
<tbody>
<tr>
<td>
<label for="{{data.id}}_category" style="padding-left: 3px;"><?php _e( 'Category', 'popup-maker' ); ?></label>
<input type="text" style="width:100%;" id="{{data.id}}_category" name="{{data.name}}[category]" value="{{data.value.category}}"/>
</td>
<td>
<label for="{{data.id}}_action" style="padding-left: 3px;"><?php _e( 'Action', 'popup-maker' ); ?></label>
<input type="text" style="width:100%;" id="{{data.id}}_action" name="{{data.name}}[action]" value="{{data.value.action}}"/>
</td>
<td>
<label for="{{data.id}}_label" style="padding-left: 3px;"><?php _e( 'Label', 'popup-maker' ); ?></label>
<input type="text" style="width:100%;" id="{{data.id}}_label" name="{{data.name}}[label]" value="{{data.value.label}}"/>
</td>
<td>
<label for="{{data.id}}_value" style="padding-left: 3px;"><?php _e( 'Value', 'popup-maker' ); ?></label>
<input type="number" style="width:100%;height: auto;" id="{{data.id}}_value" name="{{data.name}}[value]" value="{{data.value.value}}" step="0.01" max="999999" min="0"/>
</td>
</tr>
</tbody>
</table>
<hr/>
</script>
<?php
}
/**
*
*/
public static function misc_fields() {
?>
<script type="text/html" id="tmpl-jp-cc-field-section">
<div class="jp-cc-field-section {{data.classes}}">
<# _.each(data.fields, function(field) { #>
{{{field}}}
<# }); #>
</div>
</script>
<script type="text/html" id="tmpl-jp-cc-field-wrapper">
<div class="jp-cc-field jp-cc-field-{{data.type}} {{data.id}}-wrapper {{data.classes}}" data-id="{{data.id}}" <# print( data.dependencies !== '' ? "data-jp-cc-dependencies='" + data.dependencies + "'" : ''); #> <# print( data.dynamic_desc !== '' ? "data-jp-cc-dynamic-desc='" + data.dynamic_desc + "'" : ''); #>>
<# if (typeof data.label === 'string' && data.label.length > 0) { #>
<label for="{{data.id}}">
{{{data.label}}}
<# if (typeof data.doclink === 'string' && data.doclink !== '') { #>
<a href="{{data.doclink}}" title="<?php _e( 'Documentation', 'popup-maker' ); ?>: {{data.label}}" target="_blank" class="jp-cc-doclink dashicons dashicons-editor-help"></a>
<# } #>
</label>
<# } else { #>
<# if (typeof data.doclink === 'string' && data.doclink !== '') { #>
<a href="{{data.doclink}}" title="<?php _e( 'Documentation', 'popup-maker' ); ?>: {{data.label}}" target="_blank" class="jp-cc-doclink dashicons dashicons-editor-help"></a>
<# } #>
<# } #>
{{{data.field}}}
<# if (typeof data.desc === 'string' && data.desc.length > 0) { #>
<span class="jp-cc-desc desc">{{{data.desc}}}</span>
<# } #>
</div>
</script>
<script type="text/html" id="tmpl-jp-cc-field-html">
{{{data.content}}}
</script>
<script type="text/html" id="tmpl-jp-cc-field-heading">
<h3 class="jp-cc-field-heading">{{data.desc}}</h3>
</script>
<script type="text/html" id="tmpl-jp-cc-field-separator">
<# if (typeof data.desc === 'string' && data.desc.length > 0 && data.desc_position === 'top') { #>
<h3 class="jp-cc-field-heading">{{data.desc}}</h3>
<# } #>
<hr {{{data.meta}}}/>
<# if (typeof data.desc === 'string' && data.desc.length > 0 && data.desc_position === 'bottom') { #>
<h3 class="jp-cc-field-heading">{{data.desc}}</h3>
<# } #>
</script>
<?php
}
/**
*
*/
public static function helpers() {
?>
<script type="text/html" id="tmpl-jp-cc-modal">
<div id="{{data.id}}" class="jp-cc-modal-background {{data.classes}}" role="dialog" aria-hidden="true" aria-labelledby="{{data.id}}-title" aria-describedby="{{data.id}}-description" {{{data.meta}}}>
<div class="jp-cc-modal-wrap">
<form class="jp-cc-form">
<div class="jp-cc-modal-header">
<# if (data.title.length) { #>
<span id="{{data.id}}-title" class="jp-cc-modal-title">{{data.title}}</span>
<# } #>
<button type="button" class="jp-cc-modal-close" aria-label="<?php _e( 'Close', 'content-control' ); ?>"></button>
</div>
<# if (data.description.length) { #>
<span id="{{data.id}}-description" class="screen-reader-text">{{data.description}}</span>
<# } #>
<div class="jp-cc-modal-content">
{{{data.content}}}
</div>
<# if (data.save_button || data.cancel_button) { #>
<div class="jp-cc-modal-footer submitbox">
<# if (data.cancel_button) { #>
<div class="cancel">
<button type="button" class="submitdelete no-button" href="#">{{data.cancel_button}}</button>
</div>
<# } #>
<# if (data.save_button) { #>
<div class="jp-cc-submit">
<span class="spinner"></span>
<button class="button button-primary">{{data.save_button}}</button>
</div>
<# } #>
</div>
<# } #>
</form>
</div>
</div>
</script>
<script type="text/html" id="tmpl-jp-cc-tabs">
<div class="jp-cc-tabs-container {{data.classes}}" {{{data.meta}}}>
<ul class="tabs">
<# _.each(data.tabs, function(tab, key) { #>
<li class="tab">
<a href="#{{data.id + '_' + key}}">{{tab.label}}</a>
</li>
<# }); #>
</ul>
<# _.each(data.tabs, function(tab, key) { #>
<div id="{{data.id + '_' + key}}" class="tab-content">
{{{tab.content}}}
</div>
<# }); #>
</div>
</script>
<script type="text/html" id="tmpl-jp-cc-shortcode">
[{{{data.tag}}} {{{data.meta}}}]
</script>
<script type="text/html" id="tmpl-jp-cc-shortcode-w-content">
[{{{data.tag}}} {{{data.meta}}}]{{{data.content}}}[/{{{data.tag}}}]
</script>
<?php
}
/**
*
*/
public static function conditions_editor() {
?>
<script type="text/html" id="tmpl-jp-cc-field-conditions">
<# print(JPCC.conditions.template.editor({groups: data.value})); #>
</script>
<script type="text/html" id="tmpl-jp-cc-condition-editor">
<div class="facet-builder <# if (data.groups && data.groups.length) { print('has-conditions'); } #>">
<p>
<strong>
<?php _e( 'Apply this restriction if the user views content that is:', 'content-control' ); ?>
<?php /* printf( '%2$s<i class="dashicons dashicons-editor-help" title="%1$s"></i>%3$s',
__( 'Learn more about restriction content conditions', 'content-control' ),
'<a href="http://docs.wppopupmaker.com/article/140-conditions" target="_blank">',
'</a>'
); */ ?>
</strong>
</p>
<p><?php _e( 'When users visit your site, the plugin will check the viewed content against your selection below and permit or deny access.', 'content-control' ); ?></p>
<section class="jp-cc-alert-box" style="display:none"></section>
<div class="facet-groups condition-groups">
<#
_.each(data.groups, function (group, group_ID) {
print(JPCC.conditions.template.group({
index: group_ID,
facets: group
}));
});
#>
</div>
<div class="no-facet-groups">
<label for="jp-cc-first-condition"><?php _e( 'Choose a content type to get started.', 'content-control' ); ?></label>
<div class="jp-cc-field select jpselect2 jp-cc-facet-target">
<button type="button" class="jp-cc-not-operand" aria-label="<?php _e( 'Enable the Not Operand', 'content-control' ); ?>">
<span class="is"><?php _e( 'Is', 'content-control' ); ?></span>
<span class="not"><?php _e( 'Is Not', 'content-control' ); ?></span>
<input type="checkbox" id="jp-cc-first-facet-operand" value="1" />
</button>
<# print(JPCC.conditions.template.selectbox({id: 'jp-cc-first-condition', name: "", placeholder: "<?php _e( 'Choose a condition', 'content-control' ); ?>"})); #>
</div>
</div>
</div>
</script>
<script type="text/html" id="tmpl-jp-cc-condition-group">
<div class="facet-group-wrap" data-index="{{data.index}}">
<section class="facet-group">
<div class="facet-list">
<# _.each(data.facets, function (facet) {
print(JPCC.conditions.template.facet(facet));
}); #>
</div>
<div class="add-or">
<button type="button" class="add add-facet no-button" aria-label="<?php _ex( 'Add another OR condition', 'aria-label for add new OR condition button', 'content-control' ); ?>"><?php _e( 'or', 'content-control' ); ?></button>
</div>
</section>
<p class="and">
<button type="button" class="add-facet no-button" aria-label="<?php _ex( 'Add another AND condition group', 'aria-label for add new AND condition button', 'content-control' ); ?>"><?php _e( 'and', 'content-control' ); ?></button>
</p>
</div>
</script>
<script type="text/html" id="tmpl-jp-cc-condition-facet">
<div class="facet" data-index="{{data.index}}" data-target="{{data.target}}">
<i class="or"><?php _e( 'or', 'content-control' ); ?></i>
<div class="facet-col facet-target jp-cc-field jp-cc-facet-target select jpselect2 <# if (typeof data.not_operand !== 'undefined' && data.not_operand == '1') print('not-operand-checked'); #>">
<button type="button" class="jp-cc-not-operand" aria-label="<?php _e( 'Enable the Not Operand', 'content-control' ); ?>">
<span class="is"><?php _e( 'Is', 'content-control' ); ?></span>
<span class="not"><?php _e( 'Is Not', 'content-control' ); ?></span>
<input type="checkbox" name="conditions[{{data.group}}][{{data.index}}][not_operand]" value="1" <# if (typeof data.not_operand !== 'undefined') print(JPCC.checked(data.not_operand, true, true)); #> />
</button>
<# print(JPCC.conditions.template.selectbox({index: data.index, group: data.group, value: data.target, placeholder: "<?php _e( 'Choose a condition', 'content-control' ); ?>"})); #>
</div>
<div class="facet-settings facet-col">
<# print(JPCC.conditions.template.settings(data, data.settings)); #>
</div>
<div class="facet-actions">
<button type="button" class="remove remove-facet dashicons dashicons-dismiss no-button" aria-label="<?php _e( 'Remove Condition', 'content-control' ); ?>"></button>
</div>
</div>
</script>
<?php
}
public static function restrictions() {
?>
<script type="text/html" id="tmpl-jp-cc-restriction-table-row">
<tr data-index="{{data.index}}">
<th scope="row" class="check-column">
<label class="screen-reader-text" for="cb-select-{{data.index}}">
<?php _e( 'Select restriction', 'content-control' ); ?>
</label>
<input id="cb-select-{{data.index}}" type="checkbox" name="restriction[]" value="{{data.index}}">
<div class="locked-indicator"></div>
</th>
<td><i class="dashicons dashicons-menu"></i></td>
<td>
<strong>
<a href="#{{data.index}}" class="edit_restriction row-title">
{{data.title}}
</a>
</strong>
<input type="hidden" class="jp_cc_restriction" name="jp_cc_settings[restrictions][]" value='{{JSON.stringify(data)}}' />
<div class="row-actions">
<span class="edit">
<button type="button" class="edit_restriction no-button link-button" aria-label="<?php echo _x( 'Edit “{{data.title}}”', 'Edit button label for restriction table', 'content-control' ); ?>"><?php _e( 'Edit', 'content-control' ); ?></button> |
</span>
<span class="trash">
<button type="button" class="remove_restriction no-button link-button delete-button" aria-label="<?php echo _x( 'Delete “{{data.title}}!”', 'Trash button label for restriction table', 'content-control' ); ?>"><?php _e( 'Trash', 'content-control' ); ?></button> |
</span>
</div>
</td>
<td>
<# switch (data.who) {
case '' : print("<strong><?php _e( 'Everyone', 'content-control' ); ?></strong>");
break;
case 'logged_out' : print("<strong><?php _e( 'Logged Out Users', 'content-control' ); ?></strong>");
break;
case 'logged_in' :
print("<strong><?php _e( 'Logged In Users', 'content-control' ); ?></strong>: ");
if (Object.keys(data.roles).length !== 0) {
var roles = []
for (key in data.roles) {
roles.push(key.charAt(0).toUpperCase() + key.slice(1));
}
print(roles.join(', '));
} else {
print("<?php _e( 'All Users', 'content-control' ); ?>");
}
break;
} #>
<!--<br/>
<small>All Pages OR All Posts with Tag: XYZ</small>-->
</td>
</tr>
</script>
<?php
}
}

View File

@@ -0,0 +1,38 @@
<?php
// Exit if accessed directly
namespace JP\CC\Admin;
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
/**
* Class Pages
* @package JP\CC\Admin
*/
class Pages {
/**
*
*/
public static function init() {
add_action( 'admin_menu', array( __CLASS__, 'register_pages' ), 999 );
}
/**
* Register admin options pages.
*/
public static function register_pages() {
global $jp_cc_settings_page;
$jp_cc_settings_page = add_options_page( __( 'Content Control', 'content-control' ), __( 'Content Control', 'content-control' ), 'manage_options', 'jp-cc-settings', array(
'\\JP\CC\Admin\Settings',
'page',
) );
return $jp_cc_settings_page;
}
}

View File

@@ -0,0 +1,496 @@
<?php
namespace JP\CC\Admin;
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
/**
* Class JP\CC\Admin\Reviews
*
* This class adds a review request system for your plugin or theme to the WP dashboard.
*
* @since 1.1.0
*/
class Reviews {
/**
* Tracking API Endpoint.
*
* @var string
*/
public static $api_url;
/**
*
*/
public static function init() {
add_action( 'init', array( __CLASS__, 'hooks' ) );
add_action( 'wp_ajax_jp_cc_review_action', array( __CLASS__, 'ajax_handler' ) );
}
/**
* Hook into relevant WP actions.
*/
public static function hooks() {
if ( is_admin() && current_user_can( 'edit_posts' ) ) {
self::installed_on();
add_action( 'admin_notices', array( __CLASS__, 'admin_notices' ) );
add_action( 'network_admin_notices', array( __CLASS__, 'admin_notices' ) );
add_action( 'user_admin_notices', array( __CLASS__, 'admin_notices' ) );
}
}
/**
* Get the install date for comparisons. Sets the date to now if none is found.
*
* @return false|string
*/
public static function installed_on() {
$installed_on = get_option( 'jp_cc_reviews_installed_on', false );
if ( ! $installed_on ) {
$installed_on = current_time( 'mysql' );
update_option( 'jp_cc_reviews_installed_on', $installed_on );
}
return $installed_on;
}
/**
* AJAX Handler
*/
public static function ajax_handler() {
$args = wp_parse_args( $_REQUEST, array(
'group' => self::get_trigger_group(),
'code' => self::get_trigger_code(),
'pri' => self::get_current_trigger( 'pri' ),
'reason' => 'maybe_later',
) );
if ( ! wp_verify_nonce( $_REQUEST['nonce'], 'jp_cc_review_action' ) ) {
wp_send_json_error();
}
try {
$user_id = get_current_user_id();
$dismissed_triggers = self::dismissed_triggers();
$dismissed_triggers[ $args['group'] ] = $args['pri'];
update_user_meta( $user_id, '_jp_cc_reviews_dismissed_triggers', $dismissed_triggers );
update_user_meta( $user_id, '_jp_cc_reviews_last_dismissed', current_time( 'mysql' ) );
switch ( $args['reason'] ) {
case 'maybe_later':
update_user_meta( $user_id, '_jp_cc_reviews_last_dismissed', current_time( 'mysql' ) );
break;
case 'am_now':
case 'already_did':
self::already_did( true );
break;
default:
// Do nothing if the reason value does not match one of ours.
}
wp_send_json_success();
} catch ( \Exception $e ) {
wp_send_json_error( $e );
}
}
/**
* @return int|string
*/
public static function get_trigger_group() {
static $selected;
if ( ! isset( $selected ) ) {
$dismissed_triggers = self::dismissed_triggers();
$triggers = self::triggers();
foreach ( $triggers as $g => $group ) {
foreach ( $group['triggers'] as $t => $trigger ) {
if ( ! in_array( false, $trigger['conditions'] ) && ( empty( $dismissed_triggers[ $g ] ) || $dismissed_triggers[ $g ] < $trigger['pri'] ) ) {
$selected = $g;
break;
}
}
if ( isset( $selected ) ) {
break;
}
}
}
return $selected;
}
/**
* @return int|string
*/
public static function get_trigger_code() {
static $selected;
if ( ! isset( $selected ) ) {
$dismissed_triggers = self::dismissed_triggers();
foreach ( self::triggers() as $g => $group ) {
foreach ( $group['triggers'] as $t => $trigger ) {
if ( ! in_array( false, $trigger['conditions'] ) && ( empty( $dismissed_triggers[ $g ] ) || $dismissed_triggers[ $g ] < $trigger['pri'] ) ) {
$selected = $t;
break;
}
}
if ( isset( $selected ) ) {
break;
}
}
}
return $selected;
}
/**
* @param null $key
*
* @return bool|mixed
*/
public static function get_current_trigger( $key = null ) {
$group = self::get_trigger_group();
$code = self::get_trigger_code();
if ( ! $group || ! $code ) {
return false;
}
$trigger = self::triggers( $group, $code );
if ( empty( $key ) ) {
return $trigger;
} else {
return isset($trigger[$key]) ? $trigger[$key] : false;
}
}
/**
* Returns an array of dismissed trigger groups.
*
* Array contains the group key and highest priority trigger that has been shown previously for each group.
*
* $return = array(
* 'group1' => 20
* );
*
* @return array|mixed
*/
public static function dismissed_triggers() {
$user_id = get_current_user_id();
$dismissed_triggers = get_user_meta( $user_id, '_jp_cc_reviews_dismissed_triggers', true );
if ( ! $dismissed_triggers ) {
$dismissed_triggers = array();
}
return $dismissed_triggers;
}
/**
* Returns true if the user has opted to never see this again. Or sets the option.
*
* @param bool $set If set this will mark the user as having opted to never see this again.
*
* @return bool
*/
public static function already_did( $set = false ) {
$user_id = get_current_user_id();
if ( $set ) {
update_user_meta( $user_id, '_jp_cc_reviews_already_did', true );
return true;
}
return (bool) get_user_meta( $user_id, '_jp_cc_reviews_already_did', true );
}
/**
* Gets a list of triggers.
*
* @param null $group
* @param null $code
*
* @return bool|mixed
*/
public static function triggers( $group = null, $code = null ) {
static $triggers;
if ( ! isset( $triggers ) ) {
$link = 'https://wordpress.org/support/plugin/content-control/reviews/?rate=5#rate-response';
$time_message = __( 'Hi there! You\'ve been using the Content Control plugin on your site for %s now - We hope it\'s been helpful. If you\'re enjoying the plugin, would you mind rating it 5-stars to help spread the word?', 'content-control' );
$triggers = array(
'time_installed' => array(
'triggers' => array(
'one_week' => array(
'message' => sprintf( $time_message, __( '1 week', 'content-control' ) ),
'conditions' => array(
strtotime( self::installed_on() . ' +1 week' ) < time(),
),
'link' => $link,
'pri' => 10,
),
'one_month' => array(
'message' => sprintf( $time_message, __( '1 month', 'content-control' ) ),
'conditions' => array(
strtotime( self::installed_on() . ' +1 month' ) < time(),
),
'link' => $link,
'pri' => 20,
),
'three_months' => array(
'message' => sprintf( $time_message, __( '3 months', 'content-control' ) ),
'conditions' => array(
strtotime( self::installed_on() . ' +3 months' ) < time(),
),
'link' => $link,
'pri' => 30,
),
),
'pri' => 10,
),
);
$triggers = apply_filters( 'jp_cc_reviews_triggers', $triggers );
// Sort Groups
uasort( $triggers, array( __CLASS__, 'rsort_by_priority' ) );
// Sort each groups triggers.
foreach ( $triggers as $k => $v ) {
uasort( $triggers[ $k ]['triggers'], array( __CLASS__, 'rsort_by_priority' ) );
}
}
if ( isset( $group ) ) {
if ( ! isset( $triggers[ $group ] ) ) {
return false;
}
if ( ! isset( $code ) ) {
return $triggers[ $group ];
} else {
return isset( $triggers[ $group ]['triggers'][ $code ] ) ? $triggers[ $group ]['triggers'][ $code ] : false;
}
}
return $triggers;
}
/**
* Render admin notices if available.
*/
public static function admin_notices() {
if ( self::hide_notices() ) {
return;
}
$group = self::get_trigger_group();
$code = self::get_trigger_code();
$pri = self::get_current_trigger( 'pri' );
$trigger = self::get_current_trigger();
// Used to anonymously distinguish unique site+user combinations in terms of effectiveness of each trigger.
$uuid = wp_hash( home_url() . '-' . get_current_user_id() );
?>
<script type="text/javascript">
(function ($) {
var trigger = {
group: '<?php echo $group; ?>',
code: '<?php echo $code; ?>',
pri: '<?php echo $pri; ?>'
};
function dismiss(reason) {
$.ajax({
method: "POST",
dataType: "json",
url: ajaxurl,
data: {
action: 'jp_cc_review_action',
nonce: '<?php echo wp_create_nonce( 'jp_cc_review_action' ); ?>',
group: trigger.group,
code: trigger.code,
pri: trigger.pri,
reason: reason
}
});
<?php if ( ! empty( self::$api_url ) ) : ?>
$.ajax({
method: "POST",
dataType: "json",
url: '<?php echo self::$api_url; ?>',
data: {
trigger_group: trigger.group,
trigger_code: trigger.code,
reason: reason,
uuid: '<?php echo $uuid; ?>'
}
});
<?php endif; ?>
}
$(document)
.on('click', '.jp-cc-notice .jp-cc-dismiss', function (event) {
var $this = $(this),
reason = $this.data('reason'),
notice = $this.parents('.jp-cc-notice');
notice.fadeTo(100, 0, function () {
notice.slideUp(100, function () {
notice.remove();
});
});
dismiss(reason);
})
.ready(function () {
setTimeout(function () {
$('.jp-cc-notice button.notice-dismiss').click(function (event) {
dismiss('maybe_later');
});
}, 1000);
});
}(jQuery));
</script>
<style>
.jp-cc-notice p {
margin-bottom: 0;
}
.jp-cc-notice img.logo {
float: right;
margin-left: 10px;
width: 75px;
padding: 0.25em;
border: 1px solid #ccc;
}
</style>
<div class="notice notice-success is-dismissible jp-cc-notice">
<p>
<img class="logo" src="<?php echo \JP_Content_Control::$URL; ?>assets/images/icon-128x128.png" />
<strong>
<?php echo $trigger['message']; ?>
<br />
<?php
$names = array(
'<a target="_blank" href="https://twitter.com/danieliser" title="Follow Daniel on Twitter">@danieliser</a>',
'<a target="_blank" href="https://twitter.com/calumallison" title="Follow Calum on Twitter">@calumallison</a>',
);
shuffle( $names );
echo '~ ' . implode( ' & ', $names );
?>
</strong>
</p>
<ul>
<li>
<a class="jp-cc-dismiss" target="_blank" href="<?php echo $trigger['link']; ?>>" data-reason="am_now">
<strong><?php _e( 'Ok, you deserve it', 'content-control' ); ?></strong>
</a>
</li>
<li>
<a href="#" class="jp-cc-dismiss" data-reason="maybe_later">
<?php _e( 'Nope, maybe later', 'content-control' ); ?>
</a>
</li>
<li>
<a href="#" class="jp-cc-dismiss" data-reason="already_did">
<?php _e( 'I already did', 'content-control' ); ?>
</a>
</li>
</ul>
</div>
<?php
}
/**
* Checks if notices should be shown.
*
* @return bool
*/
public static function hide_notices() {
$code = self::get_trigger_code();
$conditions = array(
self::already_did(),
self::last_dismissed() && strtotime( self::last_dismissed() . ' +2 weeks' ) > time(),
empty( $code ),
);
return in_array( true, $conditions );
}
/**
* Gets the last dismissed date.
*
* @return false|string
*/
public static function last_dismissed() {
$user_id = get_current_user_id();
return get_user_meta( $user_id, '_jp_cc_reviews_last_dismissed', true );
}
/**
* Sort array by priority value
*
* @param $a
* @param $b
*
* @return int
*/
public static function sort_by_priority( $a, $b ) {
if ( ! isset( $a['pri'] ) || ! isset( $b['pri'] ) || $a['pri'] === $b['pri'] ) {
return 0;
}
return ( $a['pri'] < $b['pri'] ) ? - 1 : 1;
}
/**
* Sort array in reverse by priority value
*
* @param $a
* @param $b
*
* @return int
*/
public static function rsort_by_priority( $a, $b ) {
if ( ! isset( $a['pri'] ) || ! isset( $b['pri'] ) || $a['pri'] === $b['pri'] ) {
return 0;
}
return ( $a['pri'] < $b['pri'] ) ? 1 : - 1;
}
}

View File

@@ -0,0 +1,443 @@
<?php
namespace JP\CC\Admin;
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
class Setting_Callbacks {
private static $_prefix;
private static $_options;
public static function init( $prefix, $options = array() ) {
static::$_prefix = $prefix;
static::$_options = $options;
}
/**
* Header Callback
*
* Renders the header.
*
* @param array $args Arguments passed by the setting
*/
public static function header( $args ) {
echo '<hr/>';
}
/**
* Checkbox Callback
*
* Renders checkboxes.
*
* @param array $args Arguments passed by the setting
*/
public static function checkbox( $args ) {
$checked = isset( static::$_options[ $args['id'] ] ) ? checked( 1, static::$_options[ $args['id'] ], false ) : '';
$html = '<input type="checkbox" id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']" value="1" ' . $checked . '/>';
$html .= '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
echo $html;
}
/**
* Multicheck Callback
*
* Renders multiple checkboxes.
*
* @param array $args Arguments passed by the setting
*/
public static function multicheck( $args ) {
if ( ! empty( $args['options'] ) ) {
foreach ( $args['options'] as $key => $option ):
if ( isset( static::$_options[ $args['id'] ][ $key ] ) ) {
$enabled = $option;
} else {
$enabled = null;
}
echo '<input name="' . static::$_prefix . 'settings[' . $args['id'] . '][' . $key . ']" id="' . static::$_prefix . 'settings_' . $args['id'] . '[' . $key . ']" type="checkbox" value="' . $option . '" ' . checked( $option, $enabled, false ) . '/>&nbsp;';
echo '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '[' . $key . ']">' . $option . '</label><br/>';
endforeach;
echo '<p class="description">' . $args['desc'] . '</p>';
}
}
/**
* Radio Callback
*
* Renders radio boxes.
*
* @param array $args Arguments passed by the setting
*/
public static function radio( $args ) {
foreach ( $args['options'] as $key => $option ) :
$checked = false;
if ( isset( static::$_options[ $args['id'] ] ) && static::$_options[ $args['id'] ] == $key ) {
$checked = true;
} elseif ( isset( $args['std'] ) && $args['std'] == $key && ! isset( static::$_options[ $args['id'] ] ) ) {
$checked = true;
}
echo '<input name="' . static::$_prefix . 'settings[' . $args['id'] . ']"" id="' . static::$_prefix . 'settings_' . $args['id'] . '[' . $key . ']" type="radio" value="' . $key . '" ' . checked( true, $checked, false ) . '/>&nbsp;';
echo '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '[' . $key . ']">' . $option . '</label><br/>';
endforeach;
echo '<p class="description">' . $args['desc'] . '</p>';
}
/**
* Text Callback
*
* Renders text fields.
*
* @param array $args Arguments passed by the setting
*/
public static function text( $args ) {
if ( isset( static::$_options[ $args['id'] ] ) ) {
$value = static::$_options[ $args['id'] ];
} else {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
$readonly = $args['readonly'] === true ? ' readonly="readonly"' : '';
$size = ( isset( $args['size'] ) && ! is_null( $args['size'] ) ) ? $args['size'] : 'regular';
$html = '<input type="text" class="' . $size . '-text" id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']" value="' . esc_attr( stripslashes( $value ) ) . '"' . $readonly . '/>';
$html .= '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
echo $html;
}
/**
* Number Callback
*
* Renders number fields.
*
* @param array $args Arguments passed by the setting
*/
public static function number( $args ) {
if ( isset( static::$_options[ $args['id'] ] ) ) {
$value = static::$_options[ $args['id'] ];
} else {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
$max = isset( $args['max'] ) ? $args['max'] : 999999;
$min = isset( $args['min'] ) ? $args['min'] : 0;
$step = isset( $args['step'] ) ? $args['step'] : 1;
$size = ( isset( $args['size'] ) && ! is_null( $args['size'] ) ) ? $args['size'] : 'regular';
$html = '<input type="number" step="' . esc_attr( $step ) . '" max="' . esc_attr( $max ) . '" min="' . esc_attr( $min ) . '" class="' . $size . '-text" id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']" value="' . esc_attr( stripslashes( $value ) ) . '"/>';
$html .= '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
echo $html;
}
/**
* Textarea Callback
*
* Renders textarea fields.
*
* @param array $args Arguments passed by the setting
*/
public static function textarea( $args ) {
if ( isset( static::$_options[ $args['id'] ] ) ) {
$value = static::$_options[ $args['id'] ];
} else {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
$html = '<textarea class="large-text" cols="50" rows="5" id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']">' . esc_textarea( stripslashes( $value ) ) . '</textarea>';
$html .= '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
echo $html;
}
/**
* Password Callback
*
* Renders password fields.
*
* @param array $args Arguments passed by the setting
*/
public static function password( $args ) {
if ( isset( static::$_options[ $args['id'] ] ) ) {
$value = static::$_options[ $args['id'] ];
} else {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
$size = ( isset( $args['size'] ) && ! is_null( $args['size'] ) ) ? $args['size'] : 'regular';
$html = '<input type="password" class="' . $size . '-text" id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']" value="' . esc_attr( $value ) . '"/>';
$html .= '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
echo $html;
}
/**
* Missing Callback
*
* If a function is missing for settings callbacks alert the user.
*
* @param array $args Arguments passed by the setting
*
* @return void
*/
public static function missing( $args ) {
printf( __( 'The callback function used for the <strong>%s</strong> setting is missing.', 'content-control' ), $args['id'] );
}
/**
* Select Callback
*
* Renders select fields.
*
* @param array $args Arguments passed by the setting
*/
public static function select( $args ) {
if ( isset( static::$_options[ $args['id'] ] ) ) {
$value = static::$_options[ $args['id'] ];
} else {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
if ( isset( $args['placeholder'] ) ) {
$placeholder = $args['placeholder'];
} else {
$placeholder = '';
}
if ( isset( $args['chosen'] ) ) {
$chosen = 'class="'. static::$_prefix . '-chosen"';
} else {
$chosen = '';
}
$html = '<select id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']" ' . $chosen . 'data-placeholder="' . $placeholder . '" />';
foreach ( $args['options'] as $option => $name ) :
$selected = selected( $option, $value, false );
$html .= '<option value="' . $option . '" ' . $selected . '>' . $name . '</option>';
endforeach;
$html .= '</select>';
$html .= '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
echo $html;
}
/**
* Dashicon Callback
*
* Renders select fields with dashicon preview.
*
* @param array $args Arguments passed by the setting
*/
public static function dashicon( $args ) {
if ( isset( static::$_options[ $args['id'] ] ) ) {
$value = static::$_options[ $args['id'] ];
} else {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
$readonly = $args['readonly'] === true ? ' readonly="readonly"' : '';
$size = ( isset( $args['size'] ) && ! is_null( $args['size'] ) ) ? $args['size'] : 'regular';
$html = '<div class="dashicon-picker">';
$html .= '<input class="regular-text" type="hidden" class="' . $size . '-text" id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']" value="' . esc_attr( stripslashes( $value ) ) . '"' . $readonly . '/>';
$html .= '<span id="' . static::$_prefix . 'settings_' . $args['id'] . '_preview" class="dashicons-picker-preview dashicons ' . $value . '"></span>';
$html .= '<input type="button" data-target="#'. static::$_prefix . 'settings_' . $args['id'] . '" data-preview="#'. static::$_prefix . '_settings_' . $args['id'] . '_preview" class="button dashicons-picker" value="' . __( 'Choose Icon', 'content-control' ) . '" />';
$html .= '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
$html .= '</div>';
echo $html;
}
/**
* Color select Callback
*
* Renders color select fields.
*
* @param array $args Arguments passed by the setting
*/
public static function color_select( $args ) {
if ( isset( static::$_options[ $args['id'] ] ) ) {
$value = static::$_options[ $args['id'] ];
} else {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
$html = '<select id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']"/>';
foreach ( $args['options'] as $option => $color ) :
$selected = selected( $option, $value, false );
$html .= '<option value="' . $option . '" ' . $selected . '>' . $color['label'] . '</option>';
endforeach;
$html .= '</select>';
$html .= '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
echo $html;
}
/**
* Rich Editor Callback
*
* Renders rich editor fields.
*
* @param array $args Arguments passed by the setting
*
* @global $wp_version WordPress Version
*/
public static function rich_editor( $args ) {
global $wp_version;
if ( isset( static::$_options[ $args['id'] ] ) ) {
$value = static::$_options[ $args['id'] ];
if ( empty( $args['allow_blank'] ) && empty( $value ) ) {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
} else {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
$rows = isset( $args['size'] ) ? $args['size'] : 20;
if ( $wp_version >= 3.3 && function_exists( 'wp_editor' ) ) {
ob_start();
wp_editor( stripslashes( $value ), static::$_prefix . 'settings_' . $args['id'], array(
'textarea_name' => static::$_prefix . 'settings[' . $args['id'] . ']',
'textarea_rows' => $rows,
) );
$html = ob_get_clean();
} else {
$html = '<textarea class="large-text" rows="10" id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']">' . esc_textarea( stripslashes( $value ) ) . '</textarea>';
}
$html .= '<br/><label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
echo $html;
}
/**
* Upload Callback
*
* Renders upload fields.
*
* @param array $args Arguments passed by the setting
*/
public static function upload( $args ) {
if ( isset( static::$_options[ $args['id'] ] ) ) {
$value = static::$_options[ $args['id'] ];
} else {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
$size = ( isset( $args['size'] ) && ! is_null( $args['size'] ) ) ? $args['size'] : 'regular';
$html = '<input type="text" class="' . $size . '-text" id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']" value="' . esc_attr( stripslashes( $value ) ) . '"/>';
$html .= '<span>&nbsp;<input type="button" class="' . static::$_prefix . 'settings_upload_button button-secondary" value="' . __( 'Upload File', 'content-control' ) . '"/></span>';
$html .= '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
echo $html;
}
/**
* Color picker Callback
*
* Renders color picker fields.
*
* @param array $args Arguments passed by the setting
*/
public static function color( $args ) {
if ( isset( static::$_options[ $args['id'] ] ) ) {
$value = static::$_options[ $args['id'] ];
} else {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
$default = isset( $args['std'] ) ? $args['std'] : '';
$size = ( isset( $args['size'] ) && ! is_null( $args['size'] ) ) ? $args['size'] : 'regular';
$html = '<input type="text" class="'. static::$_prefix . 'color-picker" id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']" value="' . esc_attr( $value ) . '" data-default-color="' . esc_attr( $default ) . '" />';
$html .= '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
echo $html;
}
/**
* Descriptive text callback.
*
* Renders descriptive text onto the settings field.
*
* @param array $args Arguments passed by the setting
*
* @return void
*/
public static function descriptive_text( $args ) {
echo wp_kses_post( $args['desc'] );
}
/**
* Registers the license field callback for Software Licensing
*
* @param array $args Arguments passed by the setting
*/
public static function license_key( $args ) {
if ( isset( static::$_options[ $args['id'] ] ) ) {
$value = static::$_options[ $args['id'] ];
} else {
$value = isset( $args['std'] ) ? $args['std'] : '';
}
$size = ( isset( $args['size'] ) && ! is_null( $args['size'] ) ) ? $args['size'] : 'regular';
$html = '<input type="text" class="' . $size . '-text" id="' . static::$_prefix . 'settings_' . $args['id'] . '" name="' . static::$_prefix . 'settings[' . $args['id'] . ']" value="' . esc_attr( $value ) . '"/>';
if ( 'valid' == get_option( $args['options']['is_valid_license_option'] ) ) {
$html .= '<input type="submit" class="button-secondary" name="' . $args['id'] . '_deactivate" value="' . __( 'Deactivate License', 'content-control' ) . '"/>';
}
$html .= '<label class="field-description" for="' . static::$_prefix . 'settings_' . $args['id'] . '"> ' . $args['desc'] . '</label>';
wp_nonce_field( $args['id'] . '-nonce', $args['id'] . '-nonce' );
echo $html;
}
/**
* Hook Callback
*
* Adds a do_action() hook in place of the field
*
* @param array $args Arguments passed by the setting
*
* @return void
*/
public static function hook( $args ) {
do_action( static::$_prefix . $args['id'], $args );
}
}

View File

@@ -0,0 +1,319 @@
<?php
namespace JP\CC\Admin;
use JP\CC\Helpers;
use JP\CC\Options;
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
class Settings {
private static $title;
private static $_tabs;
private static $_prefix;
public static function init( $title, $tabs = array() ) {
static::$title = $title;
static::$_tabs = $tabs;
static::$_prefix = trim( Options::$_prefix, '_' ) . '_';
Settings\Restrictions::init();
add_action( 'admin_init', array( __CLASS__, 'register_settings' ) );
add_filter( static::$_prefix . 'settings_sanitize_text', array( __CLASS__, 'sanitize_text_field' ) );
add_filter( static::$_prefix . 'settings_sanitize_field_restrictions', array( __CLASS__, 'sanitize_restrictions' ), 10, 2 );
}
/**
* Render settings page with tabs.
*/
public static function page() {
?>
<div class="wrap">
<h1><?php echo esc_html( static::$title ); ?></h1>
<h2 id="<?php echo static::$_prefix; ?>tabs" class="nav-tab-wrapper"><?php
foreach ( static::tabs() as $id => $tab ) {
$active = $tab['active'] ? ' nav-tab-active' : '';
echo '<a href="' . esc_url( $tab['url'] ) . '" title="' . esc_attr( $tab['label'] ) . '" class="nav-tab' . $active . '">';
echo esc_html( $tab['label'] );
echo '</a>';
} ?>
</h2>
<form id="<?php echo static::$_prefix; ?>settings" method="post" action="options.php">
<?php do_action( static::$_prefix . 'form_nonce' ); ?>
<?php settings_fields( static::$_prefix . 'settings' ); ?>
<div id="poststuff">
<div id="post-body" class="metabox-holder columns-1">
<div id="post-body-content">
<div id="tab_container"><?php
if ( static::active_tab() == 'restrictions' ) :
do_action( 'jp_cc_restriction_editor' );
else : ?>
<table class="form-table"><?php
Setting_Callbacks::init( static::$_prefix, Options::get_all() );
do_settings_fields( static::$_prefix . 'settings_' . static::active_tab(), static::$_prefix . 'settings_' . static::active_tab() ); ?>
</table>
<?php endif;
submit_button(); ?>
</div>
<!-- #tab_container-->
</div>
</div>
<br class="clear" />
</div>
</form>
</div>
<?php
}
/**
* Returns all settings tabs, with labels, urls & status.
*
* @return array
*/
public static function tabs() {
static $tabs;
if ( ! isset( $tabs ) ) {
$tabs = array();
$registered_settings = static::registered_settings();
reset( static::$_tabs );
$active_tab = isset( $_GET['tab'] ) ? $_GET['tab'] : key( static::$_tabs );
foreach ( static::$_tabs as $id => $label ) {
if ( ! empty( $registered_settings[ $id ] ) ) {
$tabs[ $id ] = array(
'label' => $label,
'active' => $id == $active_tab,
'url' => add_query_arg( array(
'settings-updated' => false,
'tab' => $id,
) ),
);
}
}
}
return $tabs;
}
/**
* Check for the active / current tab.
*
* @return bool|string
*/
public static function active_tab() {
static $active;
if ( ! isset( $active ) ) {
$active = false;
foreach ( static::tabs() as $id => $tab ) {
if ( $tab['active'] ) {
$active = $id;
}
}
}
return $active;
}
/**
* Retrieve the array of plugin settings
*
* @since 1.0.0
* @return array
*/
public static function registered_settings() {
static $settings;
if ( ! isset( $settings ) ) {
/**
* 'Whitelisted' settings, filters are provided for each settings.
*/
$settings = array(
/** General Settings */
'restrictions' => apply_filters( static::$_prefix . 'settings_restrictions', array(
'restrictions' => array(
'id' => 'restrictions',
'type' => 'hook',
),
) ),
'general' => apply_filters( static::$_prefix . 'settings_general', array(
'default_denial_message' => array(
'id' => 'default_denial_message',
'label' => __( 'Default Denial Message', 'content-control' ),
'type' => 'rich_editor',
),
) ),
/** Addon Settings */
//'addons' => apply_filters( static::$_prefix . 'settings_addons', array() ),
//'licenses' => apply_filters( static::$_prefix . 'settings_licenses', array() ),
/** Misc Settings */
'misc' => apply_filters( static::$_prefix . 'settings_misc', array() ),
);
$settings = apply_filters( static::$_prefix . 'registered_settings', $settings );
}
return $settings;
}
public static function register_settings() {
if ( false == get_option( static::$_prefix . 'settings' ) ) {
add_option( static::$_prefix . 'settings' );
}
foreach ( static::registered_settings() as $tab => $settings ) {
$page = static::$_prefix . 'settings_' . $tab;
add_settings_section( $page, __return_null(), '__return_false', $page );
foreach ( $settings as $id => $option ) {
$name = isset( $option['label'] ) ? $option['label'] : '';
if ( method_exists( '\\JP\CC\Admin\Setting_Callbacks', $option['type'] ) ) {
$callback = array( '\\JP\CC\Admin\Setting_Callbacks', $option['type'] );
} elseif ( function_exists( static::$_prefix . $option['type'] . '_callback' ) ) {
$callback = static::$_prefix . $option['type'] . '_callback';
} else {
$callback = array( '\\JP\CC\Setting_Callbacks', 'missing_callback' );
}
add_settings_field( static::$_prefix . 'settings_' . $option['id'], $name, $callback, $page, $page, array(
'section' => $tab,
'id' => isset( $option['id'] ) ? $option['id'] : $id,
'desc' => ! empty( $option['desc'] ) ? $option['desc'] : '',
// TODO replace the hardcoded names in Setting_Callbacks with this value.
'name' => isset( $option['name'] ) ? $option['name'] : null,
'size' => isset( $option['size'] ) ? $option['size'] : null,
'options' => isset( $option['options'] ) ? $option['options'] : '',
'std' => isset( $option['std'] ) ? $option['std'] : '',
'min' => isset( $option['min'] ) ? $option['min'] : null,
'max' => isset( $option['max'] ) ? $option['max'] : null,
'step' => isset( $option['step'] ) ? $option['step'] : null,
'chosen' => isset( $option['chosen'] ) ? $option['chosen'] : null,
'placeholder' => isset( $option['placeholder'] ) ? $option['placeholder'] : null,
'allow_blank' => isset( $option['allow_blank'] ) ? $option['allow_blank'] : true,
'readonly' => isset( $option['readonly'] ) ? $option['readonly'] : false,
) );
}
}
// Creates our settings in the options table
register_setting( static::$_prefix . 'settings', static::$_prefix . 'settings', array( __CLASS__, 'settings_sanitize' ) );
}
public static function settings_sanitize( $input ) {
if ( empty( $_POST['_wp_http_referer'] ) ) {
return $input;
}
$current_values = Options::get_all();
parse_str( $_POST['_wp_http_referer'], $referrer );
$prefix = static::$_prefix;
$tab = isset( $referrer['tab'] ) ? $referrer['tab'] : static::active_tab();
$settings = static::registered_settings();
$input = $input ? $input : array();
// Apply a filter per tab like jp_cc_settings_general_sanitize
$input = apply_filters( "{$prefix}settings_{$tab}_sanitize", $input );
// Loop through each setting being saved and pass it through a sanitization filter
foreach ( $input as $key => $value ) {
// Field id specific filter
$value = apply_filters( "{$prefix}settings_sanitize_field_{$key}", $value );
// Get the setting type (checkbox, select, etc)
$type = isset( $settings[ $tab ][ $key ]['type'] ) ? $settings[ $tab ][ $key ]['type'] : false;
if ( $type ) {
// Field type specific filter
$value = apply_filters( "{$prefix}settings_sanitize_{$type}", $value, $key );
}
// General filter
$input[ $key ] = apply_filters( "{$prefix}settings_sanitize", $value, $key );
}
// Loop through the whitelist and unset any that are empty for the tab being saved
if ( ! empty( $settings[ $tab ] ) ) {
foreach ( $settings[ $tab ] as $key => $value ) {
// settings used to have numeric keys, now they have keys that match the option ID. This ensures both methods work
if ( is_numeric( $key ) ) {
$key = $value['id'];
}
if ( empty( $input[ $key ] ) ) {
unset( $current_values[ $key ] );
}
}
}
// Merge our new settings with the existing
$output = array_merge( $current_values, $input );
add_settings_error( 'jp-cc-notices', '', __( 'Settings updated.', 'content-control' ), 'updated' );
return $output;
}
public static function sanitize_restrictions( $restrictions = array() ) {
if ( ! empty( $restrictions ) ) {
foreach ( $restrictions as $key => $restriction ) {
if ( is_string( $restriction ) ) {
try {
$restriction = json_decode( $restriction );
} catch ( \Exception $e ) {};
}
$restrictions[ $key ] = Helpers::object_to_array( $restriction );
}
}
return $restrictions;
}
/**
* Sanitize text fields
*
* @param array $input The field value
*
* @return string $input Sanitizied value
*/
public static function sanitize_text_field( $input ) {
return trim( $input );
}
}

View File

@@ -0,0 +1,206 @@
<?php
namespace JP\CC\Admin\Settings;
use JP\CC\Helpers;
use JP\CC\Options;
use JP\CC\Conditions;
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
class Restrictions {
public static function init() {
add_action( 'jp_cc_restriction_editor', array( __CLASS__, 'restrictions_editor' ) );
}
public static function restrictions_editor() {
$restrictions = Options::get( 'restrictions', array() );
$restrictions = Helpers::object_to_array( $restrictions );
// Remove array keys.
$restrictions = array_values( $restrictions );
?>
<script type="text/javascript">
var jp_cc_restrictions = <?php echo json_encode( $restrictions ); ?>,
jp_cc_conditions = <?php echo json_encode( Conditions::instance()->get_conditions() ); ?>,
jp_cc_conditions_selectlist = <?php echo json_encode( Conditions::instance()->conditions_dropdown_list() ); ?>,
jp_cc_restriction_fields = <?php echo json_encode( static::fields() ); ?>;
</script>
<button class="add_new_restriction button" type="button"><?php _e( 'Add a Restriction', 'content-control' ); ?></button>
<div class="tablenav top">
<div class="alignleft actions bulkactions">
<label for="bulk-action-selector-top" class="screen-reader-text"><?php _e( 'Select bulk action', 'content-control' ); ?></label>
<select id="bulk-action-selector-top">
<option value="-1"><?php _e( 'Bulk Actions', 'content-control' ); ?></option>
<option value="trash"><?php _e( 'Move to Trash', 'content-control' ); ?></option>
</select>
<input type="button" class="button action" value="<?php _e( 'Apply', 'content-control' ); ?>" />
</div>
<br class="clear">
</div>
<table id="jp-cc-restrictions" class="wp-list-table widefat fixed striped posts">
<thead>
<tr>
<td id="cb" class="manage-column column-cb check-column">
<label class="screen-reader-text" for="cb-select-all-1"><?php _e( 'Select All', 'content-control' ); ?></label>
<input id="cb-select-all-1" type="checkbox" />
</td>
<th width="60" id="priority" class="manage-column column-priority" scope="col"><?php _e( 'Priority', 'content-control' ); ?></th>
<th id="title" class="manage-column column-title column-primary" scope="col"><?php _e( 'Restriction Title', 'content-control' ); ?></th>
<th id="overview" class="manage-column column-overview" scope="col"><?php _e( 'Overview', 'content-control' ); ?></th>
</tr>
</thead>
<tfoot>
<tr>
<td id="cb" class="manage-column column-cb check-column">
<label class="screen-reader-text" for="cb-select-all-1"><?php _e( 'Select All', 'content-control' ); ?></label>
<input id="cb-select-all-1" type="checkbox" />
</td>
<th id="priority" class="manage-column column-priority" scope="col"><?php _e( 'Priority', 'content-control' ); ?></th>
<th id="title" class="manage-column column-title column-primary" scope="col"><?php _e( 'Restriction Title', 'content-control' ); ?></th>
<th id="overview" class="manage-column column-overview" scope="col"><?php _e( 'Overview', 'content-control' ); ?></th>
</tr>
</tfoot>
<tbody class="no-items">
<tr>
<td class="colspanchange" colspan="4"><?php _e( 'No restrictions found.', 'content-control' ); ?></td>
</tr>
</tbody>
<tbody class="has-items">
</tbody>
</table>
<div class="tablenav bottom">
<div class="alignleft actions bulkactions">
<label for="bulk-action-selector-bottom" class="screen-reader-text">Select bulk action</label><select name="action2" id="bulk-action-selector-bottom">
<option value="-1"><?php _e( 'Bulk Actions', 'content-control' ); ?></option>
<option value="trash"><?php _e( 'Move to Trash', 'content-control' ); ?></option>
</select>
<input type="button" class="button action" value="<?php _e( 'Apply', 'content-control' ); ?>" />
</div>
<br class="clear">
</div>
<?php
}
public static function fields() {
return array(
'general' => array(
array(
'type' => 'text',
'id' => 'title',
'name' => 'title',
'label' => __( 'Restriction Title', 'content-control' ),
'placeholder' => __( 'Pages restricted to logged in users', 'content-control' ),
'std' => '',
),
array(
'type' => 'select',
'id' => 'who',
'name' => 'who',
'label' => __( 'Who can see this content?', 'content-control' ),
'std' => '',
'options' => array(
// '' = > __( "Everyone", 'content-control' ),
'logged_in' => __( "Logged In Users", 'content-control' ),
'logged_out' => __( "Logged Out Users", 'content-control' ),
),
),
array(
'type' => 'multicheck',
'id' => 'roles',
'name' => 'roles',
'label' => __( 'Choose which roles can see this content', 'content-control' ),
'options' => \JP\CC\Roles::allowed_user_roles(),
'dependencies' => array(
'who' => 'logged_in',
),
),
),
'protection' => array(
array(
'type' => 'select',
'id' => 'protection_method',
'name' => 'protection_method',
'label' => __( 'Choose how to protect your content', 'content-control' ),
'options' => array(
'custom_message' => __( 'Custom Message', 'content-control' ),
'redirect' => __( 'Redirect', 'content-control' ),
),
'std' => 'redirect',
),
array(
'type' => 'checkbox',
'id' => 'show_excerpts',
'name' => 'show_excerpts',
'dependencies' => array(
'protection_method' => 'custom_message',
),
'label' => __( 'Show excerpts above access denied message?', 'content-control' ),
),
array(
'type' => 'checkbox',
'id' => 'override_default_message',
'name' => 'override_default_message',
'label' => __( 'Override the default message?', 'content-control' ),
'dependencies' => array(
'protection_method' => 'custom_message',
),
),
array(
'type' => 'editor',
'id' => 'custom_message',
'name' => 'custom_message',
'label' => __( 'Enter a custom message to display to restricted users', 'content-control' ),
'dependencies' => array(
'protection_method' => 'custom_message',
'override_default_message' => true,
),
),
array(
'type' => 'select',
'id' => 'redirect_type',
'name' => 'redirect_type',
'label' => __( 'Where will they be taken?', 'content-control' ),
'classes' => 'protection_method--redirect',
'options' => array(
'login' => __( 'Login & Back', 'content-control' ),
'home' => __( 'Home Page', 'content-control' ),
'custom' => __( 'Custom URL', 'content-control' ),
),
'std' => 'login',
'dependencies' => array(
'protection_method' => 'redirect',
),
),
array(
'type' => 'link',
'id' => 'redirect_url',
'name' => 'redirect_url',
'classes' => 'redirect_type--custom',
'label' => __( 'Redirect URL', 'content-control' ),
'placeholder' => __( 'http://example.com', 'content-control' ),
'std' => '',
'dependencies' => array(
'protection_method' => 'redirect',
'redirect_type' => 'custom',
),
),
),
'content' => array(
array(
'type' => 'conditions',
'id' => 'conditions',
'name' => 'conditions',
),
),
);
}
}

View File

@@ -0,0 +1,114 @@
<?php
namespace JP\CC\Admin\Widget;
use JP\CC\Widget;
use JP\CC\Roles;
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
/**
* Class JP\CC\Admin\Widget_Settings
*/
class Settings {
/**
* Initialize Widget Settings
*/
public static function init() {
add_action( 'in_widget_form', array( __CLASS__, 'fields' ), 5, 3 );
add_filter( 'widget_update_callback', array( __CLASS__, 'save' ), 5, 3 );
}
/**
* Renders additional widget option fields.
*
* @param $widget
* @param $return
* @param $instance
*/
public static function fields( $widget, $return, $instance ) {
$allowed_user_roles = Roles::allowed_user_roles();
wp_nonce_field( 'jpcc-menu-editor-nonce', 'jpcc-menu-editor-nonce' );
$which_users_options = array(
'' => __( 'Everyone', 'content-control' ),
'logged_out' => __( 'Logged Out Users', 'content-control' ),
'logged_in' => __( 'Logged In Users', 'content-control' ),
);
$instance = Widget::parse_options( $instance ); ?>
<p class="widget_options-which_users">
<label for="<?php echo $widget->get_field_id( 'which_users' ); ?>">
<?php _e( 'Who can see this widget?', 'content-control' ); ?><br />
<select name="<?php echo $widget->get_field_name( 'which_users' ); ?>" id="<?php echo $widget->get_field_id( 'which_users' ); ?>" class="widefat">
<?php foreach ( $which_users_options as $option => $label ) : ?>
<option value="<?php echo $option; ?>" <?php selected( $option, $instance['which_users'] ); ?>>
<?php echo esc_html( $label ); ?>
</option>
<?php endforeach; ?>
</select>
</label>
</p>
<p class="widget_options-roles">
<?php _e( 'Choose which roles can see this widget', 'content-control' ); ?><br />
<?php foreach ( $allowed_user_roles as $option => $label ) : ?>
<label>
<input type="checkbox" name="<?php echo $widget->get_field_name( 'roles' ); ?>[]" value="<?php echo $option; ?>" <?php checked( in_array( $option, $instance['roles'] ), true ); ?>/>
<?php echo esc_html( $label ); ?>
</label>
<?php endforeach; ?>
</p>
<?php
}
/**
* Validates & saves additional widget options.
*
* @param $instance
* @param $new_instance
*
* @return array|bool
*/
public static function save( $instance, $new_instance ) {
if ( ! isset( $_POST['jpcc-menu-editor-nonce'] ) || ! wp_verify_nonce( $_POST['jpcc-menu-editor-nonce'], 'jpcc-menu-editor-nonce' ) ) {
return false;
}
$new_instance = Widget::parse_options( $new_instance );
if ( $new_instance['which_users'] == 'logged_in' ) {
$allowed_roles = Roles::allowed_user_roles();
// Validate chosen roles and remove non-allowed roles.
foreach ( (array) $new_instance['roles'] as $key => $role ) {
if ( ! array_key_exists( $role, $allowed_roles ) ) {
unset( $new_instance['roles'][ $key ] );
}
}
} else {
unset( $new_instance['roles'] );
}
return $new_instance;
}
}