Announcement

Collapse
No announcement yet.

MapSquare Class OO discussion

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

  • #76
    P.S. -- if anyone wants to keep an eye on coding progress, the working version will be kept Here.

    This is a glance into the internal development of a piece of software, so if you're expecting polish and shine you'll be disappointed. But feel free to make any comments, just don't be too harsh in your judgment, not yet. There's a fully working datamodel underneath, you just can't see it yet!

    But you can get a look at the style of the GUI I'm building. I'm working on integrating the 'real' map grafix right now.

    Comment


    • #77
      re m-v-c and map squares

      im no expert but this is my view on the subject,

      first pure m-v-c is hard to find , I think controller is a bit of an ambigous term and is not always easy to seperate from the view

      i would agree with marks post on objecting to squares extending canvas ( not that im involved in the project , yet) .

      re: jtable and m-v-c

      data objects should not draw themselves, A model contains or knows about data, and the view draws the model. in a jtable the TableModel knows about the data (leaf/nodes) as represented by seperate objects/primitives, it is the renderer that is responsible for the actual drawing of the data( and there can be multiple renderers, one for each column , or even cell). the TableModel does not know how to draw itself, it knows things like how many columns the data represents, but leaves it to the renderer to actually draw each column/cell, it is this renderer that will extend a visual component( eg JPanel , JLabel etc), not the model and certainly not the data. Note that the model does not even know about renders, they are registered with the table not the model, you can change the renderer for a model on the fly, getting different views of the same data.

      I would class the parts as follows
      JTable = 1 part of view ( and controller in that it reorders columns etc)
      Renderer = other part of view
      TableModel = model (contians data ) ( also controller, in that table sorters are implementations of models, plug a sorter between THE model and the table)


      If mapSquare extends canvas then this is not possible ( or much harder ). consider the diffrernt views of a square, the obvious one is when it is just a square on the main playing map, but i may be able to select a square for a more detailed view the square, this appears in a differnt window which gives more detailed information in a totally different display format. both views however are looking at the same object - the square.

      I went down the route of squares extending panels when i first got into OO game writing and regretted it , believe me it is better to divorce the view/gui from the model/data. having the map square extend some visual component will make it hard to make changes to the way the game model and the game view work.

      Although i'm not sure it is the best way, i currently work with a front end that observes the model, the model fires changes to the frontend which decides what to do based on the change, if a map square has altered then the model passes the square to the front end as a parameter when it fires the change off. the view can then change the display of just that square if it deems it necessary. different views act as observers, each displaying the square ( or whatever ) in their own way, eg the main map view , the detailed square info view etc

      Comment


      • #78
        Hi Puree, welcome to the forums . The more minds we've got working the better, especially ones that happen to agree with me (and can back up the position better than me)!

        F_Smith:

        Building an airplane factory, etc.

        As a design issue I don't want to get into hundreds of dedicated facility types to build different things. I don't think the player gets much out of it. And it makes the AI's job that much harder to site all these things, balancing threats against ideal production locations etc. Now your OO model can have it the way you picture it, so long as it can accomodate whatever agreement we finally reach for the standard model.

        I had intended to handle everything abstractly but ports/shipyards which pretty much Have to be in sensible places. By abstractly I mean that production capacity is plain vanilla production capacity, and can be re-assigned at will to produce whatever. The current plan is to have two modifiers of this simple scheme to get some important real-life features in the model. The first is to have a production ramp-up when you are building new things. Take last turn's production of fighters and call it X. You can build up to X fighters this turn at the base cost for fighters because the factories are already in place. Any more than X up to 2X would cost double. That's because you are reconfiguring factories and building the new planes. 2X-3X would cost quadruple, 2^(lower multiple, 2 in this case). This mechanism of course introduces nonlinearity by itself, but I think we need something like this to prevent countries switching over to total war production from peacetime production in a single month. Perhaps just a smoother function would help. The second modifier might be one awarded for 'centers' of production for certain things that could get arbitrary bonuses. A certain city, because cannon foundry and related industries really took off there might be able to make cannon for 2/3 the usual cost. This would be handled as a special just like iron ore.
        Project Lead for The Clash of Civilizations
        A Unique civ-like game that will feature low micromanagement, great AI, and a Detailed Government model including internal power struggles. Demo 8 available Now! (go to D8 thread at top of forum).
        Check it out at the Clash Web Site and Forum right here at Apolyton!

        Comment


        • #79
          Puree:

          Hi! Glad to have your comments, I need all the help I can get on this.

          We are using observers too -- I think it is absolutely the right way to go about it. My comment above about a mapsquare 'redrawing' itself was a reference to that, in fact. I was speaking about 'functionally' redrawing itself -- in other words, the square is redrawn when the data changes and the data object fires the 'hasChanged()' method. The use of extending Canvas was simply a convenience, since otherwise the data object will have to have methods to define what gets painted. Extending Canvas provided all the methods I would otherwise have had to add -- getMinimumSize, getMaximumSize, paint, update, etc. I then used the 'MapSquare' in exactly the same way you'd use a 'ListModel', adding it to a 'MapPanel'.

          The way I seperate the 'data model' and 'view' in my mind is that the 'data model' holds the information on what gets painted, while the 'view' component paints whatever the data model defines. Does this seem right?

          * * *

          Mark:

          I'm sorry, I still am not clear. More stupid questions to ask. I'm going to have to build a Gui with this functionality, so I probably better ask questions until I understand it!

          So --
          When a player has just learned how to build fighter planes, how does he go about building them? Is it 'SMAC' style, where he can build those at any base? Including a 'prototype'-style first-build cost?

          Can a player can build airplanes at any of his mapsquares? Or just in his capitals? What about 'specialization'? Can a player 'improve' his fighter plane factories seperate from his other industry, not counting new technologies? Do I understand correctly that a 'factory' can't be specifically destroyed/sabotaged/dismantled and moved on it's own? Is there then a 'factory' object at all, or just one 'infraclass'? If no 'factory' object, is there any specific game representation of a squares industrial capabilities?

          It sounds to me very much like the 'SMAC' system. If I code along those lines, will I be close to what you want?

          Comment


          • #80
            I know I should contribute to this thread more often, specially since infrastructure is already discussed in here. But I am really overwhelmed by the new semester that has just begun. It has left me timeless and exhausted. Some brief comments though:

            Whenever this is required by a certain model, the generic infraclasses can be related to specific objects. These can be military units, wonders, even the civ2-styled city-improvements. See the infra thread for further explainations - I know that since you are discussion the OO structure of the game here, this is the best solution. Only if this approach is in contrast with some model features (f.e. Mark dosn't like military units having logistics based on # of "shields" that the unit costs) should we detach the cetrain objects out of the infrastucture system (this can be claimed for food, kapital and military units).

            About factories (or the kapital infra units) being specialised to a certain type of production, I think that we could add a nonlinear factor to input cost of infra units, one that depends on the difference between this and the previous turn's input. The same can be done with the infraclass unit costs of all real infrastructure objects that we will decide to add. IMO this is easy enough.
            "In a time of universal deceit, telling the truth is a revolutionary act."
            George Orwell

            Comment


            • #81

              The mapsquare is the model of an area and everything in it, ie. it knows directly or indirectly what the terrain is , the units in it the cities in it , the resource values etc etc. It has absolutely no idea of how it will be displayed, nor does it know which data elemnts will get displayed. From that point it does not represent what will be painted, however what gets painted will ( one would hope ) will be based on the mapsquare and its data. the model should not be defining nor constraining what gets painted.

              the methods you mention : getxxxSize, paint update etc, should not be in the model ( mapsquare ), even the min/max size are not part of the models responsibilty, they belong in the view( each view may have different size constraints). the view should be working something along the lines of not production code, just idea of the process )

              if( square.getTerrain().equals( "forest" ) )
              {
              // paint some image , its size based on factors
              // that square knows nothing about nor cares about
              }
              if(square.getArmies() != null)
              {
              // paint some army image over the terrain image
              // may paint one icon no matter how many armies
              // are in the square or paint a stack of armies
              // but again this is view dependent, the model
              // nether knows nor cares
              }
              if(square.isSelected() )
              {
              // paint white border round square
              }

              ..... etc

              another view, eg the detailed square information view
              would have different code, it might go

              if(square.getTerrain().equals("forest") )
              }
              // display in different window a big image of a tree
              // and paint in the corners the resource values for
              // forest ( or the squares resource values )
              }
              if(square.getArmies() != null )
              {
              // get a collection of the armies, and for each
              // add a panel in a scroll pane , and paint on the //panel an image specific to the army, with its //combat values
              }

              // ignore selected value

              .... etc

              the important point is both views are referencing the same mapsquare, one view is ignoring half the data, the other uses it all but displays everything in a different way.

              also important is that the code for each possible view is in a different class, I may be wrong but it looks like extending canvas would mean the various views are coded in the one paint method!.

              extending an object should not be used to save time coding some methods, short term gain - long term problem, the data for a mapsquare is not a type of gui object. code the extra methods you need ( but not the ones you mention )

              if you decide to change the view ,e.g. dont like the scroll pane put the armies in a table , then nothing needs to touch the model ( or its sub/superclasses ) only that specific view needs changing.

              the swing components you mention ( table list tree etc) dont work the way I think you are saying, JList contains a model and a renderer, the renderer paints the various elements of the model. the model does not extend any nor contain any visual component , and knows nothing about renderers as they are registered with the JList not the model. the list pulls out each element of the model then passes it to the renderer, which can do what it wants with the object representing the element after which it returns the component ( the jlabel in the default ) to the Jlist, which then paints the component. ( i believe the default renderer is a JLabel with the toString() method of the element displayed on it , but ive used JPanels painting icons depending on the class type of the value object, and text for the data )


              Comment


              • #82
                cool, how did that (not)smiley get there,


                ps TheadInterruptedException in my orignal post, tables dont deal with leafs/nodes, i had been reading up on tree structures and the reference to them must have slipped in to the table thread of thought

                Comment


                • #83
                  Hi, Puree:

                  I was thinking more along the lines of the code in the view (class IsoMapPanel, in this case) saying --

                  Code:
                  
                  public void paint(Graphics g)
                      {
                          Iterator it = gamemap.getAllMapSquares();
                          
                          while(it.hasNext())
                          {
                              MapSquare msq = (MapSquare)it.next();
                              
                              if(mapSquareOnScreen(msq))
                              {
                                  if(view_selections.viewTerrainOn())
                                  {
                                      paintTerrain(msq.paintTerrain());
                                  }
                                  
                                  if(view_selections.viewResourcesOn())
                                  {
                                      paintResources(msq.paintResources());
                                  }
                              }
                          }        
                      }
                  
                  So the paintTerrain method in IsoMapCanvas would do the painting at the relevant x and y location, while the mapsquare would hold the information on what get's painted.

                  Does this seem okay, or would you completely remove the grafix data from the mapsquare? I was thinking along the lines of 'AbstractTableModel', which has a 'getColumnCount', 'getRowCount', etc. The table model holds the data on what get's drawn, while the view draws only what it wants -- there-by easily allowing multiple views of the same data. And the renderer just draws columns and rows.

                  Extending Canvas was not used to make it a 'view' component, extending Canvas was used to allow it to store 'view' data. The mapsquare will need it's own tooltip, popUpMenu, etc, which I thought should all be stored in mapsquare.

                  Comment


                  • #84
                    no the model should have no grapgics data, just the data of the objects it contains - terrain, armies etc
                    ( your earlier posts had a model of sorts for what a square would contain ).

                    this is how jtable ( and list etc work ) as well, the model contains no graphics details at all. the getcolumnCount() etc are not graphics data, they are there to provide anything using the model with basic info what the model contains. the model can say to anything else i have 10 rows and 5 columns, this is not graphics/view data, just as saying i (square ) contain 5 armies, 1 city and a river is not graphics info.

                    In a jtable the table view takes the counts to paint the basic frame for the table and then asks the model for each cell value in turn(which could anything practically, model.setvalue takes an object), passes it to the renderer which passes the table view back the component (to paint at the appropiate position)

                    analogy, mapsquare has methods like getArmies , getTerrain - but these return collections or Strings or Terrain data not graphics. the view ( say MapView ) asks the mapModel for each square, which it passes to a square renderer, the renderer passes back a component ( canvas ?) which the view uses to visually show that square.
                    The renderer will create the 'canvas' then paint what it needs to on it before returning it to the view, this is done by calling getTerrain , getArmies on square and painting grahics accordingly, ( the renderer will probably be what extends the component, so its painting on itself )

                    There can be multiple renderers all dealing with square objects, MapView might use different ones at different times or other views unrelated to mapview might use other renderers eg the DetailView uses a different renderer which returns a JScrollPane displaying a scrolling list of everyitem in the square.

                    Possible renderers could be
                    UnexploredRenderer - which just returns a black fill

                    MyEmpireRenderer - returns a 'canvas' with piccies of the armies latest city size etc,

                    OtherPLayersEmpireRenderer - returns piccy of city size but not the armies displayed,

                    ExploredButFogOfWarAppliesRenderer (well not a name that long but you get the picture) - returns piccy with a tint over it

                    If you wish to display the unexplored squares differently from last version just change UnexploredRenderer, the model does not need any changes, nor does the master mapview

                    The renderer does not have to return a component , it might return an Image instead, depends on how the Graphics are being done, everything one one JPanel , or a panel per square ?

                    The renderer only needs one method

                    public Component/Image(?) render ( MapSquare square );

                    (plus any other parameters deemed necessary)

                    add its noddiest the MapView has some method to "paint" itself like this :

                    public void display()
                    {
                    setLayout( new GridLayout(x,y) );
                    removeAllComponents();
                    SquareRenderer renderer= new SquareRenderer();
                    MapSquare[] squares = map.getSquares();
                    for ( int i = 0 ; i {
                    add( renderer.render( square[i] );
                    }
                    }

                    wouldnt set its layout everytime ( once in constructor will do , but again you get the idea)

                    P.S im not a graphics guru , but i dont think you should use a canvas or panel for each square, the renderer should return an image which the MapView paints at the correct point - saves on memory for one thing, saves on performance cos less object creation going on , and makes it easier for displays which arn't totally square based ( ive not tried sometric 'diamonds' on seperate panels but i doubt its that easy )

                    Comment


                    • #85
                      Puree:

                      Your input is being *very* helpful. Thank you so much.

                      I'm a database programmer -- I normally just build boring, basic 'Corporate' style front ends for my middleware. So I've never done this kind of grafix drawing before.

                      I think I'm beginning to understand. But it's still fuzzy. My thick skull can really get in the way sometimes.

                      So -- I need a 'renderer' between the 'view' and 'data model' object? And the 'renderer' assembles the canvas/component? Would the 'renderers' belong in the 'controller' package?

                      This sounds like I absolutely need these objects:

                        [*]IsoMapPanel[*]MapSquarePanel[*]TerrainRenderer, etc.[/list]

                        Does this sound correct? I'm still uncertain . . .

                      Comment


                      • #86
                        Axi:

                        Sorry to hear things suck timewise for you .

                        Thanks for the reminder of handling capital as infra, I'd forgotten about that completely. That part should work.

                        I still don't like treating military units as infra of any sort. But we should discuss that in the infra thread when you have the time.

                        F_Smith:

                        Yep, we've gotta reach understanding on this now, or the whole thing will be screwed up...

                        "When a player has just learned how to build fighter planes, how does he go about building them? Is it 'SMAC' style, where he can build those at any base?"
                        Basically

                        "Including a 'prototype'-style first-build cost?"
                        Not really, the expanding production cost is more than just a prototype cost. We might have prototype costs also, but I haven't gotten that far. Essentially we will have a function that increases the cost to the treasury of building fighters if you build more than the previous amount. This cost would just be paid by the central treasury.

                        "Can a player can build airplanes at any of his mapsquares?"
                        Yes, at least if we run the econ model at the mapsquare level.

                        "Or just in his capitals?" only with prov-level econ things would all be built in the provincial capital.

                        "What about 'specialization'? Can a player 'improve' his fighter plane factories seperate from his other industry, not counting new technologies?"
                        Not in the way you are thinking, I think! You can increase the capacity to build fighters using the function that takes money from the treasury above. Other than that factor production capital is the same for toasters and tanks (famous error made by the German general staff in assessing US war capacity at the beginning of WWI was that the two were not interchangeable over year-long periods of time )

                        "Do I understand correctly that a 'factory' can't be specifically destroyed/sabotaged/dismantled and moved on it's own?"
                        No, any of these can happen. Only quibble is 'factories' can't move themselves, would need a merchant/transport unit to move them.

                        "Is there then a 'factory' object at all, or just one 'infraclass'?"
                        Infraclass dedicated to production is our equivalent to a factory in civ.

                        "If no 'factory' object, is there any specific game representation of a squares industrial capabilities?"
                        Yes, infra in that square representing production capacity.

                        "It sounds to me very much like the 'SMAC' system. If I code along those lines, will I be close to what you want?"
                        I don't know. I didn't play SMAC for more than a few hours. Just long enough to tell the AI wasn't much better than in civ... If you want to cite examples Civ2 is the one to use for me when possible.

                        Hope this helps...
                        Project Lead for The Clash of Civilizations
                        A Unique civ-like game that will feature low micromanagement, great AI, and a Detailed Government model including internal power struggles. Demo 8 available Now! (go to D8 thread at top of forum).
                        Check it out at the Clash Web Site and Forum right here at Apolyton!

                        Comment


                        • #87
                          I'm not a programmer, but...

                          I think puree's making a lot of sense. Separating the graphical representation from the mapsquare data is logical.

                          FE this would mean that, if we decided to change the squarebased game into a hexbased game we would not change the mapsquareobjects, only the view/renderer or whatever. Right?

                          The reason I'm asking this is that I'm an old boardgamer, very fond of hexes . While rambling on in the map graphics thread, it crossed my mind that the hexbased map would give the opportunity to have rivers on hex-edges rather than inside the hex. Of course if we wanted to include this functionality, the objectmodelling of the map'square' would have to be changed, maybe by having an object for each 'square'-edge.

                          Just wild thoughts.


                          BTW - I just knew I'd hit a nerve when mentioning infrastructure
                          [This message has been edited by Beör (edited October 05, 2000).]
                          Civilisation means European civilisation. there is no other...
                          (Mustafa Kemal Pasha)

                          Comment


                          • #88
                            All:

                            I'm outa here till saturday evening, so please don't expect fast answers to any questions.

                            Beör:

                            I also go way back with hexes in wargaming. But computers being able to figure correct movement distances of 1.41x larger for diagonal moves eliminates a lot of the advantages that hexes had in board games IMO.

                            Putting rivers on tile boundaries can be done with squares also, so I don't get the connection of that topic with hexes. Rivers going down the center of tiles makes somewhat more sense from an economic perspective (cities, generally assumed to be at square center, are on the rivers). But of course from military and transport infrastructure position you are right that putting rivers on tile edges makes more sense. If you want to take this further, most of the previous discussion of this sort of stuff (though not necc. this particular topic) is in the most recent map generator model thread. That's IMO where we should continue this topic.
                            Project Lead for The Clash of Civilizations
                            A Unique civ-like game that will feature low micromanagement, great AI, and a Detailed Government model including internal power struggles. Demo 8 available Now! (go to D8 thread at top of forum).
                            Check it out at the Clash Web Site and Forum right here at Apolyton!

                            Comment


                            • #89
                              Off course it is possible to have rivers on square edges, they just don't look very cool, always bending at 90 degrees.

                              It's not my intention to change the basic maplayout. It was really just curiosity as to whether the separation of view/renderer from data would make such a change easier.

                              And since I'm not a cat...
                              Civilisation means European civilisation. there is no other...
                              (Mustafa Kemal Pasha)

                              Comment


                              • #90
                                Mark:

                                I think I've got it. I'm ready to code it, altho first I've got to finish this IsoMapPanel. That's taking a little bit of learning (as you can see), so give me a few more days.

                                * * *

                                Beor:

                                Absolutely, the gui components must be seperate from the data model components.

                                I usually accomplish this by using the predefined 'Swing' classes, but those won't work here for a variety of reasons. So I'm having to build custom classes I've never had to before.

                                It's a matter of *how* to seperate the code. What architecture to use to best achieve that seperation.

                                And I can think of two reasons off the top of my head for this -- hexes, and 'provinces' like risk. That's one reason the gamemap can not be stored as a multidimensional array, by the by.

                                Personally, I love hexes, I feel like there's more choices in mobility. I would not like to run the rivers between the two, but putting the river on the edge of a mapsquare would be fine, graphically. But all rivers must be 'on the map', which means they'll have to be in a square.

                                Comment

                                Working...
                                X