html arrange div inside the table - html

I need a little hand. So basically im trying to arrange the div inside the table but for some reason I could not. I already tried adding tr, td but it keeps messing the code now im here for some assistance.
Here is a sample picture of what I did.
Sample Picture
As you can see timer goes first before the Title or the names. So I want to change their position. I want to the title to appear first before the timer.
Now Here is the sample picture of what I wanted
Here below is the code for the firt picture sample.
<table width="214" border="0" align="center" cellpadding="0" cellspacing="0" style="margin-top: 10px; ">
<tr>
<td height="48" style="background-image:url(template/<?=$core['config']['template'] ?>/images/eventsmenu.png) "><div class="m_title"></div></td>
</tr>
<tr>
<td style="background-image:url(template/<?=$core['config']['template'] ?>/images/bg_snbmid.png); background-repeat:repeat-y; "><ul class="snb_1dep">
<table width="95%" height="119" border="0" cellpadding="0" cellspacing="0" class="gen_table">
<tr>
<td height="69" align="center" valign="top" class="n_back">
<table width="200" border="0" align="center" cellpadding="2" cellspacing="0">
<div id="events">
<script type="text/javascript" src="template/<?=$core['config']['template'] ?>/js/time.js"></script>
<script type="text/javascript">MuEvents.init('00:00:00');</script>
</div>
</table>
</td>
</tr>
<tr>
<td class="n_foot"> </td>
</tr>
</table>
Here is the css if you want to see.
/* Styles */
#left_box_body {
width: 220px;
margin-left: 80px;
margin-top: -100px;
margin-bottom: -90px;
}
#events dt {
padding: 1px 2px;
border-radius: 2px;
margin: 2px 0;
}
#events span {
display:block;
font-size:11px;
}
#events {
margin:5px;
width: 200px;
padding-top: 4px;
padding-left: 10px;
}
.rightfloat { float: right; }
/*
MUCore CSS Start
*/
If you are looking for the timer code here is it below.
var MuEvents = {};
MuEvents.text = [
[lang[0], lang[1]],
[lang[2], lang[3]]
];
MuEvents.sked = [
['Blood Castle', 0, '02:30', '04:30', '06:30', '08:30', '10:30', '12:30', '14:30', '16:30', '18:30', '20:30', '22:30', '22:30'],
['Chaos Castle', 0, '02:40', '04:40', '06:40', '08:40', '10:40', '12:40', '14:40', '16:40', '18:40', '20:40', '22:40', '22:40'],
['Devil Square', 0, '01:00', '03:00', '05:00', '07:00', '09:00', '11:00', '13:00', '15:00', '17:00', '19:00', '21:00', '23:00'],
['Illusion Temple', 0, '01:20', '05:20', '09:20', '13:20', '17:20', '20:20', '21:20', '23:20'],
['Happy Hour', 0, '12:00'],
['BlueEvent', 0, '10:35', '12:05', '13:25', '15:07', '18:25'],
['White Wizard', 1, '13:00', '19:00'],
['Golden Invasion', 1, '23:23', '18:25', '00:00', '06:00', '20:00', '14:05'],
['Red Dragon Invasion', 1, '14:00', '20:00'],
['Loren Deep', 0, '20:00']
];
MuEvents.init = function (e) {
if (typeof e == "string")
var g = new Date(new Date().toString().replace(/\date('H')+:\date('i')+:\date('s')+/g, e));
var f = (typeof e == "number" ? e : (g.getHours() * 60 + g.getMinutes()) * 60 + g.getSeconds()), q = MuEvents.sked, j = [];
for (var a = 0; a < q.length; a++) {
var n = q[a];
for (var k = 2; k < q[a].length; k++) {
var b = 0, p = q[a][k].split(":"), o = (p[0] * 60 + p[1] * 1) * 60, c = q[a][2].split(":");
if (q[a].length - 1 == k && (o - f) < 0) b = 1;
var r = b ? (1440 * 60 - f) + ((c[0] * 60 + c[1] * 1) * 60) : o - f;
if (f <= o || b) {
var l = Math.floor((r / 60) / 60), l = l < 10 ? "0" + l : l, d = Math.floor((r / 60) % 60), d = d < 10 ? "0" + d : d, u = r % 60, u = u < 10 ? "0" + u : u;
j.push('<dt class="event">' + (l == 0 && !q[a][1] && d < 5 ? '<img src="template/default/images/online.png" />' : '') + '<b class="rightfloat">' + q[a][b ? 2 : k] + "</b><b>" + n[0] + '</b><span><div class="rightfloat">' + (l + ":" + d + ":" + u) + "</div>" + (MuEvents.text[q[a][1]][+(l == 0 && d < (q[a][1] ? 1 : 5))]) + "</span>");
break;
};
};
};
document.getElementById("events").innerHTML = j.join("");
setTimeout(function () {
MuEvents.init(f == 86400 ? 1 : ++f);
}, 1000);
};
Im no so sure but im thinking the problem is somewhere here?
<table width="200" border="0" align="center" cellpadding="2" cellspacing="0">
<div id="events">
<script type="text/javascript" src="template/<?=$core['config']['template'] ?>/js/time.js"></script>
<script type="text/javascript">MuEvents.init('00:00:00');</script>
</div>
</table>
EDIT HTML
<div id="events"><dt class="event"><b class="rightfloat">02:30</b><b>Blood Castle</b><span><div class="rightfloat">03:22:35</div>Starts at</span></dt><dt class="event"><b class="rightfloat">02:40</b><b>Chaos Castle</b><span><div class="rightfloat">03:32:35</div>Starts at</span></dt>
<dt
class="event"><b class="rightfloat">01:00</b><b>Devil Square</b><span><div class="rightfloat">01:52:35</div>Starts at</span>
</dt><dt class="event"><b class="rightfloat">23:20</b><b>Illusion Temple</b><span><div class="rightfloat">00:12:35</div>Starts at</span></dt><dt class="event"><b class="rightfloat">12:00</b><b>Happy Hour</b><span><div class="rightfloat">12:52:35</div>Starts at</span></dt>
<dt
class="event"><b class="rightfloat">10:35</b><b>BlueEvent</b><span><div class="rightfloat">11:27:35</div>Starts at</span>
</dt><dt class="event"><b class="rightfloat">13:00</b><b>White Wizard</b><span><div class="rightfloat">13:52:35</div>Starts at</span></dt><dt class="event"><b class="rightfloat">23:23</b><b>Golden Invasion</b><span><div class="rightfloat">00:15:35</div>Starts at</span></dt>
<dt
class="event"><b class="rightfloat">14:00</b><b>Red Dragon Invasion</b><span><div class="rightfloat">14:52:35</div>Starts at</span>
</dt><dt class="event"><b class="rightfloat">20:00</b><b>Loren Deep</b><span><div class="rightfloat">20:52:35</div>Starts at</span></dt>
</div>

Related

How do I email an update to the table results for specific columns that meet the criteria less than 0?

I have a table that I would like to send an email for based on the values of columns E(table below). The Columns I would like to append to the email are A,D,E,F. The Rows I would like to include are those that have dropped below 0 from column E. How do I amend my function to allow for this change?
function EmailUpdate() {
var hty = SpreadsheetApp.getActiveSpreadsheet().getSheetByName('Historical')
var data = hty.getRange("A1:F" + hty.getLastRow()).getValues().filter(([,e], i) => i == 0 || e < 0);
var TABLEFORMAT = 'cellspacing="2" cellpadding="2" dir="ltr" border="1" style="width:100%;table-layout:fixed;font-size:10pt;font-family:arial,sans,sans-serif;border-collapse:collapse;border:1px solid #ccc;font-weight:normal;color:black;background-color:white;text-align:left;text-decoration:none;font-style:normal;'
var htmltable = '<table ' + TABLEFORMAT + ' ">';
for (row = 0; row < data.length; row++) {
htmltable += '<tr>';
for (col = 0; col < data[row].length; col++) {
if (data[row][col] === "" || 0) {
htmltable += '<td>' + 'None' + '</td>';
} else
if (row === 0) {
htmltable += '<th>' + data[row][col] + '</th>';
} else {
htmltable += '<td>' + data[row][col] + '</td>';
}
}
htmltable += '</tr>';
}
htmltable += '</table>';
Logger.log(data);
Logger.log(htmltable);
MailApp.sendEmail(Session.getActiveUser().getEmail(), 'Email Report', '' ,{
htmlBody: htmltable
})
}
Replace:
var data = hty.getRange("A1:F" + hty.getLastRow()).getValues().filter(([,e], i) => i == 0 || e < 0);
With:
var data = hty.getRange("A1:F"+hty.getLastRow()).
getDisplayValues().
map(([a,,,d,e,f]) => [a,d,e,f]).
filter((r,i)=>r[2].includes("-") || i==0 );
References:
map
filter

Color rectangle one by one in a canvas

I have canvas on which there are number of rectangle drawn so that the make a grid. What I want is to color each rectangle one by one in the grid until each of them are colored black and then again select few of them to color white in the same way one by one. I have tried few methods using "for" loop and "setTimeout" but its not working out.
I have recently started javascript that's why I need help to do this.
This code only includes the making of the grid no further because that part was not working out:
var canvas;
var ctx;
canvas = document.getElementById('canvas');
ctx = canvas.getContext('2d');
tileW = 20;
tileH = 20;
tileRowCount = 25;
tileColCount = 40;
var tile = [];
for (c = 0; c < tileColCount; c++) {
tile[c] = [];
for (r = 0; r < tileRowCount; r++){
tile[c][r] = {
x: c * (tileW + 3),
y: r * (tileH + 3),
state: 'e'
}; //state e for empty
}
}
for (c = 0; c < tileColCount; c++)
for (r = 0; r < tileRowCount; r++) {
ctx.beginPath();
ctx.fillStyle = '#AAAAAA';
ctx.rect(tile[c][r].x, tile[c][r].y, tileW, tileH);
ctx.closePath();
ctx.fill();
}
}
<!DOCTYPE html>
<html lang="en" dir="ltr">
<head>
<meta charset="utf-8">
<title></title>
</head>
<body>
<canvas id="canvas" width='1000' height='600'></canvas>
<script type="text/javascript" src='data.js'></script>
</body>
</html>
Update your rendering code to use the fillRect method from the 2d context.
Replace this:
ctx.beginPath();
ctx.fillStyle = '#AAAAAA';
ctx.rect(tile[c][r].x, tile[c][r].y, tileW, tileH);
ctx.closePath();
ctx.fill();
With this:
ctx.fillStyle = "#AAAAAA";
ctx.fillRect(tile[c][r].x, tile[c][r].y, tileW, tileH);
It is not clear what you want. My guess is that you want a checkerboard. The following will do so.
The Remainder operator
The operator % returns the remainder after division. eg 3 % 2 is 1 and 4 % 2 is 0
We can use the remainder operator to let us know which color to make each square. As we count down the rows the remainder of the row count and 2 will switch between 0 and 1. For each column we want the opposite. If you add the row count to the column count and get the remainder we get the desired result. Example (r + c) will give (0 + 0) % 2 == 0, (1 + 0) % 2 == 1, (2 + 0) % 2 == 0, (3 + 0) % 2 == 1, then the next column (0 + 1) % 2 == 1, (1 + 1) % 2 == 0, (2 + 1) % 2 == 1, (3 + 1) % 2 == 0. and so on.
The % operator has higher precedence than the addition operator + thus we need to put the grouping operators ( ) around the addition.
Eg 3 + 1 % 2 will equal 4. The 1 % 2 is done first then the 3 is added while (3 + 1) % 2 will equal 0. The (3 + 1) is first then the remainder is done
The Ternary operator
We can do this most simply using the ternary operator ?. eg color = (c + r) % 2 ? "white" : "black" which is the same as if ((c + r) % 2 === 1) { color = "white" } else { color = "black" }
Example
const ctx = canvas.getContext('2d');
const tileW = 20;
const tileH = 20;
const tileRowCount = 25;
const tileColCount = 40;
const tiles = [];
for (let c = 0; c < tileColCount; c++) {
for (let r = 0; r < tileRowCount; r++) {
tiles.push({
x: c * (tileW + 3),
y: r * (tileH + 3),
color: (c + r) % 2 ? "white" : "black",
});
}
}
for (const tile of tiles) {
ctx.fillStyle = tile.color;
ctx.fillRect(tile.x, tile.y, tileW, tileH);
}
<canvas id="canvas" width='1000' height='600'></canvas>

Change color of Chrome's calendar icon in HTML Date Input

I am having some difficulty styling the HTML 5 Date input in Chrome.
Using mark up such as
<input type="date" max="2020-06-03" value="2020-06-01">, with some background and font color styling in CSS, renders in Chrome as:
I would like to make the calendar icon on the right hand side white, so it matches the color of the text.
::-webkit-calendar-picker-indicator looked like a possible candidate. Setting the background color on this changes the color behind the icon (as expected). However I can't find any parameter that has an effect on the icon color itself.
I've managed to work around it for now using a CSS filter to invert the black color to white
::-webkit-calendar-picker-indicator {
filter: invert(1);
}
However this feels quite fragile and far from ideal.
Another way, is by setting the "color-scheme" to dark.
input {
color-scheme: dark;
}
<input type="date" />
FYI: this will also put the popup in dark mode.
The Shadow DOM style sets a background-image which can not be interacted with in CSS (except for filter). One option is to replace the whole image where you can set any fill color and this method will be forward-compatible in case Chrome decides to inherit the icon color from color later on, at the cost of having a "hardcoded" icon:
::-webkit-calendar-picker-indicator {
background-image: url('data:image/svg+xml;utf8,<svg xmlns="http://www.w3.org/2000/svg" width="16" height="15" viewBox="0 0 24 24"><path fill="%23bbbbbb" d="M20 3h-1V1h-2v2H7V1H5v2H4c-1.1 0-2 .9-2 2v16c0 1.1.9 2 2 2h16c1.1 0 2-.9 2-2V5c0-1.1-.9-2-2-2zm0 18H4V8h16v13z"/></svg>');
}
You can actually get rather creative using the filter property.
invert(100%) turns the icon white
brightness(50%) makes it gray
sepia(100%) saturates it and makes it... sepia
saturate(10000%) pumps the saturation up and turns it bright red
After that you can play around with hue-rotate to change the hue. hue-rotate(240deg) turns it blue, hue-rotate(120deg) turns it green etc. If you want to get a really specific color you should check out this question on how to transform black into any given color using only CSS filters.
Another example is;
input[type="date"]::-webkit-calendar-picker-indicator {
cursor: pointer;
border-radius: 4px;
margin-right: 2px;
opacity: 0.6;
filter: invert(0.8);
}
input[type="date"]::-webkit-calendar-picker-indicator:hover {
opacity: 1
}
I just found out about this awesome fiddle. You input the color you need in hex, and it gives you your filter code. Very pratical: https://codepen.io/sosuke/pen/Pjoqqp.
The javascript to calculate it is:
'use strict';
class Color {
constructor(r, g, b) {
this.set(r, g, b);
}
toString() {
return `rgb(${Math.round(this.r)}, ${Math.round(this.g)}, ${Math.round(this.b)})`;
}
set(r, g, b) {
this.r = this.clamp(r);
this.g = this.clamp(g);
this.b = this.clamp(b);
}
hueRotate(angle = 0) {
angle = angle / 180 * Math.PI;
const sin = Math.sin(angle);
const cos = Math.cos(angle);
this.multiply([
0.213 + cos * 0.787 - sin * 0.213,
0.715 - cos * 0.715 - sin * 0.715,
0.072 - cos * 0.072 + sin * 0.928,
0.213 - cos * 0.213 + sin * 0.143,
0.715 + cos * 0.285 + sin * 0.140,
0.072 - cos * 0.072 - sin * 0.283,
0.213 - cos * 0.213 - sin * 0.787,
0.715 - cos * 0.715 + sin * 0.715,
0.072 + cos * 0.928 + sin * 0.072,
]);
}
grayscale(value = 1) {
this.multiply([
0.2126 + 0.7874 * (1 - value),
0.7152 - 0.7152 * (1 - value),
0.0722 - 0.0722 * (1 - value),
0.2126 - 0.2126 * (1 - value),
0.7152 + 0.2848 * (1 - value),
0.0722 - 0.0722 * (1 - value),
0.2126 - 0.2126 * (1 - value),
0.7152 - 0.7152 * (1 - value),
0.0722 + 0.9278 * (1 - value),
]);
}
sepia(value = 1) {
this.multiply([
0.393 + 0.607 * (1 - value),
0.769 - 0.769 * (1 - value),
0.189 - 0.189 * (1 - value),
0.349 - 0.349 * (1 - value),
0.686 + 0.314 * (1 - value),
0.168 - 0.168 * (1 - value),
0.272 - 0.272 * (1 - value),
0.534 - 0.534 * (1 - value),
0.131 + 0.869 * (1 - value),
]);
}
saturate(value = 1) {
this.multiply([
0.213 + 0.787 * value,
0.715 - 0.715 * value,
0.072 - 0.072 * value,
0.213 - 0.213 * value,
0.715 + 0.285 * value,
0.072 - 0.072 * value,
0.213 - 0.213 * value,
0.715 - 0.715 * value,
0.072 + 0.928 * value,
]);
}
multiply(matrix) {
const newR = this.clamp(this.r * matrix[0] + this.g * matrix[1] + this.b * matrix[2]);
const newG = this.clamp(this.r * matrix[3] + this.g * matrix[4] + this.b * matrix[5]);
const newB = this.clamp(this.r * matrix[6] + this.g * matrix[7] + this.b * matrix[8]);
this.r = newR;
this.g = newG;
this.b = newB;
}
brightness(value = 1) {
this.linear(value);
}
contrast(value = 1) {
this.linear(value, -(0.5 * value) + 0.5);
}
linear(slope = 1, intercept = 0) {
this.r = this.clamp(this.r * slope + intercept * 255);
this.g = this.clamp(this.g * slope + intercept * 255);
this.b = this.clamp(this.b * slope + intercept * 255);
}
invert(value = 1) {
this.r = this.clamp((value + this.r / 255 * (1 - 2 * value)) * 255);
this.g = this.clamp((value + this.g / 255 * (1 - 2 * value)) * 255);
this.b = this.clamp((value + this.b / 255 * (1 - 2 * value)) * 255);
}
hsl() {
// Code taken from https://stackoverflow.com/a/9493060/2688027, licensed under CC BY-SA.
const r = this.r / 255;
const g = this.g / 255;
const b = this.b / 255;
const max = Math.max(r, g, b);
const min = Math.min(r, g, b);
let h, s, l = (max + min) / 2;
if (max === min) {
h = s = 0;
} else {
const d = max - min;
s = l > 0.5 ? d / (2 - max - min) : d / (max + min);
switch (max) {
case r:
h = (g - b) / d + (g < b ? 6 : 0);
break;
case g:
h = (b - r) / d + 2;
break;
case b:
h = (r - g) / d + 4;
break;
}
h /= 6;
}
return {
h: h * 100,
s: s * 100,
l: l * 100,
};
}
clamp(value) {
if (value > 255) {
value = 255;
} else if (value < 0) {
value = 0;
}
return value;
}
}
class Solver {
constructor(target, baseColor) {
this.target = target;
this.targetHSL = target.hsl();
this.reusedColor = new Color(0, 0, 0);
}
solve() {
const result = this.solveNarrow(this.solveWide());
return {
values: result.values,
loss: result.loss,
filter: this.css(result.values),
};
}
solveWide() {
const A = 5;
const c = 15;
const a = [60, 180, 18000, 600, 1.2, 1.2];
let best = { loss: Infinity };
for (let i = 0; best.loss > 25 && i < 3; i++) {
const initial = [50, 20, 3750, 50, 100, 100];
const result = this.spsa(A, a, c, initial, 1000);
if (result.loss < best.loss) {
best = result;
}
}
return best;
}
solveNarrow(wide) {
const A = wide.loss;
const c = 2;
const A1 = A + 1;
const a = [0.25 * A1, 0.25 * A1, A1, 0.25 * A1, 0.2 * A1, 0.2 * A1];
return this.spsa(A, a, c, wide.values, 500);
}
spsa(A, a, c, values, iters) {
const alpha = 1;
const gamma = 0.16666666666666666;
let best = null;
let bestLoss = Infinity;
const deltas = new Array(6);
const highArgs = new Array(6);
const lowArgs = new Array(6);
for (let k = 0; k < iters; k++) {
const ck = c / Math.pow(k + 1, gamma);
for (let i = 0; i < 6; i++) {
deltas[i] = Math.random() > 0.5 ? 1 : -1;
highArgs[i] = values[i] + ck * deltas[i];
lowArgs[i] = values[i] - ck * deltas[i];
}
const lossDiff = this.loss(highArgs) - this.loss(lowArgs);
for (let i = 0; i < 6; i++) {
const g = lossDiff / (2 * ck) * deltas[i];
const ak = a[i] / Math.pow(A + k + 1, alpha);
values[i] = fix(values[i] - ak * g, i);
}
const loss = this.loss(values);
if (loss < bestLoss) {
best = values.slice(0);
bestLoss = loss;
}
}
return { values: best, loss: bestLoss };
function fix(value, idx) {
let max = 100;
if (idx === 2 /* saturate */) {
max = 7500;
} else if (idx === 4 /* brightness */ || idx === 5 /* contrast */) {
max = 200;
}
if (idx === 3 /* hue-rotate */) {
if (value > max) {
value %= max;
} else if (value < 0) {
value = max + value % max;
}
} else if (value < 0) {
value = 0;
} else if (value > max) {
value = max;
}
return value;
}
}
loss(filters) {
// Argument is array of percentages.
const color = this.reusedColor;
color.set(0, 0, 0);
color.invert(filters[0] / 100);
color.sepia(filters[1] / 100);
color.saturate(filters[2] / 100);
color.hueRotate(filters[3] * 3.6);
color.brightness(filters[4] / 100);
color.contrast(filters[5] / 100);
const colorHSL = color.hsl();
return (
Math.abs(color.r - this.target.r) +
Math.abs(color.g - this.target.g) +
Math.abs(color.b - this.target.b) +
Math.abs(colorHSL.h - this.targetHSL.h) +
Math.abs(colorHSL.s - this.targetHSL.s) +
Math.abs(colorHSL.l - this.targetHSL.l)
);
}
css(filters) {
function fmt(idx, multiplier = 1) {
return Math.round(filters[idx] * multiplier);
}
return `filter: invert(${fmt(0)}%) sepia(${fmt(1)}%) saturate(${fmt(2)}%) hue-rotate(${fmt(3, 3.6)}deg) brightness(${fmt(4)}%) contrast(${fmt(5)}%);`;
}
}
function hexToRgb(hex) {
// Expand shorthand form (e.g. "03F") to full form (e.g. "0033FF")
const shorthandRegex = /^#?([a-f\d])([a-f\d])([a-f\d])$/i;
hex = hex.replace(shorthandRegex, (m, r, g, b) => {
return r + r + g + g + b + b;
});
const result = /^#?([a-f\d]{2})([a-f\d]{2})([a-f\d]{2})$/i.exec(hex);
return result
? [
parseInt(result[1], 16),
parseInt(result[2], 16),
parseInt(result[3], 16),
]
: null;
}
$(document).ready(() => {
$('button.execute').click(() => {
const rgb = hexToRgb($('input.target').val());
if (rgb.length !== 3) {
alert('Invalid format!');
return;
}
const color = new Color(rgb[0], rgb[1], rgb[2]);
const solver = new Solver(color);
const result = solver.solve();
let lossMsg;
if (result.loss < 1) {
lossMsg = 'This is a perfect result.';
} else if (result.loss < 5) {
lossMsg = 'The is close enough.';
} else if (result.loss < 15) {
lossMsg = 'The color is somewhat off. Consider running it again.';
} else {
lossMsg = 'The color is extremely off. Run it again!';
}
$('.realPixel').css('background-color', color.toString());
$('.filterPixel').attr('style', result.filter);
$('.filterDetail').text(result.filter);
$('.lossDetail').html(`Loss: ${result.loss.toFixed(1)}. <b>${lossMsg}</b>`);
});
});
input[type="date"]::-webkit-calendar-picker-indicator {
filter: invert(1);
margin: 0px;
margin-right: 20px !important; }
For posterity, check out this Codepen that transforms black into any color through the filter property

svg rotate hexagon pattern - hexagon point to top

How do I rotate my pattern of hexagons so that the hexagon point is at the top and the pattern is consistent across the page
var SVG_NS = 'http://www.w3.org/2000/svg';
var SVG_XLINK = "http://www.w3.org/1999/xlink"
let H = 800, W=500
var R = 9;
//var l = R;
var h = R * Math.sin(Math.PI / 3);
var offset = 1.5 * R;
let i = 0;
for(let y = 0; y<H; y+=h){
i++
let o = (i%2 == 0) ? offset : 0;
for(let x = o; x<W; x+=3*R){
hex(x,y)
}
}
function hex(x,y) {
let angle = map(x, 0, W, 0, 5*Math.PI);
let c = Math.sin(angle);
let r = R * .99;
//let r = R * Math.sin(angle)
let points = ""
for (var a = 0; a < 6; a++) {
let o = {}
o.x = x + r * Math.cos(a * Math.PI / 3);
o.y = y + r * Math.sin(a * Math.PI / 3);
points+= `${o.x}, ${o.y} `
}
let hexagon = drawSVGelmt({points:points},"polygon", svg)
}
function drawSVGelmt(o,tag, parent) {
let elmt = document.createElementNS(SVG_NS, tag);
for (let name in o) {
if (o.hasOwnProperty(name)) {
elmt.setAttributeNS(null, name, o[name]);
}
}
parent.appendChild(elmt);
return elmt;
}
function map(n, a, b, _a, _b) {
let d = b - a;
let _d = _b - _a;
let u = _d / d;
return _a + n * u;
}
html, body {
height: 100%;
margin: 0;
background: #e20341;
}
svg {
}
polygon {
fill: white;
stroke: black;
stroke-width: 1px;
}
<svg viewBox="0 0 500 280" width="100%">
<defs>
<pattern id="hexagons" width="100%" height="100%" >
<g id="svg" fill="black" x="0" y="0"></g>
</pattern>
<mask id="hexagon-halftone-mask">
<rect x="0" y="0" width="100%" height="100%" fill="url(#hexagons)" />
</mask>
</defs>
<image width="100%" xlink:href="https://cdn.pixabay.com/photo/2016/09/07/11/37/tropical-1651426_960_720.jpg" mask="url(#hexagon-halftone-mask)"/>
</svg>
Here is the new code with comments:
var SVG_NS = 'http://www.w3.org/2000/svg';
var SVG_XLINK = "http://www.w3.org/1999/xlink"
let H = 800, W=500
var R = 9;
/* switch offset and h*/
var offset = R * Math.sin(Math.PI / 3);
var h = 1.5 * R;
let i = 0;
for(let y = 0; y<H; y+=h){
i++
let o = (i%2 == 0) ? offset : 0;
for(let x = o; x<W; x+=offset*2){ /*offset*2 instead of 3*R*/
hex(x,y)
}
}
function hex(x,y) {
let angle = map(x, 0, W, 0, 5*Math.PI);
let c = Math.sin(angle);
let r = R * .99;
let points = ""
for (var a = 0; a < 6; a++) {
let o = {}
o.x = x + r * Math.sin(a * Math.PI / 3); /* sin instead of cos */
o.y = y + r * Math.cos(a * Math.PI / 3); /* cos instead of sin */
points+= `${o.x}, ${o.y} `
}
let hexagon = drawSVGelmt({points:points},"polygon", svg)
}
function drawSVGelmt(o,tag, parent) {
let elmt = document.createElementNS(SVG_NS, tag);
for (let name in o) {
if (o.hasOwnProperty(name)) {
elmt.setAttributeNS(null, name, o[name]);
}
}
parent.appendChild(elmt);
return elmt;
}
function map(n, a, b, _a, _b) {
let d = b - a;
let _d = _b - _a;
let u = _d / d;
return _a + n * u;
}
html, body {
height: 100%;
margin: 0;
background: #e20341;
}
svg {
}
polygon {
fill: white;
stroke: black;
stroke-width: 1px;
}
<svg viewBox="0 0 500 280" width="100%">
<defs>
<pattern id="hexagons" width="100%" height="100%" >
<g id="svg" fill="black" x="0" y="0"></g>
</pattern>
<mask id="hexagon-halftone-mask">
<rect x="0" y="0" width="100%" height="100%" fill="url(#hexagons)" />
</mask>
</defs>
<image width="100%" xlink:href="https://cdn.pixabay.com/photo/2016/09/07/11/37/tropical-1651426_960_720.jpg" mask="url(#hexagon-halftone-mask)"/>
</svg>

getting y position from canvas is wrong

Sometimes the y-coordinates is greater than height of imagedata. can anybody help me to find my mistake!
Width is 320 px, height is 240px.
Here is my code:
function countPixels(context) {
var nAlive = 0,
all = [];
var w = canvas.width;
var p = context.getImageData(0, 0, canvas.width, canvas.height).data;
for (var y = 0, i = 0; y < canvas.height; y++)
for (var x = 0; x < canvas.width; x++, i += 4) {
if (p[i] == 255 || p[i + 1] == 255 || p[i + 2] == 255) //Not black
{
nAlive++;
var xc = i % w;
var yc = parseInt(i / w, 10);
var pos = {};
pos.x = xc;
pos.y = yc;
all.push(pos);
}
}
var percent = ((canvas.width * canvas.height) / 100) * nAlive;
console.log("Count: " + nAlive + ",percent: " + percent + ",all: " + JSON.stringify(all));
// $("#notifies").append("Count: "+nAlive+",percent: "+ percent+",all: "+JSON.stringify(all));
return {
percentage: parseFloat(percent),
positions: all
};
}
Here is the function call:
var tmp = countPixels(ctx2);
ctx2.strokeStyle = "blue";
$.each(tmp.positions, function(i, value) {
// if (ctx2.isPointInPath(value.x, value.y))
$('div').eq(0).append("i: " + i + " " + value.x + ", " + +value.y + '</br>');
ctx2.rect(value.x, value.y, 5, 5);
});
ctx2.stroke();