I am testing Snap SVG and it's pretty nice SVG library, but I cannot get it to work in Chrome, but it's working ok in Safari, Firefox and Opera. You can see it here.
Here is the JS files that generates the SV
(function () {
var s = Snap('#snap'),
grid = 160,
imgSize = 130,
outerSize = 100,
innerSize = 90;
var team = {
person1: {
img: 'person1_bnw.jpg',
color: 'person1_color.jpg',
x: grid,
y: 0
},
person2: {
img: 'person2_bnw.jpg',
color: 'person2_color.jpg',
x: grid*2,
y: 0
}
// I removed rest of the members, but this is the idea
};
for (member in team) {
createMember(team[member]);
}
function createMember(member) {
var img, outer, mask, bnw, color, colorMask;
var showMatrix = new Snap.Matrix();
showMatrix.scale(1, 1, member.x + 130 /2, member.y + 130 /2);
var hideMatrix = new Snap.Matrix();
hideMatrix.scale(2, 2, member.x + 130 /2, member.y + 130 /2);
img = s.image('img/' + member.img, member.x, member.y, imgSize, imgSize);
mask = s.rect(member.x + 20, member.y + 20, innerSize, innerSize)
.transform('r-45')
.attr({ fill: '#fff' });
img.attr({ mask: mask });
if (member.color) {
color = s.image('img/' + member.color, member.x, member.y, imgSize, imgSize);
colorMask = s.rect(member.x + 20, member.y + 20, innerSize, innerSize)
.transform('r-45')
.attr({ fill: '#fff' });
color.attr({ mask: colorMask, transform: 's0', opacity: 0 });
}
outer = s.rect(member.x + 15, member.y + 15, outerSize, outerSize)
.transform('r-45')
.attr({
'fill-opacity': 0,
'stroke-width': 2,
'stroke-opacity': 0.5,
'stroke': '#000'
});
if (member.color) {
outer.mouseover(function () {
img.animate({ transform: hideMatrix, opacity: 0 }, 200, mina.bounce, function () { img.attr({ transform: 's0' }) });
color.animate({ transform: showMatrix, opacity: 1 }, 200, mina.bounce);
});
outer.mouseout(function () {
img.animate({ transform: showMatrix, opacity: 1 }, 200, mina.bounce);
color.animate({ transform: hideMatrix, opacity: 0 }, 200, mina.bounce, function () { color.attr({ transform: 's0' }) });
});
}
}
})();
You can check out the GitHub repo as well: https://github.com/mupkoo/snap-team
Related
So I've been trying to use the RexRainbow Phaser UI plugin, and All the Ui i make is invisible for some reason, But when I draw boundaries, it draws them, leaving me with a bunch of red boxes. Why are they all invisible?
Code Here (Github Gist)
//UI
var tabs = this.rexUI.add
.tabs({
x: 400,
y: 1600,
panel: this.rexUI.add.gridTable({
background: this.rexUI.add.roundRectangle(
0,
0,
20,
10,
10,
0x4e342e
),
table: {
width: 250,
height: 400,
cellWidth: 120,
cellHeight: 60,
columns: 1,
mask: {
padding: 2,
},
},
slider: {
//scroll bar
track: this.rexUI.add.roundRectangle(
0,
0,
20,
10,
10,
this.COLOR_DARK
),
thumb: this.rexUI.add.roundRectangle(
0,
0,
5,
40,
10,
this.COLOR_LIGHT
),
}
.layout()
.drawBounds(this.add.graphics(), 0xff0000); //debug for ui
https://codepen.io/vatsadev/pen/dyqGNBG -> full working example
It is hard too say, but I just can assume, that the reason is, that the color's used (that are not visible) are probally undefined and that's why transparent/invisible.
Without knowing the whole code, it is best to check, the variables/properties used for colors (like: this.COLOR_LIGHT, this.COLOR_DARK, ...)
Especially line 62, since here the this context is local to the tabs- object, and is not the scene object.
Tipp: for debugging purposes, I would hardcode all colors, just to see if the setup works, as intended. If so start replacing the hardcoded values with variables, like this you will find the culprit fast.
document.body.style = 'margin:0;';
const COLOR_PRIMARY = 0x4e342e;
const COLOR_LIGHT = 0x7b5e57;
const COLOR_DARK = 0x260e04;
var config = {
type: Phaser.AUTO,
width: 536,
height: 283,
scene: {
preload,
create
}
};
var isLeaking = false;
function preload (){
this.load.image('tiles', 'https://labs.phaser.io/assets/tilemaps/tiles/catastrophi_tiles_16.png');
this.load.tilemapCSV('map', 'https://labs.phaser.io/assets/tilemaps/csv/catastrophi_level2.csv');
this.load.scenePlugin({
key: "rexuiplugin",
url: "https://raw.githubusercontent.com/rexrainbow/phaser3-rex-notes/master/dist/rexuiplugin.min.js",
sceneKey: "rexUI",
});
}
function create () {
let map = this.make.tilemap({ key: 'map', tileWidth: 16, tileHeight: 16 });
let tileset = map.addTilesetImage('tiles');
let fgLayer = map.createLayer(0, tileset, 0, 0);
createUi(this);
updateMap(map);
}
function updateMap (map) {
let originPoint1 = map.getTileAtWorldXY(200, 100);
console.info(map.layers.sort((a,b) => b.depth - a.depth))
map.forEachTile(function (tile) {
var dist = Phaser.Math.Distance.Chebyshev(
originPoint1.x,
originPoint1.y,
tile.x,
tile.y
);
tile.setAlpha(1 - 0.09 * dist);
});
}
function createDataBase () {
var inventory = ['grass', 2, 'dirt', 3, 'wood', 2, 'leaves', 2, ]
// Create the database
var db = new loki();
// Create a collection
var items = db.addCollection("items");
// Insert documents
for (var i = 0; i < inventory.length; i+=2) {
items.insert({
blockType: inventory[i],
quantity: inventory[i+1],
color: Phaser.Math.Between(0, 0xffffff),
});
}
return items;
};
function createUi(scene){
var db = createDataBase();
var tabs = scene.rexUI.add
.tabs({
x: 250,
y: 250,
panel: scene.rexUI.add.gridTable({
background: scene.rexUI.add.roundRectangle(
0,
0,
20,
10,
10,
COLOR_PRIMARY
),
table: {
width: 250,
height: 400,
cellWidth: 120,
cellHeight: 60,
columns: 1,
mask: {
padding: 2,
},
},
slider: { //scroll bar
track: scene.rexUI.add.roundRectangle(0, 0, 20, 10, 10, COLOR_DARK),
thumb: scene.rexUI.add.roundRectangle(0, 0, 5, 40, 10, COLOR_LIGHT),
},
createCellContainerCallback: function (cell) { // each inventory cell
var scene = cell.scene;
var width = 250;
var height = cell.height;
var item = cell.item;
var index = cell.index;
return scene.rexUI.add.label({
width: width,
height: height,
background: scene.rexUI.add
.roundRectangle(0, 0, 20, 20, 0)
.setStrokeStyle(2, COLOR_DARK),
icon: scene.rexUI.add.roundRectangle( // inventory item texture goes here
0,
0,
20,
20,
10,
item.color
),
text: scene.add.text(0, 0, `${item.blockType}: ${item.quantity}`),
space: {
icon: 10,
left: 15,
},
});
},
}),
leftButtons: [
createButton(scene, 2, "Inv."),
],
space: {
leftButtonsOffset: 20,
leftButton: 1,
},
})
.layout()
.drawBounds(scene.add.graphics(), 0xff0000);
tabs.on(
"button.click",
function () {
// Load items into grid table
var items = db
.chain()
.data();
this.getElement("panel").setItems(items).scrollToTop();
},
tabs
);
tabs.emitButtonClick("left", 0);
}
function createButton (scene, direction, text) {
var radius;
switch (direction) {
case 0: // Right
radius = {
tr: 20,
br: 20,
};
break;
case 2: // Left
radius = {
tl: 20,
bl: 20,
};
break;
}
return scene.rexUI.add.label({
width: 50,
height: 40,
background: scene.rexUI.add.roundRectangle(
0,
0,
50,
50,
radius,
COLOR_DARK
),
text: scene.add.text(0, 0, text, {
fontSize: "18pt",
}),
space: {
left: 10,
},
});
};
new Phaser.Game(config);
<script src="//cdn.jsdelivr.net/npm/phaser#3.55.2/dist/phaser.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/lokijs/1.5.5/lokijs.min.js"></script>
I need to render table and chairs like in this picture:
I dont know how to calculate position of circles around rect. I tried some code, but its not working...Anybody knows how to solve it?
Check my code:
let smallCircleRadius = 20
let tableSize = {
width: ((seats-4/2)*(smallCircleRadius)),
height: ((seats-4/2)*(smallCircleRadius))
}
let controlY = 0
let totalCircleSide = (seats-4)/2
let controlX = 0
let distanceY = 0
let distanceX = 0
let table = new Konva.Rect({
width: tableSize.width,
height: tableSize.height,
fill: '#fff',
stroke: '#c3c6cf',//'#b2cfcf',
strokeWidth: 8,
x:150,
y: 150
});
let count = 0
group.add(table)
for (var i = 0; i < seats; i++) {
// let distanceToTable = tableSize.width/2;
// let x = i <= 2 ? table.x() + distanceToTable * i + (smallCircleRadius + 8) : count > totalCircleSide ? distanceToTable + distanceX+smallCircleRadius: controlX
// let y = i < 2 ? table.y() - distanceToTable/2: count > totalCircleSide ? controlY : distanceToTable + distanceY*smallCircleRadius
//let x = table.x()
//let y = table.y()
group.add(new Konva.Circle({ radius: smallCircleRadius, fill: '#d2d6df', stroke: '#c3c6cf',strokeWidth: 3, x, y }));
}
Make yourself a simple model that describes the position of the circles in simple relationship of circles to the table. Something like this can be extended via different models to accommodate other table layouts as the description of the layout is entirely in the model data.
const
// Set up a canvas stage
containerEle = document.getElementById('container'),
stage = new Konva.Stage({
container: "container",
size: {
width: containerEle.offsetWidth,
height: containerEle.offsetHeight
}
}),
layer = new Konva.Layer();
stage.add(layer);
const model = {
table: {
x: 100,
y: 100,
width: 200,
height: 400,
fill: 'black',
stroke: 'silver',
strokeWidth: 5
},
seat: {
radius: 40,
fill: 'white',
stroke: 'silver',
strokeWidth: 5,
gap: 20
},
seats: [{
name: "Seat 1",
x: "25%",
y: "-1r"
},
{
name: "Seat 2",
x: "75%",
y: "-1r"
},
{
name: "Seat 3",
tableX: 1,
tableY: 0,
x: "1r",
y: "16.6%"
},
{
name: "Seat 4",
tableX: 1,
tableY: 0,
x: "1r",
y: "50%"
},
{
name: "Seat 5",
tableX: 1,
tableY: 0,
x: "1r",
y: "83.3%"
},
{
name: "Seat 6",
tableX: 0,
tableY: 1,
x: "75%",
y: "1r"
},
{
name: "Seat 7",
tableX: 0,
tableY: 1,
x: "25%",
y: "1r"
},
]
}
// make the table
const table = new Konva.Rect(model.table);
layer.add(table)
for (const seat of model.seats) {
const seatShape = new Konva.Circle(model.seat);
let tablePos = {
x: seat.tableX && seat.tableX === 1 ? model.table.x + model.table.width : model.table.x,
y: seat.tableY && seat.tableY === 1 ? model.table.y + model.table.height : model.table.y
}
let position = {
x: tablePos.x + getPosComponent(seat.x, model.seat.radius, model.table.width, model.seat.gap),
y: tablePos.y + getPosComponent(seat.y, model.seat.radius, model.table.height, model.seat.gap)
}
seatShape.position(position)
layer.add(seatShape);
}
function getPosComponent(val, radius, size, gap) {
if (val.indexOf('r') > 0) {
let num = parseInt(val),
sign = Math.sign(num);
return sign * ((Math.abs(num) * radius) + gap);
} else if (val.indexOf('%') > 0) {
let num = parseFloat(val),
sign = Math.sign(num);
return sign * (size * num / 100);
}
throw new Error("Unexpected val format " + val);
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset=UTF-8>
<script src="https://unpkg.com/konva#8/konva.min.js"></script>
<style>
#container {
width: 800px;
height: 600px;
}
</style>
</head>
<body>
<div id="container"></div>
</body>
</html>
I am trying to draw a "tooltip" line on completion of each slice animation using chartistjs.
Current situation
JSFiddle
Goal
I am using chartistjs library to animate the donut. I am looking for drawing line on completion of each slice (svg animate) in the chart.on('draw') function.
Looking for a line after each slice. Any recommendations?
Gist of code
var chart = new Chartist.Pie('#inner-donut', {
series: [15, 20, 30, 25],
labels: [1, 2, 3, 4]
}, {
donut: true,
showLabel: false,
width: 800,
total: 90,
height: 400,
chartPadding: 70,
plugins: [
Chartist.plugins.fillDonut({
items: [{
content: '',
offsetY : -60,
offsetX: -200
}, {
content: ''
}]
}),
]
});
chart.on('draw', function(data) {
if(data.type === 'slice') {
var pathLength = data.element._node.getTotalLength();
data.element.attr({
'stroke-dasharray': pathLength + 'px ' + pathLength + 'px'
});
var animationDefinition = {
'stroke-dashoffset': {
id: 'anim' + data.index,
dur: 1000,
from: -pathLength + 'px',
to: '0px',
easing: Chartist.Svg.Easing.easeOutQuint,
fill: 'freeze'
},
};
if(data.index !== 0) {
animationDefinition['stroke-dashoffset'].begin = 'anim' + (data.index - 1) + '.end';
}
data.element.attr({
'stroke-dashoffset': -pathLength + 'px'
});
data.element.animate(animationDefinition, false);
}
});
Have an issue with line rendering when resizing object.
I've locked line endings positions to exact point on circles and when moving, scaling, rotating etc I have to edit lines connected to current circle.
Here is fiddle
Just try to resize circles and at some point you'll see that rendering is crashed a bit which corresponds to lines. Need a help for it, maybe rerender or something.
Or that's an issue of fabric.js
var circlesData = [{
id: 1,
x: 80,
y: 80,
r: 60
}, {
id: 2,
x: 440,
y: 190,
r: 90
}];
var connectionsData = [{
from: {id: 1, angle: 0, rdist: .8},
to: {id: 2, angle: 0, rdist: .4},
}]
var fcircles = [];
var fconnections = [];
var fcanvas;
init();
function init() {
fcanvas = new fabric.Canvas('c', {
imageSmoothingEnabled: false,
allowTouchScrolling: true,
});
fcanvas.preserveObjectStacking = true;
fcanvas.selection = false;
fcanvas.setBackgroundColor('#fff');
fcircles = circlesData.map(function(circleData) {
var circle = new fabric.Circle({
left: circleData.x,
top: circleData.y,
radius: circleData.r,
fill: 'rgba(100,100,255,0.2)',
originX: 'center',
originY: 'center'
});
circle.initialData = circleData;
circle.setControlsVisibility({
mt: false,
mb: false,
ml: false,
mr: false,
mtr: false,
});
return circle;
});
fconnections = connectionsData.map(function(connectionData) {
var line = new fabric.Line([0,0,0,0], {
strokeWidth: 6,
strokeLineCap: 'round',
fill: 'red',
stroke: 'red',
originX: 'center',
originY: 'center'
});
line.from = copyJson(connectionData.from);
line.to = copyJson(connectionData.to);
line.selectable = false;
return line;
});
fcircles.concat(fconnections).forEach(function(fobj){
fcanvas.add(fobj)
});
updateConnections(fconnections);
fcanvas.renderAll();
console.log(fcanvas.getObjects())
fcanvas.on('object:moving', onObjChange);
fcanvas.on('object:scaling', onObjChange);
fcanvas.on('object:rotating', onObjChange);
}
function onObjChange(e) {
if(['line'].indexOf(e.target.type) > -1) {
return;
}
var circle = e.target;
updateConnections(fconnections.filter(function(fconnection){
return fconnection.from.id === e.target.initialData.id || fconnection.to.id === e.target.initialData.id;
}))
}
function updateConnections(fconnections) {
fconnections.forEach(function(fconnection) {
var from = fcircles.filter(function(c){return c.initialData.id === fconnection.from.id})[0];
var to = fcircles.filter(function(c){return c.initialData.id === fconnection.to.id})[0];
var fromAngle = fconnection.from.angle - from.angle / 180 * Math.PI;
var toAngle = fconnection.to.angle - from.angle / 180 * Math.PI;
debugger;
fconnection.set({
x1: from.left + fconnection.from.rdist * from.radius * Math.cos(fromAngle),
y1: from.top + fconnection.from.rdist * from.radius * Math.sin(fromAngle),
x2: to.left + fconnection.to.rdist * to.radius * Math.cos(toAngle),
y2: to.top + fconnection.to.rdist * to.radius * Math.sin(toAngle)
});
fconnection.setCoords();
});
}
function copyJson(obj) {
return JSON.parse(JSON.stringify(obj));
}
Add to your Line object property:
objectCaching: false
From fabricjs documentation:
objectCaching :Boolean When true, object is cached on an additional
canvas. default to true since 1.7.0
I am developing a JointJs Application,I need to set font-size for a text inside a rectangle.
$('#FText,#FTextHeight,#FTextWidth,#FTextSize').on('keyup change', function () {
var FtHeight = $('#FTextHeight').val();
var FtWidth = $('#FTextWidth').val();
var FtSize = parseInt($('#FTextSize').val());
var txt = $('#FText').val();
graph2.clear();
if (txt.length > 0) {
$('#FTexterror').empty();
var myFtext = new joint.shapes.basic.Rect({
position: { x: 50, y: 50 },
size: { width: FtWidth, height: FtHeight },
attrs: {
rect: {
fill: 'white', stroke: outerColor, 'class': 'customtext',
},
text: {
text: txt, 'letter-spacing': 1, 'font-size': FtSize,
fill: outerColor, 'font-size': 11, 'y-alignment': 'middle',
}
}
});
graph2.addCells([myFtext]);
}
else {
$('#FTexterror').empty().append('*Enter valid text');
}
});
the above code is not working while setting font-size for the text.
Kindly help me on this
try this
$('.input-text')
.val(rect.attr('text/font-size')) //set initial value
.on('keyup', function () {
var val = $(this).val();
rect.attr('text/font-size', val);
});
complete demo: https://jsfiddle.net/vtalas/sav49mj4/