001/**
002 *
003 * Copyright the original author or authors
004 *
005 * Licensed under the Apache License, Version 2.0 (the "License");
006 * you may not use this file except in compliance with the License.
007 * You may obtain a copy of the License at
008 *
009 *     http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017package org.jivesoftware.smackx.jingle.mediaimpl.sshare.api;
018
019import java.awt.*;
020import java.awt.image.BufferedImage;
021import java.io.ByteArrayInputStream;
022import java.io.IOException;
023import java.net.DatagramPacket;
024import java.net.DatagramSocket;
025import java.net.InetAddress;
026import java.net.SocketException;
027
028/**
029 * UDP Image Receiver.
030 * It uses PNG Tiles into UDP packets.
031 *
032 * @author Thiago Rocha Camargo
033 */
034public class ImageReceiver extends Canvas {
035
036        private static final long serialVersionUID = -7000112305305269025L;
037        private boolean on = true;
038    private DatagramSocket socket;
039    private BufferedImage tiles[][];
040    private static final int tileWidth = ImageTransmitter.tileWidth;
041    private InetAddress localHost;
042    private InetAddress remoteHost;
043    private int localPort;
044    private int remotePort;
045    private ImageDecoder decoder;
046
047    public ImageReceiver(final InetAddress remoteHost, final int remotePort, final int localPort, int width, int height) {
048        tiles = new BufferedImage[width][height];
049
050        try {
051
052            socket = new DatagramSocket(localPort);
053            localHost = socket.getLocalAddress();
054            this.remoteHost = remoteHost;
055            this.remotePort = remotePort;
056            this.localPort = localPort;
057            this.decoder = new DefaultDecoder();
058
059            new Thread(new Runnable() {
060                public void run() {
061                    byte buf[] = new byte[1024];
062                    DatagramPacket p = new DatagramPacket(buf, 1024);
063                    try {
064                        while (on) {
065                            socket.receive(p);
066
067                            int length = p.getLength();
068
069                            BufferedImage bufferedImage = decoder.decode(new ByteArrayInputStream(p.getData(), 0, length - 2));
070
071                            if (bufferedImage != null) {
072
073                                int x = p.getData()[length - 2];
074                                int y = p.getData()[length - 1];
075
076                                drawTile(x, y, bufferedImage);
077
078                            }
079
080                        }
081                    }
082                    catch (IOException e) {
083                        e.printStackTrace();
084                    }
085                }
086            }).start();
087
088            new Thread(new Runnable() {
089                public void run() {
090                    byte buf[] = new byte[1024];
091                    DatagramPacket p = new DatagramPacket(buf, 1024);
092                    try {
093                        while (on) {
094
095                            p.setAddress(remoteHost);
096                            p.setPort(remotePort);
097                            socket.send(p);
098
099                            try {
100                                Thread.sleep(1000);
101                            }
102                            catch (InterruptedException e) {
103                                e.printStackTrace();
104                            }
105
106                        }
107                    }
108                    catch (IOException e) {
109                        e.printStackTrace();
110                    }
111                }
112            }).start();
113
114        }
115        catch (SocketException e) {
116            e.printStackTrace();
117        }
118        this.setSize(width, height);
119    }
120
121    public InetAddress getLocalHost() {
122        return localHost;
123    }
124
125    public InetAddress getRemoteHost() {
126        return remoteHost;
127    }
128
129    public int getLocalPort() {
130        return localPort;
131    }
132
133    public int getRemotePort() {
134        return remotePort;
135    }
136
137    public DatagramSocket getDatagramSocket() {
138        return socket;
139    }
140
141    public void drawTile(int x, int y, BufferedImage bufferedImage) {
142        tiles[x][y] = bufferedImage;
143        //repaint(x * tileWidth, y * tileWidth, tileWidth, tileWidth);
144        this.getGraphics().drawImage(bufferedImage, tileWidth * x, tileWidth * y, this);
145    }
146
147    public void paint(Graphics g) {
148        for (int i = 0; i < tiles.length; i++) {
149            for (int j = 0; j < tiles[0].length; j++) {
150                g.drawImage(tiles[i][j], tileWidth * i, tileWidth * j, this);
151            }
152        }
153    }
154
155    public ImageDecoder getDecoder() {
156        return decoder;
157    }
158
159    public void setDecoder(ImageDecoder decoder) {
160        this.decoder = decoder;
161    }
162
163    public void stop(){
164        this.on=false;
165        socket.close();
166    }
167}