Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add more support for entry "Read Status" #1716

Merged
merged 29 commits into from
May 27, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
29 commits
Select commit Hold shift + click to select a range
3dd5dc3
Start work on #1180
zackkatz Jul 15, 2021
b2caaf5
Merge branch 'develop' into feature/1180-is-read-status
omarkasem Mar 8, 2023
b18439e
Mark an entry as read when it's viewed on the front-end
omarkasem Mar 9, 2023
0dd6ae2
fix issues
omarkasem Mar 17, 2023
07a2cad
Add Search Bar filters for read status
omarkasem Mar 18, 2023
ce0ac6a
formatting
omarkasem Mar 18, 2023
1bc0655
Merge branch 'develop' into feature/1180-is-read-status
omarkasem May 12, 2023
1e022c4
Merge branch 'develop' into feature/1180-is-read-status
omarkasem May 12, 2024
a4f989d
Fix merge
omarkasem May 12, 2024
66d280d
Remove entry_meta_key so we don't get the callback to override the t…
omarkasem May 15, 2024
925dd4f
Update the textdomain
zackkatz Mar 13, 2024
262e2db
Fix the code running even when the entry was read
zackkatz May 21, 2024
3806100
Remove deprecated code
zackkatz May 21, 2024
94d1161
Fix AJAX not running w/out Read Status field
zackkatz May 21, 2024
e1f8d6a
Improve readability by naming the filter directly
zackkatz May 21, 2024
85ae93e
Use short array syntax
zackkatz May 21, 2024
8b64373
Add a filter to allow disabling printing of scripts
zackkatz May 21, 2024
ae3b15e
Update readme.txt
zackkatz May 21, 2024
5249688
Use the custom value when updating label via AJAX
zackkatz May 21, 2024
b3710d5
Merge branch 'develop' into feature/1180-is-read-status
zackkatz May 21, 2024
0c738d5
Restore the meta key to enable sorting
zackkatz May 21, 2024
0f78e1d
Don't run during tests
zackkatz May 21, 2024
3185178
Don't override entry meta with our class.
zackkatz May 21, 2024
3814691
Add one more filter for the label, just in case.
zackkatz May 21, 2024
f583d3f
Fix sorting by the "Is Read" field
mrcasual May 27, 2024
4077c2a
Update docblocks, filter names, etc.
mrcasual May 27, 2024
bec9580
Merge 'develop' and fix conflicts
mrcasual May 27, 2024
11a760f
Use class imports
mrcasual May 27, 2024
c4d2dbc
Use the correct filter name
mrcasual May 27, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
236 changes: 236 additions & 0 deletions includes/fields/class-gravityview-field-is-read.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,236 @@
<?php
/**
* @file class-gravityview-field-is-read.php
* @since TBD
* @subpackage includes\fields
* @package GravityView
*/

use GV\Field;
use GV\Template_Context;
use GV\Utils;
use GV\View;

/**
* Field to display whether the entry has been read.
*
* @since TBD
*/
class GravityView_Field_Is_Read extends GravityView_Field {
var $name = 'is_read';

var $is_searchable = true;

var $entry_meta_key = 'is_read';

var $search_operators = [ 'is', 'isnot' ];

var $group = 'meta';

var $contexts = [ 'single', 'multiple', 'export' ];

var $icon = 'dashicons-book-alt';

var $entry_meta_is_default_column = true;

var $is_sortable = true;

/**
* Class constructor.
*
* @since TBD
*/
public function __construct() {
$this->label = esc_html__( 'Read Status', 'gk-gravityview' );
$this->default_search_label = __( 'Is Read', 'gk-gravityview' );
$this->description = esc_html__( 'Display whether the entry has been read.', 'gk-gravityview' );

$this->add_hooks();

parent::__construct();
}

/**
* Prevents overriding Gravity Forms entry meta, even though it's a meta field.
*
* @since TBD
*
* @param array $entry_meta Existing entry meta.
*
* @return array
*/
public function add_entry_meta( $entry_meta ) {
return $entry_meta;
}

/**
* Adds field hooks.
*
* @since TBD
*/
private function add_hooks() {
/** @see Field::get_value_filters */
add_filter( 'gravityview/field/is_read/value', [ $this, 'get_value' ], 10, 3 );
add_action( 'gravityview/template/after', [ $this, 'print_script' ], 10, 1 );
}

/**
* {@inheritDoc}
*
* @since TBD
*/
public function field_options( $field_options, $template_id, $field_id, $context, $input_type, $form_id ) {
$field_options['is_read_label'] = [
'type' => 'text',
'label' => __( 'Read Label', 'gk-gravityview' ),
'desc' => __( 'If the entry has been read, display this value', 'gk-gravityview' ),
'value' => __( 'Read', 'gk-gravityview' ),
];

$field_options['is_unread_label'] = [
'type' => 'text',
'label' => __( 'Unread Label', 'gk-gravityview' ),
'desc' => __( 'If the entry has not been read, display this value', 'gk-gravityview' ),
'value' => __( 'Unread', 'gk-gravityview' ),
];

return $field_options;
}

/**
* Displays the value based on the field settings.
*
* @since 2.0
*
* @param string $value The value.
* @param Field $field The field we're doing this for.
* @param View $view The view for this context if applicable.
*
* @return string Value of the field
*/
public function get_value( $value, $field, $view ) {
if ( empty( $value ) ) {
return Utils::get( $field, 'is_unread_label', esc_html__( 'Unread', 'gk-gravityview' ) );
}

return $this->get_is_read_label( $field, $view );
}

/**
* Returns the field's "Read" label.
*
* @since TBD
*
* @param Field $field The field.
* @param View $view The View.
*
* @return string The string to use for "Read".
*/
protected function get_is_read_label( $field, $view ) {
$label = Utils::get( $field, 'is_read_label', esc_html__( 'Read', 'gk-gravityview' ) );

/**
* Modify the "Read" label.
*
* @filter `gk/gravityview/field/is-read/read-label`
*
* @since TBD
*
* @param string $label The label.
* @param Field $field The field.
* @param View $view The View.
*/
$label = apply_filters( 'gk/gravityview/field/is-read/read-label', $label, $field, $view );

return $label;
}

/**
* Returns the first "Read Status" field from the context.
*
* @since TBD
*
* @param Template_Context $context The context.
*
* @return Field|null The field or null if not found.
*/
protected function get_field_from_context( $context ) {
foreach ( $context->fields->all() as $field ) {
if ( $this->name === $field->type ) {
return $field;
}
}

return null;
}

/**
* Adds JS to the bottom of the View if there is a read field and user has `gravityview_edit_entries` capability.
*
* @since 2.0
*
* @param Template_Context $context The template context.
*
* @return void
*/
public function print_script( $context ) {
if ( ! GravityView_Roles_Capabilities::has_cap( 'gravityview_edit_entries' ) ) {
return;
}

/**
* Disable the script that marks the entry as read.
*
* @filter `gk/gravityview/field/is-read/print-script`
*
* @since TBD
*
* @param bool $print_script Whether the script be printed? Default: true.
* @param Template_Context $context The template context.
*/
if ( ! apply_filters( 'gk/gravityview/field/is-read/print-script', true, $context ) ) {
return;
}

$entry = gravityview()->request->is_entry();

if ( empty( $entry['is_read'] ) ) {
return;
}

$field = $this->get_field_from_context( $context );
$read_label = $this->get_is_read_label( $field, $context->view );
?>
<script>
jQuery( function ( $ ) {
const entryId = <?php echo (int) $context->entry->ID; ?>;
const isReadField = $( '[class*=is_read]' );
const isReadFieldLabel = '<?php echo esc_html( $read_label ); ?>';

$.ajax( {
type: 'POST',
url: "<?php echo esc_js( admin_url( 'admin-ajax.php' ) ); ?>",
data: {
action: 'rg_update_lead_property',
rg_update_lead_property: '<?php echo wp_create_nonce( 'rg_update_lead_property' ); ?>',
lead_id: entryId,
name: 'is_read',
value: 1
}
} ).done( function () {
if ( isReadField.parents( 'tbody' ).length > 0 ) {
isReadField.find( 'td' ).text( isReadFieldLabel );
} else {
isReadField.text( isReadFieldLabel );
}
} )
.fail( function () {
alert(<?php echo json_encode( __( 'There was an error updating the entry.', 'gk-gravityview' ) ); ?>);
} );
} );
</script>
<?php
}
}

new GravityView_Field_Is_Read();
35 changes: 35 additions & 0 deletions includes/widgets/search-widget/class-search-widget.php
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ class GravityView_Widget_Search extends \GV\Widget {
public function __construct() {

$this->widget_id = 'search_bar';

$this->widget_description = esc_html__( 'Display a search form for users to search a View\'s entries.', 'gk-gravityview' );
$this->widget_subtitle = esc_html__( 'Search form for searching entries.', 'gk-gravityview' );

Expand Down Expand Up @@ -401,6 +402,20 @@ public static function render_searchable_fields( $form_id = null, $current = ''
'text' => esc_html__( 'Is Starred', 'gk-gravityview' ),
'type' => 'boolean',
),
'is_read' => array(
'text' => esc_html__( 'Is Read', 'gravityview' ),
'type' => 'select',
'choices' => array(
array(
'text' => __( 'Read', 'gravityview' ),
'value' => '1',
),
array(
'text' => __( 'Unread', 'gravityview' ),
'value' => '0',
),
),
),
);

if ( gravityview()->plugin->supports( \GV\Plugin::FEATURE_GFQUERY ) ) {
Expand Down Expand Up @@ -1692,6 +1707,21 @@ public function render_frontend( $widget_args, $content = '', $context = '' ) {
$updated_field['value'] = $this->rgget_or_rgpost( 'filter_is_approved' );
$updated_field['choices'] = self::get_is_approved_choices();
break;

case 'is_read':
$updated_field['key'] = 'is_read';
$updated_field['value'] = $this->rgget_or_rgpost( 'filter_is_read' );
$updated_field['choices'] = array(
array(
'text' => __( 'Unread', 'gravityview' ),
'value' => 0,
),
array(
'text' => __( 'Read', 'gravityview' ),
'value' => 1,
),
);
break;
}

$search_fields[ $k ] = $updated_field;
Expand Down Expand Up @@ -1908,6 +1938,11 @@ private function get_search_filter_details( $field, $context, $widget_args ) {
$filter['type'] = 'created_by';
}

if( 'payment_status' === $field['field'] ) {
$filter['type'] = 'entry_meta';
$filter['choices'] = GFCommon::get_entry_payment_statuses_as_choices();
}

if ( 'payment_status' === $field['field'] ) {
$filter['type'] = 'entry_meta';
$filter['choices'] = GFCommon::get_entry_payment_statuses_as_choices();
Expand Down
12 changes: 7 additions & 5 deletions readme.txt
Original file line number Diff line number Diff line change
Expand Up @@ -23,8 +23,13 @@ Beautifully display your Gravity Forms entries. Learn more on [gravitykit.com](h

= develop =

#### 🐛 Fixed
* Searching for products only worked for price ranges.
* Added: "Read Status" field to display whether an entry has been read or not. Previously, the status was output as either 1 or 0. Now, you can customize the labels for "Read" and "Unread" statuses.
- You can now sort a View by "Read Status".

__Developer Updates:__

* Added `gk/gravityview/field/is-read/print-script` filter to modify whether to print the script in the frontend that marks an entry as "Read".
* Added `gk/gravityview/field/is-read/read-label` filter to change field "Read" label.

= 2.23 on May 17, 2024 =

Expand All @@ -33,9 +38,6 @@ This update adds support for Nested Forms' entry meta, addresses several bugs, i
#### 🚀 Added
* Support for Gravity Wiz's Gravity Forms Nested Forms entry meta (parent form and entry IDs, child form field ID) in the View editor and merge tags.

#### ✨ Improved
* The "Add All Fields" button in the View editor now adds fields in their correct form order.

#### 🐛 Fixed
* Export link View widget would cause a fatal error during multi-word searches.
* Fatal error when the search bar is configured with a Gravity Flow field and the Gravity Flow plugin is not active.
Expand Down