<?xml version="1.0" encoding="utf-8" ?><feed xmlns="http://www.w3.org/2005/Atom" xmlns:tt="http://teletype.in/" xmlns:opensearch="http://a9.com/-/spec/opensearch/1.1/"><title>@onthewaytothesun</title><author><name>@onthewaytothesun</name></author><id>https://teletype.in/atom/onthewaytothesun</id><link rel="self" type="application/atom+xml" href="https://teletype.in/atom/onthewaytothesun?offset=0"></link><link rel="alternate" type="text/html" href="https://teletype.in/@onthewaytothesun?utm_source=teletype&amp;utm_medium=feed_atom&amp;utm_campaign=onthewaytothesun"></link><link rel="next" type="application/rss+xml" href="https://teletype.in/atom/onthewaytothesun?offset=10"></link><link rel="search" type="application/opensearchdescription+xml" title="Teletype" href="https://teletype.in/opensearch.xml"></link><updated>2026-05-27T14:33:17.989Z</updated><entry><id>onthewaytothesun:zqCJIYyiN9M</id><link rel="alternate" type="text/html" href="https://teletype.in/@onthewaytothesun/zqCJIYyiN9M?utm_source=teletype&amp;utm_medium=feed_atom&amp;utm_campaign=onthewaytothesun"></link><title>Снежок для Taplink</title><published>2024-11-26T08:40:56.358Z</published><updated>2024-12-18T08:59:23.847Z</updated><summary type="html">Первая версия:</summary><content type="html">
  &lt;p id=&quot;Ty9M&quot;&gt;Первая версия:&lt;/p&gt;
  &lt;p id=&quot;BETU&quot;&gt;Демо: &lt;a href=&quot;https://tap.one-way.dev/p/f0f631/&quot; target=&quot;_blank&quot;&gt;https://tap.one-way.dev/p/f0f631/&lt;/a&gt;&lt;/p&gt;
  &lt;p id=&quot;dP6c&quot;&gt;Код:&lt;/p&gt;
  &lt;pre id=&quot;dYzp&quot;&gt;&amp;lt;script&amp;gt;
/** @license
 * DHTML Snowstorm! JavaScript-based snow for web pages
 * Making it snow on the internets since 2003. You&amp;#x27;re welcome.
 * -----------------------------------------------------------
 * Version 1.44.20131208 (Previous rev: 1.44.20131125)
 * Copyright (c) 2007, Scott Schiller. All rights reserved.
 * Code provided under the BSD License
 * http://schillmania.com/projects/snowstorm/license.txt
 */

/*jslint nomen: true, plusplus: true, sloppy: true, vars: true, white: true */
/*global window, document, navigator, clearInterval, setInterval */

var snowStorm = (function(window, document) {

  // --- common properties ---

  this.autoStart = true;          // Whether the snow should start automatically or not.
  this.excludeMobile = true;      // Snow is likely to be bad news for mobile phones&amp;#x27; CPUs (and batteries.) Enable at your own risk.
  this.flakesMax = 128;           // Limit total amount of snow made (falling + sticking)
  this.flakesMaxActive = 64;      // Limit amount of snow falling at once (less = lower CPU use)
  this.animationInterval = 50;    // Theoretical &amp;quot;miliseconds per frame&amp;quot; measurement. 20 = fast + smooth, but high CPU use. 50 = more conservative, but slower
  this.useGPU = true;             // Enable transform-based hardware acceleration, reduce CPU load.
  this.className = null;          // CSS class name for further customization on snow elements
  this.excludeMobile = true;      // Snow is likely to be bad news for mobile phones&amp;#x27; CPUs (and batteries.) By default, be nice.
  this.flakeBottom = null;        // Integer for Y axis snow limit, 0 or null for &amp;quot;full-screen&amp;quot; snow effect
  this.followMouse = false;        // Snow movement can respond to the user&amp;#x27;s mouse
  this.snowColor = &amp;#x27;#fff&amp;#x27;;        // Don&amp;#x27;t eat (or use?) yellow snow.
  this.snowCharacter = &amp;#x27;&amp;amp;bull;&amp;#x27;;  // &amp;amp;bull; = bullet, &amp;amp;middot; is square on some systems etc.
  this.snowStick = true;          // Whether or not snow should &amp;quot;stick&amp;quot; at the bottom. When off, will never collect.
  this.targetElement = null;      // element which snow will be appended to (null = document.body) - can be an element ID eg. &amp;#x27;myDiv&amp;#x27;, or a DOM node reference
  this.useMeltEffect = true;      // When recycling fallen snow (or rarely, when falling), have it &amp;quot;melt&amp;quot; and fade out if browser supports it
  this.useTwinkleEffect = false;  // Allow snow to randomly &amp;quot;flicker&amp;quot; in and out of view while falling
  this.usePositionFixed = false;  // true = snow does not shift vertically when scrolling. May increase CPU load, disabled by default - if enabled, used only where supported
  this.usePixelPosition = false;  // Whether to use pixel values for snow top/left vs. percentages. Auto-enabled if body is position:relative or targetElement is specified.

  // --- less-used bits ---

  this.freezeOnBlur = true;       // Only snow when the window is in focus (foreground.) Saves CPU.
  this.flakeLeftOffset = 0;       // Left margin/gutter space on edge of container (eg. browser window.) Bump up these values if seeing horizontal scrollbars.
  this.flakeRightOffset = 0;      // Right margin/gutter space on edge of container
  this.flakeWidth = 8;            // Max pixel width reserved for snow element
  this.flakeHeight = 8;           // Max pixel height reserved for snow element
  this.vMaxX = 5;                 // Maximum X velocity range for snow
  this.vMaxY = 4;                 // Maximum Y velocity range for snow
  this.zIndex = 0;                // CSS stacking order applied to each snowflake

  // --- &amp;quot;No user-serviceable parts inside&amp;quot; past this point, yadda yadda ---

  var storm = this,
  features,
  // UA sniffing and backCompat rendering mode checks for fixed position, etc.
  isIE = navigator.userAgent.match(/msie/i),
  isIE6 = navigator.userAgent.match(/msie 6/i),
  isMobile = navigator.userAgent.match(/mobile|opera m(ob|in)/i),
  isBackCompatIE = (isIE &amp;amp;&amp;amp; document.compatMode === &amp;#x27;BackCompat&amp;#x27;),
  noFixed = (isBackCompatIE || isIE6),
  screenX = null, screenX2 = null, screenY = null, scrollY = null, docHeight = null, vRndX = null, vRndY = null,
  windOffset = 1,
  windMultiplier = 2,
  flakeTypes = 6,
  fixedForEverything = false,
  targetElementIsRelative = false,
  opacitySupported = (function(){
    try {
      document.createElement(&amp;#x27;div&amp;#x27;).style.opacity = &amp;#x27;0.5&amp;#x27;;
    } catch(e) {
      return false;
    }
    return true;
  }()),
  didInit = false,
  docFrag = document.createDocumentFragment();

  features = (function() {

    var getAnimationFrame;

    /**
     * hat tip: paul irish
     * http://paulirish.com/2011/requestanimationframe-for-smart-animating/
     * https://gist.github.com/838785
     */

    function timeoutShim(callback) {
      window.setTimeout(callback, 1000/(storm.animationInterval || 20));
    }

    var _animationFrame = (window.requestAnimationFrame ||
        window.webkitRequestAnimationFrame ||
        window.mozRequestAnimationFrame ||
        window.oRequestAnimationFrame ||
        window.msRequestAnimationFrame ||
        timeoutShim);

    // apply to window, avoid &amp;quot;illegal invocation&amp;quot; errors in Chrome
    getAnimationFrame = _animationFrame ? function() {
      return _animationFrame.apply(window, arguments);
    } : null;

    var testDiv;

    testDiv = document.createElement(&amp;#x27;div&amp;#x27;);

    function has(prop) {

      // test for feature support
      var result = testDiv.style[prop];
      return (result !== undefined ? prop : null);

    }

    // note local scope.
    var localFeatures = {

      transform: {
        ie:  has(&amp;#x27;-ms-transform&amp;#x27;),
        moz: has(&amp;#x27;MozTransform&amp;#x27;),
        opera: has(&amp;#x27;OTransform&amp;#x27;),
        webkit: has(&amp;#x27;webkitTransform&amp;#x27;),
        w3: has(&amp;#x27;transform&amp;#x27;),
        prop: null // the normalized property value
      },

      getAnimationFrame: getAnimationFrame

    };

    localFeatures.transform.prop = (
      localFeatures.transform.w3 || 
      localFeatures.transform.moz ||
      localFeatures.transform.webkit ||
      localFeatures.transform.ie ||
      localFeatures.transform.opera
    );

    testDiv = null;

    return localFeatures;

  }());

  this.timer = null;
  this.flakes = [];
  this.disabled = false;
  this.active = false;
  this.meltFrameCount = 20;
  this.meltFrames = [];

  this.setXY = function(o, x, y) {

    if (!o) {
      return false;
    }

    if (storm.usePixelPosition || targetElementIsRelative) {

      o.style.left = (x - storm.flakeWidth) + &amp;#x27;px&amp;#x27;;
      o.style.top = (y - storm.flakeHeight) + &amp;#x27;px&amp;#x27;;

    } else if (noFixed) {

      o.style.right = (100-(x/screenX*100)) + &amp;#x27;%&amp;#x27;;
      // avoid creating vertical scrollbars
      o.style.top = (Math.min(y, docHeight-storm.flakeHeight)) + &amp;#x27;px&amp;#x27;;

    } else {

      if (!storm.flakeBottom) {

        // if not using a fixed bottom coordinate...
        o.style.right = (100-(x/screenX*100)) + &amp;#x27;%&amp;#x27;;
        o.style.bottom = (100-(y/screenY*100)) + &amp;#x27;%&amp;#x27;;

      } else {

        // absolute top.
        o.style.right = (100-(x/screenX*100)) + &amp;#x27;%&amp;#x27;;
        o.style.top = (Math.min(y, docHeight-storm.flakeHeight)) + &amp;#x27;px&amp;#x27;;

      }

    }

  };

  this.events = (function() {

    var old = (!window.addEventListener &amp;amp;&amp;amp; window.attachEvent), slice = Array.prototype.slice,
    evt = {
      add: (old?&amp;#x27;attachEvent&amp;#x27;:&amp;#x27;addEventListener&amp;#x27;),
      remove: (old?&amp;#x27;detachEvent&amp;#x27;:&amp;#x27;removeEventListener&amp;#x27;)
    };

    function getArgs(oArgs) {
      var args = slice.call(oArgs), len = args.length;
      if (old) {
        args[1] = &amp;#x27;on&amp;#x27; + args[1]; // prefix
        if (len &amp;gt; 3) {
          args.pop(); // no capture
        }
      } else if (len === 3) {
        args.push(false);
      }
      return args;
    }

    function apply(args, sType) {
      var element = args.shift(),
          method = [evt[sType]];
      if (old) {
        element[method](args[0], args[1]);
      } else {
        element[method].apply(element, args);
      }
    }

    function addEvent() {
      apply(getArgs(arguments), &amp;#x27;add&amp;#x27;);
    }

    function removeEvent() {
      apply(getArgs(arguments), &amp;#x27;remove&amp;#x27;);
    }

    return {
      add: addEvent,
      remove: removeEvent
    };

  }());

  function rnd(n,min) {
    if (isNaN(min)) {
      min = 0;
    }
    return (Math.random()*n)+min;
  }

  function plusMinus(n) {
    return (parseInt(rnd(2),10)===1?n*-1:n);
  }

  this.randomizeWind = function() {
    var i;
    vRndX = plusMinus(rnd(storm.vMaxX,0.2));
    vRndY = rnd(storm.vMaxY,0.2);
    if (this.flakes) {
      for (i=0; i&amp;lt;this.flakes.length; i++) {
        if (this.flakes[i].active) {
          this.flakes[i].setVelocities();
        }
      }
    }
  };

  this.scrollHandler = function() {
    var i;
    // &amp;quot;attach&amp;quot; snowflakes to bottom of window if no absolute bottom value was given
    scrollY = (storm.flakeBottom ? 0 : parseInt(window.scrollY || document.documentElement.scrollTop || (noFixed ? document.body.scrollTop : 0), 10));
    if (isNaN(scrollY)) {
      scrollY = 0; // Netscape 6 scroll fix
    }
    if (!fixedForEverything &amp;amp;&amp;amp; !storm.flakeBottom &amp;amp;&amp;amp; storm.flakes) {
      for (i=0; i&amp;lt;storm.flakes.length; i++) {
        if (storm.flakes[i].active === 0) {
          storm.flakes[i].stick();
        }
      }
    }
  };

  this.resizeHandler = function() {
    if (window.innerWidth || window.innerHeight) {
      screenX = window.innerWidth - 16 - storm.flakeRightOffset;
      screenY = (storm.flakeBottom || window.innerHeight);
    } else {
      screenX = (document.documentElement.clientWidth || document.body.clientWidth || document.body.scrollWidth) - (!isIE ? 8 : 0) - storm.flakeRightOffset;
      screenY = storm.flakeBottom || document.documentElement.clientHeight || document.body.clientHeight || document.body.scrollHeight;
    }
    docHeight = document.body.offsetHeight;
    screenX2 = parseInt(screenX/2,10);
  };

  this.resizeHandlerAlt = function() {
    screenX = storm.targetElement.offsetWidth - storm.flakeRightOffset;
    screenY = storm.flakeBottom || storm.targetElement.offsetHeight;
    screenX2 = parseInt(screenX/2,10);
    docHeight = document.body.offsetHeight;
  };

  this.freeze = function() {
    // pause animation
    if (!storm.disabled) {
      storm.disabled = 1;
    } else {
      return false;
    }
    storm.timer = null;
  };

  this.resume = function() {
    if (storm.disabled) {
       storm.disabled = 0;
    } else {
      return false;
    }
    storm.timerInit();
  };

  this.toggleSnow = function() {
    if (!storm.flakes.length) {
      // first run
      storm.start();
    } else {
      storm.active = !storm.active;
      if (storm.active) {
        storm.show();
        storm.resume();
      } else {
        storm.stop();
        storm.freeze();
      }
    }
  };

  this.stop = function() {
    var i;
    this.freeze();
    for (i=0; i&amp;lt;this.flakes.length; i++) {
      this.flakes[i].o.style.display = &amp;#x27;none&amp;#x27;;
    }
    storm.events.remove(window,&amp;#x27;scroll&amp;#x27;,storm.scrollHandler);
    storm.events.remove(window,&amp;#x27;resize&amp;#x27;,storm.resizeHandler);
    if (storm.freezeOnBlur) {
      if (isIE) {
        storm.events.remove(document,&amp;#x27;focusout&amp;#x27;,storm.freeze);
        storm.events.remove(document,&amp;#x27;focusin&amp;#x27;,storm.resume);
      } else {
        storm.events.remove(window,&amp;#x27;blur&amp;#x27;,storm.freeze);
        storm.events.remove(window,&amp;#x27;focus&amp;#x27;,storm.resume);
      }
    }
  };

  this.show = function() {
    var i;
    for (i=0; i&amp;lt;this.flakes.length; i++) {
      this.flakes[i].o.style.display = &amp;#x27;block&amp;#x27;;
    }
  };

  this.SnowFlake = function(type,x,y) {
    var s = this;
    this.type = type;
    this.x = x||parseInt(rnd(screenX-20),10);
    this.y = (!isNaN(y)?y:-rnd(screenY)-12);
    this.vX = null;
    this.vY = null;
    this.vAmpTypes = [1,1.2,1.4,1.6,1.8]; // &amp;quot;amplification&amp;quot; for vX/vY (based on flake size/type)
    this.vAmp = this.vAmpTypes[this.type] || 1;
    this.melting = false;
    this.meltFrameCount = storm.meltFrameCount;
    this.meltFrames = storm.meltFrames;
    this.meltFrame = 0;
    this.twinkleFrame = 0;
    this.active = 1;
    this.fontSize = (10+(this.type/5)*10);
    this.o = document.createElement(&amp;#x27;div&amp;#x27;);
    this.o.innerHTML = storm.snowCharacter;
    if (storm.className) {
      this.o.setAttribute(&amp;#x27;class&amp;#x27;, storm.className);
    }
    this.o.style.color = storm.snowColor;
    this.o.style.position = (fixedForEverything?&amp;#x27;fixed&amp;#x27;:&amp;#x27;absolute&amp;#x27;);
    if (storm.useGPU &amp;amp;&amp;amp; features.transform.prop) {
      // GPU-accelerated snow.
      this.o.style[features.transform.prop] = &amp;#x27;translate3d(0px, 0px, 0px)&amp;#x27;;
    }
    this.o.style.width = storm.flakeWidth+&amp;#x27;px&amp;#x27;;
    this.o.style.height = storm.flakeHeight+&amp;#x27;px&amp;#x27;;
    this.o.style.fontFamily = &amp;#x27;arial,verdana&amp;#x27;;
    this.o.style.cursor = &amp;#x27;default&amp;#x27;;
    this.o.style.overflow = &amp;#x27;hidden&amp;#x27;;
    this.o.style.fontWeight = &amp;#x27;normal&amp;#x27;;
    this.o.style.zIndex = storm.zIndex;
    docFrag.appendChild(this.o);

    this.refresh = function() {
      if (isNaN(s.x) || isNaN(s.y)) {
        // safety check
        return false;
      }
      storm.setXY(s.o, s.x, s.y);
    };

    this.stick = function() {
      if (noFixed || (storm.targetElement !== document.documentElement &amp;amp;&amp;amp; storm.targetElement !== document.body)) {
        s.o.style.top = (screenY+scrollY-storm.flakeHeight)+&amp;#x27;px&amp;#x27;;
      } else if (storm.flakeBottom) {
        s.o.style.top = storm.flakeBottom+&amp;#x27;px&amp;#x27;;
      } else {
        s.o.style.display = &amp;#x27;none&amp;#x27;;
        s.o.style.bottom = &amp;#x27;0%&amp;#x27;;
        s.o.style.position = &amp;#x27;fixed&amp;#x27;;
        s.o.style.display = &amp;#x27;block&amp;#x27;;
      }
    };

    this.vCheck = function() {
      if (s.vX&amp;gt;=0 &amp;amp;&amp;amp; s.vX&amp;lt;0.2) {
        s.vX = 0.2;
      } else if (s.vX&amp;lt;0 &amp;amp;&amp;amp; s.vX&amp;gt;-0.2) {
        s.vX = -0.2;
      }
      if (s.vY&amp;gt;=0 &amp;amp;&amp;amp; s.vY&amp;lt;0.2) {
        s.vY = 0.2;
      }
    };

    this.move = function() {
      var vX = s.vX*windOffset, yDiff;
      s.x += vX;
      s.y += (s.vY*s.vAmp);
      if (s.x &amp;gt;= screenX || screenX-s.x &amp;lt; storm.flakeWidth) { // X-axis scroll check
        s.x = 0;
      } else if (vX &amp;lt; 0 &amp;amp;&amp;amp; s.x-storm.flakeLeftOffset &amp;lt; -storm.flakeWidth) {
        s.x = screenX-storm.flakeWidth-1; // flakeWidth;
      }
      s.refresh();
      yDiff = screenY+scrollY-s.y+storm.flakeHeight;
      if (yDiff&amp;lt;storm.flakeHeight) {
        s.active = 0;
        if (storm.snowStick) {
          s.stick();
        } else {
          s.recycle();
        }
      } else {
        if (storm.useMeltEffect &amp;amp;&amp;amp; s.active &amp;amp;&amp;amp; s.type &amp;lt; 3 &amp;amp;&amp;amp; !s.melting &amp;amp;&amp;amp; Math.random()&amp;gt;0.998) {
          // ~1/1000 chance of melting mid-air, with each frame
          s.melting = true;
          s.melt();
          // only incrementally melt one frame
          // s.melting = false;
        }
        if (storm.useTwinkleEffect) {
          if (s.twinkleFrame &amp;lt; 0) {
            if (Math.random() &amp;gt; 0.97) {
              s.twinkleFrame = parseInt(Math.random() * 8, 10);
            }
          } else {
            s.twinkleFrame--;
            if (!opacitySupported) {
              s.o.style.visibility = (s.twinkleFrame &amp;amp;&amp;amp; s.twinkleFrame % 2 === 0 ? &amp;#x27;hidden&amp;#x27; : &amp;#x27;visible&amp;#x27;);
            } else {
              s.o.style.opacity = (s.twinkleFrame &amp;amp;&amp;amp; s.twinkleFrame % 2 === 0 ? 0 : 1);
            }
          }
        }
      }
    };

    this.animate = function() {
      // main animation loop
      // move, check status, die etc.
      s.move();
    };

    this.setVelocities = function() {
      s.vX = vRndX+rnd(storm.vMaxX*0.12,0.1);
      s.vY = vRndY+rnd(storm.vMaxY*0.12,0.1);
    };

    this.setOpacity = function(o,opacity) {
      if (!opacitySupported) {
        return false;
      }
      o.style.opacity = opacity;
    };

    this.melt = function() {
      if (!storm.useMeltEffect || !s.melting) {
        s.recycle();
      } else {
        if (s.meltFrame &amp;lt; s.meltFrameCount) {
          s.setOpacity(s.o,s.meltFrames[s.meltFrame]);
          s.o.style.fontSize = s.fontSize-(s.fontSize*(s.meltFrame/s.meltFrameCount))+&amp;#x27;px&amp;#x27;;
          s.o.style.lineHeight = storm.flakeHeight+2+(storm.flakeHeight*0.75*(s.meltFrame/s.meltFrameCount))+&amp;#x27;px&amp;#x27;;
          s.meltFrame++;
        } else {
          s.recycle();
        }
      }
    };

    this.recycle = function() {
      s.o.style.display = &amp;#x27;none&amp;#x27;;
      s.o.style.position = (fixedForEverything?&amp;#x27;fixed&amp;#x27;:&amp;#x27;absolute&amp;#x27;);
      s.o.style.bottom = &amp;#x27;auto&amp;#x27;;
      s.setVelocities();
      s.vCheck();
      s.meltFrame = 0;
      s.melting = false;
      s.setOpacity(s.o,1);
      s.o.style.padding = &amp;#x27;0px&amp;#x27;;
      s.o.style.margin = &amp;#x27;0px&amp;#x27;;
      s.o.style.fontSize = s.fontSize+&amp;#x27;px&amp;#x27;;
      s.o.style.lineHeight = (storm.flakeHeight+2)+&amp;#x27;px&amp;#x27;;
      s.o.style.textAlign = &amp;#x27;center&amp;#x27;;
      s.o.style.verticalAlign = &amp;#x27;baseline&amp;#x27;;
      s.x = parseInt(rnd(screenX-storm.flakeWidth-20),10);
      s.y = parseInt(rnd(screenY)*-1,10)-storm.flakeHeight;
      s.refresh();
      s.o.style.display = &amp;#x27;block&amp;#x27;;
      s.active = 1;
    };

    this.recycle(); // set up x/y coords etc.
    this.refresh();

  };

  this.snow = function() {
    var active = 0, flake = null, i, j;
    for (i=0, j=storm.flakes.length; i&amp;lt;j; i++) {
      if (storm.flakes[i].active === 1) {
        storm.flakes[i].move();
        active++;
      }
      if (storm.flakes[i].melting) {
        storm.flakes[i].melt();
      }
    }
    if (active&amp;lt;storm.flakesMaxActive) {
      flake = storm.flakes[parseInt(rnd(storm.flakes.length),10)];
      if (flake.active === 0) {
        flake.melting = true;
      }
    }
    if (storm.timer) {
      features.getAnimationFrame(storm.snow);
    }
  };

  this.mouseMove = function(e) {
    if (!storm.followMouse) {
      return true;
    }
    var x = parseInt(e.clientX,10);
    if (x&amp;lt;screenX2) {
      windOffset = -windMultiplier+(x/screenX2*windMultiplier);
    } else {
      x -= screenX2;
      windOffset = (x/screenX2)*windMultiplier;
    }
  };

  this.createSnow = function(limit,allowInactive) {
    var i;
    for (i=0; i&amp;lt;limit; i++) {
      storm.flakes[storm.flakes.length] = new storm.SnowFlake(parseInt(rnd(flakeTypes),10));
      if (allowInactive || i&amp;gt;storm.flakesMaxActive) {
        storm.flakes[storm.flakes.length-1].active = -1;
      }
    }
    storm.targetElement.appendChild(docFrag);
  };

  this.timerInit = function() {
    storm.timer = true;
    storm.snow();
  };

  this.init = function() {
    var i;
    for (i=0; i&amp;lt;storm.meltFrameCount; i++) {
      storm.meltFrames.push(1-(i/storm.meltFrameCount));
    }
    storm.randomizeWind();
    storm.createSnow(storm.flakesMax); // create initial batch
    storm.events.add(window,&amp;#x27;resize&amp;#x27;,storm.resizeHandler);
    storm.events.add(window,&amp;#x27;scroll&amp;#x27;,storm.scrollHandler);
    if (storm.freezeOnBlur) {
      if (isIE) {
        storm.events.add(document,&amp;#x27;focusout&amp;#x27;,storm.freeze);
        storm.events.add(document,&amp;#x27;focusin&amp;#x27;,storm.resume);
      } else {
        storm.events.add(window,&amp;#x27;blur&amp;#x27;,storm.freeze);
        storm.events.add(window,&amp;#x27;focus&amp;#x27;,storm.resume);
      }
    }
    storm.resizeHandler();
    storm.scrollHandler();
    if (storm.followMouse) {
      storm.events.add(isIE?document:window,&amp;#x27;mousemove&amp;#x27;,storm.mouseMove);
    }
    storm.animationInterval = Math.max(20,storm.animationInterval);
    storm.timerInit();
  };

  this.start = function(bFromOnLoad) {
    if (!didInit) {
      didInit = true;
    } else if (bFromOnLoad) {
      // already loaded and running
      return true;
    }
    if (typeof storm.targetElement === &amp;#x27;string&amp;#x27;) {
      var targetID = storm.targetElement;
      storm.targetElement = document.getElementById(targetID);
      if (!storm.targetElement) {
        throw new Error(&amp;#x27;Snowstorm: Unable to get targetElement &amp;quot;&amp;#x27;+targetID+&amp;#x27;&amp;quot;&amp;#x27;);
      }
    }
    if (!storm.targetElement) {
      storm.targetElement = (document.body || document.documentElement);
    }
    if (storm.targetElement !== document.documentElement &amp;amp;&amp;amp; storm.targetElement !== document.body) {
      // re-map handler to get element instead of screen dimensions
      storm.resizeHandler = storm.resizeHandlerAlt;
      //and force-enable pixel positioning
      storm.usePixelPosition = true;
    }
    storm.resizeHandler(); // get bounding box elements
    storm.usePositionFixed = (storm.usePositionFixed &amp;amp;&amp;amp; !noFixed &amp;amp;&amp;amp; !storm.flakeBottom); // whether or not position:fixed is to be used
    if (window.getComputedStyle) {
      // attempt to determine if body or user-specified snow parent element is relatlively-positioned.
      try {
        targetElementIsRelative = (window.getComputedStyle(storm.targetElement, null).getPropertyValue(&amp;#x27;position&amp;#x27;) === &amp;#x27;relative&amp;#x27;);
      } catch(e) {
        // oh well
        targetElementIsRelative = false;
      }
    }
    fixedForEverything = storm.usePositionFixed;
    if (screenX &amp;amp;&amp;amp; screenY &amp;amp;&amp;amp; !storm.disabled) {
      storm.init();
      storm.active = true;
    }
  };

  function doDelayedStart() {
    window.setTimeout(function() {
      storm.start(true);
    }, 20);
    // event cleanup
    storm.events.remove(isIE?document:window,&amp;#x27;mousemove&amp;#x27;,doDelayedStart);
  }

  function doStart() {
    if (!storm.excludeMobile || !isMobile) {
      doDelayedStart();
    }
    // event cleanup
    storm.events.remove(window, &amp;#x27;load&amp;#x27;, doStart);
  }

  // hooks for starting the snow
  if (storm.autoStart) {
    storm.events.add(window, &amp;#x27;load&amp;#x27;, doStart, false);
  }

  return this;

}(window, document));

&amp;lt;/script&amp;gt;&lt;/pre&gt;
  &lt;p id=&quot;9xBH&quot;&gt;Вторая версия:&lt;/p&gt;
  &lt;p id=&quot;OA5T&quot;&gt;Демо: &lt;a href=&quot;https://tap.one-way.dev/p/f0f613/&quot; target=&quot;_blank&quot;&gt;https://tap.one-way.dev/p/f0f613/&lt;/a&gt;&lt;/p&gt;
  &lt;p id=&quot;hBbC&quot;&gt;Код:&lt;/p&gt;
  &lt;pre id=&quot;MCoX&quot;&gt;&amp;lt;link rel=&amp;quot;stylesheet&amp;quot; href=&amp;quot;https://school.one-way.dev/chtm/tgproxy/xmas/puresnow.css&amp;quot;&amp;gt;
&amp;lt;script src=&amp;quot;https://school.one-way.dev/chtm/tgproxy/xmas/puresnow.js?v1&amp;quot; defer&amp;gt;&amp;lt;/script&amp;gt;
&amp;lt;style&amp;gt;
  #snow {    position: relative;
    z-index: 100;
    pointer-events: none;}
&amp;lt;/style&amp;gt;&lt;/pre&gt;
  &lt;p id=&quot;RdNk&quot;&gt;Если нужно, чтобы во втором коде снежинки не перекрывали собой блоки, нужно вместо 100 в z-index кода сделать цифру меньше&lt;/p&gt;

</content></entry><entry><id>onthewaytothesun:fM99JAz8HrB</id><link rel="alternate" type="text/html" href="https://teletype.in/@onthewaytothesun/fM99JAz8HrB?utm_source=teletype&amp;utm_medium=feed_atom&amp;utm_campaign=onthewaytothesun"></link><title>Как сделать страницу с редиректом в taplink</title><published>2024-11-24T17:07:36.520Z</published><updated>2024-11-25T05:37:36.281Z</updated><summary type="html">Важно: владельцы taplink не одобряют создание JavaScript-редиректов, их использование может привести к проблемам с аккаунтом</summary><content type="html">
  &lt;p id=&quot;bkAu&quot;&gt;Важно: владельцы taplink не одобряют создание JavaScript-редиректов, их использование может привести к проблемам с аккаунтом&lt;/p&gt;
  &lt;h2 id=&quot;Y0kv&quot;&gt;Делаем свой код редиректа&lt;/h2&gt;
  &lt;p id=&quot;ucjQ&quot;&gt;Для редиректа необходимо взять за основу подобный код:&lt;/p&gt;
  &lt;pre id=&quot;ZNzu&quot;&gt;document.addEventListener(&amp;quot;DOMContentLoaded&amp;quot;, function(){
window.location.href=&amp;quot;https://google.com&amp;quot;
})&lt;/pre&gt;
  &lt;p id=&quot;EPeC&quot;&gt;И поменять ссылку вместо google.com на свою&lt;/p&gt;
  &lt;h2 id=&quot;DiCA&quot;&gt;Шифруем код от Taplink&lt;/h2&gt;
  &lt;p id=&quot;ZLda&quot;&gt;После этого необходимо обфусцировать код, чтобы taplink его не расшифровал и не удалил редирект. &lt;/p&gt;
  &lt;p id=&quot;3Yh8&quot;&gt;Переходим на сайт обфускатора и вставляем код&lt;/p&gt;
  &lt;figure id=&quot;5LUD&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img4.teletype.in/files/fe/e3/fee3ff41-2312-4de0-8cd4-3e8346e53ad5.png&quot; width=&quot;2336&quot; /&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;vibI&quot;&gt;Нажимает Obfuscate. В чекбоксе &amp;quot;Compact&amp;quot; нужно не ставить галочку, иначе код некрасиво перестроится в одну строчку&lt;/p&gt;
  &lt;figure id=&quot;ti5K&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img4.teletype.in/files/fe/13/fe1329e5-2f71-4c38-9837-29ff34d48930.png&quot; width=&quot;2336&quot; /&gt;
  &lt;/figure&gt;
  &lt;h2 id=&quot;j46J&quot;&gt;Вставка в Taplink&lt;/h2&gt;
  &lt;p id=&quot;abjf&quot;&gt;В Taplink добавляем HTML-блок на странице и вставляем туда обфусцированный код, обособив его тегами &amp;lt;script&amp;gt;&lt;/p&gt;
  &lt;pre id=&quot;TInN&quot;&gt;&amp;lt;script&amp;gt;
*тут обфусцированный код*
&amp;lt;/script&amp;gt;&lt;/pre&gt;
  &lt;figure id=&quot;XCg7&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img1.teletype.in/files/c9/4e/c94e60cc-a26a-4aac-96c5-6ccc551e7b61.png&quot; width=&quot;1606&quot; /&gt;
  &lt;/figure&gt;

</content></entry><entry><id>onthewaytothesun:cwlL_NL7WTm</id><link rel="alternate" type="text/html" href="https://teletype.in/@onthewaytothesun/cwlL_NL7WTm?utm_source=teletype&amp;utm_medium=feed_atom&amp;utm_campaign=onthewaytothesun"></link><title>Как с помощью бесплатного сервера рассчитать учеников по порядку</title><published>2024-09-02T18:36:39.130Z</published><updated>2024-09-02T18:36:39.130Z</updated><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://img4.teletype.in/files/bd/24/bd24cc07-ff53-490e-8bb3-0a2550363a6c.png"></media:thumbnail><summary type="html">&lt;img src=&quot;https://img4.teletype.in/files/b5/48/b5483aae-5996-4fcd-be55-4560af90c3bc.png&quot;&gt;Поднять сервер -&gt; Использовать код</summary><content type="html">
  &lt;section style=&quot;background-color:hsl(hsl(236, 74%, var(--autocolor-background-lightness, 95%)), 85%, 85%);&quot;&gt;
    &lt;p id=&quot;uKNA&quot;&gt;&lt;a href=&quot;/@onthewaytothesun/jD5WaKPNsp7&quot;&gt;Поднять сервер&lt;/a&gt; -&amp;gt; Использовать код&lt;/p&gt;
  &lt;/section&gt;
  &lt;p id=&quot;y8Zq&quot;&gt;Этот способ применялся на практике следующим образом: ученикам выдали некие номера от 1 до числа участников, а потом через рандомайзер в прямом эфире выбрали номер победителя. Возможно, вы найдете ему и другое применение, однако как минимум для таких розыгрышей он неплохо подойдет&lt;/p&gt;
  &lt;p id=&quot;YlwG&quot;&gt;1. Создайте таблицу и сервер в App Script &lt;a href=&quot;/@onthewaytothesun/jD5WaKPNsp7&quot;&gt;по инструкции по поднятию&lt;/a&gt; сервера. Остановитесь на пункте 3, где мы могли вставить код:&lt;/p&gt;
  &lt;figure id=&quot;Oc1T&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img4.teletype.in/files/b5/48/b5483aae-5996-4fcd-be55-4560af90c3bc.png&quot; width=&quot;1904&quot; /&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;gscf&quot;&gt;2. Вставьте код:&lt;/p&gt;
  &lt;pre id=&quot;pz2a&quot;&gt;function doGet(e) {
  // Открываем активную таблицу и выбираем активный лист
  var sheet = SpreadsheetApp.getActiveSpreadsheet().getActiveSheet();
  
  // Получаем количество строк (для определения автоинкремента)
  var lastRow = sheet.getLastRow();
  
  // Определяем новое значение автоинкремента
  var newId = lastRow &amp;gt; 0 ? sheet.getRange(lastRow, 1).getValue() + 1 : 1;
  
  // Получаем текущую дату
  var currentDate = new Date();
  
  // Получаем userID из GET-параметра
  var userID = e.parameter.userID || &amp;quot;No ID provided&amp;quot;;
  
  // Добавляем новую строку
  sheet.appendRow([newId, currentDate, userID]);
  
  // Возвращаем значение автоинкремента
  return ContentService.createTextOutput(newId.toString());
}
&lt;/pre&gt;
  &lt;p id=&quot;nkuu&quot;&gt;3. &lt;a href=&quot;/@onthewaytothesun/jD5WaKPNsp7&quot;&gt;Разверните проект по инструкции&lt;/a&gt; с этим кодом. Если у вас уже был развернут проект по инструкции, вы можете переразвернуть его с имеющимся кодом. Для этого нажмите &amp;quot;управление развертываниями&amp;quot;&lt;/p&gt;
  &lt;figure id=&quot;xyPG&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img2.teletype.in/files/58/62/58620a93-6ec2-4663-ab1b-2f26a897ee71.png&quot; width=&quot;3808&quot; /&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;1H7e&quot;&gt;... затем &amp;quot;редактировать&amp;quot;&lt;/p&gt;
  &lt;figure id=&quot;pJLA&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img2.teletype.in/files/5a/27/5a279407-e81e-4368-a797-0ae46ebed084.png&quot; width=&quot;1904&quot; /&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;6NK8&quot;&gt;и &amp;quot;новая версия&amp;quot;. Когда выберите новую&lt;/p&gt;
  &lt;figure id=&quot;wMU8&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img4.teletype.in/files/fe/d1/fed16bc9-dcfc-4cce-907f-3eac02d10b1f.png&quot; width=&quot;3808&quot; /&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;AI1x&quot;&gt;4. Копируйте ссылку под надписью &amp;quot;Веб-приложение&amp;quot;&lt;/p&gt;
  &lt;figure id=&quot;exmD&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img3.teletype.in/files/ec/9a/ec9aed4c-5498-47c4-8d24-96852fba813c.png&quot; /&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;Pgi0&quot;&gt;Теперь допишите к этой ссылке гет-параметр с переменной геткурса, чтобы можно было передавать пользовательский айди. Если процесс по заказу, то выглядеть будет так:&lt;/p&gt;
  &lt;p id=&quot;wntl&quot;&gt;&lt;a href=&quot;https://script.google.com/macros/s/AKfycbxMfqQPK4dHB0zUOYnHI8Csst29y-ehTyVYID3YIUcnmoB6BT2JUzicQLua_pqxAuG3/exec?userID=&quot; target=&quot;_blank&quot;&gt;https://script.google.com/macros/s/AKfycbxMfqQPK4dHB0zUOYnHI8Csst29y-ehTyVYID3YIUcnmoB6BT2JUzicQLua_pqxAuG3/exec?userID=&lt;/a&gt;{object.user.uid}&lt;/p&gt;
  &lt;p id=&quot;WvhY&quot;&gt;Если процесс по пользователю, то получится что-то типа такого:&lt;/p&gt;
  &lt;p id=&quot;uSUo&quot;&gt;&lt;a href=&quot;https://script.google.com/macros/s/AKfycbxMfqQPK4dHB0zUOYnHI8Csst29y-ehTyVYID3YIUcnmoB6BT2JUzicQLua_pqxAuG3/exec?userID=&quot; target=&quot;_blank&quot;&gt;https://script.google.com/macros/s/AKfycbxMfqQPK4dHB0zUOYnHI8Csst29y-ehTyVYID3YIUcnmoB6BT2JUzicQLua_pqxAuG3/exec?userID=&lt;/a&gt;{object.uid}&lt;/p&gt;
  &lt;p id=&quot;0pp8&quot;&gt;5. В процессе не забудьте выбрать опцию &amp;quot;сохранить ответ в допполе&amp;quot;&lt;/p&gt;
  &lt;figure id=&quot;0fJV&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img3.teletype.in/files/e5/2f/e52fd490-2623-445f-b91f-eb6bbb197ec3.png&quot; width=&quot;660&quot; /&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;kerQ&quot;&gt;Протестируйте процесс, поставив галочку &amp;quot;выполнять по-настоящему&amp;quot;&lt;/p&gt;
  &lt;figure id=&quot;KJtU&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img4.teletype.in/files/3f/53/3f53e817-b66a-45d4-b5c1-edf7e194e6eb.png&quot; width=&quot;521&quot; /&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;73eC&quot;&gt;В табличке появится новая запись с датой. После тестирования удалите заполненные строки, и тогда отсчет вновь пойдет с единицы&lt;/p&gt;

</content></entry><entry><id>onthewaytothesun:eqhhv-RoDUG</id><link rel="alternate" type="text/html" href="https://teletype.in/@onthewaytothesun/eqhhv-RoDUG?utm_source=teletype&amp;utm_medium=feed_atom&amp;utm_campaign=onthewaytothesun"></link><title>Кнопка &quot;Поделиться&quot; для месседжеров в Taplink</title><published>2024-07-03T10:13:39.807Z</published><updated>2024-07-03T10:19:44.020Z</updated><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://img4.teletype.in/files/bc/b8/bcb8e5ef-6b1a-4131-8a26-47c32f4049e6.png"></media:thumbnail><summary type="html">&lt;img src=&quot;https://img2.teletype.in/files/9a/08/9a084241-83da-4253-b452-5853d9559005.jpeg&quot;&gt;Этот код дает пользователям мобильных телефонов возможность делиться ссылкой на страницу</summary><content type="html">
  &lt;p id=&quot;aQoF&quot;&gt;Этот код дает пользователям мобильных телефонов возможность делиться ссылкой на страницу&lt;/p&gt;
  &lt;figure id=&quot;LVaw&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img2.teletype.in/files/9a/08/9a084241-83da-4253-b452-5853d9559005.jpeg&quot; width=&quot;591&quot; /&gt;
    &lt;figcaption&gt;Функция &amp;quot;поделиться&amp;quot;&lt;/figcaption&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;86QC&quot;&gt;Пример работы: &lt;a href=&quot;https://tap.one-way.dev/p/e5eea1/&quot; target=&quot;_blank&quot;&gt;https://tap.one-way.dev/p/e5eea1/&lt;/a&gt;&lt;/p&gt;
  &lt;p id=&quot;iqfU&quot;&gt;&lt;/p&gt;
  &lt;p id=&quot;HnS4&quot;&gt;&lt;strong&gt;Добавьте общий скрипт в блок &amp;quot;HTML-код&amp;quot;&lt;/strong&gt;&lt;/p&gt;
  &lt;pre id=&quot;V1lZ&quot;&gt;&amp;lt;script&amp;gt;
window.sharePage = async () =&amp;gt; {
    if (navigator.share) {
        try {
            const url = window.location.href;
            await navigator.share({
                title: &amp;#x27;Поделиться ссылкой&amp;#x27;,
                url: url
            });
        } catch (error) {
            alert(&amp;#x27;Не удалось поделиться страницей: &amp;#x27; + error);
        }
    }
};
document.addEventListener(&amp;#x27;DOMContentLoaded&amp;#x27;, () =&amp;gt; {
    // Проверяем, поддерживается ли Web Share API
    if (!navigator.share) {
        // Если не поддерживается, получаем все ссылки
        const links = document.querySelectorAll(&amp;#x27;a[href*=&amp;quot;javascript:window.sharePage()&amp;quot;]&amp;#x27;);

        // Проходим по каждой ссылке и устанавливаем ей display: none
        links.forEach(link =&amp;gt; {
            link.closest(&amp;#x27;.block-item&amp;#x27;).style.display = &amp;#x27;none&amp;#x27;;
        });
    }
});

&amp;lt;/script&amp;gt;&lt;/pre&gt;
  &lt;p id=&quot;hrXP&quot;&gt;При желании можете заменить текст &amp;quot;Поделиться ссылкой&amp;quot; на любой свой текст&lt;/p&gt;
  &lt;p id=&quot;Edlt&quot;&gt;&lt;/p&gt;
  &lt;p id=&quot;URPI&quot;&gt;&lt;strong&gt;Добавление ссылки&lt;/strong&gt;&lt;/p&gt;
  &lt;p id=&quot;yY6m&quot;&gt;Теперь вы можете добавить специальный код в кнопку в место ссылки, чтобы клик по ней вызывал функцию &amp;quot;поделиться&amp;quot;&lt;/p&gt;
  &lt;figure id=&quot;c2Co&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img4.teletype.in/files/37/37/37370086-69a1-477d-bc91-8767e36d6764.png&quot; width=&quot;3808&quot; /&gt;
    &lt;figcaption&gt;Настройки блока ссылки&lt;/figcaption&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;yCVu&quot;&gt;Код для ссылки:&lt;/p&gt;
  &lt;pre id=&quot;fqrm&quot;&gt;javascript:window.sharePage();&lt;/pre&gt;
  &lt;p id=&quot;7Mec&quot;&gt;&lt;/p&gt;
  &lt;p id=&quot;hMZd&quot;&gt;На устройствах, которые не поддерживают share (например, персональные компьютеры и ноутбуки), кнопки будут скрываться автоматически&lt;/p&gt;
  &lt;section style=&quot;background-color:hsl(hsl(34,  84%, var(--autocolor-background-lightness, 95%)), 85%, 85%);&quot;&gt;
    &lt;p id=&quot;zgLe&quot;&gt;&lt;strong&gt;Важно!&lt;/strong&gt;&lt;/p&gt;
  &lt;/section&gt;
  &lt;p id=&quot;WPHe&quot;&gt;Не забудьте &lt;a href=&quot;https://teletype.in/@onthewaytothesun/Tc3JMxfL0S1&quot; target=&quot;_blank&quot;&gt;настроить SEO-параметры страницы&lt;/a&gt;, чтобы ссылки в месседжерах выглядели красиво&lt;/p&gt;

</content></entry><entry><id>onthewaytothesun:Tc3JMxfL0S1</id><link rel="alternate" type="text/html" href="https://teletype.in/@onthewaytothesun/Tc3JMxfL0S1?utm_source=teletype&amp;utm_medium=feed_atom&amp;utm_campaign=onthewaytothesun"></link><title>SEO-параметры страницы Taplink для месседжеров</title><published>2024-07-03T10:13:21.651Z</published><updated>2024-07-03T10:13:21.651Z</updated><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://img2.teletype.in/files/95/a6/95a61807-5da0-47dd-aaa0-642f3037e056.png"></media:thumbnail><summary type="html">&lt;img src=&quot;https://img2.teletype.in/files/95/b5/95b58c5a-3fe0-4c62-9847-b08ed64e2ee5.png&quot;&gt;Если вы присылаете ссылку на свой Taplink в месседжеры, они добавляют в сообщение специальные элементы, такие как заголовок, описание и картинка. По умолчанию это может быть главный заголовок вашей страницы и аватарка, что может не соответствовать потребностям бизнеса.</summary><content type="html">
  &lt;p id=&quot;fRpv&quot;&gt;Если вы присылаете ссылку на свой Taplink в месседжеры, они добавляют в сообщение специальные элементы, такие как заголовок, описание и картинка. По умолчанию это может быть главный заголовок вашей страницы и аватарка, что может не соответствовать потребностям бизнеса. &lt;/p&gt;
  &lt;p id=&quot;wM8I&quot;&gt;&lt;/p&gt;
  &lt;p id=&quot;31bK&quot;&gt;Вы можете настроить для любой отдельной страницы свои SEO-параметры, чтобы ссылка выглядела так:&lt;/p&gt;
  &lt;figure id=&quot;DTqc&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img2.teletype.in/files/95/b5/95b58c5a-3fe0-4c62-9847-b08ed64e2ee5.png&quot; width=&quot;780&quot; /&gt;
    &lt;figcaption&gt;Ссылка с настроенным заголовком, описанием и картинкой&lt;/figcaption&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;TF4o&quot;&gt;Заголовок, описание и картинка для встраивания обычно имеют префикс OG:, поэтому если где-нибудь на других платформах вы видели &amp;quot;OG:description&amp;quot;, то речь как раз шла об описании для мессенджеров.&lt;/p&gt;
  &lt;p id=&quot;ywsK&quot;&gt;&lt;/p&gt;
  &lt;p id=&quot;DM0v&quot;&gt;Чтобы настроить эти параметры, нажмите кнопку настроек и откройте настройки SEO&lt;/p&gt;
  &lt;figure id=&quot;3lXu&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img1.teletype.in/files/83/7e/837e92b4-6c1f-4502-8415-eb4faa1b10f5.jpeg&quot; width=&quot;1790&quot; /&gt;
    &lt;figcaption&gt;Настройки заголовка и описания&lt;/figcaption&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;j9Rr&quot;&gt;Чтобы настроить OG:image, добавьте блок &amp;quot;аватар&amp;quot;&lt;/p&gt;
  &lt;figure id=&quot;WEgY&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img4.teletype.in/files/b3/b0/b3b09818-400d-4ddb-b478-a1a6b22e1a29.png&quot; width=&quot;3808&quot; /&gt;
    &lt;figcaption&gt;Блок аватар, который настроит вам og:image&lt;/figcaption&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;72Yt&quot;&gt;Теперь вставьте ссылку на свою страницу в &lt;a href=&quot;https://t.me/WebpageBot&quot; target=&quot;_blank&quot;&gt;@WebpageBot&lt;/a&gt; и он обновит кэш на страницу в Telegram, после чего она будет встраиваться красиво. После этого можете скрыть блок с аватаром, чтобы он не мешался&lt;/p&gt;

</content></entry><entry><id>onthewaytothesun:fU_18o3lv5z</id><link rel="alternate" type="text/html" href="https://teletype.in/@onthewaytothesun/fU_18o3lv5z?utm_source=teletype&amp;utm_medium=feed_atom&amp;utm_campaign=onthewaytothesun"></link><title>Как убирать отступы через CSS в Taplink</title><published>2024-04-05T06:53:36.868Z</published><updated>2024-04-05T06:53:36.868Z</updated><summary type="html">Видео:</summary><content type="html">
  &lt;p id=&quot;WH8N&quot;&gt;Видео:&lt;/p&gt;
  &lt;figure id=&quot;DoDg&quot; class=&quot;m_column&quot;&gt;
    &lt;iframe src=&quot;https://www.youtube.com/embed/Da0DxkIxJV0?autoplay=0&amp;loop=0&amp;mute=0&quot;&gt;&lt;/iframe&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;qBfc&quot;&gt;Расширение, в котором я писал код, чтобы он автоматически применился: &lt;a href=&quot;https://chromewebstore.google.com/detail/user-css/okpjlejfhacmgjkmknjhadmkdbcldfcb&quot; target=&quot;_blank&quot;&gt;https://chromewebstore.google.com/detail/user-css/okpjlejfhacmgjkmknjhadmkdbcldfcb&lt;/a&gt;&lt;/p&gt;
  &lt;section style=&quot;background-color:hsl(hsl(236, 74%, var(--autocolor-background-lightness, 95%)), 85%, 85%);&quot;&gt;
    &lt;p id=&quot;IN6j&quot;&gt;После написания кода вы должны вставить его в HTML-блок таплинка, обернув ваш код в теги &amp;lt;style&amp;gt;&amp;lt;/style&amp;gt;&lt;/p&gt;
  &lt;/section&gt;
  &lt;p id=&quot;CyJy&quot;&gt;То есть, если у вас получился код &lt;/p&gt;
  &lt;pre id=&quot;C6Gb&quot;&gt;.b-1488228 {
padding: 0;
}&lt;/pre&gt;
  &lt;p id=&quot;DvEn&quot;&gt;То в таплинковский блок вы должны вставить&lt;/p&gt;
  &lt;pre id=&quot;GKmf&quot;&gt;&amp;lt;style&amp;gt;
.b-1488228 {
padding: 0;
}
&amp;lt;/style&amp;gt;&lt;/pre&gt;

</content></entry><entry><id>onthewaytothesun:pBTXTcrymfe</id><link rel="alternate" type="text/html" href="https://teletype.in/@onthewaytothesun/pBTXTcrymfe?utm_source=teletype&amp;utm_medium=feed_atom&amp;utm_campaign=onthewaytothesun"></link><title>Картинки GetCourse на тренингах</title><published>2024-04-02T13:39:26.919Z</published><updated>2024-04-03T06:29:09.918Z</updated><summary type="html">Если у вас стоял старый код для картинок, вырежьте его и вставьте на его место:</summary><content type="html">
  &lt;p id=&quot;tVPe&quot;&gt;Если у вас стоял старый код для картинок, вырежьте его и вставьте на его место:&lt;/p&gt;
  &lt;pre id=&quot;eseC&quot;&gt;$(&amp;#x27;.stream-table tr&amp;#x27;).each(function(){
let image = $(this).attr(&amp;#x27;data-training-image&amp;#x27;);
let $tr = $(this);
if (image!==undefined &amp;amp;&amp;amp; image !== &amp;#x27;&amp;#x27;) {
$tr.find(&amp;#x27;a&amp;#x27;).prepend(&amp;#x60;&amp;lt;img src=&amp;quot;${image}&amp;quot; /&amp;gt;&amp;#x60;);
}
})&lt;/pre&gt;
  &lt;p id=&quot;EBg9&quot;&gt;Этот код установит картинки на тренинги. Если вы вставляете код не внутрь другого готового кода, оберните код в обработчик ожидания загрузки страницы, чтобы получилось&lt;/p&gt;
  &lt;pre id=&quot;Lc8B&quot;&gt;$(()=&amp;gt;{
$(&amp;#x27;.stream-table tr&amp;#x27;).each(function(){
let image = $(this).attr(&amp;#x27;data-training-image&amp;#x27;);
let $tr = $(this);
if (image!==undefined &amp;amp;&amp;amp; image !== &amp;#x27;&amp;#x27;) {
$tr.find(&amp;#x27;a&amp;#x27;).prepend(&amp;#x60;&amp;lt;img src=&amp;quot;${image}&amp;quot; /&amp;gt;&amp;#x60;);
}
})
})&lt;/pre&gt;
  &lt;p id=&quot;TMHL&quot;&gt;Также вы можете использовать мою вариацию, которая будет также убирать ограничение на размер картинки&lt;/p&gt;
  &lt;pre id=&quot;qzB9&quot;&gt;$(()=&amp;gt;{
function removeThumbnail(string) {
  const aPart = string.match(/\/a\/\d+\/sc\/\d+/);
  const hPart = string.substring(string.indexOf(&amp;#x27;thumbnail&amp;#x27;) + 10, string.indexOf(&amp;#x27;/s/&amp;#x27;));
  return &amp;#x60;/fileservice/file/download${aPart}/${hPart}&amp;#x60;;
}
 $(&amp;#x27;.stream-table tr&amp;#x27;).each(function(){
        let image = $(this).attr(&amp;#x27;data-training-image&amp;#x27;);
        let $tr = $(this)
        if (image!==undefined&amp;amp;&amp;amp;image.includes(&amp;#x27;thumbnail&amp;#x27;)) {
            $tr.find(&amp;#x27;a&amp;#x27;).prepend(&amp;#x60;&amp;lt;img src=&amp;quot;${removeThumbnail(image)}&amp;quot; /&amp;gt;&amp;#x60;)
        }
    })
})&lt;/pre&gt;
  &lt;p id=&quot;QUrb&quot;&gt;В этом случае от вас потребуется оптимизировать все картинки перед загрузкой, поскольку не оптимизированная картинка может ухудшить скорость загрузки, однако вы сможете получить картинки оригинального качества.&lt;/p&gt;
  &lt;p id=&quot;H9Ai&quot;&gt;Спасибо за помощь в составлении кода &lt;a href=&quot;https://t.me/Alexandr_Nagiyan&quot; target=&quot;_blank&quot;&gt;@Alexandr_Nagiyan&lt;/a&gt;&lt;/p&gt;
  &lt;p id=&quot;lVHM&quot;&gt;Оптимизировать картинки следует, например, в сервисе &lt;a href=&quot;https://squoosh.app/&quot; target=&quot;_blank&quot;&gt;https://squoosh.app/&lt;/a&gt;&lt;/p&gt;

</content></entry><entry><id>onthewaytothesun:mMEMMzKu25M</id><link rel="alternate" type="text/html" href="https://teletype.in/@onthewaytothesun/mMEMMzKu25M?utm_source=teletype&amp;utm_medium=feed_atom&amp;utm_campaign=onthewaytothesun"></link><title>Уникальная стилизация секций</title><published>2024-03-27T06:22:32.759Z</published><updated>2024-03-27T06:38:20.559Z</updated><summary type="html">Видеоинструкция:</summary><content type="html">
  &lt;p id=&quot;JDQn&quot;&gt;Видеоинструкция:&lt;/p&gt;
  &lt;figure id=&quot;D5BT&quot; class=&quot;m_column&quot;&gt;
    &lt;iframe src=&quot;https://www.youtube.com/embed/fi0dzYgOd_o?autoplay=0&amp;loop=0&amp;mute=0&quot;&gt;&lt;/iframe&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;P3Sn&quot;&gt;Код для накидывания классов (должен быть внизу):&lt;/p&gt;
  &lt;pre id=&quot;gEna&quot;&gt;&amp;lt;script&amp;gt;
Array.from(document.querySelectorAll(&amp;#x27;.add-class&amp;#x27;)).map((element) =&amp;gt; {
  let classToAdd = element.getAttribute(&amp;#x27;data-class&amp;#x27;);
  element.closest(&amp;#x27;.blocks-section&amp;#x27;).classList.add(classToAdd)
  })
  Array.from(document.querySelectorAll(&amp;#x27;.collapse-text-inner&amp;#x27;)).map((element) =&amp;gt; {
  element.innerHTML = element.textContent
  })
&amp;lt;/script&amp;gt;&lt;/pre&gt;
  &lt;p id=&quot;qh9c&quot;&gt;Блок, который нужно вставлять в секцию для задания уникального класса:&lt;/p&gt;
  &lt;pre id=&quot;eI2p&quot;&gt;&amp;lt;div class=&amp;quot;add-class&amp;quot; data-class=&amp;quot;two-images&amp;quot;&amp;gt;&amp;lt;/div&amp;gt;&lt;/pre&gt;
  &lt;p id=&quot;loEg&quot;&gt;То, что написано в кавычках в data-class — это название вашего будущего уникального идентификатора вашей секции&lt;/p&gt;
  &lt;p id=&quot;rX2w&quot;&gt;&lt;strong&gt;Перед вставкой кодов стилизации убедитесь, что у вас есть теги &amp;lt;style&amp;gt;&lt;/strong&gt;&lt;/p&gt;
  &lt;p id=&quot;P18k&quot;&gt;Например, в уроке я показал код стилизации:&lt;/p&gt;
  &lt;pre id=&quot;k6jY&quot;&gt;.columns-block .section-main&amp;gt;div&amp;gt;div {
  display:grid;
  grid-template-columns:20% 80%;
}


.two-images .section-main&amp;gt;div&amp;gt;div {
  display:grid;
  grid-template-columns:30% 70%;
}&lt;/pre&gt;
  &lt;p id=&quot;E78Q&quot;&gt;Этот код написан на языке разметки CSS. Чтобы он заработал в таплинке, создайте html-блок и вставьте туда код, обособив тегами &amp;lt;style&amp;gt; (обратите внимание на их точное написание). Пример кода ниже, который должен вставляться в HTML-блок. &lt;/p&gt;
  &lt;p id=&quot;ZjW6&quot;&gt;Такой принцип работает со всеми стилями. Если вы хотите копировать CSS-код с фигмы, точно также добавьте эти теги &amp;lt;style&amp;gt;, чтобы браузер понимал, что это код стилизации&lt;/p&gt;
  &lt;pre id=&quot;sPwt&quot;&gt;&amp;lt;style&amp;gt;
.columns-block .section-main&amp;gt;div&amp;gt;div {
  display:grid;
  grid-template-columns:20% 80%;
}


.two-images .section-main&amp;gt;div&amp;gt;div {
  display:grid;
  grid-template-columns:30% 70%;
}
&amp;lt;/style&amp;gt;&lt;/pre&gt;
  &lt;section style=&quot;background-color:hsl(hsl(55,  86%, var(--autocolor-background-lightness, 95%)), 85%, 85%);&quot;&gt;
    &lt;p id=&quot;ZXef&quot;&gt;Бесплатные коды и уроки по Taplink в канале &lt;a href=&quot;https://t.me/taplinkbest&quot; target=&quot;_blank&quot;&gt;https://t.me/taplinkbest&lt;/a&gt; Бесплатная помощь по кодам в чате канала: &lt;a href=&quot;https://t.me/taplinkbestchat&quot; target=&quot;_blank&quot;&gt;https://t.me/taplinkbestchat&lt;/a&gt; (на YouTube и в Teletype не отвечаю).&lt;/p&gt;
  &lt;/section&gt;

</content></entry><entry><id>onthewaytothesun:zPNZgEUiyXU</id><link rel="alternate" type="text/html" href="https://teletype.in/@onthewaytothesun/zPNZgEUiyXU?utm_source=teletype&amp;utm_medium=feed_atom&amp;utm_campaign=onthewaytothesun"></link><title>Разбор нового дизайна страницы оплаты GetCourse</title><published>2024-02-29T08:37:46.269Z</published><updated>2024-02-29T08:40:48.547Z</updated><media:thumbnail xmlns:media="http://search.yahoo.com/mrss/" url="https://img1.teletype.in/files/41/43/414371ab-69c7-4e5e-ac1a-f119618cfcf1.png"></media:thumbnail><summary type="html">&lt;img src=&quot;https://img2.teletype.in/files/d4/59/d4598f9f-5bfe-4b05-afe1-9d3fca847996.png&quot;&gt;Бывало ли в вашей жизни такое, что вы думаете о работниках какой-то профессии, что они что-то не дорабатывают/недоделывают/некомпетентны, но стоит вам погрузиться в эту сферу, как ваше мнение меняется на «так вот оно как оказывается?»</summary><content type="html">
  &lt;h2 id=&quot;smvZ&quot;&gt;Предисловие&lt;/h2&gt;
  &lt;p id=&quot;zuGW&quot;&gt;Бывало ли в вашей жизни такое, что вы думаете о работниках какой-то профессии, что они что-то не дорабатывают/недоделывают/некомпетентны, но стоит вам погрузиться в эту сферу, как ваше мнение меняется на «так вот оно как оказывается?»&lt;/p&gt;
  &lt;p id=&quot;AXDl&quot;&gt;В моем опыте такое было с модераторами форумов. Я, в виду тогда еще юношеского максимализма, «сопротивлялся цензуре», «боролся за правду», но лишь попробовав для себя стать модератором форума увидел, какие у модераторов были рамки возможностей в виду самоуважения, правил начальства и других деталей, которых я не мог увидеть, и с которыми модераторам нужно было уживаться&lt;/p&gt;
  &lt;p id=&quot;bwG7&quot;&gt;Похожая ситуация и с разработками. Мы можем ругать разработчиков за кривой интерфейс, но в реальности они, возможно, работали по четкому тз, проектировщик ui работал по четкому тз, а заказчик, например, тогда имел другое видение платформы и имел ограниченность в средствах, но всячески старался сделать как лучше. Мы можем сетовать на то, что сервера упали, но можем даже не догадываться, что упали они из-за каких-нибудь санкций или пролития уборщицей в серверной супа на компьютеры, а разработчики и владельцы платформы в этом не виноваты. Все выше сказанное не относится конкретно к геткурсу, но суть в том, что ситуации бывают разные и не всегда людям со стороны может быть видна полная картинка для объективной оценки&lt;/p&gt;
  &lt;p id=&quot;nPFG&quot;&gt;GetCourse писался довольно давно, писался под конкретные задачи и сменил кучу подрядчиков. Вполне логично, что он написан на старых библиотеках, в некоторых разделах код писался как будто бы с целью потроллить любого, кто его посмотрит, однако это данность, которая присуща любому быстро растущему проекту.&lt;/p&gt;
  &lt;p id=&quot;melV&quot;&gt;Что куда важнее, так это то, что платформы делают, видя свои слабые стороны. Когда в конструкторе Taplink я пожаловался на обилие ошибок в консоли, разработчики платформы просто сделали правку, которая оборачивает весь пользовательский код в try, чтобы ошибки писались не красным шрифтом в разделе ошибок, а белым нейтральным в логах. У пользователей таплинка, при этом, поломались все скрипты, использующие глобальную область видимости 👍&lt;/p&gt;
  &lt;h2 id=&quot;5u0e&quot;&gt;О новом визуале GC&lt;/h2&gt;
  &lt;p id=&quot;yjnr&quot;&gt;GetCourse, как уже многим известно, уже множество раз анонсировал визуальную переработку геткурса. Первым разделом, который я смог пощупать, стала страница оплаты. &lt;/p&gt;
  &lt;p id=&quot;zbzs&quot;&gt;Важные моменты:&lt;/p&gt;
  &lt;ol id=&quot;baqi&quot;&gt;
    &lt;li id=&quot;Eqdw&quot;&gt;Новое оформление можно будет включать нативно с помощью кнопочек. Никакого кода или конструктора.&lt;/li&gt;
    &lt;li id=&quot;AnqM&quot;&gt;Старый код никак не будет задет. Если у вас стояли интеграции, скрипты для отображения уникального диза или скрипты скрытия\показа оплат по предложениям, им ничего не грозит. Так GetCourse решил проблему обратной совместимости&lt;/li&gt;
    &lt;li id=&quot;G5GL&quot;&gt;Возможности нативной кастомизации будут добавляться&lt;/li&gt;
    &lt;li id=&quot;VhXF&quot;&gt;Геткурс всегда готов идти навстречу адекватным предложениям, сопутствующим интересам платформы. Однако буду откровенен: если ваша идея сможет привести к созданию конкурента геткурсу прямо внутри их продукта, то такое предложение, очевидно, отвергнут.&lt;/li&gt;
  &lt;/ol&gt;
  &lt;figure id=&quot;4e6o&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img2.teletype.in/files/d4/59/d4598f9f-5bfe-4b05-afe1-9d3fca847996.png&quot; width=&quot;3808&quot; /&gt;
    &lt;figcaption&gt;Страница оплаты с новым видом&lt;/figcaption&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;Hm2T&quot;&gt;Ранее GetCourse уже начал реализовывать предложенную мной идею сделать возможность продавать шаблоны оформления как это сделано в некоторых других площадках: там можно купить оформление от разработчика &amp;quot;Вася Пупкин&amp;quot;, установить в школу в один клик и пользоваться новым функционалом и видеть обновленный интерфейс без лишней мороки и связи напрямую со всякими разработчками-фрилансерами\студиями\самоучками-энтузиастами, была введена возможность централизованого включения тем для всего аккаунта или конкретных разделов тренингов.&lt;/p&gt;
  &lt;p id=&quot;DJ2x&quot;&gt;В дальнейшем помимо вида страницы оплаты на скриншоте появятся новые виды, каждый из которых можно выбрать и донастроить. Возможно, что разработчиками некоторых шаблонов будут люди не из команды GetCourse, что позволит создать конкуренцию и заставит разработчиков лучше стараться, чтобы выделиться на фоне других.&lt;/p&gt;
  &lt;h2 id=&quot;MrKb&quot;&gt;Под капотом&lt;/h2&gt;
  &lt;figure id=&quot;SwRg&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img3.teletype.in/files/ef/ab/efabc92a-aa6c-4afc-91cc-53d54328b5d8.png&quot; width=&quot;3808&quot; /&gt;
    &lt;figcaption&gt;Шаблон в редакторе&lt;/figcaption&gt;
  &lt;/figure&gt;
  &lt;figure id=&quot;lyXr&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img4.teletype.in/files/7d/da/7ddac197-3ca9-4e97-be4f-78dc9ce81b63.png&quot; width=&quot;1690&quot; /&gt;
    &lt;figcaption&gt;Дополнительные настройки &lt;/figcaption&gt;
  &lt;/figure&gt;
  &lt;h3 id=&quot;KhcY&quot;&gt;Возможности доработки&lt;/h3&gt;
  &lt;p id=&quot;Hy1T&quot;&gt;Скрипты новой страницы наконец-то написаны в IDE со сборщиком, что не может не радовать. Классы на русском и закомментированные todo тут больше не живут. Таким образом, переопределять виджеты геткурса теперь проблематичнее, однако это и раньше нужно было только для исправления багов в старом коде старой страницы оплаты от прошлого разработчика. &lt;/p&gt;
  &lt;figure id=&quot;pu08&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img1.teletype.in/files/c8/b5/c8b5254e-5df2-41c4-9476-152c26ea64aa.png&quot; /&gt;
    &lt;figcaption&gt;Скриншот js-ки, взятой с обработчика кнопки&lt;/figcaption&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;loKt&quot;&gt;Добавочный js, который не вмешивается в работу самой страницы, ставить никто не помешает&lt;/p&gt;
  &lt;p id=&quot;dQ1q&quot;&gt;По части CSS возможности стилизации стали значительно проще:&lt;/p&gt;
  &lt;figure id=&quot;g2Je&quot; class=&quot;m_column&quot;&gt;
    &lt;img src=&quot;https://img3.teletype.in/files/20/0e/200e37c6-d40f-444c-8756-83e05c41ead9.png&quot; /&gt;
    &lt;figcaption&gt;HTML-структура новой страницы оплаты&lt;/figcaption&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;L3q2&quot;&gt;Благодаря унификации платежных блоков стилизовать страницу оплаты будет проще и быстрее. Если в старой платежной странице были моменты, где код стилизации писался в атрибуты элемента и это приводило к досадным визуальным багам типа лишних отступов, уродливых полосок и картинок, то теперь можно будет натянуть общий шаблон внешнего вида и не дорабатывать страницу оплаты каждый раз, когда в платежный модуль добавили новую платежку&lt;/p&gt;
  &lt;p id=&quot;p0XJ&quot;&gt;&lt;/p&gt;
  &lt;p id=&quot;FMQ9&quot;&gt;&lt;/p&gt;
  &lt;h3 id=&quot;kWka&quot;&gt;Игого&lt;/h3&gt;
  &lt;p id=&quot;ZuP3&quot;&gt;GetCourse, во всяком случае в сфере лично моих интересов, движется по очень правильному пути. Он сможет дать сообществу новый дизайн, не обесценив работу разработчиков и не поломав школы. Если у школы уже был дизайн и структура, на которую школа затратила средства, то с вводом нового вида и функциональности ресурсы этой школы не обесцениваются (они всё также будут иметь свои уникальные функции, просто кто-то среди новых и не оформленных школ бесплатно обновятся).&lt;/p&gt;

</content></entry><entry><id>onthewaytothesun:Ktz6TnnQhde</id><link rel="alternate" type="text/html" href="https://teletype.in/@onthewaytothesun/Ktz6TnnQhde?utm_source=teletype&amp;utm_medium=feed_atom&amp;utm_campaign=onthewaytothesun"></link><title>Движущиеся градиенты за 5 сек в Taplink</title><published>2024-02-07T09:00:09.896Z</published><updated>2024-02-07T09:00:09.896Z</updated><summary type="html">Все коды | Сотрудничество | Чат поддержки</summary><content type="html">
  &lt;section style=&quot;background-color:hsl(hsl(199, 50%, var(--autocolor-background-lightness, 95%)), 85%, 85%);&quot;&gt;
    &lt;p id=&quot;UckB&quot;&gt;&lt;a href=&quot;https://t.me/taplinkbest&quot; target=&quot;_blank&quot;&gt;Все коды&lt;/a&gt; | &lt;a href=&quot;https://t.me/onthewaytothesun&quot; target=&quot;_blank&quot;&gt;Сотрудничество&lt;/a&gt; | &lt;a href=&quot;https://t.me/taplinkbestchat&quot; target=&quot;_blank&quot;&gt;Чат поддержки&lt;/a&gt;&lt;/p&gt;
  &lt;/section&gt;
  &lt;p id=&quot;m7D2&quot;&gt;Пример работы: &lt;a href=&quot;https://tap.one-way.dev/p/da0c0d/&quot; target=&quot;_blank&quot;&gt;https://tap.one-way.dev/p/da0c0d/&lt;/a&gt;&lt;/p&gt;
  &lt;p id=&quot;fpOJ&quot;&gt;Видеоинструкция:&lt;/p&gt;
  &lt;figure id=&quot;zzWw&quot; class=&quot;m_column&quot;&gt;
    &lt;iframe src=&quot;https://www.youtube.com/embed/6VlzwWVGTbI?autoplay=0&amp;loop=0&amp;mute=0&quot;&gt;&lt;/iframe&gt;
  &lt;/figure&gt;
  &lt;p id=&quot;F9wl&quot;&gt;Код в примере:&lt;/p&gt;
  &lt;pre id=&quot;XWx3&quot;&gt;&amp;lt;style&amp;gt;
font[color=&amp;quot;#dee2e6&amp;quot;] {
  animation: shine 5s linear infinite;
 background: linear-gradient(270deg, rgba(5, 204, 231, 0.87) 1.5%, rgba(237, 0, 0, 0.45) 24.65%, #19AF00 49.29%, rgba(237, 0, 0, 0.46) 75.86%, rgba(5, 204, 231, 0.87) 100%);
  background-size: 200% auto;
    background-clip: text;
  text-fill-color: transparent;
  -webkit-background-clip: text;
  -webkit-text-fill-color: transparent;
}

font[color=&amp;quot;#fff4e6&amp;quot;] {
   animation: shine 5s linear infinite;
 background: linear-gradient(270deg, rgba(5, 204, 231, 0.87) 1.5%, rgba(237, 0, 0, 0.45) 24.65%, #19AF00 49.29%, rgba(237, 0, 0, 0.46) 75.86%, rgba(5, 204, 231, 0.87) 100%);
  background-size: 200% auto;
    background-clip: text;
  text-fill-color: transparent;
  -webkit-background-clip: text;
  -webkit-text-fill-color: transparent;
}

@keyframes shine {
    to {
      background-position: 200% center;
    }
  }
&amp;lt;/style&amp;gt;&lt;/pre&gt;

</content></entry></feed>