Explorar o código

Produktive initial version

Markus Spring hai 1 ano
pai
achega
afb7c043a7
Modificáronse 65 ficheiros con 3381 adicións e 0 borrados
  1. 4 0
      .gitignore
  2. BIN=BIN
      270.png
  3. BIN=BIN
      Proxima Nova Alt Bold.otf
  4. BIN=BIN
      Proxima Nova Alt Light.otf
  5. BIN=BIN
      Proxima Nova Alt Thin.otf
  6. BIN=BIN
      Proxima Nova Black.otf
  7. BIN=BIN
      Proxima Nova Bold.otf
  8. BIN=BIN
      Proxima Nova Extrabold.otf
  9. BIN=BIN
      Proxima Nova Thin.otf
  10. BIN=BIN
      ProximaNova-Regular.otf
  11. BIN=BIN
      TerminalDosis-Bold.woff
  12. BIN=BIN
      TerminalDosis-Bold.woff2
  13. BIN=BIN
      TerminalDosis-ExtraBold.woff
  14. BIN=BIN
      TerminalDosis-ExtraBold.woff2
  15. BIN=BIN
      TerminalDosis-ExtraLight.woff
  16. BIN=BIN
      TerminalDosis-ExtraLight.woff2
  17. BIN=BIN
      TerminalDosis-Light.woff
  18. BIN=BIN
      TerminalDosis-Light.woff2
  19. BIN=BIN
      TerminalDosis-Medium.woff
  20. BIN=BIN
      TerminalDosis-Medium.woff2
  21. BIN=BIN
      TerminalDosis-Regular.woff
  22. BIN=BIN
      TerminalDosis-Regular.woff2
  23. BIN=BIN
      TerminalDosis-SemiBold.woff
  24. BIN=BIN
      TerminalDosis-SemiBold.woff2
  25. 73 0
      archive.php
  26. 68 0
      archive_loop.php
  27. 139 0
      archives.php
  28. 272 0
      blogroll.php
  29. 276 0
      blogroll_lfi.php
  30. 116 0
      comments-page.php
  31. BIN=BIN
      fonts/raleway-v29-latin-300.ttf
  32. BIN=BIN
      fonts/raleway-v29-latin-300.woff2
  33. BIN=BIN
      fonts/raleway-v29-latin-300italic.ttf
  34. BIN=BIN
      fonts/raleway-v29-latin-300italic.woff2
  35. BIN=BIN
      fonts/raleway-v29-latin-500.ttf
  36. BIN=BIN
      fonts/raleway-v29-latin-500.woff2
  37. BIN=BIN
      fonts/raleway-v29-latin-700.ttf
  38. BIN=BIN
      fonts/raleway-v29-latin-700.woff2
  39. BIN=BIN
      fonts/raleway-v29-latin-700italic.ttf
  40. BIN=BIN
      fonts/raleway-v29-latin-700italic.woff2
  41. BIN=BIN
      fonts/raleway-v29-latin-italic.ttf
  42. BIN=BIN
      fonts/raleway-v29-latin-italic.woff2
  43. BIN=BIN
      fonts/raleway-v29-latin-regular.ttf
  44. BIN=BIN
      fonts/raleway-v29-latin-regular.woff2
  45. 385 0
      functions.php
  46. 35 0
      header.php
  47. 32 0
      index-common-places.php
  48. 32 0
      index-vernacular.php
  49. 48 0
      index.php
  50. 191 0
      linkpage2.php
  51. 40 0
      linkpage4.php
  52. 392 0
      linkpage5.php
  53. 42 0
      linkpage6.php
  54. 288 0
      postie-helper.php
  55. BIN=BIN
      proxima_nova_alt_light-webfont.woff
  56. BIN=BIN
      proxima_nova_alt_light-webfont.woff2
  57. BIN=BIN
      proxima_nova_thin-webfont.woff
  58. BIN=BIN
      proxima_nova_thin-webfont.woff2
  59. BIN=BIN
      proximanova-regular-webfont.woff
  60. BIN=BIN
      proximanova-regular-webfont.woff2
  61. 421 0
      style.css
  62. 45 0
      template-parts/header/site-branding.php
  63. 30 0
      template-parts/header/titlepage-header.php
  64. 179 0
      titlepage.css
  65. 273 0
      titlepage.php

+ 4 - 0
.gitignore

@@ -0,0 +1,4 @@
+*~
+titlepage.css.min
+cronlinks2.html
+cronlinks.html

BIN=BIN
270.png


BIN=BIN
Proxima Nova Alt Bold.otf


BIN=BIN
Proxima Nova Alt Light.otf


BIN=BIN
Proxima Nova Alt Thin.otf


BIN=BIN
Proxima Nova Black.otf


BIN=BIN
Proxima Nova Bold.otf


BIN=BIN
Proxima Nova Extrabold.otf


BIN=BIN
Proxima Nova Thin.otf


BIN=BIN
ProximaNova-Regular.otf


BIN=BIN
TerminalDosis-Bold.woff


BIN=BIN
TerminalDosis-Bold.woff2


BIN=BIN
TerminalDosis-ExtraBold.woff


BIN=BIN
TerminalDosis-ExtraBold.woff2


BIN=BIN
TerminalDosis-ExtraLight.woff


BIN=BIN
TerminalDosis-ExtraLight.woff2


BIN=BIN
TerminalDosis-Light.woff


BIN=BIN
TerminalDosis-Light.woff2


BIN=BIN
TerminalDosis-Medium.woff


BIN=BIN
TerminalDosis-Medium.woff2


BIN=BIN
TerminalDosis-Regular.woff


BIN=BIN
TerminalDosis-Regular.woff2


BIN=BIN
TerminalDosis-SemiBold.woff


BIN=BIN
TerminalDosis-SemiBold.woff2


+ 73 - 0
archive.php

@@ -0,0 +1,73 @@
+<?php
+/**
+ * The template for displaying archive pages.
+ *
+ * @link https://codex.wordpress.org/Template_Hierarchy
+ *
+ * @package Optics-mws
+ */
+
+#!-- ---------------------------------------------- for infinite-scroll --- --
+add_filter('next_posts_link_attributes', 'next_posts_link_attributes');
+function next_posts_link_attributes() {
+    return 'class="next pagination__next" style="float:right"';
+}
+
+get_header();
+?>
+<article id="comments-page" class="comments-page page type-page status-publish hentry entry">    
+  <header class="entry-header alignwide">
+    <?php
+    the_archive_title( '<h1 class="page-title">', '</h1>' );
+    the_archive_description( '<div class="taxonomy-description">', '</div>' );
+    ?>
+  </header><!-- .page-header -->
+  <div class="entry-content archive-wider">
+    <ul class="blocks-gallery-grid">
+    <?php while ( have_posts() ) : ?>
+              
+      <?php
+      /* get_template_part( 'template-parts/content', get_post_format() ); */
+      $post = get_post(the_post());
+      echo "<!-- post->ID: $post->ID -->\n";
+      $image = false;
+      if ( get_attached_media('image', $post->ID) ) {
+          $image = array_shift(get_attached_media('image', $post->ID));
+          $image = $image->ID;
+          echo "<!-- image->ID: $image -->\n";
+          $imgs = get_attached_media('image', $post->ID);
+          foreach($imgs as $img) 
+              echo "<!-- // img->ID: $img->ID -->\n";
+      }
+      if (! $image) {
+          $image = get_post_thumbnail_id($post->ID);
+          echo "<!-- get_the_post_thumbnail " . $image . " -->\n";
+      }
+      if ( $image ) {
+          /* $thumbsrc = wp_get_attachment_image_src($image->ID, 'optics-mws-gallery-thumb')[0]; */
+          $thumbsrc = wp_get_attachment_image_src($image, 'thumbnail')[0];
+          $fullsrc =  wp_get_attachment_image_src($image,'full')[0];
+          $style = "";
+          echo "<!-- thumbsrc: $thumbsrc // fullsrc: $fullsrc -->\n";
+      } else {
+          $thumbsrc = get_stylesheet_uri() . '/../270.png';
+          $tithumbsrc = get_stylesheet_uri() . '/../560.png';
+          echo "<!-- thumbsrc: $thumbsrc // tithumbsrc: $tithumbsrc -->\n";
+          $style = "style='display: inline-block !important; background: #ddd;'";
+      }
+      /* echo "<li class='blocks-gallery-item'><figure><a href='$fullsrc'><img src='$thumbsrc' /></a>\n"; */
+      echo "<li class='archive-slide'><figure><a href='$fullsrc'><img src='$thumbsrc' class='archive-slide-slide'/></a>\n";
+      echo "<div class='archive-slide-titlebar' $style><a href='", get_permalink($post->ID),
+      "' title='", get_the_date('', $post->ID), "'><span>", get_the_title($post->ID), "<br />(",
+      get_the_date('', $post->ID), ")</span></a></div>";   
+      echo '</figure></li>';
+      ?>
+    <?php endwhile; ?>
+    </ul>
+    <?php the_posts_pagination(); ?>
+  </div>
+</article>
+
+<?php 
+get_footer();
+?>

+ 68 - 0
archive_loop.php

@@ -0,0 +1,68 @@
+<main id="main" class="site-main" role="main"> 
+<div id="primary" class="content-area">
+<article id="comments-page" class="comments-page page type-page status-publish hentry entry">    
+  <header class="entry-header alignwide">
+    <?php
+    the_archive_title( '<h1 class="page-title">', '</h1>' );
+    the_archive_description( '<div class="taxonomy-description">', '</div>' );
+    ?>
+  </header><!-- .page-header -->
+  
+  <?php
+  if ( have_posts() ) : ?>
+    
+    <div class="entry-content">
+      <?php /* Start the Loop */ ?>
+      <div class="mosaic-container entry-content post">
+        
+      </div><!-- #mosaic-container -->
+    </div>
+  <?php else :
+  
+  get_template_part( 'template-parts/content', 'none' );
+  
+  endif; ?>
+</article>
+    <header class="entry-header alignwide">
+      <?php
+      the_archive_title( '<h1 class="page-title">', '</h1>' );
+      the_archive_description( '<div class="taxonomy-description">', '</div>' );
+      ?>
+    </header><!-- .page-header -->
+
+
+
+
+
+
+<?php while ( have_posts() ) : ?>
+              
+	      <?php
+              /* get_template_part( 'template-parts/content', get_post_format() ); */
+              $post = get_post(the_post());
+              $image = false;
+              if ( get_attached_media('image', $post->ID) ) {
+                  $image = array_shift(get_attached_media('image', $post->ID));
+                  $image = $image->ID;
+              }
+              if (! $image) {
+                  $image = get_post_thumbnail_id($post->ID);
+                  echo "<!-- get_the_post_thumbnail " . $image . " -->\n";
+              }
+              if ( $image ) {
+                  /* $thumbsrc = wp_get_attachment_image_src($image->ID, 'optics-mws-gallery-thumb')[0]; */
+                  $thumbsrc = wp_get_attachment_image_src($image, 'thumbnail')[0];
+                  $fullsrc =  wp_get_attachment_image_src($image,'full')[0];
+                  $style = "";
+              } else {
+                  $thumbsrc = get_stylesheet_uri() . '/../270.png';
+                  $tithumbsrc = get_stylesheet_uri() . '/../560.png';
+                  $style = "style='display: inline-block !important; background: #ddd;'";
+              }
+              echo "<div class='box box2'><a href='$fullsrc'><img src='$thumbsrc' /></a>\n";
+              echo "<div class='imagetitlebar' $style><a href='", get_permalink($post->ID),
+              "'><span><b>", get_the_title($post->ID), "</b><br />(",
+              get_the_date('', $post->ID), ")</span></a></div>";   
+              echo '</div><!-- end box -->';
+              ?>
+	    <?php endwhile; ?>

+ 139 - 0
archives.php

@@ -0,0 +1,139 @@
+<?php
+/*
+Template Name: Archives Template
+*/
+/************* Archive Category Walker *****************/
+$ms_stylesheet_directory = get_bloginfo('stylesheet_directory');
+class Walker_Category_Rabbit extends Walker_Category {
+    function start_el( &$output, $category, $depth = 0, $args = array(), $id = 0 ) {
+        extract($args);
+        global $ms_stylesheet_directory;
+        
+        $cat_name = esc_attr( $category->name );
+        $cat_name = apply_filters( 'list_cats', $cat_name, $category );
+        $link = '<a href="' . esc_url( get_term_link($category) ) . '" ';
+        if ( $use_desc_for_title == 0 || empty($category->description) )
+            $link .= 'title="' . esc_attr( sprintf(__( 'View all posts filed under %s' ), $cat_name) ) . '"';
+        else
+            $link .= 'title="' . esc_attr( strip_tags( apply_filters( 'category_description', $category->description, $category ) ) ) . '"';
+        $link .= '>';
+        $link .= $cat_name . '</a>';
+            
+    if ( !empty($feed_image) || !empty($feed) ) {
+      $link .= ' ';
+      
+      if ( empty($feed_image) )
+        $link .= '(';
+      
+      $link .= '<a href="' . esc_url( get_term_feed_link( $category->term_id, $category->taxonomy, $feed_type ) ) . '"';
+      
+      if ( empty($feed) ) {
+        $alt = ' alt="' . sprintf(__( 'Feed for all posts filed under %s' ), $cat_name ) . '"';
+      } else {
+        $title = ' title="' . $feed . '"';
+        $alt = ' alt="' . $feed . '"';
+        $name = $feed;
+        $link .= $title;
+      }
+
+      $link .= '>';
+      
+      if ( empty($feed_image) )
+        $link .= $name;
+      else
+        $link .= "<img src='$feed_image'$alt$title" . ' />';
+      
+      $link .= '</a>';
+      
+      if ( empty($feed_image) )
+        $link .= ')';
+    }
+    
+    if ( !empty($show_count) )
+      $link .= ' (' . intval($category->count) . ')';
+    
+    if ( 'list' == $args['style'] ) {
+      $output .= "\t<li";
+      $class = 'cat-item cat-item-' . $category->term_id;
+      if ( !empty($current_category) ) {
+        $_current_category = get_term( $current_category, $category->taxonomy );
+        if ( $category->term_id == $current_category )
+          $class .=  ' current-cat';
+        elseif ( $category->term_id == $_current_category->parent )
+          $class .=  ' current-cat-parent';
+      }
+      $output .=  ' class="' . $class . '"';
+      $output .= ">$link\n";
+    } else {
+      $output .= "\t$link<br />\n";
+    }
+  }
+}
+
+/* called in archives.php
+   adds link to mosaic_page for monthly archives */
+function miech_archive_mosaic_filter ( $link_html ) {
+    preg_match('/\/(\d\d\d\d)\/(\d\d)\//', $link_html, $match);
+    $link_html = preg_replace('/<li>\s*<a href=["\'].*?["\']/i', '<li><a href="' . home_url() . '/image-mosaic?mosaic_month=' . $match[2]
+                            . '&mosaic_year=' . $match[1] . '"', $link_html );
+    return $link_html;
+}
+
+/* debugging helper
+   from http://www.stumiller.me/sending-output-to-the-wordpress-debug-log/ */
+if (!function_exists('write_log')) {
+    function write_log ( $log )  {
+        if ( true === WP_DEBUG ) {
+            if ( is_array( $log ) || is_object( $log ) ) {
+                error_log( print_r( $log, true ) );
+            } else {
+                error_log( $log );
+            }
+        }
+    }
+}
+
+?>
+<?php get_header(); ?>
+
+<div id="content" class="site-content">
+  <div id="primary" class="content-area">
+    <main id="main" class="site-main" role="main">
+      
+      <article id="post-31164" class="post-31164 page type-page status-publish hentry entry">
+        
+	<header class="entry-header alignwide">
+	  <h1 class="entry-title">Archives</h1>			
+	</header>
+	
+	<div class="entry-content">
+	  
+          <div class="wp-block-columns">
+            <div class="wp-block-column">
+              <strong>Archives by Month</strong>
+              <ul>
+                <?php
+                #          add_filter('get_archives_link', 'miech_archive_mosaic_filter', 10, 1);
+                wp_get_archives('type=monthly&show_post_count=1');
+                #          remove_filter('get_archives_link', 'miech_archive_mosaic_filter', 10, 1);
+                ?>
+              </ul>
+            </div>
+            
+            <div class="wp-block-column">
+              <strong>Archives by Category</strong>
+              <ul>
+                <?php /* wp_list_categories('title_li=0&show_count=1&exclude=1140&walker=Walker_Category_Rabbit'); */
+                $MyWalker = new Walker_Category_Rabbit();
+                wp_list_categories(array('title_li'   => 0,
+                                         'show_count' => 1,
+                                         /* 'exclude'    => '1140', */
+                                         'walker'     => $MyWalker));
+                ?><!--  -->
+              </ul>
+            </div>
+          </div>
+        </div>
+      </article>
+
+<?php get_footer(); ?>

+ 272 - 0
blogroll.php

@@ -0,0 +1,272 @@
+<?php
+/*
+Template Name: Blogroll
+*/
+
+function scratch99_fromthisblog() {
+    $ref = $_SERVER['HTTP_REFERER'];
+    $host = $_SERVER['HTTP_HOST'];
+    if( $ref == "" ) return true;
+    if( strpos($host, $ref) !== false ) return false;
+    return false;
+} 
+
+function scratch99_last_post_thumbnail_link () {
+    $recent_posts = wp_get_recent_posts(array(
+        'numberposts' => 10, // Number of recent posts thumbnails to display
+        'post_status' => 'publish' // Show only the published posts
+    ));
+    foreach( $recent_posts as $recent ) {
+        if ( has_post_thumbnail($recent['ID']) ) { // check if the post has a Post Thumbnail assigned to it.
+            echo "<div style='text-align: right;'><a href='" . get_permalink($recent['ID']) . "'>";
+            echo "<span style='padding-right: 1em; font-weight: bold;'>New on spring2life</span> ";
+            echo get_the_post_thumbnail($recent['ID'],'thumbnail', 'style=float:right;') . "</a></div>";
+            break;
+        }
+    }
+}
+
+function debug_echo ( $text ) {
+    if ( true ) {
+        /* echo 'debug: <![CDATA[ ', str_replace('<', '&lt;', $text), " ]]><br>\n"; */
+        /* echo 'debug: ', $text, "<br>\n"; */
+    }
+}
+
+function insert_chunk_before( $before, $newest_only, $chunk ) {
+    return preg_replace("/<\/ul>\n<li class='linkhead'><h4>$before<\/h4>/",
+                        "<li>$chunk</li>\n</ul>\n<li class='linkhead'><h4>$before</h4>", $newest_only);
+}
+
+function process_oren_grad($chunk, $newest_only, $omitflag) {
+    $chunk = preg_replace('#<div class=[\'"]item-content[\'"]>.*</div>#s', '', $chunk);
+    $chunk = preg_replace('#</div>#s', '', $chunk);
+    $now = date_timestamp_get(date_create());
+    if ( false === ( $og = get_transient( 'orengrad' ) ) ) { /* no transient could be restored */
+        $result = curlDownload('http://orengrad.com/thingsseen/index.html');
+        $og[1] = md5($result); 
+        $og[0] = $now;
+        set_transient('orengrad', $og);
+    } else {                            /* there is a transient */
+        if ( $now - $og[0] > 1*3600 ) { /* timestamp older than 12h, so compare again */
+            $oldhash = $og[1];
+            $result = curlDownload('http://orengrad.com/thingsseen/index.html');/* nochmal holen */
+            $og[1] = md5($result);
+            if ( $og[1] <> $oldhash ) { /* not equal, so save again */
+                $og[0] = $now; 
+                set_transient('orengrad', $og);/* set transient with new timestamp */
+                /* } else {
+                   debug_echo('Hashes are equal'); */
+            }
+        }
+    }
+    $diff_in_seconds = date_timestamp_get(date_create()) - $og[0];
+    echo "<!-- orengrad diff_in_seconds: $diff_in_seconds -->";
+    if ( $diff_in_seconds < 24 * 3600 ) {
+        $newest_only = insert_chunk_before('A day and older', $newest_only, $chunk);
+    } elseif ( $diff_in_seconds < 30 * 24 * 3600 ) {
+        $newest_only = insert_chunk_before('Less than a month old', $newest_only, $chunk);
+    } else {
+        $newest_only = insert_chunk_before('Older', $newest_only, $chunk);
+    }
+    /* delete_transient('orengrad');  */
+    $omitflag = true;
+    return array($newest_only, $omitflag);
+}
+
+function process_lfi_online($chunk, $newest_only, $omitflag) {
+    $chunk = preg_replace('#<div class=[\'"]item-content[\'"]>.*</div>#s', '', $chunk);
+    $chunk = preg_replace('#</div>#s', '', $chunk);
+    if ( false === ( $result = get_transient( 'lfionlinede' ) ) ) {
+        $result = curlDownload('https://lfi-online.de/ceemes/en/blog/');
+        $chunk = str_replace('<div class=[\'"]blog-title[\'"]>', '', $chunk);
+        if ( preg_match('#<div class="titlebox30 cu-pointer" onclick="window.location = \'(.*?)\'">\s*<h1 class="typo-1">(.*?)</h1>\s*<span class="subline">\s*<h2 class="sl typo-26">.*?</h2>\s*<h3 class="sl typo-27">(.*?)</h3>#s', $result, $matches)) {
+            $chunk = $chunk . ":&nbsp;<span class=\"item-title\">\n<a href=\"$matches[1]\" target=\"_blank\">\n$matches[2]</a></span>";
+            set_transient('lfionlinede', $chunk, 12*3600);
+        }
+    } else {
+        $chunk = $result;
+    }
+    /* delete_transient('lfionlinede'); */
+    /* Assumption: LFI comes in the last section of all entries, because it does not show a date to google.
+       Therefore all headlines are already written to $newestonly and we can insert before */
+    /* $age_in_days = date_diff(date_create($matches[3]), date_create(date("d.m.Y")))->format('%a'); */
+    $age_in_days = date_diff(date_create($matches[3]), date_create(date("d.m.Y")));
+    #echo "<!-- lfi age in days: ", $age_in_days, " -->";
+    if ($age_in_days < 1) {
+        $newest_only = insert_chunk_before('A day and older', $newest_only, $chunk);
+    } elseif ($age_in_days < 30) {
+        $newest_only = insert_chunk_before('Less than a month old', $newest_only, $chunk);
+    } else {
+        $newest_only = insert_chunk_before('Older', $newest_only, $chunk);
+    } 
+    $omitflag = true;
+    return array($newest_only, $omitflag);
+}
+
+function cleanup_chunk ( $chunk ) {
+    $chunk = preg_replace("/[\s]*<div class=[\"']item-time[\"']>.*<\/div>/ism", "", $chunk);
+    $chunk = preg_replace("/<div class=[\"']item-content[\"']>[\r\n]?/ism", "", $chunk);
+    $chunk = preg_replace("/<div class=[\"']blog-title[\"']>[\r\n]?/ism", "<li>", $chunk);
+    $chunk = preg_replace("/<\/div>[\r\n]?/ism", ":&nbsp;", $chunk);
+    $chunk = preg_replace("/<\/span>/ism", "</span></li>", $chunk);
+    return $chunk;
+}
+
+function blogs_i_read() {
+    $url = "http://spring2life-links.blogspot.de";
+    if ( false === ( $html = get_transient( $url ) ) ) {
+        $html = curlDownload($url);
+        if ( ! $html ) {
+            echo "<h2>There is a problem with the http request!</h2>";
+        } else {
+            if ( ! preg_match('/(<ul id=\'BlogList1_blogs.*?<\/ul>)/is', $html, $matches)) {
+                echo "Error: could not retrieve valid spring2life-links blogroll<br>", $html;
+                return;
+            } else { 
+                set_transient( $url, $html, 3600 );
+            }
+        }
+    }
+    /* delete_transient($url); */
+    $html = preg_replace('/.*<div class=["\']widget BlogList["\'] id=["\']BlogList1["\']>/ism', '', $html);
+    $newest_only = "";
+    $stundenflag = false;
+    $tagflag = false;
+    $wochenflag = false;
+    $monatflag = false;
+    $pleistoflag = false;
+    preg_match_all('/<div class=["\']blog-title["\']>.*<div class=["\']item-time["\']>.*<\\/div>/Us', $html, $matches);
+    foreach ($matches[0] as $chunk) {
+        $omitflag = false;
+        if ( preg_match("/orengrad.com/ism", $chunk) ) {
+            list ($newest_only, $omitflag) = process_oren_grad($chunk, $newest_only, $omitflag);
+        }
+        if ( preg_match("#/lfi-online.de/ceemes/#", $chunk) ) {
+            list ($newest_only, $omitflag) = process_lfi_online($chunk, $newest_only, $omitflag);
+        }
+        if ( preg_match("/vor\s+\d+\s+(Minute|Stunde)/ism", $chunk) )
+            if (! $stundenflag) {
+                $chunk = "<li class='linkhead'><h4>Hot from the Sphere</h4></li>\n\n<ul>\n" . $chunk;
+                $stundenflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+(Tag)/ism", $chunk) )
+            if (! $tagflag) {
+                $chunk = "</ul>\n<li class='linkhead'><h4>A day and older</h4></li>\n<ul>\n" . $chunk;
+                $tagflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+Woche/ism", $chunk) )
+            if (! $wochenflag) {
+                $chunk = "</ul>\n<li class='linkhead'><h4>Less than a month old</h4></li>\n<ul>\n" . $chunk;
+                $wochenflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+(Monat)/ism", $chunk) )
+            if (! $monatflag) {
+                $chunk = "</ul><li class='linkhead'><h4>Older</h4></li>\n<ul>\n" . $chunk; $monatflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+(Jahr)/ism", $chunk) )
+            if (! $pleistoflag) {
+                $chunk = "</ul><li class='linkhead'><h4>From the Pleistozaen</h4></li>\n<ul>\n" . $chunk; $pleistoflag = true;
+            }
+        $chunk = cleanup_chunk($chunk);
+        if ( $omitflag == false )
+            $newest_only .= $chunk;
+        if ( preg_match('/href=\'(http:\/\/feedproxy.google.com.*?)\'/', $chunk, $match) ) {
+            $proxyurl = $match[1];
+            if ( false === ( $cleanurl = get_transient( md5('cleanurlof' . $proxyurl) ) ) ) {
+                $cleanurl = resolveUrl($proxyurl);
+                $cleanurl = doHardcore($cleanurl);
+                set_transient( md5("cleanurlof" . $proxyurl), $cleanurl, 90000 + rand(1,3600) );
+            } $chunk = str_replace($match[1], $cleanurl, $chunk);
+        }
+    }
+    return $newest_only;
+}
+
+function resolveUrl($url) {
+    try {
+        $header = doCurlRequest($url); return $header['redirect_url']; } catch (Exception $ex) {
+            _log("error freeing url $url: " . $ex->getMessage()); return $url;
+        }
+}
+
+function curlDownload($Url){
+    $ch = curl_init();
+    curl_setopt($ch, CURLOPT_URL, $Url);
+    curl_setopt($ch, CURLOPT_REFERER, "https://markus-spring.info");
+    curl_setopt($ch, CURLOPT_USERAGENT, "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:31.0) Gecko/20100101 Firefox/31.0");
+    curl_setopt($ch, CURLOPT_HEADER, 0);
+    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
+    curl_setopt($ch, CURLOPT_TIMEOUT, 10);
+    curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
+    curl_setopt($ch, CURLOPT_MAXREDIRS, 10);
+    $output = curl_exec($ch);
+    curl_close($ch);
+    return $output;
+}
+
+if(!function_exists('_log')) {
+    function _log( $message ) {
+        if( WP_DEBUG === true ) {
+            if( is_array( $message ) || is_object( $message ) ) {
+                error_log( print_r( $message, true ) );
+            } else {
+                error_log( $message );
+            }
+        }
+    }
+}
+
+function doCurlRequest($url) {
+    $curlSession = curl_init($url);
+    curl_setopt($curlSession, CURLOPT_NOBODY, 1);
+    $curlResponse = curl_exec($curlSession);
+    $header = curl_getinfo($curlSession);
+    curl_close($curlSession);
+    return $header;
+}
+
+function doHardcore($url) {
+    try {
+        $parts = explode("?", $url);
+        $ret = $parts[0];
+        _log("do hardcore: [$url] -> [$ret]");
+        return $ret;
+    } catch (Exception $ex) {
+        _log("error in hardcore: " . $ex->getMessage());
+        return $url;
+    }
+}
+
+?>
+<?php get_header(); ?>
+<div id="content" class="site-content">
+  <div id="primary" class="content-area">
+    <main id="main" class="site-main" role="main">
+      <article id="post--31201" class="post--31201 post type-post status-publish format-image hentry category-vernacular post_format-post-format-image entry">
+        <header class="entry-header">
+	  <h2 class="entry-title default-max-width">Blogs I read</h2>
+	</header><!-- .entry-header -->
+        
+        <div id="content" class="site-content">
+          <div id="primary" class="content-area">
+            <main id="main" class="site-main" role="main">
+	
+	      <div class="entry-content">
+                <ul class="linktable">
+                  <?php
+                  if (scratch99_fromthisblog()) {
+                      scratch99_last_post_thumbnail_link();
+                  }
+                  ?>
+                  <?php echo blogs_i_read(); ?>
+                </ul>
+              </div><!-- .entry-content -->
+            </main>
+          </div>
+        </div>
+      </article><!-- #post-31164 -->
+    </main><!-- #main -->
+  </div><!-- #primary -->
+</div><!-- #content -->
+<?php get_footer(); ?>

+ 276 - 0
blogroll_lfi.php

@@ -0,0 +1,276 @@
+<?php
+/*
+Template Name: Blogroll Test
+*/
+
+function scratch99_fromthisblog() {
+    $ref = $_SERVER['HTTP_REFERER'];
+    $host = $_SERVER['HTTP_HOST'];
+    if( $ref == "" ) return true;
+    if( strpos($host, $ref) !== false ) return false;
+    return false;
+} 
+
+function scratch99_last_post_thumbnail_link () {
+    $recent_posts = wp_get_recent_posts(array(
+        'numberposts' => 10, // Number of recent posts thumbnails to display
+        'post_status' => 'publish' // Show only the published posts
+    ));
+    foreach( $recent_posts as $recent ) {
+        if ( has_post_thumbnail($recent['ID']) ) { // check if the post has a Post Thumbnail assigned to it.
+            echo "<div style='text-align: right;'><a href='" . get_permalink($recent['ID']) . "'>";
+            echo "<span style='padding-right: 1em; font-weight: bold;'>New on spring2life</span> ";
+            echo get_the_post_thumbnail($recent['ID'],'thumbnail', 'style=float:right;') . "</a></div>";
+            break;
+        }
+    }
+}
+
+function debug_echo ( $text ) {
+    /* if ( false ) { */
+        /* echo 'debug: <![CDATA[ ', str_replace('<', '&lt;', $text), " ]]><br>\n"; */
+        echo 'debug: ', $text, "<br>\n";
+    /* } */
+}
+
+function insert_chunk_before( $before, $newest_only, $chunk ) {
+    return preg_replace("/<\/ul>\n<li class='linkhead'><h4>$before<\/h4>/",
+                        "<li>$chunk</li>\n</ul>\n<li class='linkhead'><h4>$before</h4>", $newest_only);
+}
+
+function process_oren_grad($chunk, $newest_only, $omitflag) {
+    $chunk = preg_replace('#<div class=[\'"]item-content[\'"]>.*</div>#s', '', $chunk);
+    $chunk = preg_replace('#</div>#s', '', $chunk);
+    $now = date_timestamp_get(date_create());
+    if ( false === ( $og = get_transient( 'orengrad' ) ) ) { /* no transient could be restored */
+        $result = curlDownload('http://orengrad.com/thingsseen/index.html');
+        $og[1] = md5($result); 
+        $og[0] = $now;
+        set_transient('orengrad', $og);
+    } else {                            /* there is a transient */
+        if ( $now - $og[0] > 1*3600 ) { /* timestamp older than 12h, so compare again */
+            $oldhash = $og[1];
+            $result = curlDownload('http://orengrad.com/thingsseen/index.html');/* nochmal holen */
+            $og[1] = md5($result);
+            if ( $og[1] <> $oldhash ) { /* not equal, so save again */
+                $og[0] = $now; 
+                set_transient('orengrad', $og);/* set transient with new timestamp */
+                /* } else {
+                   debug_echo('Hashes are equal'); */
+            }
+        }
+    }
+    $diff_in_seconds = date_timestamp_get(date_create()) - $og[0];
+    echo "<!-- orengrad diff_in_seconds: $diff_in_seconds -->";
+    if ( $diff_in_seconds < 24 * 3600 ) {
+        $newest_only = insert_chunk_before('A day and older', $newest_only, $chunk);
+    } elseif ( $diff_in_seconds < 30 * 24 * 3600 ) {
+        $newest_only = insert_chunk_before('Less than a month old', $newest_only, $chunk);
+    } else {
+        $newest_only = insert_chunk_before('Older', $newest_only, $chunk);
+    }
+    /* delete_transient('orengrad');  */
+    $omitflag = true;
+    return array($newest_only, $omitflag);
+}
+
+function process_lfi_online($chunk, $newest_only, $omitflag) {
+    $chunk = preg_replace('#<div class=[\'"]item-content[\'"]>.*</div>#s', '', $chunk);
+    $chunk = preg_replace('#</div>#s', '', $chunk);
+    $matches = [];
+    if ( false === ( $result = get_transient( 'lfionlinede' ) ) ) {
+        $result = curlDownload('https://lfi-online.de/ceemes/en/blog/');
+        $chunk = str_replace('<div class=[\'"]blog-title[\'"]>', '', $chunk);
+        if ( preg_match('#<div class="titlebox30 cu-pointer" onclick="window.location = \'(.*?)\'">\s*<h1 class="typo-1">(.*?)</h1>\s*<span class="subline">\s*<h2 class="sl typo-26">.*?</h2>\s*<h3 class="sl typo-27">(.*?)</h3>#s', $result, $matches)) {
+            $chunk = $chunk . ":&nbsp;<span class=\"item-title\">\n<a href=\"$matches[1]\" target=\"_blank\">\n$matches[2]</a></span>";
+            set_transient('lfionlinede', $chunk, 12*3600);
+        }
+    } else {
+        $chunk = $result;
+    }
+    /* delete_transient('lfionlinede'); */
+    /* Assumption: LFI comes in the last section of all entries, because it does not show a date to google.
+       Therefore all headlines are already written to $newestonly and we can insert before */
+    /* $age_in_days = date_diff(date_create($matches[3]), date_create(date("d.m.Y")))->format('%a'); */
+    $age_in_days = date_diff(date_create($matches[3]), date_create(date("d.m.Y")));
+    debug_echo($matches[0]);
+    /* debug_echo(date_create($matches[3])); */
+    /*     debug_echo(date_create(date("d.m.Y"))); */
+    #echo "<!-- lfi age in days: ", $age_in_days, " -->";
+    if ($age_in_days < 1) {
+        $newest_only = insert_chunk_before('A day and older', $newest_only, $chunk);
+    } elseif ($age_in_days < 30) {
+        $newest_only = insert_chunk_before('Less than a month old', $newest_only, $chunk);
+    } else {
+        $newest_only = insert_chunk_before('Older', $newest_only, $chunk);
+    } 
+    $omitflag = true;
+    return array($newest_only, $omitflag);
+}
+
+function cleanup_chunk ( $chunk ) {
+    $chunk = preg_replace("/[\s]*<div class=[\"']item-time[\"']>.*<\/div>/ism", "", $chunk);
+    $chunk = preg_replace("/<div class=[\"']item-content[\"']>[\r\n]?/ism", "", $chunk);
+    $chunk = preg_replace("/<div class=[\"']blog-title[\"']>[\r\n]?/ism", "<li>", $chunk);
+    $chunk = preg_replace("/<\/div>[\r\n]?/ism", ":&nbsp;", $chunk);
+    $chunk = preg_replace("/<\/span>/ism", "</span></li>", $chunk);
+    return $chunk;
+}
+
+function blogs_i_read() {
+    $url = "http://spring2life-links.blogspot.de";
+    if ( false === ( $html = get_transient( $url ) ) ) {
+        $html = curlDownload($url);
+        if ( ! $html ) {
+            echo "<h2>There is a problem with the http request!</h2>";
+        } else {
+            if ( ! preg_match('/(<ul id=\'BlogList1_blogs.*?<\/ul>)/is', $html, $matches)) {
+                echo "Error: could not retrieve valid spring2life-links blogroll<br>", $html;
+                return;
+            } else { 
+                set_transient( $url, $html, 3600 );
+            }
+        }
+    }
+    /* delete_transient($url); */
+    $html = preg_replace('/.*<div class=["\']widget BlogList["\'] id=["\']BlogList1["\']>/ism', '', $html);
+    $newest_only = "";
+    $stundenflag = false;
+    $tagflag = false;
+    $wochenflag = false;
+    $monatflag = false;
+    $pleistoflag = false;
+    preg_match_all('/<div class=["\']blog-title["\']>.*<div class=["\']item-time["\']>.*<\\/div>/Us', $html, $matches);
+    foreach ($matches[0] as $chunk) {
+        $omitflag = false;
+        if ( preg_match("/orengrad.com/ism", $chunk) ) {
+            list ($newest_only, $omitflag) = process_oren_grad($chunk, $newest_only, $omitflag);
+        }
+        if ( preg_match("#/lfi-online.de/ceemes/#", $chunk) ) {
+            list ($newest_only, $omitflag) = process_lfi_online($chunk, $newest_only, $omitflag);
+        }
+        if ( preg_match("/vor\s+\d+\s+(Minute|Stunde)/ism", $chunk) )
+            if (! $stundenflag) {
+                $chunk = "<li class='linkhead'><h4>Hot from the Sphere</h4></li>\n\n<ul>\n" . $chunk;
+                $stundenflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+(Tag)/ism", $chunk) )
+            if (! $tagflag) {
+                $chunk = "</ul>\n<li class='linkhead'><h4>A day and older</h4></li>\n<ul>\n" . $chunk;
+                $tagflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+Woche/ism", $chunk) )
+            if (! $wochenflag) {
+                $chunk = "</ul>\n<li class='linkhead'><h4>Less than a month old</h4></li>\n<ul>\n" . $chunk;
+                $wochenflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+(Monat)/ism", $chunk) )
+            if (! $monatflag) {
+                $chunk = "</ul><li class='linkhead'><h4>Older</h4></li>\n<ul>\n" . $chunk; $monatflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+(Jahr)/ism", $chunk) )
+            if (! $pleistoflag) {
+                $chunk = "</ul><li class='linkhead'><h4>From the Pleistozaen</h4></li>\n<ul>\n" . $chunk; $pleistoflag = true;
+            }
+        $chunk = cleanup_chunk($chunk);
+        if ( $omitflag == false )
+            $newest_only .= $chunk;
+        if ( preg_match('/href=\'(http:\/\/feedproxy.google.com.*?)\'/', $chunk, $match) ) {
+            $proxyurl = $match[1];
+            if ( false === ( $cleanurl = get_transient( md5('cleanurlof' . $proxyurl) ) ) ) {
+                $cleanurl = resolveUrl($proxyurl);
+                $cleanurl = doHardcore($cleanurl);
+                set_transient( md5("cleanurlof" . $proxyurl), $cleanurl, 90000 + rand(1,3600) );
+            } $chunk = str_replace($match[1], $cleanurl, $chunk);
+        }
+    }
+    return $newest_only;
+}
+
+function resolveUrl($url) {
+    try {
+        $header = doCurlRequest($url); return $header['redirect_url']; } catch (Exception $ex) {
+            _log("error freeing url $url: " . $ex->getMessage()); return $url;
+        }
+}
+
+function curlDownload($Url){
+    $ch = curl_init();
+    curl_setopt($ch, CURLOPT_URL, $Url);
+    curl_setopt($ch, CURLOPT_REFERER, "https://markus-spring.info");
+    curl_setopt($ch, CURLOPT_USERAGENT, "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:31.0) Gecko/20100101 Firefox/31.0");
+    curl_setopt($ch, CURLOPT_HEADER, 0);
+    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
+    curl_setopt($ch, CURLOPT_TIMEOUT, 10);
+    curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
+    curl_setopt($ch, CURLOPT_MAXREDIRS, 10);
+    $output = curl_exec($ch);
+    curl_close($ch);
+    return $output;
+}
+
+if(!function_exists('_log')) {
+    function _log( $message ) {
+        if( WP_DEBUG === true ) {
+            if( is_array( $message ) || is_object( $message ) ) {
+                error_log( print_r( $message, true ) );
+            } else {
+                error_log( $message );
+            }
+        }
+    }
+}
+
+function doCurlRequest($url) {
+    $curlSession = curl_init($url);
+    curl_setopt($curlSession, CURLOPT_NOBODY, 1);
+    $curlResponse = curl_exec($curlSession);
+    $header = curl_getinfo($curlSession);
+    curl_close($curlSession);
+    return $header;
+}
+
+function doHardcore($url) {
+    try {
+        $parts = explode("?", $url);
+        $ret = $parts[0];
+        _log("do hardcore: [$url] -> [$ret]");
+        return $ret;
+    } catch (Exception $ex) {
+        _log("error in hardcore: " . $ex->getMessage());
+        return $url;
+    }
+}
+
+?>
+<?php get_header(); ?>
+<div id="content" class="site-content">
+  <div id="primary" class="content-area">
+    <main id="main" class="site-main" role="main">
+      <article id="post--31201" class="post--31201 post type-post status-publish format-image hentry category-vernacular post_format-post-format-image entry">
+        <header class="entry-header">
+	  <h2 class="entry-title default-max-width">Blogs I read</h2>
+	</header><!-- .entry-header -->
+        
+        <div id="content" class="site-content">
+          <div id="primary" class="content-area">
+            <main id="main" class="site-main" role="main">
+	
+	      <div class="entry-content">
+                <ul class="linktable">
+                  <?php
+                  if (scratch99_fromthisblog()) {
+                      scratch99_last_post_thumbnail_link();
+                  }
+                  ?>
+                  <?php echo blogs_i_read(); ?>
+                </ul>
+              </div><!-- .entry-content -->
+            </main>
+          </div>
+        </div>
+      </article><!-- #post-31164 -->
+    </main><!-- #main -->
+  </div><!-- #primary -->
+</div><!-- #content -->
+<?php get_footer(); ?>

+ 116 - 0
comments-page.php

@@ -0,0 +1,116 @@
+<?php
+/*
+Template Name: Comments page
+ */
+
+$limit = 25; /* Comments per Page */
+
+function get_url_var($name) {
+    $strURL = $_SERVER['REQUEST_URI'];
+    $arrVals = split("/",$strURL);
+    $found = 0;
+    foreach ($arrVals as $index => $value) {
+        if($value == $name)
+            $found = $index;
+    }
+    $place = $found + 1;
+    return $arrVals[$place];
+}
+
+/* return thumbnail url and image find url for first image of a given post */
+function get_comment_thumb_full ( $post_id ) {
+    $images = get_attached_media('image', $post_id);
+    $thumbsrc = '';
+    $fullsrc = '';
+    foreach($images as $image) {
+        #       $thumbsrc = wp_get_attachment_image_src($image->ID,'optics-mws-gallery-thumb')[0];
+        $thumbsrc = wp_get_attachment_image_src($image->ID,'thumbnail')[0];
+        $fullsrc =  wp_get_attachment_image_src($image->ID,'full')[0];
+        break;
+    }
+    return [$thumbsrc, $fullsrc];
+}
+
+$page = get_query_var('comments');
+
+$offset = (intval($page) * $limit) - $limit;
+if ( $offset < 0 ) {
+    $offset = 0;
+}
+
+$param = array( 'status' => 'approve',
+                'offset' => $offset,
+                'number' => $limit );
+$total_comments = get_comments( array( 'status' => 'approve' ) ); 
+$pages = ceil( count( $total_comments ) / $limit );
+$comments = get_comments( $param );
+
+get_header(); ?>
+
+<div id="content" class="site-content">
+  <div id="primary" class="content-area">
+    <main id="main" class="site-main" role="main">
+    
+      <article id="comments-page" class="comments-page page type-page status-publish hentry entry">
+      
+	<header class="entry-header alignwide">
+	  <h2 class="entry-title">Comments</h1>			
+	</header>
+	
+	<div class="entry-content">
+          <?php
+          foreach( $comments as $comment ) {
+              $post_id = $comment->comment_post_ID;
+              if ( $old_post_id && $old_post_id == $post_id) {
+                  echo "	                      <div class='entry-summary'>\n";
+                  if ($comment->comment_author == 'Markus Spring') {
+                      echo " <strong><a href='{$comment->comment_author_url}' class='owner' "
+                         . "target='_blank'>{$comment->comment_author}</a></strong>\n";
+                  } else {
+                      echo " <strong><a href='{$comment->comment_author_url}'"
+                         . "target='_blank'>{$comment->comment_author}</a></strong>\n";
+                  }
+                  echo " said at {$comment->comment_date}:<br />{$comment->comment_content}\n";
+                  echo "</div><!-- .entry-summary -->\n";
+              } else {
+                  if ($old_post_id) {
+                      echo "<br style='clear: both;' /><hr class='comment-sep' />\n";
+                  }
+                  $old_post_id = $post_id;
+                  list( $thumbsrc, $fullsrc ) = get_comment_thumb_full( $post_id );
+                  if ( $thumbsrc ) {
+                      echo "<div class='wp-block-image' style='margin-bottom: 5px !important;'>"
+                         . "<a href='" . get_permalink($post_id)
+                         . "'><figure class='alignleft size-thumbnail'>"
+                         . "<img loading='lazy' width='268' height='268' "
+                         . "src='" . $thumbsrc . "' alt='' class='wp-image-comments'/></figure></a></div>\n";
+                      echo "<h4 style='display: inline;'>On&nbsp;<a href='" . get_permalink($post_id) . "'>"
+                         . get_the_title($post_id) . "</a></h4>\n"; 
+                  } else {
+                      echo "                        On '" . get_the_title($post_id) . "',<br />"; 
+                  }
+                  echo "	                      <div class='entry-summary'>\n";
+                  if ($comment->comment_author == 'Markus Spring') {
+                      echo "                            <strong><a href='{$comment->comment_author_url}' class='owner' "
+                         . "target='_blank'>{$comment->comment_author}</a></strong>\n";
+                  } else {
+                      echo "                            <strong><a href='{$comment->comment_author_url}'"
+                         . "target='_blank'>{$comment->comment_author}</a></strong>\n";
+                  }
+                  /* echo "                            said at {$comment->comment_date}:<br />{$comment->comment_content}\n"; */
+                  echo "                            said at {$comment->comment_date}:<br />"
+                     . apply_filters('the_content', $comment->comment_content) . "\n";
+                  echo "                        </div><!-- .entry-summary -->\n";
+              }
+          }
+          ?>
+          <footer class="entry-footer">
+            <?php //optics_entry_footer(); ?>
+          </footer><!-- .entry-footer -->
+        </div><!-- end search-result -->
+      </article><!-- #post-## -->
+      
+<?php
+/* get_sidebar();
+   get_footer(); */
+?>

BIN=BIN
fonts/raleway-v29-latin-300.ttf


BIN=BIN
fonts/raleway-v29-latin-300.woff2


BIN=BIN
fonts/raleway-v29-latin-300italic.ttf


BIN=BIN
fonts/raleway-v29-latin-300italic.woff2


BIN=BIN
fonts/raleway-v29-latin-500.ttf


BIN=BIN
fonts/raleway-v29-latin-500.woff2


BIN=BIN
fonts/raleway-v29-latin-700.ttf


BIN=BIN
fonts/raleway-v29-latin-700.woff2


BIN=BIN
fonts/raleway-v29-latin-700italic.ttf


BIN=BIN
fonts/raleway-v29-latin-700italic.woff2


BIN=BIN
fonts/raleway-v29-latin-italic.ttf


BIN=BIN
fonts/raleway-v29-latin-italic.woff2


BIN=BIN
fonts/raleway-v29-latin-regular.ttf


BIN=BIN
fonts/raleway-v29-latin-regular.woff2


+ 385 - 0
functions.php

@@ -0,0 +1,385 @@
+<?php
+/* test */
+remove_action( 'wp_head', 'print_emoji_detection_script', 7 );
+remove_action( 'wp_print_styles', 'print_emoji_styles' );
+
+/* enqueue scripts and style from parent theme */
+function twentytwentyone_styles() {
+    wp_enqueue_style( 'child-style', get_stylesheet_uri(),
+                      array( 'twenty-twenty-one-style' ), wp_get_theme()->get('Version') );
+}
+
+add_action( 'wp_enqueue_scripts', 'twentytwentyone_styles', 99);
+
+include 'postie-helper.php';
+
+add_filter(
+    'wp_sitemaps_posts_entry',
+    function( $entry, $post ) {
+        $entry['lastmod'] = $post->post_modified_gmt;
+        return $entry;
+    },
+    10,
+    2
+);
+// disable taxonomy sitemap
+function shapeSpace_disable_sitemap_taxonomy($taxonomies) {
+	unset($taxonomies['post_tag']); // can be post_tag, category, post_format, or any taxonomy
+	unset($taxonomies['post_format']); // can be post_tag, category, post_format, or any taxonomy
+	return $taxonomies;
+}
+add_filter('wp_sitemaps_taxonomies', 'shapeSpace_disable_sitemap_taxonomy');
+
+// disable users sitemap
+function shapeSpace_disable_sitemap_users($provider, $name) {
+	return ($name == 'users') ? false : $provider;
+}
+add_filter('wp_sitemaps_add_provider', 'shapeSpace_disable_sitemap_users', 10, 2);
+
+// disable post type sitemap
+function shapeSpace_disable_sitemap_post_types($post_types) {
+	unset($post_types['page']); // can be post, page, or any post type
+	
+	return $post_types;
+}
+add_filter('wp_sitemaps_post_types', 'shapeSpace_disable_sitemap_post_types');
+
+/* https://firstsiteguide.com/wordpress-titles/ */
+function wploop_change_separator() {
+    return '//';
+}
+add_filter('document_title_separator', 'wploop_change_separator');
+
+/* -- https://wordpress.stackexchange.com/questions/240221/modify-page-title-format-when-using-title-tag */
+add_filter( 'document_title_parts', function( $title_parts_array ) {
+    if ( get_the_ID() == 31286 ) {
+        $title_parts_array['title'] = 'Markus Spring Photography';
+    } else {
+        $title_parts_array['site'] = str_replace('spring2life', 'Markus Spring Photography',
+                                                  $title_parts_array['site']);
+    }
+    return $title_parts_array;
+}, 10, 2 );
+
+/* Basic WP SEO
+	Usage: 
+		1. add this code to functions.php
+		2. replace the $default_keywords with your own
+		3. add <?php echo basic_wp_seo(); ?> to header.php
+		4. test well and fine tune as needed
+
+	Optional: add custom description, keywords, and/or title
+	to any post or page using these custom field keys:
+
+		mm_seo_desc
+		mm_seo_keywords
+		mm_seo_title
+
+	To migrate from any SEO plugin, replace its custom field 
+	keys with those listed above. More information:
+
+		@ https://digwp.com/2013/08/basic-wp-seo/
+ */
+function wp_seo_get_description ($post) {
+    // description
+    $seo_desc = get_post_meta($post->ID, 'mm_seo_desc', true);
+    $description = get_bloginfo('description', 'display');
+    $pagedata = get_post($post->ID);
+    if (is_singular()) {
+	if (!empty($seo_desc)) {
+	    $content = $seo_desc;
+	} else if (!empty($pagedata)) {
+	    $content = apply_filters('the_excerpt_rss', $pagedata->post_content);
+	    $content = substr(trim(strip_tags($content)), 0, 155);
+	    $content = preg_replace('#\n#', ' ', $content);
+	    $content = preg_replace('#\s{2,}#', ' ', $content);
+	    $content = trim($content);
+	} 
+    } else {
+	$content = $description;	
+    }
+    return esc_attr($content);
+}
+
+function wp_seo_get_keywords ($post) {
+    // keywords
+    $default_keywords = 'Markus Spring, spring2life, Fotografie, photography, fotoblog, photoblog'; // customize
+    $keys = get_post_meta($post->ID, 'mm_seo_keywords', true);
+    $cats = get_the_category();
+    $tags = get_the_tags();
+    if (empty($keys)) {
+	if (!empty($cats)) foreach($cats as $cat) $keys .= $cat->name . ', ';
+	if (!empty($tags)) foreach($tags as $tag) $keys .= $tag->name . ', ';
+	$keys .= $default_keywords;
+    }
+    return esc_attr($keys);
+}
+
+function basic_wp_seo() {
+    global $page, $paged, $post;
+    $default_keywords = 'Markus Spring, spring2life, Fotografie, photography, fotoblog, photoblog'; // customize
+    $output = '';
+    $output .= '<meta name="description" content="' . wp_seo_get_description($post) . '">' . "\n";
+    $output .= "\t\t" . '<meta name="keywords" content="' . wp_seo_get_keywords($post) . '">' . "\n";
+    // robots
+    if (is_category() || is_tag()) {
+        $paged = (get_query_var('paged')) ? get_query_var('paged') : 1;
+        if ($paged > 1) {
+            $output .=  "\t\t" . '<meta name="robots" content="noindex,follow">' . "\n";
+        } else {
+            $output .=  "\t\t" . '<meta name="robots" content="index,follow">' . "\n";
+        }
+    } else if (is_home() || is_singular()) {
+        $output .=  "\t\t" . '<meta name="robots" content="index,follow">' . "\n";
+    } else {
+        $output .= "\t\t" . '<meta name="robots" content="noindex,follow">' . "\n";
+    }
+    
+    // title
+    $title_custom = get_post_meta($post->ID, 'mm_seo_title', true);
+    $url = ltrim(esc_url($_SERVER['REQUEST_URI']), '/');
+    $name = get_bloginfo('name', 'display');
+    $title = trim(wp_title('', false));
+    $cat = single_cat_title('', false);
+    $tag = single_tag_title('', false);
+    $search = get_search_query();
+    
+    if (!empty($title_custom)) $title = $title_custom;
+    if ($paged >= 2 || $page >= 2) $page_number = ' | ' . sprintf('Page %s', max($paged, $page));
+    else $page_number = '';
+    
+    if (is_home() || is_front_page()) $seo_title = $name . ' | ' . $description;
+    elseif (is_singular())            $seo_title = $title . ' | ' . $name;
+    elseif (is_tag())                 $seo_title = 'Tag Archive: ' . $tag . ' | ' . $name;
+    elseif (is_category())            $seo_title = 'Category Archive: ' . $cat . ' | ' . $name;
+    elseif (is_archive())             $seo_title = 'Archive: ' . $title . ' | ' . $name;
+    elseif (is_search())              $seo_title = 'Search: ' . $search . ' | ' . $name;
+    elseif (is_404())                 $seo_title = '404 - Not Found: ' . $url . ' | ' . $name;
+    else                              $seo_title = $name . ' | ' . $description;
+
+    
+    $output .= "\t\t" . '<title>' . esc_attr($seo_title . $page_number) . '</title>' . "\n";
+    
+    // OpenGraph
+    $permalink = get_permalink($post->ID);  
+    $output .= '<meta property="og:locale" content="en_GB" />' . "\n";
+    $output .= "<meta property='og:url' content='$permalink'>\n";
+    $output .= "<meta property='og:type' content='article'> \n";
+    $output .= "<meta property='og:title' content='$title'> \n";
+    $output .= "<meta property='og:site_name' content='Markus Spring Photography // spring2life'> \n";
+    $output .= "<meta property='og:description' content='$title | Markus Spring Photography'>\n";
+    $output .= "<meta property='og:image' content='" . get_post_image($post->ID) . "'> \n";
+    // <meta property="article:modified_time" content="2021-03-16T20:48:44+00:00" />
+    /*             echo "<!-- " . print_r($image_attributes) . " -->\n"; */
+    
+    return $output;
+}
+
+function get_post_image ($postID)
+{                   
+    $args = array(
+    'numberposts' => 1,
+    'order'=> 'ASC',
+    'post_mime_type' => 'image',
+    'post_parent' => $postID,
+    'post_status' => null,
+    'post_type' => 'attachment'
+    );
+    $attachments = get_children( $args );
+    //print_r($attachments);
+    if ($attachments) {
+        foreach($attachments as $attachment) {
+            $image_attributes = wp_get_attachment_image_src( $attachment->ID, 'full' );
+            /*             echo "<!-- " . print_r($image_attributes) . " -->\n"; */
+            return $image_attributes[0];
+        }
+    }
+}
+
+/* -------------------------------------------------- further cleanup --- */
+/* Disable emojicons introduced with WP 4.2 */
+/* from http://wordpress.stackexchange.com/questions/185577/disable-emojicons-introduced-with-wp-4-2 */
+function disable_wp_emojicons() {
+  // all actions related to emojis
+  remove_action( 'admin_print_styles', 'print_emoji_styles' );
+  remove_action( 'wp_head', 'print_emoji_detection_script', 7 );
+  remove_action( 'admin_print_scripts', 'print_emoji_detection_script' );
+  remove_action( 'wp_print_styles', 'print_emoji_styles' );
+  remove_filter( 'wp_mail', 'wp_staticize_emoji_for_email' );
+  remove_filter( 'the_content_feed', 'wp_staticize_emoji' );
+  remove_filter( 'comment_text_rss', 'wp_staticize_emoji' );
+  // filter to remove TinyMCE emojis
+  // add_filter( 'tiny_mce_plugins', 'disable_emojicons_tinymce' );
+}
+add_action( 'init', 'disable_wp_emojicons' );
+
+/* from https://wordpress.org/support/topic/remove-googlewebfonts */
+function remove_open_sans() {
+	wp_dequeue_style( 'open-sans-web-font' );
+	wp_deregister_style( 'open-sans-web-font' );
+}
+add_action( 'wp_enqueue_scripts', 'remove_open_sans', 25 );
+
+add_image_size( 'semilarge', 602, 0, false );
+add_image_size( 'old_old_large', 1100, 1100, false );
+add_filter( 'image_size_names_choose','miech_custom_image_sizes' );
+function miech_custom_image_sizes( $sizes ) {
+    return array_merge( $sizes, array(
+        'semilarge' => 'SemiLarge',
+        'old_old_large' => 'Old_old_Large',
+    ) );
+}
+
+/*-- ------------------------------ run postie get posts from admin bar --- --*/
+// https://markus-spring.info/wp-admin/admin.php?page=postie-settings&action=runpostie&Submit=Process+Email
+function webriti_toolbar_link($wp_admin_bar) {
+    $args = array(
+        'id' => 'customlink',
+        'title' => 'Run Postie',
+        'href' => 'https://markus-spring.info/wp-admin/admin.php?page=postie-settings&action=runpostie&Submit=Process+Email',
+        'meta' => array(
+            'class' => 'customlink',
+            'title' => 'run Postie'
+        )
+    );
+    $wp_admin_bar->add_node($args);
+}
+add_action('admin_bar_menu', 'webriti_toolbar_link', 999);
+
+add_action( 'pre_get_posts', 'prefix_category_query' );
+/**
+ * Customize category query using pre_get_posts.
+ * 
+ * @author     FAT Media <http://youneedfat.com>
+ * @copyright  Copyright (c) 2013, FAT Media, LLC
+ * @license    GPL-2.0+
+ * @todo       Change prefix to theme or plugin prefix
+ *
+ */
+function prefix_category_query( $query ) {
+    /* if ( $query->is_main_query() && ! $query->is_feed() && ! is_admin() && is_category() ) { */
+	if ( $query->is_main_query() && ! $query->is_feed() && ! is_admin() && is_archive() ) {
+		$query->set( 'posts_per_page', '40' ); //Change this number to anything you like.
+	}
+
+}
+
+/* ----------------------------------- for manipulating the main loop --- */
+$miech_active_cat;
+
+function miech_get_active_cat ($id) {
+    //_log("Querying active cat for $id");
+    $my_query = new WP_Query('posts_per_page=1');
+    while ( $my_query->have_posts() )
+        $my_query->the_post();
+    $featured_category_1 = get_theme_mod( 'featured_category_1', 'default_value' );
+    $featured_category_2 = get_theme_mod( 'featured_category_2', 'default_value' );
+    $do_not_duplicate = $id; //This is the magic line
+    if (has_category ( $featured_category_1, $id)) { /* Featured Category 1 */
+        $active_cat = $featured_category_1;
+    } else {
+        $active_cat = $featured_category_2;          /* Featured Category 2 */
+    }
+    wp_reset_query();
+    //_log("miech_get_active_cat: Active cat is $active_cat");
+    return $active_cat;
+}
+
+function miech_set_active_cat ( $this_cat ) {
+    global $miech_active_cat;
+    if (have_posts()) {
+        if ( $this_cat ) {
+            $miech_active_cat = $this_cat;
+        } else {
+            $miech_active_cat = miech_get_active_cat($post->ID);
+        }
+        //error_log("miech_set_active_cat: miech_active_cat is $miech_active_cat");
+        if ( get_query_var('paged') )
+           { $paged = get_query_var('paged'); }
+        elseif ( get_query_var('page') )
+           { $paged = get_query_var('page'); }
+        else
+           { $paged = 1; }
+        //error_log("paged: $paged");
+        if ( is_single() )
+            $posts_per_page = 1;
+        else
+            $posts_per_page = 25;
+
+        query_posts( array(
+            'order' => 'DESC',
+            'paged' => $paged,
+            'cat'   => $miech_active_cat,
+            'posts_per_page' => $posts_per_page
+        ) );
+    }
+}
+
+// turn Photon off so we can get the correct image
+$photon_removed = '';
+if ( class_exists( 'Jetpack' ) && Jetpack::is_module_active( 'photon' ) ) { // check that we are, in fact, using Photon in the first place
+    $photon_removed = remove_filter( 'image_downsize', array( Jetpack_Photon::instance(), 'filter_image_downsize' ) );
+}
+
+/*
+Diverse Einstellungen für die functions.php (dort am Ende einfügen)
+von https://faq.netzprisma.de/wordpress-html-ausmisten/
+*/
+
+// Diverse Einträge entfernen
+remove_action('wp_head', 'wp_generator');
+remove_action('wp_head', 'rsd_link');
+remove_action('wp_head', 'wlwmanifest_link');
+
+// Generator-Angaben, z.B. im Feed, entfernen
+function remove_wp_generator() { return ''; }
+add_filter('the_generator','remove_wp_generator');
+// // prev+next Links in Beiträgen entfernen
+// remove_action('wp_head', 'adjacent_posts_rel_link_wp_head');
+
+// // shortlink entfernen
+// remove_action('wp_head', 'wp_shortlink_wp_head', 10, 0);
+
+// Post+Kommentar+Kategorie RSS Feed-Links entfernen (entfernt nicht die Feeds selbst)
+remove_action('wp_head', 'feed_links', 2);
+remove_action('wp_head', 'feed_links_extra', 3);
+
+// wp Versions-Parameter ?ver=... von Skripts entfernen, falls unsere WordPress-Version angegeben wird
+function vc_remove_wp_ver_css_js( $src )
+{
+   if (  strpos($src, 'ver='. get_bloginfo('version') )  )
+      $src = remove_query_arg('ver', $src);
+   return $src;
+}
+add_filter('style_loader_src',  'vc_remove_wp_ver_css_js', 9999);
+add_filter('script_loader_src', 'vc_remove_wp_ver_css_js', 9999);
+
+// Emoji js, css und dns-preload entfernen
+remove_action('wp_head', 'print_emoji_detection_script', 7);
+remove_action('wp_print_styles', 'print_emoji_styles');
+add_filter('emoji_svg_url', '__return_false');
+
+// // REST Api Hinweise entfernen
+// remove_action('wp_head', 'rest_output_link_wp_head');
+// remove_action('wp_head', 'wp_oembed_add_discovery_links');
+// remove_action('template_redirect', 'rest_output_link_header', 11, 0);
+
+// function remove_json_api ()
+// {
+//    // REST API Zeilen aus dem HTML Header entfernen
+//    remove_action('wp_head', 'rest_output_link_wp_head', 10);
+//    remove_action('wp_head', 'wp_oembed_add_discovery_links', 10);
+//    // REST API endpoint entfernen
+//    remove_action('rest_api_init', 'wp_oembed_register_route');
+//    // oEmbed auto discovery entfernen
+//    add_filter('embed_oembed_discover', '__return_false');
+//    // oEmbed results nicht filtern
+//    remove_filter('oembed_dataparse', 'wp_filter_oembed_result', 10);
+//    // oEmbed discovery links entfernen
+//    remove_action('wp_head', 'wp_oembed_add_discovery_links');
+//    // oEmbed-JavaScript entfernen
+//    remove_action('wp_head', 'wp_oembed_add_host_js');
+//    // rewrite rules zum Einbetten entfernen
+//    add_filter('rewrite_rules_array', 'disable_embeds_rewrites');
+// }
+// add_action('after_setup_theme', 'remove_json_api');

+ 35 - 0
header.php

@@ -0,0 +1,35 @@
+<?php
+/**
+ * The header.
+ *
+ * This is the template that displays all of the <head> section and everything up until main.
+ *
+ * @link https://developer.wordpress.org/themes/basics/template-files/#template-partials
+ *
+ * @package WordPress
+ * @subpackage Twenty_Twenty_One
+ * @since Twenty Twenty-One 1.0
+ */
+
+?>
+<!doctype html>
+<html <?php language_attributes(); ?> <?php twentytwentyone_the_html_classes(); ?>>
+<head>
+	<meta charset="<?php bloginfo( 'charset' ); ?>" />
+	<meta name="viewport" content="width=device-width, initial-scale=1" />
+	<?php wp_head(); ?>
+	<?php echo basic_wp_seo(); ?>
+</head>
+
+<body <?php body_class(); ?>>
+<div style="z-index:9999" class="cr cr-top cr-right cr-sticky cr-black">#StandWithUkraine</div>
+<!-- <div style="z-index:9999" class="cl cl-top cl-right cl-sticky cl-white">Support Israel</div> -->
+<?php wp_body_open(); ?>
+<div id="page" class="site">
+	<a class="skip-link screen-reader-text" href="#content"><?php esc_html_e( 'Skip to content', 'twentytwentyone' ); ?></a>
+
+	<?php get_template_part( 'template-parts/header/site-header' ); ?>
+
+	<div id="content" class="site-content">
+		<div id="primary" class="content-area">
+			<main id="main" class="site-main">

+ 32 - 0
index-common-places.php

@@ -0,0 +1,32 @@
+<?php
+/**
+Template Name: Common places template 
+ */
+
+global $featured_post_id;
+miech_set_active_cat( get_theme_mod( 'featured_category_2', 1140 ) );
+echo '<!-- featured_category_1 => '.get_theme_mod( 'featured_category_1', 1140 )." -->\n";
+
+get_header();
+
+if ( have_posts() ) {
+
+	// Load posts loop.
+	while ( have_posts() ) {
+		the_post();
+
+		get_template_part( 'template-parts/content/content', get_theme_mod( 'display_excerpt_or_full_post', 'excerpt' ) );
+	}
+
+	// Previous/next page navigation.
+	twenty_twenty_one_the_posts_navigation();
+
+} else {
+
+	// If no content, include the "No posts found" template.
+	get_template_part( 'template-parts/content/content-none' );
+
+}
+
+get_footer();
+?>

+ 32 - 0
index-vernacular.php

@@ -0,0 +1,32 @@
+<?php
+/**
+Template Name: Vernacular template 
+ */
+
+global $featured_post_id;
+miech_set_active_cat( get_theme_mod( 'featured_category_1', 1964) );
+echo '<!-- featured_category_1 => '.get_theme_mod( 'featured_category_1', 1964 )." -->\n";
+
+get_header();
+
+if ( have_posts() ) {
+
+	// Load posts loop.
+	while ( have_posts() ) {
+		the_post();
+
+		get_template_part( 'template-parts/content/content', get_theme_mod( 'display_excerpt_or_full_post', 'excerpt' ) );
+	}
+
+	// Previous/next page navigation.
+	twenty_twenty_one_the_posts_navigation();
+
+} else {
+
+	// If no content, include the "No posts found" template.
+	get_template_part( 'template-parts/content/content-none' );
+
+}
+
+get_footer();
+?>

+ 48 - 0
index.php

@@ -0,0 +1,48 @@
+<?php
+/**
+Template Name: Original twentytwentyone template 
+ */
+/**
+ * The main template file
+ *
+ * This is the most generic template file in a WordPress theme
+ * and one of the two required files for a theme (the other being style.css).
+ * It is used to display a page when nothing more specific matches a query.
+ * E.g., it puts together the home page when no home.php file exists.
+ *
+ * @link https://developer.wordpress.org/themes/basics/template-hierarchy/
+ *
+ * @package WordPress
+ * @subpackage Twenty_Twenty_One
+ * @since Twenty Twenty-One 1.0
+ */
+
+get_header(); ?>
+
+<?php if ( is_home() && ! is_front_page() && ! empty( single_post_title( '', false ) ) ) : ?>
+	<header class="page-header alignwide">
+		<h1 class="page-title"><?php single_post_title(); ?></h1>
+	</header><!-- .page-header -->
+<?php endif; ?>
+
+<?php
+if ( have_posts() ) {
+
+	// Load posts loop.
+	while ( have_posts() ) {
+		the_post();
+
+		get_template_part( 'template-parts/content/content', get_theme_mod( 'display_excerpt_or_full_post', 'excerpt' ) );
+	}
+
+	// Previous/next page navigation.
+	twenty_twenty_one_the_posts_navigation();
+
+} else {
+
+	// If no content, include the "No posts found" template.
+	get_template_part( 'template-parts/content/content-none' );
+
+}
+
+get_footer();

+ 191 - 0
linkpage2.php

@@ -0,0 +1,191 @@
+<?php
+/*
+Template Name: NEW Blogroll TEST
+ */
+
+/*
+   * get html from linkpage blog
+   * for each blog save url, title, last post url, last post title, timestamp as transient, key is ????
+   * for leicaphilia and oren grad, get last post title and url with special function
+ */
+
+$pdo = new PDO(
+    'sqlite::memory:',
+    null,
+    null,
+    array(PDO::ATTR_PERSISTENT => false)
+); 
+
+function scratch99_fromthisblog() {
+    $ref = $_SERVER['HTTP_REFERER'];
+    $host = $_SERVER['HTTP_HOST'];
+    /* echo "<p style='color:green!important;'>Referer: $ref <br>Host: $host</p>"; */
+    if( $ref == "" ) return true;
+    if( strpos($host, $ref) !== false ) return false;
+    return false;
+} 
+
+function scratch99_last_post_thumbnail_link () {
+    $recent_posts = wp_get_recent_posts(array(
+        'numberposts' => 10, // Number of recent posts thumbnails to display
+        'post_status' => 'publish' // Show only the published posts
+    ));
+    foreach( $recent_posts as $recent ) {
+        if ( has_post_thumbnail($recent['ID']) ) { // check if the post has a Post Thumbnail assigned to it.
+            echo "<div style='text-align: right;'><a href='" . get_permalink($recent['ID']) . "'>";
+            echo "<span style='padding-right: 1em; font-weight: bold;'>New on spring2life</span> ";
+            echo get_the_post_thumbnail($recent['ID'],'thumbnail', 'style=float:right;') . "</a></div>";
+            break;
+        }
+    }
+}
+
+function blogs_i_read() {
+    $url = "http://spring2life-links.blogspot.de";
+    //$html = file_get_contents('/tmp/spring2life-links.html');
+    $html = curlDownload($url);
+    set_transient( $url, $html, 1800 );
+    if ( false === ( $html = get_transient( $url ) ) ) {
+        $html = curlDownload($url);
+        if ( ! $html )
+            echo "<h2>There is a problem with the http request!</h2>";
+        else
+            set_transient( $url, $html, 1800 );
+    }
+    if ( ! preg_match('/(<ul id=\'BlogList1_blogs.*?<\/ul>)/is', $html, $matches)) {
+        echo $html;
+        echo "Error: could not retrieve spring2life-links blogroll";
+        return;
+    }
+    $html = preg_replace('/.*<div class=["\']widget BlogList["\'] id=["\']BlogList1["\']>/ism', '', $html);
+    $newest_only = "";
+    $stundenflag = false;
+    $tagflag = false;
+    $wochenflag = false;
+    $monatflag = false;
+    $pleistoflag = false;
+    preg_match_all('/<div class=["\']blog-title["\']>.*<div class=["\']item-time["\']>.*<\\/div>/Us', $html, $matches);
+    foreach ($matches[0] as $chunk) {
+        /* if ( preg_match("/orengrad.com/ism", $chunk) ) {
+           $result = curlDownload('http://orengrad.com/thingsseen/index.html');
+           $result = preg_replace('/</ism', '&lt;', $result);
+           $result = preg_replace('/>/ism', '&gt;', $result);
+           echo "<br><tt>Orengrad: $chunk</tt><br><pre>$result</pre><br>";
+           } */
+        if ( preg_match("/vor\s+\d+\s+(Minute|Stunde)/ism", $chunk) )
+            if (! $stundenflag) {
+                $chunk = "<li class='linkhead'>Hot from the Sphere</li>\n\n" . $chunk; $stundenflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+(Tag)/ism", $chunk) )
+            if (! $tagflag) {
+                $chunk = "<li class='linkhead'>A day and older</li>\n\n" . $chunk; $tagflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+Woche/ism", $chunk) )
+            if (! $wochenflag) {
+                $chunk = "<li class='linkhead'>Less than a month old</li>\n\n" . $chunk; $wochenflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+(Monat)/ism", $chunk) )
+            if (! $monatflag) {
+                $chunk = "<li class='linkhead'>Older</li>\n\n" . $chunk; $monatflag = true;
+            }
+        if ( preg_match("/vor\s+\d+\s+(Jahr)/ism", $chunk) )
+            if (! $pleistoflag) {
+                $chunk = "<li class='linkhead'>From the Pleistozaen</li>\n\n" . $chunk; $pleistoflag = true;
+            }
+        /* if (! preg_match("/<li>/ism", $chunk) )
+           $chunk = "<li>" . $chunk; */
+        $chunk = preg_replace("/[\s]*<div class=[\"']item-time[\"']>.*<\/div>/ism", "", $chunk);
+        $chunk = preg_replace("/<div class=[\"']item-content[\"']>[\r\n]?/ism", "", $chunk);
+        $chunk = preg_replace("/<div class=[\"']blog-title[\"']>[\r\n]?/ism", "<li>", $chunk);
+        $chunk = preg_replace("/<\/div>[\r\n]?/ism", ":&nbsp;", $chunk);
+        $chunk = preg_replace("/<\/span>/ism", "</span></li>", $chunk);
+        $newest_only .= $chunk;
+        if ( preg_match('/href=\'(http:\/\/feedproxy.google.com.*?)\'/', $chunk, $match) ) {
+            $proxyurl = $match[1];
+            if ( false === ( $cleanurl = get_transient( md5('cleanurlof' . $proxyurl) ) ) ) {
+                $cleanurl = resolveUrl($proxyurl);
+                $cleanurl = doHardcore($cleanurl);
+                set_transient( md5("cleanurlof" . $proxyurl), $cleanurl, 90000 + rand(1,3600) );
+            } $chunk = str_replace($match[1], $cleanurl, $chunk);
+            /*             print_r($newest_only); die; */
+        }
+        /* $chunk = preg_replace( '/<\/li>[\s\r\n]*<\/ul>/ism', '', $chunk ); */
+        /* $newest_only .= $chunk . "</div></li>\n"; */
+    }
+    return $newest_only;
+}
+
+function resolveUrl($url) {
+    try {
+        $header = doCurlRequest($url); return $header['redirect_url']; } catch (Exception $ex) {
+            _log("error freeing url $url: " . $ex->getMessage()); return $url;
+        }
+}
+
+function curlDownload($Url){
+    $ch = curl_init();
+    curl_setopt($ch, CURLOPT_URL, $Url);
+    curl_setopt($ch, CURLOPT_REFERER, "http://markus-spring.info");
+    curl_setopt($ch, CURLOPT_USERAGENT, "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:31.0) Gecko/20100101 Firefox/31.0");
+    curl_setopt($ch, CURLOPT_HEADER, 0);
+    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
+    curl_setopt($ch, CURLOPT_TIMEOUT, 10);
+    curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
+    curl_setopt($ch, CURLOPT_MAXREDIRS, 10);
+    $output = curl_exec($ch);
+    curl_close($ch);
+    return $output;
+}
+
+if(!function_exists('_log')) {
+    function _log( $message ) {
+        if( WP_DEBUG === true ) {
+            if( is_array( $message ) || is_object( $message ) ) {
+                error_log( print_r( $message, true ) );
+            } else {
+                error_log( $message );
+            }
+        }
+    }
+}
+
+function doCurlRequest($url) {
+    $curlSession = curl_init($url);
+    curl_setopt($curlSession, CURLOPT_NOBODY, 1);
+    $curlResponse = curl_exec($curlSession);
+    $header = curl_getinfo($curlSession);
+    curl_close($curlSession);
+    return $header;
+}
+
+function doHardcore($url) {
+    try {
+        $parts = explode("?", $url);
+        $ret = $parts[0];
+        _log("do hardcore: [$url] -> [$ret]");
+        return $ret;
+    } catch (Exception $ex) {
+        _log("error in hardcore: " . $ex->getMessage());
+        return $url;
+    }
+}
+
+?>
+<?php get_header(); ?>
+<div id="content">
+  <div id="inner-content" class="wrap group">
+    <?php get_sidebar(); ?>
+    <div id="main" class="col-4-5 group" role="main">
+      <ul class="blogroll">
+        <?php
+        if (scratch99_fromthisblog()) {
+            /* echo "<p style='color:ping!important;'>Referer: $ref POSITIV</p>"; */
+            scratch99_last_post_thumbnail_link();
+        }
+        ?>
+        <?php echo blogs_i_read(); ?>
+      </ul>
+    </div> <!-- #main -->
+  </div> <!-- #inner-content -->  
+</div> <!-- #content -->  
+<?php get_footer(); ?>

+ 40 - 0
linkpage4.php

@@ -0,0 +1,40 @@
+<?php
+/*
+Template Name: NEW Blogroll 4
+ */
+?>
+<?php
+$text= file_get_contents('/var/www/html/wp-content/themes/twentytwentyone-child-spring2life/cronlinks2.html');
+?>
+<?php get_header(); ?>
+<div id="content" class="site-content">
+  <div id="primary" class="content-area">
+    <main id="main" class="site-main" role="main">
+      <article id="post--31201" class="post--31201 post type-post status-publish format-image hentry category-vernacular post_format-post-format-image entry">
+        <header class="entry-header">
+	  <h2 class="entry-title default-max-width">Blogs I read</h2>
+	</header><!-- .entry-header -->
+        
+        <div id="content" class="site-content">
+          <div id="primary" class="content-area">
+            <main id="main" class="site-main" role="main">
+	
+	      <div class="entry-content">
+                <ul class="linktable">
+                  <?php echo $text; ?>
+                </ul>
+              </div><!-- .entry-content -->
+            </main>
+          </div>
+        </div>
+      </article><!-- #post-31164 -->
+    </main><!-- #main -->
+  </div><!-- #primary -->
+</div><!-- #content -->
+<?php get_footer(); ?>
+
+<?php
+// Local variables:
+// compile-command: "php linkpage4.php"
+// End:
+?>

+ 392 - 0
linkpage5.php

@@ -0,0 +1,392 @@
+<?php
+/*
+Template Name: Blogroll 5 High Performance
+ */
+?>
+<?php
+
+$GLOBALS['blogs_i_read_min_time']     = 900;
+$GLOBALS['external_service_min_time'] = 1800; 
+$GLOBALS['external_service_pre_aged'] = 600; 
+
+// retrieve_list();
+
+function resolveUrl($url) {
+    try {
+        $header = doCurlRequest($url); return $header['redirect_url']; } catch (Exception $ex) {
+            _log("error freeing url $url: " . $ex->getMessage()); return $url;
+        }
+}
+
+function curlDownload($Url){
+    $ch = curl_init();
+    curl_setopt($ch, CURLOPT_URL, $Url);
+    curl_setopt($ch, CURLOPT_REFERER, "https://markus-spring.info");
+    curl_setopt($ch, CURLOPT_USERAGENT, "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:31.0) Gecko/20100101 Firefox/31.0");
+    curl_setopt($ch, CURLOPT_HEADER, 0);
+    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
+    curl_setopt($ch, CURLOPT_TIMEOUT, 10);
+    curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
+    curl_setopt($ch, CURLOPT_MAXREDIRS, 10);
+    $output = curl_exec($ch);
+    curl_close($ch);
+    return $output;
+}
+
+function reduce_lines( $html ) {
+    $lines = explode("\n", $html);
+    $found = 0;
+    $bloglist = '';
+    for ($i = 0; $i < count($lines); $i++) {
+        if ($lines[$i] ==  "<ul id='BlogList1_blogs'>")
+            $found = 1;
+        if ($found == 1 and $lines[$i] == "</ul>")
+            break;
+        if ($found == 1) 
+            $bloglist .= $lines[$i] . "\n";
+    }
+    return($bloglist); 
+}
+
+function make_timestamp($chunk) {   // 
+    preg_match('/vor\s(\d+)\s(\D+)/m', $chunk, $m);
+    $t = time() - 20*365*24*3600;
+    if ($m) {
+        // echo $m[1] . " " . $m[2] . " ";
+        if (strpos($m[2], 'Minute') === 0) 
+            $t =  time() - $m[1] * 60;
+        if (strpos($m[2], 'Stunde') === 0) 
+            $t =  time() - $m[1] * 3600;
+        elseif (strpos($m[2], 'Tag') === 0) 
+            $t =  time() - $m[1] * 24 * 3600;
+        elseif (strpos($m[2], 'Woche') === 0) 
+            $t =  time() - $m[1] * 7 * 24 * 3600;
+        elseif (strpos($m[2], 'Monat') === 0) 
+            $t =  time() - $m[1] * 30 * 24 * 3600;
+        elseif (strpos($m[2], 'Jahr') === 0) 
+            $t =  time() - $m[1] * 365 * 24 * 3600;
+        return $t;
+    } else
+    return 0;
+}
+
+function rework_entry ($match, $list, $offset, $housekeeping) {
+    $url = $match[1];
+    $domain = preg_replace('/(https?:\/\/|\/<?.*?$)/m', "", $match[1]);
+    $protocol = preg_replace('/:\/\/.*/', '://', $match[1]); 
+    $title = $match[2];
+    $lasturl = '';
+    $lasttitle = '';
+    # match: [0] url [1] blog title [2] post title [3] post url [4] time indicator
+    # echo "<pre style='font-size: 10px; font-weight: normal'>$domain: " . $match[3] . "</pre>\n";
+    if (preg_match('`href=\'(.*?)\'.*?>\s*(.*?)\s*</a>`m', $match[3], $m)) {
+        #echo "<pre style='font-size: 10px; font-weight: normal'>" . $match[3] . "</pre>\n";
+        $lasturl  = $m[1];
+        $lasttitle  = $m[2];
+        /* echo "Last post 1:" . $lasturl . "\n"; */
+        $timestamp  = make_timestamp($match[4]) + $offset;
+    } else {
+        if ( strpos($domain, 'lfi-online.de') === 0 ) 
+            list($timestamp, $lasturl, $lasttitle) = update_lfi($url, $list);
+        if ( strpos($domain, 'jims-ramblings.blogspot.com') === 0 ) 
+            list($timestamp, $lasturl, $lasttitle) = update_jims_ramblings($url, $list);
+        if ( strpos($domain, 'www.orengrad.com') === 0) 
+            list($timestamp, $lasturl, $lasttitle) = update_oren_grad($url, $domain, $list);
+        else {
+            // echo "unmatched domain $domain\n";
+            $id = array_search($domain, array_column($list, 'domain'));
+            $timestamp = $list[$id]['timestamp'];
+            // $timestamp  = make_timestamp($match[4]) + $offset;
+        }
+    }
+    return ['domain' => $domain, 'url' => $url, 'title' => $title, 'lasturl' => $lasturl,
+            'lasttitle' => $lasttitle, 'timestamp' => $timestamp, 'housekeeping' => $housekeeping];
+}
+
+function debug_echo ( $flag, $args ) {
+    if ($flag == 1)
+        echo "<div>" . $args . "</div>\n";
+}
+
+function update_oren_grad($url, $domain, $list) {
+    $debug = 0;
+    // foreach($list as $l)
+    //     debug_echo($l['domain']);
+    // echo '<pre>'; echo print_r($list); echo '</pre>';
+    $id = array_search($url, array_column($list, 'url'));
+    // $id = array_search($domain, array_column($list, 'domain'));
+    $lasttitle = '';
+    if ( $id === false ) { // not found in list
+        debug_echo($debug, "OG: $domain not found in list");
+        preg_match('/bodycontent[\'"]>\s*<p><img src=[\'"](pictures\/.*)[\'"] alt=[\'"]/ms', curlDownload($url), $m);
+        $timestamp = time() - $GLOBALS['external_service_pre_aged'];
+        $lasturl   = $url . '/' . $m[1];
+    } else { // found
+        debug_echo($debug, "OG: $domain found in list");
+        $timestamp = $list[$id]['timestamp'];
+        $lasturl   = $list[$id]['lasturl'];
+    }
+    debug_echo($debug, "OG: lasturl age " . (time() - $timestamp ) . "s");
+    if ( (time() - $timestamp ) > $GLOBALS['external_service_min_time'] ) {
+        debug_echo($debug, "OG: $domain found in list but outdated");
+        preg_match('/bodycontent[\'"]>\s*<p><img src=[\'"](pictures\/.*)[\'"] alt=[\'"]/ms', curlDownload($url), $m);
+        $lasturl   = $url . '/' . $m[1];
+        if ( $lasturl == $list[$id]['lasturl'] ) {
+            debug_echo( $debug, "OG: lasturl unchanged, timestamp unchanged: " . (time() - $timestamp) . "s");
+            $timestamp = $list[$id]['timestamp'];
+        } else {
+            debug_echo($debug, "OG: lasturl CHANGED, timestamp unchanged: " . (time() - $timestamp) . "s");
+            $timestamp = time() - $GLOBALS['external_service_pre_aged'];
+        }
+    }
+    debug_echo( $debug, "OG: $domain final timestamp: " . (time() - $timestamp) . "s");
+    return [$timestamp, $lasturl, $lasttitle];
+}
+
+function update_jims_ramblings($url, $list) {
+    $id = array_search($url, array_column($list, 'url'));
+    if ( $id === false ) { // not found in list
+        // echo "$url not found in list\n";
+        preg_match('/<h3 class=\'post-title entry-title\'>\s*?<a href=\'(.*?)\'>(.*?)<\/a/', curlDownload($url), $m);
+        $timestamp = time() - $GLOBALS['external_service_pre_aged'];
+        $lasturl   = $m[1];
+        $lasttitle = $m[2];
+    } else { // found
+        // echo "$url found in list\n";
+        $timestamp = $list[$id]['timestamp'];
+        $lasturl   = $list[$id]['lasturl'];
+        $lasttitle = $list[$id]['lasttitle'];
+    }
+    // echo "lasturl age " . (time() - $timestamp - 600 ) . "s\n";
+    if ( (time() - $timestamp ) > $GLOBALS['external_service_min_time'] + 600 ) {
+        // echo "$url found in list but outdated\n";
+        preg_match('/<h3 class=\'post-title entry-title\'>\s*?<a href=\'(.*?)\'>(.*?)<\/a/', curlDownload($url), $m);
+        $timestamp = time() - $GLOBALS['external_service_pre_aged'];
+        $lasturl   = $m[1];
+        $lasttitle = $m[2];
+        if ( $lasttitle == $list[$id]['lasttitle'] )
+            $timestamp = $list[$id]['timestamp'];
+    }
+    return [$timestamp, $lasturl, $lasttitle];
+}
+
+function update_lfi($url, $list) {
+    $id = array_search($url, array_column($list, 'url'));
+    if ( $id === false ) { // not found in list
+        // echo "$url not found in list\n";
+        preg_match('/location = \'(.*?)\'">\s*?<h1 class="typo-\d+">(.*?)</msi', curlDownload($url), $m);
+        $timestamp = time() - $GLOBALS['external_service_pre_aged'];
+    } else { // found
+        // echo "$url found in list\n";
+        $timestamp = $list[$id]['timestamp'];
+        $lasturl   = $list[$id]['lasturl'];
+        $lasttitle = $list[$id]['lasttitle'];
+    }
+    // echo "lasturl age " . (time() - $timestamp - 600 ) . "s\n";
+    if ( (time() - $timestamp ) > $GLOBALS['external_service_min_time'] + 600 ) {
+        // echo "$url found in list but outdated\n";
+        preg_match('/location = \'(.*?)\'">\s*?<h1 class="typo-\d+">(.*?)</msi', curlDownload($url), $m);
+        $timestamp = time() - $GLOBALS['external_service_pre_aged'];
+        $lasturl   = $m[1];
+        $lasttitle = $m[2];
+        if ( $lasttitle == $list[$id]['lasttitle'] )
+            $timestamp = $list[$id]['timestamp'];
+    }
+    return [$timestamp, $lasturl, $lasttitle];
+}
+
+function create_linklist ($list, $housekeeping) {
+    // echo '<pre>' . $housekeeping . '<pre>';
+    $debug = 0;
+    $hurl = "http://spring2life-links.blogspot.de";
+    debug_echo($debug, $hurl);
+    $html = curlDownload($hurl);
+    $bloglines = reduce_lines($html);
+    // debug_echo($debug, $bloglines);
+    # matches: 1: url 2: blog title 3. post title 4. time indicator
+    $re = '/<div class=\'blog-title\'>\s*<a href=\'(.*?)\'.*?>\s*(.*?)<\/a>.*?\'item-title\'>\s*(.*?)\s*<\/span.*?\'item-time\'>\s*(.*?)\s*<\/div>/ms';
+    preg_match_all($re, $bloglines, $matches, PREG_SET_ORDER, 0);
+    $offset = 0;
+    for ($i = 0; $i < count($matches); $i++) {
+        $result = rework_entry($matches[$i], $list, $offset, $housekeeping);
+        // print_r($result['domain'] . "\n");
+        $id = array_search( $result['domain'], array_column( $list, 'domain' ));
+        // debug_echo($debug, $result['domain']);
+        if ( is_int($id) ) {
+            $list[$id]['lasturl'] = $result['lasturl'];
+            $list[$id]['lasttitle'] = $result['lasttitle'];
+            $list[$id]['timestamp'] = $result['timestamp'];
+            $list[$id]['housekeeping'] = $housekeeping;
+        } else {
+            array_push($list, $result);
+        }
+        $offset += 1;
+    }
+    $hk = $housekeeping - 2;
+    $op = array_search('www.ruedulavoir.com', array_column($list, 'domain'));
+    echo "<pre>$op</pre>";
+    unset($list[$op]);
+    // while ( $hk < $housekeeping ) {
+    //     debug_echo($debug, $hk);
+    //     while ( is_int($to_delete = array_search($hk, array_column($list, 'housekeeping' ))) ) {
+    //         echo '<pre style="color:green;">' . $hk . ' ';
+    //         echo print_r( $list[$to_delete] );
+    //         echo '</pre>';
+    //         unset($list[$to_delete]);
+    //     }
+    //     // while ( $to_delete = array_search($hk, array_column($list, 'housekeeping' )) !== NULL) {
+    //     //     debug_echo(1, $to_delete);
+    //         // unset($list[$to_delete]);
+    //     // }
+    //     $hk = $hk + 1;
+    // }
+    return $list;
+}
+
+function retrieve_list() {
+    $debug = 0;
+    $time1 = (float) microtime(true);
+    // echo "getting content from stored list " . (time() - filemtime('/tmp/file.ser')) . "s\n";
+    // $str = file_get_contents('/tmp/file.ser');
+    // $str = get_transient( $hurl + "_hp" );
+    // if ( $str === false ) { // not found
+    //     $list = create_linklist([]);
+    // } else {                    // found
+    //     // $list = unserialize( $str );
+    //     $list = create_linklist($str);
+    // }
+    $queried_object = get_queried_object();
+    if ( $queried_object ) {
+        $post_id = $queried_object->ID;
+    }
+    // $post_id = 23342;           // for testing, fixed to the blogs-i-read page id
+    debug_echo($debug, $post_id);
+    $cache_key = '_blogs_i_read';
+    $cache = get_post_meta( $post_id, $cache_key, true );
+    $housekeeping = -1;
+    // $cache = [];
+    if ( empty( $cache ) || $cache['expires'] < time() ) {
+        debug_echo($debug, 'empty or expired');
+        if (empty($cache)) {
+            $list = [];
+            $housekeeping = 0;
+        } else {
+            debug_echo($debug, 'expired');
+            $housekeeping = $cache['housekeeping'] + 1;
+            debug_echo($debug, 'housekeeping:' . $housekeeping);
+            $list = $cache['data'];
+        }
+        $list = create_linklist($list, $housekeeping);
+        debug_echo($debug, 'after creating linklist');
+        $cache = array( 
+            'expires' => time() + $GLOBALS['blogs_i_read_min_time'],
+            'data' => $list,
+            'housekeeping' => $housekeeping );
+        update_post_meta( $post_id, $cache_key, $cache );
+        debug_echo($debug, 'after updating post meta');
+    } else {
+        debug_echo($debug, 'neither empty nor expired');
+        $housekeeping = $cache['housekeeping'];
+        create_linklist($cache['data'], $housekeeping);
+    }
+    debug_echo($debug, 'before printing');
+    return(print_list( $cache['data'], $time1 ));
+}
+
+function print_list ( $list, $time1 ) {
+    $list2 = array_msort($list, array('timestamp' => SORT_DESC));
+    $s = '';
+    $dayflag = $weekflag = $monthflag = $yearflag = false;
+    foreach ($list2 as $l) {
+        if ( ! $dayflag and ((time() - $l['timestamp']) > 24*3600) ) {
+            $s .= "<!-- " . (time() - $l['timestamp']) . " // " . 24*3600 . " -->\n";
+            $s .= "</ul>\n<li style='font-weight: bold;'>A day and older</li>\n<ul>\n";
+            $dayflag = true;
+        } elseif ( ! $weekflag and ((time() - $l['timestamp']) > 7*24*3600) ) {
+            $s .= "</ul>\n<li style='font-weight: bold;'>Less than a month</li>\n<ul>\n";
+            $weekflag = true;
+        } elseif ( ! $monthflag and ((time() - $l['timestamp']) > 30*24*3600) ) {
+            $s .= "</ul>\n<li style='font-weight: bold;'>Older</li>\n<ul>\n";
+            $monthflag = true;
+        } elseif ( ! $yearflag and ((time() - $l['timestamp']) > 365*24*3600) ) {
+            $s .= "</ul>\n<li style='font-weight: bold;'>From medieval times</li>\n<ul>\n";
+            $yearflag = true;
+        } 
+        $s .= '<li>';
+        // $s .= '<span style="color:green">' . (time() - $l['timestamp']) . '</span>; ';
+        // $s .= '<span style="color:blue">' . $l['housekeeping'] . '</span>; ';
+        $s .= '<a target="_blank" href="' . $l['url'] . '">' . $l['title'] . '</a> // <a target="_blank" href="'
+           . $l['lasturl'] . '">' . $l['lasttitle'] . "</a></li>\n";
+    }
+    $timespent = microtime(true) - $time1;
+    return $s . "<!-- Duration $timespent sec -->\n";
+}
+
+// function store_list($list) {
+//     // anpassen für wordpress, zum testen schreiben in Datei
+//     // $ser = serialize($list);
+//     // $file = fopen('/tmp/file.ser', 'wb');
+    
+//     // fwrite($file, $ser); 
+//     set_transient( $hurl + "_hp", $list, 600 );
+// }
+
+function array_msort($array, $cols) {
+    $colarr = array();
+    foreach ($cols as $col => $order) {
+        $colarr[$col] = array();
+        foreach ($array as $k => $row) { $colarr[$col]['_'.$k] = strtolower($row[$col]); }
+    }
+    $eval = 'array_multisort(';
+    foreach ($cols as $col => $order) {
+        $eval .= '$colarr[\''.$col.'\'],'.$order.',';
+    }
+    $eval = substr($eval,0,-1).');';
+    eval($eval);
+    $ret = array();
+    foreach ($colarr as $col => $arr) {
+        foreach ($arr as $k => $v) {
+            $k = substr($k,1);
+            if (!isset($ret[$k])) $ret[$k] = $array[$k];
+            $ret[$k][$col] = $array[$k][$col];
+        }
+    }
+    return $ret;
+}
+
+?>
+<?php get_header(); ?>
+<div id="content" class="site-content">
+  <div id="primary" class="content-area">
+    <main id="main" class="site-main" role="main">
+      <article id="post--31201" class="post--31201 post type-post status-publish format-image hentry category-vernacular post_format-post-format-image entry">
+        <header class="entry-header">
+	  <h2 class="entry-title default-max-width">Blogs I read</h2>
+	</header><!-- .entry-header -->
+        
+        <div id="content" class="site-content">
+          <div id="primary" class="content-area">
+            <main id="main" class="site-main" role="main">
+	
+	      <div class="entry-content">
+                <ul class="linktable">
+                  <li style="font-weight: bold;">Hot from the Sphere</li>
+                  <ul>
+                  <?php echo retrieve_list (); ?>
+                  </ul>
+                </ul>
+              </div><!-- .entry-content -->
+            </main>
+          </div>
+        </div>
+      </article><!-- #post-31164 -->
+    </main><!-- #main -->
+  </div><!-- #primary -->
+</div><!-- #content -->
+<?php get_footer(); ?>
+
+<?php
+// Local variables:
+// compile-command: "php linkpage5.php"
+// End:
+?>

+ 42 - 0
linkpage6.php

@@ -0,0 +1,42 @@
+<?php
+/*
+Template Name: Blogroll 6 Python-to-the-rescue
+ */
+?>
+
+<?php
+$text= file_get_contents('/var/www/html/wp-content/themes/twentytwentyone-child-spring2life/cronlinks.html');
+
+?>
+<?php get_header(); ?>
+<div id="content" class="site-content">
+  <div id="primary" class="content-area">
+    <main id="main" class="site-main" role="main">
+      <article id="post--31201" class="post--31201 post type-post status-publish format-image hentry category-vernacular post_format-post-format-image entry">
+        <header class="entry-header">
+	  <h2 class="entry-title default-max-width">Blogs I read</h2>
+	</header><!-- .entry-header -->
+        
+        <div id="content" class="site-content">
+          <div id="primary" class="content-area">
+            <main id="main" class="site-main" role="main">
+	
+	      <div class="entry-content">
+                <ul class="linktable">
+                  <?php echo $text; ?>
+                </ul>
+              </div><!-- .entry-content -->
+            </main>
+          </div>
+        </div>
+      </article><!-- #post-31164 -->
+    </main><!-- #main -->
+  </div><!-- #primary -->
+</div><!-- #content -->
+<?php get_footer(); ?>
+
+<?php
+// Local variables:
+// compile-command: "php linkpage5.php"
+// End:
+?>

+ 288 - 0
postie-helper.php

@@ -0,0 +1,288 @@
+<?php
+/*	$Id: postie-helper.php,v 1.2 2018/04/17 11:43:22 springm Exp springm $	*/
+
+/*	$Log: postie-helper.php,v $
+ *	Revision 1.2  2018/04/17 11:43:22  springm
+ *	Summary: Funktioniert
+ *	*/
+
+
+/* ------------------- postie helper function for leftover categories --- */
+/* postie removes categories given in the mail subject if it finds them in the
+*  wordpress categories.
+*  all other categories will be made tags of the created post
+
+for this to work, postie-settings->message->remove matched categories has to be set to no
+
+*/
+
+add_filter('postie_post_before', 'mws_auto_tag');
+
+function mws_auto_tag($post) {
+    DebugEcho('============================== mws_auto_tag ' . print_r($post, true));
+    // DebugEcho('    test for "common places" category');
+    // if (in_category( 'Common Places', $post )) {
+    //     DebugEcho('    post has "common places" category');
+    // }
+    $post = evaluate_image_exif($post, $post['post_category']);
+    $post['post_name'] = $post['post_title'];
+    DebugEcho('========================== end mws_auto_tag');
+    DebugEcho("========================== post_content before massage\n" . $post['post_content']);
+    $post['post_content'] = preg_replace('!<div class="postie-attachments">!','', $post['post_content']);
+    $post['post_content'] = preg_replace('!</div>!','', $post['post_content']);
+    $post['post_content'] = preg_replace('!<p></p>!','', $post['post_content']);
+    $post['post_content'] = preg_replace('!<br />!','', $post['post_content']);
+    $post['post_content'] = preg_replace('!\n!','', $post['post_content']);
+    $post['post_content'] = preg_replace('!&lt;!','<', $post['post_content']);
+    $post['post_content'] = preg_replace('!&gt;!','>', $post['post_content']);
+    DebugEcho("========================== post_content after massage\n" . $post['post_content']); 
+    $post = make_landscape_photos_large($post);
+    return $post;
+}
+
+/* extract information from the exif metadata of the first image in the post.
+*  if applicable create the title, categories and location information from this */ 
+function evaluate_image_exif( $post, $categories ) {
+    DebugEcho('MWS =====> begin  evaluate_image_exif');
+    $common_places_found = 0;
+    DebugEcho('    test for "common places" category');
+    if (in_category( 'common places', $post )) {
+        DebugEcho('    post has "common places" category');
+        $common_places_found = 1;
+    }
+    $iimgs = get_attached_media('image', $post['ID']);
+    $upload_dir = wp_upload_dir();
+    foreach ( $iimgs as $iimg ) {
+        $imagefile = $upload_dir['basedir'] . '/' .
+                     wp_get_attachment_metadata( get_post_thumbnail_id( $post['ID'] ) )['file'];
+        break;
+    }
+    $meta = miech_wp_read_image_metadata( get_post_meta($post['ID']), $imagefile, $sourceImageType );
+    if ( ! empty( $meta['title'] ) )
+        $post['post_title'] = $meta['title'];
+    DebugEcho('~~~~~~~~~~ ' . $post['post_title'] );
+    preg_match_all('/\[(.*?)\]/', $post['post_title'], $leftovercats);
+    print_r($leftovercats[1]); 
+    foreach ( array_merge( array( $meta['country'], $meta['state'], $meta['city'] ),
+                           explode(',', $meta['keywords']), $leftovercats[1] ) as $k) {
+        /* DebugEcho('     category/tag: ' . $k); */
+        $in_blacklist = 0;
+        foreach ( array('wp', 'blog', 'status', 'genre', 'published', 'printed', 'lens', 'treatment' ) as $b ) {
+            if ( strcasecmp( "$k", "$b" ) == 0 ) {
+                $in_blacklist = 1;
+            }
+        }
+        /* if ( $in_blacklist < 1 ) { */
+        if ( $in_blacklist < 1 and strlen($k) > 0) {
+            DebugEcho("     Examining '$k' " );
+            if ( strcasecmp('common places', "$k") == 0) {
+                DebugEcho("     '$k' GEFUNDEN!" );
+                $common_places_found = 1;
+            }
+            $cat = get_term_by('name', (string) "$k", 'category');
+            if ( isset($cat) ) {
+                if ( $cat->term_id > 1 ) {
+                    DebugEcho("     Category '$k' exists with id " . $cat->term_id );
+                    array_push( $categories, $cat->term_id );
+                } else {
+                    DebugEcho("     Category '$k' does not exist ==> '$k' becomes tag" );
+                    array_push($post['tags_input'], "$k");
+                }
+            }
+        }
+    }
+    DebugEcho("     \$common_places_found ist $common_places_found: " . print_r($categories, true) );
+    if ( $common_places_found == 0 ) {
+        array_push( $categories,  get_term_by('name', (string) "Vernacular", 'category')->term_id );
+    } else {
+        $c2 = \array_diff($categories, [1964]);
+        $categories = $c2;
+        DebugEcho("     'vernacular' removed: " . print_r($categories, true) );
+    }
+    $post['post_category'] = $categories;
+    if ( $meta['city'] )
+        $post['post_content'] = mws_add_caption( $post['post_content'], $meta );
+    /* remove leftover category strings from title */
+    $post['post_title'] = preg_replace('/\[.*\]\s*/', '', $post['post_title']);
+    DebugEcho( "MWS ===> end evaluate_image_exif " .  $imagefile);
+    return $post;
+}
+
+/* ------------------------------------------- exif related functions --- */
+function miech_wp_read_image_metadata( $meta, $file, $sourceImageType ) {
+    DebugEcho('MWS ===> beginning  miech_wp_read_image_metadata');
+    $newmeta = array();
+    
+    // read iptc first, since it might contain data not available in exif such
+    // as caption, description etc
+    getimagesize( $file, $info );
+    if ( ! empty( $info['APP13'] ) ) {
+        $iptc = iptcparse( $info['APP13'] );
+        $newmeta['title']    = trim( $iptc['2#105'][0] );
+        $newmeta['country']  = trim( $iptc['2#101'][0] );
+        $newmeta['state']    = trim( $iptc['2#095'][0] );
+        $newmeta['city']     = trim( $iptc['2#090'][0] );
+        $newmeta['location'] = trim( $iptc['2#092'][0] );
+        $keywordcount = count($iptc["2#025"]);
+        for ( $i = 0; $i < $keywordcount; $i++ ) {
+            if ( strlen($newmeta['keywords']) > 0 )
+                $newmeta['keywords'] .= ',' ;
+            $newmeta['keywords'] .= $iptc["2#025"][$i];
+        }
+    } 
+
+    $exif = @exif_read_data( $file );
+    /*     DebugEcho('Exif' . print_r($exif)); */
+    DebugEcho('GPSLatitude is ' . $exif['GPSLatitude']);
+    if ( is_numeric($exif['GPSLatitude']) )
+        DebugEcho('GPSLatitude is numeric ' );
+    else
+        DebugEcho('GPSLatitude is not numeric ' );
+        
+    if ( ! empty($exif['GPSLatitude'])) 
+        $newmeta['latitude'] = geo_single_fracs2dec($exif['GPSLatitude'] );
+    if ( ! empty($exif['GPSLongitude']))
+        $newmeta['longitude'] = geo_single_fracs2dec($exif['GPSLongitude']) ;
+    if ( ! empty($exif['GPSLatitudeRef']))
+        if ( $exif['GPSLatitudeRef'] == 'S' )
+            $newmeta['latitude'] = '-' . $newmeta['latitude'];
+    if ( ! empty($exif['GPSLongitudeRef']))
+        if ( $exif['GPSLongitudeRef'] == 'W' )
+            $newmeta['longitude'] = '-' . $newmeta['longitude'];
+
+    foreach ( array( 'city', 'location') as $key ) {
+        if ( $newmeta[ $key ] && ! seems_utf8( $newmeta[ $key ] ) )
+            $newmeta[ $key ] = utf8_encode( $newmeta[ $key ] );
+    }
+    
+    $meta = array_merge($meta, $newmeta);
+    DebugEcho('MWS ===> end miech_wp_read_image_metadata');
+    return $meta;
+}
+
+function geo_frac2dec($str) {
+  @list( $n, $d ) = explode( '/', $str );
+  if ( !empty($d) )
+    return $n / $d;
+  return $str;
+}
+
+function geo_single_fracs2dec($fracs) {
+	return	geo_frac2dec($fracs[0]) +
+		geo_frac2dec($fracs[1]) / 60 +
+		geo_frac2dec($fracs[2]) / 3600;
+}
+
+function mws_add_caption( $s, $meta ) {
+    DebugEcho('MWS ===> begin mws_add_caption');
+    $alt = $meta['title'];
+    $caption = "</div>\n<p class='mycaption'>";
+    if ( $meta['location'] ) {
+        $caption = $caption . $meta['location'] . ', ';
+        $alt     = $alt . ', ' . $meta['location'];
+    }
+    $caption = $caption . $meta['city'];
+    $alt = $alt . ', ' . $meta['city'];
+    if ( $meta['longitude'] ) {
+        $caption = $caption . ' (<a href="http://www.openstreetmap.org/?mlat=' . $meta['latitude'];
+        $caption = $caption . ';&mlon=' . $meta['longitude'] . '&zoom=14&q=mapquest" target="_blank">OSM</a>)'; 
+        $alt = $alt . ', geotagged';
+    }
+    $caption = $caption . "</p>\n";
+    $keywords = $meta['keywords'];
+    DebugEcho('Keywords: ' . $keywords);
+    $keywords = preg_replace('/(WP|Lens,|Status,|Blog,|Published,|Treatment,|)/s', '', $keywords);
+    $keywords = preg_replace('/"/s', "'", $keywords);
+    $keywords = preg_replace('/,/s', ', ', $keywords);
+    $keywords = preg_replace('/, $/', '', $keywords);
+    DebugEcho($keywords);
+    $alt = $alt . ', ' . $keywords;
+    DebugEcho($alt);
+    $s = preg_replace('/<br \/>\s*<\/div>/ims', $caption, $s, 1);
+    $s = preg_replace('/alt=""/ims', 'alt="' . $alt . '"', $s, 1);
+    DebugEcho($s); 
+    DebugEcho('MWS ===> end mws_add_caption');
+    return $s;
+}
+
+/* add the categories of the postie post to all attached images */
+add_filter('postie_post_after', 'mws_postie_add_cats_to_images'); /* MWS now */
+
+function mws_postie_add_cats_to_images( $post ) {
+    $cats = $post['post_category'];
+    $imgs = get_attached_media('image', $post['ID']);
+    $flag = 0;
+    foreach ($cats as $c) {
+        /* DebugEcho( $c ); */
+        $cat = get_category($c);
+        /* DebugEcho( print_r($cat) ); */
+        if ( $cat->cat_ID > 1 ) {
+            foreach ( $imgs as $img ) {
+                wp_set_post_categories( $img->ID, $cat->cat_ID, true );
+            }
+        }
+        $flag = 1;
+    }
+    if ( $flag > 0 ) {
+        wp_set_post_categories( $img->ID,  get_cat_ID('no_user'), true );
+    }
+    return $post;
+}
+
+function make_landscape_photos_large( $post ) {
+    DebugEcho("make_landscape_photos_large 1  +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n" . $post['post_content'] . "\n");
+    preg_match('/ postie_dunit (\d+)pxx(\d+)px /', $post['post_content'], $size);
+    DebugEcho( print_r($size) );
+    if ( $size[1] > $size[2] ) {
+        DebugEcho( "Landscape\n" );
+        #<!-- postie_dunit 750pxx422px --><!-- wp:image {"id":36954,"sizeSlug":"large","linkDestination":"media"} --><figure class="wp-block-image size-large"><a href="https://markus-spring.info/wp-content/uploads/sites/2/2021/03/Ripples-6.jpg"><img src="https://markus-spring.info/wp-content/uploads/sites/2/2021/03/Ripples-6-1200x675.jpg" alt="Ripples.jpg" class="wp-image-36954"/></a><figcaption>Saalachau, Bad Reichenhall</figcaption></figure><!-- /wp:image -->
+        #
+        # <!-- wp:image {"align":"wide","id":36936,"sizeSlug":"large","linkDestination":"media"} --><figure class="wp-block-image alignwide size-large">
+
+        $post['post_content'] = preg_replace('/{/', '{"align":"wide",', $post['post_content']);
+        $post['post_content'] = preg_replace('/wp-block-image /','wp-block-image alignwide ', $post['post_content']);
+        $post['post_content'] = preg_replace('/<!-- postie_dunit.*? -->\n*/', '', $post['post_content']);
+        DebugEcho($post['post_content']);
+    }
+    return $post;
+}
+
+
+/* add_filter('postie_post_after', 'mws_postie_rotate_ios_images');
+
+function mws_postie_rotate_ios_images ( $post ) {
+    $upload_dir = wp_upload_dir();
+    foreach ( $iimgs as $iimg ) {
+        $imagefile = $upload_dir['basedir'] . '/' .
+                     wp_get_attachment_metadata( get_post_thumbnail_id( $post['ID'] ) )['file'];
+        DebugEcho("1. Image to rotate: " .$imagefile);
+        correctImageOrientation($imagefile);
+    }
+   } */
+
+/* add_action('postie_file_added', 'mws_postie_fileadded', 10, 3); */ /* MWS now */
+
+/* function mws_postie_fileadded($postid, $attachmentid, $file_array) {
+   DebugEcho('MWS ========> begin mws_postie_fileadded');
+   $fileinfo = wp_check_filetype(get_attached_file($attachmentid));
+   $upload_dir = wp_upload_dir()['basedir'];
+   $meta = wp_get_attachment_metadata( $attachmentid );
+   $mimetype = $fileinfo['type'];
+   if (strpos($mimetype, 'image', 0) === 0) { //only if attachment is an image
+   $file = $upload_dir . '/' . $meta['file'];
+   set_title_from_exif_if_necessary($postid, $file, $meta);
+   $subdir = dirname($meta['file']);
+   $deg = correctImageOrientation($file);
+   foreach ( array_keys($meta['sizes']) as $size ) {
+   if ( $size != 'full' ) {
+   $file = $upload_dir . '/' . $subdir . '/' . $meta['sizes'][$size]['file'];
+   correctImageOrientation($file);
+   }
+   }
+   }
+   DebugEcho('MWS ========> end mws_postie_fileadded');
+   }
+ */
+
+
+?>

BIN=BIN
proxima_nova_alt_light-webfont.woff


BIN=BIN
proxima_nova_alt_light-webfont.woff2


BIN=BIN
proxima_nova_thin-webfont.woff


BIN=BIN
proxima_nova_thin-webfont.woff2


BIN=BIN
proximanova-regular-webfont.woff


BIN=BIN
proximanova-regular-webfont.woff2


+ 421 - 0
style.css

@@ -0,0 +1,421 @@
+/*
+Theme Name: Twenty Twenty One Child spring2life.
+Theme URI: https://example.com
+Description: spring2life child theme for Twenty Twenty One.
+Author: Markus Spring
+Author URI: https://markus-spring.de
+Template: twentytwentyone
+Version: 1.0
+License: GNU General Public License v2 or later
+License URI: https://www.gnu.org/licenses/gpl-2.0.html
+*/
+
+/* ----------------------------------------------------- proxima-nova --- */
+@font-face {
+    font-family: 'proxima_novaregular';
+    src: url('proximanova-regular-webfont.woff2') format('woff2'),
+         url('proximanova-regular-webfont.woff') format('woff');
+    font-weight: normal;
+    font-style: normal;
+}
+
+@font-face {
+    font-family: 'proxima_novathin';
+    src: url('proxima_nova_thin-webfont.woff2') format('woff2'),
+         url('proxima_nova_thin-webfont.woff') format('woff');
+    font-weight: normal;
+    font-style: normal;
+}
+@font-face {
+    font-family: 'proxima_nova_altlight';
+    src: url('proxima_nova_alt_light-webfont.woff2') format('woff2'),
+         url('proxima_nova_alt_light-webfont.woff') format('woff');
+    font-weight: normal;
+    font-style: normal;
+}
+
+/* raleway-300 - latin */
+@font-face {
+  font-display: swap; /* Check https://developer.mozilla.org/en-US/docs/Web/CSS/@font-face/font-display for other options. */
+  font-family: 'Raleway';
+  font-style: normal;
+  font-weight: 300;
+  src: url('fonts/raleway-v29-latin-300.woff2') format('woff2'), /* Chrome 36+, Opera 23+, Firefox 39+, Safari 12+, iOS 10+ */
+       url('fonts/raleway-v29-latin-300.ttf') format('truetype'); /* Chrome 4+, Firefox 3.5+, IE 9+, Safari 3.1+, iOS 4.2+, Android Browser 2.2+ */
+}
+
+/* raleway-300italic - latin */
+@font-face {
+  font-display: swap; /* Check https://developer.mozilla.org/en-US/docs/Web/CSS/@font-face/font-display for other options. */
+  font-family: 'Raleway';
+  font-style: italic;
+  font-weight: 300;
+  src: url('fonts/raleway-v29-latin-300italic.woff2') format('woff2'), /* Chrome 36+, Opera 23+, Firefox 39+, Safari 12+, iOS 10+ */
+       url('fonts/raleway-v29-latin-300italic.ttf') format('truetype'); /* Chrome 4+, Firefox 3.5+, IE 9+, Safari 3.1+, iOS 4.2+, Android Browser 2.2+ */
+}
+
+/* raleway-regular - latin */
+@font-face {
+  font-display: swap; /* Check https://developer.mozilla.org/en-US/docs/Web/CSS/@font-face/font-display for other options. */
+  font-family: 'Raleway';
+  font-style: normal;
+  font-weight: 400;
+  src: url('fonts/raleway-v29-latin-regular.woff2') format('woff2'), /* Chrome 36+, Opera 23+, Firefox 39+, Safari 12+, iOS 10+ */
+       url('fonts/raleway-v29-latin-regular.ttf') format('truetype'); /* Chrome 4+, Firefox 3.5+, IE 9+, Safari 3.1+, iOS 4.2+, Android Browser 2.2+ */
+}
+
+/* raleway-italic - latin */
+@font-face {
+  font-display: swap; /* Check https://developer.mozilla.org/en-US/docs/Web/CSS/@font-face/font-display for other options. */
+  font-family: 'Raleway';
+  font-style: italic;
+  font-weight: 400;
+  src: url('fonts/raleway-v29-latin-italic.woff2') format('woff2'), /* Chrome 36+, Opera 23+, Firefox 39+, Safari 12+, iOS 10+ */
+       url('fonts/raleway-v29-latin-italic.ttf') format('truetype'); /* Chrome 4+, Firefox 3.5+, IE 9+, Safari 3.1+, iOS 4.2+, Android Browser 2.2+ */
+}
+
+/* raleway-500 - latin */
+@font-face {
+  font-display: swap; /* Check https://developer.mozilla.org/en-US/docs/Web/CSS/@font-face/font-display for other options. */
+  font-family: 'Raleway';
+  font-style: normal;
+  font-weight: 500;
+  src: url('fonts/raleway-v29-latin-500.woff2') format('woff2'), /* Chrome 36+, Opera 23+, Firefox 39+, Safari 12+, iOS 10+ */
+       url('fonts/raleway-v29-latin-500.ttf') format('truetype'); /* Chrome 4+, Firefox 3.5+, IE 9+, Safari 3.1+, iOS 4.2+, Android Browser 2.2+ */
+}
+
+/* raleway-700 - latin */
+@font-face {
+  font-display: swap; /* Check https://developer.mozilla.org/en-US/docs/Web/CSS/@font-face/font-display for other options. */
+  font-family: 'Raleway';
+  font-style: normal;
+  font-weight: 700;
+  src: url('fonts/raleway-v29-latin-700.woff2') format('woff2'), /* Chrome 36+, Opera 23+, Firefox 39+, Safari 12+, iOS 10+ */
+       url('fonts/raleway-v29-latin-700.ttf') format('truetype'); /* Chrome 4+, Firefox 3.5+, IE 9+, Safari 3.1+, iOS 4.2+, Android Browser 2.2+ */
+}
+
+/* raleway-700italic - latin */
+@font-face {
+  font-display: swap; /* Check https://developer.mozilla.org/en-US/docs/Web/CSS/@font-face/font-display for other options. */
+  font-family: 'Raleway';
+  font-style: italic;
+  font-weight: 700;
+  src: url('fonts/raleway-v29-latin-700italic.woff2') format('woff2'), /* Chrome 36+, Opera 23+, Firefox 39+, Safari 12+, iOS 10+ */
+       url('fonts/raleway-v29-latin-700italic.ttf') format('truetype'); /* Chrome 4+, Firefox 3.5+, IE 9+, Safari 3.1+, iOS 4.2+, Android Browser 2.2+ */
+}
+
+
+/* --------------------------------------------------- terminal dosis --- */
+@font-face {
+    font-family: 'Terminal Dosis';
+    src: url('TerminalDosis-ExtraLight.woff2') format('woff2'),
+        url('TerminalDosis-ExtraLight.woff') format('woff');
+    font-weight: 200;
+    font-style: normal;
+    font-display: swap;
+}
+
+@font-face {
+    font-family: 'Terminal Dosis';
+    src: url('TerminalDosis-Bold.woff2') format('woff2'),
+        url('TerminalDosis-Bold.woff') format('woff');
+    font-weight: bold;
+    font-style: normal;
+    font-display: swap;
+}
+
+@font-face {
+    font-family: 'Terminal Dosis';
+    src: url('TerminalDosis-SemiBold.woff2') format('woff2'),
+        url('TerminalDosis-SemiBold.woff') format('woff');
+    font-weight: 600;
+    font-style: normal;
+    font-display: swap;
+}
+
+@font-face {
+    font-family: 'Terminal Dosis';
+    src: url('TerminalDosis-Light.woff2') format('woff2'),
+        url('TerminalDosis-Light.woff') format('woff');
+    font-weight: 300;
+    font-style: normal;
+    font-display: swap;
+}
+
+@font-face {
+    font-family: 'Terminal Dosis';
+    src: url('TerminalDosis-Regular.woff2') format('woff2'),
+        url('TerminalDosis-Regular.woff') format('woff');
+    font-weight: normal;
+    font-style: normal;
+    font-display: swap;
+}
+
+@font-face {
+    font-family: 'Terminal Dosis';
+    src: url('TerminalDosis-Medium.woff2') format('woff2'),
+        url('TerminalDosis-Medium.woff') format('woff');
+    font-weight: 500;
+    font-style: normal;
+    font-display: swap;
+}
+
+@font-face {
+    font-family: 'Terminal Dosis';
+    src: url('TerminalDosis-ExtraBold.woff2') format('woff2'),
+        url('TerminalDosis-ExtraBold.woff') format('woff');
+    font-weight: 800;
+    font-style: normal;
+    font-display: swap;
+}
+
+/* --------------------------------------------- end font definitions --- */
+:root {
+ /* --max--alignwide-width:1400px; */
+ /* --font-base:'proxima_novathin','Raleway',sans-serif; */
+ --font-base:'TerminalDosis-Regular','proxima_novathin','Raleway',sans-serif;
+ /* --font-base:'Raleway',sans-serif; */
+ --global--font-size-base:1.125rem;
+ /* --global--line-height-body:1.6; */
+ /* --font-headings:'proxima_nova_altlight','Raleway',sans-serif; */
+ --font-headings:'TerminalDosis-Regular','proxima_nova_altlight','Raleway',sans-serif;
+ /* --font-headings:'Raleway',sans-serif; */
+ /* --heading--font-weight:500; */
+ --heading--font-weight:700;
+ /* --heading--font-weight:400; */
+ --heading--font-weight-page-title:500;
+ --heading--font-weight-strong:500;
+ /* --heading--font-weight-page-title:700; */
+ /* --heading--font-weight-strong:700; */
+ /* --global--font-size-xxl:4rem; */
+ --global--font-size-xxl:2.8rem;
+ --global--font-size-xxl:3.7rem;
+ /* --primary-nav--font-size:1rem; */
+ /* --primary-nav--font-weight:400; */
+ --primary-nav--font-weight:500;
+ /* --primary-nav--font-weight:400; */
+ /* --button--border-width:1px; */
+ /* --form--border-width:1px */
+ --global--font-size-xs: max(calc(var(--global--font-size-base)*1),16px);
+}
+
+body {
+    /* font-weight: 500; */
+    font-weight: 400;
+}
+
+/* @media only screen and (max-width: 651px) :root { */
+/*     --global--font-size-page-title: min(1.5rem,var(--global--font-size-xxl)); */
+/*     --global--font-size-page-title: 0.5rem; */
+/* } */
+
+.singular .entry-title, .comment-reply-title {
+    /* font-size: calc( var(--global--font-size-page-title) / 3.5 ); */
+}
+
+
+.archive .content-area .format-aside .entry-content, .archive .content-area .format-link .entry-content, .archive .content-area .format-status .entry-content, .blog .content-area .format-aside .entry-content, .blog .content-area .format-link .entry-content, .blog .content-area .format-status .entry-content, .search .content-area .format-aside .entry-content, .search .content-area .format-link .entry-content, .search .content-area .format-status .entry-content {
+    font-size: calc( var(--global--font-size-lg) / 1.3 );
+}
+
+#masthead.site-header, .menu-button-container  {
+    padding-top: calc(var(--global--spacing-vertical)*.2);
+    padding-bottom: calc(var(--global--spacing-vertical)*.2);
+}
+
+.menu-button-container #primary-mobile-menu {
+    margin-top: -18px;
+}
+
+#submit.submit {
+    color: black;
+    background-color: transparent;
+    border-color: grey;
+}
+
+.site-title a {
+    /* font-weight: 500; */
+    font-weight: 400;
+}
+
+/* .linktable a:link { */
+/*     text-decoration: none; */
+/* } */
+
+.linktable .item-title:before {
+    content:": :";
+    /* white-space: pre; */
+}
+
+a:link {
+        text-decoration-color: #888 !important;
+}
+
+a:hover {
+    text-decoration: none !important;
+    color: red !important;
+    /* font-weight: bold; */
+    /* text-decoration-color: red !important; */
+}
+/* a:hover:after { */
+/*     content:"-->"; */
+/*     color: red; */
+/* } */
+
+a:visited {
+        text-decoration-color: #bbb !important;
+}
+
+/* ----------------------------------------------------------- iPad 2 --- */
+@media all and (device-width: 768px) and (device-height: 1024px) and (orientation:landscape) {
+    /* Landscape css rules */
+    #primary {
+        margin: 0 2em !important;
+    }
+    .site-branding {
+        margin-left: 2em;
+    }
+}
+@media all and (device-width: 768px) and (device-height: 1024px) and (orientation:portrait) {
+  /* Portrait css rules */
+    #primary {
+        margin: 0 2em !important;
+    }
+    .site-branding {
+        margin-left: 2em;
+    }
+}
+/* ------------------------------------------------------- end iPad 2 --- */
+
+.sub-menu-toggle {
+    display: none !important;
+}
+
+.box {
+    display: flex;
+    width: 268px;
+}
+
+@media all and (min-width: 1150px) {
+    /* h1.entry-title, h2.entry-title { */
+    /*     display: inline-block; */
+    /*     float: left; */
+    /*     margin-left: calc(50% - var(--responsive--alignwide-width)/2) !important; */
+    /* } */
+}
+
+#content { margin-top: 2rem;
+           padding-top: 0;
+         }
+.entry-header {
+        margin-bottom: 0 !important;
+}
+h1.entry-title, h2.entry-title, h2.comments-title, h2.comment-reply-title {
+    /* font-size: calc(var(--archive-heading-size,var(--heading--font-size-h2))/1.5) !important; */
+    font-size: calc(var(--archive-heading-size,var(--heading--font-size-h2))/1) !important; 
+    /* margin-top: -3px !important; */
+}
+h2.comment-reply-title {
+    font-size: calc(var(--archive-heading-size,var(--heading--font-size-h2))/2) !important;
+}
+.h4, h4 {
+    font-size: calc(var(--heading--font-size-h4)/1.2);
+}
+
+.wp-block-jetpack-tiled-gallery {
+    padding-top: 30px;
+}
+
+.site-name, .powered-by {
+    display: none;
+}
+
+.wpcf7-submit {
+    background: white !important;
+    color: black !important;
+}
+
+/* todo: https://www.cssscript.com/pure-css-expanding-link-underlines/ */
+
+.entry-footer {
+    margin-top: calc(var(--global--spacing-vertical)*1.4) !important;
+}
+
+img[class^="wp-image-"] {
+    padding: 4px;
+    background: white;
+    border: 1px solid #999;
+}
+
+/* --------------------------------------------------------- archives --- */
+.archive-wider {
+    max-width: calc(var(--responsive--aligndefault-width)*1.5);
+}
+
+.blocks-gallery-grid {
+    /* max-width: auto ; */
+    max-width: calc(var(--responsive--aligndefault-width)*1.5) !important;
+}
+
+.archive-slide {
+    width: 210px;
+    height: 210px;
+    margin: 7px;
+    border: solid 1px #a5a5a5;
+    border-radius: 8px;
+    -moz-border-radius: 8px;
+    -webkit-border-radius: 8px;
+    filter: alpha(opacity=85);
+    -moz-opacity: 0.85;
+    opacity: 0.85;
+    float: left;
+    position: relative;
+    padding: 40px;
+}
+
+.archive-slide-slide {
+    border: solid 1px #000000;
+}
+
+.archive-slide-titlebar a span {
+    display: block;
+    height: 40px;
+    width: 128px;
+    overflow: hidden;
+    font-size: calc(var(--global--font-size-xs) * 0.7);
+    text-align: center;
+    padding-left: -20px;
+    padding-right: -20px;
+}
+
+/* .pagination:pre { */
+/*     content:"<br style='clear: all; clear:both;'>";  */
+/* } */
+
+/* .single .site-main > article > .entry-footer { */
+.entry-footer {
+    display: grid;
+    grid-template-columns: 2fr 4fr;
+}
+
+.comments-title {
+    /* padding-top: 0 !important; */
+}
+
+#comment {
+    color: black;
+    opacity: revert;
+    font-family: 'proxima_novaregular' !important;
+    font-size: 18px;
+    /* background-blend-mode: unset; */
+    background-color: transparent;
+}
+
+#comment:focus, #comment:hover {
+    background-color:white !important;
+}
+
+/* remove wp mail smtp nags */
+div#setting-error-tgmpa, #update-nag, .update-nag, .updated.caldera_forms, wp-admin-bar-wp-mail-smtp-menu {
+    display: none;
+} 

+ 45 - 0
template-parts/header/site-branding.php

@@ -0,0 +1,45 @@
+<?php
+/**
+ * Displays header site branding
+ *
+ * @package WordPress
+ * @subpackage Twenty_Twenty_One
+ * @since Twenty Twenty-One 1.0
+ */
+
+$blog_info    = get_bloginfo( 'name' );
+$description  = get_bloginfo( 'description', 'display' );
+$show_title   = ( true === get_theme_mod( 'display_title_and_tagline', true ) );
+$header_class = $show_title ? 'site-title' : 'screen-reader-text';
+
+?>
+
+<?php if ( has_custom_logo() && $show_title ) : ?>
+	<div class="site-logo"><?php the_custom_logo(); ?></div>
+<?php endif; ?>
+
+<div class="site-branding">
+
+  <?php if ( has_custom_logo() && ! $show_title ) : ?>
+    <div class="site-logo"><?php the_custom_logo(); ?></div>
+  <?php endif; ?>
+  
+  <?php if ( $blog_info ) : ?>
+    <?php if ( is_front_page() && ! is_paged() ) : ?>
+      <!-- <h1 class="<?php echo esc_attr( $header_class ); ?>"><?php echo esc_html( $blog_info ); ?></h1> -->
+      <?php [$image_url, $post_url] = catch_that_image(); ?>
+      <!-- $post_url; <?php echo $post_url ?> -->
+      <h1 class="<?php echo esc_attr( $header_class ); ?>"><a href="<?php echo esc_url( $post_url ); ?>"><small>This post on</small> <?php echo esc_html( $blog_info ); ?></a></h1>
+    <?php elseif ( is_front_page() || is_home() ) : ?>
+      <h1 class="<?php echo esc_attr( $header_class ); ?>"><a href="<?php echo esc_url( home_url( '/' ) ); ?>"><?php echo esc_html( $blog_info ); ?></a></h1>
+    <?php else : ?>
+      <p class="<?php echo esc_attr( $header_class ); ?>"><a href="<?php echo esc_url( home_url( '/' ) ); ?>"><?php echo esc_html( $blog_info ); ?></a></p>
+    <?php endif; ?>
+  <?php endif; ?>
+  
+  <?php if ( $description && true === get_theme_mod( 'display_title_and_tagline', true ) ) : ?>
+    <p class="site-description">
+      <?php echo $description; // phpcs:ignore WordPress.Security.EscapeOutput ?>
+    </p>
+  <?php endif; ?>
+</div><!-- .site-branding -->

+ 30 - 0
template-parts/header/titlepage-header.php

@@ -0,0 +1,30 @@
+<?php
+/**
+ * Displays the site header.
+ *
+ * @package WordPress
+ * @subpackage Twenty_Twenty_One
+ * @since Twenty Twenty-One 1.0
+ */
+
+$wrapper_classes  = 'site-header';
+$wrapper_classes .= has_custom_logo() ? ' has-logo' : '';
+$wrapper_classes .= true === get_theme_mod( 'display_title_and_tagline', true ) ? ' has-title-and-tagline' : '';
+$wrapper_classes .= has_nav_menu( 'primary' ) ? ' has-menu' : '';
+?>
+
+<!-- https://www.cssscript.com/morphing-side-menu-with-pure-css-css3/ -->
+<input type="checkbox" id="menuTrigger"/>
+<div class="menu">
+  <label for="menuTrigger" class="trigger">
+    <div class="line"></div>
+    <div class="line"></div>
+    <div class="line"></div>
+  </label>
+</div>
+<header id="masthead" class="<?php echo esc_attr( $wrapper_classes ); ?>" role="banner">
+
+	<?php get_template_part( 'template-parts/header/site-branding' ); ?>
+	<?php get_template_part( 'template-parts/header/site-nav' ); ?>
+
+</header><!-- #masthead -->

+ 179 - 0
titlepage.css

@@ -0,0 +1,179 @@
+   /* --------------------------------------------- animated burger menu --- */
+   /* from  https://www.cssscript.com/morphing-side-menu-with-pure-css-css3/ */
+   
+   .menu {
+     position:fixed;
+     /* position: absolute; */
+     top: 0;
+     left: 0;
+     z-index: 1000;
+     height: 70px;
+     width: 70px;
+     overflow: hidden;
+     pointer-events: none;
+     -webkit-user-select: none;
+     -moz-user-select: none;
+     -ms-user-select: none;
+     user-select: none;
+   }
+   
+   .menu * {
+     -webkit-backface-visibility: hidden;
+     backface-visibility: hidden;
+   }
+   
+   #menuTrigger:checked ~ .menu { pointer-events: auto; }
+   
+   #menuTrigger:checked ~ .menu h3 {
+     -webkit-transform: translate3d(0, 0, 0);
+     transform: translate3d(0, 0, 0);
+     -webkit-transition-delay: 0.2s;
+     transition-delay: 0.2s;
+   }
+   
+   #menuTrigger:checked ~ header>.site-branding p {
+     color: green !important;
+     display: flex !important;
+   }
+   
+   .menu ~ header {
+     display: none !important;
+   }
+   
+   #menuTrigger:checked ~ header {
+     display: flex !important;
+   }
+   
+   #menuTrigger:checked ~ #masthead {
+     -webkit-transform: translate3d(0, 0, 0);
+     transform: translate3d(0, 0, 0);
+     -webkit-transition-delay: 0.2s;
+     transition-delay: 0.2s;
+   }
+   
+   
+   .menu .trigger {
+     position: absolute;
+     z-index: 0;
+     top: 10px;
+     left: 10px;
+     height: 56px;
+     width: 56px;
+     border-radius: 100%;
+     cursor: pointer;
+     pointer-events: auto;
+     -webkit-transition: all 0.4s ease-in-out;
+     transition: all 0.4s ease-in-out;
+     -webkit-transition-property: -webkit-transform, box-shadow;
+     transition-property: transform, box-shadow;
+     -webkit-transform: translate3d(0, 0, 0);
+     transform: translate3d(0, 0, 0);
+     box-shadow: 0 0 0 0px #424242;
+   }
+   
+   .menu .trigger:before {
+     content: '';
+     position: absolute;
+     top: 0;
+     left: 0;
+     height: 100%;
+     width: 100%;
+     border-radius: inherit;
+     overflow: hidden;
+     -webkit-transform: translate3d(0, 0, 0);
+     transform: translate3d(0, 0, 0);
+     -webkit-transition: box-shadow 0.2s 0.4s ease-in-out;
+     transition: box-shadow 0.2s 0.4s ease-in-out;
+     box-shadow: 0 0 0 28px #424242 inset, 0 0 0 28px #FF5722 inset;
+   }
+   
+   #menuTrigger:checked ~ .menu .trigger {
+     /* -webkit-transform: translate3d(94px, 0, 0); */
+     /* transform: translate3d(94px, 0, 0); */
+     /* box-shadow: 0 0 0 370px #424242; */
+   }
+   
+   #menuTrigger:checked ~ .menu .trigger:before {
+     -webkit-transition-delay: 0s;
+     transition-delay: 0s;
+     box-shadow: 0 0 0 0 #424242 inset, 0 0 0 28px #FF5722 inset;
+   }
+   
+   #menuTrigger:checked ~ .menu .trigger .line:nth-child(1) {
+     -webkit-transform: translateY(0) translate3d(-50%, -50%, 0);
+     transform: translateY(0) translate3d(-50%, -50%, 0);
+   }
+   
+   #menuTrigger:checked ~ .menu .trigger .line:nth-child(3) {
+     -webkit-transform: translateY(0) translate3d(-50%, -50%, 0);
+     transform: translateY(0) translate3d(-50%, -50%, 0);
+   }
+   
+   .menu .trigger .line {
+     position: absolute;
+     top: 50%;
+     left: 50%;
+     background: white;
+     height: 2px;
+     width: 18.66667px;
+     -webkit-transform: translate3d(-50%, -50%, 0);
+     transform: translate3d(-50%, -50%, 0);
+     -webkit-transition: -webkit-transform 0.4s ease-in-out;
+     transition: transform 0.4s ease-in-out;
+   }
+   
+   .menu .trigger .line:nth-child(1) {
+     -webkit-transform: translateY(-5px) translate3d(-50%, -50%, 0);
+     transform: translateY(-5px) translate3d(-50%, -50%, 0);
+   }
+   
+   .menu .trigger .line:nth-child(3) {
+     -webkit-transform: translateY(5px) translate3d(-50%, -50%, 0);
+     transform: translateY(5px) translate3d(-50%, -50%, 0);
+   }
+   
+   #menuTrigger {
+     position: fixed;
+     top: 0;
+     left: -60px;
+   }
+   /* ----------------------------------------- end animated burger menu --- */
+   
+   /* ------------------------------------------------------ hide footer --- */
+   .site-info {
+     display: none !important;
+   }
+
+   /* -------------------------------------------------- full size image --- */
+   * {
+     margin: 0;
+     padding: 0;
+   }
+   .imgbox {
+     display: grid;
+     height: 100%;
+     /* -webkit-animation: sk-bouncedelay 3s infinite ease-in-out both;
+        animation: sk-bouncedelay 3s infinite ease-in-out both; */
+   }
+   .center-fit {
+     max-width: 100%;
+     max-height: 100vh;
+     /* max-width: 99%;
+        max-height: 99vh; */
+     margin: auto;
+   }
+   @media all and (device-width: 768px) and (device-height: 1024px) {
+     .imgbox {
+       /* height: 100vh;  */
+       height: 100%;
+       display: flex;
+       /* background-color: red; */
+     }
+     .center-fit {
+       position: relative;
+       display:block;
+       /* top: 50%;
+          left: 50%;
+          transform: translate(-50%, -50%); */
+       ;
+     }

+ 273 - 0
titlepage.php

@@ -0,0 +1,273 @@
+<?php
+/*
+Template Name: Titlepage
+ */
+function catch_that_image() {
+    // echo "<!-- catch_that_image! -->\n";
+    $custom_query = new WP_Query( array( 'post_type' => 'post',
+                                         'posts_per_page' => 1,
+                                         'post_status' => 'publish',
+    ) );
+    if ( $custom_query->have_posts() ) {
+        // echo "<!-- if have_posts -->\n";
+        while ( $custom_query->have_posts() ) {
+            // echo "<!-- while have_posts -->\n";
+            $custom_query->the_post();
+            $post = get_post();
+            /*             echo "<!-- post: ", print_r($post, true), " -->\n"; */
+            // $url = get_permalink($post->ID);
+            $url = get_permalink();
+            $title = get_the_title($post->ID);
+            // echo "<!-- url: $url -->\n";
+            $content =  wp_seo_get_description($post);
+            // echo "<!-- content: $content -->\n";
+            $keys = wp_seo_get_keywords($post);
+            echo "<!-- keys: $keys -->\n";
+            
+            $image = false;
+            if ( get_attached_media('image') ) {
+                $image = array_shift(get_attached_media('image'));
+                $image = $image->ID;
+            }
+            if (! $image) {
+                $image = get_post_thumbnail_id();
+            }
+            if ( $image ) {
+                $full =  wp_get_attachment_image_src($image,'full');
+                return [$full, $url, $title, $content, $keys];
+            }
+        }
+    }
+    wp_reset_postdata();
+    return [$image, $url, $title, $content, $keys];
+}
+
+/* get_header(); */
+?>
+<!doctype html>
+<html <?php language_attributes(); ?> <?php twentytwentyone_the_html_classes(); ?>>
+<head>
+  <meta charset="<?php bloginfo( 'charset' ); ?>" />
+  <meta name="viewport" content="width=device-width, initial-scale=1" />
+  <?php wp_head(); 
+  [$image_url, $post_url, $post_title, $post_content, $post_keywords] = catch_that_image(); ?>
+  <!-- after wp_head -->
+  <meta name="description" content="<?php echo $post_content ?>">
+  <meta name="keywords" content="<?php echo $post_keywords ?>">
+  <!-- <meta name="robots" content="index,follow"> -->
+  <title><?php echo $post_title ?> // Markus Spring Photography</title>
+  <meta property="og:locale" content="en_GB" />
+  <meta property='og:url' content='<?php echo get_site_url() ?>'>
+  <meta property='og:type' content='article'> 
+  <meta property='og:title' content='<?php echo $post_title ?>'> 
+  <meta property='og:site_name' content='Markus Spring Photography // spring2life'> 
+  <meta property='og:description' content='<?php echo $post_content ?>'>
+  <meta property='og:image' content='<?php echo $image_url[0] ?>'> 
+  <style>
+   /* --------------------------------------------- animated burger menu --- */
+   /* from  https://www.cssscript.com/morphing-side-menu-with-pure-css-css3/ */
+   
+   .menu {
+     position:fixed;
+     /* position: absolute; */
+     top: 0;
+     left: 0;
+     z-index: 1000;
+     height: 70px;
+     width: 70px;
+     overflow: hidden;
+     pointer-events: none;
+     -webkit-user-select: none;
+     -moz-user-select: none;
+     -ms-user-select: none;
+     user-select: none;
+   }
+   
+   .menu * {
+     -webkit-backface-visibility: hidden;
+     backface-visibility: hidden;
+   }
+   
+   #menuTrigger:checked ~ .menu { pointer-events: auto; }
+   
+   #menuTrigger:checked ~ .menu h3 {
+     -webkit-transform: translate3d(0, 0, 0);
+     transform: translate3d(0, 0, 0);
+     -webkit-transition-delay: 0.2s;
+     transition-delay: 0.2s;
+   }
+   
+   #menuTrigger:checked ~ header>.site-branding p {
+     color: green !important;
+     display: flex !important;
+   }
+   
+   .menu ~ header {
+     display: none !important;
+   }
+   
+   #menuTrigger:checked ~ header {
+     display: flex !important;
+   }
+   
+   #menuTrigger:checked ~ #masthead {
+     -webkit-transform: translate3d(0, 0, 0);
+     transform: translate3d(0, 0, 0);
+     -webkit-transition-delay: 0.2s;
+     transition-delay: 0.2s;
+   }
+   
+   
+   .menu .trigger {
+     position: absolute;
+     z-index: 0;
+     top: 10px;
+     left: 10px;
+     height: 56px;
+     width: 56px;
+     border-radius: 100%;
+     cursor: pointer;
+     pointer-events: auto;
+     -webkit-transition: all 0.4s ease-in-out;
+     transition: all 0.4s ease-in-out;
+     -webkit-transition-property: -webkit-transform, box-shadow;
+     transition-property: transform, box-shadow;
+     -webkit-transform: translate3d(0, 0, 0);
+     transform: translate3d(0, 0, 0);
+     box-shadow: 0 0 0 0px #424242;
+   }
+   
+   .menu .trigger:before {
+     content: '';
+     position: absolute;
+     top: 0;
+     left: 0;
+     height: 100%;
+     width: 100%;
+     border-radius: inherit;
+     overflow: hidden;
+     -webkit-transform: translate3d(0, 0, 0);
+     transform: translate3d(0, 0, 0);
+     -webkit-transition: box-shadow 0.2s 0.4s ease-in-out;
+     transition: box-shadow 0.2s 0.4s ease-in-out;
+     box-shadow: 0 0 0 28px #424242 inset, 0 0 0 28px #FF5722 inset;
+   }
+   
+   #menuTrigger:checked ~ .menu .trigger {
+     /* -webkit-transform: translate3d(94px, 0, 0); */
+     /* transform: translate3d(94px, 0, 0); */
+     /* box-shadow: 0 0 0 370px #424242; */
+   }
+   
+   #menuTrigger:checked ~ .menu .trigger:before {
+     -webkit-transition-delay: 0s;
+     transition-delay: 0s;
+     box-shadow: 0 0 0 0 #424242 inset, 0 0 0 28px #FF5722 inset;
+   }
+   
+   #menuTrigger:checked ~ .menu .trigger .line:nth-child(1) {
+     -webkit-transform: translateY(0) translate3d(-50%, -50%, 0);
+     transform: translateY(0) translate3d(-50%, -50%, 0);
+   }
+   
+   #menuTrigger:checked ~ .menu .trigger .line:nth-child(3) {
+     -webkit-transform: translateY(0) translate3d(-50%, -50%, 0);
+     transform: translateY(0) translate3d(-50%, -50%, 0);
+   }
+   
+   .menu .trigger .line {
+     position: absolute;
+     top: 50%;
+     left: 50%;
+     background: white;
+     height: 2px;
+     width: 18.66667px;
+     -webkit-transform: translate3d(-50%, -50%, 0);
+     transform: translate3d(-50%, -50%, 0);
+     -webkit-transition: -webkit-transform 0.4s ease-in-out;
+     transition: transform 0.4s ease-in-out;
+   }
+   
+   .menu .trigger .line:nth-child(1) {
+     -webkit-transform: translateY(-5px) translate3d(-50%, -50%, 0);
+     transform: translateY(-5px) translate3d(-50%, -50%, 0);
+   }
+   
+   .menu .trigger .line:nth-child(3) {
+     -webkit-transform: translateY(5px) translate3d(-50%, -50%, 0);
+     transform: translateY(5px) translate3d(-50%, -50%, 0);
+   }
+   
+   #menuTrigger {
+     position: fixed;
+     top: 0;
+     left: -60px;
+   }
+   /* ----------------------------------------- end animated burger menu --- */
+   
+   /* ------------------------------------------------------ hide footer --- */
+   .site-info {
+     display: none !important;
+   }
+
+   /* -------------------------------------------------- full size image --- */
+   * {
+     margin: 0;
+     padding: 0;
+   }
+   .imgbox {
+     display: grid;
+     height: 100%;
+     /* -webkit-animation: sk-bouncedelay 3s infinite ease-in-out both;
+        animation: sk-bouncedelay 3s infinite ease-in-out both; */
+   }
+   .center-fit {
+     max-width: 100%;
+     max-height: 100vh;
+     /* max-width: 99%;
+        max-height: 99vh; */
+     margin: auto;
+   }
+   @media all and (device-width: 768px) and (device-height: 1024px) {
+     .imgbox {
+       /* height: 100vh;  */
+       height: 100%;
+       display: flex;
+       /* background-color: red; */
+     }
+     .center-fit {
+       position: relative;
+       display:block;
+       /* top: 50%;
+          left: 50%;
+          transform: translate(-50%, -50%); */
+       ;
+     }
+
+  </style>
+  <!-- <link rel="stylesheet" href="/wp-content/themes/twentytwentyone-child-spring2life/titlepage.css.min"> -->
+  <!-- <link rel="stylesheet" href="https://tobiasahlin.com/css/spinkit.css"> -->
+</head>
+
+<body <?php body_class(); ?>>
+    <!-- <div class="cr cr-top cr-right cr-sticky cr-black">#SupportUkraine</div> -->
+    
+<div class="cr cr-top cr-right cr-sticky cr-black">Нет войне!</div>
+    <?php wp_body_open(); ?>
+  <div id="page" class="site" style="height: 100vh; ">
+    <a class="skip-link screen-reader-text" href="#content"><?php esc_html_e( 'Skip to content', 'twentytwentyone' ); ?></a>
+    <?php /* [$image_url, $post_url, $post_title, $post_content, $post_keywords] = catch_that_image(); */
+    get_template_part( 'template-parts/header/titlepage-header' ); ?>
+    <a href='<?php echo $post_url ?>'>
+      <div class="imgbox">
+        <!-- <div class="sk-bounce skauto">
+        <div class="sk-bounce-dot"></div>
+        <div class="sk-bounce-dot"></div>
+        </div> -->
+        <img class="center-fit" src='<?php echo $image_url[0] ?>'>
+      </div>
+    </a>
+  </div>
+  <?php get_footer(); ?>
+</body>
+