otm / svg.path.js

A path extension for the svg.js library
http://otm.github.io/svg.path.js/
95 stars 32 forks source link

rounded rectangle? #10

Closed mspanish closed 10 years ago

mspanish commented 10 years ago

Hey this is a great piece of work, thank you! I"ve been trying to draw a rounded rectangle, for a dynamic SVG speech bubble feature - and I can get the sided curved, but doesn't look quite right. I am using this code so far, with 'widthy' and 'heighty' as my dynamic variables for the speech bubble based on the text length:

var recty = draw.path()
    .attr({ 
        fill: '#ffffff',
        stroke: '#000', 
        'stroke-width': .25,
    })
.M(-margin, 0)
.L(widthy, 0)
.c(
   {x:0, y:0},  
   {x:widthy*.1, y:heighty/2},   
   {x:0, y:heighty}
)
.L({x:-margin, y:heighty})
.c(
   {x:0, y:0},  
   {x:-widthy*.1, y:-heighty/2},   
   {x:0, y:-heighty}
)

The regular svg rect() with a radius works fine, but I need to manually draw the little tails for the speech bubble, so I thought I'd be better of using the path plugin.

Thanks for any help you may be able to give!

mspanish commented 10 years ago

ok I figured out how to do this, as well as drawing an upper right and lower right tail for the bubble. This code is just a snippet from mine so you'll have to use your own variables but for anybody looking how to créate a speech bubble using this plugin, it's at least a start. I size my text and bubble dynamically based on the string length, which is why you see the funky sizing stuff here.

var recty;

heighty = heighty*1.23
widthy = widthy*1.1
margin = widthy*.1;
if (bubbleSVG.has(set)) {
    bubbleSVG.remove(set)
}
// create a set to add this to later
var set = draw.set()
var tailHeight = heighty*.3

var lengthola = (the_length/10)*2;
var radius = 20 /lengthola;
var radiusHeight = heighty - radius;

if (radius>49) {
    radius = 30;
}
var y=0;
var x=0;
var rx=radius;
var ry=radius;
var h=radiusHeight;
var w=widthy;
console.log('our radius is '+radius);
// if our radius is big, make our height taller
if (rx > 20) {
    h=h*1.4;
    w=w*1.1;
}
if (rx > 29 && the_length>2) {
    h=h*1.5;
    w=w*1.2;
}
if (rx > 29 && the_length<3) {
    h=h*2.5;
    w=w*1.2;
}

if (rx > w / 2) rx = w / 2
if (ry > h / 2) ry = h / 2
var recty;

if (position === 'top-right') 
{
// tail position, top right
recty = draw.path()
    .data('colored', true, true)
    .attr({ 
        fill: App.bubbleTone,
        stroke: '#000', 
        'stroke-width': .25,
    })
.M (rx, y)
// this is our TAIL!
.H ((w - rx)*.7)
.l ({x:30, y:-tailHeight})
.l ({x:-10, y:tailHeight})
.H (w - rx)
.A (rx, ry, 0, 0, 1, {x: w, y:ry})
.V (h - ry)
.A (rx, ry, 0, 0, 1,  {x:(w - rx), y:h})
.H (rx)
.A (rx, ry, 0, 0, 1,  {x:x, y:(h - ry)})
.V (ry)
//.l ({x:0,y:-(h-ry)})
.A (rx, ry, 0, 0, 1, {x:rx, y:y})
.Z()
//.drawAnimated()
}

else {
    // tail position, bottom right
    // for now this is the tail for all things NOT top right, but later we'll add other tails
recty = draw.path()
    .data('colored', true, true)
    .attr({ 
        fill: App.bubbleTone,
        stroke: '#000', 
        'stroke-width': .25,
    })
.M (rx, y)
.H (w - rx)
.A (rx, ry, 0, 0, 1, {x: w, y:ry})
.V (h - ry)
.A (rx, ry, 0, 0, 1,  {x:(w - rx), y:h})
// this is our TAIL!
.l ({x:-w/8, y:0})
.l ({x:-20, y:tailHeight})
.l ({x:10, y:-tailHeight})
.H (rx)
.A (rx, ry, 0, 0, 1,  {x:x, y:(h - ry)})
.V (ry)
//.l ({x:0,y:-(h-ry)})
.A (rx, ry, 0, 0, 1, {x:rx, y:y})
.Z()
//.drawAnimated()
}
otm commented 10 years ago

Thanks for leaving a solution to your issue.