Arrange moving shapes in the same spot

Every time I press the button, a unique shape is generated. These shapes are dynamic and can range from polygons to circles (there are hundreds of shapes).

Each shape is composed of a series of lines.

The problem arises when each shape is positioned differently and scaled smaller or bigger than the others. I want all the shapes to have consistent scaling effects and be positioned at the same x-coordinate. Some shapes appear in the center, while others shift towards the top left.

The issue may lie in the coordinates of the lines. In the first snippet of code, it begins at (0,0) while the last shape's line starts at (15,5).

Is there a way to place the group g at the same position for all shapes? Should I position them relative to something?

var draw = SVG('drawing').viewbox(0, 0, 400, 400).attr("preserveAspectRatio", "xMidYMid meet");
var group = draw.group().translate(90, 90).scale(3)
var obj = {
    "type": "Polygon",
    "coords": [
        [
            [0, 0],
            [30, 0],
            [30, 20],
            [60, 20],
            [60, 40],
            [0, 40],
            [0, 0]
        ],
        //more coordinate arrays here...
    ]
};

shapehandler()
function shapehandler() {
    if (obj.coords.length) {
        group.clear();
        drawShape(obj.coords[0]);
        obj.coords.shift();

    }
}

//Code continues...

html, body {
    margin: 0;
    padding: 0;
    font-family: Arial;
}
svg {
    width: 100%;
    height: 100%;
  }
#drawing{
    margin: 20px;
    display: inline-block;
    position: relative;
    border: 1px solid darkgrey;
    overflow:hidden;
    box-sizing: border-box;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/svg.js/2.6.6/svg.js"></script>
 <div id="toolbar">
    <button type="button" id="btn-show-shape" onclick="shapehandler()">Show Polygon Shapes</button>
  </div>
  <div id="drawing">
  </div>

Answer №1

Your HTML code remains intact.

The CSS belongs to you, but I have incorporated a new style rule for lines. This rule sets the stroke-width property. To enhance the visual appeal, I included stroke-linecap: round.

The crucial modification I made was introducing

vector-effect: non-scaling-stroke
. This ensures that an object's stroke width remains constant regardless of transformations and zoom levels, facilitating scalability.

In JavaScript, your data (points and colors) remains unchanged, while the structure has been revised.

The key adjustment involves calculating the scale based on the group's bounding box width. The group is then translated to the center of the SVG canvas and scaled accordingly.

I trust this aligns with your requirements.

const SVG_NS = 'http://www.w3.org/2000/svg';
const W = 400, cx = W / 2;
const H = 400, cy = H / 2;

let obj = {
    type: "polygon",
    coords: [
        [
            [0, 0],
            [30, 0],
            [30, 20],
            [60, 20],
            [60, 40],
            [0, 40],
            [0, 0]
        ],
        // More polygon coordinates here
    ]
};

let colorShade = [
    '#FFDC0B',
    // More color codes array here
];

// Create SVG element
let svg = drawSVGElement(
    "svg", 
    { viewbox: `0 0 ${W} ${H}`, preserveAspectRatio: "xMidYMid meet" }, 
    drawing
);

// Create group element
let group = drawSVGElement(
    "g", 
    {/*transform:"translate(90,90) scale(3)"*/}, 
    svg
)

// Draw red dot in the canvas center
drawSVGElement("circle", { cx: cx, cy: cy, r: 5, fill: "red" }, svg)

let n = 0;

// Function to draw and scale polygons
function drawAndScale(n) {
    // Code for drawing and scaling goes here
}

drawAndScale(n);

// Shape handler function
function shapeHandler() {
    // Function logic for changing shapes goes here
}
<style>
html, body {
    margin: 0;
    padding: 0;
    font-family: Arial;
}
svg {
    width: 100%;
    height: 100%;
}
#line{
    stroke-width: 50px;
    stroke-linecap: round;
    vector-effect: non-scaling-stroke;
}
</style>
<div id="toolbar">
    <button type="button" id="btn_show_shape" onclick="shapeHandler()">Show Polygon Shapes</button>
</div>
<div id="drawing">
</div>

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Troubleshooting a problem with the Jquery Quicksearch plugin on constantly changing web

Quicksearch is pretty amazing... but it faces a usability issue that causes strange behavior. Many users hit enter after entering a search query, which reloads the page without any parameters and destroys the queries. Check this out: Adding: $('for ...

Update the DIV element's class to reflect whether the quiz answer provided is correct or incorrect

I am facing a challenge while attempting to assign a CSS class to a dynamically created element in JavaScript. The error I'm encountering pertains to the reference issue with the trackerMarker element within the event listener functionality. Although ...

React TextField is not accommodating the new line character ' ' causing recognition issues

Explanation I have encountered an issue while using Material UI TextField and mapping through an array of objects fetched from a MongoDB database. Here is the code snippet in question: {state.map((item) => ( <TextField name=" ...

Fuzzy Background to Enhance Your Bootstrap 5 Offcanvas Navigation Menu

Currently utilizing Bootstrap v5.2, I am endeavoring to replicate the image displayed in the link below: Blurry Sidebar Backdrop As per the MDN Documentation, backdrop-filter is intended for blurring the background of an element. .offcanvas-backdrop { ...

Encountering TypeScript error TS2345 while attempting to reject a Promise with an error

I recently encountered a perplexing TypeScript error message that I am struggling to comprehend. The specific error reads as follows: error TS2345: Argument of type '(error: Error) => void | Promise' is not assignable to parameter of type & ...

When utilizing jQuery and Ajax for form submission, PHP is unable to retrieve any data

I'm encountering an issue when trying to submit a form with only a radiobutton group named radiob. The script I am using for submitting the data is as follows: <script type="text/javascript"> $(function() { $("#myForm").submit(funct ...

Incorporating input utilities into a text field

Currently working on a Django blog website catering to bloggers who are not well-versed with Markdown/Markup. I am considering incorporating these tools into my textarea, as shown in the image below: https://i.sstatic.net/ud4hV.jpg Any recommendations on ...

Leveraging JavaScript to identify web browsers

I am looking to implement a feature on my website where if the visitor is using Internet Explorer 8.0 or an earlier version, they will receive an alert prompting them to upgrade their browser before proceeding. For users with other browsers, the page will ...

Is there a way to have content update automatically?

After writing this block of code, I discovered that clicking on one of the circles activates it and displays the corresponding content. Now, I am looking for a way to automate this process so that every 5 seconds, a new circle gets activated along with its ...

What is the best way to combine a hyperlink with a string in an Angular form?

Currently I am in the process of learning angular and experimenting with creating a list of websites that can be clicked on, similar to what you would find in a bookmark app. This is based on a todo example. https://github.com/LightYear9/ToDoList In orde ...

Observing mutations in HTML templates with MutationObserver

It appears that the MutationObserver does not function properly with a <template> tag. Check out this JSFiddle for more information! Any suggestions on how to effectively monitor changes in a <template> element? ...

How does the designated callback function in the filter method effectively remove any missing values from the array?

//Snippet of JavaScript code let sparseArray = [5, , 3, , 1]; let denseArray = sparseArray.filter(() => true); console.log(denseArray); The filter function in the callback removes empty elements from the sparse array. Output: [5, 3, 1] Explanation: ...

Error encountered: Unable to compute centroids with Three.js / Collada due to an undefined value

There seems to be an issue when utilizing the ColladaLoader JavaScript, as it throws an error stating "undefined is not a function" in line 2403 of ColladaLoader.js. Despite following the example provided by simply loading the .dae file: var loader = new ...

VueJS: The variable being referenced in the render is neither a defined property nor method of the instance

Check out this VueJS course on building Robots: VueJS Course Link My VueJS-RobotBuilder repository: RobotBuilder Repo Currently, I am working on a VueJS tutorial that involves an issue with an imported data object called availableParts. I have successfu ...

Add the URL link according to the specific domain name

I am looking for a way to attach additional URL parameters to any links that contain example.com on a webpage. The current script I have only works if the link does not already have parameters attached to it. <script> document.body.innerHTML = d ...

Verify whether the input from ng-model is numeric

When utilizing ng-model binding in an input field, data is usually stored as a string. Is there a way to verify if the user has entered a number? ...

How can I initiate a button click event in aspx by pressing the "Enter" key on a textbox, with the button click event being defined in the source cs file?

I am trying to trigger the btnSearchSuiteGroup_Click event when the "enter" key is pressed on the txtSuiteGroupName textbox in the aspx file. Below is the code snippet: <asp:TextBox ID="txtSuiteGroupName" runat="server" clientidmode="Static" CssClass=" ...

ClickEvent (or element selector) is experiencing functionality issues

I'm currently working on creating a small calculator using HTML, CSS, and JS. However, I'm facing an issue with selecting buttons of the calculator from the HTML script and adding EventListeners to them. Here is a snippet of my HTML code: `< ...

The execution of a function in PHP is determined by the data passed from Angular

I've encountered a new challenge while working on web development and would greatly appreciate some assistance. Currently, I have several buttons that need to execute different functions when clicked, such as ng-click='loadA', ng-click=&apos ...

Encountering issues with installing @vue/cli on Linux Ubuntu

Currently facing an issue while attempting to install the Vue CLI on Ubuntu (WSL). After running both yarn add global @vue/cli and npm install @vue/cli --global, it seems like the commands were successful. However, upon checking the version using vue --v ...