пятница, 6 января 2012 г.

Использование GWT Canvas

     Спецификация HTML 5 включает множество новых ф-ций, одной из которых является тег canvas. Он позволяет выводить графику и рисовать с использованием JavaScript. В GWT 2.2 была добавлена поддержка HTML5 Canvas елемента. 
     Canvas предоставляет такие инструменты как: 
- рисование: прямоугольников, дуг, линий и др. 
- эффекты: тени, прозрачность... 
- преобразования: масштабирование, вращение, трансформирование... 
     В пакете com.google.gwt.canvas содержится множество полезных классов для манипулирования полотном. Но перед тем как будет загружен модуль мы должны инициализировать canvas, если он поддерживается браузером.
canvas = Canvas.createIfSupported();
if (canvas == null) {
    RootPanel.get().add(new Label("Sorry, your browser doesn't support the HTML5 Canvas element"));
    return;
}


* This source code was highlighted with Source Code Highlighter.
     Если браузер не имеет поддержки HTML 5, то выводим метку с сообщением. 
Напишем пример аналоговых часов на GWT используя Canvas.
/**
* @author Dmitry Nikolaenko
*/
public class CanvasGwtApp implements EntryPoint {

    /**
     * update canvas based on interval
     */
    private static final int REFRESH_RATE = 1000;

    private static final int CANVAS_HEIGHT = 300;
    private static final int CANVAS_WIDTH = 300;

    private Canvas canvas;
    private Context2d context;

    public void onModuleLoad() {
    canvas = Canvas.createIfSupported();
    if (canvas == null) {
        RootPanel.get().add(new Label("Sorry, your browser doesn't support the HTML5 Canvas element"));
        return;
    }

        canvas.setWidth(CANVAS_WIDTH + Unit.PX.getType());
        canvas.setCoordinateSpaceWidth(CANVAS_WIDTH);
        canvas.setHeight(CANVAS_HEIGHT + Unit.PX.getType());
        canvas.setCoordinateSpaceHeight(CANVAS_HEIGHT);

        context = canvas.getContext2d();
        RootPanel.get().add(canvas);

        final Timer timer = new Timer() {
            @Override
            public void run() {
                updateClock(JsDate.create());
            }
        };
        timer.scheduleRepeating(REFRESH_RATE);
    }

    private void updateClock(JsDate date) {
        context.save();
        context.clearRect(0, 0, CANVAS_WIDTH, CANVAS_HEIGHT);
        context.translate(CANVAS_WIDTH / 2, CANVAS_HEIGHT / 2);
        context.scale(0.9, 0.9);
        context.rotate(-Math.PI / 2);
        context.setStrokeStyle("black");
        context.setLineWidth(4);
        context.setLineCap("round");

        // draw hour marks
        context.save();
        for (int i = 0; i < 12; i++) {
            context.rotate(Math.PI / 6);
            drawClockLine(120, 130);
        }
        context.restore();

        // draw minute marks
        context.save();
        context.setLineWidth(2);
        for (int i = 0; i < 60; i++) {
            if (i % 5 != 0) {
                drawClockLine(127, 130);
            }
            context.rotate(Math.PI / 30);
        }
        context.restore();

        // define current time
        long sec = date.getSeconds();
        long min = date.getMinutes();
        long hr = date.getHours();
        hr = hr >= 12 ? hr - 12 : hr;

        // write hours, save the context's state
        context.save();
        context.rotate(hr * (Math.PI / 6) + (Math.PI / 360) * min
                + (Math.PI / 21600) * sec);

        // draw the hour hands
        context.setLineWidth(6);
        drawClockLine(-20, 90);
        context.restore();

        // write minutes
        context.save();
        context.rotate((Math.PI / 30) * min + (Math.PI / 1800) * sec);

        // draw the minute hands
        context.setLineWidth(5);
        drawClockLine(-28, 112);
        context.restore();

        // write seconds
        context.save();
        context.rotate(sec * Math.PI / 30);

        context.setFillStyle(getRandomColor());
        context.setLineWidth(2);
        drawClockLine(-30, 105);

        // draw the circle at the end of seconds-hand
        context.beginPath();
        context.arc(0, 0, 10, 0, Math.PI * 2, true);
        context.fill();
        context.beginPath();
        context.arc(90, 0, 6, 0, Math.PI * 2, true);
        context.fill();
        context.stroke();
        context.closePath();
        context.setFillStyle(getRandomColor());
        context.beginPath();
        context.arc(0, 0, 3, 0, Math.PI * 2, true);
        context.fill();
        context.restore();

        // draw the main arc of the clock
        context.beginPath();
        context.setLineWidth(4);
        context.setStrokeStyle("#A25A94");
        context.arc(0, 0, 142, 0, Math.PI * 2, true);
        context.stroke();
        context.restore();
    }

    /**
     * draw the line - clock hands
     */
    private void drawClockLine(int from, int to) {
        context.beginPath();
        context.moveTo(from, 0);
        context.lineTo(to, 0);
        context.stroke();
    }

    /**
     * generate random color
     */
    private CssColor getRandomColor() {
        int redColor = Random.nextInt(255);
        int greenColor = Random.nextInt(255);
        int blueColor = Random.nextInt(255);

        // with alpha transparency
        // CssColor randomColor = CssColor.make("rgba(" + redColor + ", " +
        //        greenColor + "," + blueColor + ", " + Random.nextDouble() + ")");

        return CssColor.make(redColor, greenColor, blueColor);
    }
}


* This source code was highlighted with Source Code Highlighter.
Вот так выглядит запущенный пример:


Комментариев нет:

Отправить комментарий