diff --git a/projects/openttd_vs100.vcxproj b/projects/openttd_vs100.vcxproj --- a/projects/openttd_vs100.vcxproj +++ b/projects/openttd_vs100.vcxproj @@ -573,6 +573,8 @@ + + @@ -684,6 +686,7 @@ + diff --git a/projects/openttd_vs100.vcxproj.filters b/projects/openttd_vs100.vcxproj.filters --- a/projects/openttd_vs100.vcxproj.filters +++ b/projects/openttd_vs100.vcxproj.filters @@ -948,6 +948,12 @@ Header Files + + Header Files + + + Header Files + Header Files @@ -1281,6 +1287,9 @@ GUI Source Code + + GUI Source Code + GUI Source Code diff --git a/projects/openttd_vs80.vcproj b/projects/openttd_vs80.vcproj --- a/projects/openttd_vs80.vcproj +++ b/projects/openttd_vs80.vcproj @@ -1567,6 +1567,14 @@ > + + + + @@ -2019,6 +2027,10 @@ > + + diff --git a/projects/openttd_vs90.vcproj b/projects/openttd_vs90.vcproj --- a/projects/openttd_vs90.vcproj +++ b/projects/openttd_vs90.vcproj @@ -1564,6 +1564,14 @@ > + + + + @@ -2016,6 +2024,10 @@ > + + diff --git a/source.list b/source.list --- a/source.list +++ b/source.list @@ -306,6 +306,8 @@ terraform_gui.h textbuf_gui.h texteff.hpp +textfile_gui.h +textfile_type.h tgp.h tile_cmd.h tile_type.h @@ -436,6 +438,7 @@ statusbar_gui.cpp subsidy_gui.cpp terraform_gui.cpp +textfile_gui.cpp timetable_gui.cpp toolbar_gui.cpp town_gui.cpp diff --git a/src/ai/ai_gui.cpp b/src/ai/ai_gui.cpp --- a/src/ai/ai_gui.cpp +++ b/src/ai/ai_gui.cpp @@ -23,6 +23,7 @@ #include "../network/network.h" #include "../settings_func.h" #include "../network/network_content.h" +#include "../textfile_gui.h" #include "ai.hpp" #include "../script/api/script_log.hpp" @@ -563,6 +564,41 @@ new AISettingsWindow(&_ai_settings_desc, slot); } +/** Window for displaying the textfile of a AI. */ +struct ScriptTextfileWindow : public TextfileWindow { + CompanyID slot; ///< View the textfile of this CompanyID slot. + + ScriptTextfileWindow(const WindowDesc *desc, TextfileType file_type, CompanyID slot) : TextfileWindow(desc, file_type), slot(slot) + { + this->GetWidget(WID_TF_CAPTION)->SetDataTip(STR_TEXTFILE_README_CAPTION + file_type, STR_TOOLTIP_WINDOW_TITLE_DRAG_THIS); + + const char *textfile = GetConfig(slot)->GetScriptTextfile(file_type, slot); + + (slot == OWNER_DEITY) ? this->LoadTextfile(textfile, GAME_DIR) : this->LoadTextfile(textfile, AI_DIR); + + } + + /* virtual */ void SetStringParameters(int widget) const + { + if (widget == WID_TF_CAPTION) { + (slot == OWNER_DEITY) ? SetDParam(0, STR_CONTENT_TYPE_GAME_SCRIPT) : SetDParam(0, STR_CONTENT_TYPE_AI); + SetDParamStr(1, GetConfig(slot)->GetName()); + } + } +}; + +/** + * Open the AI version of the textfile window. + * @param file_type The type of textfile to display. + * @param slot The slot the Script is using. + */ +void ShowScriptTextfileWindow(TextfileType file_type, CompanyID slot) +{ + DeleteWindowByClass(WC_TEXTFILE); + new ScriptTextfileWindow(&_textfile_desc, file_type, slot); +} + + /** Widgets for the configure AI window. */ static const NWidgetPart _nested_ai_config_widgets[] = { NWidget(NWID_HORIZONTAL), @@ -597,6 +633,11 @@ NWidget(WWT_PUSHTXTBTN, COLOUR_YELLOW, WID_AIC_CONFIGURE), SetFill(1, 0), SetMinimalSize(93, 12), SetDataTip(STR_AI_CONFIG_CONFIGURE, STR_AI_CONFIG_CONFIGURE_TOOLTIP), NWidget(WWT_PUSHTXTBTN, COLOUR_YELLOW, WID_AIC_CLOSE), SetFill(1, 0), SetMinimalSize(93, 12), SetDataTip(STR_AI_SETTINGS_CLOSE, STR_NULL), EndContainer(), + NWidget(NWID_HORIZONTAL, NC_EQUALSIZE), SetPIP(7, 0, 7), + NWidget(WWT_PUSHTXTBTN, COLOUR_YELLOW, WID_AIC_TEXTFILE + TFT_README), SetFill(1, 0), SetResize(1, 0), SetDataTip(STR_TEXTFILE_VIEW_README, STR_NULL), + NWidget(WWT_PUSHTXTBTN, COLOUR_YELLOW, WID_AIC_TEXTFILE + TFT_CHANGELOG), SetFill(1, 0), SetResize(1, 0), SetDataTip(STR_TEXTFILE_VIEW_CHANGELOG, STR_NULL), + NWidget(WWT_PUSHTXTBTN, COLOUR_YELLOW, WID_AIC_TEXTFILE + TFT_LICENSE), SetFill(1, 0), SetResize(1, 0), SetDataTip(STR_TEXTFILE_VIEW_LICENCE, STR_NULL), + EndContainer(), NWidget(WWT_PUSHTXTBTN, COLOUR_YELLOW, WID_AIC_CONTENT_DOWNLOAD), SetFill(1, 0), SetMinimalSize(279, 12), SetPadding(0, 7, 9, 7), SetDataTip(STR_INTRO_ONLINE_CONTENT, STR_INTRO_TOOLTIP_ONLINE_CONTENT), EndContainer(), }; @@ -732,6 +773,13 @@ virtual void OnClick(Point pt, int widget, int click_count) { + if (widget >= WID_AIC_TEXTFILE && widget < WID_AIC_TEXTFILE + TFT_END) { + if (this->selected_slot == INVALID_COMPANY || GetConfig(this->selected_slot) == NULL) return; + + ShowScriptTextfileWindow((TextfileType)(widget - WID_AIC_TEXTFILE), this->selected_slot); + return; + } + switch (widget) { case WID_AIC_DECREASE: case WID_AIC_INCREASE: { @@ -822,6 +870,10 @@ this->SetWidgetDisabledState(WID_AIC_CONFIGURE, this->selected_slot == INVALID_COMPANY || GetConfig(this->selected_slot)->GetConfigList()->size() == 0); this->SetWidgetDisabledState(WID_AIC_MOVE_UP, this->selected_slot == OWNER_DEITY || this->selected_slot == INVALID_COMPANY || !IsEditable((CompanyID)(this->selected_slot - 1))); this->SetWidgetDisabledState(WID_AIC_MOVE_DOWN, this->selected_slot == OWNER_DEITY || this->selected_slot == INVALID_COMPANY || !IsEditable((CompanyID)(this->selected_slot + 1))); + + for (TextfileType tft = TFT_BEGIN; tft < TFT_END; tft++) { + this->SetWidgetDisabledState(WID_AIC_TEXTFILE + tft, this->selected_slot == INVALID_COMPANY || (GetConfig(this->selected_slot)->GetScriptTextfile(tft, this->selected_slot) == NULL)); + } } }; diff --git a/src/lang/english.txt b/src/lang/english.txt --- a/src/lang/english.txt +++ b/src/lang/english.txt @@ -2456,11 +2456,6 @@ STR_NEWGRF_SETTINGS_MOVEDOWN_TOOLTIP :{BLACK}Move the selected NewGRF file down the list STR_NEWGRF_SETTINGS_FILE_TOOLTIP :{BLACK}A list of the NewGRF files that are installed. -# Additional textfiles accompanying NewGRFs -STR_NEWGRF_SETTINGS_VIEW_README :{BLACK}View readme -STR_NEWGRF_SETTINGS_VIEW_CHANGELOG :{BLACK}Changelog -STR_NEWGRF_SETTINGS_VIEW_LICENSE :{BLACK}Licence - STR_NEWGRF_SETTINGS_SET_PARAMETERS :{BLACK}Set parameters STR_NEWGRF_SETTINGS_SHOW_PARAMETERS :{BLACK}Show parameters STR_NEWGRF_SETTINGS_TOGGLE_PALETTE :{BLACK}Toggle palette @@ -2492,11 +2487,6 @@ STR_NEWGRF_PARAMETERS_SETTING :{STRING1}: {ORANGE}{STRING1} STR_NEWGRF_PARAMETERS_NUM_PARAM :{LTBLUE}Number of parameters: {ORANGE}{NUM} -# NewGRF textfile window -STR_NEWGRF_README_CAPTION :{WHITE}NewGRF readme of {RAW_STRING} -STR_NEWGRF_CHANGELOG_CAPTION :{WHITE}NewGRF changelog of {RAW_STRING} -STR_NEWGRF_LICENSE_CAPTION :{WHITE}NewGRF licence of {RAW_STRING} - # NewGRF inspect window STR_NEWGRF_INSPECT_CAPTION :{WHITE}Inspect - {STRING5} STR_NEWGRF_INSPECT_PARENT_BUTTON :{BLACK}Parent @@ -3571,6 +3561,15 @@ STR_AI_SETTINGS_SETTING :{RAW_STRING}: {ORANGE}{STRING1} STR_AI_SETTINGS_START_DELAY :Number of days to start this AI after the previous one (give or take): {ORANGE}{STRING1} +# Textfile window +STR_TEXTFILE_README_CAPTION :{WHITE}{STRING} readme of {RAW_STRING} +STR_TEXTFILE_CHANGELOG_CAPTION :{WHITE}{STRING} changelog of {RAW_STRING} +STR_TEXTFILE_LICENCE_CAPTION :{WHITE}{STRING} licence of {RAW_STRING} +STR_TEXTFILE_VIEW_README :{BLACK}View readme +STR_TEXTFILE_VIEW_CHANGELOG :{BLACK}Changelog +STR_TEXTFILE_VIEW_LICENCE :{BLACK}Licence + + # Vehicle loading indicators STR_PERCENT_UP_SMALL :{TINY_FONT}{WHITE}{NUM}%{UP_ARROW} STR_PERCENT_UP :{WHITE}{NUM}%{UP_ARROW} diff --git a/src/newgrf_config.cpp b/src/newgrf_config.cpp --- a/src/newgrf_config.cpp +++ b/src/newgrf_config.cpp @@ -19,7 +19,7 @@ #include "window_func.h" #include "progress.h" #include "video/video_driver.hpp" -#include "strings_func.h" +#include "textfile_gui.h" #include "fileio_func.h" #include "fios.h" @@ -876,31 +876,9 @@ * @param type The type of the textfile to search for. * @return The filename for the textfile, \c NULL otherwise. */ -const char *GRFConfig::GetTextfile(TextfileType type) const +const char *GRFConfig::GetGRFTextfile(TextfileType type) const { - static const char * const prefixes[] = { - "readme", - "changelog", - "license", - }; - assert_compile(lengthof(prefixes) == TFT_END); - - const char *prefix = prefixes[type]; - if (this->filename == NULL) return NULL; - static char file_path[MAX_PATH]; - strecpy(file_path, this->filename, lastof(file_path)); - - char *slash = strrchr(file_path, PATHSEPCHAR); - if (slash == NULL) return NULL; - - seprintf(slash + 1, lastof(file_path), "%s_%s.txt", prefix, GetCurrentLanguageIsoCode()); - if (FioCheckFileExists(file_path, NEWGRF_DIR)) return file_path; - - seprintf(slash + 1, lastof(file_path), "%s_%.2s.txt", prefix, GetCurrentLanguageIsoCode()); - if (FioCheckFileExists(file_path, NEWGRF_DIR)) return file_path; - - seprintf(slash + 1, lastof(file_path), "%s.txt", prefix); - return FioCheckFileExists(file_path, NEWGRF_DIR) ? file_path : NULL; + return GetTextfile(type, NEWGRF_DIR, this->filename); } diff --git a/src/newgrf_config.h b/src/newgrf_config.h --- a/src/newgrf_config.h +++ b/src/newgrf_config.h @@ -17,6 +17,7 @@ #include "core/smallmap_type.hpp" #include "misc/countedptr.hpp" #include "fileio_type.h" +#include "textfile_gui.h" /** GRF config bit flags */ enum GCF_Flags { @@ -145,18 +146,6 @@ ~GRFTextWrapper(); }; -/** Additional text files accompanying NewGRFs */ -enum TextfileType { - TFT_BEGIN, - - TFT_README = TFT_BEGIN, ///< NewGRF readme - TFT_CHANGELOG, ///< NewGRF changelog - TFT_LICENSE, ///< NewGRF license - - TFT_END, -}; -DECLARE_POSTFIX_INCREMENT(TextfileType) - /** Information about GRF, used in the game and (part of it) in savegames */ struct GRFConfig : ZeroedMemoryAllocator { GRFConfig(const char *filename = NULL); @@ -187,7 +176,7 @@ bool IsOpenTTDBaseGRF() const; - const char *GetTextfile(TextfileType type) const; + const char *GetGRFTextfile(TextfileType type) const; const char *GetName() const; const char *GetDescription() const; const char *GetURL() const; diff --git a/src/newgrf_gui.cpp b/src/newgrf_gui.cpp --- a/src/newgrf_gui.cpp +++ b/src/newgrf_gui.cpp @@ -25,8 +25,7 @@ #include "querystring_gui.h" #include "core/geometry_func.hpp" #include "newgrf_text.h" -#include "fileio_func.h" -#include "fontcache.h" +#include "textfile_gui.h" #include "widgets/newgrf_widget.h" @@ -465,208 +464,38 @@ } /** Window for displaying the textfile of a NewGRF. */ -struct NewGRFTextfileWindow : public Window, MissingGlyphSearcher { - const GRFConfig *grf_config; ///< View the textfile of this GRFConfig. - TextfileType file_type; ///< Type of textfile to view. - int line_height; ///< Height of a line in the display widget. - Scrollbar *vscroll; ///< Vertical scrollbar. - Scrollbar *hscroll; ///< Horizontal scrollbar. - char *text; ///< Lines of text from the NewGRF's textfile. - SmallVector lines; ///< #text, split into lines in a table with lines. - uint max_length; ///< The longest line in the textfile (in pixels). +struct NewGRFTextfileWindow : public TextfileWindow { + const GRFConfig *grf_config; ///< View the textfile of this GRFConfig. - static const int TOP_SPACING = WD_FRAMETEXT_TOP; ///< Additional spacing at the top of the #WID_NT_BACKGROUND widget. - static const int BOTTOM_SPACING = WD_FRAMETEXT_BOTTOM; ///< Additional spacing at the bottom of the #WID_NT_BACKGROUND widget. + NewGRFTextfileWindow(const WindowDesc *desc, TextfileType file_type, const GRFConfig *c) : TextfileWindow(desc, file_type), grf_config(c) + { + this->GetWidget(WID_TF_CAPTION)->SetDataTip(STR_TEXTFILE_README_CAPTION + file_type, STR_TOOLTIP_WINDOW_TITLE_DRAG_THIS); - NewGRFTextfileWindow(const WindowDesc *desc, const GRFConfig *c, TextfileType file_type) : Window(), grf_config(c), file_type(file_type) - { - this->CreateNestedTree(desc); - this->GetWidget(WID_NT_CAPTION)->SetDataTip(STR_NEWGRF_README_CAPTION + file_type, STR_TOOLTIP_WINDOW_TITLE_DRAG_THIS); - this->vscroll = this->GetScrollbar(WID_NT_VSCROLLBAR); - this->hscroll = this->GetScrollbar(WID_NT_HSCROLLBAR); - this->FinishInitNested(desc); + const char *textfile = this->grf_config->GetGRFTextfile(file_type); - this->LoadTextfile(); + this->LoadTextfile(textfile, NEWGRF_DIR); } - ~NewGRFTextfileWindow() + /* virtual */ void SetStringParameters(int widget) const { - free(this->text); - } - - virtual void UpdateWidgetSize(int widget, Dimension *size, const Dimension &padding, Dimension *fill, Dimension *resize) - { - switch (widget) { - case WID_NT_BACKGROUND: - this->line_height = FONT_HEIGHT_MONO + 2; - resize->height = this->line_height; - - size->height = 4 * resize->height + TOP_SPACING + BOTTOM_SPACING; // At least 4 lines are visible. - size->width = max(200u, size->width); // At least 200 pixels wide. - break; + if (widget == WID_TF_CAPTION) { + SetDParam(0, STR_CONTENT_TYPE_NEWGRF); + SetDParamStr(1, this->grf_config->GetName()); } } - - virtual void SetStringParameters(int widget) const - { - if (widget == WID_NT_CAPTION) SetDParamStr(0, this->grf_config->GetName()); - } - - virtual void DrawWidget(const Rect &r, int widget) const - { - if (widget != WID_NT_BACKGROUND) return; - - int width = r.right - r.left + 1 - WD_BEVEL_LEFT - WD_BEVEL_RIGHT; - int height = r.bottom - r.top + 1 - WD_BEVEL_LEFT - WD_BEVEL_RIGHT; - - DrawPixelInfo new_dpi; - if (!FillDrawPixelInfo(&new_dpi, r.left + WD_BEVEL_LEFT, r.top, width, height)) return; - DrawPixelInfo *old_dpi = _cur_dpi; - _cur_dpi = &new_dpi; - - int left, right; - if (_current_text_dir == TD_RTL) { - left = width + WD_BEVEL_RIGHT - WD_FRAMETEXT_RIGHT - this->hscroll->GetCount(); - right = width + WD_BEVEL_RIGHT - WD_FRAMETEXT_RIGHT - 1 + this->hscroll->GetPosition(); - } else { - left = WD_FRAMETEXT_LEFT - WD_BEVEL_LEFT - this->hscroll->GetPosition(); - right = WD_FRAMETEXT_LEFT - WD_BEVEL_LEFT + this->hscroll->GetCount() - 1; - } - int top = TOP_SPACING; - for (uint i = 0; i < this->vscroll->GetCapacity() && i + this->vscroll->GetPosition() < this->lines.Length(); i++) { - DrawString(left, right, top + i * this->line_height, this->lines[i + this->vscroll->GetPosition()], TC_WHITE, SA_LEFT, false, FS_MONO); - } - - _cur_dpi = old_dpi; - } - - virtual void OnResize() - { - this->vscroll->SetCapacityFromWidget(this, WID_NT_BACKGROUND, TOP_SPACING + BOTTOM_SPACING); - this->hscroll->SetCapacityFromWidget(this, WID_NT_BACKGROUND); - } - -private: - uint search_iterator; ///< Iterator for the font check search. - - /* virtual */ void Reset() - { - this->search_iterator = 0; - } - - FontSize DefaultSize() - { - return FS_MONO; - } - - const char *NextString() - { - if (this->search_iterator >= this->lines.Length()) return NULL; - - return this->lines[this->search_iterator++]; - } - - /* virtual */ bool Monospace() - { - return true; - } - - /* virtual */ void SetFontNames(FreeTypeSettings *settings, const char *font_name) - { -#ifdef WITH_FREETYPE - strecpy(settings->mono_font, font_name, lastof(settings->mono_font)); -#endif /* WITH_FREETYPE */ - } - - /** - * Load the NewGRF's textfile text from file, and setup #lines, #max_length, and both scrollbars. - */ - void LoadTextfile() - { - this->lines.Clear(); - - /* Does GRF have a file of the demanded type? */ - const char *textfile = this->grf_config->GetTextfile(file_type); - if (textfile == NULL) return; - - /* Get text from file */ - size_t filesize; - FILE *handle = FioFOpenFile(textfile, "rb", NEWGRF_DIR, &filesize); - if (handle == NULL) return; - - this->text = ReallocT(this->text, filesize + 1); - size_t read = fread(this->text, 1, filesize, handle); - fclose(handle); - - if (read != filesize) return; - - this->text[filesize] = '\0'; - - /* Replace tabs and line feeds with a space since str_validate removes those. */ - for (char *p = this->text; *p != '\0'; p++) { - if (*p == '\t' || *p == '\r') *p = ' '; - } - - /* Check for the byte-order-mark, and skip it if needed. */ - char *p = this->text + (strncmp("\xEF\xBB\xBF", this->text, 3) == 0 ? 3 : 0); - - /* Make sure the string is a valid UTF-8 sequence. */ - str_validate(p, this->text + filesize, SVS_REPLACE_WITH_QUESTION_MARK | SVS_ALLOW_NEWLINE); - - /* Split the string on newlines. */ - *this->lines.Append() = p; - for (; *p != '\0'; p++) { - if (*p == '\n') { - *p = '\0'; - *this->lines.Append() = p + 1; - } - } - - CheckForMissingGlyphs(true, this); - - /* Initialize scrollbars */ - this->vscroll->SetCount(this->lines.Length()); - - this->max_length = 0; - for (uint i = 0; i < this->lines.Length(); i++) { - this->max_length = max(this->max_length, GetStringBoundingBox(this->lines[i], FS_MONO).width); - } - this->hscroll->SetCount(this->max_length + WD_FRAMETEXT_LEFT + WD_FRAMETEXT_RIGHT); - this->hscroll->SetStepSize(10); // Speed up horizontal scrollbar - } }; -static const NWidgetPart _nested_newgrf_textfile_widgets[] = { - NWidget(NWID_HORIZONTAL), - NWidget(WWT_CLOSEBOX, COLOUR_MAUVE), - NWidget(WWT_CAPTION, COLOUR_MAUVE, WID_NT_CAPTION), SetDataTip(STR_NULL, STR_TOOLTIP_WINDOW_TITLE_DRAG_THIS), - EndContainer(), - NWidget(NWID_HORIZONTAL), - NWidget(WWT_PANEL, COLOUR_MAUVE, WID_NT_BACKGROUND), SetMinimalSize(200, 125), SetResize(1, 12), SetScrollbar(WID_NT_VSCROLLBAR), - EndContainer(), - NWidget(NWID_VERTICAL), - NWidget(NWID_VSCROLLBAR, COLOUR_MAUVE, WID_NT_VSCROLLBAR), - EndContainer(), - EndContainer(), - NWidget(NWID_HORIZONTAL), - NWidget(NWID_HSCROLLBAR, COLOUR_MAUVE, WID_NT_HSCROLLBAR), - NWidget(WWT_RESIZEBOX, COLOUR_MAUVE), - EndContainer(), -}; +/** + * Open the NewGRF version of the textfile window. + * @param file_type The type of textfile to show. + * @param c The config of the NewGRF to use. + */ +void ShowNewGRFTextfileWindow(TextfileType file_type, const GRFConfig *c) +{ + DeleteWindowByClass(WC_TEXTFILE); + new NewGRFTextfileWindow(&_textfile_desc, file_type, c); +} -/** Window definition for the grf textfile window */ -static const WindowDesc _newgrf_textfile_desc( - WDP_CENTER, 630, 460, - WC_NEWGRF_TEXTFILE, WC_NONE, - WDF_UNCLICK_BUTTONS, - _nested_newgrf_textfile_widgets, lengthof(_nested_newgrf_textfile_widgets) -); - -void ShowNewGRFTextfileWindow(const GRFConfig *c, TextfileType file_type) -{ - DeleteWindowByClass(WC_NEWGRF_TEXTFILE); - new NewGRFTextfileWindow(&_newgrf_textfile_desc, c, file_type); -} static GRFPresetList _grf_preset_list; @@ -756,7 +585,7 @@ ~NewGRFWindow() { DeleteWindowByClass(WC_GRF_PARAMETERS); - DeleteWindowByClass(WC_NEWGRF_TEXTFILE); + DeleteWindowByClass(WC_TEXTFILE); if (this->editable && !this->execute) { CopyGRFConfigList(this->orig_list, this->actives, true); @@ -962,7 +791,7 @@ if (widget >= WID_NS_NEWGRF_TEXTFILE && widget < WID_NS_NEWGRF_TEXTFILE + TFT_END) { if (this->active_sel == NULL && this->avail_sel == NULL) return; - ShowNewGRFTextfileWindow(this->active_sel != NULL ? this->active_sel : this->avail_sel, (TextfileType)(widget - WID_NS_NEWGRF_TEXTFILE)); + ShowNewGRFTextfileWindow((TextfileType)(widget - WID_NS_NEWGRF_TEXTFILE), this->active_sel != NULL ? this->active_sel : this->avail_sel); return; } @@ -1185,8 +1014,8 @@ this->avail_sel = NULL; this->avail_pos = -1; this->avails.ForceRebuild(); - this->DeleteChildWindows(WC_QUERY_STRING); // Remove the parameter query window - this->DeleteChildWindows(WC_NEWGRF_TEXTFILE); // Remove the view textfile window + this->DeleteChildWindows(WC_QUERY_STRING); // Remove the parameter query window + this->DeleteChildWindows(WC_TEXTFILE); // Remove the view textfile window } virtual void OnDropdownSelect(int widget, int index) @@ -1294,7 +1123,7 @@ const GRFConfig *c = (this->avail_sel == NULL) ? this->active_sel : this->avail_sel; for (TextfileType tft = TFT_BEGIN; tft < TFT_END; tft++) { - this->SetWidgetDisabledState(WID_NS_NEWGRF_TEXTFILE + tft, c == NULL || c->GetTextfile(tft) == NULL); + this->SetWidgetDisabledState(WID_NS_NEWGRF_TEXTFILE + tft, c == NULL || c->GetGRFTextfile(tft) == NULL); } this->SetWidgetDisabledState(WID_NS_OPEN_URL, c == NULL || StrEmpty(c->GetURL())); @@ -1813,12 +1642,12 @@ NWidget(WWT_PUSHTXTBTN, COLOUR_YELLOW, WID_NS_OPEN_URL), SetFill(1, 0), SetResize(1, 0), SetDataTip(STR_CONTENT_OPEN_URL, STR_CONTENT_OPEN_URL_TOOLTIP), NWidget(WWT_PUSHTXTBTN, COLOUR_YELLOW, WID_NS_NEWGRF_TEXTFILE + TFT_README), SetFill(1, 0), SetResize(1, 0), - SetDataTip(STR_NEWGRF_SETTINGS_VIEW_README, STR_NULL), + SetDataTip(STR_TEXTFILE_VIEW_README, STR_NULL), NWidget(NWID_HORIZONTAL, NC_EQUALSIZE), NWidget(WWT_PUSHTXTBTN, COLOUR_YELLOW, WID_NS_NEWGRF_TEXTFILE + TFT_CHANGELOG), SetFill(1, 0), SetResize(1, 0), - SetDataTip(STR_NEWGRF_SETTINGS_VIEW_CHANGELOG, STR_NULL), + SetDataTip(STR_TEXTFILE_VIEW_CHANGELOG, STR_NULL), NWidget(WWT_PUSHTXTBTN, COLOUR_YELLOW, WID_NS_NEWGRF_TEXTFILE + TFT_LICENSE), SetFill(1, 0), SetResize(1, 0), - SetDataTip(STR_NEWGRF_SETTINGS_VIEW_LICENSE, STR_NULL), + SetDataTip(STR_TEXTFILE_VIEW_LICENCE, STR_NULL), EndContainer(), EndContainer(), NWidget(NWID_SELECTION, INVALID_COLOUR, WID_NS_SHOW_APPLY), diff --git a/src/script/api/game/game_window.hpp.sq b/src/script/api/game/game_window.hpp.sq --- a/src/script/api/game/game_window.hpp.sq +++ b/src/script/api/game/game_window.hpp.sq @@ -59,7 +59,7 @@ SQGSWindow.DefSQConst(engine, ScriptWindow::WC_SET_DATE, "WC_SET_DATE"); SQGSWindow.DefSQConst(engine, ScriptWindow::WC_AI_SETTINGS, "WC_AI_SETTINGS"); SQGSWindow.DefSQConst(engine, ScriptWindow::WC_GRF_PARAMETERS, "WC_GRF_PARAMETERS"); - SQGSWindow.DefSQConst(engine, ScriptWindow::WC_NEWGRF_TEXTFILE, "WC_NEWGRF_TEXTFILE"); + SQGSWindow.DefSQConst(engine, ScriptWindow::WC_TEXTFILE, "WC_TEXTFILE"); SQGSWindow.DefSQConst(engine, ScriptWindow::WC_TOWN_AUTHORITY, "WC_TOWN_AUTHORITY"); SQGSWindow.DefSQConst(engine, ScriptWindow::WC_VEHICLE_DETAILS, "WC_VEHICLE_DETAILS"); SQGSWindow.DefSQConst(engine, ScriptWindow::WC_VEHICLE_REFIT, "WC_VEHICLE_REFIT"); @@ -750,10 +750,6 @@ SQGSWindow.DefSQConst(engine, ScriptWindow::WID_NP_RESET, "WID_NP_RESET"); SQGSWindow.DefSQConst(engine, ScriptWindow::WID_NP_SHOW_DESCRIPTION, "WID_NP_SHOW_DESCRIPTION"); SQGSWindow.DefSQConst(engine, ScriptWindow::WID_NP_DESCRIPTION, "WID_NP_DESCRIPTION"); - SQGSWindow.DefSQConst(engine, ScriptWindow::WID_NT_CAPTION, "WID_NT_CAPTION"); - SQGSWindow.DefSQConst(engine, ScriptWindow::WID_NT_BACKGROUND, "WID_NT_BACKGROUND"); - SQGSWindow.DefSQConst(engine, ScriptWindow::WID_NT_VSCROLLBAR, "WID_NT_VSCROLLBAR"); - SQGSWindow.DefSQConst(engine, ScriptWindow::WID_NT_HSCROLLBAR, "WID_NT_HSCROLLBAR"); SQGSWindow.DefSQConst(engine, ScriptWindow::WID_NS_PRESET_LIST, "WID_NS_PRESET_LIST"); SQGSWindow.DefSQConst(engine, ScriptWindow::WID_NS_PRESET_SAVE, "WID_NS_PRESET_SAVE"); SQGSWindow.DefSQConst(engine, ScriptWindow::WID_NS_PRESET_DELETE, "WID_NS_PRESET_DELETE"); @@ -1158,6 +1154,10 @@ SQGSWindow.DefSQConst(engine, ScriptWindow::WID_TE_MUSIC_SOUND, "WID_TE_MUSIC_SOUND"); SQGSWindow.DefSQConst(engine, ScriptWindow::WID_TE_HELP, "WID_TE_HELP"); SQGSWindow.DefSQConst(engine, ScriptWindow::WID_TE_SWITCH_BAR, "WID_TE_SWITCH_BAR"); + SQGSWindow.DefSQConst(engine, ScriptWindow::WID_TF_CAPTION, "WID_TF_CAPTION"); + SQGSWindow.DefSQConst(engine, ScriptWindow::WID_TF_BACKGROUND, "WID_TF_BACKGROUND"); + SQGSWindow.DefSQConst(engine, ScriptWindow::WID_TF_VSCROLLBAR, "WID_TF_VSCROLLBAR"); + SQGSWindow.DefSQConst(engine, ScriptWindow::WID_TF_HSCROLLBAR, "WID_TF_HSCROLLBAR"); SQGSWindow.DefSQConst(engine, ScriptWindow::WID_TD_SORT_NAME, "WID_TD_SORT_NAME"); SQGSWindow.DefSQConst(engine, ScriptWindow::WID_TD_SORT_POPULATION, "WID_TD_SORT_POPULATION"); SQGSWindow.DefSQConst(engine, ScriptWindow::WID_TD_LIST, "WID_TD_LIST"); diff --git a/src/script/api/script_window.hpp b/src/script/api/script_window.hpp --- a/src/script/api/script_window.hpp +++ b/src/script/api/script_window.hpp @@ -246,11 +246,12 @@ */ WC_GRF_PARAMETERS = ::WC_GRF_PARAMETERS, + /** * textfile; Window numbers: * - 0 = #NewGRFTextfileWidgets */ - WC_NEWGRF_TEXTFILE = ::WC_NEWGRF_TEXTFILE, + WC_TEXTFILE = ::WC_TEXTFILE, /** @@ -1671,14 +1672,6 @@ WID_NP_DESCRIPTION = ::WID_NP_DESCRIPTION, ///< Multi-line description of a parameter. }; - /** Widgets of the #NewGRFTextfileWindow class. */ - enum NewGRFTextfileWidgets { - WID_NT_CAPTION = ::WID_NT_CAPTION, ///< The caption of the window. - WID_NT_BACKGROUND = ::WID_NT_BACKGROUND, ///< Panel to draw the textfile on. - WID_NT_VSCROLLBAR = ::WID_NT_VSCROLLBAR, ///< Vertical scrollbar to scroll through the textfile up-and-down. - WID_NT_HSCROLLBAR = ::WID_NT_HSCROLLBAR, ///< Horizontal scrollbar to scroll through the textfile left-to-right. - }; - /** Widgets of the #NewGRFWindow class. */ enum NewGRFStateWidgets { WID_NS_PRESET_LIST = ::WID_NS_PRESET_LIST, ///< Active NewGRF preset. @@ -2215,6 +2208,14 @@ WID_TE_SWITCH_BAR = ::WID_TE_SWITCH_BAR, ///< Only available when toolbar has been split to switch between different subsets. }; + /** Widgets of the #TextfileWindow class. */ + enum TextfileWidgets { + WID_TF_CAPTION = ::WID_TF_CAPTION, ///< The caption of the window. + WID_TF_BACKGROUND = ::WID_TF_BACKGROUND, ///< Panel to draw the textfile on. + WID_TF_VSCROLLBAR = ::WID_TF_VSCROLLBAR, ///< Vertical scrollbar to scroll through the textfile up-and-down. + WID_TF_HSCROLLBAR = ::WID_TF_HSCROLLBAR, ///< Horizontal scrollbar to scroll through the textfile left-to-right. + }; + /** Widgets of the #TownDirectoryWindow class. */ enum TownDirectoryWidgets { WID_TD_SORT_NAME = ::WID_TD_SORT_NAME, ///< Sort by town name. diff --git a/src/script/api/template/template_window.hpp.sq b/src/script/api/template/template_window.hpp.sq --- a/src/script/api/template/template_window.hpp.sq +++ b/src/script/api/template/template_window.hpp.sq @@ -155,8 +155,6 @@ template <> inline int Return(HSQUIRRELVM vm, ScriptWindow::SpriteAlignerWidgets res) { sq_pushinteger(vm, (int32)res); return 1; } template <> inline ScriptWindow::NewGRFParametersWidgets GetParam(ForceType, HSQUIRRELVM vm, int index, SQAutoFreePointers *ptr) { SQInteger tmp; sq_getinteger(vm, index, &tmp); return (ScriptWindow::NewGRFParametersWidgets)tmp; } template <> inline int Return(HSQUIRRELVM vm, ScriptWindow::NewGRFParametersWidgets res) { sq_pushinteger(vm, (int32)res); return 1; } - template <> inline ScriptWindow::NewGRFTextfileWidgets GetParam(ForceType, HSQUIRRELVM vm, int index, SQAutoFreePointers *ptr) { SQInteger tmp; sq_getinteger(vm, index, &tmp); return (ScriptWindow::NewGRFTextfileWidgets)tmp; } - template <> inline int Return(HSQUIRRELVM vm, ScriptWindow::NewGRFTextfileWidgets res) { sq_pushinteger(vm, (int32)res); return 1; } template <> inline ScriptWindow::NewGRFStateWidgets GetParam(ForceType, HSQUIRRELVM vm, int index, SQAutoFreePointers *ptr) { SQInteger tmp; sq_getinteger(vm, index, &tmp); return (ScriptWindow::NewGRFStateWidgets)tmp; } template <> inline int Return(HSQUIRRELVM vm, ScriptWindow::NewGRFStateWidgets res) { sq_pushinteger(vm, (int32)res); return 1; } template <> inline ScriptWindow::ScanProgressWidgets GetParam(ForceType, HSQUIRRELVM vm, int index, SQAutoFreePointers *ptr) { SQInteger tmp; sq_getinteger(vm, index, &tmp); return (ScriptWindow::ScanProgressWidgets)tmp; } @@ -223,6 +221,8 @@ template <> inline int Return(HSQUIRRELVM vm, ScriptWindow::ToolbarNormalWidgets res) { sq_pushinteger(vm, (int32)res); return 1; } template <> inline ScriptWindow::ToolbarEditorWidgets GetParam(ForceType, HSQUIRRELVM vm, int index, SQAutoFreePointers *ptr) { SQInteger tmp; sq_getinteger(vm, index, &tmp); return (ScriptWindow::ToolbarEditorWidgets)tmp; } template <> inline int Return(HSQUIRRELVM vm, ScriptWindow::ToolbarEditorWidgets res) { sq_pushinteger(vm, (int32)res); return 1; } + template <> inline ScriptWindow::TextfileWidgets GetParam(ForceType, HSQUIRRELVM vm, int index, SQAutoFreePointers *ptr) { SQInteger tmp; sq_getinteger(vm, index, &tmp); return (ScriptWindow::TextfileWidgets)tmp; } + template <> inline int Return(HSQUIRRELVM vm, ScriptWindow::TextfileWidgets res) { sq_pushinteger(vm, (int32)res); return 1; } template <> inline ScriptWindow::TownDirectoryWidgets GetParam(ForceType, HSQUIRRELVM vm, int index, SQAutoFreePointers *ptr) { SQInteger tmp; sq_getinteger(vm, index, &tmp); return (ScriptWindow::TownDirectoryWidgets)tmp; } template <> inline int Return(HSQUIRRELVM vm, ScriptWindow::TownDirectoryWidgets res) { sq_pushinteger(vm, (int32)res); return 1; } template <> inline ScriptWindow::TownAuthorityWidgets GetParam(ForceType, HSQUIRRELVM vm, int index, SQAutoFreePointers *ptr) { SQInteger tmp; sq_getinteger(vm, index, &tmp); return (ScriptWindow::TownAuthorityWidgets)tmp; } diff --git a/src/script/script_config.cpp b/src/script/script_config.cpp --- a/src/script/script_config.cpp +++ b/src/script/script_config.cpp @@ -13,6 +13,7 @@ #include "../settings_type.h" #include "../core/random_func.hpp" #include "script_info.hpp" +#include "../textfile_gui.h" void ScriptConfig::Change(const char *name, int version, bool force_exact_match, bool is_random) { @@ -198,3 +199,16 @@ size_t len = strlen(string); if (len > 0) string[len - 1] = '\0'; } + +/** + * Search a textfile file next to this Script. + * @param type The type of the textfile to search for. + * @param slot The company slot to look in. + * @return The filename for the textfile, \c NULL otherwise. + */ +const char *ScriptConfig::GetScriptTextfile(TextfileType type, CompanyID slot) const +{ + if (slot == INVALID_COMPANY || this->GetInfo() == NULL) return NULL; + + return GetTextfile(type, (slot == OWNER_DEITY) ? GAME_DIR : AI_DIR, this->GetInfo()->GetMainScript()); +} diff --git a/src/script/script_config.hpp b/src/script/script_config.hpp --- a/src/script/script_config.hpp +++ b/src/script/script_config.hpp @@ -16,6 +16,8 @@ #include #include "../core/smallmap_type.hpp" #include "../core/string_compare_type.hpp" +#include "../company_type.h" +#include "../textfile_gui.h" /** Bitmask of flags for Script settings. */ enum ScriptConfigFlags { @@ -161,6 +163,14 @@ */ void SettingsToString(char *string, size_t size) const; + /** + * Search a textfile file next to this script. + * @param type The type of the textfile to search for. + * @param slot #CompanyID to check status of. + * @return The filename for the textfile, \c NULL otherwise. + */ + const char *GetScriptTextfile(TextfileType type, CompanyID slot) const; + protected: const char *name; ///< Name of the Script int version; ///< Version of the Script diff --git a/src/textfile_gui.cpp b/src/textfile_gui.cpp new file mode 100644 --- /dev/null +++ b/src/textfile_gui.cpp @@ -0,0 +1,44 @@ +/* $Id$ */ + +/* + * This file is part of OpenTTD. + * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2. + * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see . + */ + +/** @file textfile_gui.cpp Implementation of textfile related functions. */ + +#include "stdafx.h" +#include "fileio_func.h" +#include "string_func.h" +#include "strings_func.h" +#include "textfile_type.h" + +const char *GetTextfile(TextfileType type, Subdirectory dir, const char *filename) +{ + static const char * const prefixes[] = { + "readme", + "changelog", + "license", + }; + assert_compile(lengthof(prefixes) == TFT_END); + const char *prefix = prefixes[type]; + + if (filename == NULL) return NULL; + + static char file_path[MAX_PATH]; + strecpy(file_path, filename, lastof(file_path)); + + char *slash = strrchr(file_path, PATHSEPCHAR); + if (slash == NULL) return NULL; + + seprintf(slash + 1, lastof(file_path), "%s_%s.txt", prefix, GetCurrentLanguageIsoCode()); + if (FioCheckFileExists(file_path, dir)) return file_path; + + seprintf(slash + 1, lastof(file_path), "%s_%.2s.txt", prefix, GetCurrentLanguageIsoCode()); + if (FioCheckFileExists(file_path, dir)) return file_path; + + seprintf(slash + 1, lastof(file_path), "%s.txt", prefix); + return FioCheckFileExists(file_path, dir) ? file_path : NULL; +} diff --git a/src/textfile_gui.h b/src/textfile_gui.h new file mode 100644 --- /dev/null +++ b/src/textfile_gui.h @@ -0,0 +1,228 @@ +/* $Id$ */ + +/* + * This file is part of OpenTTD. + * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2. + * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see . + */ + +/** @file textfile_gui.h GUI functions related to textfiles. */ + +#ifndef TEXTFILE_GUI_H +#define TEXTFILE_GUI_H + +#include "fileio_func.h" +#include "fontcache.h" +#include "gfx_type.h" +#include "gfx_func.h" +#include "string_func.h" +#include "strings_func.h" +#include "textfile_type.h" +#include "window_gui.h" + +#include "widgets/misc_widget.h" + +#include "table/strings.h" + +/** + * Search a textfile file next to this NewGRF. + * @param type The type of the textfile to search for. + * @param dir The subdirectory to search in. + * @param filename The filename to look for. + * @return The path to the textfile, \c NULL otherwise. + */ +const char *GetTextfile(TextfileType type, Subdirectory dir, const char *filename); + +/** Window for displaying a textfile */ +struct TextfileWindow : public Window, MissingGlyphSearcher { + TextfileType file_type; ///< Type of textfile to view. + int line_height; ///< Height of a line in the display widget. + Scrollbar *vscroll; ///< Vertical scrollbar. + Scrollbar *hscroll; ///< Horizontal scrollbar. + char *text; ///< Lines of text from the NewGRF's textfile. + SmallVector lines; ///< #text, split into lines in a table with lines. + uint max_length; ///< The longest line in the textfile (in pixels). + + static const int TOP_SPACING = WD_FRAMETEXT_TOP; ///< Additional spacing at the top of the #WID_TF_BACKGROUND widget. + static const int BOTTOM_SPACING = WD_FRAMETEXT_BOTTOM; ///< Additional spacing at the bottom of the #WID_TF_BACKGROUND widget. + + TextfileWindow(const WindowDesc *desc, TextfileType file_type) : Window(), file_type(file_type) + { + this->CreateNestedTree(desc); + this->vscroll = this->GetScrollbar(WID_TF_VSCROLLBAR); + this->hscroll = this->GetScrollbar(WID_TF_HSCROLLBAR); + this->FinishInitNested(desc); + } + + virtual ~TextfileWindow() + { + free(this->text); + } + + virtual void UpdateWidgetSize(int widget, Dimension *size, const Dimension &padding, Dimension *fill, Dimension *resize) + { + switch (widget) { + case WID_TF_BACKGROUND: + this->line_height = FONT_HEIGHT_MONO + 2; + resize->height = this->line_height; + + size->height = 4 * resize->height + TOP_SPACING + BOTTOM_SPACING; // At least 4 lines are visible. + size->width = max(200u, size->width); // At least 200 pixels wide. + break; + } + } + + virtual void SetStringParameters(int widget) const {}; + + virtual void DrawWidget(const Rect &r, int widget) const + { + if (widget != WID_TF_BACKGROUND) return; + + int width = r.right - r.left + 1 - WD_BEVEL_LEFT - WD_BEVEL_RIGHT; + int height = r.bottom - r.top + 1 - WD_BEVEL_LEFT - WD_BEVEL_RIGHT; + + DrawPixelInfo new_dpi; + if (!FillDrawPixelInfo(&new_dpi, r.left + WD_BEVEL_LEFT, r.top, width, height)) return; + DrawPixelInfo *old_dpi = _cur_dpi; + _cur_dpi = &new_dpi; + + int left, right; + if (_current_text_dir == TD_RTL) { + left = width + WD_BEVEL_RIGHT - WD_FRAMETEXT_RIGHT - this->hscroll->GetCount(); + right = width + WD_BEVEL_RIGHT - WD_FRAMETEXT_RIGHT - 1 + this->hscroll->GetPosition(); + } else { + left = WD_FRAMETEXT_LEFT - WD_BEVEL_LEFT - this->hscroll->GetPosition(); + right = WD_FRAMETEXT_LEFT - WD_BEVEL_LEFT + this->hscroll->GetCount() - 1; + } + int top = TOP_SPACING; + for (uint i = 0; i < this->vscroll->GetCapacity() && i + this->vscroll->GetPosition() < this->lines.Length(); i++) { + DrawString(left, right, top + i * this->line_height, this->lines[i + this->vscroll->GetPosition()], TC_WHITE, SA_LEFT, false, FS_MONO); + } + + _cur_dpi = old_dpi; + } + + virtual void OnResize() + { + this->vscroll->SetCapacityFromWidget(this, WID_TF_BACKGROUND, TOP_SPACING + BOTTOM_SPACING); + this->hscroll->SetCapacityFromWidget(this, WID_TF_BACKGROUND); + } + + uint search_iterator; ///< Iterator for the font check search. + + /* virtual */ void Reset() + { + this->search_iterator = 0; + } + + virtual FontSize DefaultSize() + { + return FS_MONO; + } + + virtual const char *NextString() + { + if (this->search_iterator >= this->lines.Length()) return NULL; + + return this->lines[this->search_iterator++]; + } + + /* virtual */ bool Monospace() + { + return true; + } + + /* virtual */ void SetFontNames(FreeTypeSettings *settings, const char *font_name) + { +#ifdef WITH_FREETYPE + strecpy(settings->mono_font, font_name, lastof(settings->mono_font)); +#endif /* WITH_FREETYPE */ + } + + /** + * Loads the textfile text from file, and setup #lines, #max_length, and both scrollbars. + */ + virtual void LoadTextfile(const char *textfile, Subdirectory dir) + { + if (textfile == NULL) return; + + this->lines.Clear(); + + /* Get text from file */ + size_t filesize; + FILE *handle = FioFOpenFile(textfile, "rb", dir, &filesize); + if (handle == NULL) return; + + this->text = ReallocT(this->text, filesize + 1); + size_t read = fread(this->text, 1, filesize, handle); + fclose(handle); + + if (read != filesize) return; + + this->text[filesize] = '\0'; + + /* Replace tabs and line feeds with a space since str_validate removes those. */ + for (char *p = this->text; *p != '\0'; p++) { + if (*p == '\t' || *p == '\r') *p = ' '; + } + + /* Check for the byte-order-mark, and skip it if needed. */ + char *p = this->text + (strncmp("\xEF\xBB\xBF", this->text, 3) == 0 ? 3 : 0); + + /* Make sure the string is a valid UTF-8 sequence. */ + str_validate(p, this->text + filesize, SVS_REPLACE_WITH_QUESTION_MARK | SVS_ALLOW_NEWLINE); + + /* Split the string on newlines. */ + *this->lines.Append() = p; + for (; *p != '\0'; p++) { + if (*p == '\n') { + *p = '\0'; + *this->lines.Append() = p + 1; + } + } + + CheckForMissingGlyphs(true, this); + + /* Initialize scrollbars */ + this->vscroll->SetCount(this->lines.Length()); + + this->max_length = 0; + for (uint i = 0; i < this->lines.Length(); i++) { + this->max_length = max(this->max_length, GetStringBoundingBox(this->lines[i], FS_MONO).width); + } + this->hscroll->SetCount(this->max_length + WD_FRAMETEXT_LEFT + WD_FRAMETEXT_RIGHT); + this->hscroll->SetStepSize(10); // Speed up horizontal scrollbar + } +}; + +/** Widgets for the textfile window. */ +static const NWidgetPart _nested_textfile_widgets[] = { + NWidget(NWID_HORIZONTAL), + NWidget(WWT_CLOSEBOX, COLOUR_MAUVE), + NWidget(WWT_CAPTION, COLOUR_MAUVE, WID_TF_CAPTION), SetDataTip(STR_NULL, STR_TOOLTIP_WINDOW_TITLE_DRAG_THIS), + EndContainer(), + NWidget(NWID_HORIZONTAL), + NWidget(WWT_PANEL, COLOUR_MAUVE, WID_TF_BACKGROUND), SetMinimalSize(200, 125), SetResize(1, 12), SetScrollbar(WID_TF_VSCROLLBAR), + EndContainer(), + NWidget(NWID_VERTICAL), + NWidget(NWID_VSCROLLBAR, COLOUR_MAUVE, WID_TF_VSCROLLBAR), + EndContainer(), + EndContainer(), + NWidget(NWID_HORIZONTAL), + NWidget(NWID_HSCROLLBAR, COLOUR_MAUVE, WID_TF_HSCROLLBAR), + NWidget(WWT_RESIZEBOX, COLOUR_MAUVE), + EndContainer(), +}; + +/** Window definition for the textfile window */ +static const WindowDesc _textfile_desc( + WDP_CENTER, 630, 460, + WC_TEXTFILE, WC_NONE, + WDF_UNCLICK_BUTTONS, + _nested_textfile_widgets, lengthof(_nested_textfile_widgets) +); + + + +#endif /* TEXTFILE_GUI_H */ diff --git a/src/textfile_type.h b/src/textfile_type.h new file mode 100644 --- /dev/null +++ b/src/textfile_type.h @@ -0,0 +1,27 @@ +/* $Id$ */ + +/* + * This file is part of OpenTTD. + * OpenTTD is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, version 2. + * OpenTTD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenTTD. If not, see . + */ + +/** @file textfile_type.h Types related to textfiles. */ + +#ifndef TEXTFILE_TYPE_H +#define TEXTFILE_TYPE_H + +/** Additional text files accompanying Tar archives */ +enum TextfileType { + TFT_BEGIN, + + TFT_README = TFT_BEGIN, ///< NewGRF readme + TFT_CHANGELOG, ///< NewGRF changelog + TFT_LICENSE, ///< NewGRF license + + TFT_END, +}; +DECLARE_POSTFIX_INCREMENT(TextfileType) + +#endif /* TEXTFILE_TYPE_H */ diff --git a/src/widgets/ai_widget.h b/src/widgets/ai_widget.h --- a/src/widgets/ai_widget.h +++ b/src/widgets/ai_widget.h @@ -13,6 +13,7 @@ #define WIDGETS_AI_WIDGET_H #include "../company_type.h" +#include "../textfile_type.h" /** Widgets of the #AIListWindow class. */ enum AIListWidgets { @@ -47,7 +48,8 @@ WID_AIC_CHANGE, ///< Select another AI button. WID_AIC_CONFIGURE, ///< Change AI settings button. WID_AIC_CLOSE, ///< Close window button. - WID_AIC_CONTENT_DOWNLOAD, ///< Download content button. + WID_AIC_TEXTFILE, ///< Open AI readme, changelog (+1) or license (+2). + WID_AIC_CONTENT_DOWNLOAD = WID_AIC_TEXTFILE + TFT_END, ///< Download content button. }; /** Widgets of the #AIDebugWindow class. */ diff --git a/src/widgets/misc_widget.h b/src/widgets/misc_widget.h --- a/src/widgets/misc_widget.h +++ b/src/widgets/misc_widget.h @@ -45,4 +45,12 @@ WID_Q_YES, ///< No button. }; +/** Widgets of the #TextfileWindow class. */ +enum NewGRFTextfileWidgets { + WID_TF_CAPTION, ///< The caption of the window. + WID_TF_BACKGROUND, ///< Panel to draw the textfile on. + WID_TF_VSCROLLBAR, ///< Vertical scrollbar to scroll through the textfile up-and-down. + WID_TF_HSCROLLBAR, ///< Horizontal scrollbar to scroll through the textfile left-to-right. +}; + #endif /* WIDGETS_MISC_WIDGET_H */ diff --git a/src/widgets/newgrf_widget.h b/src/widgets/newgrf_widget.h --- a/src/widgets/newgrf_widget.h +++ b/src/widgets/newgrf_widget.h @@ -29,14 +29,6 @@ WID_NP_DESCRIPTION, ///< Multi-line description of a parameter. }; -/** Widgets of the #NewGRFTextfileWindow class. */ -enum NewGRFTextfileWidgets { - WID_NT_CAPTION, ///< The caption of the window. - WID_NT_BACKGROUND, ///< Panel to draw the textfile on. - WID_NT_VSCROLLBAR, ///< Vertical scrollbar to scroll through the textfile up-and-down. - WID_NT_HSCROLLBAR, ///< Horizontal scrollbar to scroll through the textfile left-to-right. -}; - /** Widgets of the #NewGRFWindow class. */ enum NewGRFStateWidgets { WID_NS_PRESET_LIST, ///< Active NewGRF preset. diff --git a/src/window.cpp b/src/window.cpp --- a/src/window.cpp +++ b/src/window.cpp @@ -999,9 +999,9 @@ case WC_CUSTOM_CURRENCY: case WC_NETWORK_WINDOW: case WC_GRF_PARAMETERS: - case WC_NEWGRF_TEXTFILE: case WC_AI_LIST: case WC_AI_SETTINGS: + case WC_TEXTFILE: ++z_priority; case WC_CONSOLE: diff --git a/src/window_type.h b/src/window_type.h --- a/src/window_type.h +++ b/src/window_type.h @@ -179,9 +179,9 @@ /** * textfile; %Window numbers: - * - 0 = #NewGRFTextfileWidgets + * - 0 = #TextfileWidgets */ - WC_NEWGRF_TEXTFILE, + WC_TEXTFILE, /**