irie 0.0.54__py3-none-any.whl → 0.0.55__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of irie might be problematic. Click here for more details.

irie/apps/events/views.py CHANGED
@@ -32,7 +32,7 @@ def event_table(request):
32
32
  events = [i for i in sorted(EventRecord.objects.all(),
33
33
  key=lambda x: x.motion_data["event_date"], reverse=True)]
34
34
 
35
- paginator = Paginator(events, 5)
35
+ paginator = Paginator(events, 20)
36
36
 
37
37
 
38
38
  # reversed(sorted(Event.objects.all(),
@@ -33,6 +33,12 @@ class PredictorModel(models.Model):
33
33
 
34
34
  def __str__(self):
35
35
  return f"{self.asset.calid} - {self.name} : {self.description}"
36
+
37
+ def get_runner(self):
38
+ pass
39
+
40
+ def get_artist(self):
41
+ pass
36
42
 
37
43
 
38
44
  class SensorAssignment(models.Model):
@@ -500,55 +500,59 @@ class OpenSeesRunner(Runner):
500
500
  #
501
501
  # Viewing methods
502
502
  #
503
+
504
+ @property
505
+ def _csi(self):
506
+ if not hasattr(self, "_csi_data") or self._csi_data is None:
507
+ from openbim.csi import load, create_model, collect_outlines
508
+ # 1) Parse the CSI file
509
+ try:
510
+ csi_file = self.predictor.config_file
511
+ self._csi_data = load((str(line.decode()).replace("\r\n","\n") for line in csi_file.readlines()))
512
+ except Exception as e:
513
+ import sys
514
+ print(f"Error loading CSiBridge file: {e}", file=sys.stderr)
515
+ self._csi_data = None
516
+
517
+ return self._csi_data
518
+
519
+
503
520
  def structural_section(self, name):
504
- from shps.shapes import from_aisc
505
- from openbim.csi._frame.section import section_geometry, section_mesh
506
-
507
- from openbim.csi import load, create_model, collect_outlines
508
- # 1) Parse the CSI file
509
- try:
510
- csi_file = self.predictor.config_file
511
- csi = load((str(line.decode()).replace("\r\n","\n") for line in csi_file.readlines()))
512
- except:
513
- return None
514
-
515
- mesh = section_mesh(csi, name)
516
- return {}, mesh
517
- mesh = from_aisc("W12x14").create_mesh(mesh_kwds={"engine": "meshpy"})
518
- mesh = (mesh.nodes, mesh.cells())
519
- # return {}, mesh
521
+ from openbim.csi._frame.section import create_section
522
+ # from openbim.csi._frame.outlines import section_mesh
523
+ if (s:= create_section(self._csi, name)) is not None:
524
+ return {}, s._create_model(mesh_size=0.1)
525
+
526
+
527
+ def structural_sections(self):
528
+ from openbim.csi._frame.section import iter_sections
529
+ yield from iter_sections(self._csi)
530
+ # for s, name in iter_sections(self._csi):
531
+ # yield {
532
+ # "name": name,
533
+ # "type": "Section",
534
+ # "section": name,
535
+ # }
520
536
 
521
537
  def structural_members(self):
522
538
 
523
- from openbim.csi import load, create_model, collect_outlines
524
- # 1) Parse the CSI file
525
- csi_file = self.predictor.config_file
526
- try:
527
- csi = load((str(line.decode()).replace("\r\n","\n") for line in csi_file.readlines()))
528
- except Exception as e:
529
- import sys
530
- print(f"Error loading CSiBridge file: {e}", file=sys.stderr)
531
- csi = {}
532
-
533
- for item in csi.get("BRIDGE BENT DEFINITIONS 2 - COLUMN DATA",[]):
539
+ for item in self._csi.get("BRIDGE BENT DEFINITIONS 2 - COLUMN DATA",[]):
534
540
  if "ColNum" in item and "Section" in item:
535
541
  yield {
536
542
  "name": item["ColNum"],
537
543
  "type": "Column",
538
- "section": item["Section"],
544
+ # "section": item["Section"],
539
545
  }
540
546
 
541
- for item in csi.get("BRIDGE OBJECT DEFINITIONS 03 - SPANS 1 - GENERAL", []):
547
+ for item in self._csi.get("BRIDGE OBJECT DEFINITIONS 03 - SPANS 1 - GENERAL", []):
542
548
  if "SpanName" in item and "BridgeSect" in item:
543
549
  yield {
544
550
  "name": item["SpanName"],
545
551
  "type": "Span",
546
- "section": None,
552
+ # "section": None,
547
553
  }
548
554
 
549
555
 
550
-
551
-
552
556
  # import subprocess
553
557
  # class Event: pass
554
558
 
@@ -9,7 +9,7 @@
9
9
  #----------------------------------------------------------------------------#
10
10
  from django.urls import re_path
11
11
  from .views import (
12
- asset_predictors, predictor_profile, predictor_profile_detail,
12
+ asset_predictors, predictor_profile, predictor_render,
13
13
  create_mdof, create_model, asset_map
14
14
  )
15
15
 
@@ -17,7 +17,7 @@ _ROOT = "^inventory/(?P<calid>[0-9 A-Z-]*)/predictors"
17
17
 
18
18
  urlpatterns = [
19
19
  re_path(f"{_ROOT}/(?P<preid>[0-9]{{1,}})/$", predictor_profile),
20
- re_path(f"{_ROOT}/(?P<preid>[0-9]{{1,}})/detail/", predictor_profile_detail),
20
+ re_path(f"{_ROOT}/(?P<preid>[0-9]{{1,}})/render/", predictor_render),
21
21
  re_path(f"{_ROOT}/create/map/$", asset_map),
22
22
  re_path(f"{_ROOT}/create/model/$", create_model),
23
23
  re_path(f"{_ROOT}/create/v1/$", create_mdof),
@@ -14,6 +14,7 @@ import json
14
14
  import veux
15
15
  import uuid
16
16
  import base64
17
+ import hashlib
17
18
 
18
19
  from django.shortcuts import HttpResponse
19
20
  from django.template import loader, TemplateDoesNotExist
@@ -30,6 +31,14 @@ from irie.apps.prediction.models import PredictorModel
30
31
  from .forms import PredictorForm
31
32
 
32
33
 
34
+
35
+ def _string_to_id(s: str) -> str:
36
+ # 1. SHA-256 → bytes 2. URL-safe Base64 (no + / =) 3. strip padding
37
+ b64 = base64.urlsafe_b64encode(
38
+ hashlib.sha256(s.encode()).digest()
39
+ ).rstrip(b'=').decode('ascii')
40
+ return f"id_{b64}"
41
+
33
42
  @login_required(login_url="/login/")
34
43
  def asset_predictors(request, calid):
35
44
 
@@ -59,8 +68,7 @@ def asset_predictors(request, calid):
59
68
 
60
69
 
61
70
  @login_required(login_url="/login/")
62
- def predictor_profile_detail(request, calid, preid):
63
- print(preid)
71
+ def predictor_render(request, calid, preid):
64
72
  try:
65
73
  predictor = PredictorModel.objects.get(pk=int(preid))
66
74
  except ObjectDoesNotExist:
@@ -71,7 +79,18 @@ def predictor_profile_detail(request, calid, preid):
71
79
  runner = PREDICTOR_TYPES[predictor.protocol](predictor)
72
80
 
73
81
  try:
74
- data, mesh = runner.structural_section(sname)
82
+ _, mesh = runner.structural_section(sname)
83
+
84
+ can = veux._create_canvas(name="gltf")
85
+ import numpy as np
86
+ R = np.array([[1, 0],[0, 1], [0, 0]])
87
+ can.plot_lines(mesh.exterior()@R.T)
88
+ if (interior := mesh.interior()) is not None:
89
+ for i in interior:
90
+ can.plot_lines(i@R.T)
91
+ glb = can.to_glb()
92
+ return HttpResponse(glb, content_type="application/binary")
93
+
75
94
  except Exception as e:
76
95
  raise e
77
96
  return HttpResponse(
@@ -79,6 +98,7 @@ def predictor_profile_detail(request, calid, preid):
79
98
  content_type="application/json",
80
99
  status=404
81
100
  )
101
+
82
102
  from veux.plane import PlaneModel
83
103
  art = veux.create_artist(mesh, ndf=1, canvas="gltf")
84
104
  art.draw_surfaces()
@@ -86,7 +106,7 @@ def predictor_profile_detail(request, calid, preid):
86
106
 
87
107
  glb = art.canvas.to_glb()
88
108
  return HttpResponse(glb, content_type="application/binary")
89
- glb64 = base64.b64encode(glb).decode("utf-8")
109
+
90
110
  # rendering = f"data:application/octet-stream;base64,{glb64}"
91
111
  # rendering = art._repr_html_()
92
112
  r = dict(
@@ -123,8 +143,16 @@ def predictor_profile(request, calid, preid):
123
143
  try:
124
144
  if predictor.protocol == PredictorModel.Protocol.TYPE1:
125
145
  html_template = loader.get_template("prediction/xara-profile.html")
146
+
126
147
  context["members"] = context["runner"].structural_members()
127
148
 
149
+ context["sections"] = [
150
+ {
151
+ "id": _string_to_id(name),
152
+ "name": name,
153
+ } for _, name in context["runner"].structural_sections()
154
+ ]
155
+
128
156
  else:
129
157
  html_template = loader.get_template("prediction/predictor-profile.html")
130
158
 
@@ -242,7 +270,7 @@ def create_model(request, calid):
242
270
  )
243
271
  artist.draw_surfaces()
244
272
 
245
- # Generate the .glb file
273
+ # Generate the .glb data
246
274
  glb = artist.canvas.to_glb()
247
275
 
248
276
  if request.POST.get("action") == "commit":
@@ -183,7 +183,7 @@ document.addEventListener("DOMContentLoaded", function(event) {
183
183
  });
184
184
 
185
185
  if (document.querySelector('.current-year')){
186
- document.querySelector('.current-year').textContent = new Date().getFullYear();
186
+ document.querySelector('.current-year').textContent = new Date().getFullYear();
187
187
  }
188
188
  // Glide JS
189
189
  });
@@ -302,7 +302,7 @@ if (document.querySelector('.fixed-plugin')) {
302
302
 
303
303
  }
304
304
 
305
- //Set Sidebar Color
305
+ // Set Sidebar Color
306
306
  function sidebarColor(a) {
307
307
  var parent = document.querySelector(".nav-link.active");
308
308
  var color = a.getAttribute("data-color");
@@ -36,6 +36,7 @@
36
36
  </a>
37
37
  </div>
38
38
  </div>
39
+
39
40
  <div class="row">
40
41
  <div class="col">
41
42
  <form method="POST" enctype="multipart/form-data">
@@ -46,6 +47,13 @@
46
47
  </form>
47
48
  </div>
48
49
  </div>
50
+
51
+ {% if navigator %}
52
+ {% include "prediction/veux/navigator.html" with members=navigator.members sections=navigator.sections %}
53
+ {% endif %}
54
+
55
+ {% if error %}
56
+ {% endif %}
49
57
  <div class="row">
50
58
  <iframe
51
59
  id="map"
@@ -58,6 +66,25 @@
58
66
  {% endblock content %}
59
67
 
60
68
  {% block javascripts %}
69
+ {% if navigator %}
70
+ <script>
71
+
72
+ {% include "prediction/veux/navigator.js" %}
73
+
74
+ const VIEWER = new VeuxNavigator(`/inventory/{{asset.calid}}/predictors/{{predictor.id}}/render/?section=`,
75
+ document.querySelector('#tab-link-container'),
76
+ document.getElementById('tab-content-container'));
77
+
78
+ function handleMemberSelection(elem) {
79
+ VIEWER.select(elem);
80
+ }
81
+
82
+ document.addEventListener('DOMContentLoaded', function () {
83
+ VIEWER.initTabs('tab1', '.tab-link');
84
+ });
85
+ </script>
86
+ {% endif %}
87
+
61
88
  <script>
62
89
  const button = document.getElementById('render');
63
90
  const form = document.querySelector('form');
@@ -0,0 +1,121 @@
1
+ <div class="">
2
+ <div class="row align-right">
3
+ <!-- Left Side: Sensor Form -->
4
+ <div class="col-md-4" >
5
+ <div class="card bg-white-100 border-1 rounded-0 shadow">
6
+ <div class="card-header d-sm-flex flex-row align-items-center flex-0">
7
+ <select id="table-switcher"
8
+ class="form-select form-select-sm me-2">
9
+ <option value="members" >Members</option>
10
+ <option value="sections">Sections</option>
11
+ <option value="sensors" >Sensors</option>
12
+ </select>
13
+ </div>
14
+ <div class="card-body">
15
+ <div class="table-response">
16
+ <table id="members"
17
+ class="table align-items-center table-flush">
18
+ <thead class="thead-light">
19
+ <tr>
20
+ <th class="border-bottom" scope="col">#</th>
21
+ <th class="border-bottom" scope="col">Type</th>
22
+ </tr>
23
+ </thead>
24
+ <tbody>
25
+ {% for member in members %}
26
+ <tr id="veux-member-{{member.id}}"
27
+ data-section="{{ member.section }}"
28
+ style="cursor: pointer;"
29
+ onClick="handleMemberSelection(this)">
30
+ <td><code>{{ member.name }}</code></td>
31
+ <td>{{ member.type }}</td>
32
+ </tr>
33
+ {% endfor %}
34
+ </tbody>
35
+ </table>
36
+
37
+ <table id="sections" hidden
38
+ class="table align-items-center table-flush">
39
+ <thead class="thead-light">
40
+ <tr>
41
+ <th class="border-bottom" scope="col">#</th>
42
+ <th class="border-bottom" scope="col">Type</th>
43
+ </tr>
44
+ </thead>
45
+ <tbody>
46
+ {% for member in sections %}
47
+ <tr id="veux-member-{{member.id}}"
48
+ data-query="{{ member.name }}"
49
+ data-name="{{ member.name }}"
50
+ style="cursor: pointer;"
51
+ onClick="handleMemberSelection(this)">
52
+ <td><code>{{ member.name }}</code></td>
53
+ <td>{{ member.type }}</td>
54
+ </tr>
55
+ {% endfor %}
56
+ </tbody>
57
+ </table>
58
+
59
+ <table id="sensors"
60
+ class="table align-items-center table-flush" hidden>
61
+ <thead class="thead-light">
62
+ <tr>
63
+ <th class="border-bottom" scope="col">#</th>
64
+ <th class="border-bottom" scope="col">Node</th>
65
+ <th class="border-bottom" scope="col">Type</th>
66
+ </tr>
67
+ </thead>
68
+ <tbody>
69
+ {% for sensor in sensors %}
70
+ <tr id="sensor-{{sensor.id}}"
71
+ data-sensor-x="{{ sensor.sensor.x }}"
72
+ data-sensor-y="{{ sensor.sensor.y }}"
73
+ data-sensor-z="{{ sensor.sensor.z }}"
74
+ data-sensor-dx="{{ sensor.sensor.dx }}"
75
+ data-sensor-dy="{{ sensor.sensor.dy }}"
76
+ data-sensor-dz="{{ sensor.sensor.dy }}">
77
+ <td><code>{{ sensor.id }}</code></td>
78
+ <td>{{ sensor.node }}</td>
79
+ <td>{{ sensor.role }}</td>
80
+ </tr>
81
+ {% endfor %}
82
+ </tbody>
83
+ </table>
84
+ <nav>
85
+ <ul class="pagination" id="pagination"></ul>
86
+ </nav>
87
+ </div>
88
+ </div>
89
+ </div>
90
+ </div>
91
+
92
+ <!-- Right Side: Predictor Rendering -->
93
+ <div class="col-md-8">
94
+ <div id="rendering" class="card bg-white-100 border-1 rounded-0 shadow">
95
+ <div class="card-header">
96
+ <ul id="tab-link-container" class="nav nav-tabs" id="myTab" role="tablist">
97
+ <li class="nav-item" role="presentation">
98
+ <a class="nav-link tab-link active"
99
+ id="tab1-tab"
100
+ data-bs-toggle="tab" href="#"
101
+ data-tab="tab1"
102
+ role="tab">Model</a>
103
+ </li>
104
+ </ul>
105
+ </div>
106
+ <div class="card-body text-center" style="background-color: #f0f0f0;">
107
+ <div id="tab-content-container">
108
+ <div id="tab1-content" class="tab-content">
109
+ <div id="main-viewer"
110
+ style="width: 100%; height: 300px; background-color: #f0f0f0; margin: 0 auto;">
111
+ </div>
112
+ </div>
113
+ </div>
114
+ </div>
115
+ <div class="card-footer text-center">
116
+ Powered by <a href="https://veux.io/">veux</a>
117
+ </div>
118
+ </div>
119
+ </div>
120
+ </div>
121
+ </div>
@@ -4,15 +4,15 @@
4
4
  //
5
5
  //===----------------------------------------------------------------------===//
6
6
  //
7
- class VeuxViewer {
7
+ class VeuxNavigator {
8
8
  #initializedTabs;
9
9
  #table;
10
10
  #url;
11
11
  #tabLinkContainer;
12
12
  #tabContentContainer;
13
13
 
14
- constructor(url, tabLinkContainer, tabContentContainer) {
15
- this.#url = url;
14
+ constructor(baseUrl, tabLinkContainer, tabContentContainer) {
15
+ this.#url = baseUrl;
16
16
  this.#initializedTabs = [];
17
17
  this.#tabLinkContainer = tabLinkContainer;
18
18
  this.#tabContentContainer = tabContentContainer;
@@ -32,7 +32,8 @@ class VeuxViewer {
32
32
  }
33
33
 
34
34
  select(elem) {
35
- const sname = elem.dataset.section;
35
+ const sname = `${elem.id}`; //dataset.name;
36
+ // const hash = elem.dataset.hash;
36
37
 
37
38
  if (this.#initializedTabs.includes(sname)) {
38
39
  const tabLink = this.#tabLinkContainer.querySelector(`#${sname}-tab`);
@@ -40,11 +41,11 @@ class VeuxViewer {
40
41
  return;
41
42
  }
42
43
 
43
- this.addTab(sname);
44
+ this.addTab(elem);
44
45
  }
45
46
 
46
- addTab(corr) {
47
- const tab = `${corr}`;
47
+ addTab(elem) {
48
+ const tab = `${elem.id}`;
48
49
 
49
50
  //
50
51
  //
@@ -54,10 +55,10 @@ class VeuxViewer {
54
55
  tabLink.classList.add("tab-link", "nav-link", "active");
55
56
  tabLink.href = "#";
56
57
  tabLink.setAttribute('data-tab', tab);
57
- tabLink.setAttribute('data-section', corr);
58
+ tabLink.setAttribute('data-query', elem.dataset.query);
58
59
  tabLink.setAttribute('data-bs-toggle', 'tab');
59
60
  tabLink.setAttribute('role', 'tab');
60
- tabLink.innerHTML = `${corr} <button class="btn-close" type="button" aria-label="Close"></button>`;
61
+ tabLink.innerHTML = `${elem.dataset.name} <button class="btn-close" type="button" aria-label="Close"></button>`;
61
62
  const closeButton = tabLink.querySelector('.btn-close');
62
63
  closeButton.addEventListener('click', (e) => {
63
64
  this.delTab(tabLink);
@@ -83,14 +84,10 @@ class VeuxViewer {
83
84
  tabContent.style.display = 'block';
84
85
  this.#tabContentContainer.appendChild(tabContent);
85
86
 
86
- // Get the data-tab attribute to know which content to load
87
- const selectedTab = tabLink.getAttribute('data-tab');
88
-
87
+
89
88
  this.#initializedTabs.push(tab);
90
-
91
89
  this.clickTab(tabLink);
92
-
93
- this.fetchAndUpdateTab(selectedTab, corr);
90
+ this.fetchAndUpdateTab(tab, elem.dataset.query);
94
91
  return tabLink;
95
92
  }
96
93
 
@@ -133,7 +130,7 @@ class VeuxViewer {
133
130
  this.clickTab(document.getElementById('tab1-tab'));
134
131
  }
135
132
 
136
- fetchAndUpdateTab(tab) {
133
+ fetchAndUpdateTab(tab, query) {
137
134
  const contentDiv = this.#tabContentContainer.querySelector(`#${tab}-content`);
138
135
 
139
136
  // Show loading message while content is being fetched
@@ -145,7 +142,7 @@ class VeuxViewer {
145
142
  </div>
146
143
  `;
147
144
 
148
- let apiUrl = `${this.#url}${tab}`;
145
+ let apiUrl = `${this.#url}${query}`;
149
146
  console.log(`Fetching content from: ${apiUrl}`);
150
147
 
151
148
  if (true) {
@@ -162,6 +159,9 @@ class VeuxViewer {
162
159
  contentDiv.appendChild(mv);
163
160
  return;
164
161
  }
162
+
163
+ //
164
+ //
165
165
  fetch(apiUrl)
166
166
  .then(response => response.json())
167
167
  .then(data => {
@@ -35,115 +35,16 @@
35
35
  </div>
36
36
  </div>
37
37
 
38
- <div class="">
39
- <div class="row align-right">
40
- <!-- Left Side: Sensor Form -->
41
- <div class="col-md-4" >
42
- <div class="card bg-white-100 border-1 rounded-0 shadow">
43
- <div class="card-header d-sm-flex flex-row align-items-center flex-0">
44
- <select id="table-switcher"
45
- class="form-select form-select-sm me-2">
46
- <option value="members">Members</option>
47
- <option value="sensors">Sensors</option>
48
- </select>
49
- </div>
50
- <div class="card-body">
51
- <div class="table-response">
52
- <table id="members"
53
- class="table align-items-center table-flush">
54
- <thead class="thead-light">
55
- <tr>
56
- <th class="border-bottom" scope="col">#</th>
57
- <th class="border-bottom" scope="col">Type</th>
58
- <th class="border-bottom" scope="col">Section</th>
59
- </tr>
60
- </thead>
61
- <tbody>
62
- {% for member in members %}
63
- <tr id="veux-member-{{member.id}}"
64
- data-section="{{ member.section }}"
65
- style="cursor: pointer;"
66
- onClick="handleMemberSelection(this)">
67
- <td><code>{{ member.name }}</code></td>
68
- <td>{{ member.type }}</td>
69
- <td class="fw-bolder text-gray-800">
70
- {{ member.section }}
71
- </td>
72
- </tr>
73
- {% endfor %}
74
- </tbody>
75
- </table>
76
-
77
- <table id="sensors" class="table align-items-center table-flush" hidden>
78
- <thead class="thead-light">
79
- <tr>
80
- <th class="border-bottom" scope="col">#</th>
81
- <th class="border-bottom" scope="col">Node</th>
82
- <th class="border-bottom" scope="col">Type</th>
83
- </tr>
84
- </thead>
85
- <tbody>
86
- {% for sensor in sensors %}
87
- <tr id="sensor-{{sensor.id}}"
88
- data-sensor-x="{{ sensor.sensor.x }}"
89
- data-sensor-y="{{ sensor.sensor.y }}"
90
- data-sensor-z="{{ sensor.sensor.z }}"
91
- data-sensor-dx="{{ sensor.sensor.dx }}"
92
- data-sensor-dy="{{ sensor.sensor.dy }}"
93
- data-sensor-dz="{{ sensor.sensor.dy }}">
94
- <td><code>{{ sensor.id }}</code></td>
95
- <td>{{ sensor.node }}</td>
96
- <td>{{ sensor.role }}</td>
97
- </tr>
98
- {% endfor %}
99
- </tbody>
100
- </table>
101
- <nav>
102
- <ul class="pagination" id="pagination"></ul>
103
- </nav>
104
- </div>
105
- </div>
106
- </div>
107
- </div>
108
-
109
- <!-- Right Side: Predictor Rendering -->
110
- <div class="col-md-8">
111
- <div id="rendering" class="card bg-white-100 border-1 rounded-0 shadow">
112
- <div class="card-header">
113
- <ul id="tab-link-container" class="nav nav-tabs" id="myTab" role="tablist">
114
- <li class="nav-item" role="presentation">
115
- <a class="nav-link tab-link active"
116
- id="tab1-tab"
117
- data-bs-toggle="tab" href="#"
118
- data-tab="tab1"
119
- role="tab">Model</a>
120
- </li>
121
- </ul>
122
- </div>
123
- <div class="card-body text-center" style="background-color: #f0f0f0;">
124
- <div id="tab-content-container">
125
- <div id="tab1-content" class="tab-content">
126
- <div id="main-viewer"
127
- style="width: 100%; height: 300px; background-color: #f0f0f0; margin: 0 auto;">
128
- </div>
129
- </div>
130
- </div>
131
- </div>
132
- <div class="card-footer text-center">
133
- Powered by <a href="https://veux.io/">veux</a>
134
- </div>
135
- </div>
136
- </div>
137
- </div>
138
- </div>
38
+ {% include "prediction/veux/navigator.html" with members=members sections=sections sensors=sensors %}
39
+
139
40
  {% endblock content %}
140
41
 
141
42
  {% block javascripts %}
142
43
 
143
44
  <script>
144
- {% include "prediction/viewer/veux-viewer.js" %}
45
+ {% include "prediction/veux/navigator.js" %}
145
46
 
146
- const VIEWER = new VeuxViewer(`/inventory/{{asset.calid}}/predictors/{{predictor.id}}/detail/?section=`,
47
+ const VIEWER = new VeuxNavigator(`/inventory/{{asset.calid}}/predictors/{{predictor.id}}/render/?section=`,
147
48
  document.querySelector('#tab-link-container'),
148
49
  document.getElementById('tab-content-container'));
149
50
 
@@ -236,6 +236,13 @@ td.left-text{vertical-align:middle}
236
236
  <div class="col-lg-4 order-lg-1 card shadow"><img src="{{ ASSETS_ROOT }}/img/twin.png"
237
237
  alt="Digital twins"></div>
238
238
  </div>
239
+
240
+ <div class="col-lg-5 mb-5 mb-lg-0">
241
+ <h3 class="d-flex align-items-center">State-of-the-art Modeling</h3>
242
+ <p class="mb-4">PEER is partnering with the <em>California Strong Motion Intrumentation Program</em>
243
+ to push sensor data to stakeholders in real-time.</p>
244
+ </div>
245
+ <div class="col-lg-6"><img src="{{ ASSETS_ROOT}}/content_images/brace/ForceFrame.png" alt="Force formulation"></div>
239
246
  {% comment %}
240
247
  <div class="col-lg-5 order-lg-2 mb-5 mb-lg-0">
241
248
  <h3 class="d-flex align-items-center"> Corridors<span
@@ -268,8 +275,8 @@ td.left-text{vertical-align:middle}
268
275
  <a href="https://xara.so">
269
276
  <img class="first-column-layout"
270
277
  src="{{ ASSETS_ROOT }}/content_images/brace/opensees.jpg" alt="opensees"></a></td>
271
- <td class=full-center-text><a href="https://pypi.org/project/xara" >xara</a></td>
272
- <td class=left-text>Direct and idiomatic bindings to <a href="https://github.com/claudioperez/OpenSeesRT" >
278
+ <td class=full-center-text><a href="https://xara.so" >xara</a></td>
279
+ <td class=left-text>Direct and idiomatic bindings to <a href="https://github.com/peer-open-source/xara" >
273
280
  <samp>OpenSeesRT</samp></a> kernel for finite element analysis.</td>
274
281
  </tr>
275
282
  {% if False %}
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: irie
3
- Version: 0.0.54
3
+ Version: 0.0.55
4
4
  Summary: An infrastructure resilience engine
5
5
  Author-email: "Claudio M. Perez" <50180406+claudioperez@users.noreply.github.com>
6
6
  Project-URL: Repository, https://github.com/STAIRLab
@@ -49,7 +49,7 @@ irie/apps/events/models.py,sha256=YwtvQCbFKOEGhVEAlGmCCLbepxwo0Xz0uV4vQ5z8dHM,39
49
49
  irie/apps/events/tests.py,sha256=PSZUTXteVS5Fim2upOndb1HW5Pu7DoC1r25-7_1i-so,33
50
50
  irie/apps/events/tests_events.py,sha256=iVNwnlZgqug1MtEIGS_E82wcQ7522m-0q47kreN_D90,8363
51
51
  irie/apps/events/urls.py,sha256=UrVmK0NpKvmDNH9Iad4CTbN9KdXaW4W3ZNWxPpiSgUY,1052
52
- irie/apps/events/views.py,sha256=3ojyXNsvFtKf_4ID2JqYEHlS7o2kEXOeH7Sl8Lnhhjs,2977
52
+ irie/apps/events/views.py,sha256=AS2WmKE9CrKi7kfXJ-_Gpj-DDYMcet6I8CMkEr1nYv8,2978
53
53
  irie/apps/events/views_events.py,sha256=ahQQy5z1T0NH69ybLmPWahboYmAsAmiaCI8g27Md_5A,7229
54
54
  irie/apps/events/migrations/0001_initial.py,sha256=sSCS0Kbyb73m_x3kw5Q4tRrTJcCqh3gRTLmkrcf6_ps,1065
55
55
  irie/apps/events/migrations/0002_rename_event_eventrecord.py,sha256=TNRUB9-EZmdURlkyAtz7KBdtuoSXwbwCQDRP4CKmdBw,431
@@ -97,10 +97,10 @@ irie/apps/prediction/admin.py,sha256=QR9eK3JivwPJ1dqtVeBB1YlT6oa8DjE9Sx1Hu6rnJ7c
97
97
  irie/apps/prediction/apps.py,sha256=sejLu4xx8_IwQQKTnxC_DNK-vhjiqeG0_uk2Zg1ga-M,422
98
98
  irie/apps/prediction/forms.py,sha256=3alwgkBhjnJsDmyh2zDAU1Z-2ZIfdV8f_dXUVMj6atI,650
99
99
  irie/apps/prediction/metrics.py,sha256=Zh1utUZTGddQEVn4e1rLO74tbIz7bVvZli8sgmuB_X0,1410
100
- irie/apps/prediction/models.py,sha256=hmgSXRgUovuekHCxqPaqSiN7WNNjY7iAz9gqOOlELLo,2841
100
+ irie/apps/prediction/models.py,sha256=zYNY_brXriuaJATwpndMtiveK-ejxwKW-0ZNaIQjDL0,2925
101
101
  irie/apps/prediction/predictor.py,sha256=-x_4kHWnfUxiX2aQfbl3dsbVAG4lRKAFbo1CqfZNCIc,831
102
- irie/apps/prediction/urls.py,sha256=_v7CdR97c7eMcsilURYP0c1QCzxBNnex0lbcTfWrpOI,1028
103
- irie/apps/prediction/views.py,sha256=v34Kas6pzRPf1GQQ1fG0s4zVqPZYw9LiPIEVjz4E9d4,9250
102
+ irie/apps/prediction/urls.py,sha256=V41EjswrZ4FGPMetHzxkL4m0wNJvPEuV0UrwxLWqgkA,1012
103
+ irie/apps/prediction/views.py,sha256=4KbDlGBWBDP5BawrPkIZRzSd4f-g2PqLtqSyUjH5j2k,10071
104
104
  irie/apps/prediction/views_api.py,sha256=DJzLYO5ouPOWkkZJNZxZJzxC3TROKJ-L6Z2IC1NMuFQ,6888
105
105
  irie/apps/prediction/migrations/0001_initial.py,sha256=-0GWd2vUUAzSPfptccAJ3raI3UD4Xj9H0E5EJ7xN0Ek,1428
106
106
  irie/apps/prediction/migrations/0002_alter_predictormodel_protocol.py,sha256=nrQvuZ1eRR7fR17IjdS0Xyw14y9DpE6HkG2-h7HQ_zA,560
@@ -112,7 +112,7 @@ irie/apps/prediction/migrations/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm
112
112
  irie/apps/prediction/runners/__init__.py,sha256=pur6vJ5zXwjyTxl7p0TBJ8dt-2h-4Ty65KPmtRM8lyQ,2308
113
113
  irie/apps/prediction/runners/hazus.py,sha256=sWQDDmwN82wKSHW9EGx46JOOPo_IN2CTK7RF23Rx4c4,31207
114
114
  irie/apps/prediction/runners/ssid.py,sha256=_5TZrbWtt-Mid-PXiUu33QOQ7rUK2FLkyAg_B957RLc,18811
115
- irie/apps/prediction/runners/opensees/__init__.py,sha256=jHiQW2_UrmxL6EhIe2Y5sH5--l7Y0GNbpWmaofyB4Xo,23040
115
+ irie/apps/prediction/runners/opensees/__init__.py,sha256=hjyKM2ZGh6eMNgfpic2tTVAWtx5yB1z_HV2CjkSix2I,23195
116
116
  irie/apps/prediction/runners/opensees/metrics.py,sha256=HU1V0RYQDXrhTcHqwpnU2KOSl4UPNo9S6QP3sz2VcUY,6428
117
117
  irie/apps/prediction/runners/opensees/utilities.py,sha256=1cajnV6gWkJ5obYixfbHZKwxi1ECpR0sBWquAAGhseE,9032
118
118
  irie/apps/prediction/runners/opensees/xmlutils.py,sha256=Q3i5L0Dp_5nRsKRGMr-m_bS03Mxa36Ujb-RvwAmResc,7510
@@ -140,6 +140,7 @@ irie/apps/site/templatetags/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMp
140
140
  irie/apps/site/templatetags/indexing.py,sha256=Jc6onTb6xePy4WuKosaKI6xe78TnC1Xf0wy9LcMBqCQ,126
141
141
  irie/apps/static/favicon.ico,sha256=1Cq5RpjwmQAAIxISUwdTbJARATvNQKeVd0RI1_eC6Yw,410598
142
142
  irie/apps/static/sitemap.xml,sha256=3WXCikx75aEfxH58XlKidzkQJSQNq4ALSBGRsqn_96Q,316
143
+ irie/apps/static/assets/content_images/brace/ForceFrame.png,sha256=nHBTBTGmPpU6C-CQEyACLUG9g7OEG3Wn_LGaiTv6e4Y,588336
143
144
  irie/apps/static/assets/content_images/brace/mdof.svg,sha256=SJpy7HpeTceur85_wmH1FpPFHXl7JZIGGo4NjZnjBwM,50206
144
145
  irie/apps/static/assets/content_images/brace/opensees.jpg,sha256=ZX1lhOLNBfGo1lgTLTvX2O5rgPhlzhcld75KvTSNTTU,50369
145
146
  irie/apps/static/assets/content_images/brace/sdof.svg,sha256=czlgN6GGodtOIsr-UARUoKMooeh0r33ewL_c_wbNfJ8,8415
@@ -250,7 +251,7 @@ irie/apps/static/assets/inventory/ll89735.svg,sha256=5U8IN4IAO1foB6XhQHiaGAsiUgd
250
251
  irie/apps/static/assets/inventory/ll89736.svg,sha256=NqbRFY_-8s5dXV6ECthYBkUgVy9-BVMQfyXDpsFZmlQ,1098734
251
252
  irie/apps/static/assets/inventory/ll89973.svg,sha256=vGQCrGj1fSzkpDeeSn8pw4Fvniycce7Ubkoa7TK84Eg,1092572
252
253
  irie/apps/static/assets/js/787.545aecf5.chunk.js,sha256=M1ZHjaLV3MTw76zYIC5eJcpQvQNytXUIdbsx1P-Q2Dw,4599
253
- irie/apps/static/assets/js/brace.js,sha256=yKJ6DwgYMrKL8szRmgGVS7IOhptyYwvAvYflPoOMyhc,35724
254
+ irie/apps/static/assets/js/brace.js,sha256=0jeaOGdAKjNyefVsLspnu9m6tSbnB0bi_n0dSWcTFQ8,35724
254
255
  irie/apps/static/assets/js/d3.v4.min.js,sha256=hYXbQJK4qdJiAeDVjjQ9G0D6A0xLnDQ4eJI9dkm7Fpk,221957
255
256
  irie/apps/static/assets/js/events_api.js,sha256=SapCoJwzIaEMeaS-oZUyDd7U6GSRYEYGitRb2Jz7hR0,4643
256
257
  irie/apps/static/assets/js/events_page.js,sha256=qu9ah1hclAp7w9z1QO1AmzcKJCQ4avcwuJUDMzTUhk0,10285
@@ -423,19 +424,20 @@ irie/apps/templates/networks/networks.js,sha256=KsTnwiPXv0WYTd3GiejHz1gWiBkOVfIu
423
424
  irie/apps/templates/networks/styled_inputs.html,sha256=4IqtA4oQw6zAc2oypEYspIn_dS0syvVtZvkshhj1Tco,118
424
425
  irie/apps/templates/prediction/asset-predictors.html,sha256=JdaQHTVtRyYttUl1esZi34CqRiK6hiMGrIfOxxr6NPA,4823
425
426
  irie/apps/templates/prediction/create-mdof.html,sha256=QVuZGz3E5iwYvOQk_kkitAt5qxfP5zmr2zyVQBWKQzs,4602
426
- irie/apps/templates/prediction/create-model.html,sha256=QjgeuEqSCDFbJlGK3PY6LePia3vJXKqD6g2TKdpIeE4,3237
427
+ irie/apps/templates/prediction/create-model.html,sha256=MmP7HoWfDr0z22euwAMTMUGcEEZZqXGtLF-eGZeQI7I,3954
427
428
  irie/apps/templates/prediction/new-runner.html,sha256=7gMXrrD-CylMDUelIltB9JnmnqlBr4euqktTfRFnhdU,1586
428
429
  irie/apps/templates/prediction/predictor-profile.html,sha256=PWUQAOAAWQP_Ak2D-cQP5PoVjyLiz6Kc8lhNLlffnZk,1253
429
- irie/apps/templates/prediction/xara-profile.html,sha256=S1paPUML3le37pPggRFoPBixwt2zulufb0B6hS5ogcU,8842
430
+ irie/apps/templates/prediction/xara-profile.html,sha256=pzH18TDgxLaFjhtB_XRmsN-IQTV_3qbDR2zjHNEgLTM,5019
430
431
  irie/apps/templates/prediction/hazus/event.html,sha256=vcmQKfb-Gww5sd-kn6b2QL3llRrfQFv8mafVNNxTHrY,841
431
432
  irie/apps/templates/prediction/hazus/history.html,sha256=zvnwP0gxSV9JNBbYACnKlMLB9iD7hGUbdkZ6kfJtBik,136
432
433
  irie/apps/templates/prediction/hazus/history.js,sha256=blHRXzlEfMBCezPE-2dZCpt2rVgTiGHkYlY1t-clOE8,1101
433
- irie/apps/templates/prediction/viewer/veux-viewer.js,sha256=gPhTyPupjV_RD8t86Lc2wGZsY68TLuv0WjzyaDpRsfI,6189
434
+ irie/apps/templates/prediction/veux/navigator.html,sha256=Ev8iv-sQ2W4RpPY_yH_KsjNeKAN5PIiIuBWcZ1Orcew,4914
435
+ irie/apps/templates/prediction/veux/navigator.js,sha256=JWiDxupaqhtMLzOd82tuGoxoFdLpmZ3lgQ8-uIv6nbc,6181
434
436
  irie/apps/templates/sensors/render-sensors.js,sha256=u05VQ7dBDhUMsTYs0_xgdltA2V5DAqenVKgYhAlBxw0,5570
435
437
  irie/apps/templates/site/about.html,sha256=5hS5taj3XF-F8z-uIn53ZFXVHVS4apLRMg39OyvMvRs,610
436
438
  irie/apps/templates/site/asset_map.html,sha256=rnTjeYMc8NESIo6Uuq8fgZ_xcKNuKdt4zcqoUTDI8Xg,387
437
439
  irie/apps/templates/site/components-forms.html,sha256=FKOiR-3e9iw-xOHeaP2RB3O2gP10R-Mt8wdXfb1rDBQ,13865
438
- irie/apps/templates/site/index.html,sha256=bFBuqpe74Xix0Zg4qE-gmtlYsgvJFDm-j979Ms1wAIk,16983
440
+ irie/apps/templates/site/index.html,sha256=rDnQp8PxaLgVKGklG1DQie6y6vX9-9QpyT74pge82qE,17428
439
441
  irie/apps/templates/site/json-form.html,sha256=ZrRWy5xnGBOqG51b6mdVGI0Io5X1z47DTFB9wW6ZQYA,1785
440
442
  irie/apps/templates/site/page-400-sidebar.html,sha256=MimqQUyAgbgXG-oVJy1whHwrXmgf8NUgCqrwpUHCZ0s,1502
441
443
  irie/apps/templates/site/page-400.html,sha256=2X9hGL7mCPGqgQUEr86vz6neO_Z--w0RjIzyQsGNBIE,981
@@ -495,8 +497,8 @@ irie/init/management/commands/make_asset.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm
495
497
  irie/pull/nbi.py,sha256=KpBjJ9GEU72Qk1t4bGN9cg0QBeVJ8k9XcI3Y1oSgIR0,11478
496
498
  irie/rest/__main__.py,sha256=6Nf_-Rr9zGmMyp_wqCFDO7ls9QPnPd9UyUgN17rIGYw,3680
497
499
  irie/usgs/__main__.py,sha256=HiSvPn5IW5IqRiCk1qRRq5dCy3-7iISw7v1P_w2rLrk,5049
498
- irie-0.0.54.dist-info/METADATA,sha256=MyIZNsL0kY5XuOlGX6y-SXC46Lf6SYuqCfRnslHYyHk,3205
499
- irie-0.0.54.dist-info/WHEEL,sha256=ck4Vq1_RXyvS4Jt6SI0Vz6fyVs4GWg7AINwpsaGEgPE,91
500
- irie-0.0.54.dist-info/entry_points.txt,sha256=A_3h9wPBGfxGQ78_MGa-nO6Z0foxOYeAnIE47jxEztg,44
501
- irie-0.0.54.dist-info/top_level.txt,sha256=zVCxi5E2nkISZPzKq8VEhWe_dGuPcefLYV1tYqQdwlY,5
502
- irie-0.0.54.dist-info/RECORD,,
500
+ irie-0.0.55.dist-info/METADATA,sha256=BYa5IFlEM_6ZrCuKczXPymD4NOtsrbdW5rOhKwpyI2U,3205
501
+ irie-0.0.55.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
502
+ irie-0.0.55.dist-info/entry_points.txt,sha256=A_3h9wPBGfxGQ78_MGa-nO6Z0foxOYeAnIE47jxEztg,44
503
+ irie-0.0.55.dist-info/top_level.txt,sha256=zVCxi5E2nkISZPzKq8VEhWe_dGuPcefLYV1tYqQdwlY,5
504
+ irie-0.0.55.dist-info/RECORD,,
@@ -1,5 +1,5 @@
1
1
  Wheel-Version: 1.0
2
- Generator: setuptools (80.0.0)
2
+ Generator: setuptools (80.9.0)
3
3
  Root-Is-Purelib: true
4
4
  Tag: py3-none-any
5
5