hi. you can use a FormattedString:
txt = FormattedString()
txt.append("hello world", font='Skia', fontSize=150, fontVariations=dict(wdth=0.8, wght=1.3))
B = BezierPath()
B.text(txt, (100, 100))
drawPath(B)
hi. you can use a FormattedString:
txt = FormattedString()
txt.append("hello world", font='Skia', fontSize=150, fontVariations=dict(wdth=0.8, wght=1.3))
B = BezierPath()
B.text(txt, (100, 100))
drawPath(B)
@snaders in DrawBot you don’t really resize an image, you change the scale at which it is drawn. (same logic as in Draw a letter within a viewbox)
imgPath = 'https://i.ytimg.com/vi/oHg5SJYRHA0/hqdefault.jpg'
# get image width & height
imgWidth, imgHeight = imageSize(imgPath)
# define box width & height
boxWidth, boxHeight = 640, 640
# calculate scaling factors
factorHeight = boxHeight / imgHeight
factorWidth = boxWidth / imgWidth
# draw scaled image
with savedState():
scale(factorWidth, factorHeight)
image(imgPath, (0, 0))
# draw box
fill(None)
stroke(1, 0, 0)
strokeWidth(5)
rect(0, 0, boxWidth, boxHeight)
if you know the size of the box, and the size of the letter, you can calculate a scaling factor between the two:
# get lettershape as bezier
B = BezierPath()
B.text('a', (0, 0), fontSize=1000, font='Georgia')
# get lettershape bounding box
left, bottom, right, top = B.bounds()
# calculate lettershape width & height
letterWidth = right - left
letterHeight = top - bottom
# define box width & height
boxWidth, boxHeight = 800, 400
# calculate scaling factors
factorHeight = boxHeight / letterHeight
factorWidth = boxWidth / letterWidth
# draw box
fill(1, 1, 0)
rect(0, 0, boxWidth, boxHeight)
# apply scaling factors
scale(factorWidth, factorHeight)
# shift shape to origin position
translate(-left, -bottom)
# draw scaled lettershape
fill(1, 0, 0)
drawPath(B)
hi. how about this (quick & lazy):
bonus: Turtle
from turtle import *
x, y = 300, 200
sides = 7
side = 100
angleTotal = 360
angleStep = abs(angleTotal / sides)
Screen()
t = Turtle()
for i in range(sides):
t.forward(side)
t.left(angleStep)
done()
↳ run this script in Terminal or SublimeText
hello @micahmicah,
regular polygons can be described using vectors.
a vector has a length and an angle.
in regular polygons:
here is a simple example in code:
# define polygon parameters
x, y = 300, 200
sides = 5
perimeter = 1640
angleStart = 0
angleTotal = 360
autoclose = True
# calculate side length & angle
side = perimeter / sides
angleStep = abs(angleTotal / sides)
# convert angles to radians!
angleStep = radians(angleStep)
angleStart = radians(angleStart)
# create the polygon shape
B = BezierPath()
angle = angleStart
for i in range(sides):
# this is the crucial part:
# use trigonometry to calculate point B
# from point A, angle, and distance
x += cos(angle) * side
y += sin(angle) * side
if i == 0:
B.moveTo((x, y))
else:
B.lineTo((x, y))
angle += angleStep
if autoclose:
B.closePath()
fill(0, 1, 1)
strokeWidth(30)
lineCap('round')
lineJoin('round')
stroke(1, 0, 1)
drawPath(B)
@sinanatra MarginPen
used to live in roboFab.pens
. with the retirement of roboFab
, some pens were moved to a new library called fontPens.
drawBot includes the fontPens
library, which contains MarginPen
; you can use it to get the intersections of a line with a shape.
here’s an example:
from fontPens.marginPen import MarginPen
fill(None)
stroke(0)
B = BezierPath()
B.text("g", font="Helvetica-Bold", fontSize=1000)
drawPath(B)
for y in range(0, height(), 100):
strokeWidth(1)
line((0, y), (width(), y))
pen = MarginPen(dict(), y, isHorizontal=True)
B.drawToPen(pen)
strokeWidth(10)
intersections = pen.getAll()
for i, x in enumerate(intersections):
if not i % 2:
xNext = intersections[i+1]
line((x, y), (xNext, y))