I would like to have an option for the views date pager that skips links to pages with no results.

For example, in case of a pager by month, when viewing march, let the previous month link to januari if there is no content for februari.

I'll try to find some time to come up with a patch.

Support from Acquia helps fund testing for Drupal Acquia logo

Comments

KarenS’s picture

Status: Active » Closed (won't fix)

There is no easy way to do this. Basically it would require doing a query of the next and previous period, as is done now, checking to see if there are any results, if not do another query one more period out. See if there are any results for that. If not, do another query one more period out. Etc Etc. And what if there is NO period that has any matches? It might go on endlessly trying to find a period that has values. And those subsequent queries cannot be done at the time of the first query, but have to be done later, perhaps in pre_render. Performance would be terrible.

This sounds simple but is not.

casey’s picture

You only need 2 queries. Closest previous and closest next date.

Jorrit’s picture

Status: Closed (won't fix) » Active

casey is right. Query for the previous item, figure out in which period it is, display the pager. If no results, don't display the pager.

KarenS’s picture

Status: Active » Postponed

This is not the way Views works, there is only one query, the original one. It doesn't do multiple queries with dynamic logic about what to do depending on the result of the first query. If you think this is cleanly solvable you'll have to come up with a patch, because I don't think it is. And I don't plan to try to figure it out, so this is not going to happen without a patch. Leaving it 'active' implies it is going to get done.

Jorrit’s picture

Assigned: Unassigned » Jorrit
Status: Postponed » Needs work
FileSize
13.14 KB

I understand your position KarenS. However, my client really needs this so I have made a patch. Using a clone of the views query I was able to make this work with relatively few lines of code. The option to skip pages has been made optional with the default being off. I would very much like to hear your opinion on the patch.

I have not checked the patch for conformity with all possible use cases of the Date Views module, especially the special case of paging by week. I am not proposing this patch to be committed yet, I just want to get your opinion on it.

Jorrit’s picture

Status: Needs work » Needs review
FileSize
13.86 KB

Patch update: fixed a bug where the next pager was shown when it shouldn't be. Also fixed a bug in the original code where there was no format preset for the hour granularity.
I also fixed some code style issues.

I am marking this issue as "needs review" to see what the test bot thinks of it.

Status: Needs review » Needs work

The last submitted patch, date-views-skip-empty-pages-1487700-6.patch, failed testing.

Jorrit’s picture

The failing test is "MigrateException: No migration found with machine name DateExample in MigrationBase::getInstance()". I don't think it is related to my patch. If it is, please let me know.

Jorrit’s picture

Status: Needs work » Needs review

The patch has been working great for about two months now, let's see if the QA bot agrees with the patch now.

Jorrit’s picture

sanduhrs’s picture

shortspoken’s picture

Thanks for the patch. Its all working fine BUT I found a bug with the week pager. It does not let me navigate to the PREVIOUS week as it always links to the currently selected. Its probably an issue around line 76 in the date/date_views/theme/theme.inc

Before patching its:

$prev_date = clone($min_date);
    date_modify($prev_date, '-1 ' . $granularity);
    $next_date = clone($min_date);
    date_modify($next_date, '+1 ' . $granularity);
    $format = array('year' => 'Y', 'month' => 'Y-m', 'day' => 'Y-m-d');
    switch ($granularity) {
      case 'week':
        $next_week = date_week(date_format($next_date, 'Y-m-d'));
        $prev_week = date_week(date_format($prev_date, 'Y-m-d'));
        $next_arg = date_format($next_date, 'Y-\W') . date_pad($next_week);
        $prev_arg = date_format($prev_date, 'Y-\W') . date_pad($prev_week);
        break;
      default:
        $next_arg = date_format($next_date, $format[$granularity]);
        $prev_arg = date_format($prev_date, $format[$granularity]);
    }
    $next_path = str_replace($date_info->date_arg, $next_arg, $date_info->url);
    $prev_path = str_replace($date_info->date_arg, $prev_arg, $date_info->url);
    $next_args[$pos] = $next_arg;
    $prev_args[$pos] = $prev_arg;
    $vars['next_url'] = date_pager_url($view, NULL, $next_arg);
    $vars['prev_url'] = date_pager_url($view, NULL, $prev_arg);
    $vars['next_options'] = $vars['prev_options'] = array();
  }
  else {

...

and afterwards

$prev_date = $date_info->prev_date;
    $next_date = $date_info->next_date;

    $format = array('year' => 'Y', 'month' => 'Y-m', 'day' => 'Y-m-d', 'hour' => 'Y-m-d\TH');

    if (!empty($prev_date)) {
      switch ($granularity) {
        case 'week':
          $prev_week = date_week(date_format($prev_date, 'Y-m-d'));
          $prev_arg = date_format($prev_date, 'Y-\W') . date_pad($prev_week);
          break;
        default:
          $prev_arg = date_format($prev_date, $format[$granularity]);
      }
      $prev_path = str_replace($date_info->date_arg, $prev_arg, $date_info->url);
      $prev_args[$pos] = $prev_arg;
      $vars['prev_url'] = date_pager_url($view, NULL, $prev_arg);
    }
    if (!empty($next_date)) {
      switch ($granularity) {
        case 'week':
          $next_week = date_week(date_format($next_date, 'Y-m-d'));
          $next_arg = date_format($next_date, 'Y-\W') . date_pad($next_week);
          break;
        default:
          $next_arg = date_format($next_date, $format[$granularity]);
      }
      $next_path = str_replace($date_info->date_arg, $next_arg, $date_info->url);
      $next_args[$pos] = $next_arg;
      $vars['next_url'] = date_pager_url($view, NULL, $next_arg);
    }
    
    $vars['next_options'] = $vars['prev_options'] = array();
  }
  else {

...

Maybe someone can find the bug. I appreciate any help!
Cheers, Moritz

using Date 7.x-2.7

robotjox’s picture

Issue summary: View changes

this patch is not working for me. I have tried applying it manually, but it is behaving erradically for me - on my "events list" it is showing the "previous" pager for Months without any events in them whereas it seems to work for future dates.
I have tried to modify it without any luck - any chance of an updated patch or some pointers?
It is essential functionality for my site - users don't want to browse Months without any events.

Jorrit’s picture

I only use this patch to skip empty days. I think you should look at the query generated by views to see if anything must be improved for skipping months.

robotjox’s picture

thanks for replying so quickly!
In your patch description you write "For example, in case of a pager by month, when viewing march, let the previous month link to januari if there is no content for februari."
That is exactly what I need - is the patch not designed to do this?

I have messed around with the code for hours to no avail, I'll keep on trying but I'm having a hard time figuring out where/how the code queries for previous and next events.

Jorrit’s picture

That is not what I wrote, that was casey. I made the patch just for my situation, which is skipping days. Of course my hope was that it would work for any kind of interval, but apparently it doesn't. It is too long ago for me to quickly see what changes are needed. I could try to find it when I have time, but it will take a while.

robotjox’s picture

Oh, I'm sorry, I was too fast :-)
Thanks anyway - actually the patch works perfectly for Months as long as there are dates in the calendar - problems arise when there are no dates - in those cases both pagers show (although they shouldn't) and they both link to the current Month (which they shouldn't).
So my guess is that there needs to be some fallback for queries that do not reurn results. I'll update this thread if I find a solution.

El Alemaño’s picture

Hi,
With Date Module Update date-views-skip-empty-pages-1487700-6.patch was not working. Here is the small update of the Patch.

Thanks!

Status: Needs review » Needs work

The last submitted patch, 18: date-views-skip-empty-pages-1487700-7.patch, failed testing.

Valentine94’s picture

Status: Needs work » Needs review
FileSize
13.59 KB

Re-roll and some coding standards fix's.

podarok’s picture

Assigned: Jorrit » vijaycs85
Status: Needs review » Reviewed & tested by the community

I'll appreciate if You'll manual review #20
Code looks good for me

Valentine94’s picture

Status: Reviewed & tested by the community » Needs review
FileSize
5.29 KB

I've created a some test.

Please let me know if this test should be more advanced.

Thanks.

Status: Needs review » Needs work

The last submitted patch, 22: views_date_pager-1487700-22.patch, failed testing.

Valentine94’s picture

Valentine94’s picture

Status: Needs work » Needs review
FileSize
19.05 KB

I've created a some test and merged it with a latest patch.
Please let me know if this test should be more advanced.
Thanks.

Valentine94’s picture

podarok’s picture

Assigned: vijaycs85 » Unassigned
Status: Needs review » Fixed

#25 commited. Thanks!!!

Status: Fixed » Closed (fixed)

Automatically closed - issue fixed for 2 weeks with no activity.

Jorrit’s picture

I fear I may have made a mistake in my patch which ended up being committed. date_views_plugin_pager.inc now contains two references to $granularity that should not be there. They should be $this->view->date_info->granularity.

El Alemaño’s picture