summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--doc/classes/Font.xml2
-rw-r--r--doc/classes/KinematicBody.xml2
-rw-r--r--doc/classes/KinematicBody2D.xml2
-rw-r--r--doc/classes/SpotLight.xml2
-rwxr-xr-xdoc/tools/makerst.py6
-rw-r--r--editor/editor_export.cpp4
-rw-r--r--editor/editor_file_dialog.cpp19
-rw-r--r--editor/filesystem_dock.cpp35
-rw-r--r--editor/filesystem_dock.h2
-rw-r--r--editor/plugins/asset_library_editor_plugin.cpp2
-rw-r--r--editor/plugins/tile_set_editor_plugin.cpp11
-rw-r--r--editor/project_export.cpp6
-rw-r--r--editor/scene_tree_dock.cpp6
-rw-r--r--methods.py2
-rw-r--r--modules/mono/mono_gd/gd_mono_field.cpp2
-rw-r--r--platform/android/export/export.cpp4
-rw-r--r--platform/iphone/export/export.cpp4
-rw-r--r--platform/javascript/export/export.cpp6
-rw-r--r--platform/osx/export/export.cpp4
-rw-r--r--platform/server/detect.py74
-rw-r--r--platform/uwp/export/export.cpp4
-rw-r--r--platform/x11/joypad_linux.cpp8
-rw-r--r--scene/audio/audio_stream_player.cpp4
-rw-r--r--scene/gui/file_dialog.cpp3
-rw-r--r--scene/gui/text_edit.cpp2
-rw-r--r--servers/audio_server.cpp6
-rw-r--r--servers/visual/visual_server_viewport.h3
-rw-r--r--version.py1
28 files changed, 163 insertions, 63 deletions
diff --git a/doc/classes/Font.xml b/doc/classes/Font.xml
index 3e47b167ef..6cb5e0b17a 100644
--- a/doc/classes/Font.xml
+++ b/doc/classes/Font.xml
@@ -4,7 +4,7 @@
Internationalized font and text drawing support.
</brief_description>
<description>
- Font contains a unicode compatible character set, as well as the ability to draw it with variable width, ascent, descent and kerning. For creating fonts from TTF files (or other font formats), see the editor support for fonts. TODO check wikipedia for graph of ascent/baseline/descent/height/etc.
+ Font contains a unicode compatible character set, as well as the ability to draw it with variable width, ascent, descent and kerning. For creating fonts from TTF files (or other font formats), see the editor support for fonts.
</description>
<tutorials>
</tutorials>
diff --git a/doc/classes/KinematicBody.xml b/doc/classes/KinematicBody.xml
index a4fade6ab2..83abd723d0 100644
--- a/doc/classes/KinematicBody.xml
+++ b/doc/classes/KinematicBody.xml
@@ -91,7 +91,7 @@
Moves the body along a vector. If the body collides with another, it will slide along the other body rather than stop immediately. If the other body is a [code]KinematicBody[/code] or [RigidBody], it will also be affected by the motion of the other body. You can use this to make moving or rotating platforms, or to make nodes push other nodes.
[code]linear_velocity[/code] is the velocity vector (typically meters per second). Unlike in [method move_and_collide], you should [i]not[/i] multiply it by [code]delta[/code] — the physics engine handles applying the velocity.
[code]floor_normal[/code] is the up direction, used to determine what is a wall and what is a floor or a ceiling. If set to the default value of [code]Vector3(0, 0, 0)[/code], everything is considered a wall. This is useful for topdown games.
- [i]TODO: Update for new stop_on_slode argument.[/i] If the body is standing on a slope and the horizontal speed (relative to the floor's speed) goes below [code]slope_stop_min_velocity[/code], the body will stop completely. This prevents the body from sliding down slopes when you include gravity in [code]linear_velocity[/code]. When set to lower values, the body will not be able to stand still on steep slopes.
+ If the body is standing on a slope and the horizontal speed (relative to the floor's speed) goes below [code]slope_stop_min_velocity[/code], the body will stop completely. This prevents the body from sliding down slopes when you include gravity in [code]linear_velocity[/code]. When set to lower values, the body will not be able to stand still on steep slopes.
If the body collides, it will change direction a maximum of [code]max_slides[/code] times before it stops.
[code]floor_max_angle[/code] is the maximum angle (in radians) where a slope is still considered a floor (or a ceiling), rather than a wall. The default value equals 45 degrees.
Returns the movement that remained when the body stopped. To get more detailed information about collisions that occurred, use [method get_slide_collision].
diff --git a/doc/classes/KinematicBody2D.xml b/doc/classes/KinematicBody2D.xml
index f1aac2c765..d5bfc91f66 100644
--- a/doc/classes/KinematicBody2D.xml
+++ b/doc/classes/KinematicBody2D.xml
@@ -91,7 +91,7 @@
Moves the body along a vector. If the body collides with another, it will slide along the other body rather than stop immediately. If the other body is a [code]KinematicBody2D[/code] or [RigidBody2D], it will also be affected by the motion of the other body. You can use this to make moving or rotating platforms, or to make nodes push other nodes.
[code]linear_velocity[/code] is the velocity vector in pixels per second. Unlike in [method move_and_collide], you should [i]not[/i] multiply it by [code]delta[/code] — the physics engine handles applying the velocity.
[code]floor_normal[/code] is the up direction, used to determine what is a wall and what is a floor or a ceiling. If set to the default value of [code]Vector2(0, 0)[/code], everything is considered a wall. This is useful for topdown games.
- [i]TODO: Update for stop_on_slope argument.[/i] If the body is standing on a slope and the horizontal speed (relative to the floor's speed) goes below [code]slope_stop_min_velocity[/code], the body will stop completely. This prevents the body from sliding down slopes when you include gravity in [code]linear_velocity[/code]. When set to lower values, the body will not be able to stand still on steep slopes.
+ If the body is standing on a slope and the horizontal speed (relative to the floor's speed) goes below [code]slope_stop_min_velocity[/code], the body will stop completely. This prevents the body from sliding down slopes when you include gravity in [code]linear_velocity[/code]. When set to lower values, the body will not be able to stand still on steep slopes.
If the body collides, it will change direction a maximum of [code]max_slides[/code] times before it stops.
[code]floor_max_angle[/code] is the maximum angle (in radians) where a slope is still considered a floor (or a ceiling), rather than a wall. The default value equals 45 degrees.
Returns the [code]linear_velocity[/code] vector, rotated and/or scaled if a slide collision occurred. To get more detailed information about collisions that occurred, use [method get_slide_collision].
diff --git a/doc/classes/SpotLight.xml b/doc/classes/SpotLight.xml
index 11f914aac2..56ba2fc5b9 100644
--- a/doc/classes/SpotLight.xml
+++ b/doc/classes/SpotLight.xml
@@ -4,7 +4,7 @@
Spotlight [Light], such as a reflector spotlight or a lantern.
</brief_description>
<description>
- A SpotLight light is a type of [Light] node that emits lights in a specific direction, in the shape of a cone. The light is attenuated through the distance and this attenuation can be configured by changing the energy, radius and attenuation parameters of [Light]. TODO: Image of a spotlight.
+ A SpotLight light is a type of [Light] node that emits lights in a specific direction, in the shape of a cone. The light is attenuated through the distance and this attenuation can be configured by changing the energy, radius and attenuation parameters of [Light].
</description>
<tutorials>
<link>https://docs.godotengine.org/en/latest/tutorials/3d/lights_and_shadows.html</link>
diff --git a/doc/tools/makerst.py b/doc/tools/makerst.py
index 22c0b5d1fd..4b5785f604 100755
--- a/doc/tools/makerst.py
+++ b/doc/tools/makerst.py
@@ -950,6 +950,12 @@ def make_method_signature(class_def, method_def, make_ref, state): # type: (Cla
if arg.default_value is not None:
out += '=' + arg.default_value
+ if isinstance(method_def, MethodDef) and method_def.qualifiers is not None and 'vararg' in method_def.qualifiers:
+ if len(method_def.parameters) > 0:
+ out += ', ...'
+ else:
+ out += '...'
+
out += ' **)**'
if isinstance(method_def, MethodDef) and method_def.qualifiers is not None:
diff --git a/editor/editor_export.cpp b/editor/editor_export.cpp
index 0423fdf4db..62c0228f6a 100644
--- a/editor/editor_export.cpp
+++ b/editor/editor_export.cpp
@@ -1466,6 +1466,10 @@ List<String> EditorExportPlatformPC::get_binary_extensions(const Ref<EditorExpor
Error EditorExportPlatformPC::export_project(const Ref<EditorExportPreset> &p_preset, bool p_debug, const String &p_path, int p_flags) {
ExportNotifier notifier(*this, p_preset, p_debug, p_path, p_flags);
+ if (!FileAccess::exists(p_path.get_base_dir())) {
+ return ERR_FILE_BAD_PATH;
+ }
+
String custom_debug = p_preset->get("custom_template/debug");
String custom_release = p_preset->get("custom_template/release");
diff --git a/editor/editor_file_dialog.cpp b/editor/editor_file_dialog.cpp
index cdc06503e9..da16c16966 100644
--- a/editor/editor_file_dialog.cpp
+++ b/editor/editor_file_dialog.cpp
@@ -1205,8 +1205,10 @@ void EditorFileDialog::_update_favorites() {
if (name == current)
setthis = true;
name = "/";
+
+ favorites->add_item(name, folder_icon);
} else if (name.ends_with("/")) {
- if (name == current)
+ if (name == current || name == current + "/")
setthis = true;
name = name.substr(0, name.length() - 1);
name = name.get_file();
@@ -1229,6 +1231,8 @@ void EditorFileDialog::_favorite_toggled(bool p_toggle) {
bool res = access == ACCESS_RESOURCES;
String cd = get_current_dir();
+ if (!cd.ends_with("/"))
+ cd += "/";
Vector<String> favorited = EditorSettings::get_singleton()->get_favorites();
@@ -1244,13 +1248,10 @@ void EditorFileDialog::_favorite_toggled(bool p_toggle) {
}
}
- if (found) {
+ if (found)
favorited.erase(cd);
- favorite->set_pressed(false);
- } else {
+ else
favorited.push_back(cd);
- favorite->set_pressed(true);
- }
EditorSettings::get_singleton()->set_favorites(favorited);
@@ -1494,7 +1495,9 @@ EditorFileDialog::EditorFileDialog() {
HBoxContainer *pathhb = memnew(HBoxContainer);
dir_prev = memnew(ToolButton);
+ dir_prev->set_tooltip(TTR("Previous Folder"));
dir_next = memnew(ToolButton);
+ dir_next->set_tooltip(TTR("Next Folder"));
dir_up = memnew(ToolButton);
dir_up->set_tooltip(TTR("Go to parent folder"));
@@ -1513,12 +1516,14 @@ EditorFileDialog::EditorFileDialog() {
dir->set_h_size_flags(SIZE_EXPAND_FILL);
refresh = memnew(ToolButton);
+ refresh->set_tooltip(TTR("Refresh"));
refresh->connect("pressed", this, "_update_file_list");
pathhb->add_child(refresh);
favorite = memnew(ToolButton);
favorite->set_flat(true);
favorite->set_toggle_mode(true);
+ favorite->set_tooltip(TTR("(Un)favorite current folder."));
favorite->connect("toggled", this, "_favorite_toggled");
pathhb->add_child(favorite);
@@ -1532,6 +1537,7 @@ EditorFileDialog::EditorFileDialog() {
mode_thumbnails->set_toggle_mode(true);
mode_thumbnails->set_pressed(display_mode == DISPLAY_THUMBNAILS);
mode_thumbnails->set_button_group(view_mode_group);
+ mode_thumbnails->set_tooltip(TTR("View items as a grid of thumbnails."));
pathhb->add_child(mode_thumbnails);
mode_list = memnew(ToolButton);
@@ -1539,6 +1545,7 @@ EditorFileDialog::EditorFileDialog() {
mode_list->set_toggle_mode(true);
mode_list->set_pressed(display_mode == DISPLAY_LIST);
mode_list->set_button_group(view_mode_group);
+ mode_list->set_tooltip(TTR("View items as a list."));
pathhb->add_child(mode_list);
drives = memnew(OptionButton);
diff --git a/editor/filesystem_dock.cpp b/editor/filesystem_dock.cpp
index 66deb42c11..b5d9071199 100644
--- a/editor/filesystem_dock.cpp
+++ b/editor/filesystem_dock.cpp
@@ -283,7 +283,7 @@ void FileSystemDock::_notification(int p_what) {
String ei = "EditorIcons";
button_reload->set_icon(get_icon("Reload", ei));
button_toggle_display_mode->set_icon(get_icon("Panels2", ei));
- button_file_list_display_mode->connect("toggled", this, "_toggle_file_display");
+ button_file_list_display_mode->connect("pressed", this, "_toggle_file_display");
files->connect("item_activated", this, "_file_list_activate_file");
button_hist_next->connect("pressed", this, "_fw_history");
@@ -350,7 +350,7 @@ void FileSystemDock::_notification(int p_what) {
button_toggle_display_mode->set_icon(get_icon("Panels2", ei));
button_hist_next->set_icon(get_icon("Forward", ei));
button_hist_prev->set_icon(get_icon("Back", ei));
- if (button_file_list_display_mode->is_pressed()) {
+ if (file_list_display_mode == FILE_LIST_DISPLAY_LIST) {
button_file_list_display_mode->set_icon(get_icon("FileThumbnail", "EditorIcons"));
} else {
button_file_list_display_mode->set_icon(get_icon("FileList", "EditorIcons"));
@@ -501,8 +501,8 @@ void FileSystemDock::_tree_thumbnail_done(const String &p_path, const Ref<Textur
}
}
-void FileSystemDock::_toggle_file_display(bool p_active) {
- _set_file_display(p_active);
+void FileSystemDock::_toggle_file_display() {
+ _set_file_display(file_list_display_mode != FILE_LIST_DISPLAY_LIST);
emit_signal("display_mode_changed");
}
@@ -1692,8 +1692,7 @@ void FileSystemDock::set_file_list_display_mode(FileListDisplayMode p_mode) {
if (p_mode == file_list_display_mode)
return;
- button_file_list_display_mode->set_pressed(p_mode == FILE_LIST_DISPLAY_LIST);
- _toggle_file_display(p_mode == FILE_LIST_DISPLAY_LIST);
+ _toggle_file_display();
}
Variant FileSystemDock::get_drag_data_fw(const Point2 &p_point, Control *p_from) {
@@ -2377,29 +2376,6 @@ FileSystemDock::FileSystemDock(EditorNode *p_editor) {
tree_search_box->connect("text_changed", this, "_search_changed", varray(tree_search_box));
toolbar2_hbc->add_child(tree_search_box);
- //toolbar_hbc->add_spacer();
-
- //Control *spacer = memnew( Control);
-
- /*
- button_open = memnew( Button );
- button_open->set_flat(true);
- button_open->connect("pressed",this,"_tree_toggle_collapsed");
- toolbar_hbc->add_child(button_open);
- button_open->hide();
- button_open->set_focus_mode(FOCUS_NONE);
- button_open->set_tooltip("Open the selected file.\nOpen as scene if a scene, or as resource otherwise.");
-
-
- button_instance = memnew( Button );
- button_instance->set_flat(true);
- button_instance->connect("pressed",this,"_instance_pressed");
- toolbar_hbc->add_child(button_instance);
- button_instance->hide();
- button_instance->set_focus_mode(FOCUS_NONE);
- button_instance->set_tooltip(TTR("Instance the selected scene(s) as child of the selected node."));
-
-*/
file_list_popup = memnew(PopupMenu);
file_list_popup->set_hide_on_window_lose_focus(true);
add_child(file_list_popup);
@@ -2441,7 +2417,6 @@ FileSystemDock::FileSystemDock(EditorNode *p_editor) {
path_hb->add_child(file_list_search_box);
button_file_list_display_mode = memnew(ToolButton);
- button_file_list_display_mode->set_toggle_mode(true);
path_hb->add_child(button_file_list_display_mode);
files = memnew(ItemList);
diff --git a/editor/filesystem_dock.h b/editor/filesystem_dock.h
index 7cf37a7634..cd052f9700 100644
--- a/editor/filesystem_dock.h
+++ b/editor/filesystem_dock.h
@@ -181,7 +181,7 @@ private:
void _tree_gui_input(Ref<InputEvent> p_event);
void _update_file_list(bool p_keep_selection);
- void _toggle_file_display(bool p_active);
+ void _toggle_file_display();
void _set_file_display(bool p_active);
void _fs_changed();
diff --git a/editor/plugins/asset_library_editor_plugin.cpp b/editor/plugins/asset_library_editor_plugin.cpp
index ab3936407b..a9e9607bc5 100644
--- a/editor/plugins/asset_library_editor_plugin.cpp
+++ b/editor/plugins/asset_library_editor_plugin.cpp
@@ -177,6 +177,8 @@ void EditorAssetLibraryItemDescription::set_image(int p_type, int p_index, const
thumbnail = thumbnail->duplicate();
Point2 overlay_pos = Point2((thumbnail->get_width() - overlay->get_width()) / 2, (thumbnail->get_height() - overlay->get_height()) / 2);
+ // Overlay and thumbnail need the same format for `blend_rect` to work.
+ thumbnail->convert(Image::FORMAT_RGBA8);
thumbnail->lock();
thumbnail->blend_rect(overlay, overlay->get_used_rect(), overlay_pos);
thumbnail->unlock();
diff --git a/editor/plugins/tile_set_editor_plugin.cpp b/editor/plugins/tile_set_editor_plugin.cpp
index e041c3d62e..5b54384ee0 100644
--- a/editor/plugins/tile_set_editor_plugin.cpp
+++ b/editor/plugins/tile_set_editor_plugin.cpp
@@ -337,13 +337,13 @@ TileSetEditor::TileSetEditor(EditorNode *p_editor) {
tools[SELECT_NEXT] = memnew(ToolButton);
tool_hb->add_child(tools[SELECT_NEXT]);
tool_hb->move_child(tools[SELECT_NEXT], WORKSPACE_CREATE_SINGLE);
- tools[SELECT_NEXT]->set_shortcut(ED_SHORTCUT("tileset_editor/next_shape", TTR("Select next coordinate"), KEY_PAGEDOWN));
+ tools[SELECT_NEXT]->set_shortcut(ED_SHORTCUT("tileset_editor/next_shape", TTR("Next Coordinate"), KEY_PAGEDOWN));
tools[SELECT_NEXT]->connect("pressed", this, "_on_tool_clicked", varray(SELECT_NEXT));
tools[SELECT_NEXT]->set_tooltip(TTR("Select the next shape, subtile, or Tile."));
tools[SELECT_PREVIOUS] = memnew(ToolButton);
tool_hb->add_child(tools[SELECT_PREVIOUS]);
tool_hb->move_child(tools[SELECT_PREVIOUS], WORKSPACE_CREATE_SINGLE);
- tools[SELECT_PREVIOUS]->set_shortcut(ED_SHORTCUT("tileset_editor/previous_shape", TTR("Select previous coordinate"), KEY_PAGEUP));
+ tools[SELECT_PREVIOUS]->set_shortcut(ED_SHORTCUT("tileset_editor/previous_shape", TTR("Previous Coordinate"), KEY_PAGEUP));
tools[SELECT_PREVIOUS]->set_tooltip(TTR("Select the previous shape, subtile, or Tile."));
tools[SELECT_PREVIOUS]->connect("pressed", this, "_on_tool_clicked", varray(SELECT_PREVIOUS));
@@ -2918,7 +2918,8 @@ void TileSetEditor::update_texture_list_icon() {
for (int current_idx = 0; current_idx < texture_list->get_item_count(); current_idx++) {
RID rid = texture_list->get_item_metadata(current_idx);
texture_list->set_item_icon(current_idx, texture_map[rid]);
- texture_list->set_item_icon_region(current_idx, Rect2(0, 0, 150, 100));
+ Size2 texture_size = texture_map[rid]->get_size();
+ texture_list->set_item_icon_region(current_idx, Rect2(0, 0, MIN(texture_size.x, 150), MIN(texture_size.y, 100)));
}
texture_list->update();
}
@@ -2931,10 +2932,14 @@ void TileSetEditor::update_workspace_tile_mode() {
for (int i = 1; i < WORKSPACE_MODE_MAX; i++) {
tool_workspacemode[i]->set_disabled(true);
}
+ tools[SELECT_NEXT]->set_disabled(true);
+ tools[SELECT_PREVIOUS]->set_disabled(true);
} else {
for (int i = 1; i < WORKSPACE_MODE_MAX; i++) {
tool_workspacemode[i]->set_disabled(false);
}
+ tools[SELECT_NEXT]->set_disabled(false);
+ tools[SELECT_PREVIOUS]->set_disabled(false);
}
if (workspace_mode != WORKSPACE_EDIT) {
diff --git a/editor/project_export.cpp b/editor/project_export.cpp
index 831ebde3a6..82a6a07805 100644
--- a/editor/project_export.cpp
+++ b/editor/project_export.cpp
@@ -1012,7 +1012,11 @@ void ProjectExportDialog::_export_all(bool p_debug) {
Error err = platform->export_project(preset, p_debug, preset->get_export_path(), 0);
if (err != OK) {
- error_dialog->set_text(TTR("Export templates for this platform are missing/corrupted:") + " " + platform->get_name());
+ if (err == ERR_FILE_BAD_PATH) {
+ error_dialog->set_text(TTR("The given export path doesn't exist:") + "\n" + preset->get_export_path().get_base_dir());
+ } else {
+ error_dialog->set_text(TTR("Export templates for this platform are missing/corrupted:") + " " + platform->get_name());
+ }
error_dialog->show();
error_dialog->popup_centered_minsize(Size2(300, 80));
ERR_PRINT("Failed to export project");
diff --git a/editor/scene_tree_dock.cpp b/editor/scene_tree_dock.cpp
index d931d5bb37..084830ed7b 100644
--- a/editor/scene_tree_dock.cpp
+++ b/editor/scene_tree_dock.cpp
@@ -336,9 +336,13 @@ void SceneTreeDock::_tool_selected(int p_tool, bool p_confirm_override) {
} break;
case TOOL_ATTACH_SCRIPT: {
+ List<Node *> selection = editor_selection->get_selected_node_list();
+ if (selection.empty())
+ break;
+
Node *selected = scene_tree->get_selected();
if (!selected)
- break;
+ selected = selection.front()->get();
Ref<Script> existing = selected->get_script();
diff --git a/methods.py b/methods.py
index 2d4dc4921f..7465962187 100644
--- a/methods.py
+++ b/methods.py
@@ -55,7 +55,7 @@ def update_version(module_version_string=""):
f.write("#define VERSION_STATUS \"" + str(version.status) + "\"\n")
f.write("#define VERSION_BUILD \"" + str(build_name) + "\"\n")
f.write("#define VERSION_MODULE_CONFIG \"" + str(version.module_config) + module_version_string + "\"\n")
- f.write("#define VERSION_YEAR " + str(2018) + "\n")
+ f.write("#define VERSION_YEAR " + str(version.year) + "\n")
f.close()
# NOTE: It is safe to generate this file here, since this is still executed serially
diff --git a/modules/mono/mono_gd/gd_mono_field.cpp b/modules/mono/mono_gd/gd_mono_field.cpp
index 48fa380456..5e9d4db122 100644
--- a/modules/mono/mono_gd/gd_mono_field.cpp
+++ b/modules/mono/mono_gd/gd_mono_field.cpp
@@ -49,7 +49,7 @@ void GDMonoField::set_value_from_variant(MonoObject *p_object, const Variant &p_
#define SET_FROM_ARRAY(m_type) \
{ \
MonoArray *managed = GDMonoMarshal::m_type##_to_mono_array(p_value.operator ::m_type()); \
- mono_field_set_value(p_object, mono_field, &managed); \
+ mono_field_set_value(p_object, mono_field, managed); \
}
switch (type.type_encoding) {
diff --git a/platform/android/export/export.cpp b/platform/android/export/export.cpp
index aab4bc3883..fc26039c28 100644
--- a/platform/android/export/export.cpp
+++ b/platform/android/export/export.cpp
@@ -1499,6 +1499,10 @@ public:
}
}
+ if (!FileAccess::exists(p_path.get_base_dir())) {
+ return ERR_FILE_BAD_PATH;
+ }
+
FileAccess *src_f = NULL;
zlib_filefunc_def io = zipio_create_io_from_file(&src_f);
diff --git a/platform/iphone/export/export.cpp b/platform/iphone/export/export.cpp
index f25c8a4a22..49f97e5946 100644
--- a/platform/iphone/export/export.cpp
+++ b/platform/iphone/export/export.cpp
@@ -839,6 +839,10 @@ Error EditorExportPlatformIOS::export_project(const Ref<EditorExportPreset> &p_p
}
}
+ if (!FileAccess::exists(dest_dir)) {
+ return ERR_FILE_BAD_PATH;
+ }
+
DirAccess *da = DirAccess::create(DirAccess::ACCESS_FILESYSTEM);
if (da) {
String current_dir = da->get_current_dir();
diff --git a/platform/javascript/export/export.cpp b/platform/javascript/export/export.cpp
index 5704433650..b7ca1eb1d7 100644
--- a/platform/javascript/export/export.cpp
+++ b/platform/javascript/export/export.cpp
@@ -211,6 +211,10 @@ Error EditorExportPlatformJavaScript::export_project(const Ref<EditorExportPrese
template_path = find_export_template(EXPORT_TEMPLATE_WEBASSEMBLY_RELEASE);
}
+ if (!FileAccess::exists(p_path.get_base_dir())) {
+ return ERR_FILE_BAD_PATH;
+ }
+
if (template_path != String() && !FileAccess::exists(template_path)) {
EditorNode::get_singleton()->show_warning(TTR("Template file not found:") + "\n" + template_path);
return ERR_FILE_NOT_FOUND;
@@ -360,7 +364,7 @@ Error EditorExportPlatformJavaScript::run(const Ref<EditorExportPreset> &p_prese
if (err) {
return err;
}
- OS::get_singleton()->shell_open(path);
+ OS::get_singleton()->shell_open(String("file://") + path);
return OK;
}
diff --git a/platform/osx/export/export.cpp b/platform/osx/export/export.cpp
index b8f6977b39..a0eccceed0 100644
--- a/platform/osx/export/export.cpp
+++ b/platform/osx/export/export.cpp
@@ -425,6 +425,10 @@ Error EditorExportPlatformOSX::export_project(const Ref<EditorExportPreset> &p_p
}
}
+ if (!FileAccess::exists(p_path.get_base_dir())) {
+ return ERR_FILE_BAD_PATH;
+ }
+
FileAccess *src_f = NULL;
zlib_filefunc_def io = zipio_create_io_from_file(&src_f);
diff --git a/platform/server/detect.py b/platform/server/detect.py
index 392a987ee9..90a4092412 100644
--- a/platform/server/detect.py
+++ b/platform/server/detect.py
@@ -1,7 +1,10 @@
import os
import platform
import sys
+from methods import get_compiler_version, use_gcc
+# This file is mostly based on platform/x11/detect.py.
+# If editing this file, make sure to apply relevant changes here too.
def is_active():
return True
@@ -26,10 +29,16 @@ def can_build():
def get_opts():
- from SCons.Variables import BoolVariable
+ from SCons.Variables import BoolVariable, EnumVariable
return [
BoolVariable('use_llvm', 'Use the LLVM compiler', False),
BoolVariable('use_static_cpp', 'Link libgcc and libstdc++ statically for better portability', False),
+ BoolVariable('use_ubsan', 'Use LLVM/GCC compiler undefined behavior sanitizer (UBSAN)', False),
+ BoolVariable('use_asan', 'Use LLVM/GCC compiler address sanitizer (ASAN))', False),
+ BoolVariable('use_lsan', 'Use LLVM/GCC compiler leak sanitizer (LSAN))', False),
+ EnumVariable('debug_symbols', 'Add debugging symbols to release builds', 'yes', ('yes', 'no', 'full')),
+ BoolVariable('separate_debug_symbols', 'Create a separate file containing debugging symbols', False),
+ BoolVariable('execinfo', 'Use libexecinfo on systems where glibc is not available', False),
]
@@ -43,13 +52,30 @@ def configure(env):
## Build type
if (env["target"] == "release"):
- env.Append(CCFLAGS=['-O2', '-fomit-frame-pointer'])
+ if (env["optimize"] == "speed"): #optimize for speed (default)
+ env.Prepend(CCFLAGS=['-O3'])
+ else: #optimize for size
+ env.Prepend(CCFLAGS=['-Os'])
+
+ if (env["debug_symbols"] == "yes"):
+ env.Prepend(CCFLAGS=['-g1'])
+ if (env["debug_symbols"] == "full"):
+ env.Prepend(CCFLAGS=['-g2'])
elif (env["target"] == "release_debug"):
- env.Append(CCFLAGS=['-O2', '-DDEBUG_ENABLED'])
+ if (env["optimize"] == "speed"): #optimize for speed (default)
+ env.Prepend(CCFLAGS=['-O2', '-DDEBUG_ENABLED'])
+ else: #optimize for size
+ env.Prepend(CCFLAGS=['-Os', '-DDEBUG_ENABLED'])
+
+ if (env["debug_symbols"] == "yes"):
+ env.Prepend(CCFLAGS=['-g1'])
+ if (env["debug_symbols"] == "full"):
+ env.Prepend(CCFLAGS=['-g2'])
elif (env["target"] == "debug"):
- env.Append(CCFLAGS=['-g2', '-DDEBUG_ENABLED', '-DDEBUG_MEMORY_ENABLED'])
+ env.Prepend(CCFLAGS=['-g3', '-DDEBUG_ENABLED', '-DDEBUG_MEMORY_ENABLED'])
+ env.Append(LINKFLAGS=['-rdynamic'])
## Architecture
@@ -59,6 +85,10 @@ def configure(env):
## Compiler configuration
+ if 'CXX' in env and 'clang' in os.path.basename(env['CXX']):
+ # Convenience check to enforce the use_llvm overrides when CXX is clang(++)
+ env['use_llvm'] = True
+
if env['use_llvm']:
if ('clang++' not in os.path.basename(env['CXX'])):
env["CC"] = "clang"
@@ -67,6 +97,35 @@ def configure(env):
env.Append(CPPFLAGS=['-DTYPED_METHOD_BIND'])
env.extra_suffix = ".llvm" + env.extra_suffix
+
+ if env['use_ubsan'] or env['use_asan'] or env['use_lsan']:
+ env.extra_suffix += "s"
+
+ if env['use_ubsan']:
+ env.Append(CCFLAGS=['-fsanitize=undefined'])
+ env.Append(LINKFLAGS=['-fsanitize=undefined'])
+
+ if env['use_asan']:
+ env.Append(CCFLAGS=['-fsanitize=address'])
+ env.Append(LINKFLAGS=['-fsanitize=address'])
+
+ if env['use_lsan']:
+ env.Append(CCFLAGS=['-fsanitize=leak'])
+ env.Append(LINKFLAGS=['-fsanitize=leak'])
+
+ if env['use_lto']:
+ env.Append(CCFLAGS=['-flto'])
+ if not env['use_llvm'] and env.GetOption("num_jobs") > 1:
+ env.Append(LINKFLAGS=['-flto=' + str(env.GetOption("num_jobs"))])
+ else:
+ env.Append(LINKFLAGS=['-flto'])
+ if not env['use_llvm']:
+ env['RANLIB'] = 'gcc-ranlib'
+ env['AR'] = 'gcc-ar'
+
+ env.Append(CCFLAGS=['-pipe'])
+ env.Append(LINKFLAGS=['-pipe'])
+
## Dependencies
# FIXME: Check for existence of the libs before parsing their flags with pkg-config
@@ -110,6 +169,10 @@ def configure(env):
env['builtin_libogg'] = False # Needed to link against system libtheora
env['builtin_libvorbis'] = False # Needed to link against system libtheora
env.ParseConfig('pkg-config theora theoradec --cflags --libs')
+ else:
+ list_of_x86 = ['x86_64', 'x86', 'i386', 'i586']
+ if any(platform.machine() in s for s in list_of_x86):
+ env["x86_libtheora_opt_gcc"] = True
if not env['builtin_libvpx']:
env.ParseConfig('pkg-config vpx --cflags --libs')
@@ -163,6 +226,9 @@ def configure(env):
env.Append(LIBS=['dl'])
if (platform.system().find("BSD") >= 0):
+ env["execinfo"] = True
+
+ if env["execinfo"]:
env.Append(LIBS=['execinfo'])
# Link those statically for portability
diff --git a/platform/uwp/export/export.cpp b/platform/uwp/export/export.cpp
index a4655117a7..8405608dd6 100644
--- a/platform/uwp/export/export.cpp
+++ b/platform/uwp/export/export.cpp
@@ -1265,6 +1265,10 @@ public:
}
}
+ if (!FileAccess::exists(p_path.get_base_dir())) {
+ return ERR_FILE_BAD_PATH;
+ }
+
Error err = OK;
FileAccess *fa_pack = FileAccess::open(p_path, FileAccess::WRITE, &err);
diff --git a/platform/x11/joypad_linux.cpp b/platform/x11/joypad_linux.cpp
index 7cf0a1ef1e..c4dd8fe0e0 100644
--- a/platform/x11/joypad_linux.cpp
+++ b/platform/x11/joypad_linux.cpp
@@ -367,12 +367,12 @@ void JoypadLinux::open_joypad(const char *p_path) {
joy.fd = fd;
joy.devpath = String(p_path);
setup_joypad_properties(joy_num);
- sprintf(uid, "%04x%04x", __bswap_16(inpid.bustype), 0);
+ sprintf(uid, "%04x%04x", BSWAP16(inpid.bustype), 0);
if (inpid.vendor && inpid.product && inpid.version) {
- uint16_t vendor = __bswap_16(inpid.vendor);
- uint16_t product = __bswap_16(inpid.product);
- uint16_t version = __bswap_16(inpid.version);
+ uint16_t vendor = BSWAP16(inpid.vendor);
+ uint16_t product = BSWAP16(inpid.product);
+ uint16_t version = BSWAP16(inpid.version);
sprintf(uid + String(uid).length(), "%04x%04x%04x%04x%04x%04x", vendor, 0, product, 0, version, 0);
input->joy_connection_changed(joy_num, true, name, uid);
diff --git a/scene/audio/audio_stream_player.cpp b/scene/audio/audio_stream_player.cpp
index 5c95cf4279..2688041d18 100644
--- a/scene/audio/audio_stream_player.cpp
+++ b/scene/audio/audio_stream_player.cpp
@@ -91,8 +91,10 @@ void AudioStreamPlayer::_mix_internal(bool p_fadeout) {
void AudioStreamPlayer::_mix_audio() {
- if (!stream_playback.is_valid() || !active)
+ if (!stream_playback.is_valid() || !active ||
+ (stream_paused && !stream_fade)) {
return;
+ }
if (stream_fade) {
_mix_internal(true);
diff --git a/scene/gui/file_dialog.cpp b/scene/gui/file_dialog.cpp
index 5599c64daa..059e59ea21 100644
--- a/scene/gui/file_dialog.cpp
+++ b/scene/gui/file_dialog.cpp
@@ -861,7 +861,7 @@ FileDialog::FileDialog() {
HBoxContainer *hbc = memnew(HBoxContainer);
dir_up = memnew(ToolButton);
- dir_up->set_tooltip(RTR("Go to parent folder"));
+ dir_up->set_tooltip(RTR("Go to parent folder."));
hbc->add_child(dir_up);
dir_up->connect("pressed", this, "_go_up");
@@ -871,6 +871,7 @@ FileDialog::FileDialog() {
dir->set_h_size_flags(SIZE_EXPAND_FILL);
refresh = memnew(ToolButton);
+ refresh->set_tooltip(RTR("Refresh"));
refresh->connect("pressed", this, "_update_file_list");
hbc->add_child(refresh);
diff --git a/scene/gui/text_edit.cpp b/scene/gui/text_edit.cpp
index f38bc62a3c..2bf2364873 100644
--- a/scene/gui/text_edit.cpp
+++ b/scene/gui/text_edit.cpp
@@ -666,7 +666,7 @@ void TextEdit::_notification(int p_what) {
bool brace_close_matching = false;
bool brace_close_mismatch = false;
- if (brace_matching_enabled) {
+ if (brace_matching_enabled && cursor.line >= 0 && cursor.line < text.size() && cursor.column >= 0) {
if (cursor.column < text[cursor.line].length()) {
//check for open
diff --git a/servers/audio_server.cpp b/servers/audio_server.cpp
index 14c555ab5b..8c092a02a2 100644
--- a/servers/audio_server.cpp
+++ b/servers/audio_server.cpp
@@ -259,11 +259,13 @@ void AudioServer::_driver_process(int p_frames, int32_t *p_buffer) {
float l = CLAMP(buf[from + j].l, -1.0, 1.0);
int32_t vl = l * ((1 << 20) - 1);
- p_buffer[(from_buf + j) * (cs * 2) + k * 2 + 0] = vl << 11;
+ int32_t vl2 = (vl < 0 ? -1 : 1) * (ABS(vl) << 11);
+ p_buffer[(from_buf + j) * (cs * 2) + k * 2 + 0] = vl2;
float r = CLAMP(buf[from + j].r, -1.0, 1.0);
int32_t vr = r * ((1 << 20) - 1);
- p_buffer[(from_buf + j) * (cs * 2) + k * 2 + 1] = vr << 11;
+ int32_t vr2 = (vr < 0 ? -1 : 1) * (ABS(vr) << 11);
+ p_buffer[(from_buf + j) * (cs * 2) + k * 2 + 1] = vr2;
}
} else {
diff --git a/servers/visual/visual_server_viewport.h b/servers/visual/visual_server_viewport.h
index 4e3015c020..5176551540 100644
--- a/servers/visual/visual_server_viewport.h
+++ b/servers/visual/visual_server_viewport.h
@@ -90,7 +90,8 @@ public:
}
CanvasKey(const RID &p_canvas, int p_layer, int p_sublayer) {
canvas = p_canvas;
- stacking = ((int64_t)p_layer << 32) + p_sublayer;
+ int64_t sign = p_layer < 0 ? -1 : 1;
+ stacking = sign * (((int64_t)ABS(p_layer)) << 32) + p_sublayer;
}
int get_layer() const { return stacking >> 32; }
};
diff --git a/version.py b/version.py
index 17be155464..0d85b83b8d 100644
--- a/version.py
+++ b/version.py
@@ -4,3 +4,4 @@ major = 3
minor = 1
status = "beta"
module_config = ""
+year = 2019