EntityBaseDraggable

The base class for game entities that should be used with the LevelEditor. More...

Import Statement: import VPlay 2.0
Inherits:

EntityBase

Properties

Signals

Detailed Description

This component adds functionality for entities to be used with the LevelEditor. When you use this component as the base item of your entity, the user will be able to create new entities from a BuildEntityButton. Also, it is selectable by clicking on it, and the position can be changed by dragging it. To improve the user experience for mobile users, a dragOffset is added while the entity is dragged to a new position. When the new position is not available because another game entity occupies it, a red, transparent rectangle will appear. You can change this default behavior by setting showRectangleWhenBuildingNotAllowed to false.

Snapped Dragging

In some cases, you will want to limit the entity positioning in a level to a raster. In that case, you can define a gridSize. The entity is then snapped to this grid. When the gridSize is set to 16 for example, the entity can only be positioned at the x and y values 0, 16, 32, and so on.

By default, the colliderSize has the same value as gridSize. However, you can also set the gridSize to a smaller value, which allows positioning with higher accuracy of the entity.

Blinking of Selected Entity

The EntityBaseDraggable provides a convenience property opacityChangeItemWhileSelected which you can set to the visual property that should fade in and out while it is selected. The entity gets selected by clicking on the entity. To reset the entityState from "selected" to the default value, reset it when a the entity is not selected. See the Blinking of Selected Entity Example for more details.

Example Usage

The only required property for this component is setting the size of selectionMouseArea to your visual component of the entity. If you also want to check for collisions with other entities while the entity is dragged, set the colliderComponent property to your ColliderBase component.

The inLevelEditingMode property is set by default if a Scene with id scene exists. Also the gridSize property relies on a Scene with id scene by default. However, you can set these properties to any other scene if you have a different id for it.

Simple Example

The following example shows an entity definition that uses the scene id:

 import VPlay 2.0
 import QtQuick 2.0

 GameWindow {

   Scene {
     id: scene
     // the default gridSize property of Scene is 16
     gridSize: 32

     PhysicsWorld {
       id: phsysicsworld
     }

     EntityManager{
       id: entityManager
       entityContainer: scene
     }

     state: "levelEditing"

     LevelEditor {
         id: levelEditor
         toRemoveEntityTypes: ["block"]
         toStoreEntityTypes: ["block"]
     }

     EntityBaseDraggable {

       entityType: "block"

       // this property must be set for EntityBaseDraggable
       selectionMouseArea.anchors.fill: rectangle
       // for collision detection while dragging, also define colliderComponent
       colliderComponent: collider

       // these 2 properties would not need to be set explicitly, because there is a Scene component with id scene
       //gridSize: scene.gridSize
       //colliderSize: gridSize

       Rectangle {
         id: rectangle
         width: 32
         height: 32
         // NOTE: it is important that the entity position is the center of the visuals
         anchors.centerIn: parent
         color: "brown"
       }

       BoxCollider {
         id: collider
         anchors.fill: rectangle
       }
     }
   }
 }

Blinking of Selected Entity Example

 import VPlay 2.0
 import QtQuick 2.0

 GameWindow {

   Scene {
     id: scene
     gridSize: 32

     // this gets set to the currently selected entity
     property variant selectedEntity

     function entitySelected(entity) {
       // reset the internal state of the old selected entity, to stop blinking of the selected obstacle
       if(selectedEntity && selectedEntity !== entity) {
         selectedEntity.entityState = ""
       }
       selectedEntity = entity
     }

     MouseArea {
       anchors.fill: parent
       onClicked: {
         // if this is called, not an entity was clicked but to an empty place in the scene
         // thus reset the entityState in here to the default value
         scene.entitySelected(null)
       }
     }

     EntityBaseDraggable {
       id: blockEntity

       entityType: "block"
       selectionMouseArea.anchors.fill: rectangle
       colliderComponent: collider

       // the rectangle will fade in and out while the entity is selected
       // the entityState property will have the value "entitySelected" during that time
       opacityChangeItemWhileSelected: rectangle

       // set the currently selected entity to this one
       onEntityClicked: scene.entitySelected(blockEntity)

       Rectangle {
         id: rectangle
         width: 32
         height: 32
         anchors.centerIn: parent
         color: "brown"
       }

       BoxCollider {
         id: collider
         anchors.fill: rectangle
       }
     }
   }
 }

Also see the Squaby Demo, StackTheBoxWithEditor Demo and OneMoreLevel Demo for example usage of the EntityBaseDraggable and LevelEditor.

Property Documentation

allowedToBuild : bool

You can query this read-only property to check if the entity is allowed to be built at the current position.


clickingAllowed : bool

Set this property to allow clicking onto the entity to select it. By default, this is set to inLevelEditingMode.


colliderCategoriesWhileDragged : int

This collision category is set to the colliderComponent while the entity is dragged. By default, the dragged entity will collide with every other collider, so the default group is Box.All!

See also BoxCollider::categories.


colliderCollidesWithWhileDragged : int

This collidesWith property is set to the colliderComponent while the entity is dragged. By default, the dragged entity will collide with every other collider, so the default group is Box.All!

See also BoxCollider::categories.


colliderComponent : variant

This property must be set, to hold the ColliderBase component for collision detection while dragging the entity. Only if no entity is colliding with the current position of the dragged entity, building is allowed. Also the colliderSize must be set, which is used for detecting a dragging out of the scene or level borders.

Note: The size of the collider is decreased while the entity is dragged, because otherwise a collision would be detected when two adjacent bodies would just touch each other. Thus do not connect to the colliderComponent size with any visual elements. Also the bodyType is set to Body.Dynamic, as otherwise no collisions between other static bodyTypes could be detected. After dragging, the collider gets reset to its initial property values before the dragging started.


colliderSize : int

This property is used for calculation if building the entity is allowed at a position. By default, it is set to the gridSize property.


delayDragOffset : bool

Set this to true if you want the EntityBaseDraggable::dragOffset to be delayed until an actual drag has started, instead of getting applied at the moment the entity is pressed. This makes sense if you need to click the entity and don't want the EntityBaseDraggable::dragOffset to be applied in those cases. By default, this is set to false.


dragOffset : variant

This point property holds the offset that should be applied when dragging the entity in the level. The default offset is set to Qt.point(0,-70). That means while the entity is dragged, it is shifted up by 70 pixels of the initial press position. That is required especially on mobile devices, because otherwise the entity would not be visible under the finger. On desktop platforms where a mouse is used for positioning, this offset might be set to Qt.point(0,0).

If you don't want the dragOffset to be applied immediately on pressing the entity, set EntityBaseDraggable::delayDragOffset to true.


draggingAllowed : bool

Set this property to allow dragging of the entity. By default, this is set to inLevelEditingMode.


entityState : string

This property holds the current state of the EntityBaseDraggable. It can either be "entityDragged", "entitySelected" or the default state "".

Note: The entityState must be reset to its default state if the entitySelected state was reached. Usually you have a MouseArea over the complete scene, and then reset the entityState if an empty spot was clicked or another entity got selected. See the Blinking of Selected Entity Example for a full source code example.


forbidBuild : bool

This property allows you to manually forbid building of this entity. You can use this for example to prohibit the dragging of an entity into a certain area of the scene.

This QML property was introduced in V-Play 2.6.2.


gridSize : real

This property is needed for snapping the entity position to a grid. The default value is scene.gridSize. If no object with id scene is found, the gridSize is set to 1.

See also Scene::gridSize and Snapped Dragging.


ignoreBounds : bool

When setting this property to true, you can drag & drop entities outside the level boundaries.

This QML property was introduced in V-Play 2.6.2.


inLevelEditingMode : bool

Only if this property is set to true, dragging and clicking on the selectionMouseArea is allowed. Thus the default value of clickingAllowed, draggingAllowed and selectEntityWhenClickedAllowed are set to this value.

The default value is set to scene.state === "levelEditing". So if you set the state of your game scene with the id scene to levelEditing, clicking, dragging and selecting is true. If no id with scene is found, the default value is true.


levelHeight : real

This property holds the height of the EntityManager::entityContainer. If no id with entityManager can be found, the default value is 10000. This size limits the dragging of the entity so it cannot be dragged out of the level. So the selectionMouseArea.drag.maximumY is set to this value by default.


levelWidth : real

This property holds the width of the EntityManager::entityContainer. If no id with entityManager can be found, the default value is 10000. This size limits the dragging of the entity so it cannot be dragged out of the level. So the selectionMouseArea.drag.maximumX is set to this value by default.


notAllowedRectangle : alias

This property alias points to the Rectangle element of red color, which is shown by default when building is not allowed.


opacityChangeItemWhileSelected : alias

Set this property to the visual component that should blink while it is selected. If none is selected, no visual will fade in and out while selected.

Make sure to reset the entityState after another entity was selected. See the Blinking of Selected Entity Example for a full source code example.


selectionMouseArea : alias

This alias property points to the MouseArea that is used to drag or click the entity, when it is already in the level. So for allowing to drag the entity once it was positioned in the level, the size of this MouseArea should be set to the visual component of the entity. Either use selectionMouseArea.anchors.fill to set the size, or by assigning the width & height manually, probably together with the anchors.centerIn: parent when the visual part is centered at the entity position.


showRectangleWhenBuildingNotAllowed : bool

This property holds whether a red rectangle is displayed, if the entity can not be dragged to the current position. By default, a red rectangle with the size of the colliderComponent and opacity of 0.5 is shown. You can access it with the notAllowedRectangle property.

If you want a custom overlay when building is not allowed, you can listen to a change of allowedToBuild like in this example:

 EntityBaseDraggable {

   showRectangleWhenBuildingNotAllowed: false

   // use a custom Image instead of the red rectangle
   Image {
     // connect the visible property with the allowedToBuild property from EntityBaseDraggable
     visible: !allowedToBuild
     source: "buildingNotAllowed.png"
   }
 }

Signal Documentation

beginContactWhileDragged(variant other)

This handler gets called when the entity starts colliding with another fixture while dragging it. You have access to the colliding fixture via "other".

 EntityBaseDraggable {
   onBeginContactWhileDragged: {
     var fixture = other;
     var body = other.getBody();
     var collidedEntity = body.target;
     var collidedEntityType = collidedEntity.entityType;
     console.log("onBeginContactWhileDragged: collided with entity " + collidedEntity)
   }
 }

endContactWhileDragged(variant other)

This handler gets called when the entity stops colliding with another fixture while dragging it. You have access to the colliding fixture via "other".

 EntityBaseDraggable {
   onEndContactWhileDragged: {
     var fixture = other;
     var body = other.getBody();
     var collidedEntity = body.target;
     var collidedEntityType = collidedEntity.entityType;
     console.log("onEndContactWhileDragged: collided with entity " + collidedEntity)
   }
 }

entityClicked()

This handler is called when the entity got clicked.


entityPressAndHold()

This handler is called when the entity got pressed and held, i.e. if there is a long press (currently 800ms).

You can use this handler for example to open a popup menu to modify or delete the entity.


entityPressed()

This handler is called when the entity got pressed.


entityReleased()

This handler is called when the entity got released.


Videos

Voted #1 for:

  • Easiest to learn
  • Most time saving
  • Best support

Develop Cross-Platform Apps and Games 50% Faster!

  • Voted the best supported, most time-saving and easiest to learn cross-platform development tool
  • Based on the Qt framework, with native performance and appearance on all platforms including iOS and Android
  • Offers a variety of plugins to monetize, analyze and engage users
FREE!
create apps
create games
cross platform
native performance
3rd party services
game network
multiplayer
level editor
easiest to learn
biggest time saving
best support