Feature update

-- added search result page
This commit is contained in:
sairaj mote 2022-01-16 03:11:21 +05:30
parent b442f04cd7
commit 737b08f5b4
5 changed files with 95 additions and 34 deletions

View File

@ -3665,7 +3665,7 @@ customElements.define('tags-input', class extends HTMLElement {
e.preventDefault() e.preventDefault()
} }
if (e.target.value.trim() !== '') { if (e.target.value.trim() !== '') {
if (e.key === 'Enter' || e.key === ',' || e.key === '/' || e.code === 'Space') { if (e.key === 'Enter' || e.key === ',' || e.key === '/') {
const tagValue = e.target.value.trim() const tagValue = e.target.value.trim()
if (this.tags.has(tagValue)) { if (this.tags.has(tagValue)) {
this.tagsWrapper.querySelector(`[data-value="${tagValue}"]`).animate([ this.tagsWrapper.querySelector(`[data-value="${tagValue}"]`).animate([

View File

@ -395,6 +395,7 @@ ul {
} }
.logo { .logo {
position: absolute;
color: inherit; color: inherit;
display: grid; display: grid;
align-items: center; align-items: center;
@ -653,6 +654,7 @@ main {
} }
theme-toggle { theme-toggle {
margin-left: auto;
padding: 0 0.5rem; padding: 0 0.5rem;
} }
@ -669,7 +671,8 @@ theme-toggle {
font-size: 0.9rem; font-size: 0.9rem;
} }
#latest_articles_list { #latest_articles_list,
#query_results_list {
margin: 1rem 0; margin: 1rem 0;
gap: 1.6rem; gap: 1.6rem;
} }
@ -701,6 +704,10 @@ theme-toggle {
gap: 0.3rem; gap: 0.3rem;
} }
#explore {
padding-top: 1.5rem;
}
#article { #article {
gap: 2rem 0; gap: 2rem 0;
padding-bottom: 3rem; padding-bottom: 3rem;
@ -713,6 +720,19 @@ theme-toggle {
padding-top: 1.5rem; padding-top: 1.5rem;
} }
#article_contributors {
flex-wrap: wrap;
gap: 0.3rem;
margin: 0.5rem 0 1rem 0;
}
.contributor {
font-size: 0.8rem;
background-color: rgba(var(--text-color), 0.06);
border-radius: 0.3rem;
padding: 0.3rem 0.5rem;
}
#dashboard { #dashboard {
height: -webkit-max-content; height: -webkit-max-content;
height: -moz-max-content; height: -moz-max-content;

2
css/main.min.css vendored

File diff suppressed because one or more lines are too long

View File

@ -382,6 +382,7 @@ ul {
cursor: pointer; cursor: pointer;
} }
.logo { .logo {
position: absolute;
color: inherit; color: inherit;
display: grid; display: grid;
align-items: center; align-items: center;
@ -610,6 +611,7 @@ main {
width: 100%; width: 100%;
} }
theme-toggle { theme-toggle {
margin-left: auto;
padding: 0 0.5rem; padding: 0 0.5rem;
} }
@ -631,7 +633,8 @@ theme-toggle {
font-size: 0.9rem; font-size: 0.9rem;
} }
#latest_articles_list { #latest_articles_list,
#query_results_list {
margin: 1rem 0; margin: 1rem 0;
gap: 1.6rem; gap: 1.6rem;
} }
@ -662,6 +665,10 @@ theme-toggle {
} }
} }
#explore {
padding-top: 1.5rem;
}
#article { #article {
gap: 2rem 0; gap: 2rem 0;
padding-bottom: 3rem; padding-bottom: 3rem;
@ -673,6 +680,17 @@ theme-toggle {
grid-template-columns: minmax(0, 1fr); grid-template-columns: minmax(0, 1fr);
padding-top: 1.5rem; padding-top: 1.5rem;
} }
#article_contributors {
flex-wrap: wrap;
gap: 0.3rem;
margin: 0.5rem 0 1rem 0;
}
.contributor {
font-size: 0.8rem;
background-color: rgba(var(--text-color), 0.06);
border-radius: 0.3rem;
padding: 0.3rem 0.5rem;
}
#dashboard { #dashboard {
height: max-content; height: max-content;

View File

@ -238,8 +238,10 @@
</section> </section>
</article> </article>
<article id="explore" class="page page-layout hide-completely"> <article id="explore" class="page page-layout hide-completely">
<h1>Explore</h1> <section class="flex direction-column">
<div id="query_results_list" class="grid"></div> <h1 id="explore_heading">Explore</h1>
<div id="query_results_list" class="grid"></div>
</section>
</article> </article>
<article id="article" class="page page-layout hide-completely"> <article id="article" class="page page-layout hide-completely">
<section class="hero-section"> <section class="hero-section">
@ -588,11 +590,7 @@
let params = {} let params = {}
let searchParams let searchParams
if (targetPage === '') { if (targetPage === '') {
if (typeof myFloID === "undefined") { pageId = 'main_page'
pageId = 'landing'
} else {
pageId = 'main_page'
}
} else { } else {
if (targetPage.includes('/')) { if (targetPage.includes('/')) {
if (targetPage.includes('?')) { if (targetPage.includes('?')) {
@ -610,7 +608,6 @@
pageId = targetPage pageId = targetPage
} }
} }
if (typeof myFloID === "undefined" && !(['sign_up', 'sign_in', 'loading', 'landing'].includes(pageId))) return
if (searchParams) { if (searchParams) {
const urlSearchParams = new URLSearchParams('?' + searchParams); const urlSearchParams = new URLSearchParams('?' + searchParams);
params = Object.fromEntries(urlSearchParams.entries()); params = Object.fromEntries(urlSearchParams.entries());
@ -638,11 +635,11 @@
break; break;
case 'article': case 'article':
targetPage = 'article' targetPage = 'article'
renderArticle(params.articleID) await renderArticle(params.articleID)
break; break;
case 'explore': case 'explore':
targetPage = 'explore' targetPage = 'explore'
renderArticle(params.articleID) renderExplorePage(params)
break; break;
case 'dashboard': case 'dashboard':
targetPage = 'dashboard' targetPage = 'dashboard'
@ -777,7 +774,12 @@
} }
const getArticles = async () => { const getArticles = async () => {
await floCloudAPI.requestObjectData('articles') await Promise.all([
floCloudAPI.requestObjectData('articles'),
floCloudAPI.requestObjectData('articlesContent')
])
delete floGlobals.appObjects.articlesContent
showPage(window.location.hash, { firstLoad: true })
} }
function getArrayOfObj(obj) { function getArrayOfObj(obj) {
@ -809,13 +811,33 @@
} }
async function renderArticle(articleID) { async function renderArticle(articleID) {
await floCloudAPI.requestObjectData(articleID) const allArticles = await compactIDB.readData('appObjects', 'articlesContent')
const articleBody = floGlobals.appObjects[articleID] const { title, published, readTime, contributors } = floGlobals.appObjects.articles[articleID]
const { title, published, readTime } = floGlobals.appObjects.articles[articleID]
getRef('article_title').textContent = title getRef('article_title').textContent = title
getRef('published_time').textContent = getFormattedTime(published, 'date-only') getRef('published_time').textContent = getFormattedTime(published, 'date-only')
getRef('reading_time').textContent = `${readTime} Min read` getRef('reading_time').textContent = `${readTime} Min read`
getRef('article_body').innerHTML = articleBody getRef('article_body').innerHTML = allArticles[articleID]
const frag = document.createDocumentFragment()
contributors.forEach(id => {
frag.append(createElement('div', {
textContent: id,
className: 'contributor'
}))
})
getRef('article_contributors').innerHTML = ''
getRef('article_contributors').append(frag)
}
function renderExplorePage(params) {
const { type, query } = params
const frag = document.createDocumentFragment()
const options = (type === 'category') ? { keys: ['category'] } : { keys: ['title', 'category', 'tags'], threshold: 0.3 }
const fuse = new Fuse(getArrayOfObj(floGlobals.appObjects.articles).sort((a, b) => b.published - a.published), options)
const searchResult = fuse.search(query).map(v => v.item)
searchResult.forEach(articleDetail => frag.append(render.articleCard(articleDetail)))
getRef('explore_heading').textContent = `${type === 'category' ? 'Explore' : 'Related to'} ${query}`
getRef('query_results_list').innerHTML = ''
getRef('query_results_list').append(frag)
} }
async function renderPublishingRequests() { async function renderPublishingRequests() {
@ -834,12 +856,12 @@
if (e.target.closest('.publish-button')) { if (e.target.closest('.publish-button')) {
const button = e.target.closest('.publish-button'); const button = e.target.closest('.publish-button');
const vc = button.closest('.request-card').dataset.vc; const vc = button.closest('.request-card').dataset.vc;
const { message: { articleID, category, content, title, tags, readTime }, vectorClock } = floGlobals.generalData[`publishing_requests|${floGlobals.adminID}|${floGlobals.application}`][vc]; const { message: { articleID, category, content, contributors, title, tags, readTime }, vectorClock } = floGlobals.generalData[`publishing_requests|${floGlobals.adminID}|${floGlobals.application}`][vc];
const isPublished = floGlobals.appObjects['articles'].hasOwnProperty(articleID) const isPublished = floGlobals.appObjects['articles'].hasOwnProperty(articleID)
getConfirmation(`${isPublished ? 'Update' : 'Publish'} article?`).then(res => { getConfirmation(`${isPublished ? 'Update' : 'Publish'} article?`).then(res => {
if (res) { if (res) {
floGlobals.appObjects['publishedVc'][vectorClock] = true floGlobals.appObjects['publishedVc'][vectorClock] = true
floGlobals.appObjects[articleID] = content floGlobals.appObjects.articlesContent[articleID] = content
if (isPublished) { if (isPublished) {
floGlobals.appObjects['articles'][articleID]['updated'] = Date.now(); floGlobals.appObjects['articles'][articleID]['updated'] = Date.now();
} else { } else {
@ -847,13 +869,14 @@
floGlobals.appObjects['articles'][articleID]['published'] = Date.now(); floGlobals.appObjects['articles'][articleID]['published'] = Date.now();
} }
floGlobals.appObjects['articles'][articleID].category = category floGlobals.appObjects['articles'][articleID].category = category
floGlobals.appObjects['articles'][articleID].contributors = contributors
floGlobals.appObjects['articles'][articleID].title = title floGlobals.appObjects['articles'][articleID].title = title
floGlobals.appObjects['articles'][articleID].tags = tags floGlobals.appObjects['articles'][articleID].tags = tags
floGlobals.appObjects['articles'][articleID].readTime = readTime floGlobals.appObjects['articles'][articleID].readTime = readTime
Promise.all([ Promise.all([
floCloudAPI.updateObjectData('articles'), floCloudAPI.updateObjectData('articles'),
floCloudAPI.updateObjectData('publishedVc'), floCloudAPI.updateObjectData('publishedVc'),
floCloudAPI.resetObjectData(articleID) floCloudAPI.updateObjectData('articlesContent'),
]).then(() => { ]).then(() => {
notify(`${isPublished ? 'Updated' : 'Published'} article`, 'success') notify(`${isPublished ? 'Updated' : 'Published'} article`, 'success')
button.closest('.request-card').remove() button.closest('.request-card').remove()
@ -886,7 +909,7 @@
keys: ['title', 'tags', 'category'], keys: ['title', 'tags', 'category'],
threshold: 0.3 threshold: 0.3
} }
const fuse = new Fuse(getArrayOfObj(floGlobals.appObjects.articles), options) const fuse = new Fuse(getArrayOfObj(floGlobals.appObjects.articles).sort((a, b) => b.published - a.published), options)
const searchResult = fuse.search(searchKey).map(v => v.item) const searchResult = fuse.search(searchKey).map(v => v.item)
getRef('search_suggestions').innerHTML = '' getRef('search_suggestions').innerHTML = ''
if (searchResult.length) { if (searchResult.length) {
@ -919,24 +942,24 @@
} }
}, 100)) }, 100))
getRef('search_articles').addEventListener('keyup', e => {
if (e.target.value.trim() !== '' && e.code === 'Enter') {
location.hash = `#/explore?type=search&query=${e.target.value.trim()}`
e.target.value = ''
}
})
function getSignedIn() { function getSignedIn() {
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
if (window.location.hash.includes('sign_in') || window.location.hash.includes('sign_up')) {
showPage(window.location.hash)
} else {
showPage('landing', { isPreview: location.hash.includes('preview') })
}
getRef('sign_in_button').onclick = () => { getRef('sign_in_button').onclick = () => {
resolve(getRef('private_key_field').value.trim()) resolve(getRef('private_key_field').value.trim())
getRef('private_key_field').value = '' getRef('private_key_field').value = ''
showPage('loading')
} }
getRef('sign_up_button').onclick = () => { getRef('sign_up_button').onclick = () => {
resolve(getRef('generated_private_key').value.trim()) resolve(getRef('generated_private_key').value.trim())
getRef('generated_private_key').value = '' getRef('generated_private_key').value = ''
showPage('loading')
} }
}) })
} }
@ -962,15 +985,15 @@
getRef('user_flo_id').value = myFloID getRef('user_flo_id').value = myFloID
floGlobals.isSubAdmin = floGlobals.subAdmins.includes(myFloID) floGlobals.isSubAdmin = floGlobals.subAdmins.includes(myFloID)
if (floGlobals.isSubAdmin) { if (floGlobals.isSubAdmin) {
getRef('publishing_requests').addEventListener('click', handleRequestClick) getRef('publishing_requests').addEventListener('click', handleRequestClick);
document.querySelectorAll('.admin-option').forEach(elem => elem.classList.remove('hide-completely')) document.querySelectorAll('.admin-option').forEach(elem => elem.classList.remove('hide-completely'));
floGlobals.appObjects.articlesContent = await compactIDB.readData('appObjects', 'articlesContent')
} else { } else {
getRef('publishing_requests').removeEventListener('click', handleRequestClick) getRef('publishing_requests').removeEventListener('click', handleRequestClick)
document.querySelectorAll('.admin-option').forEach(elem => elem.classList.add('hide-completely')) document.querySelectorAll('.admin-option').forEach(elem => elem.classList.add('hide-completely'))
} }
if (location.hash.includes('sign_in') || location.hash.includes('sign_up')) if (location.hash.includes('sign_in') || location.hash.includes('sign_up'))
location.hash = floGlobals.isSubAdmin ? '#/dashboard' : '#/home' location.hash = floGlobals.isSubAdmin ? '#/dashboard' : '#/home'
showPage(window.location.hash, { firstLoad: true })
console.log(result) console.log(result)
}).catch(error => console.error(error)) }).catch(error => console.error(error))
} }
@ -9930,7 +9953,7 @@
promises[i] = compactIDB.readAllData(loadData[i]) promises[i] = compactIDB.readAllData(loadData[i])
Promise.all(promises).then(results => { Promise.all(promises).then(results => {
for (var i = 0; i < loadData.length; i++) for (var i = 0; i < loadData.length; i++)
floGlobals[loadData[i]] = results[i] floGlobals[loadData[i]] = results[i];
resolve("Loaded Data from app IDB") resolve("Loaded Data from app IDB")
}).catch(error => reject(error)) }).catch(error => reject(error))
}) })