From 7202f590ed5fddd1e8cfffcca4e32469a3b2d8ba Mon Sep 17 00:00:00 2001 From: acanas Date: Tue, 11 Oct 2022 21:36:37 +0200 Subject: [PATCH] Version 22.42: Oct 11, 2022 Review of projects (not finished). --- icon/comment-slash.svg | 1 + icon/thumbs-down.svg | 1 + icon/thumbs-up.svg | 1 + swad_changelog.h | 12 ++++- swad_database.c | 70 +++++++++++++++++-------- swad_project.c | 113 ++++++++++++++++++++++++++++++++++------ swad_project.h | 13 +++++ swad_project_database.c | 33 ++++++++++++ swad_text.c | 77 +++++++++++++++++++++++++-- 9 files changed, 281 insertions(+), 40 deletions(-) create mode 100644 icon/comment-slash.svg create mode 100644 icon/thumbs-down.svg create mode 100644 icon/thumbs-up.svg diff --git a/icon/comment-slash.svg b/icon/comment-slash.svg new file mode 100644 index 00000000..32ea4f10 --- /dev/null +++ b/icon/comment-slash.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/icon/thumbs-down.svg b/icon/thumbs-down.svg new file mode 100644 index 00000000..788a91c5 --- /dev/null +++ b/icon/thumbs-down.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/icon/thumbs-up.svg b/icon/thumbs-up.svg new file mode 100644 index 00000000..d3fcfb1c --- /dev/null +++ b/icon/thumbs-up.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/swad_changelog.h b/swad_changelog.h index 19b4edcc..96199837 100644 --- a/swad_changelog.h +++ b/swad_changelog.h @@ -606,10 +606,20 @@ TODO: Fix bug: error al enviar un mensaje a dos recipientes, error on duplicate TODO: Attach pdf files in multimedia. */ -#define Log_PLATFORM_VERSION "SWAD 22.41.1 (2022-10-07)" +#define Log_PLATFORM_VERSION "SWAD 22.42 (2022-10-11)" #define CSS_FILE "swad22.40.css" #define JS_FILE "swad21.100.js" /* + Version 22.42: Oct 11, 2022 Review of projects (not finished). (? lines) + 3 changes necessary in database: +ALTER TABLE prj_projects ADD COLUMN ReviewStatus ENUM('unreviewed','unapproved','approved') NOT NULL DEFAULT 'unreviewed' AFTER URL,ADD INDEX (CrsCod,ReviewStatus); +ALTER TABLE prj_projects ADD COLUMN ReviewTime DATETIME NOT NULL DEFAULT '1970-01-01 01:00:00' AFTER ReviewStatus; +ALTER TABLE prj_projects ADD COLUMN ReviewTxt TEXT NOT NULL AFTER ReviewTime; +Copy the following icons to icon public directory: +sudo cp icon/comment-slash.svg /var/www/html/swad/icon/ +sudo cp icon/thumbs-down.svg /var/www/html/swad/icon/ +sudo cp icon/thumbs-up.svg /var/www/html/swad/icon/ + Version 22.41.1: Oct 07, 2022 Fixed issue in main title. (332512 lines) Version 22.41: Oct 06, 2022 Changes in the behavior of the expansion/contraction of program items. (332511 lines) Version 22.40: Oct 04, 2022 Link in main title. (332514 lines) diff --git a/swad_database.c b/swad_database.c index 30b38f12..c1f9c792 100644 --- a/swad_database.c +++ b/swad_database.c @@ -2595,26 +2595,29 @@ mysql> DESCRIBE prj_config; /***** Table prj_projects *****/ /* mysql> DESCRIBE prj_projects; -+-------------+-------------------------------------+------+-----+---------+----------------+ -| Field | Type | Null | Key | Default | Extra | -+-------------+-------------------------------------+------+-----+---------+----------------+ -| PrjCod | int(11) | NO | PRI | NULL | auto_increment | -| CrsCod | int(11) | NO | MUL | -1 | | -| DptCod | int(11) | NO | | -1 | | -| Locked | enum('N','Y') | NO | | N | | -| Hidden | enum('N','Y') | NO | | N | | -| Assigned | enum('N','Y') | NO | | N | | -| NumStds | int(11) | NO | | 1 | | -| Proposal | enum('new','modified','unmodified') | NO | | new | | -| CreatTime | datetime | NO | | NULL | | -| ModifTime | datetime | NO | | NULL | | -| Title | varchar(4095) | NO | | NULL | | -| Description | text | NO | | NULL | | -| Knowledge | text | NO | | NULL | | -| Materials | text | NO | | NULL | | -| URL | varchar(255) | NO | | NULL | | -+-------------+-------------------------------------+------+-----+---------+----------------+ -15 rows in set (0.00 sec) ++--------------+--------------------------------------------+------+-----+---------------------+----------------+ +| Field | Type | Null | Key | Default | Extra | ++--------------+--------------------------------------------+------+-----+---------------------+----------------+ +| PrjCod | int | NO | PRI | NULL | auto_increment | +| CrsCod | int | NO | MUL | -1 | | +| DptCod | int | NO | | -1 | | +| Locked | enum('N','Y') | NO | | N | | +| Hidden | enum('N','Y') | NO | | N | | +| Assigned | enum('N','Y') | NO | | N | | +| NumStds | int | NO | | 1 | | +| Proposal | enum('new','modified','unmodified') | NO | | new | | +| CreatTime | datetime | NO | | NULL | | +| ModifTime | datetime | NO | | NULL | | +| Title | varchar(4095) | NO | | NULL | | +| Description | text | NO | | NULL | | +| Knowledge | text | NO | | NULL | | +| Materials | text | NO | | NULL | | +| URL | varchar(255) | NO | | NULL | | +| ReviewStatus | enum('unreviewed','unapproved','approved') | NO | | unreviewed | | +| ReviewTime | datetime | NO | | 1970-01-01 01:00:00 | | +| ReviewTxt | text | NO | | NULL | | ++--------------+--------------------------------------------+------+-----+---------------------+----------------+ +18 rows in set (0,00 sec) */ DB_CreateTable ("CREATE TABLE IF NOT EXISTS prj_projects (" "PrjCod INT NOT NULL AUTO_INCREMENT," @@ -2632,11 +2635,36 @@ mysql> DESCRIBE prj_projects; "Knowledge TEXT NOT NULL," // Cns_MAX_BYTES_TEXT "Materials TEXT NOT NULL," // Cns_MAX_BYTES_TEXT "URL VARCHAR(255) NOT NULL," // Cns_MAX_BYTES_WWW + "ReviewStatus ENUM('unreviewed','unapproved','approved') NOT NULL DEFAULT 'unreviewed'," + "ReviewTime DATETIME NOT NULL DEFAULT '1970-01-01 01:00:00'," + "ReviewTxt TEXT NOT NULL," // Cns_MAX_BYTES_TEXT "UNIQUE INDEX(PrjCod)," "INDEX(CrsCod,Hidden)," "INDEX(CrsCod,CreatTime)," "INDEX(CrsCod,ModifTime)," - "INDEX(CrsCod,DptCod))"); + "INDEX(CrsCod,DptCod)," + "INDEX(CrsCod,ReviewStatus))"); + + /***** Table prj_reviews *****/ +/* +mysql> DESCRIBE prj_reviews; ++------------+--------------------------------------+------+-----+----------+-------+ +| Field | Type | Null | Key | Default | Extra | ++------------+--------------------------------------+------+-----+----------+-------+ +| PrjCod | int | NO | MUL | NULL | | +| ReviewTime | datetime | NO | | NULL | | +| Result | enum('negative','solved','positive') | NO | | negative | | +| Txt | text | NO | | NULL | | ++------------+--------------------------------------+------+-----+----------+-------+ +4 rows in set (0,00 sec) +*/ + DB_CreateTable ("CREATE TABLE IF NOT EXISTS prj_reviews (" + "PrjCod INT NOT NULL," + "ReviewTime DATETIME NOT NULL," + "Result ENUM('negative','solved','positive') NOT NULL DEFAULT 'negative'," + "Txt TEXT NOT NULL," // Cns_MAX_BYTES_TEXT + "INDEX(PrjCod,ReviewTime)," + "INDEX(PrjCod,Result))"); /***** Table prj_users *****/ /* diff --git a/swad_project.c b/swad_project.c index e417a201..fcd8fa19 100644 --- a/swad_project.c +++ b/swad_project.c @@ -69,6 +69,7 @@ extern struct Globals Gbl; #define Prj_PARAM_PRE_NON_NAME "PreNon" #define Prj_PARAM_HID_VIS_NAME "HidVis" #define Prj_PARAM_FAULTIN_NAME "Faulti" +#define Prj_PARAM_REVIEW_NAME "Review" /***** Type of view when writing one project *****/ typedef enum @@ -159,16 +160,19 @@ static void Prj_ShowFormToFilterByMy_All (const struct Prj_Projects *Projects); static void Prj_ShowFormToFilterByAssign (const struct Prj_Projects *Projects); static void Prj_ShowFormToFilterByHidden (const struct Prj_Projects *Projects); static void Prj_ShowFormToFilterByWarning (const struct Prj_Projects *Projects); +static void Prj_ShowFormToFilterByReview (const struct Prj_Projects *Projects); static void Prj_ShowFormToFilterByDpt (const struct Prj_Projects *Projects); static void Prj_PutCurrentParams (void *Projects); static void Prj_PutHiddenParamAssign (unsigned Assign); static void Prj_PutHiddenParamHidden (unsigned Hidden); static void Prj_PutHiddenParamFaulti (unsigned Faulti); +static void Prj_PutHiddenParamReview (unsigned Review); static void Prj_PutHiddenParamDptCod (long DptCod); static void Prj_GetHiddenParamPreNon (struct Prj_Projects *Projects); static Prj_HiddenVisibl_t Prj_GetHiddenParamHidVis (void); static unsigned Prj_GetHiddenParamFaulti (void); +static unsigned Prj_GetHiddenParamReview (void); static long Prj_GetHiddenParamDptCod (void); static Usr_Who_t Prj_GetParamWho (void); @@ -464,19 +468,22 @@ static void Prj_ShowPrjsInCurrentPage (void *Projects) /***** Put filters to choice which projects to show *****/ /* 1st. row */ Set_BeginSettingsHead (); - Prj_ShowFormToFilterByMy_All ((struct Prj_Projects *) Projects); - Prj_ShowFormToFilterByAssign ((struct Prj_Projects *) Projects); - switch (Gbl.Usrs.Me.Role.Logged) - { - case Rol_NET: - case Rol_TCH: - case Rol_SYS_ADM: - Prj_ShowFormToFilterByHidden ((struct Prj_Projects *) Projects); - break; - default: // Students will see only visible projects - break; - } - Prj_ShowFormToFilterByWarning ((struct Prj_Projects *) Projects); + + Prj_ShowFormToFilterByMy_All ((struct Prj_Projects *) Projects); + Prj_ShowFormToFilterByAssign ((struct Prj_Projects *) Projects); + switch (Gbl.Usrs.Me.Role.Logged) + { + case Rol_NET: + case Rol_TCH: + case Rol_SYS_ADM: + Prj_ShowFormToFilterByHidden ((struct Prj_Projects *) Projects); + break; + default: // Students will see only visible projects + break; + } + Prj_ShowFormToFilterByWarning ((struct Prj_Projects *) Projects); + Prj_ShowFormToFilterByReview ((struct Prj_Projects *) Projects); + Set_EndSettingsHead (); /* 2nd. row */ @@ -575,6 +582,7 @@ static void Prj_ShowFormToFilterByMy_All (const struct Prj_Projects *Projects) Filter.Assign = Projects->Filter.Assign; Filter.Hidden = Projects->Filter.Hidden; Filter.Faulti = Projects->Filter.Faulti; + Filter.Review = Projects->Filter.Review; Filter.DptCod = Projects->Filter.DptCod; Prj_PutParams (&Filter, Projects->SelectedOrder, @@ -608,6 +616,7 @@ static void Prj_ShowFormToFilterByAssign (const struct Prj_Projects *Projects) Filter.Assign = Projects->Filter.Assign ^ (1 << Assign); // Toggle Filter.Hidden = Projects->Filter.Hidden; Filter.Faulti = Projects->Filter.Faulti; + Filter.Review = Projects->Filter.Review; Filter.DptCod = Projects->Filter.DptCod; Prj_PutParams (&Filter, Projects->SelectedOrder, @@ -651,6 +660,7 @@ static void Prj_ShowFormToFilterByHidden (const struct Prj_Projects *Projects) Filter.Assign = Projects->Filter.Assign; Filter.Hidden = Projects->Filter.Hidden ^ (1 << HidVis); // Toggle Filter.Faulti = Projects->Filter.Faulti; + Filter.Review = Projects->Filter.Review; Filter.DptCod = Projects->Filter.DptCod; Prj_PutParams (&Filter, Projects->SelectedOrder, @@ -681,7 +691,7 @@ static void Prj_ShowFormToFilterByWarning (const struct Prj_Projects *Projects) } FaultinessIcon[Prj_NUM_FAULTINESS] = { [Prj_FAULTY ] = {"exclamation-triangle.svg",Ico_YELLOW}, - [Prj_FAULTLESS] = {"check-circle.svg" ,Ico_GREEN}, + [Prj_FAULTLESS] = {"check-circle.svg" ,Ico_GREEN }, }; Set_BeginOneSettingSelector (); @@ -695,6 +705,7 @@ static void Prj_ShowFormToFilterByWarning (const struct Prj_Projects *Projects) Filter.Assign = Projects->Filter.Assign; Filter.Hidden = Projects->Filter.Hidden; Filter.Faulti = Projects->Filter.Faulti ^ (1 << Faultiness); // Toggle + Filter.Review = Projects->Filter.Review; Filter.DptCod = Projects->Filter.DptCod; Prj_PutParams (&Filter, Projects->SelectedOrder, @@ -709,6 +720,52 @@ static void Prj_ShowFormToFilterByWarning (const struct Prj_Projects *Projects) Set_EndOneSettingSelector (); } +/*****************************************************************************/ +/********** Show form to select projects depending on review status **********/ +/*****************************************************************************/ + +static void Prj_ShowFormToFilterByReview (const struct Prj_Projects *Projects) + { + extern const char *Txt_PROJECT_REVIEWED_PROJECTS[Prj_NUM_REVIEW_STATUS]; + struct Prj_Filter Filter; + Prj_ReviewStatus_t ReviewStatus; + struct + { + const char *Icon; + Ico_Color_t Color; + } ReviewIcon[Prj_NUM_REVIEW_STATUS] = + { + [Prj_UNREVIEWED] = {"comment-slash.svg",Ico_BLACK}, + [Prj_UNAPPROVED] = {"thumbs-down.svg" ,Ico_RED }, + [Prj_APPROVED ] = {"thumbs-up.svg" ,Ico_GREEN}, + }; + + Set_BeginOneSettingSelector (); + for (ReviewStatus = (Prj_ReviewStatus_t) 0; + ReviewStatus <= (Prj_ReviewStatus_t) (Prj_NUM_REVIEW_STATUS - 1); + ReviewStatus++) + { + Set_BeginPref ((Projects->Filter.Review & (1 << ReviewStatus))); + Frm_BeginForm (ActSeePrj); + Filter.Who = Projects->Filter.Who; + Filter.Assign = Projects->Filter.Assign; + Filter.Hidden = Projects->Filter.Hidden; + Filter.Faulti = Projects->Filter.Faulti; + Filter.Review = Projects->Filter.Review ^ (1 << ReviewStatus); // Toggle + Filter.DptCod = Projects->Filter.DptCod; + Prj_PutParams (&Filter, + Projects->SelectedOrder, + Projects->CurrentPage, + -1L); + Ico_PutSettingIconLink (ReviewIcon[ReviewStatus].Icon, + ReviewIcon[ReviewStatus].Color, + Txt_PROJECT_REVIEWED_PROJECTS[ReviewStatus]); + Frm_EndForm (); + Set_EndPref (); + } + Set_EndOneSettingSelector (); + } + /*****************************************************************************/ /*************** Show form to filter projects by department ******************/ /*****************************************************************************/ @@ -726,6 +783,7 @@ static void Prj_ShowFormToFilterByDpt (const struct Prj_Projects *Projects) Filter.Assign = Projects->Filter.Assign; Filter.Hidden = Projects->Filter.Hidden; Filter.Faulti = Projects->Filter.Faulti; + Filter.Review = Projects->Filter.Review; Filter.DptCod = Prj_FILTER_DPT_DEFAULT; // Do not put department parameter here Prj_PutParams (&Filter, Projects->SelectedOrder, @@ -787,6 +845,11 @@ void Prj_PutParams (struct Prj_Filter *Filter, (unsigned) Prj_FILTER_FAULTLESS_DEFAULT)) Prj_PutHiddenParamFaulti (Filter->Faulti); + if (Filter->Review != ((unsigned) Prj_FILTER_UNREVIEWED_DEFAULT | + (unsigned) Prj_FILTER_UNAPPROVED_DEFAULT | + (unsigned) Prj_FILTER_APPROVED_DEFAULT)) + Prj_PutHiddenParamReview (Filter->Review); + if (Filter->DptCod != Prj_FILTER_DPT_DEFAULT) Prj_PutHiddenParamDptCod (Filter->DptCod); @@ -830,6 +893,11 @@ static void Prj_PutHiddenParamFaulti (unsigned Faulti) Par_PutHiddenParamUnsigned (NULL,Prj_PARAM_FAULTIN_NAME,Faulti); } +static void Prj_PutHiddenParamReview (unsigned Review) + { + Par_PutHiddenParamUnsigned (NULL,Prj_PARAM_REVIEW_NAME,Review); + } + static void Prj_PutHiddenParamDptCod (long DptCod) { Par_PutHiddenParamUnsigned (NULL,Dpt_PARAM_DPT_COD_NAME,DptCod); @@ -882,6 +950,19 @@ static unsigned Prj_GetHiddenParamFaulti (void) (unsigned) Prj_FILTER_FAULTLESS_DEFAULT); } +static unsigned Prj_GetHiddenParamReview (void) + { + return (unsigned) + Par_GetParToUnsignedLong (Prj_PARAM_REVIEW_NAME, + 0, + (1 << Prj_UNREVIEWED) | + (1 << Prj_UNAPPROVED) | + (1 << Prj_APPROVED), + (unsigned) Prj_FILTER_UNREVIEWED_DEFAULT | + (unsigned) Prj_FILTER_UNAPPROVED_DEFAULT | + (unsigned) Prj_FILTER_APPROVED_DEFAULT); + } + static long Prj_GetHiddenParamDptCod (void) { return Par_GetParToLong (Dpt_PARAM_DPT_COD_NAME); @@ -898,6 +979,7 @@ void Prj_GetParams (struct Prj_Projects *Projects) Prj_GetHiddenParamPreNon (Projects); Projects->Filter.Hidden = Prj_GetHiddenParamHidVis (); Projects->Filter.Faulti = Prj_GetHiddenParamFaulti (); + Projects->Filter.Review = Prj_GetHiddenParamReview (); Projects->Filter.DptCod = Prj_GetHiddenParamDptCod (); /***** Get order and page *****/ @@ -2833,7 +2915,8 @@ static void Prj_GetListProjects (struct Prj_Projects *Projects) if (Projects->Filter.Assign && // Any selector is on Projects->Filter.Hidden && // Any selector is on - Projects->Filter.Faulti) // Any selector is on + Projects->Filter.Faulti && // Any selector is on + Projects->Filter.Review) // Any selector is on { /****** Get users selected *****/ if (Projects->Filter.Who == Usr_WHO_SELECTED) diff --git a/swad_project.h b/swad_project.h index b89a5304..b05ff994 100644 --- a/swad_project.h +++ b/swad_project.h @@ -83,6 +83,18 @@ typedef enum #define Prj_FILTER_FAULTY_DEFAULT (1 << Prj_FAULTY) // on #define Prj_FILTER_FAULTLESS_DEFAULT (1 << Prj_FAULTLESS) // on +/* Review status project */ +#define Prj_NUM_REVIEW_STATUS 3 +typedef enum + { + Prj_UNREVIEWED = 0, + Prj_UNAPPROVED = 1, + Prj_APPROVED = 2, + } Prj_ReviewStatus_t; +#define Prj_FILTER_UNREVIEWED_DEFAULT (1 << Prj_UNREVIEWED) // on +#define Prj_FILTER_UNAPPROVED_DEFAULT (1 << Prj_UNAPPROVED) // on +#define Prj_FILTER_APPROVED_DEFAULT (1 << Prj_APPROVED) // on + /* Project department */ #define Prj_FILTER_DPT_DEFAULT -1L // Any department @@ -93,6 +105,7 @@ struct Prj_Filter unsigned Assign; // Show assigned / non assigned projects unsigned Hidden; // Show hidden / visible projects unsigned Faulti; // Show faulty / faultless projects + unsigned Review; // Show projects depending on review status long DptCod; // Show projects of this department }; diff --git a/swad_project_database.c b/swad_project_database.c index 407c3309..06a33b0a 100644 --- a/swad_project_database.c +++ b/swad_project_database.c @@ -279,6 +279,39 @@ unsigned Prj_DB_GetListProjects (MYSQL_RES **mysql_res, break; } + /* Review status subquery */ + switch (Projects->Filter.Review) + { + case (1 << Prj_UNREVIEWED): // Unreviewed projects + if (asprintf (&AssignSubQuery," AND prj_projects.ReviewStatus='unreviewed'") < 0) + Err_NotEnoughMemoryExit (); + break; + case (1 << Prj_UNAPPROVED): // Unapproved projects + if (asprintf (&AssignSubQuery," AND prj_projects.ReviewStatus='unapproved'") < 0) + Err_NotEnoughMemoryExit (); + break; + case (1 << Prj_APPROVED): // Approved projects + if (asprintf (&AssignSubQuery," AND prj_projects.ReviewStatus='approved'") < 0) + Err_NotEnoughMemoryExit (); + break; + case (1 << Prj_UNREVIEWED | 1 << Prj_UNAPPROVED): // Unreviewed and unapproved projects + if (asprintf (&AssignSubQuery," AND prj_projects.ReviewStatus IN ('unreviewed','unapproved')") < 0) + Err_NotEnoughMemoryExit (); + break; + case (1 << Prj_UNREVIEWED | 1 << Prj_APPROVED): // Unreviewed and approved projects + if (asprintf (&AssignSubQuery," AND prj_projects.ReviewStatus IN ('unreviewed','approved')") < 0) + Err_NotEnoughMemoryExit (); + break; + case (1 << Prj_UNAPPROVED | 1 << Prj_APPROVED): // Unapproved and approved projects + if (asprintf (&AssignSubQuery," AND prj_projects.ReviewStatus IN ('unapproved','approved')") < 0) + Err_NotEnoughMemoryExit (); + break; + default: // All projects + if (asprintf (&AssignSubQuery,"%s","") < 0) + Err_NotEnoughMemoryExit (); + break; + } + /* Department subquery */ if (Projects->Filter.DptCod >= 0) { diff --git a/swad_text.c b/swad_text.c index c00ace34..14a5af84 100644 --- a/swad_text.c +++ b/swad_text.c @@ -32921,7 +32921,6 @@ const char *Txt_PROJECT_STATUS[Prj_NUM_PROPOSAL_TYPES] = "Project proposed in previous calls, without modifications" // Çeviri lazim! #endif }; - const char *Txt_PROJECT_FAULTY_FAULTLESS_PROJECTS[Prj_NUM_FAULTINESS] = { [Prj_FAULTY] = @@ -32944,7 +32943,7 @@ const char *Txt_PROJECT_FAULTY_FAULTLESS_PROJECTS[Prj_NUM_FAULTINESS] = #elif L==9 // pt "Projetos defeituosos" #elif L==10 // tr - "Faulty projects" // Çeviri lazim! + "Hatalı projeler" #endif , [Prj_FAULTLESS] = @@ -32967,7 +32966,79 @@ const char *Txt_PROJECT_FAULTY_FAULTLESS_PROJECTS[Prj_NUM_FAULTINESS] = #elif L==9 // pt "Projetos sem falhas" #elif L==10 // tr - "Faultless projects" // Çeviri lazim! + "Kusursuz projeler" +#endif + }; + +const char *Txt_PROJECT_REVIEWED_PROJECTS[Prj_NUM_REVIEW_STATUS] = + { + [Prj_UNREVIEWED] = +#if L==1 // ca + "Projectes sense revisar" +#elif L==2 // de + "Ungeprüfte Projekte" +#elif L==3 // en + "Unreviewed projects" +#elif L==4 // es + "Proyectos sin revisar" +#elif L==5 // fr + "Projets non revus" +#elif L==6 // gn + "Proyectos sin revisar" // Okoteve traducción +#elif L==7 // it + "Progetti non recensiti" +#elif L==8 // pl + "Niesprawdzone projekty" +#elif L==9 // pt + "Projetos não revisados" +#elif L==10 // tr + "İncelenmemiş projeler" +#endif + , + [Prj_UNAPPROVED] = +#if L==1 // ca + "Projectes sense aprovar" +#elif L==2 // de + "Nicht genehmigte Projekte" +#elif L==3 // en + "Unapproved projects" +#elif L==4 // es + "Proyectos sin aprobar" +#elif L==5 // fr + "Projets non approuvés" +#elif L==6 // gn + "Proyectos sin aprobar" // Okoteve traducción +#elif L==7 // it + "Progetti non approvati" +#elif L==8 // pl + "Niezatwierdzone projekty" +#elif L==9 // pt + "Projetos não aprovados" +#elif L==10 // tr + "Onaylanmamış projeler" +#endif + , + [Prj_APPROVED] = +#if L==1 // ca + "Projectes aprovats" +#elif L==2 // de + "Genehmigte Projekte" +#elif L==3 // en + "Approved projects" +#elif L==4 // es + "Proyectos aprobados" +#elif L==5 // fr + "Projets approuvés" +#elif L==6 // gn + "Proyectos aprobados" // Okoteve traducción +#elif L==7 // it + "Progetti approvati" +#elif L==8 // pl + "Zatwierdzone projekty" +#elif L==9 // pt + "Projetos aprovados" +#elif L==10 // tr + "Onaylanmış projeler" #endif };