Адаптивный SVG-текст для переноса динамического содержимого c - PullRequest
2 голосов
/ 17 марта 2020

Я пытаюсь обернуть блок новостей (который будет варьироваться по ширине и высоте) с анимированным SVG-шаблоном вокруг него. Я получил это до сих пор:

	#canvas{
	height: 100vh;
	width: 100vw;
	}
	.svg-container { 
	display: inline-block;
	position: relative;
	width: 100%;
	padding-bottom: 100%; 
	vertical-align: middle; 
	overflow: hidden; 
}
 <div class="svg-container">
    <svg id="canvas" version="1.1"  viewBox="0 0 500 500">  
        <path width="100%"  id="curve" fill="none" d="M0,0 h200 a20,20 0 0 1 20,20 v200 a20,20 0 0 1 -20,20 h-200 a20,20 0 0 1 -20,-20 v-200 a20,20 0 0 1 20,-20 z" />
        <text font-family="Helvetica" font-size="20" fill="black">
            <textPath xlink:href="#curve" startOffset="0%" id="text">Last News</textPath>
        <animate xlink:href="#text" attributeName="startOffset" from="0%" to="100%" begin="0s" dur="10s" repeatCount="indefinite"/>
        </text>
    </svg>
    </div>

рабочая анимация: https://jsfiddle.net/xebfjL1p/

Это будет дочерний контент:

<div class="lastnews">
    <div class="post-grid">

        <a class="post-link" href="#">
        <div class="post">
            <img src="https://via.placeholder.com/768x461.png">
            <h2>Some very long long title with too many words</h2>
        </div>
        </a>

        <a class="post-link" href="#">
        <div class="post">
            <img src="https://via.placeholder.com/768x461.png">
            <h2>Some very long long title with too many words</h2>
        </div>
        </a>

        <a class="post-link" href="#">
        <div class="post">
            <img src="https://via.placeholder.com/768x461.png">
            <h2>Short title</h2>
        </div>
        </a>

        <a class="post-link" href="#">
        <div class="post">
            <img src="https://via.placeholder.com/768x461.png">
            <h2>Some very long long title with too many words</h2>
        </div>
        </a>

        <a class="post-link" href="#">
        <div class="post">
            <img src="https://via.placeholder.com/768x461.png">
            <h2>Some very long long title with too many words</h2>
        </div>
        </a>

        <a class="post-link" href="#">
        <div class="post">
            <img src="https://via.placeholder.com/768x461.png">
            <h2>Some very long long title with too many words</h2>
        </div>
        </a>

        <a class="post-link" href="#">
        <div class="post">
            <img src="https://via.placeholder.com/768x461.png">
            <h2>Some very long long title with too many words</h2>
        </div>
        </a>

        <a class="post-link" href="#">
        <div class="post">
            <img src="https://via.placeholder.com/768x461.png">
            <h2>Some very long long title with too many words</h2>
        </div>
        </a>            

    </div>
</div>

Я нашел несколько способов сделать svg отзывчивым, но возможно ли сделать svg путь адаптируемым к дочернему содержимому div?

вот результат, который я хотел бы получить: enter image description here

заранее спасибо

1 Ответ

2 голосов
/ 17 марта 2020

Вот как я это сделаю: я помещаю div с текстом и svg в одного родителя position:relative. .text-container имеет абсолютную позицию и располагается над элементом svg.

Также ширина .text-container имеет ширину, но height:auto, поскольку содержимое является динамическим c.

. нужен размер .text-container, и вы будете использовать его для вычисления нового viewBox элемента svg и нового значения атрибута d #curve

let txtCont = document.querySelector(".text-container");
// get the size of the text container
let box = txtCont.getBoundingClientRect()

//set the new viewBox of the svg element
canvas.setAttributeNS(null,"viewBox",`-50 -30 310 ${box.height}`)
//set the new d attribute of the curve
curve.setAttributeNS(null,"d", `M0,0 h200 a20,20 0 0 1 20,20 v${box.height  - 100} a20,20 0 0 1 -20,20 h-200 a20,20 0 0 1 -20,-20 v-${box.height - 100} a20,20 0 0 1 20,-20 z`)
#wrap {
  height: auto;
  width: 300px;
  margin: 0;
  padding: 0;
  position: relative;
}
.text-container {
  box-sizing: border-box;
  padding: 30px 50px;
  position: absolute;
  width: 100%;
  height: auto;
  top: 0;
  left: 0;
}
#canvas {
  border: 1px solid;
  margin: 0;
}
<div id="wrap">
    <svg id="canvas"  viewBox="-50 -30 310 310">  
        <path width="100%"  id="curve" fill="none" stroke="gold" d="" />
        <text font-family="Helvetica" font-size="20" fill="black">
            <textPath xlink:href="#curve" startOffset="0%" id="text">Last News</textPath>
        <animate xlink:href="#text" attributeName="startOffset" from="0%" to="100%" begin="0s" dur="10s" repeatCount="indefinite"/>
        </text>
    </svg>

<div class="text-container">
  <p>I'm trying to wrap a block of news (which will vary on width & height) with an animated SVG textpath around it. I got this so far</p>
  </div>
</div>

Пожалуйста, измените текст .text-container, чтобы увидеть изменение анимации.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...