people tags #387
This commit is contained in:
parent
3493225dc5
commit
15c8f8f526
@ -26,6 +26,12 @@ else
|
||||
<p>@Html.Raw(Model.LastResult)</p>
|
||||
}
|
||||
|
||||
<script>
|
||||
// full catalog of every person except the subject ($Model.Person) - same shape/purpose as
|
||||
// allGeoLocations/allGeoPeople in ReviewEdits.cshtml/Editor.cshtml, see OtherPeopleJson
|
||||
var otherPeopleCatalog = @Html.Raw(Model.OtherPeopleJson);
|
||||
</script>
|
||||
|
||||
<div class="up-card">
|
||||
<form method="post" action="/User/SuggestNewPersonRelation?personId=@Model.Person.Id&Handler=Suggest">
|
||||
@Html.AntiForgeryToken()
|
||||
@ -34,13 +40,28 @@ else
|
||||
<tr>
|
||||
<td>خویشاوند یا نامبردۀ دیگر:</td>
|
||||
<td>
|
||||
<select asp-for="OtherPersonId">
|
||||
<option value="0">— انتخاب کنید —</option>
|
||||
@foreach (var p in Model.OtherPeople)
|
||||
{
|
||||
<option value="@p.Id">@p.Name</option>
|
||||
}
|
||||
</select>
|
||||
<div class="up-autocomplete-wrap">
|
||||
<input type="text" id="other-person-search" autocomplete="off" placeholder="نام خویشاوند یا نامبردۀ دیگر را تایپ کنید..."
|
||||
value="@(Model.OtherPersonId != 0 ? (Model.OtherPeople ?? new List<RMuseum.Models.Ganjoor.GanjoorRelatedPerson>()).Where(p => p.Id == Model.OtherPersonId).Select(p => p.Name).FirstOrDefault() : null)" />
|
||||
<input type="hidden" asp-for="OtherPersonId" />
|
||||
<div id="other-person-results" class="up-autocomplete-results" style="display:none;"></div>
|
||||
</div>
|
||||
<p class="up-hint"><small>
|
||||
اگر بیش از یک نامبرده با نام مشابه در فهرست باشد (مثلاً شخصیتهای شاهنامه)، پس از انتخاب از روی سال تولد/وفات مطمئن شوید
|
||||
یا با کلیک روی 👁 اطلاعات کامل آن را ببینید.
|
||||
</small></p>
|
||||
<script>
|
||||
setupPersonAutocomplete(
|
||||
document.getElementById('other-person-search'),
|
||||
document.getElementById('OtherPersonId'),
|
||||
document.getElementById('other-person-results'),
|
||||
otherPeopleCatalog,
|
||||
null,
|
||||
function (typedText) {
|
||||
upToast('این نامبرده در فهرست نیست. طرف دیگر یک رابطه باید از قبل تعریفشده باشد؛ برای افزودن یک نامبردۀ تازه، ابتدا او را بهطور جدا از صفحهٔ ویرایشگر تعریف کنید.', 'error');
|
||||
}
|
||||
);
|
||||
</script>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
|
||||
@ -40,6 +40,21 @@ namespace GanjooRazor.Areas.User.Pages
|
||||
|
||||
public List<GanjoorRelatedPerson> OtherPeople { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// camelCase JSON of OtherPeople (id/name/birthYearInLHijri/deathYearInLHijri only), used
|
||||
/// client-side for the search-as-you-type person picker replacing the old plain <select>
|
||||
/// (see setupPersonAutocomplete in bk.js) - same shape/purpose as
|
||||
/// ReviewEdits.cshtml.cs's/Editor.cshtml.cs's AllPeopleJson. The catalog can legitimately
|
||||
/// contain more than one person sharing the same name (e.g. Shahnameh figures), so the
|
||||
/// picker shows birth/death years as a disambiguating subtitle and a "👁 view full info" link
|
||||
/// once a candidate is picked.
|
||||
/// </summary>
|
||||
public string OtherPeopleJson =>
|
||||
JsonConvert.SerializeObject(
|
||||
(OtherPeople ?? new List<GanjoorRelatedPerson>()).Select(p => new { p.Id, p.Name, p.BirthYearInLHijri, p.DeathYearInLHijri }),
|
||||
new JsonSerializerSettings { ContractResolver = new Newtonsoft.Json.Serialization.CamelCasePropertyNamesContractResolver() }
|
||||
);
|
||||
|
||||
[BindProperty]
|
||||
public int OtherPersonId { get; set; }
|
||||
|
||||
|
||||
@ -2885,6 +2885,35 @@ function setupLocationAutocomplete(searchInput, hiddenInput, resultsBox, locatio
|
||||
function setupPersonAutocomplete(searchInput, hiddenInput, resultsBox, people, onSelect, onNotFound) {
|
||||
var MAX_RESULTS = 12;
|
||||
|
||||
// The birth/death-year subtitle in each dropdown row below helps tell two same-named people
|
||||
// apart (the Shahnameh/mythological person catalog in particular has several), but it's not
|
||||
// always enough - two people can share both a name and era, or the subtitle can be blank if
|
||||
// neither year is recorded. So once a pick is made (or the field already carries one from the
|
||||
// server, e.g. correcting an existing suggestion), show a small "👁 view full info" link right
|
||||
// next to the box, opening that exact person's full profile (PersonWindow.open) so whoever is
|
||||
// picking - or a moderator reviewing someone else's pick - can be sure it's the right person,
|
||||
// not just one with a matching name/years.
|
||||
var viewLink = document.createElement('a');
|
||||
viewLink.href = 'javascript:void(0)';
|
||||
viewLink.className = 'up-icon-btn';
|
||||
viewLink.title = 'مشاهدهٔ اطلاعات کامل این شخصیت';
|
||||
viewLink.setAttribute('aria-label', 'مشاهدهٔ اطلاعات کامل این شخصیت');
|
||||
viewLink.style.marginRight = '4px';
|
||||
viewLink.textContent = '👁';
|
||||
viewLink.addEventListener('click', function () {
|
||||
var id = parseInt(hiddenInput.value, 10);
|
||||
if (id) PersonWindow.open(id);
|
||||
});
|
||||
if (searchInput.parentNode) {
|
||||
searchInput.parentNode.insertBefore(viewLink, searchInput.nextSibling);
|
||||
}
|
||||
|
||||
function updateViewLink() {
|
||||
var id = parseInt(hiddenInput.value, 10);
|
||||
viewLink.style.display = id ? 'inline' : 'none';
|
||||
}
|
||||
updateViewLink(); // the hidden input may already carry a value set by the server (editing/correcting an existing pick)
|
||||
|
||||
function hide() {
|
||||
resultsBox.style.display = 'none';
|
||||
resultsBox.innerHTML = '';
|
||||
@ -2906,6 +2935,7 @@ function setupPersonAutocomplete(searchInput, hiddenInput, resultsBox, people, o
|
||||
function selectPerson(p) {
|
||||
searchInput.value = p.name;
|
||||
hiddenInput.value = String(p.id);
|
||||
updateViewLink();
|
||||
hide();
|
||||
if (onSelect) onSelect(p);
|
||||
}
|
||||
@ -2953,6 +2983,7 @@ function setupPersonAutocomplete(searchInput, hiddenInput, resultsBox, people, o
|
||||
|
||||
searchInput.addEventListener('input', function () {
|
||||
hiddenInput.value = ''; // typing invalidates whatever was previously selected
|
||||
updateViewLink();
|
||||
var typed = searchInput.value.trim();
|
||||
if (typed == '') {
|
||||
hide();
|
||||
|
||||
Loading…
Reference in New Issue
Block a user