On Wed, Jun 1, 2011 at 11:44 PM, James Nash <cir...@twiddles.com> wrote:
In general, I like your idea quite well, but it appears quite difficult to implement. I had hoped for something that fits quite well into the existing framework. So let me start by explaining what is currently there, and then think about how something like your idea could be added on top of it without a year of coding :-). There are two ways to pick mapobjects for placing on the map: 1. Click on an object in the mapview. 2. Click on an object in the entity list. Once picked, you can place that object down as often as you want, unless you release it by right clicking or pressing ESC. The problem is that objects not present on the map or at the current location can only be selected from the entity list. And that contains all available mapobjects. Thus, the idea is to filter that list in some fashion. Placing objects itself is aided by a dynamic grid. This works very well for objects of the same size (or multiples of that size), but requires manual adjustment for objects of different sizes. Like a straight wall and a corner part. The idea here is, that in almost all cases, a tile has 4 sides to which other tiles can connect. And if regarding a single side, in almost all cases an adjusting tile will be either centered or aligned to one of the outer edges. The grid controls work under that assumption. See here: http://adonthell.berlios.de/doc/index.php/Tools:Mapedit:Grid The problem, of course, is that you will have to switch back and forth between the grid controls and the main window often as right now there is no information how two tiles are connected and therefore the grid cannot adapt automatically. That is where I thought your idea could help in two ways: 1. By indicating matching tiles, the entity list can be filtered to only show tiles that can be attached to the selected object. (But it's less suited to filter for pieces of matching furniture, for example. That's why I still see the tag based filtering as a worthwhile alternative.) 2. By specifying how any two tiles are aligned, the grid can be automatically set accordingly, so that the picked mapobject can be placed directly on the map without the need for manual adjustments. I'm not as good as you in providing mockups, so I have to do with a simple description of the sequence I would envision. 1. Pick a horizontal wall piece. 2. Enable "matching filter" (hopefully with a simple key shortcut) 3. The entity view shows a number of matching horizontal and corner pieces. 4. Place a line of wall pieces (left click), then release the current piece (right click) 5. Pick a corner piece from the entity list 6. The filter changes to show mapobjects matching this new piece. 7. The grid changes so the corner can be placed seamlessly next to the last horizontal wall piece. (left click) 8. Release the corner piece (right click), select a vertical wall piece from the entity list. 9. The filter changes 10. The grid changes. 11. (and so on) ... The advantage I see here is that the amount of work required to get this working is very small. Filtering a listview in GTK+ is trivial. The grid and alignment stuff is already there, it just needs to be toggled via a function call instead of a button press. No need for extra highlighting, edge detection, showing "drop down" lists of matching mapobjects (although I would quite like the latter, so maybe at a later point it could be added as an alternative for picking from the entity list.). There is a second part to all that, and that is defining the meta-data required by the above. I do like your general idea here, as it seems much more convenient than what I had in mind. But instead of adding a special "connector" shape, perhaps we could just stick to the four edges (back, front, left, right) of a tile (I'd rather not worry about top and bottom). Consider the following ASCII art Let that be a horizontal wall piece. You'd have connecting edges on the left and right. ,-----------, A '-----------' A Since you want to be able to add that same wall piece on either side, your connecting edges would have to have the same id. Now let there be a matching corner tile. ,-----, A '---, | | | |_| B The left side would have the same id as the horizontal wall above. The front side would have a different id, equal to that of matching vertical wall pieces. When the horizontal piece is selected, the filter would show the corner since one of its sides has the same id. We could even improve the code and only consider ids of facing sides. (I.e. object A left id == object B right id would be a match whereas object A left id == object B left id would not result in a match). A ground tile OTOH would usually have the same id on all four sides. A transition tile between different types of ground would have different ids. The auto-filtering would then work well for those too. For most decoration, ids for the sides would not make sense. But there might be exceptions, for example if you have a middle part of a table or bench and two corner parts. In addition to the side ids, we'd need to specify the alignment meta data. I don't think we can get away with a simplistic center/left/right scheme. We may need something similar to what you proposed: the area where the connection is made. Again, I would keep it simple and just specify one such "connector" per side, with a start and end position. Initially those would be the corner points of that side, so for a lot of tiles no change to the values would be required. For L, T, or X shapes, you could adapt them as needed, In theory, it would be nice to specify the "length" once for each id, because matching "connectors" should be the same size on every shape. Then you would just adapt the starting point of the connector, if necessary. But in practice, the implementation would be more difficult without much added benefit. The grid can then be positioned such that the connectors on facing sides line up, which is simple math. Implementation wise, a "connector" object would have a side, an id, and two integers for start and end position. (Since we already know the side, we only need one coordinate for each). Each model then simply gets a list of connectors. That way, if we want to get fancy, you could have multiple connectors per side. For now, I can't think of a case where this would be needed. A GUI for editing these four properties would be easy to add to modeller and I wouldn't even mind saving the connector data in the actual model. In addition, the selected connector could be displayed on the model, so it would be easier to set start and end. OTOH, maybe keeping connector data separate from the model would allow to "pick" from a list of existing connectors. That might make adding connectors to a model easier, as you do not have to type the id every time. I'm certainly open to suggestions here. As for the other meta-data fields you suggested: * Tags: my idea is that you can add additional tags in mapedit, together with the "automatic", directory based tags. There's already a tab in the entity property dialog for that purpose, it just has no logic implemented yet. The property dialog shows the first time you add a new object to the map, and it can be brought up any time later by hovering over an object and pressing enter. My idea was, that the tag list for that mapobject would have the same functionality as the tag list in the filter dialog, so that you can bring that up instead to filter for similar objects without the need to know which tags might be assigned to any specific object. * Description: not sure if this should go into modeller or mapedit. But I assume you'd want to be able to see it in mapedit. Maybe I've got an idea here: would it be helpful if the entity property dialog had a button that would open the current mapobject in modeller? Then you could edit description and tags and stuff in modeller (where it would seem to belong more naturally) and only have a readonly display in mapedit, Don't expect fancy stuff like automatic synchronisation when saving in modeller, however! But it's only a single button click to reload the entity list anyway. Okay, this was kinda long, so lets hear your opinion first. I admit that it's not as fancy as what you had in mind (shows I'm no artist, just a lazy programmer), but it should come close in functionality and require only a little bit of additional coding to make it work. So what do you say? Kai > My 2p on the filtering: > > Perhaps it's better to reflect the directory structure of the models in > mapedit for now. Related wall parts and suchlike are already grouped in a > single directory, so we can exploit that. Perhaps have one > pane/dialog/whatever with collapsible directories (like Windows Explorer) and > another which then shows a list of mapobjects within the currently selected > directory. > As far as the templates go, there are a few simple options for hiding them: > - We just move them out of the gfx48/models48 directory trees and keep them > separately somewhere else. > - Or: In mapedit we just hide any directory whose name matches *template* > (possibly this can be enabled/disabled via a tickbox somewhere). > > Ultimately though, I think meta-data that describes which mapobjects fit > together and user-defined tags are the way to go. Once we have a format for > such data and have augmented the mapobjects with it we can do much better > filtering. IMHO, finding mapobjects that way will ultimately be the default, > so users don't need to know or care about the directory structure. > > I think the meta-data topic deserves a bit more discussion first though. Off > the top of my head, I'd like support for stuff like: > > - User-defined keywords (aka tags) to help categorise the mapobjects > - Descriptions: I'm thinking a free text field where designers can put > comments about intended usage, tips, instructions etc. > > As for describing how objects fit together, I'd propose something like the > following: > > - We have something that describes the surfaces where two related objects > touch. E.g. the left & right vertical sides of a facing wall piece. When > tiling that piece, the left side of one touches the right of the other. Let's > call it a "connecting surface" for now (can't think of a snappier name right > now). > - This connecting surface would most likely be created in the modeller > as a special kind of shape. It is saved as an individual file though. > - It gets a unique ID assigned to it (probably automatically) > - Possibly it has an optional, user-friendly display name too > > - Then, when creating actual object in the modeller you can import relevant > connecting surfaces and position them on the model. The idea is that you > describe where any other object that contains the a connecting surface with > the same ID can connect. > > I think this is preferable to, for example, explicitly linking from one > object to another since that can quickly become a maintenance nightmare when > you get lots of objects. > > > Later on, the mapeditor can use this meta-data to suggest the next object to > place on the map. I imagine this to be a bit like auto-complete in an IDE or > browser address bar. E.g. I put an object on the map and as I move the mouse > cursor near one of its connecting surfaces I get some kind of indication that > there is a connecting surface (maybe it lights up or I get a different > cursor). Some key or button press then displays a new object that is > connected to the previous one (maybe it's duplicate of the one I just placed > initially) and using some other button I can cycle through other available > objects until I find the one I want. > > Hmm... this'll be a lot easier to describe in picture. I'll make a quick UI > mock-up. brb! > > > - James > > > > > On 1 Jun 2011, at 19:49, Kai Sterker wrote: > >> Seems I've ran into a bit of trouble with my tag based filtering idea >> for mapedit. I've attached the filter dialog I've implemented so far, >> but I'd like to get some input on the underlying logic. >> >> Basically, there are two ways to filter the list of map objects: show >> only objects that "match" the current object, i.e. all objects that >> could possibly be placed seamlessly next to the current object. Since >> the meta-data for this feature would have to be supplied by the user, >> I did not start on this type of filter yet. I've got some concept in >> mind and I don't expect much trouble there. >> >> I did start with the supposedly easier, tag based filtering, where the >> components of the model path make up the tags attached to each model. >> (In the future, this might be extended with user-supplied tags, too). >> The result of the current model48/ content is shown in the filter >> dialog screenshot (The Count column gives the number of models with >> the given tag). >> >> My idea was, to automatically exclude the "template" stuff from the >> model list, but in a way that would be obvious to the user. So it's in >> the list like a regular tag, but unchecked by default. Going with >> that, the filter logic would have to be "hide all objects that contain >> 'template/' in their file path". But then I thought, when editing a >> map, I might want to see all "inside" "walls". And it would be easier >> if I could just check those two tags to narrow down the list. But that >> would also include all the inside wall templates. And now I am stuck, >> not really able to decide which route to go. >> >> Maybe just hardcode the template stuff filtering and otherwise go with >> the latter filtering logic? >> >> Or there could be two columns of checkboxes, one for inclusion and the >> other for exclusion. Then I could include "inside" "wall"s and exclude >> "templates" at the same time (and "stone" and "mine" and "cave" walls >> too, if I wanted), OTOH, perhaps I'd be better of to just filter for >> "plaster" "walls" then. >> >> Anyone got a better idea? >> >> >> I've got some stuff to work on besides the filtering, so I'll let that >> sit for a little and wait for your suggestions. >> >> Kai >> <filter.png>_______________________________________________ >> Adonthell-devel mailing list >> Adonthell-devel@nongnu.org >> https://lists.nongnu.org/mailman/listinfo/adonthell-devel > > _______________________________________________ Adonthell-devel mailing list Adonthell-devel@nongnu.org https://lists.nongnu.org/mailman/listinfo/adonthell-devel