I am currently trying to make a cooldown effect similar to the ones you can see in World of Warcraft. (See the square with the 2m text on it? The idea is to have the square ''lighten'' in a circular manner, also illustrated in at 0:23.). I am using GWT, so I am mainly looking for a means to do this using pure CSS and/or javascript.
To achieve this, I only need to be able to create a square image similar to the dark area in 1. I could then apply this image in overlay to my main image, and use a timer to make the illusion of mouvement.
However I am at a loss as to how to create such an image. It seems possible to create shapes using CSS only, but I could not understand if, and how, creating what I needed was possible.
I also found something that uses Silverlight, but it is not an option for me.
I am not sure I have expressed my need clearly enough. If that were the case, I'd be more than happy to add clarifications.
Thanks in advance for any hint,
Sébastien Tromp
I am currently trying to make a cooldown effect similar to the ones you can see in World of Warcraft. (See the square with the 2m text on it? The idea is to have the square ''lighten'' in a circular manner, also illustrated in http://www.youtube./watch?v=R51QXmkyelQ at 0:23.). I am using GWT, so I am mainly looking for a means to do this using pure CSS and/or javascript.
To achieve this, I only need to be able to create a square image similar to the dark area in 1. I could then apply this image in overlay to my main image, and use a timer to make the illusion of mouvement.
However I am at a loss as to how to create such an image. It seems possible to create shapes using CSS only, but I could not understand if, and how, creating what I needed was possible.
I also found something that uses Silverlight, but it is not an option for me.
I am not sure I have expressed my need clearly enough. If that were the case, I'd be more than happy to add clarifications.
Thanks in advance for any hint,
Sébastien Tromp
4 Answers
Reset to default 6This is what I came up with. Basically what it does is, it encapsulates an image and a 0.5 opacity canvas on top of each other in a posite widget. The animation draws lines on the canvas from the center towards the edges in a circular fashion in a given time interval. Canvas has a clickHandler to start the animation. Hope it helps. It uses GWT Canvas so this widget may not be supported on all browsers.
Class CoolDownAnimation :
public class CoolDownAnimation extends Animation {
Canvas canvas;
Context2d context;
int centerX;
int centerY;
static final CssColor BLACK = CssColor.make("rgba(0,0,0,0.6)");
static final CssColor WHITE = CssColor.make("rgba(255,255,255,0.6)");
public CoolDownAnimation(Canvas canvas) {
this.canvas = canvas;
canvas.setCoordinateSpaceHeight(20);
canvas.setCoordinateSpaceWidth(20);
canvas.getElement().getStyle().setOpacity(0.5);
this.context = canvas.getContext2d();
centerX = canvas.getCoordinateSpaceWidth() / 2;
centerY = canvas.getCoordinateSpaceHeight() / 2;
}
@Override
protected void onStart() {
context.beginPath();
context.setStrokeStyle(BLACK);
context.fillRect(0, 0, centerX * 2, centerY * 2);
context.setStrokeStyle(WHITE);
super.onStart();
}
@Override
protected void onUpdate(double progress) {
context.moveTo(centerX, centerY);
context.lineTo(
centerX + 2 * centerX * Math.cos((progress * Math.PI * 2)-Math.PI/2),
centerY + 2 * centerY * Math.sin((progress * Math.PI * 2)-Math.PI/2));
context.stroke();
}
@Override
protected void onComplete() {
super.onComplete();
context.closePath();
context.clearRect(0, 0, centerX*2, centerY*2);
}
}
Class CoolDownWidget :
public class CoolDownWidget extends Composite {
private CoolDownAnimation coolDown;
private AbsolutePanel wrapper;
private Image image;
private Canvas canvas;
private int sizeX = 50;
private int sizeY = 50;
private int coolDownDuration = 5000;
public CoolDownWidget(){
canvas = Canvas.createIfSupported();
if (canvas==null){
Window.alert("Fail! You dont have canvas support");
}
canvas.getElement().getStyle().setOpacity(0.5);
canvas.setPixelSize(sizeX,sizeY);
coolDown = new CoolDownAnimation(canvas);
image = new Image("images/icon.png");
image.setPixelSize(sizeX, sizeY);
canvas.addClickHandler(new ClickHandler() {
@Override
public void onClick(ClickEvent event) {
coolDown.cancel();
coolDown.run(coolDownDuration);
}
});
wrapper = new AbsolutePanel();
wrapper.setPixelSize(sizeX, sizeY);
wrapper.add(image, 0, 0);
wrapper.add(canvas,0,0);
initWidget(wrapper);
}
}
finally onModuleLoad to wrap things up :
public void onModuleLoad() {
RootPanel.get().add(new CoolDownWidget());
}
This is a javascript/css version that uses jquery.
Find the live version http://codepen.io/anon/pen/aZzNbY.
<html>
<head>
<script src="https://code.jquery./jquery-2.2.4.min.js"></script>
<style type="text/css">
.box{
width:128px;
height:128px;
background-color:black;
overflow:hidden;
padding:5px;
border:4px solid #ddd;
border-radius:12px;
position:relative;
}
input[type="submit"] {
width: 100%;
height: 100%;
border: 0;
background: url('http://icons.iconseeker./png/fullsize/smoothicons-12/warcraft-1.png') no-repeat ;
}
.cooldown{
position:absolute;
top:5%;
left:5%;
width:90%;
height:90%;
overflow:hidden;
opacity:0;
}
.cooldown-half{
width:50%;
height:100%;
overflow:hidden;
position:relative;
float:left;
}
.cooldown-half-rotator{
width:200%;
height:200%;
top:-50%;
position:absolute;
background-color:rgba(1,1,1,0.5);
}
.cooldown-half-rotator-right{
transform-origin:left center;
}
.cooldown-half-rotator-left{
right:0;
transform-origin:right center;
}
</style>
</head>
<body>
<div class='box'>
<input type="submit" value="" ><div></div></input>
<div class='cooldown'>
<div class='cooldown-half'>
<div class='cooldown-half-rotator cooldown-half-rotator-left'>
</div>
</div>
<div class='cooldown-half'>
<div class='cooldown-half-rotator cooldown-half-rotator-right'>
</div>
</div>
</div>
</div>
Click me
<script>
function setCooldown( time, stopper ){
$(".cooldown").css({"opacity":1});
$(".cooldown-half-rotator-right").css({
"transform":"rotate(180deg)",
"transition":"transform "+(time/2000)+"s",
"transition-timing-function":"linear"
});
setTimeout( function(){
$(".cooldown-half-rotator-left").css({
"transform":"rotate(180deg)",
"transition":"transform "+(time/2000)+"s",
"transition-timing-function":"linear"
});
setTimeout( function(){
$(".cooldown-half-rotator-right").css({"transform":"rotate(0deg)","transition":"transform 0s"});
$(".cooldown-half-rotator-left").css({"transform":"rotate(0deg)","transition":"transform 0s"});
$(".cooldown").css({"opacity":0});
}, time/2 );
}, time/2 );
}
window.onload = function(){
$(".box").click(function(){
setCooldown( 3000 );
});
}
</script>
</body>
</html>
you could use Jquery rotate
Look at example 3
Alternatively: you could divide the square into little pie-slices (a bit hard to see, but like this pizza). Make a transparant image for each one, and just show/hide them in order one by one using jquery. This is probably the easiest and fastest solution.
Another variation on the solution proposed by pistolPanties for the onUpdate() method:
this.context.clearRect(0, 0, this.width, this.height);
// Black background
this.context.setFillStyle(BLACK);
this.context.fillRect(0, 0, this.width, this.height);
// White to show the progress
this.context.setFillStyle(WHITE);
this.context.beginPath();
this.context.moveTo(this.centerX, this.centerY);
this.context.arc(this.centerX, this.centerY, this.width, -Math.PI / 2, 2 * Math.PI * progress - Math.PI / 2, false);
this.context.lineTo(this.centerX, this.centerY);
this.context.fill();
this.context.closePath();
The advantage it has is that it delimitates the full portion to render as White, and fills it. This ensures that the area is always properly colored - and thus more resilient to browser slow downs.