Jump to content
  • Advertisement

Search the Community

Showing results for tags 'Java'.

The search index is currently processing. Current results may not be complete.


More search options

  • Search By Tags

    Type tags separated by commas.
  • Search By Author

Content Type


Categories

  • Audio
    • Music and Sound FX
  • Business
    • Business and Law
    • Career Development
    • Production and Management
  • Game Design
    • Game Design and Theory
    • Writing for Games
    • UX for Games
  • Industry
    • Interviews
    • Event Coverage
  • Programming
    • Artificial Intelligence
    • General and Gameplay Programming
    • Graphics and GPU Programming
    • Engines and Middleware
    • Math and Physics
    • Networking and Multiplayer
  • Visual Arts
  • Archive

Categories

  • Audio
  • Visual Arts
  • Programming
  • Writing

Categories

  • Game Dev Loadout
  • Game Dev Unchained

Categories

  • Game Developers Conference
    • GDC 2017
    • GDC 2018
  • Power-Up Digital Games Conference
    • PDGC I: Words of Wisdom
    • PDGC II: The Devs Strike Back
    • PDGC III: Syntax Error

Forums

  • Audio
    • Music and Sound FX
  • Business
    • Games Career Development
    • Production and Management
    • Games Business and Law
  • Game Design
    • Game Design and Theory
    • Writing for Games
  • Programming
    • Artificial Intelligence
    • Engines and Middleware
    • General and Gameplay Programming
    • Graphics and GPU Programming
    • Math and Physics
    • Networking and Multiplayer
  • Visual Arts
    • 2D and 3D Art
    • Art Critique and Feedback
  • Community
    • GameDev Challenges
    • GDNet+ Member Forum
    • GDNet Lounge
    • GDNet Comments, Suggestions, and Ideas
    • Coding Horrors
    • Your Announcements
    • Hobby Project Classifieds
    • Indie Showcase
    • Article Writing
  • Affiliates
    • NeHe Productions
    • AngelCode
  • Topical
    • Virtual and Augmented Reality
    • News
  • Workshops
    • C# Workshop
    • CPP Workshop
    • Freehand Drawing Workshop
    • Hands-On Interactive Game Development
    • SICP Workshop
    • XNA 4.0 Workshop
  • Archive
    • Topical
    • Affiliates
    • Contests
    • Technical
  • GameDev Challenges's Topics
  • For Beginners's Forum
  • Unreal Engine Users's Unreal Engine Group Forum
  • Unity Developers's Forum
  • Unity Developers's Asset Share

Calendars

  • Community Calendar
  • Games Industry Events
  • Game Jams
  • GameDev Challenges's Schedule

Blogs

There are no results to display.

There are no results to display.

Product Groups

  • Advertisements
  • GameDev Gear

Find results in...

Find results that contain...


Date Created

  • Start

    End


Last Updated

  • Start

    End


Filter by number of...

Joined

  • Start

    End


Group


About Me


Website


Role


Twitter


Github


Twitch


Steam

Found 90 results

  1. I'm working on my first Android game and I have a few questions. I need to scale the graphics for different screen sizes/resolutions. I'm working in 16:9 and plan to use letter boxing to maintain this aspect ratio. Everything is fine for standard screen resolutions. Going from 320:180 to 640:360, one pixel just becomes four. I'm a little confused though as to what happens when you letterbox on a screen with a unusual resolution. Say, just for exsample, my original graphics are 160:90. Then to fit the devise I stretch everything by 1.1 and end up with a final resolution of 176:99. Its still 16:9 but now everything is a mess. If I had a sprite that used to be at x-33 y-33 it's new location would now be at x-36.3 y-36.3. Would I just drop the 0.3 of a pixel, round down and accept that it's no longer in its exact position? Secondly what exactly happens when you stretch images by an amount like 1.1? How dose it decide what pixels to add to the image to make it bigger?
  2. I continue the extension of the graphic facade (see previous article), with here the addition of a very classic form of drawing for video games: tiles. These make it possible to compose an image using small images called tiles. There are several types of tiles, I propose in this article the simplest case with rectangular tiles. This post is part of the AWT GUI Facade series. For the implementation, the approach that I propose to follow is similar to the one used for images: we use a factory (Factory Method Pattern) to instantiate layers that allow drawing with tiles. On the GUIFacade main interface side, I add the following two methods, one to create a layer, and the other to draw it: For layers (Layer interface), I propose to manage the tiles with one texture image by layer, and with tiles of a fixed size. In addition, the rendering of tiles can be memorized by the layer: in doing so, it is sufficient to indicate which tiles should be displayed in which places, and then the layer will display these tiles continuously. These renderings are called in this article sprites, so as not to confuse them with tiles (e.g., a tile is just a small picture, and a sprite is a small picture displayed at a specific location on the screen). At this stage of design, layers able to renders independently may seem unnecessary: we could continuously consult the game data for rendering. Later, when it will be necessary to make multi-threaded synchronization, independent layers are a blessing. In addition, for low-level implementations (such as OpenGL), it allows you to use vertex buffers, which greatly speeds up rendering. These properties can be obtained via an interface like the following one: The getTileWidth() and getTileHeight() methods return the size of the tiles (for example, 16 by 16 pixels); The getTextureWidth() and getTextureHeight() methods return the number of tiles in the texture image, in width and height; The setTileSize() method is used to set the size of tiles; The setTexture() method is used to define and load the texture image; The setSpriteCount() method is used to set the number of sprites managed by the layer; The setSpriteTexture() method is used to define the tile used by a sprite. The tile rectangle defines the used tile: they are coordinates in tiles, and not in pixels. For example, if the tile size is 16×16 pixels, and the tile rectangle is (3,4,1,2), then the tile location in pixels is (3 * 16,4 * 16,1 * 16,2 * 16) = (48,64,16,32). By convention, if the rectangle argument is null, then the sprite is disabled; The setSpriteLocation() method is used to define the location where the sprite is drawn. The rectangle is in pixels, and may be larger or smaller than the tiles used, to achieve a zoom effect. AWT Implementation For the implementation, we still use the AWT library, with the AWTLayer class (the methods of the Layer interface are not repeated): The tileWidth, tileHeight, textureWidth, and textureHeight attributes define the size of the tiles and the texture image; The texture attribute contains the texture image; The texture and location arrays contain all sprite information: tiles to use and render locations; The draw() method draws the entire layer. Most methods are accessors / mutators (getters / setters) whose implementation is very simple. The draw () method is less obvious: public void draw(Graphics graphics) { for (int i = 0; i < locations.length; i++) { if (textures[i] != null) { graphics.drawImage(texture, locations[i].x, locations[i].y, locations[i].x + locations[i].width, locations[i].y + locations[i].height, textures[i].x * tileWidth, textures[i].y * tileHeight, (textures[i].x+textures[i].width) * tileWidth, (textures[i].y+textures[i].height) * tileHeight, null); } } } All sprites are traversed (l.2), if a sprite is well defined (l.3), we draw an image (l.4-13). Lines 5 to 8 define the rendering location, in pixels: it is the coordinates of the upper left corner and the lower right corner of the rectangle. Lines 9 to 12 define a rectangle in the texture image: all coordinates are multiplied by tile size (tileWidth, tileHeight). Use case To illustrate this facade with tile drawing, I propose to consider two layers: one for the background, and the other for the buildings. In both cases, we consider the same tile size of 16 × 16 pixels, and the same area of rendering (the level of the game) of 17 × 17 tiles. In addition, a scale factor is used to zoom tiles. These parameters are placed in variables: int scale = 2; int tileWidth = 16; int tileHeight = 16; int levelWidth = 17; int levelHeight = 17; For the background layer, each sprite uses only one tile, and we always use the same one: Layer backgroundLayer = gui.createLayer(); backgroundLayer.setTileSize(tileWidth,tileHeight); backgroundLayer.setTexture("advancewars-tileset1.png"); backgroundLayer.setSpriteCount(levelWidth*levelHeight); for(int y=0;y<levelHeight;y++) { for(int x=0;x<levelWidth;x++) { int index = x + y * levelWidth; backgroundLayer.setSpriteLocation(index, new Rectangle(scale*x*tileWidth, scale*y*tileHeight, scale*tileWidth, scale*tileHeight)); backgroundLayer.setSpriteTexture(index, new Rectangle(new Point(7,0), new Dimension(1,1))); } } Lines 1-4 instantiate and initialize the layer. Then, for each cell of the level (l, 5-6), we associate a sprite (l, 7). To achieve this association, it is necessary to define a unique number for each cell of the level: to do this, the cells are numbered from left to right then from top to bottom. The rendering area of each sprite is defined in lines 8-9, which is a simple scaling: everything is multiplied by the tileWidth, tileHeight, and the global scale. Finally, the tile is selected in lines 10-11, with the 8th column of the first line of the texture Point (7,0) and the size of a tile Dimension (1,1) The following layer is used to display buildings, with the particularity that these have a height of two tiles in height: Layer groundLayer = gui.createLayer(); groundLayer.setTileSize(tileWidth,tileHeight); groundLayer.setTexture("advancewars-tileset2.png"); groundLayer.setSpriteCount(2); groundLayer.setSpriteLocation(0, new Rectangle(scale*8*tileWidth, scale*6*tileHeight, scale*tileWidth, scale*2*tileHeight) ); groundLayer.setSpriteTexture(0, new Rectangle(new Point(0,2), new Dimension(1,2))); groundLayer.setSpriteLocation(1, new Rectangle(scale*8*tileWidth, scale*7*tileHeight, scale*tileWidth, scale*2*tileHeight) ); groundLayer.setSpriteTexture(1, new Rectangle(new Point(0,4), new Dimension(1,2))); Lines 1-4 instantiate the layer and initialize its properties: tile size, texture image, and sprite numbers (2). Lines 6 through 11 define the properties of the first sprite (index 0): its render location is at cell (8,6) of the grid (l. 7), its render size equals a tile width and two heights of tiles (l. 8). Its tiles are at coordinates (0,2) in the texture and use a tile of width one and height two (l. 11). Lines 13 to 18 define the properties of the second sprite: it is drawn on the cell just below, and its tiles start at the coordinates (0,4) in the texture. If all goes well, the top of the second building sprite should cover the bottom of the first: Finally, in the game’s main loop, displaying layers is as easy as displaying an image: if (gui.beginPaint()) { gui.drawLayer(backgroundLayer); gui.drawLayer(groundLayer); gui.endPaint(); } The code of this article can be downloaded here: awtfacade04.zip Some improvements have been made compared to the version of the previous article: it uses a canvas and limits the number of images per second. These improvements are purely related to the problems of video games, and does not change the concepts presented above. To compile: javac com/learngameprog/awtfacade04/Main.java To run: java com.learngameprog.awtfacade04.Main Next post in this series View the full article
  3. In this article, I propose to use the Visitor Pattern to easily load a level. The GUI facade in the previous post is used to display the level. This pattern allows (among other things) to easily browse a data structure to extract information. In our case, it is an XML file created by “Tiled Map Editor” which is analyzed to load a level in memory. This post is part of the AWT GUI Facade series I start by creating a level in XML with Tiled: You have to choose in the left panel Tile layer format as “XML”. This produces an XML file that looks like this: <map version="1.0" orientation="orthogonal" renderorder="left-up" width="16" height="16" tilewidth="16" tileheight="16" nextobjectid="1"> <tileset firstgid="1" name="advancewars-tileset1" tilewidth="16" tileheight="16" tilecount="256"> <image source="advancewars-tileset1.png" width="256" height="256"/> </tileset> <tileset firstgid="257" name="advancewars-tileset2" tilewidth="16" tileheight="16" tilecount="256"> <image source="advancewars-tileset2.png" width="256" height="256"/> </tileset> <layer name="Ground" width="16" height="16"> <data> <tile gid="41"/> <tile gid="41"/> <tile gid="41"/> <tile gid="41"/> <tile gid="41"/> <tile gid="41"/> <tile gid="41"/> <tile gid="41"/> ... <tile gid="41"/> </data> </layer> <layer name="Objects" width="16" height="16"> <data> <tile gid="0"/> <tile gid="0"/> <tile gid="0"/> <tile gid="0"/> <tile gid="0"/> ... <tile gid="0"/> <tile gid="0"/> <tile gid="0"/> </data> </layer> </map> We first have a <main> tag with global properties, then two <tileset> tags that define the tile sets used (one for the background, the other for the objects), and finally two <layer> tags that define the tiles for two layers (one for the background, the other for the objects). To decode this file, I propose to use the XML parser included in the standard Java library. It is based on the Visitor pattern, and allows you to easily work on tags without having to worry about character decoding issues. Visitor Pattern The Visitor pattern can be presented as follows: The IElement interface represents the elements of the structure. In this example, there are two possible types of objects: ElementA and ElementB. The interface requires a method like accept() which takes as argument a visitor who implements the IVisitor interface. There can be several ways to visit the structure, and so many other methods similar to accept(). Parameters can also be used to influence the traversal. The IVisitor interface is implemented by the user who wants to traverse the structured data. In general, the interface methods correspond to the different types of elements that compose it: in this example, they are the ElementA and ElementB classes. It is quite possible to imagine other cases that may interest a user, such as being at the beginning or at the end of an element. In all cases, the accept() method calls the methods of the IVisitor interface according to the cases encountered during its course. Within these methods, the user is free to view and modify the data. Load a level To read and store the level information, I define a Level class that contains this information in attributes: public class Level { private ArrayList<String> tilesetImages = new ArrayList(); private int tileWidth; private int tileHeight; private int width; private int height; private int[][][] level; private int tilesetWidth; private int tilesetHeight; private int x; private int y; ... The tilesetImages attribute contains the file names of texture images; The tileWidth and tileHeight attributes contain the width and height of a tile (16 x 16 pixels in our example); The width and height attributes contain the width and height of the level (16 x 16 cells in our example); The level attribute contains for each cell coordinate: the (x, y) tile coordinates of the tile to draw, and the tile set to use. The following attributes are only used to decode the information in the file. To decode the file, I define a LevelLoader class that implements org.xml.sax.helpers.DefaultHandler. The LevelLoader class is the equivalent of the Visitor class in the diagram above, and DefaultHandler is the equivalent of IVisitor. I’m only interested in the startElement() method, equivalent to the visitElementA() and visitElementB() methods in the diagram above. This method is called whenever the parser encounters a new opening tag: public class LevelLoader extends DefaultHandler { public void startElement (String uri, String localName, String qName, Attributes attributes) throws SAXException { if (qName.equals("tileset")) { if (tilesetImages.isEmpty()) { tileWidth = Integer.parseInt(attributes.getValue("tilewidth")); tileHeight = Integer.parseInt(attributes.getValue("tileheight")); } } else if (qName.equals("image")) { if (tilesetImages.isEmpty()) { tilesetWidth = Integer.parseInt(attributes.getValue("width")) / tileWidth; tilesetHeight = Integer.parseInt(attributes.getValue("height")) / tileHeight; } tilesetImages.add(attributes.getValue("source")); } else if (qName.equals("layer")) { if (level == null) { width = Integer.parseInt(attributes.getValue("width")); height = Integer.parseInt(attributes.getValue("height")); level = new int[height][width][3]; } x = 0; y = 0; } else if (qName.equals("tile")) { int id = Integer.parseInt(attributes.getValue("gid")); if (id != 0) { if (id >= 257) { level[x][y][2] = 1; id -= 256; level[x][y][0] = id % tilesetWidth - 1; level[x][y][1] = id / tilesetWidth - 1; } else { level[x][y][0] = id % tilesetWidth - 1; level[x][y][1] = id / tilesetWidth; } } x ++; if (x >= width) { x = 0; y ++; if (y > height) { throw new SAXException("Erreur dans le fichier"); } } } } } The method is a long discussion based on the tag encountered, whose name is placed in the qName argument. For the “tileset” and “image” cases the information relating to a set of tiles is decoded. For the “layer” case, the level is initialized, and for “tile”, the information relating to a tile is stored. The x and y attributes are used to store the coordinates of the next tile to be decoded. Finally, I define a load() method in the Level class that uses the LevelLoader class to load the level: public boolean load(String fileName) { try { SAXParserFactory spf = SAXParserFactory.newInstance(); SAXParser saxParser = spf.newSAXParser(); XMLReader xmlReader = saxParser.getXMLReader(); xmlReader.setContentHandler(new LevelLoader()); URL fileURL = this.getClass().getClassLoader().getResource(fileName); xmlReader.parse(fileURL.toString()); return true; } catch(Exception ex) { return false; } } The Level class also has accessors/mutators (getters/setters) not listed here. Display the level To display the level, I use the GUI facade from the previous post: Level level = new Level(); if (!level.load("advancewars-map1.tmx")) { JOptionPane.showMessageDialog(null, "Error when loading advancewars-map1.tmx", "Error", JOptionPane.ERROR_MESSAGE); return; } int scale = 2; Layer backgroundLayer = gui.createLayer(); backgroundLayer.setTileSize(level.getTileWidth(),level.getTileHeight()); backgroundLayer.setTexture(level.getTilesetImage(0)); backgroundLayer.setSpriteCount(level.getWidth()*level.getHeight()); for(int y=0;y<level.getHeight();y++) { for(int x=0;x<level.getWidth();x++) { int index = x + y * level.getWidth(); backgroundLayer.setSpriteLocation(index, new Rectangle(scale*x*level.getTileWidth(), scale*y*level.getTileHeight(), scale*level.getTileWidth(), scale*level.getTileHeight())); if (level.getTileset(x, y) == 0) { Rectangle tile = new Rectangle(level.getTile(x, y), new Dimension(1,1)); backgroundLayer.setSpriteTexture(index, tile); } } } Layer groundLayer = gui.createLayer(); groundLayer.setTileSize(level.getTileWidth(),level.getTileHeight()); groundLayer.setTexture(level.getTilesetImage(1)); groundLayer.setSpriteCount(level.getWidth()*level.getHeight()); for(int y=0;y<level.getHeight();y++) { for(int x=0;x<level.getWidth();x++) { int index = x + y * level.getWidth(); groundLayer.setSpriteLocation(index, new Rectangle(scale*x*level.getTileWidth(), scale*(y-1)*level.getTileHeight(), scale*level.getTileWidth(), scale*2*level.getTileHeight())); if (level.getTileset(x, y) == 1) { Rectangle tile = new Rectangle(level.getTile(x, y), new Dimension(1,2)); groundLayer.setSpriteTexture(index, tile); } } } gui.createWindow("Load a level with the Visitor Pattern", scale*level.getTileWidth()*level.getWidth(), scale*level.getTileHeight()*level.getHeight()); The code of this post can be downloaded here: Download Now! To compile: javac com/learngameprog/awtfacade05/Main.java To run: java com.learngameprog.awtfacade05.Main View the full article
  4. I have been fascinated by programming before 8 years from now. The journey took me from someone who loves to be software engineer to be a networks engineer. I work as full time IP networks engineer. Well, I am a great fun of indie games developers. I have been following Dev-Logs for several indie game developers for a while. In the previous years many ideas of games have been floating in my mind and finally I took the decision to start my own small game project. I have been planning for the last 2 weeks for my game. I have decided to write the whole game and engine myself. My estimations are : Because I am doing this as side project the whole idea ( a 2D platformer ) will take me between 6 months to 1 year. The Game Engine will be developed in parallel with the game I am probably going to Use Java LWJGL or any other OpenGl library I should find a way to target my audience ( probably Youtube channel and dev-logs) Perfectioning the game might have a longer duration than the development of it. I will publish it when it meets the 95% of my expectations If There is any piece of advice of how to start the journey, It will be very helpful. If you have any thoughts about my plan please share it with me. If you have any guidance about how to use this platform I would be more than happy to hear from you. I am just a man who lost his way when making his career related decisions and he is doing a lot of things for fun. Thank you.
  5. The facade seen in the previous article has only an interface with its methods. It is also possible to enrich a facade with additional interfaces, connected to each other by various means. To illustrate it, I propose to add image management. This addition also makes it possible to present another design pattern: the Factory Method Pattern. This post is part of the AWT GUI Facade series. In graphic libraries, it is generally not possible to directly access the raw data of an image, it is always necessary to go through an identifier or a class to apply some processing. Knowing this, a relevant approach is to encapsulate what makes it possible to process the image in a dedicated class, for example: Compared to the previous article, the following methods have been added to the GUIFacade interface: The createImage() method creates an Image from the name of a file. In doing so, we are using the Factory Method pattern, which allows us to abstract the creation of objects, and whose creation process depends on inheritance. In this case, the user of the createImage() method does not know which implementation of the Image interface will be used. This choice depends on the class that implements GUIFacade interface, whose details are not necessarily known to the user, since it is a facade. Once again, the idea is to free the user of specific features, and let him focus on the problem he has to deal with, in our case the rendering of a 2D tile game. The drawImage() method is used to draw an image at (x, y) coordinates. Other methods dedicated to the creation and processing of images can be imagined, these are only examples among others. The Image interface is used to represent access to an image managed by the graphics library. Methods can be proposed to work with an image. In our example, the getWidth() and getHeight() methods return the width and height of the image. Other methods can be imagined, such as a draw() method that would draw the image, instead of the one within the GUIFacade interface. For the implementation of the facade, we still use the AWT library. For the Image interface implementation, an AWTImage class is proposed: public class AWTImage implements Image { private BufferedImage image; @Override public int getWidth() { if (image == null) { throw new RuntimeException("The image was not loaded"); } return image.getWidth(); } @Override public int getHeight() { if (image == null) { throw new RuntimeException("The image was not loaded"); } return image.getHeight(); } void loadImage(String fileName) { try { image = ImageIO.read(this.getClass().getClassLoader().getResource(fileName)); } catch (IOException ex) { throw new RuntimeException("Error when reading "+fileName); } } void draw(Graphics graphics,int x,int y) { graphics.drawImage(image, x, y, null); } } The AWTImage class holds an image reference to a java.awt.image.BufferedImage. getWidth() and getHeight() methods return the width and height of the image. The other two methods are not part of the facade, and are invisible to its users. They are used by the AWTGUIFacade class to load the image (loadImage() method) and display it in a java.awt.Graphics (draw() method): public class AWTGUIFacade implements GUIFacade { ... @Override public Image createImage(String fileName) { AWTImage image = new AWTImage(); image.loadImage(fileName); return image; } @Override public void drawImage(Image image, int x, int y) { if (!(image instanceof AWTImage)) throw new IllegalArgumentException("Invalid image type"); AWTImage awtImage = (AWTImage) image; awtImage.draw(graphics,x,y); } } This new version of the facade can be used in the following way to display a window with an image: public static void run(GUIFacade gui) { Image titleImage = gui.createImage("title.png"); gui.createWindow("AWT Graphic User Interface Facade", titleImage.getWidth(),titleImage.getHeight()); while(!gui.isClosingRequested()) { if (gui.beginPaint()) { gui.drawImage(titleImage,0,0); gui.endPaint(); } } gui.dispose(); } The image is created from the file “title.png” (1. 2), a window of the size of the image is also created (l.3), and as long as the game is not finished (l. 5), the drawing is started (1. 6), the picture is displayed (1. 7) and the drawing is ended (1. 8). The code of this post can be downloaded here: awtfacade03.zip To compile: javac com/learngameprog/awtfacade03/Main.java To run: java com.learngameprog.awtfacade03.Main Next post in this series View the full article
  6. In this article, I propose to continue the design of a facade for a 2D tile game (previous post). I add two new features: creation/destruction of the window, and basic drawing. Each feature is managed by a batch of methods in a GUIFacade interface. This post is part of the AWT GUI Facade series. The GUIFacade interface can be represented in the following way: The first four methods handle the window: The createWindow() method builds the window with a given title; The setClosingRequested() method is used to define whether the game should be completed; The isClosingRequested() method lets you know if the game needs to be completed; The dispose() method destroys the window and all associated elements. The last three methods allow you to draw in the window: The beginPaint() method starts the drawing, and returns true if it is possible; The drawLine() method draws a line. This is an example of a drawing method, a whole collection can be imagined to draw rectangles, circles, etc .; The endPaint() method completes the drawing. Most graphic libraries used to follow these steps where you have to start by “preparing” the drawing with a method like beginPaint(), then “free” it with a method like endPaint(). In addition, there is usually a form of blocking between these two calls, which means that you have to draw “as quickly as possible” if you want to offer a good user experience. These methods can be used as follows: the window is created (l.2) and we repeat until the game is finished (l.3). If it is possible to start drawing (l.4), draw a line (l.5) and finish the drawing (l.6). Finally, the window is destroyed (l. 9): public static void run(GUIFacade gui) { gui.createWindow("AWT GUI Facade"); while(!gui.isClosingRequested()) { if (gui.beginPaint()) { gui.drawLine(100, 150, 600, 350); gui.endPaint(); } } gui.dispose(); } Note: In this example, there is no limitation on the number of frames per second. This can saturate a processor core and cause minor issues on some configurations. We’ll see in another post how to get a better frame rate. The use of the facade does not depend on its implementation: it is possible to use different implementations, for example the AWT library included in the standard Java library: public class AWTGUIFacade implements GUIFacade { private AWTWindow window; private boolean closingRequested = false; private BufferStrategy bufferStrategy; private Graphics graphics; @Override public void createWindow(String title) { window = new AWTWindow(this); window.init(title); window.setLocationRelativeTo(null); window.setVisible(true); window.createBufferStrategy(2); } @Override public void setClosingRequested(boolean b) { closingRequested = b; } @Override public boolean isClosingRequested() { return closingRequested; } @Override public void dispose() { window.dispose(); } @Override public boolean beginPaint() { bufferStrategy = window.getBufferStrategy(); if (bufferStrategy == null) return false; graphics = bufferStrategy.getDrawGraphics(); if (graphics == null) return false; graphics.setColor(Color.black); graphics.fillRect(0, 0, window.getWidth(), window.getHeight()); return true; } @Override public void drawLine(int x1, int y1, int x2, int y2) { graphics.setColor(Color.white); graphics.drawLine(x1, y1, x2, y2); } @Override public void endPaint() { graphics.dispose(); bufferStrategy.show(); } } The window attribute is a reference to an AWTWindow class that inherits from java.awt.Frame, shown below. The closingRequested attribute is true if the game must end. The bufferStrategy and graphics attributes are used to handle double buffering rendering. The init() method is the same as in the previous article, except for the creation of a double buffer with window.createBufferStrategy(2); The setClosingRequested() and isClosingRequested() methods manage the closingRequested attribute. The dispose() method controls the destruction of the window. The beginPaint() and endPaint() methods handle the display cycle. In the first one, the current buffer is obtained (1.37), then a java.awt.Graphics is created from it (1.40). In both situations, various reasons may cause issues, in which case false is returned. The end of the beginPaint() method erases all the content: this approach can be interesting or not, depending on the case. The endPaint() method destroys graphics (1. 56) and inverts the two buffers (1. 57). Finally, the drawLine() method uses graphics to draw a line: it’s easy to imagine other use cases for drawing rectangles, circles, and so on. The AWTWindow class is an AWT window initialized by the init() method with a specific configuration. When window closing is requested by the user, the facade is notified that the game must be completed (1. 16): public class AWTWindow extends Frame { private final AWTGUIFacade gui; public AWTWindow(AWTGUIFacade gui) { this.gui = gui; } public void init(String title) { setTitle(title); setSize(640, 480); setResizable(false); addWindowListener(new WindowAdapter() { @Override public void windowClosing(WindowEvent we) { gui.setClosingRequested(true); } }); } } Note: The rendering method is simple but not optimal: it is better to use canvas to draw inside a window. This implementation may cause some undesirable effects. The code of this post can be downloaded here: awtfacade02.zip To compile: javac com/learngameprog/awtfacade02/Main.java To run: java com.learngameprog.awtfacade02.Main Next post in this series View the full article
  7. In this series, I propose to discover the Facade Pattern. In short, this pattern defines an interface that allows a reduced and simplified use of a set of features. To illustrate, we design a facade of the AWT graphic library for a 2D tile game. This post is part of the AWT GUI Facade series. Let’s start with the simplest facade with a unique createWindow() method that allows the user to create a new window: Creating a window with this facade is very simple: we instantiate an implementation of the facade (l.1), and call the createWindow() method (l.2): GUIFacade gui = new AWTGUIFacade(); gui.createWindow("AWT GUI Facade"); In this example, I propose to implement a window creation with the AWT library: other implementations are possible without changing the GUIFacade interface and its use. An AWTWindow class that implements java.awt.Frame is defined to handle our window: The createWindow() method of the AWTGUIFacade class instantiates an AWTWindow (l .4), initializes it with a title (l.5), places it in the center of the screen (l.6) and makes it visible (l. 7): public class AWTGUIFacade implements GUIFacade { @Override public void createWindow(String title) { AWTWindow window = new AWTWindow(); window.init(title); window.setLocationRelativeTo(null); window.setVisible(true); } } The AWTWindow class has an init() method that initializes the window with a given title (l.3), a size of 640 by 480 pixels (l.4), prohibits resizing (l.5), and ensures that the window is destroyed when closed (L.6-11): public class AWTWindow extends Frame { public void init(String title) { setTitle(title); setSize(640, 480); setResizable(false); addWindowListener(new WindowAdapter() { @Override public void windowClosing(WindowEvent we) { dispose(); } }); } } The creation of the window is split between the createWindow() method of the AWTGUIFacade class and the init() method of the AWTWindow class. The main motivation here is to separate the more dynamic operations, such as the position of the window, from more static operations, such as the title or the fact that the window is not designed to be resized. There are many other possibilities depending on the possible extensions of the facade. With this facade, a user can easily create a window for a specific use, without having to know all the methods of a graphic library. Moreover, apart from the instantiation of a layout of the facade (i.e., new AWTGUIFacade()), all the following code no longer depends on the graphic library (the gui variable in the first example code is of type GUIFacade). This means that it is possible to switch from one implementation to another, and therefore from one graphic library to another. This property is very interesting when you want to cross-platform, or if the first choice of the graphic library was not good. In any case, we can switch from one library to another without having to rewrite the entire application! This article presents a very simple first approach, and presents the basics of the facade pattern. In the following articles, things will become more complex, and you will see what can be achieved from a pattern whose principle seems so simple! The code of this post can be downloaded here: awtface01.zip To compile: javac com/learngameprog/awtfacade01/Main.java To run: java com.learngameprog.awtfacade01.Main Next post in this series View the full article
  8. Wograld Homepage Wograld is an open-source 2d multi-player online rpg. We are in need of the following team members. 1.) Marketing. This would just be a get the word out position. Play the alpha, make videos, get it talked about on different forums blogs and youtube channels, or whatever else you can think of. Even if it isn't yet ready for everyone to play, there is nothing like getting everyone all hyped up and excited about the existing game and what new features will be implemented next. I would prefer someone who can already compile and run the game from the latest sources, but if you can't do that yet, I would be willing to spend many hours getting you up to speed for the right (or left) person. 2.) Game mechanics Designer. Okay, I said this is a design position, but I would prefer someone with some basic understanding of the C programing language as well in order to help implement actual code changes.. The main issue is with the game mechanics. Some of them could use some serious tweaking. There is a lot that is fun, and some stuff that really isn't fun. We want to move from the current level system to a more skill based system, but without the grind and macroing that characterized games like Ultima Online. 3.) Java Updater - Unfortunately, this position sounds like the least fun. Who actually wants to take old java code, that works on Java 8, and get it to work on Java 11 and beyond. Maybe someone who wants to prove they can do it and then get a high paying Java developer job after showing off a portfolio. Perhaps someone who is so enthralled with the game idea and also happens to know the latest Java stuff.
  9. Hi guys, Check this new free Android game I just released today in Play Store - Grazomvity. Specially designed to be played one handed while standing in train, bus etc. https://play.google.com/store/apps/details?id=com.adriasys.grazomvity There are no make-believed, over-hyped, fabricated comments and ratings from friends or family. YOU be the FIRST to rate and comment. As a bonus, the winner gets free temporary upgrade and eventually can see the entire game source code. Your feedback is much appreciated. Thanks guys, Lee
  10. I have a class for the NPCs in my game. Each NPC has an athleticism attribute that ranges from zero to one-thousand. I am randomly generating this value. I want 70%-80% people to have a roughly average amount of athleticism, somewhere close to 500. Is there some algorithm I can apply that will skew the randomly determined athleticism score so that it's usually close to 500, but always returns a few scores that are either much lower or a lot higher?
  11. I am working on a multiplayer game which uses UDP protocol in Java. I have a server and multiple clients. The clients connect to the server and they each have their player. When one client moves a player, the position of it is sent to all the other clients connected to the server. The positional data isn't sent from the client to server and then from server to all clients. It is sent directly from the client who moved the player to all other clients connected to the server. The player is then moved in all clients windows according to the positional data sent. I know packet loss exists and there is delay in receiving packets. But I dunno how other games manage to smooth out their multiplayer player movement. Can you explain how they do it and how I can go on implementing it my self. The bottom code is happening in the client who hasn't moved. this is the client who has received the positional data of the client who HAS moved. The bottom code runs when ever the other client moves. // here is some pseudo code of how I manage my player movement. // This packet contains the x and y position of the player who has moved. Packet receivedPacket = new Packet(recievedData); // this is the player which represents the player who has moved. player.setX(receivedPacket.getX()); player.setY(receivedPacket.getY()); The problem is there is very laggy player movement especially if the clients are on different computers. This is most probably due to packet loss and packet delay across the network. I have tried tweaking the player's position to the position that is received by the client. But still there is some lag. Please help me.
  12. Hey all. I've created a Java library that offers a couple of different algorithms for generating random text (e.g. to generate character names or place names for an adventure game). It's pretty well documented, covered by tests, scanned for code quality, and available via Maven Central -- overkill for this kind of project, I know, but this is really a project I conceived of while training myself in the Java language (having worked for the past several years in Python and JS). I welcome feedback and contributions! The library and docs: https://github.com/joeclark-phd/random-text-generators A repo that uses the library to generate lots of example text: https://github.com/joeclark-phd/procedural-generation-examples The main algorithm of interest is one that uses Markov chains to learn from a training dataset and produce new data with similar character sequences. Depending on the training data, this can do a good job of making original new text that sounds like it belongs in the original. For example, I trained it on a database of about 1300 ancient roman names and here are some examples of the random text output: caelis domidus pilianus naso recunobaro potiti cerius petrentius herenialio caelius venatius octovergilio favenaeus surus wasyllvianus nentius soceanus lucia eulo atric caranoratus melus sily fulcherialio dula