From 631669b434e5dec17beb3ecc653cfad1efd01852 Mon Sep 17 00:00:00 2001 From: timkaltenbach Date: Fri, 6 Oct 2023 14:04:41 -0700 Subject: [PATCH 01/77] Adding recent changes --- public/javascripts/SVValidate/src/Main.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/public/javascripts/SVValidate/src/Main.js b/public/javascripts/SVValidate/src/Main.js index cf544f3180..764c2ac209 100644 --- a/public/javascripts/SVValidate/src/Main.js +++ b/public/javascripts/SVValidate/src/Main.js @@ -202,7 +202,7 @@ function Main (param) { const labelType = param.labelList[0].getAuditProperty('labelType'); - const missionStartTutorial = new MissionStartTutorial('validate', labelType, { nLabels: param.mission.labels_validated }, svv, param.language); + const missionStartTutorial = new MissionStartTutorial('validate', labelType, { labelCount: param.mission.labels_validated }, svv, param.language); } // Gets all the text on the validation page for the correct language. From b586b75a6853ae92a1f5e8ea91b39f094a1f3a11 Mon Sep 17 00:00:00 2001 From: timkaltenbach Date: Fri, 6 Oct 2023 14:16:21 -0700 Subject: [PATCH 02/77] Adding recent changes --- .../javascripts/common/MissionStartTutorial.js | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/public/javascripts/common/MissionStartTutorial.js b/public/javascripts/common/MissionStartTutorial.js index d12f137590..e1d6580e29 100644 --- a/public/javascripts/common/MissionStartTutorial.js +++ b/public/javascripts/common/MissionStartTutorial.js @@ -2,7 +2,7 @@ * Initializes a full screen carousel for the mission start tutorial. * @param missionType mission type. Currently only VALIDATE mission is supported. * @param labelType one of the seven label types for which the tutorial needs to be initialized. - * @param labelCount the number of labels to validate in the current mission (VALIDATE mission only). + * @param nLabels the number of labels to validate in the current mission (VALIDATE mission only). * @param svvOrsvl the svvOrsvl SVValidate or SVLabel object to log interactions and perform other actions upon closing the tutorial. * @param language Fdfadfda */ @@ -46,7 +46,7 @@ function MissionStartTutorial(missionType, labelType, data, svvOrsvl, language = 'CurbRamp': { 'missionInstruction1': i18next.t('validate:mission-start-tutorial.mst-instruction-1'), 'missionInstruction2': i18next.t('validate:mission-start-tutorial.mst-instruction-2', - {'nLabels': data.labelCount, 'labelType': i18next.t('common:curb-ramp')}), + {'nLabels': data.nLabels, 'labelType': i18next.t('common:curb-ramp')}), 'slides': [ { 'isExampleCorrect': true, @@ -93,7 +93,7 @@ function MissionStartTutorial(missionType, labelType, data, svvOrsvl, language = 'NoCurbRamp': { 'missionInstruction1': i18next.t('validate:mission-start-tutorial.mst-instruction-1'), 'missionInstruction2': i18next.t('validate:mission-start-tutorial.mst-instruction-2', - {'nLabels': data.labelCount, 'labelType': i18next.t('common:no-curb-ramp')}), + {'nLabels': data.nLabels, 'labelType': i18next.t('common:no-curb-ramp')}), 'slides': [ { 'isExampleCorrect': true, @@ -153,7 +153,7 @@ function MissionStartTutorial(missionType, labelType, data, svvOrsvl, language = 'Obstacle': { 'missionInstruction1': i18next.t('validate:mission-start-tutorial.mst-instruction-1'), 'missionInstruction2': i18next.t('validate:mission-start-tutorial.mst-instruction-2', - {'nLabels': data.labelCount, 'labelType': i18next.t('common:obstacle')}), + {'nLabels': data.nLabels, 'labelType': i18next.t('common:obstacle')}), 'slides': [ { 'isExampleCorrect': true, @@ -213,7 +213,7 @@ function MissionStartTutorial(missionType, labelType, data, svvOrsvl, language = 'SurfaceProblem': { 'missionInstruction1': i18next.t('validate:mission-start-tutorial.mst-instruction-1'), 'missionInstruction2': i18next.t('validate:mission-start-tutorial.mst-instruction-2', - {'nLabels': data.labelCount, 'labelType': i18next.t('common:surface-problem')}), + {'nLabels': data.nLabels, 'labelType': i18next.t('common:surface-problem')}), 'slides': [ { 'isExampleCorrect': true, @@ -260,7 +260,7 @@ function MissionStartTutorial(missionType, labelType, data, svvOrsvl, language = 'NoSideWalk': { 'missionInstruction1': i18next.t('validate:mission-start-tutorial.mst-instruction-1'), 'missionInstruction2': i18next.t('validate:mission-start-tutorial.mst-instruction-2', - {'nLabels': data.labelCount, 'labelType': i18next.t('common:no-sidewalk')}), + {'nLabels': data.nLabels, 'labelType': i18next.t('common:no-sidewalk')}), 'slides': [ { 'isExampleCorrect': true, @@ -307,7 +307,7 @@ function MissionStartTutorial(missionType, labelType, data, svvOrsvl, language = 'Crosswalk': { 'missionInstruction1': i18next.t('validate:mission-start-tutorial.mst-instruction-1'), 'missionInstruction2': i18next.t('validate:mission-start-tutorial.mst-instruction-2', - {'nLabels': data.labelCount, 'labelType': i18next.t('common:crosswalk')}), + {'nLabels': data.nLabels, 'labelType': i18next.t('common:crosswalk')}), 'slides': [ { 'isExampleCorrect': true, @@ -367,7 +367,7 @@ function MissionStartTutorial(missionType, labelType, data, svvOrsvl, language = 'Signal': { 'missionInstruction1': i18next.t('validate:mission-start-tutorial.mst-instruction-1'), 'missionInstruction2': i18next.t('validate:mission-start-tutorial.mst-instruction-2', - {'nLabels': data.labelCount, 'labelType': i18next.t('common:signal')}), + {'nLabels': data.nLabels, 'labelType': i18next.t('common:signal')}), 'slides': [ { 'isExampleCorrect': true, From 5b4f790d95e33f1cd4dbe6affbff7d2f1356ee74 Mon Sep 17 00:00:00 2001 From: timkaltenbach Date: Fri, 6 Oct 2023 14:33:07 -0700 Subject: [PATCH 03/77] Adding recent changes --- public/javascripts/SVValidate/src/Main.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/public/javascripts/SVValidate/src/Main.js b/public/javascripts/SVValidate/src/Main.js index 764c2ac209..cf544f3180 100644 --- a/public/javascripts/SVValidate/src/Main.js +++ b/public/javascripts/SVValidate/src/Main.js @@ -202,7 +202,7 @@ function Main (param) { const labelType = param.labelList[0].getAuditProperty('labelType'); - const missionStartTutorial = new MissionStartTutorial('validate', labelType, { labelCount: param.mission.labels_validated }, svv, param.language); + const missionStartTutorial = new MissionStartTutorial('validate', labelType, { nLabels: param.mission.labels_validated }, svv, param.language); } // Gets all the text on the validation page for the correct language. From 6d932533cc2be1f7c1cc3150482971b9c302c9ee Mon Sep 17 00:00:00 2001 From: timkaltenbach Date: Fri, 13 Oct 2023 12:44:55 -0700 Subject: [PATCH 04/77] Adding full language names --- app/views/navbar.scala.html | 2 +- conf/messages | 8 ++++++++ 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/app/views/navbar.scala.html b/app/views/navbar.scala.html index b7462cf21a..2cfdbb1a4a 100644 --- a/app/views/navbar.scala.html +++ b/app/views/navbar.scala.html @@ -215,7 +215,7 @@ @for(language <- Play.configuration.getString("application.langs").get.split(",").toList) { @if(language != lang.code) {
  • - @language + @Messages(s"lang.name.$language")
  • } } diff --git a/conf/messages b/conf/messages index 728e3ac4db..76611a471d 100644 --- a/conf/messages +++ b/conf/messages @@ -44,3 +44,11 @@ country.name.taiwan = Taiwan country.name.new-zealand = New Zealand country.name.ecuador = Ecuador country.name.canada = Canada + +lang.name.en-US = US English +lang.name.en-NZ = NZ English +lang.name.en = English +lang.name.es = Español +lang.name.nl = Nederlandse +lang.name.de = Deutsch +lang.name.zh-TW = 繁體中文 From 8b1b34375fecd33417752bf2fb8d3d1e7c0298bf Mon Sep 17 00:00:00 2001 From: Matthew Broadhead Date: Fri, 3 Nov 2023 12:56:39 -0700 Subject: [PATCH 05/77] Remove "sidewalk" schema from Model classes --- app/models/amt/AMTAssignmentTable.scala | 2 +- app/models/attribute/ConfigTable.scala | 2 +- .../attribute/GlobalAttributeTable.scala | 4 +-- .../GlobalAttributeUserAttributeTable.scala | 2 +- .../GlobalClusteringSessionTable.scala | 2 +- .../attribute/UserAttributeLabelTable.scala | 2 +- app/models/attribute/UserAttributeTable.scala | 2 +- .../UserClusteringSessionTable.scala | 2 +- app/models/audit/AuditTaskCommentTable.scala | 2 +- .../audit/AuditTaskEnvironmentTable.scala | 2 +- .../audit/AuditTaskIncompleteTable.scala | 2 +- .../audit/AuditTaskInteractionTable.scala | 2 +- app/models/audit/AuditTaskTable.scala | 2 +- .../daos/slick/DBTableDefinitions.scala | 8 ++--- .../gallery/GalleryTaskEnvironmentTable.scala | 2 +- .../gallery/GalleryTaskInteractionTable.scala | 2 +- app/models/gsv/GSVDataTable.scala | 2 +- app/models/gsv/GSVLinkTable.scala | 2 +- app/models/label/LabelPointTable.scala | 2 +- app/models/label/LabelTable.scala | 2 +- app/models/label/LabelTagTable.scala | 2 +- app/models/label/LabelTypeTable.scala | 2 +- app/models/label/LabelValidationTable.scala | 2 +- app/models/label/TagTable.scala | 2 +- app/models/mission/MissionTable.scala | 2 +- app/models/mission/MissionTypeTable.scala | 2 +- app/models/region/RegionCompletionTable.scala | 2 +- app/models/region/RegionTable.scala | 2 +- .../route/AuditTaskUserRouteTable.scala | 2 +- app/models/route/RouteStreetTable.scala | 2 +- app/models/route/RouteTable.scala | 2 +- app/models/route/UserRouteTable.scala | 2 +- app/models/street/OsmWayStreetEdgeTable.scala | 2 +- app/models/street/StreetEdgeIssueTable.scala | 2 +- .../street/StreetEdgePriorityTable.scala | 2 +- app/models/street/StreetEdgeRegionTable.scala | 2 +- app/models/street/StreetEdgeTable.scala | 2 +- app/models/survey/SurveyOptionTable.scala | 2 +- app/models/survey/SurveyQuestionTable.scala | 2 +- app/models/user/OrganizationTable.scala | 2 +- app/models/user/RoleTable.scala | 2 +- app/models/user/UserCurrentRegionTable.scala | 2 +- app/models/user/UserOrgTable.scala | 2 +- app/models/user/UserRoleTable.scala | 2 +- app/models/user/UserStatTable.scala | 2 +- .../user/UserSurveyOptionSubmission.scala | 2 +- .../user/UserSurveyTextSubmission.scala | 2 +- app/models/user/VersionTable.scala | 2 +- app/models/user/WebpageActivityTable.scala | 2 +- .../ValidationTaskCommentTable.scala | 2 +- .../ValidationTaskEnvironmentTable.scala | 2 +- .../ValidationTaskInteractionTable.scala | 2 +- package.json | 34 +++++++++---------- 53 files changed, 73 insertions(+), 73 deletions(-) diff --git a/app/models/amt/AMTAssignmentTable.scala b/app/models/amt/AMTAssignmentTable.scala index d198f9cd90..048c1627b7 100644 --- a/app/models/amt/AMTAssignmentTable.scala +++ b/app/models/amt/AMTAssignmentTable.scala @@ -12,7 +12,7 @@ case class AMTAssignment(amtAssignmentId: Int, hitId: String, assignmentId: Stri /** * */ -class AMTAssignmentTable(tag: Tag) extends Table[AMTAssignment](tag, Some("sidewalk"), "amt_assignment") { +class AMTAssignmentTable(tag: Tag) extends Table[AMTAssignment](tag, "amt_assignment") { def amtAssignmentId = column[Int]("amt_assignment_id", O.PrimaryKey, O.AutoInc) def hitId = column[String]("hit_id", O.NotNull) def assignmentId = column[String]("assignment_id", O.NotNull) diff --git a/app/models/attribute/ConfigTable.scala b/app/models/attribute/ConfigTable.scala index 06df84112a..ae4b222a1e 100644 --- a/app/models/attribute/ConfigTable.scala +++ b/app/models/attribute/ConfigTable.scala @@ -22,7 +22,7 @@ case class Config(openStatus: String, mapathonEventLink: Option[String], cityMap tutorialStreetEdgeID: Int, offsetHours: Int, excludedTags: String, apiAttribute: MapParams, apiStreet: MapParams, apiRegion: MapParams) -class ConfigTable(tag: slick.lifted.Tag) extends Table[Config](tag, Some("sidewalk"), "config") { +class ConfigTable(tag: slick.lifted.Tag) extends Table[Config](tag, "config") { def openStatus: Column[String] = column[String]("open_status", O.NotNull) def mapathonEventLink: Column[Option[String]] = column[Option[String]]("mapathon_event_link") def cityCenterLat: Column[Double] = column[Double]("city_center_lat", O.NotNull) diff --git a/app/models/attribute/GlobalAttributeTable.scala b/app/models/attribute/GlobalAttributeTable.scala index c8f05c60a5..81ba6c84f4 100644 --- a/app/models/attribute/GlobalAttributeTable.scala +++ b/app/models/attribute/GlobalAttributeTable.scala @@ -145,7 +145,7 @@ case class GlobalAttributeWithLabelForAPI(val globalAttributeId: Int, "\"[" + labelTags.mkString(",") + "]\"", "\"" + labelDescription.getOrElse("NA") + "\"", userId) } -class GlobalAttributeTable(tag: Tag) extends Table[GlobalAttribute](tag, Some("sidewalk"), "global_attribute") { +class GlobalAttributeTable(tag: Tag) extends Table[GlobalAttribute](tag, "global_attribute") { def globalAttributeId: Column[Int] = column[Int]("global_attribute_id", O.NotNull, O.PrimaryKey, O.AutoInc) def globalClusteringSessionId: Column[Int] = column[Int]("global_clustering_session_id", O.NotNull) def clusteringThreshold: Column[Float] = column[Float]("clustering_threshold", O.NotNull) @@ -248,7 +248,7 @@ object GlobalAttributeTable { | INNER JOIN global_attribute_user_attribute ON global_attribute.global_attribute_id = global_attribute_user_attribute.global_attribute_id | INNER JOIN user_attribute_label ON global_attribute_user_attribute.user_attribute_id = user_attribute_label.user_attribute_id | INNER JOIN label ON user_attribute_label.label_id = label.label_id - | INNER JOIN sidewalk.gsv_data ON label.gsv_panorama_id = gsv_data.gsv_panorama_id + | INNER JOIN gsv_data ON label.gsv_panorama_id = gsv_data.gsv_panorama_id | INNER JOIN audit_task ON label.audit_task_id = audit_task.audit_task_id | GROUP BY global_attribute.global_attribute_id, gsv_data.gsv_panorama_id |) capture_dates diff --git a/app/models/attribute/GlobalAttributeUserAttributeTable.scala b/app/models/attribute/GlobalAttributeUserAttributeTable.scala index c0b85c609b..05b0c39d82 100644 --- a/app/models/attribute/GlobalAttributeUserAttributeTable.scala +++ b/app/models/attribute/GlobalAttributeUserAttributeTable.scala @@ -8,7 +8,7 @@ import scala.language.postfixOps case class GlobalAttributeUserAttribute(globalAttributeUserAttributeId: Int, globalAttributeId: Int, userAttributeId: Int) -class GlobalAttributeUserAttributeTable(tag: Tag) extends Table[GlobalAttributeUserAttribute](tag, Some("sidewalk"), "global_attribute_user_attribute") { +class GlobalAttributeUserAttributeTable(tag: Tag) extends Table[GlobalAttributeUserAttribute](tag, "global_attribute_user_attribute") { def globalAttributeUserAttributeId: Column[Int] = column[Int]("global_attribute_user_attribute_id", O.NotNull, O.PrimaryKey, O.AutoInc) def globalAttributeId: Column[Int] = column[Int]("global_attribute_id", O.NotNull) def userAttributeId: Column[Int] = column[Int]("user_attribute_id", O.NotNull) diff --git a/app/models/attribute/GlobalClusteringSessionTable.scala b/app/models/attribute/GlobalClusteringSessionTable.scala index 8e6604c92e..9871c472fe 100644 --- a/app/models/attribute/GlobalClusteringSessionTable.scala +++ b/app/models/attribute/GlobalClusteringSessionTable.scala @@ -10,7 +10,7 @@ import scala.language.postfixOps case class GlobalClusteringSession(globalClusteringSessionId: Int, regionId: Int, timeCreated: java.sql.Timestamp) -class GlobalClusteringSessionTable(tag: Tag) extends Table[GlobalClusteringSession](tag, Some("sidewalk"), "global_clustering_session") { +class GlobalClusteringSessionTable(tag: Tag) extends Table[GlobalClusteringSession](tag, "global_clustering_session") { def globalClusteringSessionId: Column[Int] = column[Int]("global_clustering_session_id", O.NotNull, O.PrimaryKey, O.AutoInc) def regionId: Column[Int] = column[Int]("region_id", O.NotNull) def timeCreated: Column[java.sql.Timestamp] = column[java.sql.Timestamp]("time_created", O.NotNull) diff --git a/app/models/attribute/UserAttributeLabelTable.scala b/app/models/attribute/UserAttributeLabelTable.scala index 873d92d635..ba5994583a 100644 --- a/app/models/attribute/UserAttributeLabelTable.scala +++ b/app/models/attribute/UserAttributeLabelTable.scala @@ -9,7 +9,7 @@ import scala.language.postfixOps case class UserAttributeLabel(userAttributeLabelId: Int, userAttributeId: Int, labelId: Int) -class UserAttributeLabelTable(tag: Tag) extends Table[UserAttributeLabel](tag, Some("sidewalk"), "user_attribute_label") { +class UserAttributeLabelTable(tag: Tag) extends Table[UserAttributeLabel](tag, "user_attribute_label") { def userAttributeLabelId: Column[Int] = column[Int]("user_attribute_label_id", O.NotNull, O.PrimaryKey, O.AutoInc) def userAttributeId: Column[Int] = column[Int]("user_attribute_id", O.NotNull) def labelId: Column[Int] = column[Int]("label_id", O.NotNull) diff --git a/app/models/attribute/UserAttributeTable.scala b/app/models/attribute/UserAttributeTable.scala index de51d209dd..a57a62dcfe 100644 --- a/app/models/attribute/UserAttributeTable.scala +++ b/app/models/attribute/UserAttributeTable.scala @@ -18,7 +18,7 @@ case class UserAttribute(userAttributeId: Int, severity: Option[Int], temporary: Boolean) -class UserAttributeTable(tag: Tag) extends Table[UserAttribute](tag, Some("sidewalk"), "user_attribute") { +class UserAttributeTable(tag: Tag) extends Table[UserAttribute](tag, "user_attribute") { def userAttributeId: Column[Int] = column[Int]("user_attribute_id", O.NotNull, O.PrimaryKey, O.AutoInc) def userClusteringSessionId: Column[Int] = column[Int]("user_clustering_session_id", O.NotNull) def clusteringThreshold: Column[Float] = column[Float]("clustering_threshold", O.NotNull) diff --git a/app/models/attribute/UserClusteringSessionTable.scala b/app/models/attribute/UserClusteringSessionTable.scala index d40e64bdb0..16395679b9 100644 --- a/app/models/attribute/UserClusteringSessionTable.scala +++ b/app/models/attribute/UserClusteringSessionTable.scala @@ -40,7 +40,7 @@ case class LabelToCluster(userId: String, case class UserClusteringSession(userClusteringSessionId: Int, userId: String, timeCreated: java.sql.Timestamp) -class UserClusteringSessionTable(tag: Tag) extends Table[UserClusteringSession](tag, Some("sidewalk"), "user_clustering_session") { +class UserClusteringSessionTable(tag: Tag) extends Table[UserClusteringSession](tag, "user_clustering_session") { def userClusteringSessionId: Column[Int] = column[Int]("user_clustering_session_id", O.NotNull, O.PrimaryKey, O.AutoInc) def userId: Column[String] = column[String]("user_id", O.NotNull) def timeCreated: Column[java.sql.Timestamp] = column[java.sql.Timestamp]("time_created", O.NotNull) diff --git a/app/models/audit/AuditTaskCommentTable.scala b/app/models/audit/AuditTaskCommentTable.scala index 1a21605b0b..86dcf0bf2a 100644 --- a/app/models/audit/AuditTaskCommentTable.scala +++ b/app/models/audit/AuditTaskCommentTable.scala @@ -15,7 +15,7 @@ case class AuditTaskComment(auditTaskCommentId: Int, auditTaskId: Int, missionId timestamp: Timestamp, comment: String) case class GenericComment(commentType: String, username: String, gsvPanoramaId: Option[String], timestamp: Timestamp, comment: String, heading: Option[Double], pitch: Option[Double], zoom: Option[Int], labelId: Option[Int]) -class AuditTaskCommentTable(tag: Tag) extends Table[AuditTaskComment](tag, Some("sidewalk"), "audit_task_comment") { +class AuditTaskCommentTable(tag: Tag) extends Table[AuditTaskComment](tag, "audit_task_comment") { def auditTaskCommentId = column[Int]("audit_task_comment_id", O.PrimaryKey, O.AutoInc) def auditTaskId = column[Int]("audit_task_id", O.NotNull) def missionId = column[Int]("mission_id", O.NotNull) diff --git a/app/models/audit/AuditTaskEnvironmentTable.scala b/app/models/audit/AuditTaskEnvironmentTable.scala index b7bd607a26..078972626a 100644 --- a/app/models/audit/AuditTaskEnvironmentTable.scala +++ b/app/models/audit/AuditTaskEnvironmentTable.scala @@ -11,7 +11,7 @@ case class AuditTaskEnvironment(auditTaskEnvironmentId: Int, auditTaskId: Int, m screenHeight: Option[Int], operatingSystem: Option[String], ipAddress: Option[String], language: String) -class AuditTaskEnvironmentTable(tag: Tag) extends Table[AuditTaskEnvironment](tag, Some("sidewalk"), "audit_task_environment") { +class AuditTaskEnvironmentTable(tag: Tag) extends Table[AuditTaskEnvironment](tag, "audit_task_environment") { def auditTaskEnvironmentId = column[Int]("audit_task_environment_id", O.PrimaryKey, O.AutoInc) def auditTaskId = column[Int]("audit_task_id", O.NotNull) def missionId = column[Int]("mission_id", O.NotNull) diff --git a/app/models/audit/AuditTaskIncompleteTable.scala b/app/models/audit/AuditTaskIncompleteTable.scala index 264e22bea3..c6bea9fcc3 100644 --- a/app/models/audit/AuditTaskIncompleteTable.scala +++ b/app/models/audit/AuditTaskIncompleteTable.scala @@ -7,7 +7,7 @@ import scala.slick.lifted.ForeignKeyQuery case class AuditTaskIncomplete(auditTaskIncompleteId: Int, auditTaskId: Int, missionId: Int, issueDescription: String, lat: Float, lng: Float) -class AuditTaskIncompleteTable(tag: Tag) extends Table[AuditTaskIncomplete](tag, Some("sidewalk"), "audit_task_incomplete") { +class AuditTaskIncompleteTable(tag: Tag) extends Table[AuditTaskIncomplete](tag, "audit_task_incomplete") { def auditTaskIncompleteId = column[Int]("audit_task_incomplete_id", O.PrimaryKey, O.AutoInc) def auditTaskId = column[Int]("audit_task_id", O.NotNull) def missionId = column[Int]("mission_id", O.NotNull) diff --git a/app/models/audit/AuditTaskInteractionTable.scala b/app/models/audit/AuditTaskInteractionTable.scala index 5be5be4fa3..89a9e670af 100644 --- a/app/models/audit/AuditTaskInteractionTable.scala +++ b/app/models/audit/AuditTaskInteractionTable.scala @@ -31,7 +31,7 @@ case class InteractionWithLabel(auditTaskInteractionId: Int, auditTaskId: Int, m canvasX: Int, canvasY: Int) -class AuditTaskInteractionTable(tag: slick.lifted.Tag) extends Table[AuditTaskInteraction](tag, Some("sidewalk"), "audit_task_interaction") { +class AuditTaskInteractionTable(tag: slick.lifted.Tag) extends Table[AuditTaskInteraction](tag, "audit_task_interaction") { def auditTaskInteractionId = column[Int]("audit_task_interaction_id", O.PrimaryKey, O.AutoInc) def auditTaskId = column[Int]("audit_task_id", O.NotNull) def missionId = column[Int]("mission_id", O.NotNull) diff --git a/app/models/audit/AuditTaskTable.scala b/app/models/audit/AuditTaskTable.scala index 2f057d5a32..7fbb90dbc5 100644 --- a/app/models/audit/AuditTaskTable.scala +++ b/app/models/audit/AuditTaskTable.scala @@ -83,7 +83,7 @@ case class AuditedStreetWithTimestamp(streetEdgeId: Int, auditTaskId: Int, case class StreetEdgeWithAuditStatus(streetEdgeId: Int, geom: LineString, regionId: Int, wayType: String, audited: Boolean) -class AuditTaskTable(tag: slick.lifted.Tag) extends Table[AuditTask](tag, Some("sidewalk"), "audit_task") { +class AuditTaskTable(tag: slick.lifted.Tag) extends Table[AuditTask](tag, "audit_task") { def auditTaskId = column[Int]("audit_task_id", O.PrimaryKey, O.AutoInc) def amtAssignmentId = column[Option[Int]]("amt_assignment_id", O.Nullable) def userId = column[String]("user_id", O.NotNull) diff --git a/app/models/daos/slick/DBTableDefinitions.scala b/app/models/daos/slick/DBTableDefinitions.scala index eeb25bb756..8c197b83bf 100644 --- a/app/models/daos/slick/DBTableDefinitions.scala +++ b/app/models/daos/slick/DBTableDefinitions.scala @@ -8,7 +8,7 @@ object DBTableDefinitions { case class DBUser (userId: String, username: String, email: String ) - class UserTable(tag: Tag) extends Table[DBUser](tag, Some("sidewalk"), "sidewalk_user") { + class UserTable(tag: Tag) extends Table[DBUser](tag, "sidewalk_user") { def userId = column[String]("user_id", O.PrimaryKey) def username = column[String]("username") def email = column[String]("email") @@ -17,7 +17,7 @@ object DBTableDefinitions { case class DBLoginInfo (id: Option[Long], providerID: String, providerKey: String ) - class LoginInfos(tag: Tag) extends Table[DBLoginInfo](tag, Some("sidewalk"), "login_info") { + class LoginInfos(tag: Tag) extends Table[DBLoginInfo](tag, "login_info") { def loginInfoId = column[Long]("login_info_id", O.PrimaryKey, O.AutoInc) def providerID = column[String]("provider_id") def providerKey = column[String]("provider_key") @@ -26,7 +26,7 @@ object DBTableDefinitions { case class DBUserLoginInfo (userID: String, loginInfoId: Long) - class UserLoginInfoTable(tag: Tag) extends Table[DBUserLoginInfo](tag, Some("sidewalk"), "user_login_info") { + class UserLoginInfoTable(tag: Tag) extends Table[DBUserLoginInfo](tag, "user_login_info") { def userID = column[String]("user_id", O.NotNull) def loginInfoId = column[Long]("login_info_id", O.NotNull) def * = (userID, loginInfoId) <> (DBUserLoginInfo.tupled, DBUserLoginInfo.unapply) @@ -34,7 +34,7 @@ object DBTableDefinitions { case class DBPasswordInfo (hasher: String, password: String, salt: Option[String], loginInfoId: Long) - class PasswordInfoTable(tag: Tag) extends Table[DBPasswordInfo](tag, Some("sidewalk"), "user_password_info") { + class PasswordInfoTable(tag: Tag) extends Table[DBPasswordInfo](tag, "user_password_info") { def hasher = column[String]("hasher") def password = column[String]("password") def salt = column[Option[String]]("salt") diff --git a/app/models/gallery/GalleryTaskEnvironmentTable.scala b/app/models/gallery/GalleryTaskEnvironmentTable.scala index b8f11ea405..de46b2447d 100644 --- a/app/models/gallery/GalleryTaskEnvironmentTable.scala +++ b/app/models/gallery/GalleryTaskEnvironmentTable.scala @@ -11,7 +11,7 @@ case class GalleryTaskEnvironment(galleryTaskEnvironmentId: Int, browser: Option screenHeight: Option[Int], operatingSystem: Option[String], ipAddress: Option[String], language: String, userId: Option[String]) -class GalleryTaskEnvironmentTable(tag: Tag) extends Table[GalleryTaskEnvironment](tag, Some("sidewalk"), "gallery_task_environment") { +class GalleryTaskEnvironmentTable(tag: Tag) extends Table[GalleryTaskEnvironment](tag, "gallery_task_environment") { def galleryTaskEnvironmentId = column[Int]("gallery_task_environment_id", O.PrimaryKey, O.AutoInc) def browser = column[Option[String]]("browser", O.Nullable) def browserVersion = column[Option[String]]("browser_version", O.Nullable) diff --git a/app/models/gallery/GalleryTaskInteractionTable.scala b/app/models/gallery/GalleryTaskInteractionTable.scala index cf22f246de..6f385e642a 100644 --- a/app/models/gallery/GalleryTaskInteractionTable.scala +++ b/app/models/gallery/GalleryTaskInteractionTable.scala @@ -8,7 +8,7 @@ import scala.slick.lifted.ForeignKeyQuery case class GalleryTaskInteraction(galleryTaskInteractionId: Int, action: String, panoId: Option[String], note: Option[String], timestamp: java.sql.Timestamp, userId: Option[String]) -class GalleryTaskInteractionTable(tag: slick.lifted.Tag) extends Table[GalleryTaskInteraction](tag, Some("sidewalk"), "gallery_task_interaction") { +class GalleryTaskInteractionTable(tag: slick.lifted.Tag) extends Table[GalleryTaskInteraction](tag, "gallery_task_interaction") { def galleryTaskInteractionId = column[Int]("gallery_task_interaction_id", O.PrimaryKey, O.AutoInc) def action = column[String]("action", O.NotNull) def panoId = column[Option[String]]("pano_id", O.Nullable) diff --git a/app/models/gsv/GSVDataTable.scala b/app/models/gsv/GSVDataTable.scala index c22e3de0f6..1382f255be 100644 --- a/app/models/gsv/GSVDataTable.scala +++ b/app/models/gsv/GSVDataTable.scala @@ -13,7 +13,7 @@ case class GSVData(gsvPanoramaId: String, width: Option[Int], height: Option[Int case class GSVDataSlim(gsvPanoramaId: String, width: Option[Int], height: Option[Int], lat: Option[Float], lng: Option[Float], cameraHeading: Option[Float], cameraPitch: Option[Float]) -class GSVDataTable(tag: Tag) extends Table[GSVData](tag, Some("sidewalk"), "gsv_data") { +class GSVDataTable(tag: Tag) extends Table[GSVData](tag, "gsv_data") { def gsvPanoramaId = column[String]("gsv_panorama_id", O.PrimaryKey) def width = column[Option[Int]]("width") def height = column[Option[Int]]("height") diff --git a/app/models/gsv/GSVLinkTable.scala b/app/models/gsv/GSVLinkTable.scala index 5a425861b7..9d307fe5aa 100644 --- a/app/models/gsv/GSVLinkTable.scala +++ b/app/models/gsv/GSVLinkTable.scala @@ -5,7 +5,7 @@ import play.api.Play.current case class GSVLink(gsvPanoramaId: String, targetGsvPanoramaId: String, yawDeg: Double, description: String) -class GSVLinkTable(tag: Tag) extends Table[GSVLink](tag, Some("sidewalk"), "gsv_link") { +class GSVLinkTable(tag: Tag) extends Table[GSVLink](tag, "gsv_link") { def gsvPanoramaId = column[String]("gsv_panorama_id", O.PrimaryKey) def targetGsvPanoramaId = column[String]("target_panorama_id", O.NotNull) def yawDeg = column[Double]("yaw_deg", O.NotNull) diff --git a/app/models/label/LabelPointTable.scala b/app/models/label/LabelPointTable.scala index 1b3ac51cc6..54278e04c4 100644 --- a/app/models/label/LabelPointTable.scala +++ b/app/models/label/LabelPointTable.scala @@ -9,7 +9,7 @@ case class LabelPoint(labelPointId: Int, labelId: Int, panoX: Int, panoY: Int, c heading: Float, pitch: Float, zoom: Int, lat: Option[Float], lng: Option[Float], geom: Option[Point], computationMethod: Option[String]) -class LabelPointTable(tag: slick.lifted.Tag) extends Table[LabelPoint](tag, Some("sidewalk"), "label_point") { +class LabelPointTable(tag: slick.lifted.Tag) extends Table[LabelPoint](tag, "label_point") { def labelPointId = column[Int]("label_point_id", O.PrimaryKey, O.AutoInc) def labelId = column[Int]("label_id", O.NotNull) def panoX = column[Int]("pano_x", O.NotNull) diff --git a/app/models/label/LabelTable.scala b/app/models/label/LabelTable.scala index 383267dcbb..97e4c9ffac 100644 --- a/app/models/label/LabelTable.scala +++ b/app/models/label/LabelTable.scala @@ -44,7 +44,7 @@ case class ProjectSidewalkStats(launchDate: String, kmExplored: Float, kmExplore nLabels: Int, severityByLabelType: Map[String, LabelSeverityStats], nValidations: Int, accuracyByLabelType: Map[String, LabelAccuracy]) -class LabelTable(tag: slick.lifted.Tag) extends Table[Label](tag, Some("sidewalk"), "label") { +class LabelTable(tag: slick.lifted.Tag) extends Table[Label](tag, "label") { def labelId = column[Int]("label_id", O.PrimaryKey, O.AutoInc) def auditTaskId = column[Int]("audit_task_id", O.NotNull) def missionId = column[Int]("mission_id", O.NotNull) diff --git a/app/models/label/LabelTagTable.scala b/app/models/label/LabelTagTable.scala index 45b713799f..a7c388d601 100644 --- a/app/models/label/LabelTagTable.scala +++ b/app/models/label/LabelTagTable.scala @@ -6,7 +6,7 @@ import scala.slick.lifted.ForeignKeyQuery case class LabelTag(labelTagId: Int, labelId: Int, tagId: Int) -class LabelTagTable(tagParam: slick.lifted.Tag) extends Table[LabelTag](tagParam, Some("sidewalk"), "label_tag") { +class LabelTagTable(tagParam: slick.lifted.Tag) extends Table[LabelTag](tagParam, "label_tag") { def labelTagId: Column[Int] = column[Int]("label_tag_id", O.PrimaryKey, O.AutoInc) def labelId: Column[Int] = column[Int]("label_id") def tagId: Column[Int] = column[Int]("tag_id") diff --git a/app/models/label/LabelTypeTable.scala b/app/models/label/LabelTypeTable.scala index dd7a928d53..c36c7c3a35 100644 --- a/app/models/label/LabelTypeTable.scala +++ b/app/models/label/LabelTypeTable.scala @@ -5,7 +5,7 @@ import play.api.Play.current case class LabelType(labelTypeId: Int, labelType: String, description: String) -class LabelTypeTable(tag: slick.lifted.Tag) extends Table[LabelType](tag, Some("sidewalk"), "label_type") { +class LabelTypeTable(tag: slick.lifted.Tag) extends Table[LabelType](tag, "label_type") { def labelTypeId = column[Int]("label_type_id", O.PrimaryKey, O.AutoInc) def labelType = column[String]("label_type", O.NotNull) def description = column[String]("description") diff --git a/app/models/label/LabelValidationTable.scala b/app/models/label/LabelValidationTable.scala index 7c3b5a515f..4656e4bc56 100644 --- a/app/models/label/LabelValidationTable.scala +++ b/app/models/label/LabelValidationTable.scala @@ -33,7 +33,7 @@ case class LabelValidation(labelValidationId: Int, * https://www.programcreek.com/scala/slick.lifted.ForeignKeyQuery * @param tag */ -class LabelValidationTable (tag: slick.lifted.Tag) extends Table[LabelValidation](tag, Some("sidewalk"), "label_validation") { +class LabelValidationTable (tag: slick.lifted.Tag) extends Table[LabelValidation](tag, "label_validation") { def labelValidationId = column[Int]("label_validation_id", O.AutoInc) def labelId = column[Int]("label_id", O.NotNull) def validationResult = column[Int]("validation_result", O.NotNull) // 1 = Agree, 2 = Disagree, 3 = Notsure diff --git a/app/models/label/TagTable.scala b/app/models/label/TagTable.scala index 05aac8bb79..1a2c79b881 100644 --- a/app/models/label/TagTable.scala +++ b/app/models/label/TagTable.scala @@ -6,7 +6,7 @@ import scala.slick.lifted.ForeignKeyQuery case class Tag(tagId: Int, labelTypeId: Int, tag: String) -class TagTable(tagParam: slick.lifted.Tag) extends Table[Tag](tagParam, Some("sidewalk"), "tag") { +class TagTable(tagParam: slick.lifted.Tag) extends Table[Tag](tagParam, "tag") { def tagId: Column[Int] = column[Int]("tag_id", O.PrimaryKey, O.AutoInc) def labelTypeId: Column[Int] = column[Int]("label_type_id") def tag: Column[String] = column[String]("tag") diff --git a/app/models/mission/MissionTable.scala b/app/models/mission/MissionTable.scala index 24bdd3f219..3d405c7714 100644 --- a/app/models/mission/MissionTable.scala +++ b/app/models/mission/MissionTable.scala @@ -48,7 +48,7 @@ case class Mission(missionId: Int, missionTypeId: Int, userId: String, missionSt } } -class MissionTable(tag: Tag) extends Table[Mission](tag, Some("sidewalk"), "mission") { +class MissionTable(tag: Tag) extends Table[Mission](tag, "mission") { def missionId: Column[Int] = column[Int]("mission_id", O.PrimaryKey, O.AutoInc) def missionTypeId: Column[Int] = column[Int]("mission_type_id", O.NotNull) def userId: Column[String] = column[String]("user_id", O.NotNull) diff --git a/app/models/mission/MissionTypeTable.scala b/app/models/mission/MissionTypeTable.scala index 3b1670c187..e987910064 100644 --- a/app/models/mission/MissionTypeTable.scala +++ b/app/models/mission/MissionTypeTable.scala @@ -5,7 +5,7 @@ import play.api.Play.current case class MissionType(missionTypeId: Int, missionType: String) -class MissionTypeTable(tag: slick.lifted.Tag) extends Table[MissionType](tag, Some("sidewalk"), "mission_type") { +class MissionTypeTable(tag: slick.lifted.Tag) extends Table[MissionType](tag, "mission_type") { def missionTypeId: Column[Int] = column[Int]("mission_type_id", O.PrimaryKey, O.AutoInc) def missionType: Column[String] = column[String]("mission_type", O.NotNull) diff --git a/app/models/region/RegionCompletionTable.scala b/app/models/region/RegionCompletionTable.scala index 70364ab24d..3b8d38f5ea 100644 --- a/app/models/region/RegionCompletionTable.scala +++ b/app/models/region/RegionCompletionTable.scala @@ -9,7 +9,7 @@ import scala.slick.jdbc.{GetResult, StaticQuery => Q} case class RegionCompletion(regionId: Int, totalDistance: Double, auditedDistance: Double) case class NamedRegionCompletion(regionId: Int, name: String, totalDistance: Double, auditedDistance: Double) -class RegionCompletionTable(tag: Tag) extends Table[RegionCompletion](tag, Some("sidewalk"), "region_completion") { +class RegionCompletionTable(tag: Tag) extends Table[RegionCompletion](tag, "region_completion") { def regionId = column[Int]("region_id", O.PrimaryKey) def totalDistance = column[Double]("total_distance") def auditedDistance = column[Double]("audited_distance") diff --git a/app/models/region/RegionTable.scala b/app/models/region/RegionTable.scala index 11b5b42e95..cbc76f2eaf 100644 --- a/app/models/region/RegionTable.scala +++ b/app/models/region/RegionTable.scala @@ -16,7 +16,7 @@ import scala.slick.jdbc.{GetResult, StaticQuery => Q} case class Region(regionId: Int, dataSource: String, name: String, geom: MultiPolygon, deleted: Boolean) -class RegionTable(tag: Tag) extends Table[Region](tag, Some("sidewalk"), "region") { +class RegionTable(tag: Tag) extends Table[Region](tag, "region") { def regionId = column[Int]("region_id", O.PrimaryKey, O.AutoInc) def dataSource = column[String]("data_source", O.NotNull) def name = column[String]("name", O.NotNull) diff --git a/app/models/route/AuditTaskUserRouteTable.scala b/app/models/route/AuditTaskUserRouteTable.scala index dc3caf89ef..d9e6783e9c 100644 --- a/app/models/route/AuditTaskUserRouteTable.scala +++ b/app/models/route/AuditTaskUserRouteTable.scala @@ -7,7 +7,7 @@ import scala.slick.lifted.ForeignKeyQuery case class AuditTaskUserRoute(auditTaskUserRouteId: Int, userRouteId: Int, auditTaskId: Int, routeStreetId: Int) -class AuditTaskUserRouteTable(tag: slick.lifted.Tag) extends Table[AuditTaskUserRoute](tag, Some("sidewalk"), "audit_task_user_route") { +class AuditTaskUserRouteTable(tag: slick.lifted.Tag) extends Table[AuditTaskUserRoute](tag, "audit_task_user_route") { def auditTaskUserRouteId: Column[Int] = column[Int]("audit_task_user_route_id", O.PrimaryKey, O.AutoInc) def userRouteId: Column[Int] = column[Int]("user_route_id", O.NotNull) def auditTaskId: Column[Int] = column[Int]("audit_task_id", O.NotNull) diff --git a/app/models/route/RouteStreetTable.scala b/app/models/route/RouteStreetTable.scala index d635df2966..dd08ca29f7 100644 --- a/app/models/route/RouteStreetTable.scala +++ b/app/models/route/RouteStreetTable.scala @@ -7,7 +7,7 @@ import scala.slick.lifted.ForeignKeyQuery case class RouteStreet(routeStreetId: Int, routeId: Int, streetEdgeId: Int, firstStreet: Boolean) -class RouteStreetTable(tag: slick.lifted.Tag) extends Table[RouteStreet](tag, Some("sidewalk"), "route_street") { +class RouteStreetTable(tag: slick.lifted.Tag) extends Table[RouteStreet](tag, "route_street") { def routeStreetId: Column[Int] = column[Int]("route_street_id", O.PrimaryKey, O.AutoInc) def routeId: Column[Int] = column[Int]("route_id", O.NotNull) def streetEdgeId: Column[Int] = column[Int]("street_edge_id", O.NotNull) diff --git a/app/models/route/RouteTable.scala b/app/models/route/RouteTable.scala index 67eedcebbd..96d047ac4a 100644 --- a/app/models/route/RouteTable.scala +++ b/app/models/route/RouteTable.scala @@ -8,7 +8,7 @@ import scala.slick.lifted.ForeignKeyQuery case class Route(routeId: Int, userId: String, regionId: Int, name: String, public: Boolean, deleted: Boolean) -class RouteTable(tag: slick.lifted.Tag) extends Table[Route](tag, Some("sidewalk"), "route") { +class RouteTable(tag: slick.lifted.Tag) extends Table[Route](tag, "route") { def routeId: Column[Int] = column[Int]("route_id", O.PrimaryKey, O.AutoInc) def userId: Column[String] = column[String]("user_id", O.NotNull) def regionId: Column[Int] = column[Int]("region_id", O.NotNull) diff --git a/app/models/route/UserRouteTable.scala b/app/models/route/UserRouteTable.scala index 52d7379c01..ee77dfc7c4 100644 --- a/app/models/route/UserRouteTable.scala +++ b/app/models/route/UserRouteTable.scala @@ -13,7 +13,7 @@ import scala.slick.lifted.ForeignKeyQuery case class UserRoute(userRouteId: Int, routeId: Int, userId: String, completed: Boolean, discarded: Boolean) -class UserRouteTable(tag: slick.lifted.Tag) extends Table[UserRoute](tag, Some("sidewalk"), "user_route") { +class UserRouteTable(tag: slick.lifted.Tag) extends Table[UserRoute](tag, "user_route") { def userRouteId: Column[Int] = column[Int]("user_route_id", O.PrimaryKey, O.AutoInc) def routeId: Column[Int] = column[Int]("route_id", O.NotNull) def userId: Column[String] = column[String]("user_id", O.NotNull) diff --git a/app/models/street/OsmWayStreetEdgeTable.scala b/app/models/street/OsmWayStreetEdgeTable.scala index 63f0bd835f..44b8e7f78e 100644 --- a/app/models/street/OsmWayStreetEdgeTable.scala +++ b/app/models/street/OsmWayStreetEdgeTable.scala @@ -7,7 +7,7 @@ import scala.slick.lifted.{Tag} case class OsmWayStreetEdge(osmWayStreetEdgeId: Int, osmWayId: Int, streetEdgeId: Int) -class OsmWayStreetEdgeTable(tag: Tag) extends Table[OsmWayStreetEdge](tag, Some("sidewalk"), "osm_way_street_edge") { +class OsmWayStreetEdgeTable(tag: Tag) extends Table[OsmWayStreetEdge](tag, "osm_way_street_edge") { def osmWayStreetEdgeId = column[Int]("osm_way_street_edge_id", O.NotNull, O.PrimaryKey, O.AutoInc) def osmWayId = column[Int]("osm_way_id", O.NotNull) def streetEdgeId = column[Int]("street_edge_id", O.NotNull) diff --git a/app/models/street/StreetEdgeIssueTable.scala b/app/models/street/StreetEdgeIssueTable.scala index a8d837cf25..ee9c8b7454 100644 --- a/app/models/street/StreetEdgeIssueTable.scala +++ b/app/models/street/StreetEdgeIssueTable.scala @@ -6,7 +6,7 @@ import play.api.Play.current case class StreetEdgeIssue(streetEdgeIssueId: Int, streetEdgeId: Int, issue: String, userId: String, ipAddress: String, timestamp: Timestamp) -class StreetEdgeIssueTable(tag: Tag) extends Table[StreetEdgeIssue](tag, Some("sidewalk"), "street_edge_issue") { +class StreetEdgeIssueTable(tag: Tag) extends Table[StreetEdgeIssue](tag, "street_edge_issue") { def streetEdgeIssueId = column[Int]("street_edge_issue_id", O.PrimaryKey, O.AutoInc) def streetEdgeId = column[Int]("street_edge_id", O.NotNull) def issue = column[String]("issue") diff --git a/app/models/street/StreetEdgePriorityTable.scala b/app/models/street/StreetEdgePriorityTable.scala index cb957c8507..3d39222103 100644 --- a/app/models/street/StreetEdgePriorityTable.scala +++ b/app/models/street/StreetEdgePriorityTable.scala @@ -20,7 +20,7 @@ case class StreetEdgePriority(streetEdgePriorityId: Int, streetEdgeId: Int, prio } } -class StreetEdgePriorityTable(tag: slick.lifted.Tag) extends Table[StreetEdgePriority](tag, Some("sidewalk"), "street_edge_priority") { +class StreetEdgePriorityTable(tag: slick.lifted.Tag) extends Table[StreetEdgePriority](tag, "street_edge_priority") { def streetEdgePriorityId = column[Int]("street_edge_priority_id", O.NotNull, O.PrimaryKey, O.AutoInc) def streetEdgeId = column[Int]("street_edge_id", O.NotNull) def priority = column[Double]("priority", O.NotNull) diff --git a/app/models/street/StreetEdgeRegionTable.scala b/app/models/street/StreetEdgeRegionTable.scala index 478c602dd6..e8c3afae2f 100644 --- a/app/models/street/StreetEdgeRegionTable.scala +++ b/app/models/street/StreetEdgeRegionTable.scala @@ -8,7 +8,7 @@ import scala.slick.lifted.ForeignKeyQuery case class StreetEdgeRegion(streetEdgeId: Int, regionId: Int) -class StreetEdgeRegionTable(tag: Tag) extends Table[StreetEdgeRegion](tag, Some("sidewalk"), "street_edge_region") { +class StreetEdgeRegionTable(tag: Tag) extends Table[StreetEdgeRegion](tag, "street_edge_region") { def streetEdgeId = column[Int]("street_edge_id") def regionId = column[Int]("region_id") diff --git a/app/models/street/StreetEdgeTable.scala b/app/models/street/StreetEdgeTable.scala index 7eae5fa5f8..daed95a78e 100644 --- a/app/models/street/StreetEdgeTable.scala +++ b/app/models/street/StreetEdgeTable.scala @@ -19,7 +19,7 @@ case class StreetEdge(streetEdgeId: Int, geom: LineString, x1: Float, y1: Float, case class StreetEdgeInfo(val street: StreetEdge, osmId: Int, regionId: Int, val auditCount: Int) -class StreetEdgeTable(tag: Tag) extends Table[StreetEdge](tag, Some("sidewalk"), "street_edge") { +class StreetEdgeTable(tag: Tag) extends Table[StreetEdge](tag, "street_edge") { def streetEdgeId = column[Int]("street_edge_id", O.PrimaryKey) def geom = column[LineString]("geom") def x1 = column[Float]("x1") diff --git a/app/models/survey/SurveyOptionTable.scala b/app/models/survey/SurveyOptionTable.scala index 992c254bb0..3b535c56fb 100644 --- a/app/models/survey/SurveyOptionTable.scala +++ b/app/models/survey/SurveyOptionTable.scala @@ -6,7 +6,7 @@ import scala.slick.lifted.ForeignKeyQuery case class SurveyOption(surveyOptionId: Int, surveyQuestionId: Int, surveyDisplayRank: Option[Int]) -class SurveyOptionTable(tag: Tag) extends Table[SurveyOption](tag, Some("sidewalk"), "survey_option") { +class SurveyOptionTable(tag: Tag) extends Table[SurveyOption](tag, "survey_option") { def surveyOptionId = column[Int]("survey_option_id", O.PrimaryKey) def surveyQuestionId = column[Int]("survey_question_id", O.NotNull) def surveyDisplayRank = column[Option[Int]]("survey_display_rank", O.Nullable) diff --git a/app/models/survey/SurveyQuestionTable.scala b/app/models/survey/SurveyQuestionTable.scala index fb504f1eb7..30eb01141d 100644 --- a/app/models/survey/SurveyQuestionTable.scala +++ b/app/models/survey/SurveyQuestionTable.scala @@ -5,7 +5,7 @@ import play.api.Play.current case class SurveyQuestion(surveyQuestionId: Int, surveyQuestionTextId: String, surveyInputType: String, surveyDisplayRank: Option[Int], deleted: Boolean, surveyUserRoleId: Int, required: Boolean) -class SurveyQuestionTable(tag: Tag) extends Table[SurveyQuestion](tag, Some("sidewalk"), "survey_question") { +class SurveyQuestionTable(tag: Tag) extends Table[SurveyQuestion](tag, "survey_question") { def surveyQuestionId = column[Int]("survey_question_id", O.PrimaryKey, O.AutoInc) def surveyQuestionTextId = column[String]("survey_question_text_id", O.NotNull) def surveyInputType = column[String]("survey_input_type", O.NotNull) diff --git a/app/models/user/OrganizationTable.scala b/app/models/user/OrganizationTable.scala index 95b8762876..8bf9123cb8 100644 --- a/app/models/user/OrganizationTable.scala +++ b/app/models/user/OrganizationTable.scala @@ -5,7 +5,7 @@ import play.api.Play.current case class Organization(orgId: Int, orgName: String, orgDescription: String) -class OrganizationTable(tag: slick.lifted.Tag) extends Table[Organization](tag, Some("sidewalk"), "organization") { +class OrganizationTable(tag: slick.lifted.Tag) extends Table[Organization](tag, "organization") { def orgId = column[Int]("org_id", O.PrimaryKey, O.AutoInc) def orgName = column[String]("org_name", O.NotNull) def orgDescription = column[String]("org_description", O.NotNull) diff --git a/app/models/user/RoleTable.scala b/app/models/user/RoleTable.scala index 62b8cf48c4..83f6f9b887 100644 --- a/app/models/user/RoleTable.scala +++ b/app/models/user/RoleTable.scala @@ -5,7 +5,7 @@ import play.api.Play.current case class Role(roleId: Int, role: String) -class RoleTable(tag: Tag) extends Table[Role](tag, Some("sidewalk"), "role") { +class RoleTable(tag: Tag) extends Table[Role](tag, "role") { def roleId = column[Int]("role_id", O.PrimaryKey, O.AutoInc) def role = column[String]("role", O.NotNull) diff --git a/app/models/user/UserCurrentRegionTable.scala b/app/models/user/UserCurrentRegionTable.scala index 845457523f..0352146607 100644 --- a/app/models/user/UserCurrentRegionTable.scala +++ b/app/models/user/UserCurrentRegionTable.scala @@ -10,7 +10,7 @@ import models.utils.CommonUtils.METERS_TO_MILES case class UserCurrentRegion(userCurrentRegionId: Int, userId: String, regionId: Int) -class UserCurrentRegionTable(tag: Tag) extends Table[UserCurrentRegion](tag, Some("sidewalk"), "user_current_region") { +class UserCurrentRegionTable(tag: Tag) extends Table[UserCurrentRegion](tag, "user_current_region") { def userCurrentRegionId = column[Int]("user_current_region_id", O.PrimaryKey, O.AutoInc) def userId = column[String]("user_id", O.NotNull) def regionId = column[Int]("region_id", O.NotNull) diff --git a/app/models/user/UserOrgTable.scala b/app/models/user/UserOrgTable.scala index c545bfad39..2146bcc447 100644 --- a/app/models/user/UserOrgTable.scala +++ b/app/models/user/UserOrgTable.scala @@ -6,7 +6,7 @@ import play.api.Play.current case class UserOrg(userOrgId: Int, userId: String, orgId: Int) -class UserOrgTable(tag: slick.lifted.Tag) extends Table[UserOrg](tag, Some("sidewalk"), "user_org") { +class UserOrgTable(tag: slick.lifted.Tag) extends Table[UserOrg](tag, "user_org") { def userOrgId = column[Int]("user_org_id", O.PrimaryKey, O.AutoInc) def userId = column[String]("user_id", O.NotNull) def orgId = column[Int]("org_id", O.NotNull) diff --git a/app/models/user/UserRoleTable.scala b/app/models/user/UserRoleTable.scala index 126c7689e7..26bfd110ce 100644 --- a/app/models/user/UserRoleTable.scala +++ b/app/models/user/UserRoleTable.scala @@ -7,7 +7,7 @@ import scala.util.control.NonFatal case class UserRole(userRoleId: Int, userId: String, roleId: Int, communityService: Boolean) -class UserRoleTable(tag: Tag) extends Table[UserRole](tag, Some("sidewalk"), "user_role") { +class UserRoleTable(tag: Tag) extends Table[UserRole](tag, "user_role") { def userRoleId = column[Int]("user_role_id", O.PrimaryKey, O.AutoInc) def userId = column[String]("user_id", O.NotNull) def roleId = column[Int]("role_id", O.NotNull) diff --git a/app/models/user/UserStatTable.scala b/app/models/user/UserStatTable.scala index 5bd38da4f6..f2a1b9e454 100644 --- a/app/models/user/UserStatTable.scala +++ b/app/models/user/UserStatTable.scala @@ -78,7 +78,7 @@ case class UserStatAPI(userId: String, labels: Int, metersExplored: Float, label case class LeaderboardStat(username: String, labelCount: Int, missionCount: Int, distanceMeters: Float, accuracy: Option[Float], score: Float) -class UserStatTable(tag: Tag) extends Table[UserStat](tag, Some("sidewalk"), "user_stat") { +class UserStatTable(tag: Tag) extends Table[UserStat](tag, "user_stat") { def userStatId = column[Int]("user_stat_id", O.PrimaryKey, O.AutoInc) def userId = column[String]("user_id", O.NotNull) def metersAudited = column[Float]("meters_audited", O.NotNull) diff --git a/app/models/user/UserSurveyOptionSubmission.scala b/app/models/user/UserSurveyOptionSubmission.scala index 5e7d95b97a..5f5450712f 100644 --- a/app/models/user/UserSurveyOptionSubmission.scala +++ b/app/models/user/UserSurveyOptionSubmission.scala @@ -9,7 +9,7 @@ import scala.slick.lifted.ForeignKeyQuery case class UserSurveyOptionSubmission(userSurveyOptionSubmissionId: Int, userId: String, surveyQuestionId: Int, surveyOptionId: Option[Int], timeSubmitted: Timestamp, numMissionsCompleted: Int) -class UserSurveyOptionSubmissionTable(tag: Tag) extends Table[UserSurveyOptionSubmission](tag, Some("sidewalk"), "user_survey_option_submission") { +class UserSurveyOptionSubmissionTable(tag: Tag) extends Table[UserSurveyOptionSubmission](tag, "user_survey_option_submission") { def userSurveyOptionSubmissionId = column[Int]("user_survey_option_submission_id", O.PrimaryKey, O.AutoInc) def userId = column[String]("user_id", O.NotNull) def surveyQuestionId = column[Int]("survey_question_id", O.NotNull) diff --git a/app/models/user/UserSurveyTextSubmission.scala b/app/models/user/UserSurveyTextSubmission.scala index 315b94d278..bb04a37693 100644 --- a/app/models/user/UserSurveyTextSubmission.scala +++ b/app/models/user/UserSurveyTextSubmission.scala @@ -9,7 +9,7 @@ import scala.slick.lifted.ForeignKeyQuery case class UserSurveyTextSubmission(userSurveyTextSubmissionId: Int, userId: String, surveyQuestionId: Int, surveyTextSubmission: Option[String], timeSubmitted: Timestamp, numMissionsCompleted: Int) -class UserSurveyTextSubmissionTable(tag: Tag) extends Table[UserSurveyTextSubmission](tag, Some("sidewalk"), "user_survey_text_submission") { +class UserSurveyTextSubmissionTable(tag: Tag) extends Table[UserSurveyTextSubmission](tag, "user_survey_text_submission") { def userSurveyTextSubmissionId = column[Int]("user_survey_text_submission_id", O.PrimaryKey, O.AutoInc) def userId = column[String]("user_id", O.NotNull) def surveyQuestionId = column[Int]("survey_question_id", O.NotNull) diff --git a/app/models/user/VersionTable.scala b/app/models/user/VersionTable.scala index 90f7cce995..82ad92bab9 100644 --- a/app/models/user/VersionTable.scala +++ b/app/models/user/VersionTable.scala @@ -11,7 +11,7 @@ import play.api.Play.current case class Version(versionId: String, versionStartTime: Timestamp, description: Option[String]) -class VersionTable(tag: Tag) extends Table[Version](tag, Some("sidewalk"), "version") { +class VersionTable(tag: Tag) extends Table[Version](tag, "version") { def versionId = column[String]("version_id", O.PrimaryKey) def versionStartTime = column[Timestamp]("version_start_time", O.NotNull) def description = column[Option[String]]("description") diff --git a/app/models/user/WebpageActivityTable.scala b/app/models/user/WebpageActivityTable.scala index 217d17797e..3559ae830e 100644 --- a/app/models/user/WebpageActivityTable.scala +++ b/app/models/user/WebpageActivityTable.scala @@ -7,7 +7,7 @@ import play.api.libs.json.{JsObject, Json} case class WebpageActivity(webpageActivityId: Int, userId: String, ipAddress: String, description: String, timestamp: java.sql.Timestamp) -class WebpageActivityTable(tag: Tag) extends Table[WebpageActivity](tag, Some("sidewalk"), "webpage_activity") { +class WebpageActivityTable(tag: Tag) extends Table[WebpageActivity](tag, "webpage_activity") { def webpageActivityId = column[Int]("webpage_activity_id", O.PrimaryKey, O.AutoInc) def userId = column[String]("user_id", O.NotNull) def ipAddress = column[String]("ip_address", O.NotNull) diff --git a/app/models/validation/ValidationTaskCommentTable.scala b/app/models/validation/ValidationTaskCommentTable.scala index ba01565c98..a51a96b3d8 100644 --- a/app/models/validation/ValidationTaskCommentTable.scala +++ b/app/models/validation/ValidationTaskCommentTable.scala @@ -9,7 +9,7 @@ case class ValidationTaskComment(validationTaskCommentId: Int, missionId: Int, l heading: Double, pitch: Double, zoom: Int, lat: Double, lng: Double, timestamp: Timestamp, comment: String) -class ValidationTaskCommentTable(tag: Tag) extends Table[ValidationTaskComment](tag, Some("sidewalk"), "validation_task_comment") { +class ValidationTaskCommentTable(tag: Tag) extends Table[ValidationTaskComment](tag, "validation_task_comment") { def validationTaskCommentId = column[Int]("validation_task_comment_id", O.PrimaryKey, O.AutoInc) def missionId = column[Int]("mission_id", O.NotNull) def labelId = column[Int]("label_id", O.NotNull) diff --git a/app/models/validation/ValidationTaskEnvironmentTable.scala b/app/models/validation/ValidationTaskEnvironmentTable.scala index 8c9db7c04d..da5147d625 100644 --- a/app/models/validation/ValidationTaskEnvironmentTable.scala +++ b/app/models/validation/ValidationTaskEnvironmentTable.scala @@ -11,7 +11,7 @@ case class ValidationTaskEnvironment(validationTaskEnvironmentId: Int, missionId screenHeight: Option[Int], operatingSystem: Option[String], ipAddress: Option[String], language: String) -class ValidationTaskEnvironmentTable(tag: Tag) extends Table[ValidationTaskEnvironment](tag, Some("sidewalk"), "validation_task_environment") { +class ValidationTaskEnvironmentTable(tag: Tag) extends Table[ValidationTaskEnvironment](tag, "validation_task_environment") { def validationTaskEnvironmentId = column[Int]("validation_task_environment_id", O.PrimaryKey, O.AutoInc) def missionId = column[Option[Int]]("mission_id", O.Nullable) def browser = column[Option[String]]("browser", O.Nullable) diff --git a/app/models/validation/ValidationTaskInteractionTable.scala b/app/models/validation/ValidationTaskInteractionTable.scala index a183cc9f05..e1b140c721 100644 --- a/app/models/validation/ValidationTaskInteractionTable.scala +++ b/app/models/validation/ValidationTaskInteractionTable.scala @@ -18,7 +18,7 @@ case class ValidationTaskInteraction(validationTaskInteractionId: Int, timestamp: java.sql.Timestamp, isMobile: Boolean) -class ValidationTaskInteractionTable(tag: slick.lifted.Tag) extends Table[ValidationTaskInteraction](tag, Some("sidewalk"), "validation_task_interaction") { +class ValidationTaskInteractionTable(tag: slick.lifted.Tag) extends Table[ValidationTaskInteraction](tag, "validation_task_interaction") { def validationTaskInteractionId = column[Int]("validation_task_interaction_id", O.PrimaryKey, O.AutoInc) def missionId = column[Option[Int]]("mission_id", O.Nullable) def action = column[String]("action", O.NotNull) diff --git a/package.json b/package.json index ea95bdcdec..9ffd19c0ca 100644 --- a/package.json +++ b/package.json @@ -1,19 +1,19 @@ { - "devDependencies": { - "eslint": "^7.26.0", - "grunt": "^1.4.0", - "grunt-concat-css": "*", - "grunt-contrib-concat": "*", - "grunt-contrib-watch": "*", - "htmlhint": "^0.14.2", - "stylelint": "^13.13.1", - "stylelint-config-standard": "^22.0.0" - }, - "scripts": { - "grunt-concat": "grunt concat && grunt concat_css", - "build": "npm install && grunt", - "debug": "npm run grunt-concat && grunt watch & sbt -jvm-debug 9998 run", - "start": "npm run grunt-concat && grunt watch & sbt -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' -mem 12288 compile \"~ run\" shell", - "test": "grunt && grunt test" - } + "devDependencies": { + "eslint": "^7.26.0", + "grunt": "^1.4.0", + "grunt-concat-css": "*", + "grunt-contrib-concat": "*", + "grunt-contrib-watch": "*", + "htmlhint": "^0.14.2", + "stylelint": "^13.13.1", + "stylelint-config-standard": "^22.0.0" + }, + "scripts": { + "grunt-concat": "grunt concat && grunt concat_css", + "build": "npm install && grunt", + "debug": "npm run grunt-concat && grunt watch & sbt -jvm-debug 9998 run", + "start": "npm run grunt-concat && grunt watch & sbt -Dhttp.port=$SIDEWALK_HTTP_PORT -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' -mem 12288 compile \"~ run\" shell", + "test": "grunt && grunt test" + } } From a84175eee90e2bb619231fe505edbb37a2caff03 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Tue, 7 Nov 2023 14:07:08 -0800 Subject: [PATCH 06/77] updates map styling for RouteBuilder --- public/javascripts/routeBuilder.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index f7fb1dc986..e01156ee95 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -21,7 +21,7 @@ function RouteBuilder ($, mapParamData) { mapboxgl.accessToken = mapParamData.mapbox_api_key; var map = new mapboxgl.Map({ container: 'route-builder-map', - style: 'mapbox://styles/mapbox/streets-v11', + style: 'mapbox://styles/projectsidewalk/cloov4big002801rc0qw75w5g', minZoom: 9, maxZoom: 19 }); From b2825647ff83b1641dd42dd03bd75f41ce8a7bb0 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Tue, 7 Nov 2023 16:57:42 -0800 Subject: [PATCH 07/77] updates RouteBuilder street styling towards new mocks --- public/javascripts/routeBuilder.js | 74 ++++++++++++++++++++---------- 1 file changed, 50 insertions(+), 24 deletions(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index e01156ee95..714da783f1 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -8,6 +8,7 @@ function RouteBuilder ($, mapParamData) { let neighborhoodData = null; let streetData = null; + let streetDataInRoute = null; let currRoute = []; let currRegionId = null; let savedRoute = null; @@ -138,8 +139,9 @@ function RouteBuilder ($, mapParamData) { } }); // Make sure that the polygons are visually below the streets. - if (map.getLayer('streets')) { + if (map.getLayer('streets') && map.getLayer('streets-chosen')) { map.moveLayer('neighborhoods', 'streets'); + map.moveLayer('streets', 'streets-chosen'); } } function renderNeighborhoods(neighborhoodDataIn) { @@ -159,6 +161,44 @@ function RouteBuilder ($, mapParamData) { data: streetData, promoteId: 'street_edge_id' }); + // Add another source for the streets that have been added to the route. + streetDataInRoute = { + type: 'FeatureCollection', + features: [] + }; + map.addSource('streets-chosen', { + type: 'geojson', + data: streetDataInRoute, + promoteId: 'street_edge_id' + }); + map.loadImage( + '/assets/images/icons/routebuilder-street-vector.png', + (err, image) => { + // Add the image to the map style. + map.addImage('street-arrow', image); + + // Create a new layer and style it using `fill-pattern`. + map.addLayer({ + 'id': 'streets-chosen', + 'type': 'line', + 'source': 'streets-chosen', + 'layout': { + 'line-join': 'round', + 'line-cap': 'round' + }, + 'paint': { + 'line-pattern': 'street-arrow', + // Line width scales based on zoom level. + 'line-width': [ + 'interpolate', ['linear'], ['zoom'], + 12, 1, + 15, 5 + ], + 'line-opacity': 0.75 + } + }); + } + ); map.addLayer({ id: 'streets', type: 'line', @@ -169,9 +209,8 @@ function RouteBuilder ($, mapParamData) { }, paint: { 'line-color': ['case', - ['boolean', ['feature-state', 'chosen'], false], '#4a6', - ['boolean', ['feature-state', 'hover'], false], '#da1', - '#777' + ['boolean', ['feature-state', 'hover'], false], '#236ee0', + '#ddefff' ], // Line width scales based on zoom level. 'line-width': [ @@ -179,7 +218,10 @@ function RouteBuilder ($, mapParamData) { 12, 1, 15, 5 ], - 'line-opacity': 0.75 + 'line-opacity': ['case', + ['boolean', ['feature-state', 'chosen'], false], 0.0, + 0.75 + ] } }); @@ -235,6 +277,7 @@ function RouteBuilder ($, mapParamData) { if (currState.chosen) { // If the street was in the route, remove it from the route. currRoute = currRoute.filter(s => s.properties.street_edge_id !== streetId); + streetDataInRoute.features = streetDataInRoute.features.filter(s => s.properties.street_edge_id !== streetId); // If there are no longer any streets in the route, any street can now be selected. Update styles. if (currRoute.length === 0) { @@ -243,20 +286,12 @@ function RouteBuilder ($, mapParamData) { currRegionId = null; saveButton.attr('aria-disabled', true); saveButton.tooltip('disable'); - map.setPaintProperty( - 'streets', - 'line-color', - ['case', - ['boolean', ['feature-state', 'chosen'], false], '#4a6', - ['boolean', ['feature-state', 'hover'], false], '#da1', - '#777' - ] - ); } } else { // Add the new street to the route. currRoute.push(street[0]); + streetDataInRoute.features.push(street[0]); // If this was first street added, change style to show you can't choose streets in other regions. if (currRoute.length === 1) { @@ -264,18 +299,9 @@ function RouteBuilder ($, mapParamData) { saveButton.attr('aria-disabled', false); saveButton.tooltip('disable'); map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: true }); - map.setPaintProperty( - 'streets', - 'line-color', - ['case', - ['boolean', ['!=', ['get', 'region_id'], currRegionId]], '#bbb', - ['boolean', ['feature-state', 'chosen'], false], '#4a6', - ['boolean', ['feature-state', 'hover'], false], '#da1', - '#777' - ] - ); } } + map.getSource('streets-chosen').setData(streetDataInRoute); setRouteDistanceText(); }); } From e7323443a0a53453c37f50ee506ed65829d158ac Mon Sep 17 00:00:00 2001 From: dylanbun <56641275+dylanbun@users.noreply.github.com> Date: Wed, 8 Nov 2023 14:18:09 -0800 Subject: [PATCH 08/77] added constraint via foreign key --- conf/evolutions/default/206.sql | 7 +++++++ 1 file changed, 7 insertions(+) create mode 100644 conf/evolutions/default/206.sql diff --git a/conf/evolutions/default/206.sql b/conf/evolutions/default/206.sql new file mode 100644 index 0000000000..e151e42c36 --- /dev/null +++ b/conf/evolutions/default/206.sql @@ -0,0 +1,7 @@ +# --- !Ups +DELETE FROM webpage_activity WHERE user_id IS NULL OR user_is NOT IN (SELECT user_id FROM sidewalk_user); + +ALTER TABLE webpage_activity ADD CONSTRAINT fk_webpage_activity_user_id FOREIGN KEY (user_id) REFERENCES sidewalk_user (user_id); + +# --- !Downs +ALTER TABLE webpage_activity DROP CONSTRAINT fk_webpage_activity_user_id; From 25549d5e298a290f99c46d0ba113419889f76628 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Wed, 8 Nov 2023 14:38:06 -0800 Subject: [PATCH 09/77] RouteBuilder streets appear now appear to reverse direction on 2nd click --- .../icons/routebuilder-street-vector.png | Bin 0 -> 215 bytes public/javascripts/routeBuilder.js | 21 +++++++++++++----- 2 files changed, 15 insertions(+), 6 deletions(-) create mode 100644 public/images/icons/routebuilder-street-vector.png diff --git a/public/images/icons/routebuilder-street-vector.png b/public/images/icons/routebuilder-street-vector.png new file mode 100644 index 0000000000000000000000000000000000000000..7fe434b2de5aa14752ad304bb9d688444838a941 GIT binary patch literal 215 zcmeAS@N?(olHy`uVBq!ia0vp^azM<(!3HEt^>~ed6lZ})WHAE+w=f7ZGR&GI0Tg5` z4sv&5Sa(k5C6L3C?&#~tz_78O`%fY(ke}n};uuoFcyx-P&;bPwmiM35J;_aaxVv|T z(o7FU-kgU47VqXT3y7^17ijW5#d(62f2w9s& s.properties.street_edge_id !== streetId); streetDataInRoute.features = streetDataInRoute.features.filter(s => s.properties.street_edge_id !== streetId); @@ -287,8 +292,11 @@ function RouteBuilder ($, mapParamData) { saveButton.attr('aria-disabled', true); saveButton.tooltip('disable'); } - } - else { + } else if (currState.chosen === 'chosen') { + // If the street was in the route, reverse it on this click. + streetDataInRoute.features.find(s => s.properties.street_edge_id === streetId).geometry.coordinates.reverse(); + map.getSource('streets-chosen').setData(streetDataInRoute); + } else { // Add the new street to the route. currRoute.push(street[0]); streetDataInRoute.features.push(street[0]); @@ -301,6 +309,7 @@ function RouteBuilder ($, mapParamData) { map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: true }); } } + console.log(streetDataInRoute); map.getSource('streets-chosen').setData(streetDataInRoute); setRouteDistanceText(); }); From e60cf7702433629996abe370856699e6a4847f27 Mon Sep 17 00:00:00 2001 From: timkaltenbach Date: Wed, 8 Nov 2023 14:42:08 -0800 Subject: [PATCH 10/77] cleaning up --- public/javascripts/SVValidate/src/Main.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/public/javascripts/SVValidate/src/Main.js b/public/javascripts/SVValidate/src/Main.js index 764c2ac209..cf544f3180 100644 --- a/public/javascripts/SVValidate/src/Main.js +++ b/public/javascripts/SVValidate/src/Main.js @@ -202,7 +202,7 @@ function Main (param) { const labelType = param.labelList[0].getAuditProperty('labelType'); - const missionStartTutorial = new MissionStartTutorial('validate', labelType, { labelCount: param.mission.labels_validated }, svv, param.language); + const missionStartTutorial = new MissionStartTutorial('validate', labelType, { nLabels: param.mission.labels_validated }, svv, param.language); } // Gets all the text on the validation page for the correct language. From 4e11e828f2a7087cd6a77ce35e562ad23c4fca39 Mon Sep 17 00:00:00 2001 From: Matthew Broadhead Date: Thu, 9 Nov 2023 13:33:43 -0800 Subject: [PATCH 11/77] Separate out start-no-docker for backward compatibility --- package.json | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/package.json b/package.json index 9ffd19c0ca..abeb7de08e 100644 --- a/package.json +++ b/package.json @@ -13,7 +13,8 @@ "grunt-concat": "grunt concat && grunt concat_css", "build": "npm install && grunt", "debug": "npm run grunt-concat && grunt watch & sbt -jvm-debug 9998 run", - "start": "npm run grunt-concat && grunt watch & sbt -Dhttp.port=$SIDEWALK_HTTP_PORT -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' -mem 12288 compile \"~ run\" shell", + "start": "npm run grunt-concat && grunt watch & sbt -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' -mem 12288 compile \"~ run\" shell", + "start-no-docker": "npm run grunt-concat && grunt watch & sbt -Dhttp.port=$SIDEWALK_HTTP_PORT -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' -mem 12288 compile \"~ run\" shell", "test": "grunt && grunt test" } } From 7d89859d65439aaa71e18c7ec58d4df7258ca167 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 9 Nov 2023 15:37:16 -0800 Subject: [PATCH 12/77] RouteBuilder streets have improved hover functionality, switched to sprites --- .../icons/routebuilder-street-vector.png | Bin 215 -> 0 bytes public/javascripts/routeBuilder.js | 153 +++++++++++------- 2 files changed, 99 insertions(+), 54 deletions(-) delete mode 100644 public/images/icons/routebuilder-street-vector.png diff --git a/public/images/icons/routebuilder-street-vector.png b/public/images/icons/routebuilder-street-vector.png deleted file mode 100644 index 7fe434b2de5aa14752ad304bb9d688444838a941..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 215 zcmeAS@N?(olHy`uVBq!ia0vp^azM<(!3HEt^>~ed6lZ})WHAE+w=f7ZGR&GI0Tg5` z4sv&5Sa(k5C6L3C?&#~tz_78O`%fY(ke}n};uuoFcyx-P&;bPwmiM35J;_aaxVv|T z(o7FU-kgU47VqXT3y7^17ijW5#d(62f2w9s& { - // Add the image to the map style. - map.addImage('street-arrow', image); + map.addSource('chosen-hover-flip', { + type: 'geojson', + data: { type: 'FeatureCollection', features: [] }, + promoteId: 'street_edge_id' + }); + map.addSource('chosen-hover-remove', { + type: 'geojson', + data: { type: 'FeatureCollection', features: [] }, + promoteId: 'street_edge_id' + }); - // Create a new layer and style it using `fill-pattern`. - map.addLayer({ - 'id': 'streets-chosen', - 'type': 'line', - 'source': 'streets-chosen', - 'layout': { - 'line-join': 'round', - 'line-cap': 'round' - }, - 'paint': { - 'line-pattern': 'street-arrow', - // Line width scales based on zoom level. - 'line-width': [ - 'interpolate', ['linear'], ['zoom'], - 12, 1, - 15, 5 - ], - 'line-opacity': 0.75 - } - }); + map.addLayer({ + 'id': 'streets-chosen', + 'type': 'line', + 'source': 'streets-chosen', + 'paint': { + 'line-pattern': 'street-arrow1', + // Line width scales based on zoom level. + 'line-width': [ + 'interpolate', ['linear'], ['zoom'], + 12, 1, + 15, 5 + ], + 'line-opacity': ['case', + ['boolean', ['feature-state', 'hover'], false], 0.0, + 0.75 + ] } - ); + }); + map.addLayer({ + 'id': 'chosen-hover-flip', + 'type': 'line', + 'source': 'chosen-hover-flip', + 'paint': { + 'line-pattern': 'street-arrow1-reversed', + // 'line-color': '#333333', + // Line width scales based on zoom level. + 'line-width': [ + 'interpolate', ['linear'], ['zoom'], + 12, 1, + 15, 5 + ], + 'line-opacity': 0.75 + } + }); + map.addLayer({ + 'id': 'chosen-hover-remove', + 'type': 'line', + 'source': 'chosen-hover-remove', + 'paint': { + 'line-pattern': 'street-arrow2', + // Line width scales based on zoom level. + 'line-width': [ + 'interpolate', ['linear'], ['zoom'], + 12, 1, + 15, 5 + ], + 'line-opacity': 0.75 + } + }); map.addLayer({ id: 'streets', type: 'line', source: 'streets', - layout: { - 'line-join': 'round', - 'line-cap': 'round' - }, paint: { 'line-color': ['case', ['boolean', ['feature-state', 'hover'], false], '#236ee0', @@ -234,22 +261,37 @@ function RouteBuilder ($, mapParamData) { // Mark when a street is being hovered over. map.on('mousemove', (event) => { - const street = map.queryRenderedFeatures(event.point, { layers: ['streets'] }); - if (!street.length) return; + const streetQuery = map.queryRenderedFeatures(event.point, { layers: ['streets', 'streets-chosen'] }); + const street = streetQuery.filter(s => s.layer.id === 'streets')[0]; + if (!street) return; + const chosenStreet = streetQuery.filter(s => s.layer.id === 'streets-chosen')[0]; // If we moved directly from hovering over one street to another, set the previous as hover: false. if (streetId) map.setFeatureState({ source: 'streets', id: streetId }, { hover: false }); - streetId = street[0].properties.street_edge_id; + if (streetId) map.setFeatureState({ source: 'streets-chosen', id: streetId }, { hover: false }); + streetId = street.properties.street_edge_id; map.setFeatureState({ source: 'streets', id: streetId }, { hover: true }); + map.setFeatureState({ source: 'streets-chosen', id: streetId }, { hover: true }); map.getCanvas().style.cursor = 'pointer'; // Show a tooltip informing user that they can't have multiple regions in the same route. - if (currRegionId && currRegionId !== street[0].properties.region_id) { - popup.setLngLat(street[0].geometry.coordinates[0]) + if (currRegionId && currRegionId !== street.properties.region_id) { + popup.setLngLat(street.geometry.coordinates[0]) .addTo(map); } + if (chosenStreet && street.state.chosen === 'chosen') { + map.getSource('chosen-hover-flip').setData({ type: 'FeatureCollection', features: [chosenStreet] }); + map.getSource('chosen-hover-remove').setData({ type: 'FeatureCollection', features: [] }); + } else if (chosenStreet && street.state.chosen === 'chosen reversed') { + map.getSource('chosen-hover-flip').setData({ type: 'FeatureCollection', features: [] }); + map.getSource('chosen-hover-remove').setData({ type: 'FeatureCollection', features: [chosenStreet] }); + } else { + map.getSource('chosen-hover-flip').setData({ type: 'FeatureCollection', features: [] }); + map.getSource('chosen-hover-remove').setData({ type: 'FeatureCollection', features: [] }); + } + // const popup = new mapboxgl.Popup({ offset: [0, -15] }) // .setLngLat(street[0].geometry.coordinates[0]) // .setHTML(`

    ${street[0].properties.street_edge_id}

    ${street[0].properties.way_type}

    `) @@ -258,7 +300,12 @@ function RouteBuilder ($, mapParamData) { // When not hovering over any streets, set prev street to hover: false and reset cursor. map.on('mouseleave', 'streets', () => { - if (streetId) map.setFeatureState({ source: 'streets', id: streetId }, { hover: false }); + if (streetId) { + map.setFeatureState({ source: 'streets', id: streetId }, { hover: false }); + map.setFeatureState({ source: 'streets-chosen', id: streetId }, { hover: false }); + map.getSource('chosen-hover-flip').setData({ type: 'FeatureCollection', features: [] }); + map.getSource('chosen-hover-remove').setData({ type: 'FeatureCollection', features: [] }); + } streetId = null; map.getCanvas().style.cursor = ''; popup.remove(); @@ -272,14 +319,15 @@ function RouteBuilder ($, mapParamData) { } streetId = street[0].properties.street_edge_id; - let currState = map.getFeatureState({ source: 'streets', id: streetId }); - let newState; - if (currState.chosen === 'chosen') newState = 'chosen reversed'; - else if (currState.chosen === 'chosen reversed') newState = 'not chosen'; - else newState = 'chosen'; - map.setFeatureState({ source: 'streets', id: streetId }, { chosen: newState }); + let currState = street[0].state; - if (currState.chosen === 'chosen reversed') { + if (currState.chosen === 'chosen') { + map.setFeatureState({ source: 'streets', id: streetId }, { chosen: 'chosen reversed' }); + // If the street was in the route, reverse it on this click. + streetDataInRoute.features.find(s => s.properties.street_edge_id === streetId).geometry.coordinates.reverse(); + map.getSource('streets-chosen').setData(streetDataInRoute); + } else if (currState.chosen === 'chosen reversed') { + map.setFeatureState({ source: 'streets', id: streetId }, { chosen: 'not chosen' }); // If the street was in the route, remove it from the route. currRoute = currRoute.filter(s => s.properties.street_edge_id !== streetId); streetDataInRoute.features = streetDataInRoute.features.filter(s => s.properties.street_edge_id !== streetId); @@ -292,11 +340,8 @@ function RouteBuilder ($, mapParamData) { saveButton.attr('aria-disabled', true); saveButton.tooltip('disable'); } - } else if (currState.chosen === 'chosen') { - // If the street was in the route, reverse it on this click. - streetDataInRoute.features.find(s => s.properties.street_edge_id === streetId).geometry.coordinates.reverse(); - map.getSource('streets-chosen').setData(streetDataInRoute); } else { + map.setFeatureState({ source: 'streets', id: streetId }, { chosen: 'chosen' }); // Add the new street to the route. currRoute.push(street[0]); streetDataInRoute.features.push(street[0]); @@ -309,7 +354,7 @@ function RouteBuilder ($, mapParamData) { map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: true }); } } - console.log(streetDataInRoute); + // console.log(streetDataInRoute); map.getSource('streets-chosen').setData(streetDataInRoute); setRouteDistanceText(); }); From 591d7c36252704d710746b58634c4a425fa75f82 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 9 Nov 2023 15:52:57 -0800 Subject: [PATCH 13/77] RouteBuilder no longer showing hover effectis immediately after clicking --- public/javascripts/routeBuilder.js | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 9e1411504c..fffd62423f 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -254,6 +254,7 @@ function RouteBuilder ($, mapParamData) { }); let streetId = null; + let clickedStreetId = null; const popup = new mapboxgl.Popup({ closeButton: false, closeOnClick: false @@ -263,7 +264,8 @@ function RouteBuilder ($, mapParamData) { map.on('mousemove', (event) => { const streetQuery = map.queryRenderedFeatures(event.point, { layers: ['streets', 'streets-chosen'] }); const street = streetQuery.filter(s => s.layer.id === 'streets')[0]; - if (!street) return; + // Don't show hover effects if the street was just clicked on. + if (!street || street.properties.street_edge_id === clickedStreetId) return; const chosenStreet = streetQuery.filter(s => s.layer.id === 'streets-chosen')[0]; // If we moved directly from hovering over one street to another, set the previous as hover: false. @@ -307,6 +309,7 @@ function RouteBuilder ($, mapParamData) { map.getSource('chosen-hover-remove').setData({ type: 'FeatureCollection', features: [] }); } streetId = null; + clickedStreetId = null; // This helps avoid showing hover effects directly after clicking a street. map.getCanvas().style.cursor = ''; popup.remove(); }); @@ -319,6 +322,7 @@ function RouteBuilder ($, mapParamData) { } streetId = street[0].properties.street_edge_id; + clickedStreetId = streetId; let currState = street[0].state; if (currState.chosen === 'chosen') { From 161683254a81777e88bac81f99d094e0b6e1dcdf Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 9 Nov 2023 16:29:03 -0800 Subject: [PATCH 14/77] fixes some edge case issues with hovering over selected streets in RouteBuilder --- public/javascripts/routeBuilder.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index fffd62423f..ba272a1441 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -206,7 +206,6 @@ function RouteBuilder ($, mapParamData) { 'source': 'chosen-hover-flip', 'paint': { 'line-pattern': 'street-arrow1-reversed', - // 'line-color': '#333333', // Line width scales based on zoom level. 'line-width': [ 'interpolate', ['linear'], ['zoom'], @@ -274,7 +273,9 @@ function RouteBuilder ($, mapParamData) { streetId = street.properties.street_edge_id; map.setFeatureState({ source: 'streets', id: streetId }, { hover: true }); - map.setFeatureState({ source: 'streets-chosen', id: streetId }, { hover: true }); + if (chosenStreet && clickedStreetId !== chosenStreet.properties.street_edge_id) { + map.setFeatureState({ source: 'streets-chosen', id: streetId }, { hover: true }); + } map.getCanvas().style.cursor = 'pointer'; // Show a tooltip informing user that they can't have multiple regions in the same route. @@ -349,6 +350,7 @@ function RouteBuilder ($, mapParamData) { // Add the new street to the route. currRoute.push(street[0]); streetDataInRoute.features.push(street[0]); + map.getSource('streets-chosen').setData(streetDataInRoute); // If this was first street added, change style to show you can't choose streets in other regions. if (currRoute.length === 1) { @@ -358,8 +360,6 @@ function RouteBuilder ($, mapParamData) { map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: true }); } } - // console.log(streetDataInRoute); - map.getSource('streets-chosen').setData(streetDataInRoute); setRouteDistanceText(); }); } From 0a84ac540fb67a68435d119a685a42492b4fa921 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 9 Nov 2023 16:32:24 -0800 Subject: [PATCH 15/77] RouteBuilder removed streets no longer remaining visible for a bit --- public/javascripts/routeBuilder.js | 2 ++ 1 file changed, 2 insertions(+) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index ba272a1441..ffb60dc69f 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -333,9 +333,11 @@ function RouteBuilder ($, mapParamData) { map.getSource('streets-chosen').setData(streetDataInRoute); } else if (currState.chosen === 'chosen reversed') { map.setFeatureState({ source: 'streets', id: streetId }, { chosen: 'not chosen' }); + // If the street was in the route, remove it from the route. currRoute = currRoute.filter(s => s.properties.street_edge_id !== streetId); streetDataInRoute.features = streetDataInRoute.features.filter(s => s.properties.street_edge_id !== streetId); + map.getSource('streets-chosen').setData(streetDataInRoute); // If there are no longer any streets in the route, any street can now be selected. Update styles. if (currRoute.length === 0) { From 74c95cbc1389a753e797ca02b41a336c79c1db56 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Fri, 10 Nov 2023 11:04:06 -0800 Subject: [PATCH 16/77] disables double click zoom in RouteBuilder --- public/javascripts/routeBuilder.js | 1 + 1 file changed, 1 insertion(+) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index ffb60dc69f..5cbb3d6590 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -26,6 +26,7 @@ function RouteBuilder ($, mapParamData) { minZoom: 9, maxZoom: 19 }); + map.doubleClickZoom.disable(); const mapboxLang = new MapboxLanguage({ defaultLanguage: i18next.t('common:mapbox-language-code') }); map.addControl(mapboxLang); map.addControl(new mapboxgl.NavigationControl({ visualizePitch: true }), 'top-left'); From cb3476ebd4dee0131bdeac43b68672c7726cdf23 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Fri, 10 Nov 2023 13:50:23 -0800 Subject: [PATCH 17/77] RouteBuilder WIP grouping routes into contiguous sections --- app/views/routeBuilder.scala.html | 1 + public/javascripts/routeBuilder.js | 44 ++++++++++++++++++++++++++++++ 2 files changed, 45 insertions(+) diff --git a/app/views/routeBuilder.scala.html b/app/views/routeBuilder.scala.html index f3bf88c336..af560e3e7e 100644 --- a/app/views/routeBuilder.scala.html +++ b/app/views/routeBuilder.scala.html @@ -48,6 +48,7 @@ }); $.when(initMap, loadStreets).done(function(d0, streetData) { routeBuilder.renderStreets(streetData[0]); + window.routeBuilder = routeBuilder; }); }); }); diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 5cbb3d6590..26ba78f0a8 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -352,6 +352,7 @@ function RouteBuilder ($, mapParamData) { map.setFeatureState({ source: 'streets', id: streetId }, { chosen: 'chosen' }); // Add the new street to the route. currRoute.push(street[0]); + console.log(street[0].properties.street_edge_id); streetDataInRoute.features.push(street[0]); map.getSource('streets-chosen').setData(streetDataInRoute); @@ -382,6 +383,49 @@ function RouteBuilder ($, mapParamData) { streetDistanceElem.text(i18next.t('route-length', { dist: routeDistance.toFixed(2) })); } + + // Using streetDataInRoute, find the contiguous routes as a list of lists of features. + // TODO do something to preserve ordering + function computeContiguousRoutes() { + let contiguousRoutes = []; + let currContiguousRoute = []; + let streetsInRoute = Array.from(streetDataInRoute.features); // shallow copy + console.log(streetsInRoute); + while (streetsInRoute.length > 0) { + if (currContiguousRoute.length === 0 && streetsInRoute.length === 1) { + console.log(streetsInRoute[0].properties.street_edge_id); + contiguousRoutes.push([streetsInRoute.shift()]); + } else if (currContiguousRoute.length === 0) { + console.log(streetsInRoute[0].properties.street_edge_id); + currContiguousRoute.push(streetsInRoute.shift()); + } else { + let connectedStreetFound = false; + let lastStreet = currContiguousRoute[currContiguousRoute.length - 1]; + let p1 = turf.point(lastStreet.geometry.coordinates[lastStreet.geometry.coordinates.length - 1]); + for (let i = 0; i < streetsInRoute.length; i++) { + let p2 = turf.point(streetsInRoute[i].geometry.coordinates[0]); + let distance = turf.distance(p1, p2, { units: 'kilometers' }); + console.log(p1); + console.log(p2); + console.log(distance); + if (distance < 0.01) { + console.log(streetsInRoute[i].properties.street_edge_id); + currContiguousRoute.push(streetsInRoute.splice(i, 1)[0]); + connectedStreetFound = true; + break; + } + } + if (!connectedStreetFound) { + contiguousRoutes.push(currContiguousRoute); + currContiguousRoute = []; + } + } + } + + return contiguousRoutes; + } + self.computeContiguousRoutes = computeContiguousRoutes; + /** * Used to log user activity to the `webpage_activity` table. * @param activity From 32f1ed9c435d54e3ea2a46bacf9f823eee39d5a2 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Fri, 10 Nov 2023 14:28:40 -0800 Subject: [PATCH 18/77] RouteBuilder func to compute contiguous sections of route is done --- public/javascripts/routeBuilder.js | 47 ++++++++++++++---------------- 1 file changed, 22 insertions(+), 25 deletions(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 26ba78f0a8..6df8111e40 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -47,7 +47,6 @@ function RouteBuilder ($, mapParamData) { [mapParamData.southwest_boundary.lng, mapParamData.southwest_boundary.lat], [mapParamData.northeast_boundary.lng, mapParamData.northeast_boundary.lat] ]); - console.log(map); // Set up the route length in the top-right of the map. let units = i18next.t('common:unit-distance'); @@ -352,7 +351,6 @@ function RouteBuilder ($, mapParamData) { map.setFeatureState({ source: 'streets', id: streetId }, { chosen: 'chosen' }); // Add the new street to the route. currRoute.push(street[0]); - console.log(street[0].properties.street_edge_id); streetDataInRoute.features.push(street[0]); map.getSource('streets-chosen').setData(streetDataInRoute); @@ -384,45 +382,44 @@ function RouteBuilder ($, mapParamData) { } - // Using streetDataInRoute, find the contiguous routes as a list of lists of features. - // TODO do something to preserve ordering + // Find the contiguous sections of the route as a list of lists of features. We do this by looping through the + // streets in the order that they were added to the route, and checking the remaining streets in the route (also in + // the order they were chosen) to see if any of their start points are connected to the end point of the current + // street. When there are no connected streets, that contiguous section is done and we start a new one. + // TODO do something to preserve ordering, I'm not sure if mapbox guarantees that ordering is preserved. + // Could either add a property with the ordering, or keep track in a separate list. function computeContiguousRoutes() { - let contiguousRoutes = []; - let currContiguousRoute = []; + let contiguousSections = []; + let currContiguousSection = []; let streetsInRoute = Array.from(streetDataInRoute.features); // shallow copy - console.log(streetsInRoute); while (streetsInRoute.length > 0) { - if (currContiguousRoute.length === 0 && streetsInRoute.length === 1) { - console.log(streetsInRoute[0].properties.street_edge_id); - contiguousRoutes.push([streetsInRoute.shift()]); - } else if (currContiguousRoute.length === 0) { - console.log(streetsInRoute[0].properties.street_edge_id); - currContiguousRoute.push(streetsInRoute.shift()); + if (currContiguousSection.length === 0) { + currContiguousSection.push(streetsInRoute.shift()); } else { + // Search for least recently chosen street with endpoint within 10 m of the current street. + let currStreet = currContiguousSection.slice(-1)[0]; + let p1 = turf.point(currStreet.geometry.coordinates.slice(-1)[0]); let connectedStreetFound = false; - let lastStreet = currContiguousRoute[currContiguousRoute.length - 1]; - let p1 = turf.point(lastStreet.geometry.coordinates[lastStreet.geometry.coordinates.length - 1]); for (let i = 0; i < streetsInRoute.length; i++) { let p2 = turf.point(streetsInRoute[i].geometry.coordinates[0]); - let distance = turf.distance(p1, p2, { units: 'kilometers' }); - console.log(p1); - console.log(p2); - console.log(distance); - if (distance < 0.01) { - console.log(streetsInRoute[i].properties.street_edge_id); - currContiguousRoute.push(streetsInRoute.splice(i, 1)[0]); + if (turf.distance(p1, p2, { units: 'kilometers' }) < 0.01) { + currContiguousSection.push(streetsInRoute.splice(i, 1)[0]); connectedStreetFound = true; break; } } + // If no connected street was found, this contiguous section is done. if (!connectedStreetFound) { - contiguousRoutes.push(currContiguousRoute); - currContiguousRoute = []; + contiguousSections.push(currContiguousSection); + currContiguousSection = []; } } } + if (currContiguousSection.length > 0) { + contiguousSections.push(currContiguousSection); + } - return contiguousRoutes; + return contiguousSections; } self.computeContiguousRoutes = computeContiguousRoutes; From 79a1dcad82d2faa585feaf45d7deab3ae4d7dafc Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Mon, 13 Nov 2023 13:21:10 -0800 Subject: [PATCH 19/77] RouteBuilder now has start/end markers for the route --- public/images/icons/end-point.png | Bin 0 -> 585 bytes public/images/icons/start-point.png | Bin 0 -> 725 bytes public/javascripts/routeBuilder.js | 13 +++++++++++++ public/stylesheets/routeBuilder.css | 14 ++++++++++++++ 4 files changed, 27 insertions(+) create mode 100644 public/images/icons/end-point.png create mode 100644 public/images/icons/start-point.png diff --git a/public/images/icons/end-point.png b/public/images/icons/end-point.png new file mode 100644 index 0000000000000000000000000000000000000000..cf0918952753adc53ce500029bd709f1225f2dee GIT binary patch literal 585 zcmV-P0=E5$P);M1&0drDELIAGL9O(c600d`2O+f$vv5yPn-rJD4cKWG3vieOM~V4_fqA zTOo+UExyrZFR*fxISq;g7-S$(VNttc6O5uJ3z0;1T+`1mClQCn*Lmwh2u0>aG{paL zwi;o8jB=#m7h@8F7Fbr*qPP3B-4+d-gi}+6QwmHk&;eG6I3DJRCA+A_5pr>HVRe=R ze$IsQfJ@{-nUTCsHLIVQwZ*+(((-n`vz9##7 zD*`S+mtBb?Yy(Vcpn&be54EJ6;3IL#>y+Be?N`Yjbpv^!=FCdW+2o1LtK;^$3i)*? zXD}EC(=Zv6gQ?*6YS2xVz1-IflNHHY7U&_XA3pZomJIG9=JLT8h_Dq0H`pvjs$B)u zSVCW%W;3vOeNzX*u3s0IdmI=%Hh?z^c(;%P$*%7cHiUupur3%?>}P4faySN}t}!BX zBC0?Q@Yr*b^DxeO(!zS?fN5YXnn%ZL)k_?JoWR X+<%1%2|Ltm00000NkvXXu0mjf;M1&0drDELIAGL9O(c600d`2O+f$vv5yP?sgM2h%A!Z}7MklI&Ns&9(?;LU|;;hbi18N#;N$9KDHLMO>n3X4pJGB7Hf+g`;Q zEW5uBJ4yr<_4(}FJ>gt+f9i6l!B+N*LgSFYTMx=BT;m({r7Pkdg7aC0dX)=jJ5e0?`<4K(_Y1} zfg0XHruwe2RSn`rWdYwB;x5n><>&c{yPb9Frb_j)+DJ2d1@Rn literal 0 HcmV?d00001 diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 6df8111e40..67a1fb52d4 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -381,6 +381,19 @@ function RouteBuilder ($, mapParamData) { streetDistanceElem.text(i18next.t('route-length', { dist: routeDistance.toFixed(2) })); } + // Draws the endpoints for the contiguous sections of the route on the map. + function drawContiguousEndpointMarkers() { + const startPointEl = document.createElement('div'); + startPointEl.className = 'marker marker-start'; + const endPointEl = document.createElement('div'); + endPointEl.className = 'marker marker-end'; + let contigSections = computeContiguousRoutes(); + let startPoint = turf.point(contigSections[0][0].geometry.coordinates[0]); + let endPoint = turf.point(contigSections.slice(-1)[0].slice(-1)[0].geometry.coordinates.slice(-1)[0]); + new mapboxgl.Marker(startPointEl).setLngLat(startPoint.geometry.coordinates).addTo(map); + new mapboxgl.Marker(endPointEl).setLngLat(endPoint.geometry.coordinates).addTo(map); + } + self.drawContiguousEndpointMarkers = drawContiguousEndpointMarkers; // Find the contiguous sections of the route as a list of lists of features. We do this by looping through the // streets in the order that they were added to the route, and checking the remaining streets in the route (also in diff --git a/public/stylesheets/routeBuilder.css b/public/stylesheets/routeBuilder.css index ccec41f16a..f276b6d36f 100644 --- a/public/stylesheets/routeBuilder.css +++ b/public/stylesheets/routeBuilder.css @@ -39,3 +39,17 @@ .route-builder-button[aria-disabled="true"] { background-color: #ddd; } + +.marker { + background-position: center; + width: 27px; + height: 27px; +} + +.marker-start { + background-image: url(/assets/images/icons/start-point.png); +} + +.marker-end { + background-image: url(/assets/images/icons/end-point.png); +} From bd10c38780c28466e47db8d39ce8c99711a7e710 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Mon, 13 Nov 2023 16:09:16 -0800 Subject: [PATCH 20/77] RouteBuilder now shows connections b/w contiguous segments --- public/javascripts/routeBuilder.js | 43 ++++++++++++++++++++++++----- public/stylesheets/routeBuilder.css | 11 ++++++++ 2 files changed, 47 insertions(+), 7 deletions(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 67a1fb52d4..32322a4a8d 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -13,6 +13,9 @@ function RouteBuilder ($, mapParamData) { let currRegionId = null; let savedRoute = null; + let currentMarkers = []; + const endpointColors = ['#80c32a', '#ffc300', '#ff9700', '#ff6a00']; + let streetDistanceElem = $('#street-distance'); let saveButton = $('#route-builder-save-button'); let exploreButton = $('#route-builder-explore-button'); @@ -362,6 +365,7 @@ function RouteBuilder ($, mapParamData) { map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: true }); } } + updateMarkers(); setRouteDistanceText(); }); } @@ -381,19 +385,45 @@ function RouteBuilder ($, mapParamData) { streetDistanceElem.text(i18next.t('route-length', { dist: routeDistance.toFixed(2) })); } + // Delete old markers and draw new ones. + function updateMarkers() { + currentMarkers.forEach(m => m.remove()); + currentMarkers = []; + drawContiguousEndpointMarkers(); + } + // Draws the endpoints for the contiguous sections of the route on the map. function drawContiguousEndpointMarkers() { + // Add start point. const startPointEl = document.createElement('div'); startPointEl.className = 'marker marker-start'; + let contigSections = computeContiguousRoutes(); + let startPoint = contigSections[0][0].geometry.coordinates[0]; + let startMarker = new mapboxgl.Marker(startPointEl).setLngLat(startPoint).addTo(map); + currentMarkers.push(startMarker); + + // Add colors for the midpoints. + for (let i = 0; i < contigSections.length - 1; i++) { + let midpointEl1 = document.createElement('div'); + let midpointEl2 = document.createElement('div'); + midpointEl1.className = midpointEl2.className = 'marker marker-number'; + midpointEl1.innerHTML = midpointEl2.innerHTML = (i + 1).toString(); + midpointEl1.style.background = midpointEl2.style.background = endpointColors[i % endpointColors.length]; + let midPoint1 = contigSections[i].slice(-1)[0].geometry.coordinates.slice(-1)[0]; + let midPoint2 = contigSections[i + 1][0].geometry.coordinates[0]; + let p1Marker = new mapboxgl.Marker(midpointEl1).setLngLat(midPoint1).addTo(map); + let p2Marker = new mapboxgl.Marker(midpointEl2).setLngLat(midPoint2).addTo(map); + currentMarkers.push(p1Marker); + currentMarkers.push(p2Marker); + } + + // Add endpoint. const endPointEl = document.createElement('div'); endPointEl.className = 'marker marker-end'; - let contigSections = computeContiguousRoutes(); - let startPoint = turf.point(contigSections[0][0].geometry.coordinates[0]); - let endPoint = turf.point(contigSections.slice(-1)[0].slice(-1)[0].geometry.coordinates.slice(-1)[0]); - new mapboxgl.Marker(startPointEl).setLngLat(startPoint.geometry.coordinates).addTo(map); - new mapboxgl.Marker(endPointEl).setLngLat(endPoint.geometry.coordinates).addTo(map); + let endPoint = contigSections.slice(-1)[0].slice(-1)[0].geometry.coordinates.slice(-1)[0]; + let endMarker = new mapboxgl.Marker(endPointEl).setLngLat(endPoint).addTo(map); + currentMarkers.push(endMarker); } - self.drawContiguousEndpointMarkers = drawContiguousEndpointMarkers; // Find the contiguous sections of the route as a list of lists of features. We do this by looping through the // streets in the order that they were added to the route, and checking the remaining streets in the route (also in @@ -434,7 +464,6 @@ function RouteBuilder ($, mapParamData) { return contiguousSections; } - self.computeContiguousRoutes = computeContiguousRoutes; /** * Used to log user activity to the `webpage_activity` table. diff --git a/public/stylesheets/routeBuilder.css b/public/stylesheets/routeBuilder.css index f276b6d36f..ef0f1648da 100644 --- a/public/stylesheets/routeBuilder.css +++ b/public/stylesheets/routeBuilder.css @@ -53,3 +53,14 @@ .marker-end { background-image: url(/assets/images/icons/end-point.png); } + +.marker-number { + width: 21px; + height: 21px; + border-radius: 50%; + color: #fff; + text-align: center; + /* Possibly change font-weight to 600 (bold) and remove font-family if we keep icons this size, bc that looks cleaner. */ + font-family: Roboto, serif; + font-weight: 900; +} From 7f20445b8b812c588f7929b1f62dcd9c060bcf67 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Mon, 13 Nov 2023 16:22:43 -0800 Subject: [PATCH 21/77] RouteBuilder start icon now points towards first street bearing --- public/images/icons/start-point.png | Bin 725 -> 678 bytes public/javascripts/routeBuilder.js | 7 +++++-- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/public/images/icons/start-point.png b/public/images/icons/start-point.png index 572cb11a19fd076a9d54c7df292acb6f2f01afe9..3207f522c91b870d0ad33965e958caf0a23d6024 100644 GIT binary patch delta 603 zcmV-h0;K)b1*Qd%R)0H5L_t(|0o_)=Z__{&{_YY4BA{BT2pe@420GvjAa#H`e?eUV z5?jJbhqeQ(P5%Puz+Bit> z?z`vr<2&G{f)%pba17v<10Go5d16U298KK`t%o*6 zR)ak;4J|kpqkqwj$Vw#}1<%0-6tob`Qpq@b zs`G0nqLH6e3)v0|nFdC=g4sl#n$-ra-_^RRWCDXc4`=cj%-dDv0xN z>fMj{wl_SdS)D}&`lJM|N+$Ivz*^E;=EXbSNA2GNY$9@rP@;FZi`LE;)c!AE;2)(^ zG0}SJD5X$9_8m>!@bkbsAoTXioLG7R5%Bu3XF#J pXt4IfA`sM{_o;2_`q$OX#ToAisMNUNoM-?5002ovPDHLkV1h)`0U5w$hSUR3Ob9w6$ai$4;3 zvK~Bmun>>stf^k?Nj-TnoK5===&dKxdTLTkT4MzCQZ8s?OlYf6`UC2`RW=K=yR+Da z?`5;I^WJCPzBlv6k;~-{(IrXfqFi<+{W`26vzteuzJXF>Q-6IYU2>jAv`0p)Cj`I4 zBlP32`iz%^crynFyo!Tjoz?*Sh~81 z^v)vwR}^8YFV2l~1ws)W1w^97k{?T0sZqwu>HT;*SR`!cR zYTMx= zBT;m({eSmy9D3rLXaR9BQjE3v8SiZzMblozuz?!hL8khyu~iM?MP&is8saX{6y@jn ziMyS3>ZVHdvf4;9dj-op66AsB3KDFQRu> Date: Tue, 14 Nov 2023 10:52:56 -0800 Subject: [PATCH 22/77] adds initial instructions to RouteBuilder --- app/views/routeBuilder.scala.html | 8 +++++++- public/stylesheets/routeBuilder.css | 30 +++++++++++++++++++++++++++++ 2 files changed, 37 insertions(+), 1 deletion(-) diff --git a/app/views/routeBuilder.scala.html b/app/views/routeBuilder.scala.html index af560e3e7e..3025ef582e 100644 --- a/app/views/routeBuilder.scala.html +++ b/app/views/routeBuilder.scala.html @@ -15,7 +15,13 @@
    -
    +
    + Welcome to RouteBuilder + Improving accessibility in the neighborhood of your choosing by building, exploring and sharing your own route! + Click on a street to start building your route. +
    + + -
    -
    - A green circle with a white checkmark in the center -
    - Route Saved! - Edit this route +
    +
    +
    + A green circle with a white checkmark in the center +
    + Route Saved! + Edit this route +
    -
    -
    - Start exploring this route and labeling accessibility issues -
    - - +
    + Start exploring this route and labeling accessibility issues +
    + + +
    -
    -
    - Invite friends to explore this route with the following link -
    - https://sidewalk-sea.cs.washington.edu/explore?rout... - +
    + Invite friends to explore this route with the following link +
    + https://sidewalk-sea.cs.washington.edu/explore?rout... + +
    diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 07ba7920ab..bb377306e0 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -18,8 +18,9 @@ function RouteBuilder ($, mapParamData) { let streetDistanceElem = $('#route-length-value'); let saveButton = $('#save-button'); - let exploreButton = $('#route-builder-explore-button'); - let shareButton = $('#route-builder-share-button'); + let exploreButton = $('#explore-button'); + let copyLinkButton = $('#copy-link-button'); + let linkText = $('#share-route-link'); // Initialize the map. mapboxgl.accessToken = mapParamData.mapbox_api_key; @@ -57,8 +58,8 @@ function RouteBuilder ($, mapParamData) { // Create instructional tooltips for the buttons. saveButton.tooltip({ title: i18next.t('save-button-tooltip'), container: 'body' }); - exploreButton.tooltip({ title: i18next.t('explore-button-tooltip'), container: 'body' }); - shareButton.tooltip({ title: i18next.t('share-button-tooltip'), container: 'body' }); + // exploreButton.tooltip({ title: i18next.t('explore-button-tooltip'), container: 'body' }); + copyLinkButton.tooltip({ title: i18next.t('share-button-tooltip'), container: 'body' }); // These functions will temporarily show a tooltip. Used when the user clicks the 'copy to clipboard' button. function setTemporaryTooltip(btn, message) { @@ -92,8 +93,13 @@ function RouteBuilder ($, mapParamData) { }) .then((response) => response.json()) .then((data) => { + // Show the route saved modal. + document.getElementById('route-saved-modal-overlay').style.visibility = 'visible'; + + + savedRoute = streetIds; - setTemporaryTooltip(saveButton, i18next.t('route-saved')); + // setTemporaryTooltip(saveButton, i18next.t('route-saved')); logActivity(`RouteBuilder_Click=SaveSuccess_RouteId=${data.route_id}`); // Update link and tooltip for Explore route button. @@ -103,18 +109,20 @@ function RouteBuilder ($, mapParamData) { logActivity(`RouteBuilder_Click=Explore_RouteId=${data.route_id}`); window.location.replace(exploreURL); }); - exploreButton.attr('aria-disabled', false); - exploreButton.tooltip('disable'); + // exploreButton.attr('aria-disabled', false); + // exploreButton.tooltip('disable'); // Add the 'copied to clipboard' tooltip on click. - shareButton.tooltip('disable'); - shareButton.off('click'); - shareButton.click(function (e) { + document.getElementById('share-route-link').textContent = `${window.location.origin}${exploreURL}`; + + copyLinkButton.tooltip('disable'); + copyLinkButton.off('click'); + copyLinkButton.click(function (e) { navigator.clipboard.writeText(`${window.location.origin}${exploreURL}`); setTemporaryTooltip(e.currentTarget, i18next.t('copied-to-clipboard')); logActivity(`RouteBuilder_Click=Copy_RouteId=${data.route_id}`); }); - shareButton.attr('aria-disabled', false); + // copyLinkButton.attr('aria-disabled', false); }) .catch((error) => { console.error('Error:', error); diff --git a/public/stylesheets/routeBuilder.css b/public/stylesheets/routeBuilder.css index 2f31ca7f7e..aa80c01f30 100644 --- a/public/stylesheets/routeBuilder.css +++ b/public/stylesheets/routeBuilder.css @@ -131,6 +131,17 @@ } +#route-saved-modal-overlay { + visibility: hidden; /* Show once the route has been saved. */ + height: 935px; /* navbar height + map height and margin + filler */ + width: 100%; + position: fixed; + top: 0; + left: 0; + background: rgba(0,0,0,0.1); + z-index: 2; +} + #route-saved-modal { position: absolute; top: calc(4% + 85px); /* 2% + navbar height + map margin-top */ From e158700bd70fbc19f65ca61719a7908e33e7a14b Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Wed, 15 Nov 2023 12:21:49 -0800 Subject: [PATCH 27/77] adds ability to clear the route in RouteBuilder --- public/javascripts/routeBuilder.js | 44 ++++++++++++++++++++++++----- public/stylesheets/routeBuilder.css | 8 +++--- 2 files changed, 41 insertions(+), 11 deletions(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index bb377306e0..8097394bb7 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -57,7 +57,7 @@ function RouteBuilder ($, mapParamData) { setRouteDistanceText(); // Create instructional tooltips for the buttons. - saveButton.tooltip({ title: i18next.t('save-button-tooltip'), container: 'body' }); + // saveButton.tooltip({ title: i18next.t('save-button-tooltip'), container: 'body' }); // exploreButton.tooltip({ title: i18next.t('explore-button-tooltip'), container: 'body' }); copyLinkButton.tooltip({ title: i18next.t('share-button-tooltip'), container: 'body' }); @@ -72,6 +72,11 @@ function RouteBuilder ($, mapParamData) { }, 1000); } + // Add the click event for the clear route buttons. + document.getElementById('build-new-route-button').addEventListener('click', clearRoute); + document.getElementById('cancel-button').addEventListener('click', clearRoute); + + // Saves the route to the database, enables explore/share buttons, updates tooltips for all buttons. let saveRoute = function() { let streetIds = currRoute.map(s => s.properties.street_edge_id); @@ -355,8 +360,10 @@ function RouteBuilder ($, mapParamData) { map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: false }); currRegionId = null; - saveButton.attr('aria-disabled', true); - saveButton.tooltip('disable'); + document.getElementById('routebuilder-intro').style.visibility = 'visible'; + document.getElementById('routebuilder-overlay2').style.visibility = 'hidden'; + // saveButton.attr('aria-disabled', true); + // saveButton.tooltip('disable'); } } else { map.setFeatureState({ source: 'streets', id: streetId }, { chosen: 'chosen' }); @@ -368,14 +375,13 @@ function RouteBuilder ($, mapParamData) { // If this was first street added, make additional UI changes. if (currRoute.length === 1) { // Remove the intro instructions and show the route length UI on the right. - let introEl = document.getElementById('routebuilder-intro'); - introEl.parentNode.removeChild(introEl); + document.getElementById('routebuilder-intro').style.visibility = 'hidden'; document.getElementById('routebuilder-overlay2').style.visibility = 'visible'; // Change style to show you can't choose streets in other regions. currRegionId = street[0].properties.region_id; - saveButton.attr('aria-disabled', false); - saveButton.tooltip('disable'); + // saveButton.attr('aria-disabled', false); + // saveButton.tooltip('disable'); map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: true }); } } @@ -482,6 +488,30 @@ function RouteBuilder ($, mapParamData) { return contiguousSections; } + /** + * Clear the current route and reset the map. + */ + function clearRoute() { + // Remove all the streets from the route. + currRoute.forEach(s => { + map.setFeatureState({ source: 'streets', id: s.properties.street_edge_id }, { chosen: 'not chosen' }); + }); + currRoute = []; + streetDataInRoute.features = []; + map.getSource('streets-chosen').setData(streetDataInRoute); + + // Reset the map. + map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: false }); + currRegionId = null; + setRouteDistanceText(); + + // Reset the UI. + document.getElementById('route-saved-modal-overlay').style.visibility = 'hidden'; + document.getElementById('routebuilder-overlay2').style.visibility = 'hidden'; + document.getElementById('routebuilder-intro').style.visibility = 'visible'; + updateMarkers(); + } + /** * Used to log user activity to the `webpage_activity` table. * @param activity diff --git a/public/stylesheets/routeBuilder.css b/public/stylesheets/routeBuilder.css index aa80c01f30..0f88a8d0e5 100644 --- a/public/stylesheets/routeBuilder.css +++ b/public/stylesheets/routeBuilder.css @@ -126,8 +126,8 @@ } #cancel-button { - background: var(--primary-white, #FFF); - color: var(--primary-asphalt, #2D2A3F); + background: #FFF; + color: #2D2A3F; } @@ -220,8 +220,8 @@ #build-new-route-button { border: 1.5px solid #525252; - background: var(--primary-white, #FFF); - color: var(--primary-asphalt, #2D2A3F); + background: #FFF; + color: #2D2A3F; } #route-saved-body-2 { From ffcdccce9f7ce432eea2f5b3fe00f8b5e1d9dbe2 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Wed, 15 Nov 2023 13:02:01 -0800 Subject: [PATCH 28/77] removes code from old implementation of RouteBuilder --- app/views/routeBuilder.scala.html | 12 ++----- conf/messages.de | 4 +-- conf/messages.en | 4 +-- conf/messages.es | 4 +-- conf/messages.nl | 4 +-- conf/messages.zh-TW | 4 +-- public/images/icons/test-check.svg | 3 ++ public/javascripts/routeBuilder.js | 45 +++++++------------------- public/locales/de/routebuilder.json | 4 --- public/locales/en/routebuilder.json | 4 --- public/locales/es/routebuilder.json | 4 --- public/locales/nl/routebuilder.json | 4 --- public/locales/zh-TW/routebuilder.json | 4 --- public/stylesheets/routeBuilder.css | 25 +------------- 14 files changed, 23 insertions(+), 102 deletions(-) create mode 100644 public/images/icons/test-check.svg diff --git a/app/views/routeBuilder.scala.html b/app/views/routeBuilder.scala.html index 860d1944fb..295f2e0e08 100644 --- a/app/views/routeBuilder.scala.html +++ b/app/views/routeBuilder.scala.html @@ -20,7 +20,7 @@ Improving accessibility in the neighborhood of your choosing by building, exploring and sharing your own route! Click on a street to start building your route.
    -
    +
    Creating Route
    @@ -55,7 +55,7 @@
    A green circle with a white checkmark in the center
    - Route Saved! + @Messages("routebuilder.saved") Edit this route
    @@ -76,14 +76,6 @@
    - - @@ -14,60 +14,58 @@ -
    +
    - Welcome to RouteBuilder - Improving accessibility in the neighborhood of your choosing by building, exploring and sharing your own route! - Click on a street to start building your route. + @Messages("routebuilder.welcome") + @Messages("routebuilder.intro.content") + @Messages("routebuilder.intro.instruction")
    -
    -
    - Creating Route -
    - @Messages("routebuilder.route.length") - +
    + @Messages("routebuilder.creating.route") +
    + @Messages("routebuilder.route.length") + +
    +
    +
    + @Messages("routebuilder.editing.route") +
    + @Messages( + @Messages("routebuilder.add.street.instruction")
    -
    -
    - Editing Route -
    - A map pin icon with a plus in the center - Click on streets on the map to add them to your route. -
    -
    - Two arrows forming a circle to indicate rotation - Click on any added street once to rotate the direction. -
    -
    - A trash can with an X on it - Click on any added street twice to delete it from the route. -
    +
    + @Messages( + @Messages("routebuilder.rotate.street.instruction")
    - To finish the build, click "Save Route". -
    - - +
    + @Messages( + @Messages("routebuilder.delete.street.instruction")
    + @Messages("routebuilder.save.route.instruction") +
    + + +
    - A green circle with a white checkmark in the center + @Messages( @Messages("routebuilder.saved")
    -
    - Start exploring this route and labeling accessibility issues +
    + @Messages("routebuilder.explore.title")
    - - + +
    -
    - Invite friends to explore this route with the following link -
    - https://sidewalk-sea.cs.washington.edu/explore?rout... - +
    + @Messages("routebuilder.share.title") +
    + +
    diff --git a/conf/messages.de b/conf/messages.de index 7aeb0fbba0..e5aa79fc0b 100644 --- a/conf/messages.de +++ b/conf/messages.de @@ -358,10 +358,28 @@ gallery.labels.not.found = Keine Treffer. Erkundung startenStart exploring to gallery.cards = Labels are sorted randomly based on selected filters gallery.clear.filters = Clear Filters -route.builder.name = RouteBuilder +routebuilder.name = RouteBuilder +routebuilder.welcome = Welcome to RouteBuilder +routebuilder.intro.content = Improving accessibility in the neighborhood of your choosing by building, exploring and sharing your own route! +routebuilder.intro.instruction = Click on a street to start building your route. +routebuilder.creating.route = Creating Route routebuilder.route.length = Route Length -route.builder.save = Save route +routebuilder.editing.route = Editing Route +routebuilder.add.street.icon.alt = A map pin icon with a plus in the center +routebuilder.add.street.instruction = Click on streets on the map to add them to your route. +routebuilder.rotate.street.icon.alt = Two arrows forming a circle to indicate rotation +routebuilder.rotate.street.instruction = Click on any added street once to rotate the direction. +routebuilder.delete.street.icon.alt = A trash can with an X on it +routebuilder.delete.street.instruction = Click on any added street twice to delete it from the route. +routebuilder.save.route.instruction = To finish the build, click "Save Route" +routebuilder.save = Save route +routebuilder.saved.icon.alt = A green circle with a white checkmark in the center routebuilder.saved = Route saved! +routebuilder.explore.title = Start exploring this route and labeling accessibility issues +routebuilder.explore.route = Explore This Route +routebuilder.build.another.route = Build Another Route +routebuilder.share.title = Invite friends to explore this route with the following link +routebuilder.copy.link = Copy Link help.rating.1 = Rating 1: Passable help.rating.3 = Rating 3: Neutral diff --git a/conf/messages.es b/conf/messages.es index 76ff7c8058..a0c492dc0e 100644 --- a/conf/messages.es +++ b/conf/messages.es @@ -360,10 +360,28 @@ gallery.labels.not.found = No hay resultados. ¡Comienza a ex gallery.cards = Las etiquetas se ordenan aleatoriamente según los filtros seleccionados gallery.clear.filters = Borrar Filtros -route.builder.name = Constructor de rutas +routebuilder.name = Constructor de rutas +routebuilder.welcome = Bienvenido a RouteBuilder +routebuilder.intro.content = ¡Mejora de la accesibilidad en el vecindario de su elección mediante la construcción, explorando y compartiendo su propia ruta! +routebuilder.intro.instruction = Haga clic en una calle para comenzar a construir su ruta. +routebuilder.creating.route = Creación de ruta routebuilder.route.length = Longitud de la ruta -route.builder.save = Guardar ruta +routebuilder.editing.route = Ruta de edición +routebuilder.add.street.icon.alt = Un icono de pin de mapa con una ventaja en el centro +routebuilder.add.street.instruction = Haga clic en las calles del mapa para agregarlas a su ruta. +routebuilder.rotate.street.icon.alt = Dos flechas que forman un círculo para indicar la rotación +routebuilder.rotate.street.instruction = Haga clic en cualquier calle agregada una vez para rotar la dirección. +routebuilder.delete.street.icon.alt = Un bote de basura con una x +routebuilder.delete.street.instruction = Haga clic en cualquier calle agregada dos veces para eliminarla de la ruta. +routebuilder.save.route.instruction = Para finalizar la compilación, haga clic en "Guardar ruta" +routebuilder.save = Guardar ruta +routebuilder.saved.icon.alt = Un círculo verde con una marca de verificación blanca en el centro routebuilder.saved = Ruta guardada! +routebuilder.explore.title = Comience a explorar esta ruta y etiquetar problemas de accesibilidad +routebuilder.explore.route = Explore esta ruta +routebuilder.build.another.route = Construir otra ruta +routebuilder.share.title = Invite a sus amigos a explorar esta ruta con el siguiente enlace +routebuilder.copy.link = Copiar link help.rating.1 = Calificación 1: Transitable help.rating.3 = Calificación 3: Neutral diff --git a/conf/messages.nl b/conf/messages.nl index ddfce4d765..1940b9844f 100644 --- a/conf/messages.nl +++ b/conf/messages.nl @@ -360,10 +360,28 @@ gallery.labels.not.found = Geen overeenkomsten. Begin met ver gallery.cards = Labels worden willekeurig gesorteerd op basis van geselecteerde filters gallery.clear.filters = Filters Wissen -route.builder.name = Routebuilder +routebuilder.name = Routebuilder +routebuilder.welcome = Welkom bij Routebuilder +routebuilder.intro.content = Verbetering van de toegankelijkheid in de buurt van uw keuze door uw eigen route te bouwen, te verkennen en te delen! +routebuilder.intro.instruction = Klik op een straat om uw route te bouwen. +routebuilder.creating.route = Route creëren routebuilder.route.length = Routelengte -route.builder.save = Route bewaren +routebuilder.editing.route = Bewerkingsroute +routebuilder.add.street.icon.alt = Een map pin -pictogram met een pluspunt in het midden +routebuilder.add.street.instruction = Klik op de straten op de kaart om ze aan uw route toe te voegen. +routebuilder.rotate.street.icon.alt = Twee pijlen vormen een cirkel om rotatie aan te geven +routebuilder.rotate.street.instruction = Klik eenmaal op een toegevoegde straat om de richting te roteren. +routebuilder.delete.street.icon.alt = Een prullenbak met een X erop +routebuilder.delete.street.instruction = Klik twee keer op een toegevoegde straat om deze uit de route te verwijderen. +routebuilder.save.route.instruction = Klik op "Route opslaan" om de build te voltooien +routebuilder.save = Route bewaren +routebuilder.saved.icon.alt = Een groene cirkel met een wit vinkje in het midden routebuilder.saved = Route opgeslagen! +routebuilder.explore.title = Begin met het verkennen van deze route en het labelen van toegankelijkheidsproblemen +routebuilder.explore.route = Verken deze route +routebuilder.build.another.route = Bouw een andere route +routebuilder.share.title = Nodig vrienden uit om deze route te verkennen met de volgende link +routebuilder.copy.link = Kopieer link help.rating.1 = Rating 1: Begaanbaar help.rating.3 = Rating 3: Neutraal diff --git a/conf/messages.zh-TW b/conf/messages.zh-TW index 07092172c2..3407edfb17 100644 --- a/conf/messages.zh-TW +++ b/conf/messages.zh-TW @@ -384,10 +384,28 @@ gallery.labels.not.found = 無相符資料。 開始探索`); hoverReversePopup._content.className = 'tooltip-no-outline'; // Remove default styling. @@ -322,7 +322,7 @@ function RouteBuilder ($, mapParams) { currRegionId = null; introUI.style.visibility = 'visible'; - streetDistOveraly.style.visibility = 'hidden'; + streetDistOverlay.style.visibility = 'hidden'; } } else { map.setFeatureState({ source: 'streets', id: streetId }, { chosen: 'chosen' }); @@ -344,7 +344,7 @@ function RouteBuilder ($, mapParams) { if (chosenStreets.features.length === 1) { // Remove the intro instructions and show the route length UI on the right. introUI.style.visibility = 'hidden'; - streetDistOveraly.style.visibility = 'visible'; + streetDistOverlay.style.visibility = 'visible'; // Change style to show you can't choose streets in other regions. currRegionId = street[0].properties.region_id; @@ -502,7 +502,7 @@ function RouteBuilder ($, mapParams) { // Reset the UI. routeSavedModal.style.visibility = 'hidden'; - streetDistOveraly.style.visibility = 'hidden'; + streetDistOverlay.style.visibility = 'hidden'; introUI.style.visibility = 'visible'; updateMarkers(); } diff --git a/public/locales/de/routebuilder.json b/public/locales/de/routebuilder.json index 3fa719c234..7ab195fb69 100644 --- a/public/locales/de/routebuilder.json +++ b/public/locales/de/routebuilder.json @@ -1,5 +1,6 @@ { "route-length": "{{dist}} $t(common:unit-distance-abbreviation)", + "hover-add-street": "Klicken Sie auf eine Straße, um Ihre Route zu bauen.", "copied-to-clipboard": "In die Zwischenablage kopiert!", "one-neighborhood-warning": "Eine Route kann zu diesem Zeitpunkt nur Straßen aus einer Nachbarschaft aus sein." } diff --git a/public/locales/en/routebuilder.json b/public/locales/en/routebuilder.json index 6522f249d3..6f3ce46994 100644 --- a/public/locales/en/routebuilder.json +++ b/public/locales/en/routebuilder.json @@ -1,5 +1,6 @@ { "route-length": "{{dist}} $t(common:unit-distance-abbreviation)", + "hover-add-street": "Click on a street to start building your route", "copied-to-clipboard": "Copied to clipboard!", "one-neighborhood-warning": "A route can only have streets from one neighborhood in it at this time." } diff --git a/public/locales/es/routebuilder.json b/public/locales/es/routebuilder.json index f675d8b364..d39e427b5d 100644 --- a/public/locales/es/routebuilder.json +++ b/public/locales/es/routebuilder.json @@ -1,5 +1,6 @@ { "route-length": "{{dist}} $t(common:unit-distance-abbreviation)", + "hover-add-street": "Haga clic en una calle para comenzar a construir su ruta.", "copied-to-clipboard": "¡Copiado al portapapeles!", "one-neighborhood-warning": "Una ruta solo puede tener calles de un vecindario en este momento." } diff --git a/public/locales/nl/routebuilder.json b/public/locales/nl/routebuilder.json index 7c34dd7140..60527bd6b6 100644 --- a/public/locales/nl/routebuilder.json +++ b/public/locales/nl/routebuilder.json @@ -1,5 +1,6 @@ { "route-length": "{{dist}} $t(common:unit-distance-abbreviation)", + "hover-add-street": "Klik op een straat om uw route te bouwen.", "copied-to-clipboard": "Gekopieerd naar het klembord!", "one-neighborhood-warning": "Een route kan op dit moment slechts straten uit één buurt hebben." } diff --git a/public/locales/zh-TW/routebuilder.json b/public/locales/zh-TW/routebuilder.json index 4e55f2f36a..c3be956d2a 100644 --- a/public/locales/zh-TW/routebuilder.json +++ b/public/locales/zh-TW/routebuilder.json @@ -1,5 +1,6 @@ { "route-length": "{{dist}} $t(common:unit-distance-abbreviation)", + "hover-add-street": "Click on a street to start building your route", "copied-to-clipboard": "已複製到剪貼板!", "one-neighborhood-warning": "目前,一條路線內只能包涵一個社區內的街道。" } diff --git a/public/stylesheets/routeBuilder.css b/public/stylesheets/routeBuilder.css index 11a84b0d62..461a6a1a87 100644 --- a/public/stylesheets/routeBuilder.css +++ b/public/stylesheets/routeBuilder.css @@ -1,4 +1,4 @@ -#route-builder-map { +#routebuilder-map { width: 98%; height: 800px; margin-top: 15px; @@ -35,7 +35,7 @@ padding-top: 16px; } -#routebuilder-overlay { +#creating-route-overlay { visibility: hidden; /* Show once the first street has been selected. */ position: absolute; top: calc(2% + 85px); /* 2% + navbar height + map margin-top */ @@ -48,21 +48,16 @@ background: #FFF; color: #000; box-shadow: 0px 4px 8px 0px rgba(0, 0, 0, 0.25); -} - -#routebuilder-overlay-instructions { - display: flex; - flex-direction: column; gap: 16px; } -#routebuilder-overlay-title { +#creating-route-title { font-size: 22px; font-weight: 700; line-height: 28px; /* 127.273% */ } -#routebuilder-route-length { +#route-length-section { display: flex; flex-direction: column; } @@ -71,7 +66,7 @@ font-size: 16px; } -#route-length-value { +#route-length-val { font-size: 36px; line-height: 44px; /* 122.222% */ } @@ -82,32 +77,32 @@ background: #b6b6b6; } -#route-editing-instructions { +#editing-route-section { display: flex; flex-direction: column; gap: 12px; } -#route-editing-title { +#editing-route-title { font-size: 16px; } -.route-edit-subsection { +.editing-route-subsection { display: flex; align-items: center; gap: 12px; } -.route-edit-icon { +.editing-route-icon { width: 48px; height: 48px; } -.route-edit-content { +.editing-route-subsection-content { flex: 1 0 0; } -#routebuilder-buttons { +#creating-route-buttons { display: flex; gap: 12px; } @@ -179,7 +174,7 @@ font-weight: 700; } -#route-saved-body-1 { +#route-saved-explore-section { display: flex; flex-direction: column; align-items: center; @@ -187,7 +182,7 @@ align-self: stretch; } -#route-saved-body-1-title { +#route-saved-explore-title { align-self: stretch; } @@ -207,18 +202,18 @@ color: #2D2A3F; } -#route-saved-body-2 { +#route-saved-share-section { display: flex; flex-direction: column; gap: 16px; align-self: stretch; } -#route-saved-body-2-title { +#route-saved-share-title { align-self: stretch; } -#share-route-section { +#share-route-subsection { display: flex; padding: 10px 20px; align-items: center; From cf4c2f21700e7f625fb70fc32fa7da1ce09155b4 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Tue, 28 Nov 2023 16:24:55 -0800 Subject: [PATCH 55/77] RouteBuilder start route tooltip now only shown for first street --- public/javascripts/routeBuilder.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 37c7935885..181715eb32 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -256,7 +256,7 @@ function RouteBuilder ($, mapParams) { hoverDeletePopup.addTo(map); hoverDeletePopup._content.parentNode.querySelector('[class*="tip"]').remove(); // Remove the arrow. } - } else { // Not yet chosen. + } else if (chosenStreets.features.length === 0) { // Not yet chosen and route is empty. hoverChoosePopup.setLngLat(event.lngLat); if (!hoverChoosePopup.isOpen()) { hoverChoosePopup.addTo(map); From 0dea45b9fadb7a46968b22847af8d26720ae7d91 Mon Sep 17 00:00:00 2001 From: dylanbun <56641275+dylanbun@users.noreply.github.com> Date: Wed, 29 Nov 2023 10:27:05 -0800 Subject: [PATCH 56/77] mysql syntax != postgresql... --- conf/evolutions/default/206.sql | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/conf/evolutions/default/206.sql b/conf/evolutions/default/206.sql index c769000bb9..73a6cdf05e 100644 --- a/conf/evolutions/default/206.sql +++ b/conf/evolutions/default/206.sql @@ -1,5 +1,5 @@ # --- !Ups -DELETE FROM webpage_activity FROM webpage_activity LEFT JOIN sidewalk_user ON webpage_activity.user_id = sidewalk_user.user_id WHERE webpage_activity.user_id IS NULL OR sidewalk_user.user_id IS NULL; +DELETE FROM webpage_activity USING sidewalk_user WHERE webpage_activity.user_id = sidewalk_user.user_id AND sidewalk_user.user_id IS NULL; ALTER TABLE webpage_activity ADD CONSTRAINT webpage_activity_user_id_fkey FOREIGN KEY (user_id) REFERENCES sidewalk_user (user_id); From 53eae70ac33ec46e31e55e7b69434d8e4a3e6806 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Wed, 29 Nov 2023 11:14:34 -0800 Subject: [PATCH 57/77] CSS adjustments for internationalizing RouteBuilder --- public/javascripts/routeBuilder.js | 2 +- public/stylesheets/routeBuilder.css | 3 ++- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 181715eb32..66684cfc4d 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -213,7 +213,7 @@ function RouteBuilder ($, mapParams) { // Create tooltips for when the user hovers over a street. const neighborhoodPopup = new mapboxgl.Popup({ closeButton: false, closeOnClick: false}) .setHTML(i18next.t('one-neighborhood-warning')); - const hoverChoosePopup = new mapboxgl.Popup({ closeButton: false, closeOnClick: false, offset: 10 }) + const hoverChoosePopup = new mapboxgl.Popup({ closeButton: false, closeOnClick: false, offset: 10, maxWidth: '340px' }) .setHTML(i18next.t('hover-add-street')); const hoverReversePopup = new mapboxgl.Popup({ closeButton: false, closeOnClick: false }) .setHTML(`Reverse`); diff --git a/public/stylesheets/routeBuilder.css b/public/stylesheets/routeBuilder.css index 461a6a1a87..85c6b09cf0 100644 --- a/public/stylesheets/routeBuilder.css +++ b/public/stylesheets/routeBuilder.css @@ -110,7 +110,8 @@ .routebuilder-button { display: flex; height: 30px; - padding: 8px 16px; + padding: 8px 13px; + font-size: 13px; align-items: center; border-radius: 6px; } From ffd1ac0ab8dd10aa00c8397e3a2ef6cef989298b Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Wed, 29 Nov 2023 13:14:25 -0800 Subject: [PATCH 58/77] consolidates RouteBuilder CSS --- app/views/routeBuilder.scala.html | 44 ++++---- public/javascripts/routeBuilder.js | 6 +- public/stylesheets/routeBuilder.css | 152 +++++----------------------- 3 files changed, 53 insertions(+), 149 deletions(-) diff --git a/app/views/routeBuilder.scala.html b/app/views/routeBuilder.scala.html index 7e5c7a0aed..0ac8e18969 100644 --- a/app/views/routeBuilder.scala.html +++ b/app/views/routeBuilder.scala.html @@ -15,20 +15,20 @@
    -
    - @Messages("routebuilder.welcome") +
    + @Messages("routebuilder.welcome") @Messages("routebuilder.intro.content") - @Messages("routebuilder.intro.instruction") + @Messages("routebuilder.intro.instruction")
    -
    - @Messages("routebuilder.creating.route") -
    - @Messages("routebuilder.route.length") +
    + @Messages("routebuilder.creating.route") +
    + @Messages("routebuilder.route.length")
    -
    - @Messages("routebuilder.editing.route") +
    + @Messages("routebuilder.editing.route")
    @Messages( @Messages("routebuilder.add.street.instruction") @@ -43,29 +43,29 @@
    @Messages("routebuilder.save.route.instruction") -
    - - +
    + +
    -
    -
    +
    +
    @Messages( - @Messages("routebuilder.saved") + @Messages("routebuilder.saved")
    -
    +
    @Messages("routebuilder.explore.title") -
    - - +
    + +
    -
    +
    @Messages("routebuilder.share.title") -
    +
    - +
    diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 66684cfc4d..3759ac58c4 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -390,7 +390,7 @@ function RouteBuilder ($, mapParams) { // Add start point. const startPointEl = document.createElement('div'); - startPointEl.className = 'marker marker-start'; + startPointEl.className = 'marker-start'; let startPoint = contigSections[0][0].geometry.coordinates[0]; let rotation = turf.bearing(startPoint, contigSections[0][0].geometry.coordinates[1]); let startMarker = new mapboxgl.Marker(startPointEl).setLngLat(startPoint).setRotation(rotation).addTo(map); @@ -400,7 +400,7 @@ function RouteBuilder ($, mapParams) { for (let i = 0; i < contigSections.length - 1; i++) { let midpointEl1 = document.createElement('div'); let midpointEl2 = document.createElement('div'); - midpointEl1.className = midpointEl2.className = 'marker marker-number'; + midpointEl1.className = midpointEl2.className = 'marker-number'; midpointEl1.innerHTML = midpointEl2.innerHTML = (i + 1).toString(); midpointEl1.style.background = midpointEl2.style.background = endpointColors[i % endpointColors.length]; let midPoint1 = contigSections[i].slice(-1)[0].geometry.coordinates.slice(-1)[0]; @@ -413,7 +413,7 @@ function RouteBuilder ($, mapParams) { // Add endpoint. const endPointEl = document.createElement('div'); - endPointEl.className = 'marker marker-end'; + endPointEl.className = 'marker-end'; let endPoint = contigSections.slice(-1)[0].slice(-1)[0].geometry.coordinates.slice(-1)[0]; let endMarker = new mapboxgl.Marker(endPointEl).setLngLat(endPoint).addTo(map); currentMarkers.push(endMarker); diff --git a/public/stylesheets/routeBuilder.css b/public/stylesheets/routeBuilder.css index 85c6b09cf0..3f1b6e9f08 100644 --- a/public/stylesheets/routeBuilder.css +++ b/public/stylesheets/routeBuilder.css @@ -5,91 +5,71 @@ left: 1%; } -#routebuilder-intro { - position: absolute; +.flex-div-col, .routebuilder-overlay { display: flex; - width: 520px; - padding: 20px 40px; - top: calc(4% + 85px); /* 2% + navbar height + map margin-top */ - left: calc(50% - 260px); /* 50% - width/2 */ flex-direction: column; +} + +.flex-div-row, .editing-route-subsection, .routebuilder-button { + display: flex; + flex-direction: row; + align-items: center; +} + +.routebuilder-overlay { + position: absolute; + padding: 20px 40px; border-radius: 20px; background: #FFF; box-shadow: 0px 4px 8px 0px rgba(0, 0, 0, 0.25); + color: #000; } -#routebuilder-intro-title { - color: #000; +.routebuilder-centered-overlay { + width: 520px; + top: calc(4% + 85px); /* 2% + navbar height + map margin-top */ + left: calc(50% - 260px); /* 50% - width/2 */ +} + +.routebuilder-h1 { font-size: 22px; font-weight: 700; + line-height: 28px; /* 127.273% */ } -#routebuilder-intro-content { - color: #000; +.routebuilder-h2 { + font-size: 16px; } #routebuilder-intro-instruction { color: #236EE0; - font-size: 16px; font-weight: 800; padding-top: 16px; } #creating-route-overlay { visibility: hidden; /* Show once the first street has been selected. */ - position: absolute; top: calc(2% + 85px); /* 2% + navbar height + map margin-top */ right: 3%; - display: flex; width: 320px; - padding: 20px 40px; - flex-direction: column; - border-radius: 20px; - background: #FFF; - color: #000; - box-shadow: 0px 4px 8px 0px rgba(0, 0, 0, 0.25); gap: 16px; } -#creating-route-title { - font-size: 22px; - font-weight: 700; - line-height: 28px; /* 127.273% */ -} - -#route-length-section { - display: flex; - flex-direction: column; -} - -#route-length-title { - font-size: 16px; -} - #route-length-val { font-size: 36px; line-height: 44px; /* 122.222% */ } #line-divider { - width: 240px; height: 1px; background: #b6b6b6; } #editing-route-section { - display: flex; - flex-direction: column; gap: 12px; } -#editing-route-title { - font-size: 16px; -} - .editing-route-subsection { - display: flex; - align-items: center; gap: 12px; } @@ -103,30 +83,28 @@ } #creating-route-buttons { - display: flex; gap: 12px; } .routebuilder-button { - display: flex; height: 30px; padding: 8px 13px; font-size: 13px; - align-items: center; border-radius: 6px; } -#save-button { +.blue-button { background: #236EE0; color: #FFF; + border: 1.5px solid #236EE0; } -#cancel-button { +.white-button { background: #FFF; color: #2D2A3F; + border: 1.5px solid #525252; } - #route-saved-modal-overlay { visibility: hidden; /* Show once the route has been saved. */ height: 935px; /* navbar height + map height and margin + filler */ @@ -139,48 +117,18 @@ } #route-saved-modal { - position: absolute; - top: calc(4% + 85px); /* 2% + navbar height + map margin-top */ - left: calc(50% - 260px); /* 50% - width/2 */ - display: flex; - width: 520px; - padding: 20px 40px; - flex-direction: column; - align-items: center; gap: 24px; - border-radius: 20px; - background: #FFF; - box-shadow: 0px 4px 8px 0px rgba(0, 0, 0, 0.25); - - color: #000; } #route-saved-title-section { - display: flex; padding-top: 8px; - flex-direction: column; align-items: center; gap: 12px; } -#route-saved-checkmark { - width: 80px; - height: 80px; - flex-shrink: 0; - fill: #00C354; -} - -#route-saved-title { - font-size: 22px; - font-weight: 700; -} - #route-saved-explore-section { - display: flex; - flex-direction: column; align-items: center; gap: 16px; - align-self: stretch; } #route-saved-explore-title { @@ -188,38 +136,15 @@ } #route-saved-buttons { - display: flex; gap: 12px; } -#explore-button { - background: #236EE0; - color: #FFF; -} - -#build-new-route-button { - border: 1.5px solid #525252; - background: #FFF; - color: #2D2A3F; -} - #route-saved-share-section { - display: flex; - flex-direction: column; gap: 16px; - align-self: stretch; -} - -#route-saved-share-title { - align-self: stretch; } #share-route-subsection { - display: flex; padding: 10px 20px; - align-items: center; - gap: 10px; - align-self: stretch; border-radius: 10px; background: #F2F2F2; } @@ -231,31 +156,11 @@ } #copy-link-button { - height: 30px; padding: 4px 8px; - border-radius: 4px; - background: #236EE0; - color: #FFF; font-size: 12px; } - - - -#route-builder-overlay { - position: absolute; - top: 80px; - right: 27px; - background: #fff; - margin-top: 20px; - padding: 5px; - width: 350px; - border-radius: 3px; - overflow: auto; -} - -.marker { - background-position: center; +.marker-start, .marker-end { width: 27px; height: 27px; } @@ -274,7 +179,6 @@ border-radius: 50%; color: #fff; text-align: center; - /* Possibly change font-weight to 600 (bold) and remove font-family if we keep icons this size, bc that looks cleaner. */ font-family: Roboto, serif; font-weight: 900; } From d727e46fe2b05420611ed8ff5d1a149704716d65 Mon Sep 17 00:00:00 2001 From: Matthew Broadhead Date: Thu, 30 Nov 2023 11:29:04 -0800 Subject: [PATCH 59/77] Remove -mem arg from sbt invocations so it aligns with prod --- package.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/package.json b/package.json index 5b80e0a302..a969352280 100644 --- a/package.json +++ b/package.json @@ -13,8 +13,8 @@ "grunt-concat": "grunt concat && grunt concat_css", "build": "npm install && grunt", "debug": "npm run grunt-concat && grunt watch & sbt -jvm-debug 9998 run", - "start": "npm run grunt-concat && grunt watch & sbt -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' -mem 12288 compile \"~ run\" shell", - "start-no-docker": "npm run grunt-concat && grunt watch & sbt -Dhttp.port=$SIDEWALK_HTTP_PORT -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' -mem 12288 compile \"~ run\" shell", + "start": "npm run grunt-concat && grunt watch & sbt -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' compile \"~ run\" shell", + "start-no-docker": "npm run grunt-concat && grunt watch & sbt -Dhttp.port=$SIDEWALK_HTTP_PORT -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' compile \"~ run\" shell", "test": "grunt && grunt test" } } From a97e40f7c8b573c540e8ecd7ed04e9814b227048 Mon Sep 17 00:00:00 2001 From: Matthew Broadhead Date: Thu, 30 Nov 2023 14:49:01 -0800 Subject: [PATCH 60/77] Updated to reflect removal of mem arg --- README.md | 1 - 1 file changed, 1 deletion(-) diff --git a/README.md b/README.md index de9c4485c4..f35fe78430 100644 --- a/README.md +++ b/README.md @@ -77,7 +77,6 @@ On Windows, we recommend [Windows Powershell](https://docs.microsoft.com/en-us/p 1. Email Mikey (michaelssaugstad@gmail.com) and ask for a database dump, a Mapbox API key, and a Google Maps API key & secret (if you are not part of our team, you'll have to [create a Google Maps API key](https://developers.google.com/maps/documentation/javascript/get-api-key) yourself). 1. If your computer has an Apple Silicon (M1 or M2) chip, then you should modify the `platform` line in the `docker-compose.yml`, changing it to `linux/arm64`. -1. If your computer has less than 16 GB of RAM, I'd recommend modifying `-mem 12288` to `-mem 8192` or lower in the `package.json` file so that you don't fill up your computer's memory. 1. Modify the `MAPBOX_API_KEY`, `GOOGLE_MAPS_API_KEY`, and `GOOGLE_MAPS_SECRET` lines in the `docker-compose.yml` using the keys and secret you've acquired. 1. Modify the `SIDEWALK_CITY_ID` line in the `docker-compose.yml` to use the ID of the appropriate city, listed [here](https://github.com/ProjectSidewalk/SidewalkWebpage/wiki/Docker-Troubleshooting#first-heres-a-table-that-youll-reference-when-setting-up-your-dev-env). 1. Modify the `DATABASE_URL` line in the `docker-compose.yml`, replacing "sidewalk" with the database name from the table [linked above](https://github.com/ProjectSidewalk/SidewalkWebpage/wiki/Docker-Troubleshooting#first-heres-a-table-that-youll-reference-when-setting-up-your-dev-env). From 832c62380e8bc25065c9337dcef3bb7bd709e78c Mon Sep 17 00:00:00 2001 From: dylanbun <56641275+dylanbun@users.noreply.github.com> Date: Fri, 1 Dec 2023 15:12:27 -0800 Subject: [PATCH 61/77] thank you Sir Saugstad --- conf/evolutions/default/206.sql | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/conf/evolutions/default/206.sql b/conf/evolutions/default/206.sql index 73a6cdf05e..af69075c8b 100644 --- a/conf/evolutions/default/206.sql +++ b/conf/evolutions/default/206.sql @@ -1,5 +1,5 @@ # --- !Ups -DELETE FROM webpage_activity USING sidewalk_user WHERE webpage_activity.user_id = sidewalk_user.user_id AND sidewalk_user.user_id IS NULL; +DELETE FROM webpage_activity LEFT JOIN sidewalk_user ON webpage_activity.user_id = sidewalk_user.user_id WHERE webpage_activity.user_id IS NULL OR sidewalk_user.user_id IS NULL; ALTER TABLE webpage_activity ADD CONSTRAINT webpage_activity_user_id_fkey FOREIGN KEY (user_id) REFERENCES sidewalk_user (user_id); From b64d8edaac250e09841cd2e0f097bd606d10e88e Mon Sep 17 00:00:00 2001 From: dylanbun <56641275+dylanbun@users.noreply.github.com> Date: Fri, 1 Dec 2023 15:16:49 -0800 Subject: [PATCH 62/77] this sould work now... --- conf/evolutions/default/206.sql | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/conf/evolutions/default/206.sql b/conf/evolutions/default/206.sql index af69075c8b..9dbebd85c1 100644 --- a/conf/evolutions/default/206.sql +++ b/conf/evolutions/default/206.sql @@ -1,5 +1,5 @@ # --- !Ups -DELETE FROM webpage_activity LEFT JOIN sidewalk_user ON webpage_activity.user_id = sidewalk_user.user_id WHERE webpage_activity.user_id IS NULL OR sidewalk_user.user_id IS NULL; +DELETE FROM webpage_activity USING sidewalk_user WHERE webpage_activity.user_id = sidewalk_user.user_id AND (webpage_activity.user_id IS NULL OR sidewalk_user.user_id IS NULL); ALTER TABLE webpage_activity ADD CONSTRAINT webpage_activity_user_id_fkey FOREIGN KEY (user_id) REFERENCES sidewalk_user (user_id); From 52cef6a101030e24d688f92840c8ddc885aa3e0f Mon Sep 17 00:00:00 2001 From: dylanbun <56641275+dylanbun@users.noreply.github.com> Date: Mon, 4 Dec 2023 11:02:34 -0800 Subject: [PATCH 63/77] surely the query works now --- conf/evolutions/default/206.sql | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/conf/evolutions/default/206.sql b/conf/evolutions/default/206.sql index 9dbebd85c1..551eacd2a2 100644 --- a/conf/evolutions/default/206.sql +++ b/conf/evolutions/default/206.sql @@ -1,5 +1,8 @@ # --- !Ups -DELETE FROM webpage_activity USING sidewalk_user WHERE webpage_activity.user_id = sidewalk_user.user_id AND (webpage_activity.user_id IS NULL OR sidewalk_user.user_id IS NULL); +DELETE FROM webpage_activity + USING webpage_activity as wa +LEFT JOIN sidewalk_user ON wa.user_id = sidewalk_user.user_id +WHERE webpage_activity.user_id IS NULL OR sidewalk_user.user_id IS NULL; ALTER TABLE webpage_activity ADD CONSTRAINT webpage_activity_user_id_fkey FOREIGN KEY (user_id) REFERENCES sidewalk_user (user_id); From 6540919595a491c845ef04505c2b16221bb96f25 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Mon, 4 Dec 2023 11:49:42 -0800 Subject: [PATCH 64/77] RouteBuilder adds alert before deleting a route --- app/views/routeBuilder.scala.html | 27 +++++++++++++++++++-------- conf/messages.de | 9 +++++++-- conf/messages.en | 9 +++++++-- conf/messages.es | 9 +++++++-- conf/messages.nl | 9 +++++++-- conf/messages.zh-TW | 9 +++++++-- public/javascripts/routeBuilder.js | 17 +++++++++++++++-- public/stylesheets/routeBuilder.css | 26 ++++++++++++++++---------- 8 files changed, 85 insertions(+), 30 deletions(-) diff --git a/app/views/routeBuilder.scala.html b/app/views/routeBuilder.scala.html index 0ac8e18969..a08e3bad5b 100644 --- a/app/views/routeBuilder.scala.html +++ b/app/views/routeBuilder.scala.html @@ -48,25 +48,36 @@
    -
    +
    +
    +
    + @Messages( + @Messages("routebuilder.not.saved") + @Messages("routebuilder.not.saved.explanation") +
    +
    + + +
    +
    +
    +
    @Messages( @Messages("routebuilder.saved")
    -
    - @Messages("routebuilder.explore.title") -
    - - -
    -
    @Messages("routebuilder.share.title")
    + @Messages("routebuilder.share.warning") +
    +
    + +
    diff --git a/conf/messages.de b/conf/messages.de index e5aa79fc0b..54389506e0 100644 --- a/conf/messages.de +++ b/conf/messages.de @@ -33,6 +33,7 @@ dist.metric.abbr = km distance.icon.alt = Symbol mit kurvigem Pfad zum Ziel ok = Ok cancel = Abbrechen +back = Zurück error = Fehler! yes.caps = Ja no.caps = Nein @@ -373,13 +374,17 @@ routebuilder.delete.street.icon.alt = Eine Müll kann mit einem X darauf routebuilder.delete.street.instruction = Klicken Sie zweimal auf eine beliebige Straße hinzugefügt, um sie von der Route zu löschen. routebuilder.save.route.instruction = Klicken Sie, um den Build zu beenden, auf "Route speichern". routebuilder.save = Route speichern +routebuilder.delete.route.icon.alt = Ein orangefarbener Kreis mit einem weißen Ausrufezeichen in der Mitte +routebuilder.not.saved = Die Route wurde nicht gerettet. +routebuilder.not.saved.explanation = Sie werden diese Route später nicht wiederherstellen können. +routebuilder.delete.route = Route löschen routebuilder.saved.icon.alt = Ein grüner Kreis mit einem weißen Checkmark in der Mitte routebuilder.saved = Route gespeichert! -routebuilder.explore.title = Erforschen Sie diese Route und kennzeichnen Sie Probleme mit Barrierefreiheit routebuilder.explore.route = Erforschen Sie diese Route routebuilder.build.another.route = Bauen Sie eine andere Route -routebuilder.share.title = Laden Sie Freunde ein, diese Route mit dem folgenden Link zu erkunden +routebuilder.share.title = Speichern Sie diesen Link für den zukünftigen Zugriff: routebuilder.copy.link = Link kopieren +routebuilder.share.warning = Ohne den Link können Sie nicht auf diese Route zugreifen. help.rating.1 = Bewertung 1: Passierbar help.rating.3 = Bewertung 3: Schwer passierbar diff --git a/conf/messages.en b/conf/messages.en index 1283aa81d2..9669c8da06 100644 --- a/conf/messages.en +++ b/conf/messages.en @@ -33,6 +33,7 @@ dist.metric.abbr = mi distance.icon.alt = Icon showing curved path to destination ok = OK cancel = Cancel +back = Back error = Error! yes.caps = Yes no.caps = No @@ -368,13 +369,17 @@ routebuilder.delete.street.icon.alt = A trash can with an X on it routebuilder.delete.street.instruction = Click on any added street twice to delete it from the route. routebuilder.save.route.instruction = To finish the build, click "Save Route" routebuilder.save = Save route +routebuilder.delete.route.icon.alt = An orange circle with a white exclamation mark in the center +routebuilder.not.saved = Route has not been saved. +routebuilder.not.saved.explanation = You will not be able to recover this route later. +routebuilder.delete.route = Delete Route routebuilder.saved.icon.alt = A green circle with a white checkmark in the center routebuilder.saved = Route saved! -routebuilder.explore.title = Start exploring this route and labeling accessibility issues routebuilder.explore.route = Explore This Route routebuilder.build.another.route = Build Another Route -routebuilder.share.title = Invite friends to explore this route with the following link +routebuilder.share.title = Save this link for future access: routebuilder.copy.link = Copy Link +routebuilder.share.warning = You will not be able to access this route without the link. help.rating.1 = Rating 1: Passable help.rating.3 = Rating 3: Neutral diff --git a/conf/messages.es b/conf/messages.es index a0c492dc0e..9b01283e53 100644 --- a/conf/messages.es +++ b/conf/messages.es @@ -33,6 +33,7 @@ dist.metric.abbr = km distance.icon.alt = Icono que muestra el camino curvo hacia el destino ok = OK cancel = Cancelar +back = Atrás error = ¡Error! yes.caps = Sí no.caps = No @@ -375,13 +376,17 @@ routebuilder.delete.street.icon.alt = Un bote de basura con una x routebuilder.delete.street.instruction = Haga clic en cualquier calle agregada dos veces para eliminarla de la ruta. routebuilder.save.route.instruction = Para finalizar la compilación, haga clic en "Guardar ruta" routebuilder.save = Guardar ruta +routebuilder.delete.route.icon.alt = Un círculo naranja con una marca de exclamación blanca en el centro +routebuilder.not.saved = La ruta no se ha guardado. +routebuilder.not.saved.explanation = No podrá recuperar esta ruta más tarde. +routebuilder.delete.route = Eliminar ruta routebuilder.saved.icon.alt = Un círculo verde con una marca de verificación blanca en el centro routebuilder.saved = Ruta guardada! -routebuilder.explore.title = Comience a explorar esta ruta y etiquetar problemas de accesibilidad routebuilder.explore.route = Explore esta ruta routebuilder.build.another.route = Construir otra ruta -routebuilder.share.title = Invite a sus amigos a explorar esta ruta con el siguiente enlace +routebuilder.share.title = Guarde este enlace para el acceso futuro: routebuilder.copy.link = Copiar link +routebuilder.share.warning = No podrá acceder a esta ruta sin el enlace. help.rating.1 = Calificación 1: Transitable help.rating.3 = Calificación 3: Neutral diff --git a/conf/messages.nl b/conf/messages.nl index 1940b9844f..5c2582ad15 100644 --- a/conf/messages.nl +++ b/conf/messages.nl @@ -33,6 +33,7 @@ dist.metric.abbr = km distance.icon.alt = Pictogram met gebogen pad naar bestemming ok = OK cancel = Annuleer +back = Rug error = Error! yes.caps = Ja no.caps = Nee @@ -375,13 +376,17 @@ routebuilder.delete.street.icon.alt = Een prullenbak met een X erop routebuilder.delete.street.instruction = Klik twee keer op een toegevoegde straat om deze uit de route te verwijderen. routebuilder.save.route.instruction = Klik op "Route opslaan" om de build te voltooien routebuilder.save = Route bewaren +routebuilder.delete.route.icon.alt = Een oranje cirkel met een witte uitroepteken in het midden +routebuilder.not.saved = Route is niet opgeslagen. +routebuilder.not.saved.explanation = U kunt deze route later niet herstellen. +routebuilder.delete.route = Verwijder route routebuilder.saved.icon.alt = Een groene cirkel met een wit vinkje in het midden routebuilder.saved = Route opgeslagen! -routebuilder.explore.title = Begin met het verkennen van deze route en het labelen van toegankelijkheidsproblemen routebuilder.explore.route = Verken deze route routebuilder.build.another.route = Bouw een andere route -routebuilder.share.title = Nodig vrienden uit om deze route te verkennen met de volgende link +routebuilder.share.title = Sla deze link op voor toekomstige toegang: routebuilder.copy.link = Kopieer link +routebuilder.share.warning = U hebt geen toegang tot deze route zonder de link. help.rating.1 = Rating 1: Begaanbaar help.rating.3 = Rating 3: Neutraal diff --git a/conf/messages.zh-TW b/conf/messages.zh-TW index 3407edfb17..abb5a817e3 100644 --- a/conf/messages.zh-TW +++ b/conf/messages.zh-TW @@ -33,6 +33,7 @@ dist.metric.abbr = 哩 distance.icon.alt = 顯示彎曲路徑到達目的地的圖示 ok = 確認 cancel = 取消 +back = Back error = 錯誤! yes.caps = 是 no.caps = 否 @@ -399,13 +400,17 @@ routebuilder.delete.street.icon.alt = A trash can with an X on it routebuilder.delete.street.instruction = Click on any added street twice to delete it from the route. routebuilder.save.route.instruction = To finish the build, click "Save Route" routebuilder.save = 儲存路線 +routebuilder.delete.route.icon.alt = An orange circle with a white exclamation mark in the center +routebuilder.not.saved = Route has not been saved. +routebuilder.not.saved.explanation = You will not be able to recover this route later. +routebuilder.delete.route = Delete Route routebuilder.saved.icon.alt = A green circle with a white checkmark in the center routebuilder.saved = 路線已儲存! -routebuilder.explore.title = Start exploring this route and labeling accessibility issues routebuilder.explore.route = Explore This Route routebuilder.build.another.route = Build Another Route -routebuilder.share.title = Invite friends to explore this route with the following link +routebuilder.share.title = Save this link for future access: routebuilder.copy.link = Copy Link +routebuilder.share.warning = You will not be able to access this route without the link. help.rating.1 = Rating 1: 能通行 help.rating.3 = Rating 3: 普通 diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 3759ac58c4..08ee75a5a4 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -17,9 +17,11 @@ function RouteBuilder ($, mapParams) { let savedRoute = null; let currentMarkers = []; + // Get the DOM elements. let introUI = document.getElementById('routebuilder-intro'); let streetDistOverlay = document.getElementById('creating-route-overlay'); - let routeSavedModal = document.getElementById('route-saved-modal-overlay'); + let deleteRouteModal = document.getElementById('delete-route-modal-backdrop'); + let routeSavedModal = document.getElementById('route-saved-modal-backdrop'); let streetDistanceEl = document.getElementById('route-length-val'); let saveButton = document.getElementById('save-button'); let exploreButton = $('#explore-button'); @@ -27,8 +29,10 @@ function RouteBuilder ($, mapParams) { let copyLinkButton = $('#copy-link-button'); // Add the click event for the clear route buttons. + document.getElementById('cancel-button').addEventListener('click', showDeleteRouteModal); + document.getElementById('delete-route-button').addEventListener('click', clearRoute); + document.getElementById('cancel-delete-route-button').addEventListener('click', hideDeleteRouteModal); document.getElementById('build-new-route-button').addEventListener('click', clearRoute); - document.getElementById('cancel-button').addEventListener('click', clearRoute); // Initialize the map. mapboxgl.accessToken = mapParams.mapbox_api_key; @@ -484,6 +488,14 @@ function RouteBuilder ($, mapParams) { return shouldReverse; } + function showDeleteRouteModal() { + deleteRouteModal.style.visibility = 'visible'; + } + + function hideDeleteRouteModal() { + deleteRouteModal.style.visibility = 'hidden'; + } + /** * Clear the current route and reset the map. */ @@ -501,6 +513,7 @@ function RouteBuilder ($, mapParams) { setRouteDistanceText(); // Reset the UI. + deleteRouteModal.style.visibility = 'hidden'; routeSavedModal.style.visibility = 'hidden'; streetDistOverlay.style.visibility = 'hidden'; introUI.style.visibility = 'visible'; diff --git a/public/stylesheets/routeBuilder.css b/public/stylesheets/routeBuilder.css index 3f1b6e9f08..5f7031882f 100644 --- a/public/stylesheets/routeBuilder.css +++ b/public/stylesheets/routeBuilder.css @@ -105,8 +105,8 @@ border: 1.5px solid #525252; } -#route-saved-modal-overlay { - visibility: hidden; /* Show once the route has been saved. */ +.routebuilder-overlay-backdrop { + visibility: hidden; /* Show using JS at the appropriate times. */ height: 935px; /* navbar height + map height and margin + filler */ width: 100%; position: fixed; @@ -116,31 +116,32 @@ z-index: 2; } +#delete-route-modal { + align-items: center; + gap: 24px; +} + #route-saved-modal { gap: 24px; } -#route-saved-title-section { +#route-saved-title-section, #delete-route-title-section { padding-top: 8px; align-items: center; gap: 12px; } -#route-saved-explore-section { - align-items: center; - gap: 16px; -} - #route-saved-explore-title { align-self: stretch; } -#route-saved-buttons { +#route-saved-buttons, #delete-route-buttons { gap: 12px; + justify-content: center; } #route-saved-share-section { - gap: 16px; + gap: 8px; } #share-route-subsection { @@ -160,6 +161,11 @@ font-size: 12px; } +#route-saved-share-warnings { + color: #F68D3E; + font-weight: 600; +} + .marker-start, .marker-end { width: 27px; height: 27px; From ccf8cfd34927ef56be895c9e229c15ca7f5877c4 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Mon, 4 Dec 2023 13:13:01 -0800 Subject: [PATCH 65/77] updates RouteBuilder neighborhood overlays --- .../icons/routebuilder/delete-route.svg | 6 +++ public/javascripts/routeBuilder.js | 48 ++++++++++++++----- 2 files changed, 41 insertions(+), 13 deletions(-) create mode 100644 public/images/icons/routebuilder/delete-route.svg diff --git a/public/images/icons/routebuilder/delete-route.svg b/public/images/icons/routebuilder/delete-route.svg new file mode 100644 index 0000000000..b6d759c068 --- /dev/null +++ b/public/images/icons/routebuilder/delete-route.svg @@ -0,0 +1,6 @@ + + + + + + diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 08ee75a5a4..d4a9aa7604 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -63,6 +63,19 @@ function RouteBuilder ($, mapParams) { } }); + // Once all the layers have loaded, put them in the correct order. + map.on('sourcedataloading', moveLayers); + function moveLayers() { + if (map.getLayer('streets') && map.getLayer('streets-chosen') && map.getLayer('chosen-hover-flip') + && map.getLayer('chosen-hover-remove') && map.getLayer('neighborhoods')) { + map.moveLayer('streets', 'streets-chosen'); + map.moveLayer('chosen-hover-flip', 'streets-chosen'); + map.moveLayer('chosen-hover-remove', 'streets-chosen'); + map.moveLayer('streets', 'neighborhoods'); + map.off('sourcedataloading', moveLayers); // Remove the listener so we only do this once. + } + } + /* * Function definitions. */ @@ -89,21 +102,26 @@ function RouteBuilder ($, mapParams) { type: 'fill', source: 'neighborhoods', paint: { - 'fill-opacity': 0.1, - 'fill-color': ['case', - ['boolean', ['feature-state', 'current'], false], '#4a6', - '#222' - ] + 'fill-color': '#000000', + 'fill-opacity': 0.0 + } + }); + + // Create layer for an overlay outside of neighborhood boundaries using turf.mask. + let outsideNeighborhoods = turf.mask(neighborhoodData); + map.addSource('outside-neighborhoods', { + type: 'geojson', + data: outsideNeighborhoods + }); + map.addLayer({ + id: 'outside-neighborhoods', + type: 'fill', + source: 'outside-neighborhoods', + paint: { + 'fill-opacity': 0.3, + 'fill-color': '#000000' } }); - // Make sure that the polygons are visually below the streets. - // TODO we shouldn't require that all those layers are available. Though is 'streets' is, the others should be. - if (map.getLayer('streets') && map.getLayer('streets-chosen') && map.getLayer('streets-chosen-hovered')) { - map.moveLayer('neighborhoods', 'streets'); - map.moveLayer('streets', 'streets-chosen'); - map.moveLayer('chosen-hover-flip', 'streets-chosen'); - map.moveLayer('chosen-hover-remove', 'streets-chosen'); - } } function renderNeighborhoods(neighborhoodDataIn) { neighborhoodData = neighborhoodDataIn; @@ -323,6 +341,8 @@ function RouteBuilder ($, mapParams) { // If there are no longer any streets in the route, any street can now be selected. Update styles. if (chosenStreets.features.length === 0) { map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: false }); + map.setPaintProperty('neighborhoods', 'fill-opacity', 0.0); + map.setPaintProperty('outside-neighborhoods', 'fill-opacity', 0.3); currRegionId = null; introUI.style.visibility = 'visible'; @@ -353,6 +373,8 @@ function RouteBuilder ($, mapParams) { // Change style to show you can't choose streets in other regions. currRegionId = street[0].properties.region_id; map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: true }); + map.setPaintProperty('neighborhoods', 'fill-opacity', ['case', ['boolean', ['feature-state', 'current'], false], 0.0, 0.3 ]); + map.setPaintProperty('outside-neighborhoods', 'fill-opacity', 0.5); } } updateMarkers(); From 11fc182bed5eaf80501307363bbc7bc770453a45 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Mon, 4 Dec 2023 16:13:30 -0800 Subject: [PATCH 66/77] RouteBuilder code cleanup, adding comments --- public/javascripts/routeBuilder.js | 190 ++++++++++++++++------------- 1 file changed, 107 insertions(+), 83 deletions(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index d4a9aa7604..0a98892ba3 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -6,14 +6,15 @@ function RouteBuilder ($, mapParams) { streetsLoaded: false }; - // Declaring variables used throughout the code. + // Constants used throughout the code. const endpointColors = ['#80c32a', '#ffc300', '#ff9700', '#ff6a00']; const units = i18next.t('common:unit-distance'); + // Variables used throughout the code. let neighborhoodData = null; let currRegionId = null; let streetData = null; - let chosenStreets = null; + let streetsInRoute = null; let savedRoute = null; let currentMarkers = []; @@ -49,7 +50,6 @@ function RouteBuilder ($, mapParams) { ], doubleClickZoom: false }); - // const mapboxLang = new MapboxLanguage({ defaultLanguage: i18next.t('common:mapbox-language-code') }); map.addControl(new MapboxLanguage({ defaultLanguage: i18next.t('common:mapbox-language-code') })); map.addControl(new mapboxgl.NavigationControl({ visualizePitch: true }), 'top-left'); map.on('load', () => { @@ -91,6 +91,9 @@ function RouteBuilder ($, mapParams) { }, 1000); } + /** + * Renders the neighborhoods and an overlay outside the neighborhood boundaries on the map. + */ function renderNeighborhoodsHelper() { map.addSource('neighborhoods', { type: 'geojson', @@ -123,6 +126,7 @@ function RouteBuilder ($, mapParams) { } }); } + function renderNeighborhoods(neighborhoodDataIn) { neighborhoodData = neighborhoodDataIn; // If the map already loaded, it's safe to render neighborhoods now. O/w they will load after the map does. @@ -134,6 +138,17 @@ function RouteBuilder ($, mapParams) { /** * Renders the streets on the map. Adds the hover/click events for the streets as well. + * + * We have two separate data sources for the streets. The 'streets' source contains all the streets in the city. The + * 'streets-chosen' source contains the streets that have been added to the route. This just makes it a bit easier + * to keep track of the streets in the route and render streets differently when we reverse their direction. + * + * Because Mapbox doesn't allow us to change the line-pattern (or switch between line-pattern and line-color) based + * on feature state, we have four separate layers for the streets: + * 1. streets: streets that aren't in the route (light blue colored). + * 2. streets-chosen: streets that are in the route (white/blue arrow pattern). + * 3. chosen-hover-flip: streets in the route on hover (translucent dark/light blue arrow pattern). + * 4. chosen-hover-remove: streets in the route after being reversed, on hover (red/purple arrow pattern). */ function renderStreetsHelper() { map.addSource('streets', { @@ -141,14 +156,35 @@ function RouteBuilder ($, mapParams) { data: streetData, promoteId: 'street_edge_id' }); - // Add another source for the streets that have been added to the route, and another for added streets on hover. - chosenStreets = { type: 'FeatureCollection', features: [] }; + streetsInRoute = { type: 'FeatureCollection', features: [] }; map.addSource('streets-chosen', { type: 'geojson', - data: chosenStreets, + data: streetsInRoute, promoteId: 'street_edge_id' }); + map.addLayer({ + id: 'streets', + type: 'line', + source: 'streets', + paint: { + 'line-color': ['case', + ['boolean', ['feature-state', 'hover'], false], '#236ee0', + '#ddefff' + ], + // Line width scales based on zoom level. + 'line-width': [ + 'interpolate', ['linear'], ['zoom'], + 12, 2, + 15, 7 + ], + // Show only when street hasn't been chosen. + 'line-opacity': ['case', + ['==', ['string', ['feature-state', 'chosen'], 'not chosen'], 'not chosen'], 0.75, + 0.0 + ] + } + }); map.addLayer({ 'id': 'streets-chosen', 'type': 'line', @@ -209,28 +245,6 @@ function RouteBuilder ($, mapParams) { ] } }); - map.addLayer({ - id: 'streets', - type: 'line', - source: 'streets', - paint: { - 'line-color': ['case', - ['boolean', ['feature-state', 'hover'], false], '#236ee0', - '#ddefff' - ], - // Line width scales based on zoom level. - 'line-width': [ - 'interpolate', ['linear'], ['zoom'], - 12, 2, - 15, 7 - ], - // Show only when street hasn't been chosen. - 'line-opacity': ['case', - ['==', ['string', ['feature-state', 'chosen'], 'not chosen'], 'not chosen'], 0.75, - 0.0 - ] - } - }); // Create tooltips for when the user hovers over a street. const neighborhoodPopup = new mapboxgl.Popup({ closeButton: false, closeOnClick: false}) @@ -245,24 +259,26 @@ function RouteBuilder ($, mapParams) { hoverDeletePopup._content.className = 'tooltip-no-outline'; // Remove default styling. // Mark when a street is being hovered over. - let streetId = null; - let clickedStreetId = null; + let hoveredStreet = null; + let clickedStreet = null; map.on('mousemove', (event) => { const streetQuery = map.queryRenderedFeatures(event.point, { layers: ['streets', 'streets-chosen'] }); const street = streetQuery.filter(s => s.layer.id === 'streets')[0]; // Don't show hover effects if the street was just clicked on. - if (!street || street.properties.street_edge_id === clickedStreetId) return; + if (!street || street.properties.street_edge_id === clickedStreet) return; let chosenState = street.state ? street.state.chosen : 'not chosen'; // If we moved directly from hovering over one street to another, set the previous as hover: false. - if (streetId) map.setFeatureState({ source: 'streets', id: streetId }, { hover: false }); - if (streetId) map.setFeatureState({ source: 'streets-chosen', id: streetId }, { hover: false }); - streetId = street.properties.street_edge_id; + if (hoveredStreet) { + map.setFeatureState({ source: 'streets', id: hoveredStreet }, { hover: false }); + map.setFeatureState({ source: 'streets-chosen', id: hoveredStreet }, { hover: false }); + } + hoveredStreet = street.properties.street_edge_id; // Set the hover state. - map.setFeatureState({ source: 'streets', id: streetId }, { hover: true }); - if (chosenState !== 'not chosen' && clickedStreetId !== street.properties.street_edge_id) { - map.setFeatureState({ source: 'streets-chosen', id: streetId }, { hover: true }); + map.setFeatureState({ source: 'streets', id: hoveredStreet }, { hover: true }); + if (chosenState !== 'not chosen' && clickedStreet !== street.properties.street_edge_id) { + map.setFeatureState({ source: 'streets-chosen', id: hoveredStreet }, { hover: true }); } // Update the reverse/delete tooltips above the cursor. @@ -278,7 +294,7 @@ function RouteBuilder ($, mapParams) { hoverDeletePopup.addTo(map); hoverDeletePopup._content.parentNode.querySelector('[class*="tip"]').remove(); // Remove the arrow. } - } else if (chosenStreets.features.length === 0) { // Not yet chosen and route is empty. + } else if (streetsInRoute.features.length === 0) { // Not yet chosen and route is empty. hoverChoosePopup.setLngLat(event.lngLat); if (!hoverChoosePopup.isOpen()) { hoverChoosePopup.addTo(map); @@ -289,19 +305,18 @@ function RouteBuilder ($, mapParams) { // Show a tooltip informing user that they can't have multiple regions in the same route. if (currRegionId && currRegionId !== street.properties.region_id) { - neighborhoodPopup.setLngLat(event.lngLat) - .addTo(map); + neighborhoodPopup.setLngLat(event.lngLat).addTo(map); } }); // When not hovering over any streets, set prev street to hover: false and reset cursor. map.on('mouseleave', 'streets', () => { - if (streetId) { - map.setFeatureState({ source: 'streets', id: streetId }, { hover: false }); - map.setFeatureState({ source: 'streets-chosen', id: streetId }, { hover: false }); + if (hoveredStreet) { + map.setFeatureState({ source: 'streets', id: hoveredStreet }, { hover: false }); + map.setFeatureState({ source: 'streets-chosen', id: hoveredStreet }, { hover: false }); } - streetId = null; - clickedStreetId = null; // This helps avoid showing hover effects directly after clicking a street. + hoveredStreet = null; + clickedStreet = null; // This helps avoid showing hover effects directly after clicking a street. map.getCanvas().style.cursor = ''; neighborhoodPopup.remove(); hoverChoosePopup.remove(); @@ -316,30 +331,30 @@ function RouteBuilder ($, mapParams) { return; } - streetId = street[0].properties.street_edge_id; - clickedStreetId = streetId; + hoveredStreet = street[0].properties.street_edge_id; + clickedStreet = hoveredStreet; let prevState = street[0].state; - if (prevState.chosen === 'chosen') { - map.setFeatureState({ source: 'streets', id: streetId }, { chosen: 'chosen reversed' }); - map.setFeatureState({ source: 'streets-chosen', id: streetId }, { chosen: 'chosen reversed' }); - // If the street was in the route, reverse it on this click. - let streetToReverse = chosenStreets.features.find(s => s.properties.street_edge_id === streetId) + if (prevState.chosen === 'chosen') { // If the street was in the route, reverse it. + map.setFeatureState({ source: 'streets', id: clickedStreet }, { chosen: 'chosen reversed' }); + map.setFeatureState({ source: 'streets-chosen', id: clickedStreet }, { chosen: 'chosen reversed' }); + + let streetToReverse = streetsInRoute.features.find(s => s.properties.street_edge_id === clickedStreet); streetToReverse.geometry.coordinates.reverse(); streetToReverse.properties.reverse = !streetToReverse.properties.reverse; - map.getSource('streets-chosen').setData(chosenStreets); + map.getSource('streets-chosen').setData(streetsInRoute); + hoverReversePopup.remove(); // Hide the reverse tooltip. - } else if (prevState.chosen === 'chosen reversed') { - map.setFeatureState({ source: 'streets', id: streetId }, { chosen: 'not chosen' }); + } else if (prevState.chosen === 'chosen reversed') { // If street was in the route & reversed, remove it. + map.setFeatureState({ source: 'streets', id: clickedStreet }, { chosen: 'not chosen' }); - // If the street was in the route, remove it from the route. - chosenStreets.features = chosenStreets.features.filter(s => s.properties.street_edge_id !== streetId); - map.getSource('streets-chosen').setData(chosenStreets); + streetsInRoute.features = streetsInRoute.features.filter(s => s.properties.street_edge_id !== clickedStreet); + map.getSource('streets-chosen').setData(streetsInRoute); hoverDeletePopup.remove(); // Hide the delete tooltip. // If there are no longer any streets in the route, any street can now be selected. Update styles. - if (chosenStreets.features.length === 0) { + if (streetsInRoute.features.length === 0) { map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: false }); map.setPaintProperty('neighborhoods', 'fill-opacity', 0.0); map.setPaintProperty('outside-neighborhoods', 'fill-opacity', 0.3); @@ -348,24 +363,24 @@ function RouteBuilder ($, mapParams) { introUI.style.visibility = 'visible'; streetDistOverlay.style.visibility = 'hidden'; } - } else { - map.setFeatureState({ source: 'streets', id: streetId }, { chosen: 'chosen' }); + } else { // If the street was not in the route, add it to the route. + map.setFeatureState({ source: 'streets', id: hoveredStreet }, { chosen: 'chosen' }); + // Check if we should reverse the street direction to minimize number of contiguous sections. if (shouldReverseStreet(street[0])) { - console.log('reverse!'); street[0].geometry.coordinates.reverse(); - street[0].properties.reverse = true; + street[0].properties.reverse = !street[0].properties.reverse; } // Add the new street to the route and set it's state. - chosenStreets.features.push(street[0]); - map.getSource('streets-chosen').setData(chosenStreets); - map.setFeatureState({ source: 'streets-chosen', id: streetId }, { chosen: 'chosen' }); + streetsInRoute.features.push(street[0]); + map.getSource('streets-chosen').setData(streetsInRoute); + map.setFeatureState({ source: 'streets-chosen', id: hoveredStreet }, { chosen: 'chosen' }); hoverChoosePopup.remove(); // Hide the start building a route tooltip. // If this was first street added, make additional UI changes. - if (chosenStreets.features.length === 1) { + if (streetsInRoute.features.length === 1) { // Remove the intro instructions and show the route length UI on the right. introUI.style.visibility = 'hidden'; streetDistOverlay.style.visibility = 'visible'; @@ -377,6 +392,10 @@ function RouteBuilder ($, mapParams) { map.setPaintProperty('outside-neighborhoods', 'fill-opacity', 0.5); } } + + // Set hover to false so that we don't show hover effect immediately after being clicked. + map.setFeatureState({ source: 'streets', id: hoveredStreet }, { hover: false }); + map.setFeatureState({ source: 'streets-chosen', id: hoveredStreet }, { hover: false }); updateMarkers(); setRouteDistanceText(); }); @@ -394,7 +413,7 @@ function RouteBuilder ($, mapParams) { * Updates the route distance text shown in the upper-right corner of the map. */ function setRouteDistanceText() { - let routeDist = chosenStreets.features.reduce((sum, street) => sum + turf.length(street, { units: units }), 0); + let routeDist = streetsInRoute.features.reduce((sum, street) => sum + turf.length(street, { units: units }), 0); streetDistanceEl.innerText = i18next.t('route-length', { dist: routeDist.toFixed(2) }); } @@ -445,28 +464,33 @@ function RouteBuilder ($, mapParams) { currentMarkers.push(endMarker); } - // Find the contiguous sections of the route as a list of lists of features. We do this by looping through the - // streets in the order that they were added to the route, and checking the remaining streets in the route (also in - // the order they were chosen) to see if any of their start points are connected to the end point of the current - // street. When there are no connected streets, that contiguous section is done and we start a new one. // TODO do something to preserve ordering, I'm not sure if mapbox guarantees that ordering is preserved. // Could either add a property with the ordering, or keep track in a separate list. + + /** + * Computes a set of contiguous sections of the route. + * + * We do this by looping through the streets in the order that they were added to the route, checking the remaining + * streets in the route (also in the order they were chosen) to see if any of their start points are connected to + * the end point of the current street. When there are no connected streets, that contiguous section is done and + * we start a new one. + */ function computeContiguousRoutes() { let contiguousSections = []; let currContiguousSection = []; - let streetsInRoute = Array.from(chosenStreets.features); // shallow copy - while (streetsInRoute.length > 0) { + let streetsInRouteCopy = Array.from(streetsInRoute.features); // shallow copy + while (streetsInRouteCopy.length > 0) { if (currContiguousSection.length === 0) { - currContiguousSection.push(streetsInRoute.shift()); + currContiguousSection.push(streetsInRouteCopy.shift()); } else { // Search for least recently chosen street with endpoint within 10 m of the current street. let currStreet = currContiguousSection.slice(-1)[0]; let p1 = turf.point(currStreet.geometry.coordinates.slice(-1)[0]); let connectedStreetFound = false; - for (let i = 0; i < streetsInRoute.length; i++) { - let p2 = turf.point(streetsInRoute[i].geometry.coordinates[0]); + for (let i = 0; i < streetsInRouteCopy.length; i++) { + let p2 = turf.point(streetsInRouteCopy[i].geometry.coordinates[0]); if (turf.distance(p1, p2, { units: 'kilometers' }) < 0.01) { - currContiguousSection.push(streetsInRoute.splice(i, 1)[0]); + currContiguousSection.push(streetsInRouteCopy.splice(i, 1)[0]); connectedStreetFound = true; break; } @@ -523,11 +547,11 @@ function RouteBuilder ($, mapParams) { */ function clearRoute() { // Remove all the streets from the route. - chosenStreets.features.forEach(s => { + streetsInRoute.features.forEach(s => { map.setFeatureState({ source: 'streets', id: s.properties.street_edge_id }, { chosen: 'not chosen' }); }); - chosenStreets.features = []; - map.getSource('streets-chosen').setData(chosenStreets); + streetsInRoute.features = []; + map.getSource('streets-chosen').setData(streetsInRoute); // Reset the map. map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: false }); @@ -535,7 +559,7 @@ function RouteBuilder ($, mapParams) { setRouteDistanceText(); // Reset the UI. - deleteRouteModal.style.visibility = 'hidden'; + hideDeleteRouteModal(); routeSavedModal.style.visibility = 'hidden'; streetDistOverlay.style.visibility = 'hidden'; introUI.style.visibility = 'visible'; @@ -551,7 +575,7 @@ function RouteBuilder ($, mapParams) { street_id: s.properties.street_edge_id, reverse: s.properties.reverse === true })); - console.log(streetProps); + // Don't save if the route is empty or hasn't changed. if (JSON.stringify(streetProps) === JSON.stringify(savedRoute)) { logActivity(`RouteBuilder_Click=SaveDuplicate`); From 43114d2ee9ab8491dfb94ca28181f202d42c59fc Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Wed, 6 Dec 2023 11:44:10 -0800 Subject: [PATCH 67/77] fixes query to remove webpage_activity entries w/ no user --- conf/evolutions/default/206.sql | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/conf/evolutions/default/206.sql b/conf/evolutions/default/206.sql index 551eacd2a2..eff64eb29a 100644 --- a/conf/evolutions/default/206.sql +++ b/conf/evolutions/default/206.sql @@ -1,8 +1,9 @@ # --- !Ups DELETE FROM webpage_activity - USING webpage_activity as wa +USING webpage_activity as wa LEFT JOIN sidewalk_user ON wa.user_id = sidewalk_user.user_id -WHERE webpage_activity.user_id IS NULL OR sidewalk_user.user_id IS NULL; +WHERE webpage_activity.webpage_activity_id = wa.webpage_activity_id + AND sidewalk_user.user_id IS NULL; ALTER TABLE webpage_activity ADD CONSTRAINT webpage_activity_user_id_fkey FOREIGN KEY (user_id) REFERENCES sidewalk_user (user_id); From 14bbbd027878e07457245c3107bc4a8dfab978d8 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Wed, 6 Dec 2023 17:02:35 -0800 Subject: [PATCH 68/77] increases Java memory size from 1 gb to 1.5 gb temporarily --- package.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/package.json b/package.json index a969352280..87e7070180 100644 --- a/package.json +++ b/package.json @@ -13,8 +13,8 @@ "grunt-concat": "grunt concat && grunt concat_css", "build": "npm install && grunt", "debug": "npm run grunt-concat && grunt watch & sbt -jvm-debug 9998 run", - "start": "npm run grunt-concat && grunt watch & sbt -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' compile \"~ run\" shell", - "start-no-docker": "npm run grunt-concat && grunt watch & sbt -Dhttp.port=$SIDEWALK_HTTP_PORT -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' compile \"~ run\" shell", + "start": "npm run grunt-concat && grunt watch & sbt -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' -mem 1536 compile \"~ run\" shell", + "start-no-docker": "npm run grunt-concat && grunt watch & sbt -Dhttp.port=$SIDEWALK_HTTP_PORT -Dsbt.ivy.home='.ivy2' -Dsbt.global.base='.sbt' -Dsbt.repository.config='.sbt/repositories' -mem 1536 compile \"~ run\" shell", "test": "grunt && grunt test" } } From c2586b9b085941a75883d7a7abf0cd1a73848f70 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 7 Dec 2023 10:47:09 -0800 Subject: [PATCH 69/77] adds Chinese translations to RouteBuilder --- conf/messages.zh-TW | 60 ++++++++++++++++++++++----------------------- 1 file changed, 30 insertions(+), 30 deletions(-) diff --git a/conf/messages.zh-TW b/conf/messages.zh-TW index abb5a817e3..326610ebe3 100644 --- a/conf/messages.zh-TW +++ b/conf/messages.zh-TW @@ -386,38 +386,38 @@ gallery.cards = 所有標記依據所選定的過濾器而隨機排序 gallery.clear.filters = 清除過濾器 routebuilder.name = 路線設立工具 -routebuilder.welcome = Welcome to RouteBuilder -routebuilder.intro.content = Improving accessibility in the neighborhood of your choosing by building, exploring and sharing your own route! -routebuilder.intro.instruction = Click on a street to start building your route. -routebuilder.creating.route = Creating Route +routebuilder.welcome = 歡迎使用路線設立工具 +routebuilder.intro.content = 在您所想要改善可及性(無障礙性)的鄰里內,您可以設立自己的路線,以便探索它並將它分享給他人! +routebuilder.intro.instruction = 請點選一條街道來開始設立您的路線。 +routebuilder.creating.route = 路線創立中 routebuilder.route.length = 路線長度 -routebuilder.editing.route = Editing Route -routebuilder.add.street.icon.alt = A map pin icon with a plus in the center -routebuilder.add.street.instruction = Click on streets on the map to add them to your route. -routebuilder.rotate.street.icon.alt = Two arrows forming a circle to indicate rotation -routebuilder.rotate.street.instruction = Click on any added street once to rotate the direction. -routebuilder.delete.street.icon.alt = A trash can with an X on it -routebuilder.delete.street.instruction = Click on any added street twice to delete it from the route. -routebuilder.save.route.instruction = To finish the build, click "Save Route" +routebuilder.editing.route = 編輯路線中 +routebuilder.add.street.icon.alt = 有「+」符號在中心的圖釘圖示 +routebuilder.add.street.instruction = 請點選地圖上的街道來將它加入您的路線裡。 +routebuilder.rotate.street.icon.alt = 兩個箭頭形成一個圓圈時,這表示旋轉。 +routebuilder.rotate.street.instruction = 請將任何加入的街道點擊一次來旋轉方向。 +routebuilder.delete.street.icon.alt = 有「X」符號的垃圾桶。 +routebuilder.delete.street.instruction = 請將任何加入的街道點擊兩次來將它從路線中刪除。 +routebuilder.save.route.instruction = 要完成建立路線,請點擊「儲存路線」。 routebuilder.save = 儲存路線 -routebuilder.delete.route.icon.alt = An orange circle with a white exclamation mark in the center -routebuilder.not.saved = Route has not been saved. -routebuilder.not.saved.explanation = You will not be able to recover this route later. -routebuilder.delete.route = Delete Route -routebuilder.saved.icon.alt = A green circle with a white checkmark in the center +routebuilder.delete.route.icon.alt = 一個有白色驚嘆號在中心的橘色圓圈 +routebuilder.not.saved = 路線未儲存。 +routebuilder.not.saved.explanation = 此後您將無法還原此路線。 +routebuilder.delete.route = 刪除路線 +routebuilder.saved.icon.alt = 一個有白色勾號在中心的綠色圓圈 routebuilder.saved = 路線已儲存! -routebuilder.explore.route = Explore This Route -routebuilder.build.another.route = Build Another Route -routebuilder.share.title = Save this link for future access: -routebuilder.copy.link = Copy Link -routebuilder.share.warning = You will not be able to access this route without the link. - -help.rating.1 = Rating 1: 能通行 -help.rating.3 = Rating 3: 普通 +routebuilder.explore.route = 探索此路線 +routebuilder.build.another.route = 設立另一條路線 +routebuilder.share.title = 儲存此連結供未來使用: +routebuilder.copy.link = 複製連結 +routebuilder.share.warning = 當無此連結時,您將無法取得此路線。 + +help.rating.1 = Rating 1: 順暢通行 +help.rating.3 = Rating 3: 還好 help.rating.5 = Rating 5: 無法通行 -footer.logo.nsf.alt = 美國國家科學基金會徽標 -footer.logo.google.alt = Google 徽標 -footer.logo.sloan.alt = 阿爾弗雷德·P·斯隆基金會徽標 -footer.logo.pactrans.alt = 太平洋西北運輸聯盟 (PacTrans) 徽標 -footer.logo.create.alt = 無障礙技術和體驗研究與教育中心 (CREATE) 徽標 +footer.logo.nsf.alt = 美國國家科學基金會標誌 +footer.logo.google.alt = Google 標誌 +footer.logo.sloan.alt = 阿爾弗雷德·P·斯隆基金會標誌 +footer.logo.pactrans.alt = 太平洋西北地區運輸聯盟 (PacTrans) 標誌 +footer.logo.create.alt = 無障礙技術和體驗研究與教育中心 (CREATE) 標誌 From 7a704ba3d8f1145059e1a4ca0a01f1a72a9c2964 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 7 Dec 2023 10:57:57 -0800 Subject: [PATCH 70/77] rewords rotate to reverse in RouteBuilder --- app/views/routeBuilder.scala.html | 6 +++--- conf/messages.de | 4 ++-- conf/messages.en | 4 ++-- conf/messages.es | 4 ++-- conf/messages.nl | 4 ++-- conf/messages.zh-TW | 4 ++-- .../routebuilder/{rotate-street.svg => reverse-street.svg} | 0 7 files changed, 13 insertions(+), 13 deletions(-) rename public/images/icons/routebuilder/{rotate-street.svg => reverse-street.svg} (100%) diff --git a/app/views/routeBuilder.scala.html b/app/views/routeBuilder.scala.html index a08e3bad5b..cf0229a293 100644 --- a/app/views/routeBuilder.scala.html +++ b/app/views/routeBuilder.scala.html @@ -33,9 +33,9 @@ @Messages( @Messages("routebuilder.add.street.instruction")
    -
    - @Messages( - @Messages("routebuilder.rotate.street.instruction") +
    + @Messages( + @Messages("routebuilder.reverse.street.instruction")
    @Messages( diff --git a/conf/messages.de b/conf/messages.de index 54389506e0..091da5721b 100644 --- a/conf/messages.de +++ b/conf/messages.de @@ -368,8 +368,8 @@ routebuilder.route.length = Routenlänge routebuilder.editing.route = Bearbeitungsroute routebuilder.add.street.icon.alt = Ein Karten -Pin -Symbol mit einem Plus in der Mitte routebuilder.add.street.instruction = Klicken Sie auf Straßen auf der Karte, um sie zu Ihrer Route hinzuzufügen. -routebuilder.rotate.street.icon.alt = Zwei Pfeile bilden einen Kreis, um die Rotation anzuzeigen -routebuilder.rotate.street.instruction = Klicken Sie einmal auf eine beliebige Straße hinzugefügt, um die Richtung zu drehen. +routebuilder.reverse.street.icon.alt = Zwei Pfeile bilden einen Kreis, um die Umkehrung anzuzeigen +routebuilder.reverse.street.instruction = Klicken Sie einmal auf eine beliebige Straße hinzugefügt, um die Richtung zu drehen. routebuilder.delete.street.icon.alt = Eine Müll kann mit einem X darauf routebuilder.delete.street.instruction = Klicken Sie zweimal auf eine beliebige Straße hinzugefügt, um sie von der Route zu löschen. routebuilder.save.route.instruction = Klicken Sie, um den Build zu beenden, auf "Route speichern". diff --git a/conf/messages.en b/conf/messages.en index 9669c8da06..2becf7736c 100644 --- a/conf/messages.en +++ b/conf/messages.en @@ -363,8 +363,8 @@ routebuilder.route.length = Route Length routebuilder.editing.route = Editing Route routebuilder.add.street.icon.alt = A map pin icon with a plus in the center routebuilder.add.street.instruction = Click on streets on the map to add them to your route. -routebuilder.rotate.street.icon.alt = Two arrows forming a circle to indicate rotation -routebuilder.rotate.street.instruction = Click on any added street once to rotate the direction. +routebuilder.reverse.street.icon.alt = Two arrows forming a circle to indicate reversal +routebuilder.reverse.street.instruction = Click on any added street once to reverse the direction. routebuilder.delete.street.icon.alt = A trash can with an X on it routebuilder.delete.street.instruction = Click on any added street twice to delete it from the route. routebuilder.save.route.instruction = To finish the build, click "Save Route" diff --git a/conf/messages.es b/conf/messages.es index 9b01283e53..dc664444c6 100644 --- a/conf/messages.es +++ b/conf/messages.es @@ -370,8 +370,8 @@ routebuilder.route.length = Longitud de la ruta routebuilder.editing.route = Ruta de edición routebuilder.add.street.icon.alt = Un icono de pin de mapa con una ventaja en el centro routebuilder.add.street.instruction = Haga clic en las calles del mapa para agregarlas a su ruta. -routebuilder.rotate.street.icon.alt = Dos flechas que forman un círculo para indicar la rotación -routebuilder.rotate.street.instruction = Haga clic en cualquier calle agregada una vez para rotar la dirección. +routebuilder.reverse.street.icon.alt = Dos flechas que forman un círculo para indicar la inversión +routebuilder.reverse.street.instruction = Haga clic en cualquier calle agregada una vez para rotar la dirección. routebuilder.delete.street.icon.alt = Un bote de basura con una x routebuilder.delete.street.instruction = Haga clic en cualquier calle agregada dos veces para eliminarla de la ruta. routebuilder.save.route.instruction = Para finalizar la compilación, haga clic en "Guardar ruta" diff --git a/conf/messages.nl b/conf/messages.nl index 5c2582ad15..3e4a25a9e1 100644 --- a/conf/messages.nl +++ b/conf/messages.nl @@ -370,8 +370,8 @@ routebuilder.route.length = Routelengte routebuilder.editing.route = Bewerkingsroute routebuilder.add.street.icon.alt = Een map pin -pictogram met een pluspunt in het midden routebuilder.add.street.instruction = Klik op de straten op de kaart om ze aan uw route toe te voegen. -routebuilder.rotate.street.icon.alt = Twee pijlen vormen een cirkel om rotatie aan te geven -routebuilder.rotate.street.instruction = Klik eenmaal op een toegevoegde straat om de richting te roteren. +routebuilder.reverse.street.icon.alt = Twee pijlen vormen een cirkel om omkering aan te geven +routebuilder.reverse.street.instruction = Klik eenmaal op een toegevoegde straat om de richting te roteren. routebuilder.delete.street.icon.alt = Een prullenbak met een X erop routebuilder.delete.street.instruction = Klik twee keer op een toegevoegde straat om deze uit de route te verwijderen. routebuilder.save.route.instruction = Klik op "Route opslaan" om de build te voltooien diff --git a/conf/messages.zh-TW b/conf/messages.zh-TW index 326610ebe3..03b02e8dd7 100644 --- a/conf/messages.zh-TW +++ b/conf/messages.zh-TW @@ -394,8 +394,8 @@ routebuilder.route.length = 路線長度 routebuilder.editing.route = 編輯路線中 routebuilder.add.street.icon.alt = 有「+」符號在中心的圖釘圖示 routebuilder.add.street.instruction = 請點選地圖上的街道來將它加入您的路線裡。 -routebuilder.rotate.street.icon.alt = 兩個箭頭形成一個圓圈時,這表示旋轉。 -routebuilder.rotate.street.instruction = 請將任何加入的街道點擊一次來旋轉方向。 +routebuilder.reverse.street.icon.alt = 兩個箭頭形成一個圓圈時,這表示旋轉。 +routebuilder.reverse.street.instruction = 請將任何加入的街道點擊一次來旋轉方向。 routebuilder.delete.street.icon.alt = 有「X」符號的垃圾桶。 routebuilder.delete.street.instruction = 請將任何加入的街道點擊兩次來將它從路線中刪除。 routebuilder.save.route.instruction = 要完成建立路線,請點擊「儲存路線」。 diff --git a/public/images/icons/routebuilder/rotate-street.svg b/public/images/icons/routebuilder/reverse-street.svg similarity index 100% rename from public/images/icons/routebuilder/rotate-street.svg rename to public/images/icons/routebuilder/reverse-street.svg From 3458b30456de6bae72df9c0e887a8205fd87adf0 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 7 Dec 2023 11:00:10 -0800 Subject: [PATCH 71/77] renames RouteBuilder icons for consistency --- .../{Delete_Hover.png => delete-hover.png} | Bin .../{Switch_Hover.png => reverse-hover.png} | Bin public/javascripts/routeBuilder.js | 4 ++-- 3 files changed, 2 insertions(+), 2 deletions(-) rename public/images/icons/routebuilder/{Delete_Hover.png => delete-hover.png} (100%) rename public/images/icons/routebuilder/{Switch_Hover.png => reverse-hover.png} (100%) diff --git a/public/images/icons/routebuilder/Delete_Hover.png b/public/images/icons/routebuilder/delete-hover.png similarity index 100% rename from public/images/icons/routebuilder/Delete_Hover.png rename to public/images/icons/routebuilder/delete-hover.png diff --git a/public/images/icons/routebuilder/Switch_Hover.png b/public/images/icons/routebuilder/reverse-hover.png similarity index 100% rename from public/images/icons/routebuilder/Switch_Hover.png rename to public/images/icons/routebuilder/reverse-hover.png diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 0a98892ba3..c46cfdd422 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -252,10 +252,10 @@ function RouteBuilder ($, mapParams) { const hoverChoosePopup = new mapboxgl.Popup({ closeButton: false, closeOnClick: false, offset: 10, maxWidth: '340px' }) .setHTML(i18next.t('hover-add-street')); const hoverReversePopup = new mapboxgl.Popup({ closeButton: false, closeOnClick: false }) - .setHTML(`Reverse`); + .setHTML(`Reverse`); hoverReversePopup._content.className = 'tooltip-no-outline'; // Remove default styling. const hoverDeletePopup = new mapboxgl.Popup({ closeButton: false, closeOnClick: false }) - .setHTML(`Reverse`); + .setHTML(`Reverse`); hoverDeletePopup._content.className = 'tooltip-no-outline'; // Remove default styling. // Mark when a street is being hovered over. From a05631278fc1533f51ef797e5a95ab7bf9e3a52e Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 7 Dec 2023 11:14:17 -0800 Subject: [PATCH 72/77] RouteBuilder neighborhood styles now reset after deleting route --- public/javascripts/routeBuilder.js | 28 ++++++++++++++++------------ 1 file changed, 16 insertions(+), 12 deletions(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index c46cfdd422..022646968c 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -355,13 +355,7 @@ function RouteBuilder ($, mapParams) { // If there are no longer any streets in the route, any street can now be selected. Update styles. if (streetsInRoute.features.length === 0) { - map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: false }); - map.setPaintProperty('neighborhoods', 'fill-opacity', 0.0); - map.setPaintProperty('outside-neighborhoods', 'fill-opacity', 0.3); - - currRegionId = null; - introUI.style.visibility = 'visible'; - streetDistOverlay.style.visibility = 'hidden'; + resetUI(); } } else { // If the street was not in the route, add it to the route. map.setFeatureState({ source: 'streets', id: hoveredStreet }, { chosen: 'chosen' }); @@ -558,14 +552,24 @@ function RouteBuilder ($, mapParams) { currRegionId = null; setRouteDistanceText(); - // Reset the UI. - hideDeleteRouteModal(); - routeSavedModal.style.visibility = 'hidden'; - streetDistOverlay.style.visibility = 'hidden'; - introUI.style.visibility = 'visible'; + resetUI(); updateMarkers(); } + function resetUI() { + // Update neighborhood styling. + map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: false }); + map.setPaintProperty('neighborhoods', 'fill-opacity', 0.0); + map.setPaintProperty('outside-neighborhoods', 'fill-opacity', 0.3); + currRegionId = null; + + // Show intro UI and hide all others. + introUI.style.visibility = 'visible'; + streetDistOverlay.style.visibility = 'hidden'; + routeSavedModal.style.visibility = 'hidden'; + hideDeleteRouteModal(); + } + /** * Saves the route to the database, shows the Route Saved modal, and updates the links/buttons in that modal. */ From 8072fde037f851f959ab84f31799d3e8604c56d4 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 7 Dec 2023 11:18:29 -0800 Subject: [PATCH 73/77] fixes a couple RouteBuilder Chinese translations --- conf/messages.zh-TW | 2 +- public/locales/zh-TW/routebuilder.json | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/conf/messages.zh-TW b/conf/messages.zh-TW index 03b02e8dd7..f5c45366fc 100644 --- a/conf/messages.zh-TW +++ b/conf/messages.zh-TW @@ -33,7 +33,7 @@ dist.metric.abbr = 哩 distance.icon.alt = 顯示彎曲路徑到達目的地的圖示 ok = 確認 cancel = 取消 -back = Back +back = 後退 error = 錯誤! yes.caps = 是 no.caps = 否 diff --git a/public/locales/zh-TW/routebuilder.json b/public/locales/zh-TW/routebuilder.json index c3be956d2a..3507be9862 100644 --- a/public/locales/zh-TW/routebuilder.json +++ b/public/locales/zh-TW/routebuilder.json @@ -1,6 +1,6 @@ { "route-length": "{{dist}} $t(common:unit-distance-abbreviation)", - "hover-add-street": "Click on a street to start building your route", + "hover-add-street": "請點選一條街道來開始設立您的路線。", "copied-to-clipboard": "已複製到剪貼板!", "one-neighborhood-warning": "目前,一條路線內只能包涵一個社區內的街道。" } From 1491f40b9c64c9c2d2b9c3bcedc0c426d583de00 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 7 Dec 2023 11:53:07 -0800 Subject: [PATCH 74/77] updates RouteBuilder logging --- public/javascripts/routeBuilder.js | 33 +++++++++++++++++------------- 1 file changed, 19 insertions(+), 14 deletions(-) diff --git a/public/javascripts/routeBuilder.js b/public/javascripts/routeBuilder.js index 022646968c..7c6acb08f0 100644 --- a/public/javascripts/routeBuilder.js +++ b/public/javascripts/routeBuilder.js @@ -15,7 +15,6 @@ function RouteBuilder ($, mapParams) { let currRegionId = null; let streetData = null; let streetsInRoute = null; - let savedRoute = null; let currentMarkers = []; // Get the DOM elements. @@ -30,9 +29,9 @@ function RouteBuilder ($, mapParams) { let copyLinkButton = $('#copy-link-button'); // Add the click event for the clear route buttons. - document.getElementById('cancel-button').addEventListener('click', showDeleteRouteModal); + document.getElementById('cancel-button').addEventListener('click', clickCancelRoute); document.getElementById('delete-route-button').addEventListener('click', clearRoute); - document.getElementById('cancel-delete-route-button').addEventListener('click', hideDeleteRouteModal); + document.getElementById('cancel-delete-route-button').addEventListener('click', clickResumeRoute); document.getElementById('build-new-route-button').addEventListener('click', clearRoute); // Initialize the map. @@ -528,18 +527,20 @@ function RouteBuilder ($, mapParams) { return shouldReverse; } - function showDeleteRouteModal() { + function clickCancelRoute() { + logActivity('RouteBuilder_Click=CancelRoute'); deleteRouteModal.style.visibility = 'visible'; } - function hideDeleteRouteModal() { + function clickResumeRoute() { + logActivity('RouteBuilder_Click=ResumeRoute'); deleteRouteModal.style.visibility = 'hidden'; } /** * Clear the current route and reset the map. */ - function clearRoute() { + function clearRoute(e) { // Remove all the streets from the route. streetsInRoute.features.forEach(s => { map.setFeatureState({ source: 'streets', id: s.properties.street_edge_id }, { chosen: 'not chosen' }); @@ -551,9 +552,18 @@ function RouteBuilder ($, mapParams) { map.setFeatureState({ source: 'neighborhoods', id: currRegionId }, { current: false }); currRegionId = null; setRouteDistanceText(); + updateMarkers(); resetUI(); - updateMarkers(); + + // Log if clearing route from a button. + if (e && e.target && e.target.id) { + if (e.target.id === 'delete-route-button') { + logActivity(`RouteBuilder_Click=ConfirmCancelRoute`); + } else if (e.target.id === 'build-new-route-button') { + logActivity(`RouteBuilder_Click=BuildNewRoute`); + } + } } function resetUI() { @@ -567,7 +577,7 @@ function RouteBuilder ($, mapParams) { introUI.style.visibility = 'visible'; streetDistOverlay.style.visibility = 'hidden'; routeSavedModal.style.visibility = 'hidden'; - hideDeleteRouteModal(); + deleteRouteModal.style.visibility = 'hidden'; } /** @@ -580,11 +590,7 @@ function RouteBuilder ($, mapParams) { reverse: s.properties.reverse === true })); - // Don't save if the route is empty or hasn't changed. - if (JSON.stringify(streetProps) === JSON.stringify(savedRoute)) { - logActivity(`RouteBuilder_Click=SaveDuplicate`); - return; - } + // Save the route and then update UI. fetch('/saveRoute', { method: 'POST', headers: { @@ -595,7 +601,6 @@ function RouteBuilder ($, mapParams) { }) .then((response) => response.json()) .then((data) => { - savedRoute = streetProps; routeSavedModal.style.visibility = 'visible'; let exploreRelURL = `/explore?routeId=${data.route_id}`; let exploreURL = `${window.location.origin}${exploreRelURL}` From 184a99f739d853d4949a1d839c37b6e892a0178f Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 7 Dec 2023 12:16:20 -0800 Subject: [PATCH 75/77] updates people nudge url to public nudge --- app/views/index.scala.html | 4 +- conf/messages.de | 2 +- conf/messages.en | 2 +- conf/messages.es | 2 +- conf/messages.nl | 2 +- conf/messages.zh-TW | 2 +- .../Deploy_Seattle&Oradell_Aug 3.py | 82 ++++++++++++++++++ ...e_nudge_logo.png => public_nudge_logo.png} | Bin 8 files changed, 89 insertions(+), 7 deletions(-) create mode 100644 public/assets/prediction-model/Deploy_Seattle&Oradell_Aug 3.py rename public/assets/{people_nudge_logo.png => public_nudge_logo.png} (100%) diff --git a/app/views/index.scala.html b/app/views/index.scala.html index 62b88d3943..40025274e9 100644 --- a/app/views/index.scala.html +++ b/app/views/index.scala.html @@ -214,8 +214,8 @@ @if(List("taipei", "new-taipei-tw", "keelung-tw").contains(currentCity.cityId)){ } else { diff --git a/conf/messages.de b/conf/messages.de index 091da5721b..b17672b802 100644 --- a/conf/messages.de +++ b/conf/messages.de @@ -125,7 +125,7 @@ landing.collaborators.logo.open.columbus.alt = Columbus-Logo öffnen landing.collaborators.logo.world.enabled.alt = World Enabled-Logo landing.collaborators.logo.city.of.amsterdam.alt = Logo der Stadt Amsterdam landing.collaborators.logo.amsterdam.intelligence.alt = Amsterdam Intelligence Logo -landing.collaborators.logo.people.nudge.alt = People Nudge Logo +landing.collaborators.logo.public.nudge.alt = Public Nudge Logo landing.clouds.alt = Weiße Wolken bedecken teilweise das Bild oben, mit Statistiken über den Wolken. Landing.skyline1.png.alt = Eine Illustration einer Kreuzung mit Menschen, die über die Straße fahren. Landing.skyline2.png.alt = Eine Illustration einer Kreuzung mit Menschen, die über die Straße fahren. Im Hintergrund ist eine Flagge in den Farben der mexikanischen Flagge zu sehen. diff --git a/conf/messages.en b/conf/messages.en index 2becf7736c..221b33af45 100644 --- a/conf/messages.en +++ b/conf/messages.en @@ -120,7 +120,7 @@ landing.collaborators.logo.open.columbus.alt = Open Columbus Logo landing.collaborators.logo.world.enabled.alt = World Enabled Logo landing.collaborators.logo.city.of.amsterdam.alt = City of Amsterdam Logo landing.collaborators.logo.amsterdam.intelligence.alt = Amsterdam Intelligence Logo -landing.collaborators.logo.people.nudge.alt = People Nudge Logo +landing.collaborators.logo.public.nudge.alt = Public Nudge Logo landing.clouds.alt = White clouds partially covering the image above, with statistics shown on top of the clouds. landing.skyline1.png.alt = An illustration of an intersection with people traveling across the street. landing.skyline2.png.alt = An illustration of an intersection with people traveling across the street. A flag showing the colors of the flag of Mexico is in the background. diff --git a/conf/messages.es b/conf/messages.es index dc664444c6..ce84ee2d55 100644 --- a/conf/messages.es +++ b/conf/messages.es @@ -129,7 +129,7 @@ landing.collaborators.logo.open.columbus.alt = Logotipo abierto de Columbus landing.collaborators.logo.world.enabled.alt = Logotipo habilitado para el mundo landing.collaborators.logo.city.of.amsterdam.alt = Logotipo de la ciudad de Ámsterdam landing.collaborators.logo.amsterdam.intelligence.alt = Logotipo de Inteligencia de Ámsterdam -landing.collaborators.logo.people.nudge.alt = Logotipo de empujón de personas +landing.collaborators.logo.public.nudge.alt = Logotipo de Nudge Public landing.clouds.alt = Nubes blancas que cubren parcialmente la imagen de arriba, con estadísticas mostradas encima de las nubes. landing.skyline1.png.alt = Una ilustración de una intersección con personas cruzando la calle. landing.skyline2.png.alt = Una ilustración de una intersección con personas cruzando la calle. Al fondo hay una bandera que muestra los colores de la bandera de México. diff --git a/conf/messages.nl b/conf/messages.nl index 3e4a25a9e1..09d2dba831 100644 --- a/conf/messages.nl +++ b/conf/messages.nl @@ -128,7 +128,7 @@ landing.collaborators.logo.open.columbus.alt = Open het Columbus-logo landing.collaborators.logo.world.enabled.alt = Wereld ingeschakeld logo landing.collaborators.logo.city.of.amsterdam.alt = Logo gemeente Amsterdam landing.collaborators.logo.amsterdam.intelligence.alt = Amsterdam Intelligence-logo -landing.collaborators.logo.people.nudge.alt = Mensen duwen logo +landing.collaborators.logo.public.nudge.alt = Public Nudge -logo landing.clouds.alt = Witte wolken bedekken de afbeelding hierboven gedeeltelijk, terwijl de statistieken bovenop de wolken worden weergegeven. landing.skyline1.png.alt = Een illustratie van een kruispunt met mensen die de straat oversteken. landing.skyline2.png.alt = Een illustratie van een kruispunt met mensen die de straat oversteken. Op de achtergrond staat een vlag met de kleuren van de vlag van Mexico. diff --git a/conf/messages.zh-TW b/conf/messages.zh-TW index f5c45366fc..a0a0f97cda 100644 --- a/conf/messages.zh-TW +++ b/conf/messages.zh-TW @@ -151,7 +151,7 @@ landing.collaborators.logo.open.columbus.alt = 打開哥倫布徽標 landing.collaborators.logo.world.enabled.alt = 世界啟用徽標 landing.collaborators.logo.city.of.amsterdam.alt = 阿姆斯特丹市標誌 landing.collaborators.logo.amsterdam.intelligence.alt = 阿姆斯特丹情報局標誌 -landing.collaborators.logo.people.nudge.alt = 人們輕推標誌 +landing.collaborators.logo.public.nudge.alt = 人們輕推標誌 landing.clouds.alt = 白雲部分覆蓋了上圖,統計數據顯示在雲層頂部。 landing.skyline1.png.alt = 十字路口的插圖,行人過馬路。 landing.skyline2.png.alt = 十字路口的插圖,行人過馬路。 背景是一面顯示墨西哥國旗顏色的旗幟。 diff --git a/public/assets/prediction-model/Deploy_Seattle&Oradell_Aug 3.py b/public/assets/prediction-model/Deploy_Seattle&Oradell_Aug 3.py new file mode 100644 index 0000000000..23d09a5c20 --- /dev/null +++ b/public/assets/prediction-model/Deploy_Seattle&Oradell_Aug 3.py @@ -0,0 +1,82 @@ +import onnxruntime as rt +import numpy as np + +# Function to preprocess the model input +def preprocess_model_input(severity, zoom, clustered, distance_to_road, distance_to_intersection, tag, description, label_type, way_type): + # Combine the input features into a list + data = [severity, zoom, clustered, distance_to_road, distance_to_intersection, tag, description] + + # Encode the label type as one-hot vector + if label_type == 'CurbRamp': + data += [1, 0, 0, 0, 0] + elif label_type == 'NoCurbRamp': + data += [0, 1, 0, 0, 0] + elif label_type == 'NoSidewalk': + data += [0, 0, 1, 0, 0] + elif label_type == 'Obstacle': + data += [0, 0, 0, 1, 0] + elif label_type == 'SurfaceProblem': + data += [0, 0, 0, 0, 1] + else: + data += [0, 0, 0, 0, 0] + + # Encode the way type as one-hot vector + if way_type == 'living_street': + data += [1, 0, 0, 0, 0, 0, 0] + elif way_type == 'primary': + data += [0, 1, 0, 0, 0, 0, 0] + elif way_type == 'residential': + data += [0, 0, 1, 0, 0, 0, 0] + elif way_type == 'secondary': + data += [0, 0, 0, 1, 0, 0, 0] + elif way_type == 'tertiary': + data += [0, 0, 0, 0, 1, 0, 0] + elif way_type == 'trunk': + data += [0, 0, 0, 0, 0, 1, 0] + elif way_type == 'unclassified': + data += [0, 0, 0, 0, 0, 0, 1] + else: + data += [0, 0, 0, 0, 0, 0, 0] + + # Convert the data list into a numpy array of type float32 + input_array = np.array([data], dtype=np.float32) + # print("input_array type: " + str(type(input_array))) + + # Return the array + return input_array + + +# Function to predict using the ONNX model +def predict_model_seattle(session, model_input_name, model_output_name, model_input): + # Run the model + output = session.run([model_output_name], {model_input_name: model_input}) + predictions = output[0] + + return predictions + + +# Load the ONNX model +onnx_path = "seattle_Prediction_MLP.onnx" +session = rt.InferenceSession(onnx_path) + +# Get the input and output names for the model +model_input_name = session.get_inputs()[0].name +model_output_name = session.get_outputs()[0].name + +# Test - example input data +severity = 5 +zoom = 1 +clustered = 1 +distance_to_road = 18 +distance_to_intersection = 0 +tag = 1 +description = 0 +way_type = 'residential' +label_type = 'Obstacle' + +# Pass input data to the preprocessing function +preprocessed_data = preprocess_model_input(severity, zoom, clustered, distance_to_road, distance_to_intersection, tag, description, label_type, way_type) + +# Result - Prediction +result = predict_model_seattle(session, model_input_name, model_output_name, preprocessed_data) +print("Predictions:", result) diff --git a/public/assets/people_nudge_logo.png b/public/assets/public_nudge_logo.png similarity index 100% rename from public/assets/people_nudge_logo.png rename to public/assets/public_nudge_logo.png From 729e7ddd2e2961da1f4471263dcdb985188c252e Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 7 Dec 2023 12:19:51 -0800 Subject: [PATCH 76/77] removes file accidentally committed --- .../Deploy_Seattle&Oradell_Aug 3.py | 82 ------------------- 1 file changed, 82 deletions(-) delete mode 100644 public/assets/prediction-model/Deploy_Seattle&Oradell_Aug 3.py diff --git a/public/assets/prediction-model/Deploy_Seattle&Oradell_Aug 3.py b/public/assets/prediction-model/Deploy_Seattle&Oradell_Aug 3.py deleted file mode 100644 index 23d09a5c20..0000000000 --- a/public/assets/prediction-model/Deploy_Seattle&Oradell_Aug 3.py +++ /dev/null @@ -1,82 +0,0 @@ -import onnxruntime as rt -import numpy as np - -# Function to preprocess the model input -def preprocess_model_input(severity, zoom, clustered, distance_to_road, distance_to_intersection, tag, description, label_type, way_type): - # Combine the input features into a list - data = [severity, zoom, clustered, distance_to_road, distance_to_intersection, tag, description] - - # Encode the label type as one-hot vector - if label_type == 'CurbRamp': - data += [1, 0, 0, 0, 0] - elif label_type == 'NoCurbRamp': - data += [0, 1, 0, 0, 0] - elif label_type == 'NoSidewalk': - data += [0, 0, 1, 0, 0] - elif label_type == 'Obstacle': - data += [0, 0, 0, 1, 0] - elif label_type == 'SurfaceProblem': - data += [0, 0, 0, 0, 1] - else: - data += [0, 0, 0, 0, 0] - - # Encode the way type as one-hot vector - if way_type == 'living_street': - data += [1, 0, 0, 0, 0, 0, 0] - elif way_type == 'primary': - data += [0, 1, 0, 0, 0, 0, 0] - elif way_type == 'residential': - data += [0, 0, 1, 0, 0, 0, 0] - elif way_type == 'secondary': - data += [0, 0, 0, 1, 0, 0, 0] - elif way_type == 'tertiary': - data += [0, 0, 0, 0, 1, 0, 0] - elif way_type == 'trunk': - data += [0, 0, 0, 0, 0, 1, 0] - elif way_type == 'unclassified': - data += [0, 0, 0, 0, 0, 0, 1] - else: - data += [0, 0, 0, 0, 0, 0, 0] - - # Convert the data list into a numpy array of type float32 - input_array = np.array([data], dtype=np.float32) - # print("input_array type: " + str(type(input_array))) - - # Return the array - return input_array - - -# Function to predict using the ONNX model -def predict_model_seattle(session, model_input_name, model_output_name, model_input): - # Run the model - output = session.run([model_output_name], {model_input_name: model_input}) - predictions = output[0] - - return predictions - - -# Load the ONNX model -onnx_path = "seattle_Prediction_MLP.onnx" -session = rt.InferenceSession(onnx_path) - -# Get the input and output names for the model -model_input_name = session.get_inputs()[0].name -model_output_name = session.get_outputs()[0].name - -# Test - example input data -severity = 5 -zoom = 1 -clustered = 1 -distance_to_road = 18 -distance_to_intersection = 0 -tag = 1 -description = 0 -way_type = 'residential' -label_type = 'Obstacle' - -# Pass input data to the preprocessing function -preprocessed_data = preprocess_model_input(severity, zoom, clustered, distance_to_road, distance_to_intersection, tag, description, label_type, way_type) - -# Result - Prediction -result = predict_model_seattle(session, model_input_name, model_output_name, preprocessed_data) -print("Predictions:", result) From 6e7d58dd33202d970c12f405119484781d017608 Mon Sep 17 00:00:00 2001 From: Mikey Saugstad Date: Thu, 7 Dec 2023 12:42:06 -0800 Subject: [PATCH 77/77] 7.16.1 -> 7.17.0 --- build.sbt | 2 +- conf/evolutions/default/208.sql | 5 +++++ 2 files changed, 6 insertions(+), 1 deletion(-) create mode 100644 conf/evolutions/default/208.sql diff --git a/build.sbt b/build.sbt index 10d3032bd6..7a8ab7b8ad 100644 --- a/build.sbt +++ b/build.sbt @@ -2,7 +2,7 @@ import play.PlayScala name := """sidewalk-webpage""" -version := "7.16.1" +version := "7.17.0" scalaVersion := "2.10.7" diff --git a/conf/evolutions/default/208.sql b/conf/evolutions/default/208.sql new file mode 100644 index 0000000000..19d49d4242 --- /dev/null +++ b/conf/evolutions/default/208.sql @@ -0,0 +1,5 @@ +# --- !Ups +INSERT INTO version VALUES ('7.17.0', now(), 'RouteBuilder has been completely redesigned.'); + +# --- !Downs +DELETE FROM version WHERE version_id = '7.17.0';