New here. I am a sys-admin with medium experience with html/css/php. I've worked on modX, Wordpress and Joomla in the past, and now my boss wants something that requires javascript or jquery knowledge (less than basic in my case).
Problem description: .x-container is with fluid height and .x-column also, .ult-new has fixed height 230px with margin set in css (20px) and position relative. x-column has width: 22% and position relative and margin-right: 4%. And i need to display randomly each ult-new inside each x-column (inside each x-container). Those elements are created dynamically with php and shortcodes. So i need to vertically position them in random places in those columns and relative to each other (with 20px margin top and bottom).
As i understand i need to count the height of each x-column and than count the number of .ult-new elements in each of those columns. And than i need to posiotion those elements as absolute and do some math (first will be 0px from the top plus 20px margin, and then second element needs to be 230px from the top plus 20px margin top etc).
How do i translate this to javascript? Is there something else i don't see? :)
<div class"x-container">
<div class="x-column">
<div class="ult-new">
<!--some code here (text, hyperllinks etc)-->
</div>
<div class="ult-new">
</div>
<div class="ult-new">
</div>
<!--some code here (text, hyperllinks etc)-->
</div>
<div class="x-column">
<div class="ult-new">
</div>
<div class="ult-new">
</div>
<div class="ult-new">
</div>
</div>
<!--and many more x-column-->
</div>
<div class"x-container">
<div class="x-column">
<div class="ult-new">
</div>
<div class="ult-new">
</div>
<div class="ult-new">
</div>
</div>
<div class="x-column">
<div class="ult-new">
</div>
<div class="ult-new">
</div>
<div class="ult-new">
</div>
</div>
</div>
<!--and many more x-container-->
I may not fully understand what your doing but the best information i can give you is this jquery. now your gonna have to do some of the work to configure it but i believe in you!
var x; // move horizontal
var y; // move vertical
$('.YOURCLASS').css({"width":"50px","margin","50px","position":"absolute","transform":`translateX(${x})`,"transform":`translateY(${Y})`}) //sets styles
$('.YOURCLASS').css("width") // gives the width of element
var randomnum = Math.floor((Math.random() * 10) + 1); // random number 1-10
y = randomnum
x = randomnum
// use position:absolute then pass x,y in
Related
I am trying to set elements (children of a container with transform) to fixed position relative to the viewport. I'm attempting to find each of them, and assign to a variable via getBoundingClientRect(), then define style properties from that variable.
<div>
<div class="preview-container">
<div>
<!-- Image -->
</div>
</div>
</div>
<div>
<div class="preview-container">
<div>
<!-- Image -->
</div>
</div>
</div>
<!-- more -->
JS v1
$('.preview-container').each(function(el) {
preview = this.getBoundingClientRect();
console.log(preview);
preview.style.position = "fixed";
preview.style.top = "0";
preview.style.left = "0";
});
This works without the three style lines and console displays all of the .preview-container elements correctly. Adding the style lines produces errors about those style properties not being defined:
jQuery.Deferred exception: Cannot set properties of undefined (setting 'position')
Uncaught TypeError: Cannot set properties of undefined (setting 'position')
I don't understand that because preview is working in console.
JS v2
This attempt works as is, but is less complete. console is producing all of the .preview-container elements, but I haven't been able to incorporate getBoundingClientRect():
document.querySelectorAll(".preview-container").forEach(preview => {
preview.style.position = "fixed";
preview.style.top = "0";
preview.style.left = "0";
console.log(preview);
});
I feel like I am closer with JS v1, and am missing something simple with the style properties. How should I proceed?
You have a problem with the name of your variables, in the first one you call it el and you refer as preview. And to get the values of getBoundingClientRect you need to create another variable.
document.querySelectorAll(".preview-container").forEach(preview => {
previewValues = preview.getBoundingClientRect();
preview.style.position = "fixed";
preview.style.top = "0";
preview.style.left = "0";
console.log(preview);
console.log(previewValues);}
)
<div>
<div class="preview-container">
<div>
<!-- Image -->
</div>
</div>
</div>
<div>
<div class="preview-container">
<div>
<!-- Image -->
</div>
</div>
</div>
<!-- more -->
Looking at the interfaces for DOMRect (there are several), it states that updating properties of a DOMRect updates the position of the element it was called on, as in this example:
"use strict";
$('.preview-container').each(function(el) {
var rect = this.getBoundingClientRect();
this.style.position = "fixed";
// this.style.top = "0";
rect.x = 0;
// this.style.left = "0";
rect.y = 0;
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.6.0/jquery.min.js"></script>
<!-- body-html -->
<div>
<div class="preview-container">
<div>
Image 1
</div>
</div>
</div>
<div>
<div class="preview-container">
<div>
Image 2
</div>
</div>
</div>
Note
this has been used to refer to preview divisions in the each argument function, not el.
Changes to position are made by setting properties of rect, not style, as allowed in the standard, but this is uncommon.
Usually positions are set either in CSS, or using element style objects (the this.style lines commented out above), without calling getBoundingClientRect to obtain a DOMRect first.
However when an element descends from an element with a transform property, the transform element behaves as the containing block for fixed elements below as shown here:
$('.preview-container').each(function(el) {
this.style.position = "fixed";
this.style.top = "0";
this.style.left = "0";
});
/* CSS from https://developer.mozilla.org/en-US/docs/Web/CSS/transform */
div.ancestor {
border: solid red;
transform: translate(30px, 20px) rotate(20deg);
width: 140px;
height: 60px;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.6.0/jquery.min.js"></script>
<!-- body-html -->
<div class="ancestor">
<div class="preview-container">
<div>
Image 1
</div>
</div>
</div>
<div class="ancestor">
<div class="preview-container">
<div>
Image 2
</div>
</div>
</div>
If you want to fix preview container positioning relative to the view port, try moving them out from under the transform ancestor by, say, appending them to the body element. If aspects of the transform operation need to be retained on moved preview containers, a suitable CSS transform would need to be separately applied to them after the move.
Using css and html I created 13 objects that look like boxes that each have a unique background color. Then added some random color changing functionality with javascript.
What I wanted to happen: after you click any of the 13 boxes, every box turns a 'new' color. This 'new' color will be randomly chosen from the initially fixed colors for each box. And this would go on forever.
What happened: when clicking boxes they do change color like I wanted, but after clicking only ~5-10 times they would have all turned the exact same color.
How do I get the function to keep on going and not stop at a certain color?
I probably messed up the for loop/all of javascript but can't figure it out. Any help greatly appreciated.
Here's my full code: https://codepen.io/zaemees/pen/roGgGV
Some code:
html:
<div class="aqua1 specs"></div>
<div class="chartreuse1 specs"></div>
<div class="deeppink1 specs"></div>
<div class="dodgerblue1 specs"></div>
<div class="gold1 specs"></div>
<div class="indigo1 specs"> </div>
<div class="lightpink1 specs"></div>
<div class="mediumpurple1 specs"></div>
<div class="coral1 specs"></div>
<div class="springgreen1 specs"></div>
<div class="red1 specs"></div>
<div class="peachpuff1 specs"></div>
<div class="deepskyblue1 specs"></div>
js:
var bloop = document.getElementsByClassName('specs');
for (var i = 0; i < bloop.length; i++){
bloop[i].onclick = function() {
for (var i = 0; i < bloop.length; i++){
bloop[i].style.backgroundColor = window.getComputedStyle(bloop[Math.floor(Math.random()*13)]).getPropertyValue('background-color');
}
}
}
Your code's main problem is that you are not preventing the same color from being selected multiple times. When you run it the first time, there is a high likelihood that at least one of your colors will be chosen twice. Think of it as simply selecting a number between one and ten at random. It is very difficult to randomly choose a different number ten times and never repeat.
Therefore, when you run your function again you have changed the backgroundColor property of each box, and some of them will have the same color, i.e. you do not have 13 different colors to choose from anymore. This means the second time your function runs you have fewer choices, and this continues and continues until you end up with only one or two possible colors to choose and every box ends up with the same color.
One way to prevent this is to have an array of your choices and remove your choice from the array whenever you select it. This will prevent duplicates, and is how most card dealing programs work so two people don't both get dealt a queen of hearts. Try this example:
var bloop = document.getElementsByClassName('specs');
for (var i = 0; i < bloop.length; i++) {
bloop[i].onclick = function() {
var colours = ['aqua','chartreuse','deeppink','dodgerblue','gold','indigo','lightpink','mediumpurple','coral','springgreen','red','peachpuff','deepskyblue'];
for (var i = 0; i < bloop.length; i++) {
var rando = Math.floor(Math.random()*colours.length)
bloop[i].style.backgroundColor = colours[rando];
colours.splice(rando, 1);
}
}
}
.specs{
display:inline-block;
height:100px;
width:100px;
border:3px solid white;
}
.aqua1{
background-color:aqua;
}
.chartreuse1{
background-color:chartreuse;
}
.deeppink1{
background-color:deeppink;
}
.dodgerblue1{
background-color:dodgerblue;
}
.gold1{
background-color:gold;
}
.indigo1{
background-color:indigo;
}
.lightpink1{
background-color:lightpink;
}
.mediumpurple1{
background-color:mediumpurple;
}
.coral1{
background-color:coral;
}
.springgreen1{
background-color:springgreen;
}
.red1{
background-color:red;
}
.peachpuff1{
background-color:peachpuff;
}
.deepskyblue1{
background-color:deepskyblue;
}
<div class="aqua1 specs">
</div>
<div class="chartreuse1 specs">
</div>
<div class="deeppink1 specs">
</div>
<div class="dodgerblue1 specs">
</div>
<div class="gold1 specs">
</div>
<div class="indigo1 specs">
</div>
<div class="lightpink1 specs">
</div>
<div class="mediumpurple1 specs">
</div>
<div class="coral1 specs">
</div>
<div class="springgreen1 specs">
</div>
<div class="red1 specs">
</div>
<div class="peachpuff1 specs">
</div>
<div class="deepskyblue1 specs">
</div>
I'm not sure I completely understand this code, but from what I do comprehend, you are using the variable 'i' twice in both for loops. I don't know if this is intentional, but changing the nested variable 'i' to a 'j' should do the job. I hope that helps!
<div class="row" data-ng-repeat="row in imageDataUrls" >
<div class="col-sm-3" data-ng-repeat="imageDataUrl in row" >
<img alt="img" class="img-responsive"data-ng-src="{{imageDataUrl.url}}" />
</div>
</div>
I am showing the image using data URLs, but how can I get the current height and width in pixel to resize it proportionally in angular js?
I have some algorithm to resize it independently
I'm not sure what data imageDataUrl has in it but you can get the image dimensions in JavaScript easily:
var img = new Image();
img.onload = function() {
console.log(this.width + 'x' + this.height);
}
img.src = 'http://lorempixel.com/400/200/';
as pointed by mvermand comment, you can just add CSS to your class or directly height/width attributes.
<div class="row" data-ng-repeat="row in imageDataUrls" >
<div class="col-sm-3" data-ng-repeat="imageDataUrl in row" >
<img alt="img" class="img-responsive" src="https://upload.wikimedia.org/wikipedia/commons/thumb/e/e0/SNice.svg/2000px-SNice.svg.png" width="300"/>
</div>
</div>
If using only height or width, the other attribute is calculated to respect the image proportions.
Now, regarding the size you want, you can also use percents - like width="100%" to use the full width.
Cheers
If your goal is to resize proportionally, why not resize using CSS percentages?
CSS:
.smaller {
width: 80%;
}
Your Code:
<div class="row" data-ng-repeat="row in imageDataUrls" >
<div class="col-sm-3" data-ng-repeat="imageDataUrl in row" >
<img alt="img" class="img-responsive smaller" data-ng-src="{{imageDataUrl.url}}" />
</div>
</div>
you can get/set the height and width properties with angular.element("selector").height or width.
I am basically trying to build a 3D Cube and having trouble with the translateZ property. I want to get the width of the browser and store it into the translateZ for a particular element. This will create the 3D cube responsive even when the browser is being re-sized. I want it to store the value as it works with the .auto-size
resizeDiv();
window.onresize = function(event) {
resizeDiv();
}
function resizeDiv() {
vpw = $(window).width();
vph = $(window).height();
$('.auto-size').css({'height': vph + 'px', 'width': vpw + 'px'});
$('.full-z').css({'transform': 'translateZ' ( vpw + 'px' ); });
}
The translateZ value is given to a css class so i can use that multiple times for different divs. My markup is as follows
<div class="viewport">
<div class="cube">
<div class="cube-side1 auto-size cube-face" id="front">
</div>
<div class="cube-side2 auto-size cube-face full-z" id="back">
</div>
<div class="cube-side3 auto-size cube-face" id="left">
</div>
<div class="cube-side4 auto-size cube-face" id="right">
</div>
<div class="cube-side5 auto-size cube-face" id="top">
</div>
<div class="cube-side6 auto-size cube-face" id="bottom">
</div>
</div>
</div>
It works with the widths and heights but not with the transform property. I have very little knowledge of jQuery.
I don't know what am I doing wrong.. but I have 3 columns where I want to apply equal heights
here is my html
<div id="wrapper">
<div class="LeftBG"></div>
<div id="MainBlock">THIS IS A TEST</div>
<div class="RightBG"></div>
<!-- END CONTENT BLOCK -->
</div>
and here is my function and just doesn't work....
var highestCol = Math.max(
$('.LeftBG').height(),
$('.RightBG').height());
$('#MainBlock').height(highestCol);
To see what I am doing click here
Change your code to this to set all three blocks to the same height:
var highestCol = Math.max(
$('.RightBG').height(),
$('.LeftBG').height());
$('#MainBlock, .RightBG, .LeftBG').height(highestCol);
See it here: http://jsfiddle.net/jfriend00/Rv4fr/
What you did fixes the middle column, now apply it to the other classes as well...
var highestCol = Math.max(
$('.RightBG').height(),
$('.LeftBG').height());
$('#MainBlock').height(highestCol);
$('.RightBG').height(highestCol);
$('.LeftBG').height(highestCol);